Skip to content

Commit

Permalink
add database and options to share and delete
Browse files Browse the repository at this point in the history
  • Loading branch information
woheller69 committed Feb 12, 2024
1 parent 529de32 commit a500d8b
Show file tree
Hide file tree
Showing 9 changed files with 161 additions and 3 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
package org.tensorflow.lite.examples.soundclassifier;

import android.content.ContentValues;
import android.content.Context;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import java.util.*;

public class BirdDBHelper extends SQLiteOpenHelper {

// Database name and table columns
private static final String DB_NAME = "BirdDatabase.db";
private static final int DATABASE_VERSION = 1;
public static final String TABLE_NAME = "BirdObservations";
private static final String COLUMN_ID = "ID";
private static final String COLUMN_MILLIS = "TimeInMillis";
private static final String COLUMN_LATITUDE = "Latitude";
private static final String COLUMN_LONGITUDE = "Longitude";
private static final String COLUMN_NAME = "SpeciesName";
private static final String COLUMN_SPECIES_ID = "BirdNET_ID";
private static final String COLUMN_PROBABILITY = "Probability";
private static BirdDBHelper instance = null;

public BirdDBHelper(Context context) {
super(context, DB_NAME, null, DATABASE_VERSION);
}

@Override
public void onCreate(SQLiteDatabase db) {
// Create the table for bird observations with all columns and their data types.
String CREATE_TABLE = "CREATE TABLE IF NOT EXISTS "+TABLE_NAME+" (" +
COLUMN_ID + " INTEGER PRIMARY KEY AUTOINCREMENT," +
COLUMN_MILLIS + " LONG," +
COLUMN_LATITUDE + " FLOAT," +
COLUMN_LONGITUDE + " FLOAT," +
COLUMN_NAME + " TEXT," +
COLUMN_SPECIES_ID + " INTEGER," +
COLUMN_PROBABILITY + " FLOAT);";
db.execSQL(CREATE_TABLE);
}

@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
// Drop the table and create it again if there's a version change in the database schema.
db.execSQL("DROP TABLE IF EXISTS "+TABLE_NAME);
this.onCreate(db);
}

public void addEntry(String name, float latitude, float longitude, int speciesId, float probability) {
// Insert a new row into the table with all columns and their values from parameters.
SQLiteDatabase db = getWritableDatabase();
ContentValues cv = new ContentValues();
cv.put(COLUMN_NAME, name);
cv.put(COLUMN_MILLIS, System.currentTimeMillis()); // time in milliseconds
cv.put(COLUMN_LATITUDE, latitude);
cv.put(COLUMN_LONGITUDE, longitude);
cv.put(COLUMN_SPECIES_ID, speciesId);
cv.put(COLUMN_PROBABILITY, probability);

db.insert(TABLE_NAME, null, cv); // Insert the row into the table with all columns and their values from parameters.
}

public void clearAllEntries() {
SQLiteDatabase db = getWritableDatabase();
String CLEAR_TABLE = "DELETE FROM "+ TABLE_NAME;

db.execSQL(CLEAR_TABLE); // Delete all rows in the table, effectively clearing it out.
}

public List<String> exportAllEntriesAsCSV() {
SQLiteDatabase db = getReadableDatabase();
String SELECT_ALL = "SELECT * FROM "+ TABLE_NAME;

Cursor cursor = db.rawQuery(SELECT_ALL, null); // Execute the query to select all rows from the table and store them in a cursor object for further processing.

List<String> csvDataList = new ArrayList<>(); // Create an empty list of strings that will hold each row's data as CSV formatted string.

if (cursor != null && cursor.moveToFirst()) {
do {
long millis = cursor.getLong(1); // time in milliseconds
float latitude = cursor.getFloat(2); // latitude
float longitude = cursor.getFloat(3); // longitude
String nameStr = cursor.getString(4); // name of the bird species
int speciesId = cursor.getInt(5); // id for the species in BirdNET
float probability = cursor.getFloat(6); // estimated probability that this observation is correct

String csvString = millis + "," + latitude + "," + longitude + "," + nameStr + "," + speciesId + "," + probability;

csvDataList.add(csvString);
} while (cursor.moveToNext());
cursor.close();
}
return csvDataList;
}
public static BirdDBHelper getInstance(Context context) {
if (instance == null && context != null) {
instance = new BirdDBHelper(context.getApplicationContext());
}
return instance;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
package org.tensorflow.lite.examples.soundclassifier

import android.Manifest
import android.content.Intent
import android.content.pm.PackageManager
import android.os.Bundle
import android.view.ViewGroup
Expand Down Expand Up @@ -59,6 +60,24 @@ class MainActivity : AppCompatActivity() {
if (binding.progressHorizontal.isIndeterminate) binding.progressHorizontal.setIndeterminate(false)
else binding.progressHorizontal.setIndeterminate(true)
}
binding.bottomNavigationView.setOnNavigationItemSelectedListener { item ->
when (item.itemId) {
R.id.action_share -> {
val database = BirdDBHelper.getInstance(this)
val intent = Intent(Intent.ACTION_SEND)
val shareBody = database.exportAllEntriesAsCSV().joinToString("\n")
intent.setType("text/plain")
intent.putExtra(Intent.EXTRA_TEXT, shareBody)
startActivity(Intent.createChooser(intent, ""))
}
R.id.action_delete -> {
val database = BirdDBHelper.getInstance(this)
database.clearAllEntries()
Toast.makeText(this, getString(R.string.clear_db),Toast.LENGTH_SHORT).show()
}
}
true
}

if (GithubStar.shouldShowStarDialog(this)) GithubStar.starDialog(this, "https://github.com/woheller69/whoBIRD")

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -67,9 +67,11 @@ class SoundClassifier(
DefaultLifecycleObserver {
internal var mContext: Context
internal var mBinding: ActivityMainBinding
private var database: BirdDBHelper? = null
init {
this.mContext = context.applicationContext
this.mBinding = binding
this.database = BirdDBHelper.getInstance(mContext)
}
class Options constructor(
/** Path of the converted model label file, relative to the assets/ directory. */
Expand Down Expand Up @@ -341,8 +343,8 @@ class SoundClassifier(
fun runMetaInterpreter(location: Location) {
val dayOfYear = LocalDate.now().dayOfYear
val week = ceil( dayOfYear*48.0/366.0) //model year has 48 weeks
val lat = location.latitude.toFloat()
val lon = location.longitude.toFloat()
lat = location.latitude.toFloat()
lon = location.longitude.toFloat()

Handler(Looper.getMainLooper()).post {
mBinding.gps.setText(mContext.getString(R.string.latitude)+": " + (round(lat*100.0)/100.0).toString() + " / " + mContext.getString(R.string.longitude) + ": " + (round(lon*100.0)/100).toString())
Expand Down Expand Up @@ -558,6 +560,7 @@ class SoundClassifier(
else if (max.value < 0.65) mBinding.text1.setBackgroundResource(R.drawable.oval_holo_orange_dark)
else if (max.value < 0.8) mBinding.text1.setBackgroundResource(R.drawable.oval_holo_orange_light)
else mBinding.text1.setBackgroundResource(R.drawable.oval_holo_green_light)
database?.addEntry(labelAtMaxIndex, lat, lon, max.index, max.value)
}
} else {
Handler(Looper.getMainLooper()).post {
Expand Down Expand Up @@ -615,7 +618,8 @@ class SoundClassifier(

companion object {
private const val TAG = "SoundClassifier"

var lat: Float = 0.0f
var lon: Float = 0.0f
/** Number of nanoseconds in a millisecond */
private const val NANOS_IN_MILLIS = 1_000_000.toDouble()
}
Expand Down
9 changes: 9 additions & 0 deletions app/src/main/res/drawable/ic_delete_24dp.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp"
android:height="24dp"
android:viewportWidth="960"
android:viewportHeight="960">
<path
android:fillColor="#FF000000"
android:pathData="M280,840q-33,0 -56.5,-23.5T200,760v-520h-40v-80h200v-40h240v40h200v80h-40v520q0,33 -23.5,56.5T680,840L280,840ZM680,240L280,240v520h400v-520ZM360,680h80v-360h-80v360ZM520,680h80v-360h-80v360ZM280,240v520,-520Z"/>
</vector>
9 changes: 9 additions & 0 deletions app/src/main/res/drawable/ic_share_24dp.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp"
android:height="24dp"
android:viewportWidth="960"
android:viewportHeight="960">
<path
android:fillColor="#FF000000"
android:pathData="M720,880q-50,0 -85,-35t-35,-85q0,-7 1,-14.5t3,-13.5L322,568q-17,15 -38,23.5t-44,8.5q-50,0 -85,-35t-35,-85q0,-50 35,-85t85,-35q23,0 44,8.5t38,23.5l282,-164q-2,-6 -3,-13.5t-1,-14.5q0,-50 35,-85t85,-35q50,0 85,35t35,85q0,50 -35,85t-85,35q-23,0 -44,-8.5T638,288L356,452q2,6 3,13.5t1,14.5q0,7 -1,14.5t-3,13.5l282,164q17,-15 38,-23.5t44,-8.5q50,0 85,35t35,85q0,50 -35,85t-85,35ZM720,240q17,0 28.5,-11.5T760,200q0,-17 -11.5,-28.5T720,160q-17,0 -28.5,11.5T680,200q0,17 11.5,28.5T720,240ZM240,520q17,0 28.5,-11.5T280,480q0,-17 -11.5,-28.5T240,440q-17,0 -28.5,11.5T200,480q0,17 11.5,28.5T240,520ZM720,800q17,0 28.5,-11.5T760,760q0,-17 -11.5,-28.5T720,720q-17,0 -28.5,11.5T680,760q0,17 11.5,28.5T720,800ZM720,200ZM240,480ZM720,760Z"/>
</vector>
1 change: 1 addition & 0 deletions app/src/main/res/layout/activity_main.xml
Original file line number Diff line number Diff line change
Expand Up @@ -155,6 +155,7 @@
app:itemIconTint="@color/orange500"
app:itemTextColor="@color/orange500"
app:labelVisibilityMode="unlabeled"
app:menu="@menu/bottom_bar"
android:background="@drawable/background_transparent" />

</com.google.android.material.bottomappbar.BottomAppBar>
Expand Down
12 changes: 12 additions & 0 deletions app/src/main/res/menu/bottom_bar.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<menu xmlns:tools="http://schemas.android.com/tools"
xmlns:android="http://schemas.android.com/apk/res/android">
<item tools:ignore="MenuTitle" />
<item tools:ignore="MenuTitle" />
<item tools:ignore="MenuTitle" />
<item android:id="@+id/action_share"
android:icon="@drawable/ic_share_24dp"
tools:ignore="MenuTitle" />
<item android:id="@+id/action_delete"
android:icon="@drawable/ic_delete_24dp"
tools:ignore="MenuTitle" />
</menu>
1 change: 1 addition & 0 deletions app/src/main/res/values-de/strings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -14,5 +14,6 @@
<string name="error_audio_permission">Berechtigung für Mikrofon fehlt</string>
<string name="error_location_permission">Berechtigung für Standort fehlt</string>
<string name="show_images">Bilder anzeigen</string>
<string name="clear_db">Beobachtungen gelöscht</string>

</resources>
1 change: 1 addition & 0 deletions app/src/main/res/values/strings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -15,5 +15,6 @@
<string name="error_audio_permission">Microphone permission not granted</string>
<string name="error_location_permission">Location permission not granted</string>
<string name="show_images">Show images</string>
<string name="clear_db">Observations deleted</string>

</resources>

0 comments on commit a500d8b

Please sign in to comment.