@@ -5,6 +5,7 @@ | |||
<option name="linkedExternalProjectsSettings"> | |||
<GradleProjectSettings> | |||
<option name="testRunner" value="PLATFORM" /> | |||
<option name="disableWrapperSourceDistributionNotification" value="true" /> | |||
<option name="distributionType" value="DEFAULT_WRAPPED" /> | |||
<option name="externalProjectPath" value="$PROJECT_DIR$" /> | |||
<option name="gradleJvm" value="JDK" /> |
@@ -2,6 +2,7 @@ | |||
<manifest xmlns:android="http://schemas.android.com/apk/res/android" | |||
package="com.example.fcm"> | |||
<uses-permission android:name="android.permission.INTERNET" /> | |||
<uses-permission android:name="android.permission.VIBRATE" /> | |||
<uses-permission android:name="com.google.android.c2dm.permission.RECEIVE" /> | |||
<application | |||
android:allowBackup="true" | |||
@@ -10,13 +11,13 @@ | |||
android:roundIcon="@mipmap/ic_launcher_round" | |||
android:supportsRtl="true" | |||
android:theme="@style/Theme.App"> | |||
<service android:name=".MyFirebaseMessagingService" | |||
<service android:name="com.example.fcm.MyFirebaseMessagingService" | |||
android:exported="false"> | |||
<intent-filter> | |||
<action android:name="com.google.firebase.MESSAGING_EVENT" /> | |||
</intent-filter> | |||
</service> | |||
<activity android:name=".MainActivity"> | |||
<activity android:name="com.example.fcm.MainActivity"> | |||
<intent-filter> | |||
<action android:name="android.intent.action.MAIN" /> | |||
@@ -5,10 +5,14 @@ import androidx.appcompat.app.AppCompatActivity; | |||
import android.annotation.SuppressLint; | |||
import android.app.NotificationChannel; | |||
import android.app.NotificationManager; | |||
import android.content.Context; | |||
import android.os.Build; | |||
import android.os.Bundle; | |||
import android.os.VibrationEffect; | |||
import android.os.Vibrator; | |||
import android.util.Log; | |||
import android.widget.Button; | |||
import android.widget.EditText; | |||
import android.widget.Toast; | |||
import com.android.volley.toolbox.JsonObjectRequest; | |||
import com.example.fcm.databinding.ActivityMainBinding; | |||
@@ -28,6 +32,7 @@ public class MainActivity extends AppCompatActivity { | |||
final private String FCM_API = "https://fcm.googleapis.com/fcm/send"; | |||
final private String serverKey = "key=" + "AAAA446tEwQ:APA91bEAqpEFQ0ufbp9WSFIGV68P8kUgNlnKzuEHIcWLeS1YlMwJewRdnAGRae0VpDzriag7ZQbMUMPDiT-LD1kTXLQFM73C9DC13iN4nn9gEYCPVp4MN8JHFm20m1BxS8zWZcKDYFcz"; | |||
final private String contentType = "application/json"; | |||
final private String topic = "vibration"; | |||
private static final String TAG = "MainActivity"; | |||
String NOTIFICATION_TITLE; | |||
@@ -41,6 +46,9 @@ public class MainActivity extends AppCompatActivity { | |||
setContentView(binding.getRoot()); | |||
Button buttonSend = findViewById(R.id.sendButton); | |||
EditText level = findViewById(R.id.level); | |||
EditText delay = findViewById(R.id.delay); | |||
EditText duration = findViewById(R.id.duration); | |||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { | |||
// Create channel to show notifications. | |||
@@ -72,7 +80,7 @@ public class MainActivity extends AppCompatActivity { | |||
binding.subscribeButton.setOnClickListener(v -> { | |||
Log.d(TAG, "Subscribing to topic"); | |||
// [START subscribe_topics] | |||
FirebaseMessaging.getInstance().subscribeToTopic("testForMDT") | |||
FirebaseMessaging.getInstance().subscribeToTopic(topic) | |||
.addOnCompleteListener(task -> { | |||
String msg = getString(R.string.msg_subscribed); | |||
if (!task.isSuccessful()) { | |||
@@ -106,15 +114,18 @@ public class MainActivity extends AppCompatActivity { | |||
}); | |||
buttonSend.setOnClickListener(v -> { | |||
TOPIC = "/topics/testForMDT"; //topic must match with what the receiver subscribed to | |||
NOTIFICATION_TITLE = "Test"; | |||
NOTIFICATION_MESSAGE = "Gregor"; | |||
TOPIC = "/topics/" + topic; //topic must match with what the receiver subscribed to | |||
NOTIFICATION_TITLE = "Test values"; | |||
NOTIFICATION_MESSAGE = "von Gregor"; | |||
JSONObject notification = new JSONObject(); | |||
JSONObject notifcationBody = new JSONObject(); | |||
try { | |||
notifcationBody.put("title", NOTIFICATION_TITLE); | |||
notifcationBody.put("message", NOTIFICATION_MESSAGE); | |||
notifcationBody.put("level", level.getText().toString()); | |||
notifcationBody.put("delay", delay.getText().toString()); | |||
notifcationBody.put("duration", duration.getText().toString()); | |||
notification.put("to", TOPIC); | |||
notification.put("data", notifcationBody); | |||
@@ -146,4 +157,5 @@ public class MainActivity extends AppCompatActivity { | |||
}; | |||
MySingleton.getInstance(getApplicationContext()).addToRequestQueue(jsonObjectRequest); | |||
} | |||
} |
@@ -9,6 +9,8 @@ import android.graphics.Color; | |||
import android.media.RingtoneManager; | |||
import android.net.Uri; | |||
import android.os.Build; | |||
import android.os.VibrationEffect; | |||
import android.os.Vibrator; | |||
import android.util.Log; | |||
import androidx.annotation.RequiresApi; | |||
@@ -64,12 +66,29 @@ public class MyFirebaseMessagingService extends FirebaseMessagingService { | |||
PendingIntent pendingIntent = PendingIntent.getActivity(this , 0, intent, | |||
PendingIntent.FLAG_ONE_SHOT); | |||
String title = remoteMessage.getData().get("title"); | |||
String message = remoteMessage.getData().get("message"); | |||
String level = remoteMessage.getData().get("level"); | |||
String delay = remoteMessage.getData().get("delay"); | |||
String duration = remoteMessage.getData().get("duration"); | |||
String wholeMessage = message + "," + level + "," + delay + "," + duration; | |||
//MainActivity main = new Vibration(); | |||
assert level != null; | |||
assert delay != null; | |||
assert duration != null; | |||
try { | |||
triggerVibration(Integer.parseInt(level), Integer.parseInt(delay), Integer.parseInt(duration)); | |||
} catch (InterruptedException e) { | |||
e.printStackTrace(); | |||
} | |||
Uri notificationSoundUri = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION); | |||
NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this, ADMIN_CHANNEL_ID) | |||
.setSmallIcon(R.drawable.ic_stat_ic_notification) | |||
.setContentTitle(remoteMessage.getData().get("title")) | |||
.setContentText(remoteMessage.getData().get("message")) | |||
.setContentTitle(title) | |||
.setContentText(wholeMessage) | |||
.setAutoCancel(true) | |||
.setSound(notificationSoundUri) | |||
.setContentIntent(pendingIntent); | |||
@@ -187,17 +206,6 @@ public class MyFirebaseMessagingService extends FirebaseMessagingService { | |||
notificationManager.notify(0 /* ID of notification */, notificationBuilder.build()); | |||
} | |||
//public static void sendNotificationToUser(String user, final String message) { | |||
// Firebase ref = new Firebase(FIREBASE_URL); | |||
// final Firebase notifications = ref.child("notificationRequests"); | |||
//Map notification = new HashMap<>(); | |||
// notification.put("username", user); | |||
// notification.put("message", message); | |||
// notifications.push().setValue(notification); | |||
//} | |||
@RequiresApi(api = Build.VERSION_CODES.O) | |||
private void setupChannels(NotificationManager notificationManager){ | |||
CharSequence adminChannelName = "New notification"; | |||
@@ -214,6 +222,23 @@ public class MyFirebaseMessagingService extends FirebaseMessagingService { | |||
} | |||
} | |||
public void triggerVibration(int level, int delay, int duration) throws InterruptedException { | |||
Log.i("Vibration","triggerVibration"); | |||
Log.i("Vibration","level:" + level); | |||
Log.i("Vibration","delay:" + delay + "ms"); | |||
Log.i("Vibration","duration:" + duration + "ms"); | |||
Vibrator a = (Vibrator) getSystemService(Context.VIBRATOR_SERVICE); | |||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { | |||
try { | |||
Thread.sleep(delay); | |||
} catch(InterruptedException ex){ | |||
Thread.currentThread().interrupt(); | |||
} | |||
a.vibrate(VibrationEffect.createOneShot(duration, level)); | |||
} else { | |||
//deprecated in API 26 | |||
a.vibrate(2000); | |||
} | |||
} | |||
} |
@@ -0,0 +1,34 @@ | |||
package com.example.fcm; | |||
import android.content.Context; | |||
import android.os.Build; | |||
import android.os.VibrationEffect; | |||
import android.os.Vibrator; | |||
import android.util.Log; | |||
import androidx.appcompat.app.AppCompatActivity; | |||
public class Vibration extends AppCompatActivity { | |||
public void triggerVibration(int level, int delay, int duration) throws InterruptedException { | |||
Log.i("Vibration","triggerVibration"); | |||
Log.i("Vibration","level:" + level); | |||
Log.i("Vibration","delay:" + delay); | |||
Log.i("Vibration","duration:" + duration); | |||
Vibrator a = (Vibrator) getSystemService(Context.VIBRATOR_SERVICE); | |||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { | |||
try { | |||
Thread.sleep(delay); | |||
} catch(InterruptedException ex){ | |||
Thread.currentThread().interrupt(); | |||
} | |||
a.vibrate(VibrationEffect.createOneShot(duration, level)); | |||
} else { | |||
//deprecated in API 26 | |||
a.vibrate(2000); | |||
} | |||
} | |||
} |
@@ -11,14 +11,6 @@ | |||
android:paddingTop="@dimen/activity_vertical_margin" | |||
tools:context=".MainActivity"> | |||
<TextView | |||
android:id="@+id/informationTextView" | |||
android:layout_width="wrap_content" | |||
android:layout_height="wrap_content" | |||
android:layout_gravity="center_horizontal" | |||
android:gravity="center_horizontal" | |||
android:text="@string/quickstart_message" /> | |||
<Button | |||
android:id="@+id/subscribeButton" | |||
android:layout_width="@dimen/standard_field_width" | |||
@@ -34,12 +26,36 @@ | |||
android:layout_gravity="center_horizontal" | |||
android:text="@string/log_token" /> | |||
<EditText | |||
android:id="@+id/level" | |||
android:layout_width="200dp" | |||
android:layout_height="wrap_content" | |||
android:layout_gravity="center_horizontal" | |||
android:hint="Level (1-255)" | |||
/> | |||
<EditText | |||
android:id="@+id/delay" | |||
android:layout_width="200dp" | |||
android:layout_height="wrap_content" | |||
android:layout_gravity="center_horizontal" | |||
android:hint="Delay (ms)" | |||
/> | |||
<EditText | |||
android:id="@+id/duration" | |||
android:layout_width="200dp" | |||
android:layout_height="wrap_content" | |||
android:layout_gravity="center_horizontal" | |||
android:hint="Duration (ms)" | |||
/> | |||
<Button | |||
android:id="@+id/sendButton" | |||
android:layout_width="@dimen/standard_field_width" | |||
android:layout_height="wrap_content" | |||
android:layout_gravity="center_horizontal" | |||
android:text="Send message" /> | |||
android:text="Send Command" /> | |||
</LinearLayout> |
@@ -3,7 +3,7 @@ | |||
<string name="quickstart_message">Quickstart message</string> | |||
<string name="log_token">Log token</string> | |||
<string name="subscribe_to_weather">Subscribe</string> | |||
<string name="msg_subscribed">Subscribed to testForMDT topic</string> | |||
<string name="msg_subscribed">Subscribed to vibration topic</string> | |||
<string name="msg_token_fmt" translatable="false">InstanceID Token: %s</string> | |||
<string name="default_notification_channel_id" translatable="false">fcm_default_channel</string> | |||
@@ -12,9 +12,9 @@ | |||
It should describe the category of notifications that will be sent through this channel | |||
--> | |||
<!-- [START fcm_default_icon_string] --> | |||
<string name="default_notification_channel_name" translatable="true">testForMDT</string> | |||
<string name="default_notification_channel_name" translatable="true">vibration</string> | |||
<!-- [END fcm_default_icon_string] --> | |||
<string name="msg_subscribe_failed">Failed to subscribe to testForMDT topic</string> | |||
<string name="msg_subscribe_failed">Failed to subscribe to vibration topic</string> | |||
<string name="fcm_message">FCM Message</string> | |||
<string name="subscribe">Subscribe</string> | |||
</resources> |