I have a game application made up of several different activities. The first to be called is a splash screen, when this completes, this finishes and starts up another activity via an intent. In order to have access to some global data that is consistent across all the activities, I also have a "globals" class like this:
public class Globals extends Application
{
int global_variable_A;
int global_variable_B;
int global_variable_C;
public void onCreate()
{
// stuff
}
}
In the androidmanifest.xml I have the the following (amongst other things):
<application
android:icon="#drawable/mygame_icon"
android:screenOrientation="portrait"
android:label='"My Game"' android:name=".Globals">
<activity
android:label="My Game"
android:name=".Splash"
android:screenOrientation="portrait">
<intent-filter >
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
My question now is, which will be executed first, the onCreate of Globals or the onCreate of Splash? Or are they run at the same time on different threads? I ask because I'm getting some inconsistent behaviour that would be explained if they were on different threads.
onCreate() Global off course.. Application gets executed first and then the Activity,,.. you can test for yourself by keeping a debug point in Application onCreate() method..
Related
Problem:
My Launching Activity creatively named LoadingActivity's onCreate method is called 2 times.
Manifest Content:
<manifest>
<application>
...
<activity
android:launchMode="singleTop"
android:name="com.awesome.app.activites.LoadingActivity"
android:screenOrientation="portrait">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
...
</application>
</manifest>
First onCreate call is called with Bundle savedInstanceState which is null, shortly after which the onCreate method is called again, but this time with Bundle savedInstanceState which contains the following serialized content:
Bundle[{com.google.app_measurement.screen_service=Bundle[{referrer_name=LoadingActivity, id=1612091517631091562, name=null}], android:viewHierarchyState=Bundle[{android:views={16908290=android.view.AbsSavedState$1#a24446f, 2131296302=android.view.AbsSavedState$1#a24446f, 2131296313=android.view.AbsSavedState$1#a24446f, 2131296424=android.view.AbsSavedState$1#a24446f, 2131296445=android.widget.ProgressBar$SavedState#b25257c, 2131296581=android.view.AbsSavedState$1#a24446f, 2131296582=android.view.AbsSavedState$1#a24446f}}], androidx.lifecycle.BundlableSavedStateRegistry.key=Bundle[{}], android:lastAutofillId=1073741823, android:fragments=android.app.FragmentManagerState#a24ee05}]
Yes, this doesn't mean much, but it may be related to something at the bottom of the post.
Tried:
I have tried setting launchmode settings with android:launchMode="singleTop" for the LoadingActivty in my AndroidManifest.xml, but this does not help at all, it still runs the onCreate 2 times.
I have gone through my onCreate method, no where do I onCreate again or change ApplicationContext settings i.e. Orientation (physically or programmatically), etc.
Any idea why this happens and what I can do to resolve it.
For what it is worth, I have recently updated my deps and see this in my Manifest:
It compiles (change the package name for obv reasons) with the portrait launchmode, but I think this may have something to do with the double launch
I am trying to start a new activity when an Android device is rotated, but I don;t even seem to be detecting the rotation in the emulator.
I've read the thread at Android: listen for Orientation change? and that all seems to amke sense, but its just not working.
In my manifest I have:
<activity
android:name=".MainActivity"
android:configChanges="orientation|screenSize"
android:screenOrientation="portrait"
android:windowSoftInputMode="stateHidden">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
and in my mainActivity.java I have:
#Override
public void onConfigurationChanged (Configuration newConfig) {
super.onConfigurationChanged(newConfig);
int orientation=newConfig.orientation;
switch(orientation) {
case Configuration.ORIENTATION_LANDSCAPE:
showMessage("landscape");
break;
case Configuration.ORIENTATION_PORTRAIT:
showMessage("portrait");
break;
}
}
This obviously won't start the new Activity, but I am trying to get the orientation detection working first (showMessage just calls a Toast and is working elsewhere in my code, so that's not why I am not seeing anything).
When I run this in the emulator and use the rotate buttons, the emulator rotates as expected but I never see the Toast...
Where am I going wrong? (I am importing android.content.res.Configuration as required for the Configuration constants).
onConfigurationChanged method will not be invoked when you rotate your device, actually, nothing will be invoked because of this line:
android:screenOrientation="portrait"
device is just locked in a portrait mode, remove this line, and onConfigurationChanged method should be invoked.
If you want to detect that device is rotated and keep android:screenOrientation="portrait" line you can use accelerometer sensor.
Try after removing this lines
android:configChanges="orientation|screenSize"
android:screenOrientation="portrait"
because you are locking screen orientation in manifest and you are
also overriding on config change in activity.
I'm hoping one of you fine folk may be able to help me out with a little issue I am having whilst using Android Intent.createChooser(). I am learning as I go with my application so I apologise if I have the wrong end of the stick with how this should work!
I have been following a number of tutorials and have implemented some code which starts an Intent.createChooser() to share a picture to social media. The code that I have used works fine in that I am able to share the picture as I intended, my issue is that when the code is run my main activity (or any activity I call the code from) appears to close and the chooser appears in front of the homescreen or any other applications I may have open. The effect that I was hoping to have, and the one which seemed to be apparent in the tutorials, is for the chooser to appear in front of the running activity (eg as it does for the gallery).
I am using LibGDX meaning that I have had to use an interface to call the android function that executes the chooser code (in my AndroidLauncher java file). The interfaces all work fine but I wasn't sure if that may have a bearing on the way in which this code operates. I have also played around with swapping to a new activity to implement the chooser code, which I had moved from the AndroidLauncher. This had the same end result.
Any advice on how to make the chooser appear in front of my application would be greatly appreciated! The code which implements the createChooser is included below:
public void ShareHandler(){
String type = "image/*";
String mediaPath = Environment.getExternalStorageDirectory().getPath()+"/Smile.png";
createShareIntent(type, mediaPath);
}
private void createShareIntent(String type, String mediaPath)
{
Intent share = new Intent(Intent.ACTION_SEND);
share.setType(type);
File media = new File(mediaPath);
Uri uri = Uri.fromFile(media);
share.putExtra(Intent.EXTRA_STREAM, uri);
startActivity(Intent.createChooser(share, "Share to"));
}
Android Manifest:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.game"
android:versionCode="1"
android:versionName="1.0">
<uses-sdk
android:minSdkVersion="8"
android:targetSdkVersion="25" />
<uses-permission android:name="android.permission.INTERNET" />
<application
android:allowBackup="true"
android:icon="#drawable/ic_launcher"
android:label="#string/app_name"
android:theme="#style/GdxTheme">
<activity
android:name=".AndroidLauncher"
android:configChanges="keyboard|keyboardHidden|orientation|screenSize"
android:label="#string/app_name"
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=".FacebookServiceHandler" />
<meta-data
android:name="come.facebook.sdk.ApplicationID"
android:value="#string/facebook_app_id" />
<provider
android:name="com.facebook.FacebookContentProvider"
android:authorities="com.facebook.app.FacebookContentProviderxxxxxxxxxxxxx"
android:exported="true" />
</application>
</manifest>
Thanks in advance, Ben.
If
android:name=".FacebookServiceHandler"
is the activity, that handle the social media sharing of the picture, i would expand that to something like this:
<activity
android:name=".FacebookServiceHandler">
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value=".AndroidLauncher">
</meta-data>
</activity>
This will tell the programm, that the AndroidLauncher is the parentactivity and should make it appear in front of your activity.
Thank you for the suggestions, I have now solved my issue. It turned out that my code was working correctly all along and the issue I was experiencing was as a result of an exit statement within my Core (LibGDX) java code. Essentially when the startActivity(Intent.createChooser(...)) was called, a dispose function within my core files was also being called. This dispose function contained the exit command and was causing the application to finish.
I have added my Android app to the "Share-Via" window. Following code is added to the onCreate() method of my code.
if(getIntent().getAction().equals(Intent.ACTION_SEND))
{
String text = getIntent().getStringExtra(Intent.EXTRA_TEXT);
textField.setText(text);
}
Now the issues is, if this app activity get called from the share-via, it works. But if it get called directly (user opens the app -> go to that activity) this crashes with NullPointerException. I am getting NullPointerException right in here
if(getIntent().getAction().equals(Intent.ACTION_SEND))
Following is how this Share-Via configured in the manifest file.
<activity
android:name="com.xx.xx.xx"
android:screenOrientation="portrait"
android:label="#string/app_name" >
<intent-filter>
<action android:name="android.intent.action.SEND" />
<category android:name="android.intent.category.DEFAULT" />
<data android:mimeType="text/plain"/>
</intent-filter>
</activity>
What is the issue here?
Either getIntent() or getAction() is returning null.
You need to check for that.
I made three apps, which I now want to ship in one apk file (one installation). On startup of the "wrapper app" the user should decide which app to run.
So far, so good, but the problem is, each app is using global constants from an Application file. Is there a way to build the three apps into one, where each app uses its own application file?
Thanks!
To avoid confusion i add a short example:
App 1:
public class AApplication extends Application {
public static String CONSTANT_1 = "aaa";
}
App 2:
public class BApplication extends Application {
public static String CONSTANT_1 = "bbb";
}
App 3:
public class CApplication extends Application {
public static String CONSTANT_1 = "ccc";
}
Ok, since the idea I head is obviously not realizable I came up with the following workaround:
I created an Apllication class in the new Project
public class NewApplication extends OldSuperApplication {}
I added a method
public static void setApplication(RGCApplication a) {
CONSTANT_1 = a.CONSTANT_1;
...
}
after selecting the desired "sub-app" on the startscreen in this case application "A" i call
NewApplication.setApplication(new AApplication());
or
NewApplication.setApplication(new BApplication());
I'm not sure if this is smelly coding or not, but it works!
Probably you want three activity that can be launched. Add in the manifest something like this:
<activity
android:name=".Activityone"
android:label="First Activity" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name=".Activitysecond"
android:label="Second Activity" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name=".Activitythree"
android:label="Third Activity" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
In this way user has three icons (activity) to click.
You can not integrate 3 different apk and its respective code-base to run by single apk, either integrate all 3 code-base in single application and divide all 3 as different modules to run depending upon selection by user.