Autore Topic: Map v2, come gestire il tocco.  (Letto 1982 volte)

Offline casim

  • Nuovo arrivato
  • *
  • Post: 9
  • Respect: +2
    • Mostra profilo
  • Dispositivo Android:
    galaxy note 3, galaxy note 10.1
  • Sistema operativo:
    windows xp
Map v2, come gestire il tocco.
« il: 30 Luglio 2014, 15:47:30 CEST »
+2
Salve a tutti! Mi è capitato di avere la necessità di gestire il tocco sulle google map v2, in particolare l'action up. Purtroppo la classe non permette di utilizzare il metodo setOnTouchListener. Cercando online ho trovato delle soluzioni, che sebbene funzionino (le ho testate personalmente), secondo me sono troppo macchinose (qui qualche esempio How to detect a user pan/touch/drag on android map v2 | dimitar.me). Si contempla la creazione di 2 classi custom che estendono FrameLayout e SupportMapFragment (quest'ultima da aggiungere dinamicamente dentro la precedente), per poi implementare un'interfaccia, che risponda agli eventi di tocco.

Ma a me è venuta un'altra idea, e funziona alla grande! Basta aggiungere la mappa via xml all'interno di una android.gesture.GestureOverlayView, alla quale si può settare come trasparente il colore della gesture col seguente attributo:

android:gestureColor="#00000000"

Quindi si avrà il seguente pezzo di layout:
Codice (XML): [Seleziona]
<android.gesture.GestureOverlayView
       android:id="@+id/gesture"
       android:layout_width="match_parent"
       android:layout_height="wrap_content"
       android:gestureColor="#00000000">
       
        <com.google.android.gms.maps.MapView
                android:id="@+id/map"
                android:layout_width="match_parent"
                android:layout_height="match_parent" />
       
    </android.gesture.GestureOverlayView>

Fatto questo, nell'activity/fragment, basterà implementare sulla gestureOverlayView il listener "OnGestureListener" (tramite il metodo setOnGestureListener) e il gioco è fatto! Devono essere implementati 4 metodi:

onGestureStarted: può essere usato come actiondown;
onGesture: può essere usato come actionmove;
onGestureEnded: può essere usato come actionup;
onGestureCancel: non rientra negli scopi di questo tutorial.

Codice (Java): [Seleziona]
gesture.addOnGestureListener(new OnGestureListener(){

                        @Override
                        public void onGesture(GestureOverlayView overlay, MotionEvent event) {}

                        @Override
                        public void onGestureCancelled(GestureOverlayView overlay,
                                        MotionEvent event) {}

                        @Override
                        public void onGestureEnded(GestureOverlayView overlay,
                                        MotionEvent event) {}

                        @Override
                        public void onGestureStarted(GestureOverlayView overlay,
                                        MotionEvent event) {}});

Tutti i metodi passano come attributo un MotionEvent, dunque si può utilizzare come un OnTouchListener, forse un po' più limitato ma sufficiente per usi generici. Ovviamente il tocco non viene preso sulla mappa, ma sulla gestureOverlayView, ma se le dimensioni sono le stesse, il risultato non cambia!
Spero torni utile a qualcuno!

Offline Nicola_D

  • Utente storico
  • *****
  • Post: 2479
  • SBAGLIATO!
  • Respect: +323
    • Github
    • Google+
    • nicoladorigatti
    • Mostra profilo
  • Dispositivo Android:
    Nexus 6p, Nexus 4, Nexus S, Nexus 7(2012)
  • Sistema operativo:
    Windows 7
Re:Map v2, come gestire il tocco.
« Risposta #1 il: 31 Luglio 2014, 10:29:16 CEST »
+1
molte grazie! Potrebbe tornarmi utile in quanto volevo usare il doppio tap in uno specifico flow di interazione con la mappa ma non volevo usare tutto quel meccanismo da te citato per una cosa del genere, ma con questo metodo potrebbe essere più semplice.

Ti risulta facile delegare correttamente alla mappa gli eventi in caso tu non li debba usare?
Se si, aggiungilo allo snippet, può essere utile!
IMPORTANTE:NON RISPONDO A PROBLEMI VIA MESSAGGIO PRIVATO
LOGCAT: Non sai cos'è? -> Android Debug Bridge | Android Developers
               Dov'è in Eclipse? -> Window -> Open Prospective -> DDMS e guarda in basso!
[Obbligatorio] Logcat, questo sconosciuto! (Gruppo AndDev.it LOGTFO) - Android Developers Italia

Offline casim

  • Nuovo arrivato
  • *
  • Post: 9
  • Respect: +2
    • Mostra profilo
  • Dispositivo Android:
    galaxy note 3, galaxy note 10.1
  • Sistema operativo:
    windows xp
Re:Map v2, come gestire il tocco.
« Risposta #2 il: 01 Agosto 2014, 10:11:45 CEST »
0
molte grazie! Potrebbe tornarmi utile in quanto volevo usare il doppio tap in uno specifico flow di interazione con la mappa ma non volevo usare tutto quel meccanismo da te citato per una cosa del genere, ma con questo metodo potrebbe essere più semplice.

Ti risulta facile delegare correttamente alla mappa gli eventi in caso tu non li debba usare?
Se si, aggiungilo allo snippet, può essere utile!

Ti capisco, io dovevo abilitare il pan della mappa al tocco prolungato (e fin qui nulla di strano), e disabilitarlo non appena si solleva il dito!
Invece, in merito alla tua domanda, potresti farmi qualche esempio pratico di quello che vorresti fare?

Offline Nicola_D

  • Utente storico
  • *****
  • Post: 2479
  • SBAGLIATO!
  • Respect: +323
    • Github
    • Google+
    • nicoladorigatti
    • Mostra profilo
  • Dispositivo Android:
    Nexus 6p, Nexus 4, Nexus S, Nexus 7(2012)
  • Sistema operativo:
    Windows 7
Re:Map v2, come gestire il tocco.
« Risposta #3 il: 01 Agosto 2014, 10:17:43 CEST »
0
nel senso che il gesture listener cattura le gesture, tipo il classico "doppiotap+pan" fa lo zoom, il long click deve passare il long click alla mappa ecc ecc..
io vorrei poter usare il wrapper solo in alcuni casi del tipo:
- Situazione di partenza, il doppio tap seguito da pan fa lo zoom
- L'utente abilità la modalità X, da ora in poi il doppio tap serve per disabilitarla, quindi niente doppiotap+pan per lo zoom
- La modalità X è disabilitata, quindi il toppio tap torna a fare zoom se seguito da pan

E poi tutte le altre gesture tipo pinch ecc, dovrebbero essere gestite nativamente (tipo gmap.sendTouchEvent(event) o simile...
Non so se son stato chiaro... :D
IMPORTANTE:NON RISPONDO A PROBLEMI VIA MESSAGGIO PRIVATO
LOGCAT: Non sai cos'è? -> Android Debug Bridge | Android Developers
               Dov'è in Eclipse? -> Window -> Open Prospective -> DDMS e guarda in basso!
[Obbligatorio] Logcat, questo sconosciuto! (Gruppo AndDev.it LOGTFO) - Android Developers Italia

Offline casim

  • Nuovo arrivato
  • *
  • Post: 9
  • Respect: +2
    • Mostra profilo
  • Dispositivo Android:
    galaxy note 3, galaxy note 10.1
  • Sistema operativo:
    windows xp
Re:Map v2, come gestire il tocco.
« Risposta #4 il: 03 Agosto 2014, 11:35:03 CEST »
0
nel senso che il gesture listener cattura le gesture, tipo il classico "doppiotap+pan" fa lo zoom, il long click deve passare il long click alla mappa ecc ecc..
io vorrei poter usare il wrapper solo in alcuni casi del tipo:
- Situazione di partenza, il doppio tap seguito da pan fa lo zoom
- L'utente abilità la modalità X, da ora in poi il doppio tap serve per disabilitarla, quindi niente doppiotap+pan per lo zoom
- La modalità X è disabilitata, quindi il toppio tap torna a fare zoom se seguito da pan

E poi tutte le altre gesture tipo pinch ecc, dovrebbero essere gestite nativamente (tipo gmap.sendTouchEvent(event) o simile...
Non so se son stato chiaro... :D

Ciao, scusa per il ritardo!

Utilizzando il GestureOverlayView come contenitore, qualsiasi evento di tocco viene effettivamente inviato alla mappa (se hai già provato, noterai come pinch, pan, e tutti gli eventi di tocco continuino a funzionare, come se avessi solo la mappa). Ma questi eventi vengono anche presi dalla view contenitore, che attraverso il metodo che ti ho suggerito, permette di gestirli, ottenendo dunque qualcosa in più in termini di controllo. Nello specifico, l'esempio che mi hai fatto si può gestire definendo l'evento di doppio tap sul contenitore. Credo che sia implementata nelle librerie di android la gesture del doppio tap (ma sono fuori adesso, non saprei che cosa devi usare), se non è così scriverla a mano dovrebbe comunque essere abbastanza semplice.
Quando esegui il doppio tap, dovresti vedere (se ti trovi nella circostanza in cui hai attivato l'impostazione che hai chiamato X) di disattivare lo zoom della mappa, mi pare si possa fare con map.getUiSettings(), o una cosa del genere.