Autore Topic: Non ottengo il riferimento a GoogleMap  (Letto 532 volte)

Offline Elmvor

  • Utente normale
  • ***
  • Post: 166
  • Respect: 0
    • Mostra profilo
  • Sistema operativo:
    Ubuntu 14.04, Windows 8.1
Non ottengo il riferimento a GoogleMap
« il: 21 Dicembre 2013, 16:23:24 CET »
0
Per la precisione ci ero riuscito facilmente a modo mio. Poi ho deciso di migliorare il codice seguendo una guida più professionale,
ma essendo la stessa piuttosto confusionaria, l'app non funziona come dovrebbe. Per la precisione se provo a svolgere una qualsiasi
operazione sull'oggetto GoogleMap ottengo nullpointerexception, suppongo perché nel mio codice non viene mai effettivamente
inizializzato (e stando alla guida non dovrebbe assolutamente essere così).

Posto il codice di interesse..

Activity principale

Codice: [Seleziona]
.
.
.
protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_single_fragment);
        mLatLngGpxList = new ArrayList<LatLng>();
        mMapPref = PreferenceManager.getDefaultSharedPreferences(this);
        mLocationClient = new LocationClient(this, mConnectionCallbacks, mOnConnectionFailedListener);
    }

    private LocationListener mLocationListener = new LocationListener() {

        @Override
        public void onLocationChanged(Location location) {
            showMapFragment();
        }
    };

    /*Metodo che si occupa di mostrare la mappa nella UI che invochiamo quando
      la location è disponibile.*/
    private void showMapFragment() {
        Fragment existingMapFragment = getSupportFragmentManager().findFragmentByTag(MAP_FRAGMENT_TAG);
        if(existingMapFragment == null && mCurrentLocation != null) {
            //Creiamo il MapFragment per mostrare la posizione sulla mappa
            SupportMapFragment mapFragment = SupportMapFragment.newInstance();
            FragmentTransaction fragmentTransaction = getSupportFragmentManager().beginTransaction();
            fragmentTransaction.add(R.id.anchor_point, mapFragment, MAP_FRAGMENT_TAG);
            fragmentTransaction.commit();
            //Prendiamo l'oggetto mGoogleMap
            mGoogleMap = mapFragment.getMap();
        }
        else {
            //Prendiamo l'oggetto mGoogleMap dall'oggetto esistente
            mGoogleMap = ((SupportMapFragment)existingMapFragment).getMap();
            //Impostiamo il tipo di mappa
            synchMapType();
        }
    }

    @Override
    public void mapIsReady(final GoogleMap googleMap) {
        //Salviamo la GoogleMap reference
        mGoogleMap = googleMap;
        //Impostiamo il tipo di mappa
        synchMapType();
    }

    private void synchMapType() {
        // Leggiamo il tipo di mappa  nelle preferenze e impostiamolo per Map
        String mapTypePrefs = PreferenceManager.getDefaultSharedPreferences(this)
                .getString(MAP_TYPE_KEY, null);
        int mapType = Utility.getGoogleMapTypeFromResourceValue(this, mapTypePrefs);
        mGoogleMap.setMapType(mapType);
    }

    @Override
    protected void onStart() {
        super.onStart();
        //Connettiamo il LocationClient
        mLocationClient.connect();
    }

    @Override
    protected void onResume() {
        super.onResume();
        // Here we check if the PLay Services APK is installed on the device and
        // for which version
        final int checkPlayStatus = GooglePlayServicesUtil.isGooglePlayServicesAvailable(this);
        if (checkPlayStatus == ConnectionResult.SUCCESS) {
            // In this case everything is ok so we go on
            Toast.makeText(MainActivity.this, "Everything is ok!", Toast.LENGTH_SHORT).show();
        } else {
            // Here there's some problems so we get the dialog to manage it
            // with the user and ask him what to do.
            /*mErrorDialog = GooglePlayServicesUtil.getErrorDialog(checkPlayStatus,
                    this, PLAY_DOWNLOAD_REQUEST_ID, new DialogInterface.OnCancelListener() {
                @Override
                public void onCancel(DialogInterface dialog) {
                    // The SDK is mandatory
                    finish();
                }
            });
            mErrorDialog.show();*/
            Toast.makeText(MainActivity.this, "The SDK is mandatory!", Toast.LENGTH_SHORT).show();
        }
        // Set the map type
        if (mGoogleMap != null) {
            synchMapType();
        }
    }

    @Override
    protected void onStop() {
        //Disconnettiamo il LocationClient
        if(mLocationClient.isConnected()) {
            mLocationClient.removeLocationUpdates(mLocationListener);
        }
        mLocationClient.disconnect();
        super.onStop();
    }
private GooglePlayServicesClient.ConnectionCallbacks mConnectionCallbacks
            = new GooglePlayServicesClient.ConnectionCallbacks() {

        @Override
        public void onConnected(Bundle bundle) {
            Log.d(TAG_LOG, "Connected with Google Play Services");
            Toast.makeText(MainActivity.this, "Connected", Toast.LENGTH_SHORT).show();
            //Mostriamo la currentLocation
            mCurrentLocation = mLocationClient.getLastLocation();
            Toast.makeText(MainActivity.this, "Last Location: " + mCurrentLocation, Toast.LENGTH_SHORT).show();
        }

        @Override
        public void onDisconnected() {
            Log.d(TAG_LOG, "Disconnected with Google Play Services");
            Toast.makeText(MainActivity.this, "Disconnected", Toast.LENGTH_SHORT).show();
        }
    };

Fragment per ottenere la mappa..

Codice: [Seleziona]
public class CallbackMapFragment extends SupportMapFragment {

    public interface OnGoogleMapReadyListener {

        void mapIsReady(GoogleMap googleMap);
    }

    private OnGoogleMapReadyListener mOnGoogleMapReadyListener;

    @Override
    public void onAttach(Activity activity) {
        super.onAttach(activity);
        if(activity instanceof OnGoogleMapReadyListener) {
            mOnGoogleMapReadyListener = (OnGoogleMapReadyListener)activity;
        }
    }

    @Override
    public View onCreateView(LayoutInflater infilater, ViewGroup container, Bundle savedInstanceState) {
        View superView = super.onCreateView(infilater, container, savedInstanceState);
        //La view è pronta, quindi notifichiamo se necessario
        if(mOnGoogleMapReadyListener != null) {
            mOnGoogleMapReadyListener.mapIsReady(getMap());
        }
        //Torniamo alla view precedente
        return superView;
    }
}



Post unito: 21 Dicembre 2013, 16:35:42 CET
Aggiungo che la guida usa questo layout:

Codice: [Seleziona]
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
                xmlns:tools="http://schemas.android.com/tools"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:id="@+id/anchor_point"
                tools:context=".MainActivity">
</RelativeLayout>
Definisce l'anchor_point per il fragment, quindi da quel che ho capito non serve aggiungere la mappa tramite i tag <fragment>.
Se provo a mettere solo questo però, non visualizzo alcuna mappa...

Post unito: 21 Dicembre 2013, 19:57:33 CET
Ho modificato questo

Codice: [Seleziona]
SupportMapFragment mapFragment = SupportMapFragment.newInstance();

in questo

Codice: [Seleziona]
SupportMapFragment mapFragment = new CallbackMapFragment();

ed in effetti era un errore, ma non ho risolto assolutamente nulla...

Post unito: 21 Dicembre 2013, 22:31:54 CET
Ho risolto. Non ho chiamato il metodo showMapFragment() nel metodo onConnected()..
« Ultima modifica: 21 Dicembre 2013, 22:31:54 CET da Elmvor, Reason: Merged DoublePost »

Offline LinkOut

  • Utente normale
  • ***
  • Post: 269
  • Respect: +37
    • Mostra profilo
  • Dispositivo Android:
    Xiaomi Mi5
Re:Non ottengo il riferimento a GoogleMap
« Risposta #1 il: 23 Dicembre 2013, 08:32:54 CET »
0
Ti metto un riferimento: MapFragment | Android Developers

A GoogleMap can only be acquired using getMap() when the underlying maps system is loaded and the underlying view in the fragment exists. This class automatically initializes the maps system and the view; however you cannot be guaranteed when it will be ready because this depends on the availability of the Google Play services APK. If a GoogleMap is not available, getMap() will return null.

Dovresti aspettare ed essere sicuro che il MapFragment sia correttamente caricato ... poi proseguire... Se questo non accade, getMap restituirà null...


Saluti.

Offline Elmvor

  • Utente normale
  • ***
  • Post: 166
  • Respect: 0
    • Mostra profilo
  • Sistema operativo:
    Ubuntu 14.04, Windows 8.1
Re:Non ottengo il riferimento a GoogleMap
« Risposta #2 il: 23 Dicembre 2013, 09:18:32 CET »
0
Si come ho scritto mi ero dimenticato di chiamare il metodo showMapFragment() una volta ottenuta la connessione! :)