I am trying to lock the orientation of an entire app on phone sized layouts to portrait only but allow both portrait and landscape on tablet sized layouts.
I know that I can attribute the Activity to use a specific orientation but this is applied on both layout sizes.
[Activity(
Label = "Brs.Members.Droid"
, MainLauncher = true
, Icon = "#mipmap/icon"
, Theme = "#style/Theme.Splash"
, NoHistory = true
, ScreenOrientation = ScreenOrientation.Portrait)]
public class SplashScreen : MvxSplashScreenActivity
{
public SplashScreen() : base(Resource.Layout.SplashScreen)
{
}
}
Is there a method to only exclude landscape layouts on phone size devices?
Try the code below,check your device if it is tablet first and then set the orientation:
[Activity(Label = "MyOrientationDemo", MainLauncher = true, Icon = "#drawable/icon")]
public class MainActivity : Activity
{
protected override void OnCreate(Bundle bundle)
{
base.OnCreate(bundle);
if (!isPad(this))
{
RequestedOrientation = ScreenOrientation.Portrait;
}
SetContentView (Resource.Layout.Main);
}
public static bool isPad(Context context)
{
return (context.Resources.Configuration.ScreenLayout& ScreenLayout.SizeMask)>= ScreenLayout.SizeLarge;
}
}
What you can do is to first check if the device is tablet and then lock the orientation to portrait at run time.
Here is a useful post post to determine if the device is tablet :
Determine if the device is a smartphone or tablet?
So here is what you can do :
Create a values resource file with the qualifier of Smallest screen width equal to 600dp. (sw600dp)
Inside the file set the boolean value of isTablet to true :
<resources>
<bool name="isTablet">true</bool>
</resources>
Then inside the normal values file (without the screen size qualifier) set the value of isTablet to false :
<resources>
<bool name="isTablet">false</bool>
</resources>
Then get the isTablet value in onCreate and set the orientation accordingly :
boolean isTablet = getResources().getBoolean(R.bool.isTablet);
if (!isTablet) {
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
}
Related
I want to make my application compatible with Android Nougat and specifically with the density change and the font size change.
What I am doing in my tests is:
Launch the application
Put it in Multi-Window mode (top part of a Pixel C, portrait mode, on emulator)
Put some filters on a list in my application
Change the display size or the font size through the second half of my screen with the settings app
If I don't listen for configuration changes with the density value in the manifest, it recreates my activity (which is not good because I have some filters on and I lose them).
If I listen to them, the densityDpi value is the same in the newConfig value passed as a parameter than the one I get with getResources().getConfiguration().densityDpi.
My current line on the manifest is as below :
android:configChanges="screenSize|smallestScreenSize|screenLayout|orientation|keyboardHidden|density"
I have tried something like this:
#Override
public void onConfigurationChanged(Configuration newConfig) {
super.onConfigurationChanged(newConfig);
// some code
if(mOldConfiguration != null && newConfig.densityDpi!= mOldConfiguration.densityDpi){
// Neither densityDpi nor fontScale works, they are always the same
}
if(mOldConfiguration != null && newConfig.fontScale != mOldConfiguration.fontScale){
// I will later have a method which will recreate the activity with my filters saved
recreate();
}
mOldConfiguration = newConfig;
}
I already listen to other configuration changes but can't figure out how to detect in this method that the change was a density / font size change.
You can listen to density changes by add this line in the Manifest file:
android:configChanges="density"
In the activity, you can get the new configuration value when having a change:
#Override
public void onConfigurationChanged(Configuration newConfig) {
super.onConfigurationChanged(newConfig);
Log.e("TRUNGDH", newConfig.densityDpi + "<= densityDpi");
}
With font size changes, you can add some code like this:
android:configChanges="fontScale"
#Override
public void onConfigurationChanged(Configuration newConfig) {
super.onConfigurationChanged(newConfig);
Log.e("TRUNGDH", newConfig.fontScale + "<= fontScale");
}
Hello friends I'm new to Android Development and Stackoverflow,
I'm facing some issues in android layout,
I have created two layout folders one for portrait and one for landscape(both for tablet TVDPI)
layout-sw600dp-land-tvdpi & layout-sw600dp-port-tvdpi
The issue I'm facing is when I run my program in portrait mode it shows me correct layout of portrait but when I turn my device portrait to landscape it shows me same layout of portrait, and same case when I run it in landscape mode it run correctly and turn to potrait it shows me the landscape layout...
Why?
Try this
#region Handle State on Orientation
//this has been done using better technique
protected override void OnSaveInstanceState(Bundle outState)
{
base.OnSaveInstanceState(outState);
//adding spinner/dropdownlist selected item
if (ViewModel.IsLoading == true)
{
isLoadingState = true;
AndroidHUD.AndHUD.Shared.Dismiss(this);
}
var preferences = GetSharedPreferences("TmsAppData", FileCreationMode.Private);
var editor = preferences.Edit();
//editor.PutString("DeviceId", registrationId);
editor.PutBoolean("IsOrientationChange", true);
editor.Commit();
//outState.PutInt("_AlreadySelectedPostion", _AlreadySelectedPostion);
outState.PutBoolean("_isLoadingState", isLoadingState);
}
protected override void OnRestoreInstanceState(Bundle savedInstanceState)
{
base.OnRestoreInstanceState(savedInstanceState);
//setting a flag to manage spinner selected state
_IsStateViewActive = true;
isLoadingState = savedInstanceState.GetBoolean("_isLoadingState");
if (ViewModel.IsLoading == true)
{
isLoadingState = false;
ViewModel.IsLoading = true;
}
//getting the previous selected item from the saved state for spinner / dropdownlist
//_AlreadySelectedPostion = savedInstanceState.GetInt("_AlreadySelectedPostion");
}
#endregion
I have a simple activity with a boolean. I want it to change from portrait to landscape if and only if that boolean is false (only if the screen changes orientation, of course).
I tried this:
#Override
public void onConfigurationChanged(final Configuration newConfig) {
super.onConfigurationChanged((listening) ? getListeningConfiguration(newConfig)
: newConfig);
setContentView(R.layout.medidor);
preconfigureLayout();
}
public Configuration getListeningConfiguration(final Configuration c) {
c.orientation = Configuration.ORIENTATION_PORTRAIT;
return c;
}
But it simply won't work.
How can I force an activity to remain in portrait state unless I tell it it can change?
In manifest file in activity tag add
android:configChanges="orientation|keyboardHidden"
android:screenOrientation="portrait"
That will keep your activity in portrait mode. then use your code for orientation change.
Just call this to keep it in portrait:
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
That should do the trick
I have code to set a different layout for portrait and landscape. Is there a way to change the layout while the activity is running, if the user flips the device?
Code to set layout
void SetView()
{
int w=getWindowManager().getDefaultDisplay().getWidth();
int h=getWindowManager().getDefaultDisplay().getHeight();
if (w>h)
setContentView(R.layout.mainHor);
else
setContentView(R.layout.mainVer);
}
Make two new folders in res called layout-land and layout-port. Put your landscape layout in layout-land and your portrait in layout-port. Make sure the xml files have the same name.
Also, as was mentioned in the comments, making just the layout-land folder is good enough as long as you also have a default xml for the Activity in the layout folder. If for any reason Android can't find the layout needed in the alternative layout-[orientation] folder, it will take what it finds in layout.
make two folder under res folder with name layout and layout-land. Put seprate layouts for portrait and landscape.
and then override onConfigurationChanged
public void onConfigurationChanged(Configuration newConfig) {
super.onConfigurationChanged(newConfig);
setContentView(R.layout.homepage_screen);
}
public void onConfigurationChanged(Configuration newConfig) {
super.onConfigurationChanged(newConfig);
if (newConfig.orientation == Configuration.ORIENTATION_LANDSCAPE) {
setContentView(R.layout.mainHor);
} else if (newConfig.orientation == Configuration.ORIENTATION_PORTRAIT){
setContentView(R.layout.mainVer);
}
}
Do this
#Override
public void onConfigurationChanged(Configuration configuration) {
super.onConfigurationChanged(configuration);
if (configuration.orientation == Configuration.ORIENTATION_LANDSCAPE) {
setContentView(R.layout.landscape_layout);
} else if (configuration.orientation == Configuration.ORIENTATION_PORTRAIT){
setContentView(R.layout.portrait_layout);
}
}
I have create dialog box which will be displayed first when i start application (which is coded in onCreate method ) and then question and answer will be displayed on textview
so to solve problem of orientation (so dialog box again not displayed when orientation change) i have used Manifest with:
android:configChanges="keyboardHidden|orientation"
I have res/layout-land, res/layout-port
but to change only COLOR of background
I have used onConfigurationChanged in my Activity (it get's called on rotation).
so now when orientation change the dialog box will not appear again and background is redrawn but the question and answer which is initialized on onCreate() will not display
so how to maintain
Using android:configChanges="keyboardHidden|orientation" means that your activity handles a configuration change itself, and the system will not change the layout.. take a lokk at http://developer.android.com/guide/topics/resources/runtime-changes.html
To reset the text view, in case of not using android:configChanges="keyboardHidden|orientation":
#Override
public Object onRetainNonConfigurationInstance() {
final MyDataObject data = collectMyLoadedData();
//here get the text from the text view, and any other info
return data;
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
final MyDataObject data = (MyDataObject) getLastNonConfigurationInstance();
if (data != null) {
//get the text and set it in the text view
}
}
When you change the orientation of the devide, android continue the execution without calling onCreate again, but if you put the code in onResume, this code will executed again.
In OnCreate add for your main layout as
LinearLayout lv=(LinearLayout)findViewById(R.id.mainlayout);
lv.setBackgroundColor(android.R.color.black); // for default potrait or landscape view and after that add this in that activity
#Override
public void onConfigurationChanged(Configuration newConfig) {
Configuration c = getResources().getConfiguration();
if(c.orientation == Configuration.ORIENTATION_PORTRAIT ) {
// portrait
lv.setBackgroundColor(android.R.color.black);
} else if(c.orientation == Configuration.ORIENTATION_LANDSCAPE ){
// landscape
lv.setBackgroundColor(android.R.color.white);
}
}
and also add this in menifest in your activity defined
android:configChanges="keyboardHidden|orientation"
Did you use onSaveInstanceState to save the data and onRestoreInstanceState for retriving the data?
If you have done this then you can display the same dialog box in onRestoreInstanceState.
Well I have a question for you. How did you kept the background color unchanged when changing the orientations? And what to do if the color is unknown or a random color?