Here SDK - Change map location - java

This is the sample code from Here API. But the problem I have is that the initial location where the map is loaded is wrong. What I need is for the map to be displayed where you are.
What is the method that modifies the position of the map?
private MapViewLite mapView;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// Get a MapViewLite instance from the layout.
mapView = findViewById(R.id.map_view);
mapView.onCreate(savedInstanceState);
}
private void loadMapScene() {
// Load a scene from the SDK to render the map with a map style.
mapView.getMapScene().loadScene(MapStyle.NORMAL_DAY, new MapScene.LoadSceneCallback() {
#Override
public void onLoadScene(#Nullable MapScene.ErrorCode errorCode) {
if (errorCode == null) {
mapView.getCamera().setTarget(new GeoCoordinates(52.530932, 13.384915));
mapView.getCamera().setZoomLevel(14);
} else {
Log.d(TAG, "onLoadScene failed: " + errorCode.toString());
}
}
});
}

This is the piece of code that hard codes the position:
mapView.getCamera().setTarget(new GeoCoordinates(52.530932, 13.384915))
Instead, set the coordinates to be the user's click. In order to do so, you will need to surround that piece of code with an onTouch() listener and check the action of the user. I'll use an ImageView as an example. So something like this:
imageView.setOnTouchListener(new View.OnTouchListener() {
#Override
public boolean onTouch(View v, MotionEvent event) {
if (event.getAction() == MotionEvent.ACTION_DOWN){
//whatever you want to do
//to fetch the coordinates of the user's click use event.getX() and event.getY()
}
return true;
}
});

Related

How can you change ViewPager2 position inside the ViewPager2Adapter?

I programmed a Vocabulary Trainer with Vocabulary Cards. The Vocabulary Cards are Entries in a Room Database created from an asset. I am displaying these Vocabulary Cards with ViewPager2 in an Activity. I have a 'correct' and a 'false' button and when the user clicks on either, I want to update the Vocabulary Card (-> The entry in the sqlite database) and automatically swipe to the next item of the ViewPager2.
If I implement the buttons in the ViewPager2Adapter, I can't find a way to change the position of the ViewPager2. If I implement the buttons in the activity the sqlite entry does not update properly (After it updates the entry, the activity is constantly refreshed, it seems like it never the leaves the OnClick methode of the button).
So is it possible to change the position of ViewPager2 from inside the ViewPager2Adpater?
Thanks for your help!
That is the relevant code if I have the buttons in my ViewPager2Adapter. Here I don't know how to change the position of the ViewPager2
public void onBindViewHolder(#NonNull #NotNull ViewHolder holder, int position) {
VocabularyCard vocabularyCard = currentCards.get(position);
holder.btn_correct.setOnClickListener(view -> {
vocabularyViewModel.updateSingleVocabularyCard(vocabularyCard);
});
holder.btn_false.setOnClickListener(v15 -> {
vocabularyViewModel.updateSingleVocabularyCard(vocabularyCard);
});
That is the relevant code if I have the buttons in the Activity. Here the update function triggers an infinite updating of the Activity:
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_test);
initAll();
btn_correct_2.setOnClickListener(view -> {
int currentPos = viewpager2.getCurrentItem();
vocabularyViewModel.getCurrentCards().observe(this, vocabularyCards -> {
if (vocabularyCards.size() == currentPos){
Intent intent = new Intent(TestActivity.this, MainActivity.class);
startActivity(intent);
}else {
viewpager2.setCurrentItem(currentPos + 1);
}
VocabularyCard vocabularyCard = vocabularyCards.get(currentPos);
vocabularyViewModel.updateSingleVocabularyCard(vocabularyCard);
});
});
btn_false_2.setOnClickListener(view -> {
int currentPos = viewpager2.getCurrentItem();
vocabularyViewModel.getCurrentCards().observe(this, vocabularyCards -> {
if (vocabularyCards.size() == currentPos){
Intent intent = new Intent(TestActivity.this, MainActivity.class);
startActivity(intent);
}else {
viewpager2.setCurrentItem(currentPos + 1);
}
VocabularyCard vocabularyCard = vocabularyCards.get(currentPos);
vocabularyViewModel.updateSingleVocabularyCard(vocabularyCard);
});
});
Objects.requireNonNull(getSupportActionBar()).setTitle(getResources().getString(R.string.learn_new_words));
LiveData<List<VocabularyCard>> allNewCards = vocabularyViewModel.getAllNewCards(goal);
allNewCards.observe(this, vocabularyCards -> vocabularyViewModel.setCurrentCards(vocabularyCards));
vocabularyViewModel.getCurrentCards().observe(this, vocabularyCards -> {
viewPager2Adapter.setCurrentCards(vocabularyCards);
viewpager2.setAdapter(viewPager2Adapter);
viewpager2.registerOnPageChangeCallback(new ViewPager2.OnPageChangeCallback() {
#Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
super.onPageScrolled(position, positionOffset, positionOffsetPixels);
}
#Override
public void onPageSelected(int position) {
super.onPageSelected(position);
}
#Override
public void onPageScrollStateChanged(int state) {
super.onPageScrollStateChanged(state);
}
});
});
The update function in the Room DAO is straightforward:
#Update
void updateSingleVocabularyCard(VocabularyCard vocabularyCard);
I left out all the code that is not relevant.
There are several ways to propagate an event from the adapter to the activity where you manage your cards using ViewPager2. Let's have a look how it can be done either using an interface or using the same view model. But in any case I strongly recommend you to update your database in a background thread to prevent any possible UI lags.
1. Using an interface
This option is more flexible since you can propagate events as well as pass data as parameters. You can also reuse this interface for other cases. As far as I See you have a holder that has 2 buttons for the users to make choices. So our event here would be something like ChoiceEventListener, let's call this interface like so. Then you'd have to add a method to handle this event from within anywhere you wanna hear this event, and let's call its handle method onChoice(). Finally we would need a variable to indicate what the choice is. Now that ready to implement, let's write the new interface...
ChoiceEventListener.java
public interface ChoiceEventListener {
void onChoice(VocabularyCard vocabularyCard, boolean choice);
}
The next thing to do is to implement this interface where you want to listen to this event. In this case it is in your activity. There are 2 ways to do this:
You make your activity to inherit its methods using the implements keyword
YourActivity.java
public class YourActivity extends AppCompatActivity implements ChoiceEventListener {
// Use a background thread for database operations
private Executor executor = Executors.newSingleThreadExecutor();
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_test);
initAll();
// You must construct your adapter class with the listener
ViewPager2Adapter adapter = new ViewPager2Adapter(/* Other params... */, this);
}
#Override
public void onChoice(VocabularyCard vocabularyCard, boolean choice) {
if(choice) {
// User pressed the correct button
}
else {
// User pressed the false button
}
// Update card in the background
executor.execute(()-> vocabularyViewModel.updateSingleVocabularyCard(vocabularyCard));
}
}
You can implement it as an anonymous function
YourActivity.java
public class YourActivity extends AppCompatActivity {
// Use a background thread for database operations
private Executor executor = Executors.newSingleThreadExecutor();
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_test);
initAll();
// You must construct your adapter class with the listener
ViewPager2Adapter adapter = new ViewPager2Adapter(/* Other params... */, (vocabularyCard, choice) -> {
if(choice) {
// User pressed the correct button
}
else {
// User pressed the false button
}
// Update card in the background
executor.execute(()-> vocabularyViewModel.updateSingleVocabularyCard(vocabularyCard));
});
}
}
Finally the ViewPager2Adapter class implementation would be something like this:
ViewPager2Adapter.java
public class ViewPager2Adapter extends RecyclerView.Adapter<ViewPager2ViewHolder> {
// Here is your listener to deliver the choice event to it
private final ChoiceEventListener listener;
// Constructor
public ViewPager2Adapter(/* Other params... */, ChoiceEventListener listener) {
/* Other inits */
this.listener = listener;
}
public void onBindViewHolder(#NonNull #NotNull ViewHolder holder, int position) {
VocabularyCard vocabularyCard = currentCards.get(position);
holder.btn_correct.setOnClickListener(view -> {
listener.onChoice(vocabularyCard, true); // true for correct
});
holder.btn_false.setOnClickListener(v15 -> {
listener.onChoice(vocabularyCard, false); // false for false :)
});
}
}
2. Use the ViewModel for inter-communication
In this option we use a LiveData object to make page switching. The only thing you need to know in your activity is the current position which you get it from the adapter class. Once you update it in the adapter, set the current position value in live data so that you can switch the page in your activity.
VocabularyViewModel.java
public class VocabularyViewModel extends ViewModel {
public MutableLiveData<Integer> mldCurrentPosition = new MutableLiveData<>(0);
}
YourActivity.java
public class YourActivity extends AppCompatActivity {
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_test);
initAll();
vocabularyViewModel.mldCurrentPosition().observe(this, currentPosition -> {
if(currenPosition == null) return; // ignore when null
viewpager2.setCurrentItem(currentPosition + 1);
}
}
}
Finally the ViewPager2Adapter class implementation would be something like this:
ViewPager2Adapter.java
public class ViewPager2Adapter extends RecyclerView.Adapter<ViewPager2ViewHolder> {
// Use a background thread for database operations
private Executor executor = Executors.newSingleThreadExecutor();
public void onBindViewHolder(#NonNull #NotNull ViewHolder holder, int position) {
VocabularyCard vocabularyCard = currentCards.get(position);
holder.btn_correct.setOnClickListener(view -> {
// Update card in the background
executor.execute(()-> vocabularyViewModel.updateSingleVocabularyCard(vocabularyCard));
// Then invoke switching to the next card
vocabularyViewModel.mldCurrentPosition.setValue(position + 1);
});
holder.btn_false.setOnClickListener(v15 -> {
// Update card in the background
executor.execute(()-> vocabularyViewModel.updateSingleVocabularyCard(vocabularyCard));
// Then invoke switching to the next card
vocabularyViewModel.mldCurrentPosition.setValue(position + 1);
});
}
}

Handaling single and double taps android kotlin

I want to display some toast when my button is clicked once and other toast when my button is clicked twice. Is there any built in library or do I need to implement custom logic?
You can Gesture Detector for detecting double taps.
final GestureDetector mDetector = new GestureDetector(getContext(), new GestureDetector.SimpleOnGestureListener {
#Override
public boolean onDown(MotionEvent e) {
return true;
}
#Override
public boolean onDoubleTap(MotionEvent e) {
return true;
}
});
For more details you can check this documentation.
Answer given by #TaranmeetSingh is absolutely right but there is a better solution. You can use this library to do it.
How to implement
Add this library -> implementation 'com.github.pedromassango:doubleClick:CURRENT-VERSION'(Version is given above).
Instead of using an onClickListenerObject for onClickListener, you can use DoubleClickListener Check the example below
Button btn = new Button(this);
btn.setOnClickListener( new DoubleClick(new DoubleClickListener() {
#Override
public void onSingleClick(View view) {
// Single tap here.
}
#Override
public void onDoubleClick(View view) {
// Double tap here.
}
});

when button click to activated mouse scroll in android

After button click to mouse scroll to be activted,then scroll up to value increment and scroll down to value decrement.Button inside code here not working, my sample code here,please analysis code to help me.
enter code here
public class MainActivity extends Activity {
Button button;
int x,f;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
button=(Button)findViewById(R.id.button1);
button.setOnTouchListener(new OnTouchListener() {
#SuppressLint("NewApi") #Override
public boolean onTouch(View arg0, MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_SCROLL:
if (event.getAxisValue(MotionEvent.AXIS_VSCROLL) < 0.0f)
//selectNext();
{
x=Integer.parseInt(button.getText().toString());
f=x+5;
button.setText(""+f);
}
else
{
x=Integer.parseInt(button.getText().toString());
f=x-5;
button.setText(""+f);
return true;
}
}
return false;
}
});
}
You can implement a ScrollView as your layout in your UI.
With this layout you can program your button to handle the click and use the ScrollView.scrollBy(x,y) function to do the necessary.

How can I check wether a (Google maps API) map has loaded?

I have started building an android application that focuses on a map from google-play-services-libs. When I start the app, it takes a while for the map to load from the gray grid to showing the map image.
I'd like to move/play around a bit with the map when it has fully loaded the part that is currently on screen. I have however been unable to find a way to programmatically check whether the map has loaded.
How can I achieve this?
In short:
From a instance of GoogleMap, how do I determine if it is actually showing something?
You can try using a OnCameraChangeListener on your map. The onCameraChange call will be called when the map's tiles are initially loaded.
this.map.setOnCameraChangeListener(new OnCameraChangeListener() {
public void onCameraChange(CameraPosition arg0) {
isMapReady = true;
map.setOnCameraChangeListener(null);
}
});
chckReady() function checks whether the map is ready or not
public class MapView extends android.support.v4.app.FragmentActivity {
private GoogleMap mMap;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.ui_settings_demo);
setUpMapIfNeeded();
}
#Override
protected void onResume() {
super.onResume();
setUpMapIfNeeded();
}
private void setUpMapIfNeeded() {
if (mMap == null) {
mMap = ((SupportMapFragment) getSupportFragmentManager().findFragmentById(R.id.map))
.getMap();
}
}
private boolean checkReady() {
if (mMap == null) {
return false;
}
}
}

Hide infowindow android map api v2

I was trying to close the default infowindow in the android map.
I used .hideInfoWindow() but nothing appends.
Thanks.
Change the return statement
#Override
public boolean onMarkerClick(Marker marker) {
return false;
}
(to)
#Override
public boolean onMarkerClick(Marker marker) {
return true;
}
Use
mapa.setOnInfoWindowClickListener(new GoogleMap.OnInfoWindowClickListener() {
#Override
public void onInfoWindowClick(Marker marker) {
marker.hideInfoWindow();
}
});
I hope that helps.
I assume you want to close the infowindow when you click the marker for the second time. It seems you need to keep track of the last clicked marker. I can't get it to work by simply checking if the clicked marker is currently shown and then close it, but this works nicely.
private Marker lastClicked;
private class MyMarkerClickListener implements OnMarkerClickListener {
#Override
public boolean onMarkerClick(Marker marker) {
if (lastClicked != null && lastClicked.equals(marker)) {
lastClicked = null;
marker.hideInfoWindow();
return true;
} else {
lastClicked = marker;
return false;
}
}
}
Setting the pin title and snippet to null, will result in no info window being displayed. This shall cover both cases when selecting and clicking a pin.

Categories

Resources