0

I am trying to save markers to my app when users tap on the map. Previously I uses a different method of doing this, (using eclipse) but have since moved on to android studio and for some weird reason that code doesn't work crashes when app launch. I have also asked a question on SO (thanks to all that helped) but wasn't successful. So I was advised to use a different method, so have decided to use SQLite database.

So this is what I am sitting with now:

24434-24434/com.new.newapp E/AndroidRuntime﹕ FATAL EXCEPTION: main
Process: com.new.newapp, PID: 24434
java.lang.NullPointerException: Attempt to invoke virtual method 'android.database.Cursor android.database.sqlite.SQLiteDatabase.query(java.lang.String, java.lang.String[], java.lang.String, java.lang.String[], java.lang.String, java.lang.String, java.lang.String, java.lang.String)' on a null object reference
        at com.new.newapp.activity.FragmentGoogleMap.onViewCreated(FragmentGoogleMap.java:109)
        at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:973)
        at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1138)
        at android.support.v4.app.BackStackRecord.run(BackStackRecord.java:740)
        at android.support.v4.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:1501)
        at android.support.v4.app.FragmentManagerImpl$1.run(FragmentManager.java:458)
        at android.os.Handler.handleCallback(Handler.java:739)
        at android.os.Handler.dispatchMessage(Handler.java:95)
        at android.os.Looper.loop(Looper.java:145)
        at android.app.ActivityThread.main(ActivityThread.java:5832)
        at java.lang.reflect.Method.invoke(Native Method)
        at java.lang.reflect.Method.invoke(Method.java:372)
        at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1399)
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1194)

So here is my code:

FragmentGoogleMap class:

Context context = getActivity();
MarkerDataSource Mdata;
MyMarkerObj Mobj;
static final  ContentValues contentValues = new ContentValues();
boolean dbCheckedOpen = false;

.....

 @Override
public void onViewCreated(View view, @Nullable Bundle savedInstanceState) {
    super.onViewCreated(view, savedInstanceState);
    SupportMapFragment mapFragment = (SupportMapFragment) getChildFragmentManager().findFragmentById(R.id.map);
    mapFragment.getMapAsync(this);
    Mdata = new MarkerDataSource(context);
    Mobj = new MyMarkerObj();

    try {
        Mdata.open();
        dbCheckedOpen = true;
    }
    catch (Exception e) {
    }

//LINE 109 -->// Cursor cursor = Mdata.db.query(LocationsDB.DATABASE_TABLE, Mdata.cols, null, null, null, null, null, null);
    if (cursor != null) {

        List<MyMarkerObj> mmo = Mdata.getMarkers();
        for (int i = 0; i < mmo.size(); i++)
        {
            String latidutes = mmo.get(i).getLat().toString();
            String langidutes = mmo.get(i).getLng().toString();
            LatLng latlngs = new LatLng(Double.valueOf(latitudes), Double.valueOf(longitudes));
            mMap.addMarker(new MarkerOptions()
                    .title(mmo.get(i).getTitle().toString())
                    .snippet(mmo.get(i).getSnippet().toString())
                    .position(latlngs));
        }
    }

 }

.....

@Override
public void onMapLongClick(final LatLng point) {
    if (dbCheckedOpen == false)
    {
        try {
            Mdata.open();
        }
        catch (Exception e) {
        }
    }

 LayoutInflater li = LayoutInflater.from(getActivity());
    final View v = li.inflate(R.layout.alertlayout, null);
    AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
    builder.setView(v);
    builder.setIcon(R.drawable.ic_home);
    builder.setCancelable(true);
    builder.setPositiveButton("Take Photo", new DialogInterface.OnClickListener() {

        public void onClick(DialogInterface dialog, int which) {
            EditText title = (EditText) v.findViewById(R.id.ettitle);
            EditText snippet = (EditText) v.findViewById(R.id.etsnippet);
            Marker marker = mMap.addMarker(new MarkerOptions()
                    .title(title.getText().toString())
                    .snippet(snippet.getText().toString())
                    .icon(BitmapDescriptorFactory
                            .defaultMarker(BitmapDescriptorFactory.HUE_BLUE))
                    .position(point));
            markerId = marker.getId();

            Intent imageIntent = new Intent(android.provider.MediaStore.ACTION_VIDEO_CAPTURE);
            timeStamp = new SimpleDateFormat("ddMMMyyyy_HH:mm:ss").format(new Date());
            File imagesFolder = new File(Environment.getExternalStorageDirectory(), "Images");
            imagesFolder.mkdirs();
            image = new File(imagesFolder.getPath(), "MyMarkerImages_" + timeStamp + ".jpg");
            fileUri = Uri.fromFile(image);

            imageIntent.putExtra(MediaStore.EXTRA_OUTPUT, fileUri);
            startActivityForResult(imageIntent, TAKE_PICTURE);

            Mobj.setLat(String.valueOf(point.latitude));
            Mobj.setLng(String.valueOf(point.longitude));
            Mobj.setZom(String.valueOf(mMap.getCameraPosition().zoom));
            Mobj.setTitle(String.valueOf(title.getText()));
            Mobj.setSnippet(String.valueOf(snippet.getText()));
            Mobj.setImage(String.valueOf(markerId));
            Mobj.setFilepath(String.valueOf(image.getAbsolutePath()));

            contentValues.put(LocationsDB.FIELD_LAT, Mobj.getLat());
            contentValues.put(LocationsDB.FIELD_LNG, Mobj.getLng());
            contentValues.put(LocationsDB.FIELD_ZOM, Mobj.getZom());
            contentValues.put(LocationsDB.FIELD_TITLE, Mobj.getTitle());
            contentValues.put(LocationsDB.FIELD_SNIP, Mobj.getSnippet());
            contentValues.put(LocationsDB.FIELD_IMAGE, Mobj.getImage());
            contentValues.put(LocationsDB.FIELD_FILEPATH, Mobj.getFilepath ());

Locations DB Class:

public class LocationsDB extends SQLiteOpenHelper {

/** Database name */
private static final String DBNAME  = "markerlocations.db";

/** Version number of the database */
private static final int    VERSION = 1;
public static final String  FIELD_ROW_ID = "_id";
public static final String  FIELD_LAT  = "lat";
public static final String  FIELD_LNG  = "lng";
public static final String  FIELD_ZOM  = "zom";
public static final String  FIELD_TITLE  = "title";
public static final String  FIELD_SNIP = "snip";
public static final String  FIELD_IMAGE = "img";
public static final String  FIELD_FILEPATH = "filep";

/** A constant, stores the the table name */
public static final String  DATABASE_TABLE = "locations";
public static final String  DB_CREATE = "create table " + DATABASE_TABLE + " ( " +
        FIELD_ROW_ID + " integer primary key autoincrement , " +
        FIELD_LNG + " text , " +
        FIELD_LAT + " text , " +
        FIELD_ZOM + " text , " +
        FIELD_TITLE + " text , " +
        FIELD_SNIP + " text , " +
        FIELD_IMAGE + " blob , " +
        FIELD_FILEPATH + "text , " +
        " ) ";


/** Constructor */
public LocationsDB(Context context) {
    super(context, DBNAME, null, VERSION);

}

@Override
public void onCreate(SQLiteDatabase db) {

    db.execSQL(DB_CREATE);
}

@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
    if (db == null) {
        db.execSQL(DATABASE_TABLE);
        onCreate(db);
    }
}
}

MarkerDataSource Class

public class MarkerDataSource {

LocationsDB mDB;
SQLiteDatabase db;
final String[] cols = {
        LocationsDB.FIELD_LAT,
        LocationsDB.FIELD_LNG,
        LocationsDB.FIELD_ZOM,
        LocationsDB.FIELD_TITLE,
        LocationsDB.FIELD_SNIP,
        LocationsDB.FIELD_IMAGE,
        LocationsDB.FIELD_FILEPATH };

FragmentGoogleMap main;


public MarkerDataSource(Context C) {

    mDB = new LocationsDB(C);

}


public void open() throws SQLException
{
    db = mDB.getWritableDatabase();
}


public void close()
{
    db.close();
}


public void addMarker()
{
    main = new FragmentGoogleMap();
    db.insert(LocationsDB.DATABASE_TABLE, null, main.contentValues);
}


public List<MyMarkerObj> getMarkers() {
    List<MyMarkerObj> markers = new ArrayList<MyMarkerObj>();
    Cursor cursor = db.query(LocationsDB.DATABASE_TABLE, cols, null, null, null, null, null, null);
    cursor.moveToFirst();
    while ( !cursor.isAfterLast())
    {
        MyMarkerObj mmo = cursorToMarker(cursor);
        markers.add(mmo);
        cursor.moveToNext();
    }
    cursor.close();

    return markers;
}


private MyMarkerObj cursorToMarker(Cursor cursor) {
    MyMarkerObj mmo = new MyMarkerObj();
    mmo.setLat(cursor.getString(0));
    mmo.setLng(cursor.getString(1));
    mmo.setZom(cursor.getString(2));
    mmo.setTitle(cursor.getString(3));
    mmo.setSnippet(cursor.getString(4));
    mmo.setFilepath(cursor.getString(5));
    mmo.setLng(cursor.getString(1));
    return mmo;
}

MyMarkerObj Class

public class MyMarkerObj {

private Long   id;
private String lat;
private String lng;
private String zom;
private String title;
private String snip;
private String image;
private String filep;



public MyMarkerObj() {
    // TODO Auto-generated constructor stub
}


public MyMarkerObj(Long id, String lat, String lng, String zom, String title, String snip, String img, String filep)
{
    this.setId(id);
    this.setLat(lat);
    this.setLng(lng);
    this.setZom(zom);
    this.setTitle(title);
    this.setSnippet(snip);
    this.setImage(img);
    this.setFilepath(filep);

}


public MyMarkerObj(String lat, String lng, String zom, String title, String snip, String img, String filep)
{
    this.setLat(lat);
    this.setLng(lng);
    this.setZom(zom);
    this.setTitle(title);
    this.setSnippet(snip);
    this.setImage(img);
    this.setFilepath(filep);
}

//ID
public Long getId() {
    return id;
}
public void setId(Long id) {
    this.id = id;
}

//Latitude
public String getLat() {
    return lat;
}
public void setLat(String lat) {
    this.lat = lat;
}

//Longitude
public String getLng() {
    return lng;
}
 public void setLng(String lng) {
    this.lng = lng;
}

//Zoom
public String getZom() {
    return zom;
}
public void setZom(String zom) {
    this.zom = zom;
}

//Title
public String getTitle() {
    return zom;
}
public void setTitle(String title) {
    this.title = title;
}

//Snippet
public String getSnippet() {
    return zom;
}
public void setSnippet(String snip) {
    this.snip = snip;
}

//File Path
public String getImage() {
    return image;
}
public void setImage(String image) {
    this.image = image;
}

//File Path
public String getFilepath() {
    return filep;
}
public void setFilepath(String filep) {
    this.filep = filep;
}

I am really sorry for all the code, but am not sure what I am doing wrong?

1 Answers1

0

DON'T SWALLOW EXCEPTIONS!

You do:

try {
    Mdata.open();
    dbCheckedOpen = true;
}
catch (Exception e) {
}

and assume the database opened correctly, without even a log message. At a latter stage, an error that implies that implies that there was indeed an error and MarkerDataSource.db points a null reference happens...

If you get an exception thrown at it, you either know how to handle it (and do handle it that way), or log it and crash the program/module in an user-friendly way

Check the exception you are getting whe nopening the DB, try to solve it or poste it here (as a different question, because this is already answered).

SJuan76
  • 24,532
  • 6
  • 47
  • 87