Android: How to get allowTaskReparenting="true" to work - android

I am writing an app that can be launched from another app by receiving an intent with ACTION_VIEW or ACTION_EDIT. For example, it can be opened by viewing an email attachment. The trouble is that when you click on the home button and click again on the launch icon of the email app you were using, my activity is killed and any user edits that had been made are lost. What I want to happen is that when the user clicks the home button, my activity is re-parented so that it resumes when the user clicks on the launch icon of my app. I've tried setting android:allowTaskReparenting="true" in manifest.xml but this doesn't work. Sometimes it doesn't have any effect at all, and sometimes the activity is moved to my launch icon, yet still gets killed when you click again on the email app icon.
The documentation on allowTaskReparenting is really vague. It says the property means:
“Whether or not the activity can move from the task that started it to the task it has an affinity for.”
What does the word can mean here? What I want is a guarantee that the activity does move (and stays there). Is there any way to achieve this?
Thanks in advance to anyone who can help.
EDIT
In response to comments below, I have put together a baby version demonstrating the problems I am encountering. When you start EditFileActivity by clicking on a file in another app (e.g, an attachment to an email) you can then edit the file. But clicking on the home icon and then clicking again on the email app icon causes the changes you have made to the file to be lost. I want the android system to only forget about an instance of EditFileActivity if the user explicitly clicks back and then says "yes" or "no". Ideally I want all instances of EditFileActivity to stack up on my app's launch icon. I could implement something similar to this by using singleTask or singleInstance and writing some kind of activity showing all open files in tabs, but it would be much easier if I could get the android system itself to help me. Any ideas?
Here is a complete project demonstrating the problem.
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.Example"
android:versionCode="1"
android:versionName="1.0">
<uses-sdk
android:minSdkVersion="11"
android:targetSdkVersion="11"/>
<application
android:label="Example"
android:icon="#drawable/ic_launcher">
<activity
android:name=".LaunchActivity"
android:label="LaunchActivity"
android:screenOrientation="portrait">
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
</activity>
<activity
android:name=".EditFileActivity"
android:label="EditFileActivity"
android:screenOrientation="portrait">
<!-- This is just an example. I wouldn't use this intent filter in a real app! -->
<intent-filter>
<action android:name="android.intent.action.VIEW"/>
<action android:name="android.intent.action.EDIT"/>
<category android:name="android.intent.category.DEFAULT"/>
<category android:name="android.intent.category.BROWSABLE"/>
<data android:scheme="file"/>
<data android:scheme="content"/>
<data android:mimeType="*/*"/>
<data android:host="*"/>
</intent-filter>
</activity>
</application>
</manifest>`
LaunchActivity:
public class LaunchActivity extends Activity {
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
TextView textView = new TextView(this);
textView.setText("This is the activity you see when you click on the application's launch icon. It does absolutely nothing.");
textView.setTextSize(18);
setContentView(textView);
}
}
EditFileActivity:
public class EditFileActivity extends Activity {
// This String represents the contents of the file.
// In a "real" app the String would be initialised by reading the data from the Intent that started the activity.
// However, for the purposes of this example, the initial value is "Default".
private String fileContents = "Default";
private boolean editsMade = false;
private TextView textView;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
textView = new TextView(this);
textView.setText(fileContents);
textView.setTextSize(18);
textView.setPadding(10, 10, 10, 10);
setContentView(textView);
textView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
makeEdits();
}
});
}
#Override
public void onBackPressed() {
if (editsMade) {
savePrompt();
} else {
finish();
}
}
private void savePrompt() {
DialogInterface.OnClickListener listener = new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
if (which == Dialog.BUTTON_POSITIVE) {
// Here is where I would save the edited file.
Toast.makeText(EditFileActivity.this, "File saved", Toast.LENGTH_LONG).show();
}
finish();
}
};
new AlertDialog.Builder(this)
.setTitle("Close File")
.setMessage("Do you want to save the changes you made?")
.setPositiveButton("Yes", listener)
.setNegativeButton("No", listener)
.show();
}
private void makeEdits() {
final EditText editText = new EditText(this);
editText.setText(fileContents);
new AlertDialog.Builder(this)
.setTitle("Edit File")
.setView(editText)
.setPositiveButton("OK", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int whichButton) {
Editable editable = editText.getText();
assert editable != null;
String newContents = editable.toString();
if (!fileContents.equals(newContents)) {
editsMade = true;
fileContents = newContents;
textView.setText(fileContents);
}
}
})
.setNegativeButton("Cancel", null)
.show();
}
}
UPDATE 10/12/2014
The problems encountered were due to the use of the Intent flag FLAG_ACTIVITY_CLEAR_WHEN_TASK_RESET.
Fortunately, Google have deprecated this flag, as of API Level 21.

Issue:
The trouble is that when you click on the home button and click again
on the launch icon of the email app you were using, my activity is
killed and any user edits that had been made are lost.
This happens because the email application had set FLAG_ACTIVITY_CLEAR_WHEN_TASK_RESET intent flag while launching your activity. When this flag is set, next time when the task is brought to the foreground, your activity will be finished, so that user returns to the previous activity.
From docs:
This is useful for cases where you have a logical break in your
application. For example, an e-mail application may have a command to
view an attachment, which launches an image view activity to display
it. This activity should be part of the e-mail application's task,
since it is a part of the task the user is involved in. However, if
the user leaves that task, and later selects the e-mail app from home,
we may like them to return to the conversation they were viewing, not
the picture attachment, since that is confusing. By setting this flag
when launching the image viewer, that viewer and any activities it
starts will be removed the next time the user returns to mail.
Solution:
Use singleTask launchMode for your activity. The email app will not kill your activity, as the activity belongs to different task now.
If the activity instance is already in the task and an attempt is made to launch the activity again, then a new instance is not created. Instead onNewIntent is called. Here you can prompt the user to save the previous edit if any, before presenting new content.

As discussed above, the system's default behavior preserves the state
of an activity when it is stopped. This way, when users navigate back
to a previous activity, its user interface appears the way they left
it. However, you can—and should—proactively retain the state of your
activities using callback methods, in case the activity is destroyed
and must be recreated.
When the system stops one of your activities (such as when a new
activity starts or the task moves to the background), the system might
destroy that activity completely if it needs to recover system memory.
When this happens, information about the activity state is lost. If
this happens, the system still knows that the activity has a place in
the back stack, but when the activity is brought to the top of the
stack the system must recreate it (rather than resume it). In order to
avoid losing the user's work, you should proactively retain it by
implementing the onSaveInstanceState() callback methods in your
activity.
Source

Related

Backstack not cleared when notification clicked

I'm using Firebase Cloud Messenger (FCM) to push notifications to my app.
The notifications are received when the app is in the background so onMessageReceived is not triggered as the notification doesn't have a payload (data). Everything is fine with that but it means I can't create my own notification as everything is automatically handled by System tray.
When I click the notification I expect the entire backstack to be cleared and the app to restart from scratch. Basically I want the opposite of this post.
This is supposed to be the default behaviour.
However, when I click on the notification, if the app was already opened, the app restarts from the launcher but on top of the existing backstack.
For instance if you have:
HomeScreen -> Page1
when the notification is clicked, you now have in the stack:
HomeScreen -> Page1 -> HomeScreen
when it's supposed to only be:
HomeScreen
My launcher is an Activity only displayed when the app starts so I don't want it to be kept in the backstack. I turns out this this why I get this issue. So basically if the Launcher Activity calls finish() on itself and/or has noHistory="true" set in the Manifest, the backstack is not cleared when the notification is clicked.
How can I solve this issue?
I found a solution. The idea is to create a new LauncherActivity in charge of launching the existing one and clearing the backstack in the process.
There are probably other ways to do that but I wanted to keep the original Launcher with noHistory="true" as otherwise I have issue with the transition animation with the next Activity if I implemented the below solution directly to it.
The new Launcher is called StartActivity
In the Manifest:
<activity
android:name=".StartActivity"
android:screenOrientation="portrait"
android:theme="#style/AppTheme">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
The Activity:
public class StartActivity extends AppCompatActivity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Intent intent = new Intent(this, LauncherActivity.class);
// Add the flags to clear the stack
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK | Intent.FLAG_ACTIVITY_NEW_TASK);
// Start the intent with a defined transition animation. The animation is not
// required but it make the transition seamless.
startActivity(intent, getFadeInOutAnimation(this));
// Necessary for the app not to crash. Basically just a FrameLayout
setContentView(R.layout.activity_start);
}
public static Bundle getFadeInOutAnimation(Context context) {
// Allows us to display a fading animation as transition between the activities.
// The animation can be whatever you want
return ActivityOptions.makeCustomAnimation(context,
R.anim.fade_in, R.anim.fade_out).toBundle();
}
}

Android: Sharing Data and Receiving text from 3rd party app. Why doesn't my app receive new text?

Summary
I am attempting to get data sent from the user via the Share menu. In this case, I'll use the basic Android web browser to select text and then share it to my app.
Problem
The first time the user shares the text my app gets the text as expected and displays it via Log.d() -- see the handleSendText() method in the code below.
However, each time thereafter even though the user has selected new text in the web browser and shared it with my app, I still get the original text the user selected (previous value).
Question
How do you reset the Intent -- or whatever it is -- so that I can obtain the new text the user has selected after the first time?
Details
My application has a MainActivity and I've followed the Google docs at :
http://developer.android.com/training/sharing/receive.html
With code like the following in my MainActivity
public class MainActivity extends AppCompatActivity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Intent intent = getIntent();
String action = intent.getAction();
String type = intent.getType();
if (Intent.ACTION_SEND.equals(action) && type != null) {
if ("text/plain".equals(type)) {
handleSendText(intent, "onCreate"); // Handle text being sent
}
}
}
#Override
public void onResume(){
super.onResume();
Intent intent = getIntent();
String action = intent.getAction();
String type = intent.getType();
if (Intent.ACTION_SEND.equals(action) && type != null) {
if ("text/plain".equals(type)) {
handleSendText(intent, "onResume"); // Handle text being sent
}
}
}
void handleSendText(Intent intent, String callingMethodName) {
String sharedText = intent.getStringExtra(Intent.EXTRA_TEXT);
if (sharedText != null) {
Log.d("MainActivity", "sharedText : " + sharedText + " called from : " + callingMethodName);
}
}
}
My AndroidManifest section for the activity has the filter added like:
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
<intent-filter>
<action android:name="android.intent.action.SEND" />
<category android:name="android.intent.category.DEFAULT" />
<data android:mimeType="text/plain" />
</intent-filter>
</activity>
Walk-Thru With Screens and Log
NOTE: Please notice that I've implemented the onResume() in my app also to insure that I don't only get the Intent when onCreate() is called (only one time when the app is started).
Start up browser and grab the text "hurricane".
Choose the app to share with (our test app).
View the log and notice that onCreate() and onResume() are called and value is 'hurricane'
Go back to browser again to share more text...
Select a new word, Atlantic, to share.
Extra note: When we click that Share link this time the Android MenuChooser doesn't display, instead, it automatically opens GrabText again. I found that behavior somewhat odd.
Notice that the Intent text still has the value of hurricane. You can see that there are now two new entries in the logcat.
Attempted Workaround Solutions
I have found that I can destroy the app entirely by overriding onPause() and calling finish() on my Activity (thus closing the entire app) and that seems to work, but isn't there some other way to reset that Intent or the associated text or something?
Do you know of any other way to insure that the new data is retrieved?
I appreciate any help.
UPDATE
Note:I'm updating because there's not a great way to show additional code tried, however, I wouldn't have know to try this without input from other SO User, CommonsWare.
The first answer I received was that I should add an #Override onNewIntent() so I added the following code to my MainActivity:
#Override
protected void onNewIntent(Intent intent) {
super.onNewIntent(intent);
Log.d("MainActivity", "onNewIntent()...");
String action = intent.getAction();
String type = intent.getType();
if (Intent.ACTION_SEND.equals(action) && type != null) {
if ("text/plain".equals(type)) {
handleSendText(intent, "onNewIntent"); // Handle text being sent
}
}
}
Upon adding that code and running and attempting the copy and then second copy of the new word, I still saw the following in logcat:
It doesn't even look as if the onNewItent() method is even called.
EDIT 2
I altered the emulator Settings...Developer Options... and turned off the "Don't keep activities" setting. It was previously turned on (checked).
After that, I ran the app which contains the onNewIntent() override but now it shows just the one onCreate() gone (which makes sense because the activity is still loaded) but still does not show the onNewIntent() call.
In this sample, I captured the word "remnants".
Edit 3
I built the app and created an APK and deployed it to my Samsung Galaxy Core Prime and I ended up with the same results. onNewIntent() is never called.
I just looked up onNewIntent in Google docs and it states:
onNewIntent(Intent intent) This is called for activities that set
launchMode to "singleTop" in their package, or if a client used the
FLAG_ACTIVITY_SINGLE_TOP flag when calling startActivity(Intent).
I haven't set singleTop so I will try it now. Hmm....
EDIT 4
I have now tried the singleTop variation. I was previously testing on API 15 (v4.0.4)on an emulator so I switched to API 21 (v5.0) to see if there'd be any different.
Here's what the addition of singleTop did to my AndroidManifest.xml:
<activity android:name=".MainActivity" android:launchMode="singleTop">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
<action android:name="android.intent.action.SEND" />
<category android:name="android.intent.category.DEFAULT" />
<data android:mimeType="text/plain" />
</intent-filter>
</activity>
Notice I also collapsed the two intent-filter nodes into the one.
Selected Text Did Change
On Android API Level 21 the Intent text was now coming in different each time I selected text in the browser.
onNewIntent Is Never Called
However, onNewIntent is NEVER called. I don't ever see it fire.
Share Menu Displayed Every Time
Also, now (on API 21) I see the Share menu every time I select text.
However, I also see an interesting thing when I switch to the browser. You can see multiple copies of the Activity in the list. What?!
Notice also that I implemented the MainActivity as a ListView (scrollable) so I could see the entries even without logcat (for running on real device). That made something else apparent: that the ListView was being updated on each newly shown Activity. But really, it should be the original Activity being appended to.
Creates Numerous GrabText Activities
Yes, now it creates a new GrabText Activity window each time I select text. I thought maybe that was because I had the singleTop set so I removed it but they still appear even after removing singleTop on API LEVEL 21.
Now that I saw it work -- provide different text each time on API 21 I decided to switch back to API Level 15 emulator and try it.
I will report back after I try some things back on API Level 15 again.
API Level 15 : Test Again
I started my other emulator running API Level 15 again and ran the app and even with singleTop set the value is never updated.
You can see this in the logcat and on the updated ListView:
You can also see that the code acts completely different, though I've not changed anything since it appends to the ListView of the one running Activity on api level 15.
I've written a book on this terribly documented thing. I hope this helps someone and that a Google Android dev sees this and explains it.
If your activity already exists, it will be called with onNewIntent() instead of onCreate(). onNewIntent() will be passed the Intent that you need to use for your message.
Try changing the android:launchMode of your activity in the manifest.xml to
singleTop
this way if the activity is already launched, new intents will be received in onNewIntent() method
There is only one answer that actually works, but it could cause other problems.
You just have to decide to call finish() whenever the Activity goes into onPause().
Here's the exact code I implemented which works on all API LEVELS.
#Override
public void onPause(){
super.onPause();
finish();
}
Destroy the Activity
When you add that code then every time you switch back to the app you are sharing from (the web browser in our case) then the onPause will fire on your MainActivity and the finish() method will set the Activity for destruction.
Share Menu Displayed Every Time After This
With this solution every time you select text from your sharing app (web browser) then the Share menu will be displayed and will display GrabText as one of the choices (instead of automatically forcing GrabText to the front again).
Shared Text Is Always the New Text
Since the MainActivity is completely destroyed it then has to be completely loaded (onCreate()) again and so it receives the new Intent text which was sent.
Not A Great Workaround
This isn't a great workaround however, because I believe dialog boxes in your app would also create onPause() to be called and your Activity would be destroyed. Obviously destroying your Activity onPause() just isn't great either because you are beginning to manage "memory" in a way that really should be left to the OS. However, in this case it seems to be the only way around the issue.

If App running, start login activity else splash activity

Update
I changed the logic as pointed out by #dunnololz in his answer. But now Splash always appears when clicking on launcher icon even though application is running. I was hoping first time when app is not running splash would show otherwise login activity show but this is not happening.
Here is my code:
manifest splash launcher activity:
<activity
android:name=".activities.Splash"
android:label="#string/app_name"
android:launchMode="singleInstance"
android:noHistory="true"
android:screenOrientation="portrait"
android:theme="#android:style/Theme.Black.NoTitleBar" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
Splash.Java:
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
startService(new Intent(Splash.this, IMService.class));
setContentView(R.layout.activity_splash);
Thread background = new Thread() {
public void run() {
try {
// Thread will sleep for 3 seconds
sleep(3 * 1000);
Intent intent = new Intent(getBaseContext(), Login.class);
// intent.addFlags(Intent.FLAG_ACTIVITY_NO_HISTORY);
startActivity(intent);
finish();
} catch (Exception e) {
}
}
};
// start thread
background.start();
}
I am using this gist to determine whether app is running or not. I found it via this tutorial. So that class uses Application.ActivityLifecycleCallbacks for API level 14+ which is what I need.
What I want to do is:
If application is running either in foreground or background, start login activity
If application is not running, start splash activity
Here is my code:
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Intent intent = new Intent(getBaseContext(), Splash.class);
if (Foreground.get(this).isForeground()
|| Foreground.get(this).isBackground()) {
intent = new Intent(EntryPoint.this, Login.class);
}
startActivity(intent);
finish();
}
And here is my application class:
public class MyApp extends Application {
#Override
public void onCreate() {
super.onCreate();
Foreground.init(this);
}
}
Of course I have added my app to manifest file as well:
<application
android:name=".MyApp"
The problem is that Splash activity is never started. It is the Login activity which is always started.
I just want to be able to do this:
If application is running either in foreground or background, start login activity
If application is not running, start splash activity
But not sure how to get this working, I might be missing something obvious here. Or even it might be that my requirement of either in foreground or background is wrong as I am new to Android.
Thanks for the help
Generally in Android it is not advised to determine behavior based on whether the app is currently being kept in memory or not. That is what the OS should be concerned about and not something you want to concern yourself about.
In the current version of Android (since I'm not sure if this behavior is true for older versions), when you tap an app to launch it, the OS checks to see if the app is already "open". If it is, it restores the state of the "open" app. If the app is not already "open", Android will launch the activity that is marked at the launcher. So the solution to this problem is simply to let Android handle it. Make a splash activity and mark it as the launcher in your AndroidManifest.xml. Then have the launcher open your login activity after some time.
Now, if the app is already open, Android simply will restore the last open activity. Otherwise it will show the launcher.

How to handle home button issue in Android Launcher applications

I'm creating a sample lock screen application in this i must override the home button, after i researched in both google and stackoverflow i got the result, it's complicated to do it. Here i mention what i did in my app,
Created a service with broadcast-receiver to show my lock screen when the screen goes to off. - working fine.
To override the home, menu, back and search buttons i used the following code,
hope we can override the home button when the application only becomes a launcher so in my manifest.xml i added this code.
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.HOME" />
<category android:name="android.intent.category.DEFAULT" />
<!-- <category android:name="android.intent.category.LAUNCHER" /> -->
</intent-filter>
Also in my Activity i used this code too
#Override
public void onAttachedToWindow() {
// TODO Auto-generated method stub
this.getWindow().setType(
WindowManager.LayoutParams.TYPE_KEYGUARD_DIALOG
| WindowManager.LayoutParams.FLAG_FULLSCREEN);
this.getWindow().setType(WindowManager.LayoutParams.TYPE_KEYGUARD);
super.onAttachedToWindow();
}
So far in my sample application i successfully completed the above to. Now my problem is,
When i unlock the screen then go to any apps, then i click the Device home button, My Lock screen will appear. i tired to disable this but i don't know how can i exactly do this, for this i used some code like below,
/* This should come from a preference that let's the user select an activity that can handle the HOME intent */
String packageName = "com.android.launcher";
String packageClass = "com.android.launcher2.Launcher";
Intent home_intent = new Intent(Intent.ACTION_MAIN);
home_intent.addCategory(Intent.CATEGORY_HOME);
home_intent.setComponent(new ComponentName(packageName, packageClass));
home_intent.addFlags(Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS);
/* Here you should catch the exception when the launcher has been uninstalled, and let the user save themselves by opening the Market or an app list or something. Users sometimes use root apps to uninstall the system launcher, so your fake launcher is all that is left. Might as well give the poor user a hand. */
startActivity(home_intent);
No code will help me, my exact need is once i unlock the screen i need to show the default home screen until the screen goes to screen off. is any idea to handle this issue? Thanks in Advance.
Try this solution,
Create a static variable flag which is set to true when you receive the broadcast for when screen goes to off
now in your activity check if the flag is true
#Override
public void onAttachedToWindow() {
if(MyService.Flag == true){
//Continue with your code ...
//....
}else{
finish();
}
}
or do it on onCreate which ever is suitable for you
Once your screen is unlocked then
//Disable the flag
MyService.Flag = false;
Now when your user clicks the Home button the activity is called and check again the flag again and if its false then call the finish() to close the activity

Trying to make home replacement app?

I'm trying to make a Home Replacement app, but I'm running into a bunch of glitches. When the app launches for the first time, you go through several setup screens that allow you to configure basic settings. Once you are done with that, you get to the HomeScreen activity. In the AndroidManifest.xml I have included the following:
<activity android:name="HomeScreenMain"
android:theme="#style/Theme"
android:launchMode="singleInstance"
android:stateNotNeeded="true">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.HOME"/>
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</activity>
In the HomeScreen activity, I have included the following methods:
protected void onNewIntent(Intent intent) {
super.onNewIntent(intent);
if (Intent.ACTION_MAIN.equals(intent.getAction())) {
getWindow().closeAllPanels();
}
}
public void onDestroy() {
super.onDestroy();
}
Also in the HomeScreen activity, I have a button that effectively exits the entire app. The associated code is:
public void exitApp(View view){
this.finish();
Intent intent = new Intent(Intent.ACTION_MAIN);
intent.addCategory(Intent.CATEGORY_HOME);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);
}
So basically what I want is that when you get to the HomeScreen activity the first time, a prompt comes up telling you to select your default Home Screen (this doesn't happen unless I press the Home Button, I want this to happen as soon as the activity is launched). Once I do set this as my default Home Screen, it works, but only fundamentally. Pressing the home button brings me back to this activity (as it should), but when I tap the Exit button, I don't get returned to the stock Home Launcher, which is what I want.
First, your Manifest is ok,
but in your exitApp you want to finish the activity, right?
in your code you finish it and then start it again..
Pressing the home button brings me back to this activity (as it should),
but when I tap the Exit button, I don't get returned to the stock Launcher,
which is what I want.
if a user had installed another home replacment app (e.g. Go Launcher Ex)
and if the user had set Go Launcher as default before defaulting to your app,
you want to return to Go Launcher Ex, right?
I assume yes.
This is partially possible,
what you can do is prompting the user which home launcher to use
after exiting your launcher:
import android.content.pm.PackageManager;
public void exitApp()
{
//call this method to exit _CLEARLY_,
//and prompt the user which launcher to use next
//clear the default for your app (to show the prompt when exiting)
final PackageManager pm = getPackageManager();
pm.clearPackagePreferredActivities(getApplicationContext().getPackageName());
//exit _CLEARLY_
//calling finish(); would be ok also,
//but there would stay a 'zombie' in the dalvik cache
//and 'zombies' only use up your memory, so kill your entire app:
android.os.Process.killProcess(android.os.Process.myPid());
}
So basically what I want is that when you get to the HomeScreen
activity the first time, a prompt comes up telling you to select your
default Home Screen (this doesn't happen unless I press the Home
Button, I want this to happen as soon as the activity is launched).
then call this function in onCreate(),
it simulates a homebutton press by calling an intent with Intent.CATEGORY_HOME:
public void showPrompt()
{
Intent i = new Intent(Intent.ACTION_MAIN);
i.addCategory(Intent.CATEGORY_HOME);
startActivity(i);
}
Hope this is what you wanted

Categories

Resources