protected void onPause()
{
super.onPause();
// If the screen is off then the device has been locked
PowerManager powerManager = (PowerManager) getSystemService(POWER_SERVICE);
boolean isScreenOn = powerManager.isScreenOn();
//screen locked
if (!isScreenOn) {
boolean pressed = onKeyDown(26, null);
//power button pressed
if(pressed){
//remove keyguard
getWindow().addFlags(WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED);
getWindow().addFlags(WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD);
//start intent
Intent i = new Intent(this, VoiceRecognitionActivity.class);
startActivity(i);
}
}
}
the above code does is when power button is pressed, the keyguard will be dismissed and the activity onpaused will be resumed.
However, the keyguard is not dimissed when i pressed the power button, and i have to unlock manually.
When i pressed the power button, the window of my activity flashed for a second and the keyguard window is shown.
If you want to prevent phone from turning screen off (and locking the phone in result) you should use WakeLock. You can use PowerManager.newWakeLock() with FLAG_KEEP_SCREEN_ON or even
FULL_WAKE_LOCK.
This code snippet may help:
final Window win = getWindow();
win.addFlags(WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED
| WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD);
// Turn on the screen unless we are being launched from the AlarmAlert
// subclass.
final boolean screenOff = getIntent().getBooleanExtra(SCREEN_OFF, false);
if (!screenOff) {
try {
// API 8+
win.addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON
| WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON
| WindowManager.LayoutParams.FLAG_ALLOW_LOCK_WHILE_SCREEN_ON);
} catch (final Throwable whocares) {
// API 7+
win.addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON
| WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON);
}
}
Related
For my app I'm trying to get it where the notification wakes up the screen and displays a view from the app. I can't figure how to get the app to wake up when its in a lock screen. I've tried a few things but none seem to work or they crash the app.
There is my solution:
createNotification(); //your implementation
PowerManager pm = (PowerManager) context.getSystemService(Context.POWER_SERVICE);
boolean isScreenOn = Build.VERSION.SDK_INT >= 20 ? pm.isInteractive() : pm.isScreenOn(); // check if screen is on
if (!isScreenOn) {
PowerManager.WakeLock wl = pm.newWakeLock(PowerManager.SCREEN_DIM_WAKE_LOCK | PowerManager.ACQUIRE_CAUSES_WAKEUP, "myApp:notificationLock");
wl.acquire(3000); //set your time in milliseconds
}
More at PowerManager
This BroadCastReceiver Works For, your App Is in back ground State/ mobile In lock mode. That time when notification is recieved i have to redirect particular screen, for that one i added Intent code,
After receiving Notification this code helps to your requirement
public class FirebaseDataReceiver extends WakefulBroadcastReceiver {
private final String TAG = "FirebaseDataReceiver";
public void onReceive(Context context, Intent intent) {
PowerManager pm = (PowerManager)context.getSystemService(Context.POWER_SERVICE);
boolean isScreenOn = pm.isScreenOn();
if(isScreenOn==false)
{
PowerManager.WakeLock wl = pm.newWakeLock(PowerManager.FULL_WAKE_LOCK |PowerManager.ACQUIRE_CAUSES_WAKEUP |PowerManager.ON_AFTER_RELEASE,"MyLock");
wl.acquire(10000);
PowerManager.WakeLock wl_cpu = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK,"MyCpuLock");
wl_cpu.acquire(10000);
}
//Redirect particular screen after receiving notification, this is like ola driver app concept accepting driver request
intent = new Intent(context, MyTicketListActivity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(intent);
}
}
Also remember to specify the permission used in the AndroidManifest.xml:
<uses-permission android:name="android.permission.WAKE_LOCK" />
I faced a similar situation. It was required to show a notification screen for the user to accept or reject the notification, even when the screen is off. I fumbled with it for a while until now. The requirements demand the screen should be on and this can be achieved with a combination of flags for the window manager and the wake lock as shown below.
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
PowerManager pm = (PowerManager) this.getSystemService(Context.POWER_SERVICE);
boolean isScreenOn = pm.isScreenOn();
int flags = PowerManager.FULL_WAKE_LOCK
| PowerManager.ACQUIRE_CAUSES_WAKEUP
| PowerManager.ON_AFTER_RELEASE;
if (!isScreenOn) {
wakeLock = pm.newWakeLock(flags, "my_app:full_lock");
wakeLock.acquire(20000);
}
setContentView(R.layout.activity_incoming_request);
getWindow().addFlags(WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED |
WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON |
WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON |
WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD |
WindowManager.LayoutParams.FLAG_ALLOW_LOCK_WHILE_SCREEN_ON);
...
startRingingPhone();
}
This code block will display the activity on the lock screen.
Put below code before notification creates,
PowerManager powerManager = (PowerManager) context.getSystemService(context.POWER_SERVICE);
PowerManager.WakeLock wakeLock = powerManager.newWakeLock(PowerManager.FULL_WAKE_LOCK |
PowerManager.ACQUIRE_CAUSES_WAKEUP |
PowerManager.ON_AFTER_RELEASE, "appname::WakeLock");
//acquire will turn on the display
wakeLock.acquire(1*60*1000L);
And make sure to set this permission in the manifest :
<uses-permission android:name="android.permission.WAKE_LOCK"/>
I'm developing a music player application. In which, I want to display a small floating button on screen for play/pause event when app is minimized(paused). (Functionality like face book messenger chat head). It works perfectly fine on devices which has SDK < 23. But in Device with SDK >= 23, It asks for permission only 1st time when app in installed.
If permission is granted, it also perfectly displays floating button. But once the app is closed and again started, It is not showing floating button any more.
my code for opening permission dialogue box is:
public final static int REQUEST_CODE = 100;
public void checkDrawOverlayPermission() {
/** check if we already have permission to draw over other apps */
if (!Settings.canDrawOverlays(this)) {
/** if not construct intent to request permission */
Intent intent = new Intent(Settings.ACTION_MANAGE_OVERLAY_PERMISSION,
Uri.parse("package:" + getPackageName()));
/** request permission via start activity for result */
startActivityForResult(intent, REQUEST_CODE);
}
}
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
/** check if received result code
is equal our requested code for draw permission */
if (requestCode == REQUEST_CODE) {
if (Settings.canDrawOverlays(this)) {
// continue here - permission was granted
if(isServiceRunning != true){
isServiceRunning = true;
intent12 = new Intent(this, notificationService.class);
bindService(intent12, notificationConnection, Context.BIND_AUTO_CREATE);
startService(intent12);
}
}
}
}
I'm displaying floating button when app is paused(when home button or back button is pressed to minimize the app). So I'm calling this checkDrawOverlayPermission() method in onPause() method of my apps mainActivity, like this:
#Override
protected void onPause() {
super.onPause();
if (Build.VERSION.SDK_INT >= 23) {
checkDrawOverlayPermission();
} else {
if(isServiceRunning != true){
isServiceRunning = true;
intent12 = new Intent(this, notificationService.class);
bindService(intent12, notificationConnection, Context.BIND_AUTO_CREATE);
startService(intent12);
}
}
}
But I can't understand what I'm missing here. I think code for checking permission is ok because first time it displays floating button on the screen along with asking permission in a small dialogue. Please help. Thanks!
You are not doing anything if the permission is already given in SDK > 23.
Add an else part to the checkDrawOverlayPermission method like this.
public void checkDrawOverlayPermission() {
/** check if we already have permission to draw over other apps */
if (!Settings.canDrawOverlays(this)) { // WHAT IF THIS EVALUATES TO FALSE.
/** if not construct intent to request permission */
Intent intent = new Intent(Settings.ACTION_MANAGE_OVERLAY_PERMISSION,
Uri.parse("package:" + getPackageName()));
/** request permission via start activity for result */
startActivityForResult(intent, REQUEST_CODE);
} else { // ADD THIS.
// Add code to bind and start the service directly.
}
}
How can I have a timer fire a method to wake up the screen of an Android device?
I inserted this:
final Window win = getWindow();
win.addFlags(WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED
| WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD);
win.addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON
| WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON);
into the
#Override
protected void onCreate(Bundle savedInstanceState) {
method.
Additionally, I made a timer after a user clicks a button which runs the following program:
final int interval = 3000; // 3 Seconds
Handler handler = new Handler();
Runnable runnable = new Runnable(){
public void run() {
Toast.makeText(getApplicationContext(), "Here", Toast.LENGTH_SHORT).show();
}
};
handler.postAtTime(runnable, System.currentTimeMillis()+interval);
handler.postDelayed(runnable, interval);
I want to be able to click the power button of my Android device to sleep it within the 3 second interval and have it wake up after the run() gets fired.
What do I call to trigger the screen to turn on?
This method also instantly turns on the screen:
PowerManager powerManager = (PowerManager) getSystemService(Context.POWER_SERVICE);
PowerManager.WakeLock TempWakeLock = powerManager.newWakeLock(PowerManager.SCREEN_DIM_WAKE_LOCK|PowerManager.ACQUIRE_CAUSES_WAKEUP, "TempWakeLock");
TempWakeLock.acquire();
TempWakeLock.release();
try to add to onCreate() :
PowerManager pm = (PowerManager) getApplicationContext().getSystemService(Context.POWER_SERVICE);
WakeLock wakeLock = pm.newWakeLock((PowerManager.SCREEN_BRIGHT_WAKE_LOCK | PowerManager.FULL_WAKE_LOCK | PowerManager.ACQUIRE_CAUSES_WAKEUP), "TAG");
wakeLock.acquire();
To release the screen lock:
KeyguardManager keyguardManager = (KeyguardManager) getApplicationContext().getSystemService(Context.KEYGUARD_SERVICE);
KeyguardLock keyguardLock = keyguardManager.newKeyguardLock("TAG");
keyguardLock.disableKeyguard();
Add to the manifest:
<uses-permission android:name="android.permission.WAKE_LOCK" />
<uses-permission android:name="android.permission.DISABLE_KEYGUARD" />
I've created an application where you press "start logging" which starts a service that periodically logs data. The button changes to show "stop logging". You then minimize the application and allow it to log in the background whilst you go about your business. However, I have had to implement "startForeground" as the application would close/be destroyed, and with "startForeground" a notification is required.
Now, when I run the application and minimize, then re-open the app, it is fine, but if i attempt to reopen via the notification it resets the screen so that the button now says "start logging" again and when clicked, starts logging again (takes over the current service). The service was still logging even when it said "start logging" so it has something to do with the screen not saving the button state I assume?
I have tried this, but to no avail:
#Override
public void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
outState.putString("message", (String) but1.getText());
}
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.logorcheck);
System.out.println("goes in oncreate");
if (savedInstanceState != null) {
but1.setText(savedInstanceState.getString("message"));
Here are a few snippets:
LoggingService.java
NotificationManager nm = (NotificationManager) this
.getSystemService(Context.NOTIFICATION_SERVICE);
Resources res = this.getResources();
Notification.Builder builder = new Notification.Builder(this);
builder.setContentIntent(contentIntent)
.setSmallIcon(R.drawable.arrow_up_float)
.setLargeIcon(BitmapFactory.decodeResource(res, R.drawable.arrow_down_float))
.setWhen(System.currentTimeMillis())
.setAutoCancel(true)
.setContentTitle("App")
.setContentText("Service running OK");
Notification n = builder.getNotification();
// !
startForeground(100, n);
return Service.START_STICKY;
LogOrCheck.java
if (isClicked) {
Context context = getApplicationContext();
Toast toast = Toast.makeText(context, "Please press 'MINIMIZE' at the top to continue logging.", Toast.LENGTH_LONG);
toast.setGravity(Gravity.TOP|Gravity.RIGHT, 10, 55);
toast.show();
System.out.println("Start logging");
but1.setText("Stop Logging");
but1.setTextColor(Color.RED);
// START SERVICE, DONE. (STOP IS BELOW).
startService(myIntent);
isClicked = false;
}
else if (!isClicked) {
System.out.println("Stop Logging");
but1.setText("Start Logging");
// STOP SERVICE, DONE.
stopService(myIntent);
but1.setTextColor(Color.BLACK);
isClicked = true;
}
Thanks for any help, it seems an easy fix that I can't figure out how to do it, especially with notificationBuilder. Sorry for the long message! Thanks.
The Simplest thing you could do would be to create a static boolean variable in your LoggingService.java something like isLogging and set it accordingly in the service when changes occur.
In the onResume() of the activity access that variable and set the button state accordingly.
I want to implement the following scenario:
When a user presses the Home key a Notification is displayed in the Status bar and the App is normally hidden. When user taps the Notification App is normally restored.
Here is my code for this:
private int NOTIFICATION = R.string.local_service_started;
private NotificationManager mNM;
private void showNotification() {
CharSequence text = getText(R.string.local_service_started);
Notification notification = new Notification(R.drawable.icon, text, System.currentTimeMillis());
PendingIntent contentIntent = PendingIntent.getActivity(this, 0, new Intent(this, JingleCartoucheActivity.class), 0);
notification.setLatestEventInfo(this, getText(R.string.local_service_label), text, contentIntent);
mNM.notify(NOTIFICATION, notification);
}
#Override
public void onPause() {
super.onPause();
if (!isFinishing()) {
showNotification();
}
}
#Override
public void onResume() {
super.onResume();
mNM.cancel(NOTIFICATION);
}
All of this is working well except for one thing:
When the App is run and the user rotates the phone, the notification is created and immediately destroyed. Is there a way to detect the phone orientation change in onPause() and not show this Notification?
You can get the current orientation using the getResources().getConfiguration().orientation. At the onCreate you store the orientation value and then you can compare it later. Be sure to store the value into a static variable, since when you rotate the phone, the activity is destroyed and so are it's values.
When the user rotate the screen the activity is destroyed and recreated , If you want to display the notification after orientation change make a static flag in onDestroy method and check it in the onCreate method to display the notification like
public void onDestroy() {
Flag = 1;
}
and
public static int Flag = 0;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
if(Flag == 1) {
showNotification();
}
else {
.......//
}
}