diff --git a/.idea/misc.xml b/.idea/misc.xml index 94427d2..1bdb314 100644 --- a/.idea/misc.xml +++ b/.idea/misc.xml @@ -11,9 +11,13 @@ + + + + diff --git a/mobile/src/main/java/de/rhaeus/dndsync/DNDNotificationService.java b/mobile/src/main/java/de/rhaeus/dndsync/DNDNotificationService.java index 9c36aa0..18f407f 100644 --- a/mobile/src/main/java/de/rhaeus/dndsync/DNDNotificationService.java +++ b/mobile/src/main/java/de/rhaeus/dndsync/DNDNotificationService.java @@ -82,9 +82,8 @@ private void sendDNDSync(int dndState) { } else { for (Node node : connectedNodes) { if (node.isNearby()) { - byte[] data = new byte[2]; - data[0] = 1; // bedtime mode - data[1] = (byte) dndState; + byte[] data = new byte[1]; + data[0] = (byte) dndState; Task sendTask = Wearable.getMessageClient(this).sendMessage(node.getId(), DND_SYNC_MESSAGE_PATH, data); diff --git a/mobile/src/main/java/de/rhaeus/dndsync/DNDSyncListenerService.java b/mobile/src/main/java/de/rhaeus/dndsync/DNDSyncListenerService.java index cbc5325..945bbda 100644 --- a/mobile/src/main/java/de/rhaeus/dndsync/DNDSyncListenerService.java +++ b/mobile/src/main/java/de/rhaeus/dndsync/DNDSyncListenerService.java @@ -26,18 +26,13 @@ public void onMessageReceived (MessageEvent messageEvent) { if (messageEvent.getPath().equalsIgnoreCase(DND_SYNC_MESSAGE_PATH)) { byte[] data = messageEvent.getData(); - // data[0] contains if dnd or bedtime mode - // 0 = dnd - // 1 = bedtime mode - // data[1] contains dnd mode of phone + // data[0] contains dnd mode of phone // 0 = INTERRUPTION_FILTER_UNKNOWN // 1 = INTERRUPTION_FILTER_ALL (all notifications pass) // 2 = INTERRUPTION_FILTER_PRIORITY // 3 = INTERRUPTION_FILTER_NONE (no notification passes) // 4 = INTERRUPTION_FILTER_ALARMS - byte mode = data[0]; - Log.d(TAG, "mode: " + mode); - byte dndStatePhone = data[1]; + byte dndStatePhone = data[0]; Log.d(TAG, "dndStatePhone: " + dndStatePhone); // get dnd state @@ -54,15 +49,12 @@ public void onMessageReceived (MessageEvent messageEvent) { byte currentDndState = (byte) filterState; Log.d(TAG, "currentDndState: " + currentDndState); - if (mode == 0) { //dnd - if (dndStatePhone != currentDndState) { - mNotificationManager.setInterruptionFilter(dndStatePhone); + if (dndStatePhone != currentDndState) { + mNotificationManager.setInterruptionFilter(dndStatePhone); // Toast.makeText(getApplicationContext(), "DND set to " + dndStatePhone, Toast.LENGTH_LONG).show(); - Log.d(TAG, "DND set to " + dndStatePhone); - } - } else { - Log.d(TAG, "DNDSync mode went wrong: " + mode); + Log.d(TAG, "DND set to " + dndStatePhone); } + } else { super.onMessageReceived(messageEvent); } diff --git a/mobile/src/main/res/values/strings.xml b/mobile/src/main/res/values/strings.xml index 76e1909..bcbc79d 100644 --- a/mobile/src/main/res/values/strings.xml +++ b/mobile/src/main/res/values/strings.xml @@ -10,6 +10,6 @@ DND access denied - Sync DND state with watch + Sync DND state to watch \ No newline at end of file diff --git a/wear/build.gradle b/wear/build.gradle index 694bca8..ed6bc7a 100644 --- a/wear/build.gradle +++ b/wear/build.gradle @@ -31,5 +31,8 @@ dependencies { implementation 'androidx.legacy:legacy-support-v4:1.0.0' implementation 'androidx.recyclerview:recyclerview:1.2.1' implementation 'androidx.wear:wear:1.1.0' + implementation 'androidx.preference:preference:1.1.1' + implementation 'androidx.appcompat:appcompat:1.3.1' + implementation 'com.google.android.material:material:1.4.0' wearApp project(":wear") } \ No newline at end of file diff --git a/wear/src/main/AndroidManifest.xml b/wear/src/main/AndroidManifest.xml index cf3dc5e..694a0af 100644 --- a/wear/src/main/AndroidManifest.xml +++ b/wear/src/main/AndroidManifest.xml @@ -4,7 +4,7 @@ - + @@ -14,10 +14,21 @@ android:label="@string/app_name" android:supportsRtl="true" android:theme="@android:style/Theme.DeviceDefault"> + + + + + + + + - - + + + @@ -71,7 +81,6 @@ - \ No newline at end of file diff --git a/wear/src/main/java/de/rhaeus/dndsync/DNDNotificationService.java b/wear/src/main/java/de/rhaeus/dndsync/DNDNotificationService.java index c2d50c3..7b6712a 100644 --- a/wear/src/main/java/de/rhaeus/dndsync/DNDNotificationService.java +++ b/wear/src/main/java/de/rhaeus/dndsync/DNDNotificationService.java @@ -2,12 +2,14 @@ import android.content.ComponentName; +import android.content.SharedPreferences; import android.content.pm.PackageManager; import android.service.notification.NotificationListenerService; import android.util.Log; import android.widget.Toast; import androidx.annotation.NonNull; +import androidx.preference.PreferenceManager; import com.google.android.gms.tasks.OnFailureListener; import com.google.android.gms.tasks.OnSuccessListener; @@ -54,11 +56,15 @@ public void onInterruptionFilterChanged (int interruptionFilter) { // Unable to retrieve node with transcription capability // Toast.makeText(getApplicationContext(), "interruption filter changed to " + interruptionFilter, Toast.LENGTH_LONG).show(); - new Thread(new Runnable() { - public void run() { - sendDNDSync(interruptionFilter); - } - }).start(); + SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(this); + Boolean syncDnd = prefs.getBoolean("dnd_sync_key", true); + if(syncDnd) { + new Thread(new Runnable() { + public void run() { + sendDNDSync(interruptionFilter); + } + }).start(); + } } private void sendDNDSync(int dndState) { @@ -90,8 +96,7 @@ private void sendDNDSync(int dndState) { for (Node node : connectedNodes) { if (node.isNearby()) { byte[] data = new byte[2]; - data[0] = 0; // dnd mode - data[1] = (byte) dndState; + data[0] = (byte) dndState; Task sendTask = Wearable.getMessageClient(this).sendMessage(node.getId(), DND_SYNC_MESSAGE_PATH, data); diff --git a/wear/src/main/java/de/rhaeus/dndsync/DNDSyncListenerService.java b/wear/src/main/java/de/rhaeus/dndsync/DNDSyncListenerService.java index 3db8ed0..8d1bbce 100644 --- a/wear/src/main/java/de/rhaeus/dndsync/DNDSyncListenerService.java +++ b/wear/src/main/java/de/rhaeus/dndsync/DNDSyncListenerService.java @@ -2,6 +2,7 @@ import android.app.NotificationManager; import android.content.Context; +import android.content.SharedPreferences; import android.os.Build; import android.os.Handler; import android.os.PowerManager; @@ -10,6 +11,8 @@ import android.util.Log; import android.widget.Toast; +import androidx.preference.PreferenceManager; + import com.google.android.gms.wearable.MessageEvent; import com.google.android.gms.wearable.WearableListenerService; @@ -28,26 +31,17 @@ public void onMessageReceived (MessageEvent messageEvent) { vibrate(); byte[] data = messageEvent.getData(); - // data[0] contains if dnd or bedtime mode - // 0 = dnd - // 1 = bedtime mode - // data[1] contains dnd mode of phone + // data[0] contains dnd mode of phone // 0 = INTERRUPTION_FILTER_UNKNOWN // 1 = INTERRUPTION_FILTER_ALL (all notifications pass) // 2 = INTERRUPTION_FILTER_PRIORITY // 3 = INTERRUPTION_FILTER_NONE (no notification passes) // 4 = INTERRUPTION_FILTER_ALARMS - byte mode = data[0]; - Log.d(TAG, "mode: " + mode); - byte dndStatePhone = data[1]; + byte dndStatePhone = data[0]; Log.d(TAG, "dndStatePhone: " + dndStatePhone); // get dnd state NotificationManager mNotificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE); -// if (!mNotificationManager.isNotificationPolicyAccessGranted()) { -// Toast.makeText(getApplicationContext(), "DNDSync missing DND permission!", Toast.LENGTH_SHORT).show(); -// Log.d(TAG, "DNDSync missing DND permission!"); -// } int filterState = mNotificationManager.getCurrentInterruptionFilter(); if (filterState < 0 || filterState > 4) { @@ -56,43 +50,17 @@ public void onMessageReceived (MessageEvent messageEvent) { byte currentDndState = (byte) filterState; Log.d(TAG, "currentDndState: " + currentDndState); - switch (mode) { - case 0: //dnd - { - if (dndStatePhone != currentDndState) { - mNotificationManager.setInterruptionFilter(dndStatePhone); -// Toast.makeText(getApplicationContext(), "DND set to " + dndStatePhone, Toast.LENGTH_LONG).show(); - Log.d(TAG, "DND set to " + dndStatePhone); - } - break; - } - case 1: //bedtime - { - if (dndStatePhone != currentDndState) { - toggleBedtimeMode(); - // set DND just in case bedtime toggle does not work to have at least DND - mNotificationManager.setInterruptionFilter(dndStatePhone); - Log.d(TAG, "DND set to " + dndStatePhone); - } - -// // now toggle bedtime mode -// Log.d(TAG, "toggle bedtime mode"); -// if(currentDndState == NotificationManager.INTERRUPTION_FILTER_ALL && dndStatePhone != NotificationManager.INTERRUPTION_FILTER_ALL) { -// // watch dnd is off but phone dnd is not off -> turn bedtime mode on -// Log.d(TAG, "DNDSync enables bedtime mode"); -// toggleBedtimeMode(); -// } else if (currentDndState != NotificationManager.INTERRUPTION_FILTER_ALL && dndStatePhone == NotificationManager.INTERRUPTION_FILTER_ALL) { -// // watch dnd is not off but phone dnd is off -> turn bedtime mode off -// Log.d(TAG, "DNDSync disables bedtime mode"); -// toggleBedtimeMode(); -// } - break; - } - default: - { - Log.d(TAG, "DNDSync mode went wrong: " + mode); + if (dndStatePhone != currentDndState) { + SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(this); + Boolean useBedtimeMode = prefs.getBoolean("bedtime_key", true); + if (useBedtimeMode) { + toggleBedtimeMode(); } + // set DND anyways, also in case bedtime toggle does not work to have at least DND + mNotificationManager.setInterruptionFilter(dndStatePhone); + Log.d(TAG, "DND set to " + dndStatePhone); } + } else { super.onMessageReceived(messageEvent); } diff --git a/wear/src/main/java/de/rhaeus/dndsync/MainActivity.java b/wear/src/main/java/de/rhaeus/dndsync/MainActivity.java index 8110477..2c8f6d7 100644 --- a/wear/src/main/java/de/rhaeus/dndsync/MainActivity.java +++ b/wear/src/main/java/de/rhaeus/dndsync/MainActivity.java @@ -24,58 +24,60 @@ protected void onCreate(Bundle savedInstanceState) { binding = ActivityMainBinding.inflate(getLayoutInflater()); setContentView(binding.getRoot()); -// Intent intent = new Intent(this, DummyNotificationListener.class); // fails because of permission -// startService(intent); - Button btnDndCheck = (Button) findViewById(R.id.btnDndCheck); - btnDndCheck.setOnClickListener(new View.OnClickListener() { - public void onClick(View v) { - -// Intent intent = new Intent(android.provider.Settings.ACTION_NOTIFICATION_LISTENER_SETTINGS); //fails -// startActivity(intent); +// Intent intent = new Intent(this, DummyNotificationListener.class); // fails because of permission +// startService(intent); -// // Check if the notification policy access has been granted for the app. - NotificationManager mNotificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE); -// int fil = mNotificationManager.getCurrentInterruptionFilter(); -// Toast.makeText(getApplicationContext(), "DND permission filter: " + fil, Toast.LENGTH_SHORT).show(); +// Button btnDndCheck = (Button) findViewById(R.id.btnDndCheck); +// btnDndCheck.setOnClickListener(new View.OnClickListener() { +// public void onClick(View v) { +// +//// Intent intent = new Intent(android.provider.Settings.ACTION_NOTIFICATION_LISTENER_SETTINGS); //fails +//// startActivity(intent); +// +// +//// // Check if the notification policy access has been granted for the app. +// NotificationManager mNotificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE); +//// int fil = mNotificationManager.getCurrentInterruptionFilter(); +//// Toast.makeText(getApplicationContext(), "DND permission filter: " + fil, Toast.LENGTH_SHORT).show(); +//// mNotificationManager.setInterruptionFilter(NotificationManager.INTERRUPTION_FILTER_PRIORITY); +// if (mNotificationManager.isNotificationPolicyAccessGranted()) { +// Toast.makeText(getApplicationContext(), "DND permission ok!", Toast.LENGTH_SHORT).show(); +// } else { +// Toast.makeText(getApplicationContext(), "DND permission missing!", Toast.LENGTH_SHORT).show(); +// } +// +// } +// }); +// +// Button btnAccCheck = (Button) findViewById(R.id.btnAccCheck); +// btnAccCheck.setOnClickListener(new View.OnClickListener() { +// public void onClick(View v) { +// serv = DNDSyncAccessService.getSharedInstance(); +// if (serv == null) { +// Toast.makeText(getApplicationContext(), "Accessibility service NOT connected!", Toast.LENGTH_SHORT).show(); +// } else { +// Toast.makeText(getApplicationContext(), "Accessibility service connected!", Toast.LENGTH_SHORT).show(); +// } +// } +// }); +// +// Button btnEnableDND = (Button) findViewById(R.id.btnEnableDND); +// btnEnableDND.setOnClickListener(new View.OnClickListener() { +// public void onClick(View v) { +// NotificationManager mNotificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE); // mNotificationManager.setInterruptionFilter(NotificationManager.INTERRUPTION_FILTER_PRIORITY); - if (mNotificationManager.isNotificationPolicyAccessGranted()) { - Toast.makeText(getApplicationContext(), "DND permission ok!", Toast.LENGTH_SHORT).show(); - } else { - Toast.makeText(getApplicationContext(), "DND permission missing!", Toast.LENGTH_SHORT).show(); - } - - } - }); - - Button btnAccCheck = (Button) findViewById(R.id.btnAccCheck); - btnAccCheck.setOnClickListener(new View.OnClickListener() { - public void onClick(View v) { - serv = DNDSyncAccessService.getSharedInstance(); - if (serv == null) { - Toast.makeText(getApplicationContext(), "Accessibility service NOT connected!", Toast.LENGTH_SHORT).show(); - } else { - Toast.makeText(getApplicationContext(), "Accessibility service connected!", Toast.LENGTH_SHORT).show(); - } - } - }); - - Button btnEnableDND = (Button) findViewById(R.id.btnEnableDND); - btnEnableDND.setOnClickListener(new View.OnClickListener() { - public void onClick(View v) { - NotificationManager mNotificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE); - mNotificationManager.setInterruptionFilter(NotificationManager.INTERRUPTION_FILTER_PRIORITY); - } - }); - Button btnDisableDND = (Button) findViewById(R.id.btnDisableDND); - btnDisableDND.setOnClickListener(new View.OnClickListener() { - public void onClick(View v) { - NotificationManager mNotificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE); - mNotificationManager.setInterruptionFilter(NotificationManager.INTERRUPTION_FILTER_ALL); - } - }); +// } +// }); +// Button btnDisableDND = (Button) findViewById(R.id.btnDisableDND); +// btnDisableDND.setOnClickListener(new View.OnClickListener() { +// public void onClick(View v) { +// NotificationManager mNotificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE); +// mNotificationManager.setInterruptionFilter(NotificationManager.INTERRUPTION_FILTER_ALL); +// } +// }); diff --git a/wear/src/main/java/de/rhaeus/dndsync/SettingsActivity.java b/wear/src/main/java/de/rhaeus/dndsync/SettingsActivity.java new file mode 100644 index 0000000..366afc1 --- /dev/null +++ b/wear/src/main/java/de/rhaeus/dndsync/SettingsActivity.java @@ -0,0 +1,33 @@ +package de.rhaeus.dndsync; + +import android.os.Bundle; + +import androidx.appcompat.app.ActionBar; +import androidx.appcompat.app.AppCompatActivity; +import androidx.preference.PreferenceFragmentCompat; + +public class SettingsActivity extends AppCompatActivity { + + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.settings_activity); + if (savedInstanceState == null) { + getSupportFragmentManager() + .beginTransaction() + .replace(R.id.settings, new SettingsFragment()) + .commit(); + } +// ActionBar actionBar = getSupportActionBar(); +// if (actionBar != null) { +// actionBar.setDisplayHomeAsUpEnabled(true); +// } + } + +// public static class SettingsFragment extends PreferenceFragmentCompat { +// @Override +// public void onCreatePreferences(Bundle savedInstanceState, String rootKey) { +// setPreferencesFromResource(R.xml.root_preferences, rootKey); +// } +// } +} \ No newline at end of file diff --git a/wear/src/main/java/de/rhaeus/dndsync/SettingsFragment.java b/wear/src/main/java/de/rhaeus/dndsync/SettingsFragment.java new file mode 100644 index 0000000..ea30a55 --- /dev/null +++ b/wear/src/main/java/de/rhaeus/dndsync/SettingsFragment.java @@ -0,0 +1,80 @@ +package de.rhaeus.dndsync; + +import android.app.NotificationManager; +import android.content.Context; +import android.content.Intent; +import android.os.Bundle; +import android.provider.Settings; +import android.widget.Toast; + +import androidx.preference.Preference; +import androidx.preference.PreferenceFragmentCompat; + +public class SettingsFragment extends PreferenceFragmentCompat { + private Preference dndPref; + private Preference accPref; + + @Override + public void onCreatePreferences(Bundle savedInstanceState, String rootKey) { + setPreferencesFromResource(R.xml.root_preferences, rootKey); + + dndPref = findPreference("dnd_permission_key"); + accPref = findPreference("acc_permission_key"); +// test = findPreference("test"); +// test.setOnPreferenceClickListener(new Preference.OnPreferenceClickListener() { +// public boolean onPreferenceClick(Preference preference) { +// +// return true; +// } +// }); + + dndPref.setOnPreferenceClickListener(new Preference.OnPreferenceClickListener() { + public boolean onPreferenceClick(Preference preference) { + if (!checkDNDPermission()) { + Toast.makeText(getContext(), "Follow the instructions to grant the permission via ADB!", Toast.LENGTH_SHORT).show(); + } + return true; + } + }); + + accPref.setOnPreferenceClickListener(new Preference.OnPreferenceClickListener() { + public boolean onPreferenceClick(Preference preference) { + if (!checkAccessibilityService()) { + openAccessibility(); + } + return true; + } + }); + + checkDNDPermission(); + checkAccessibilityService(); + + } + + private boolean checkAccessibilityService() { + DNDSyncAccessService serv = DNDSyncAccessService.getSharedInstance(); + boolean connected = serv != null; + if (connected) { + accPref.setSummary(R.string.acc_permission_allowed); + } else { + accPref.setSummary(R.string.acc_permission_not_allowed); + } + return connected; + } + + private boolean checkDNDPermission() { + NotificationManager mNotificationManager = (NotificationManager) getContext().getSystemService(Context.NOTIFICATION_SERVICE); + boolean allowed = mNotificationManager.isNotificationPolicyAccessGranted(); + if (allowed) { + dndPref.setSummary(R.string.dnd_permission_allowed); + } else { + dndPref.setSummary(R.string.dnd_permission_not_allowed); + } + return allowed; + } + + private void openAccessibility() { + Intent intent = new Intent(Settings.ACTION_ACCESSIBILITY_SETTINGS); + startActivity(intent); + } +} \ No newline at end of file diff --git a/wear/src/main/res/layout/activity_main.xml b/wear/src/main/res/layout/activity_main.xml index 940f4b3..3ab6ce4 100644 --- a/wear/src/main/res/layout/activity_main.xml +++ b/wear/src/main/res/layout/activity_main.xml @@ -1,51 +1,8 @@ - - - - - - - - -