is there any chance to force change screen orientation based device screen resolution?
Have app for tablets, but I want to run app on mobile device too. I have a few pages, where I need to change orientation to landscape on phone, because then is my listview a litle bit messy.
Thank you for any advice and I apologize for the bad English :)
You can use MessagingCenter to achieve that .
For example , when navigating from MainPage to PageTwo in Forms , the content page of PageTwo as follow :
public partial class PageTwo : ContentPage
{
public PageTwo()
{
InitializeComponent();
}
protected override void OnAppearing()
{
base.OnAppearing();
MessagingCenter.Send(this, "allowLandScape");
}
//during page close setting back to portrait
protected override void OnDisappearing()
{
base.OnDisappearing();
MessagingCenter.Send(this, "quitLandScape");
}
}
In Android , need to modify MainActivity as follow :
[Activity(Label = "ForceOrientation", Icon = "#mipmap/icon", Theme = "#style/MainTheme", MainLauncher = true, ConfigurationChanges = ConfigChanges.ScreenSize | ConfigChanges.Orientation, ScreenOrientation = ScreenOrientation.Portrait)]
public class MainActivity : global::Xamarin.Forms.Platform.Android.FormsAppCompatActivity
{
//allowing the device to change the screen orientation based on the rotation
protected override void OnCreate(Bundle savedInstanceState)
{
TabLayoutResource = Resource.Layout.Tabbar;
ToolbarResource = Resource.Layout.Toolbar;
base.OnCreate(savedInstanceState);
Xamarin.Essentials.Platform.Init(this, savedInstanceState);
global::Xamarin.Forms.Forms.Init(this, savedInstanceState);
LoadApplication(new App());
MessagingCenter.Subscribe<PageTwo>(this, "allowLandScape", sender =>
{
RequestedOrientation = ScreenOrientation.Landscape;
});
//during page close setting back to portrait
MessagingCenter.Subscribe<PageTwo>(this, "quitLandScape", sender =>
{
RequestedOrientation = ScreenOrientation.Portrait;
});
}
}
In iOS , we need to create a PageTwoRenderer as follow :
[assembly: ExportRenderer(typeof(PageTwo), typeof(PageTwoRenderer))]
namespace ForceOrientation.iOS
{
public class PageTwoRenderer : PageRenderer
{
public PageTwoRenderer()
{
MessagingCenter.Subscribe<PageTwo>(this, "allowLandScape", sender =>
{
UIDevice.CurrentDevice.SetValueForKey(NSNumber.FromNInt((int)(UIInterfaceOrientation.LandscapeLeft)), new NSString("orientation"));
});
//during page close setting back to portrait
MessagingCenter.Subscribe<PageTwo>(this, "quitLandScape", sender =>
{
UIDevice.CurrentDevice.SetValueForKey(NSNumber.FromNInt((int)(UIInterfaceOrientation.Portrait)), new NSString("orientation"));
});
}
}
}
==============================Update=============================
We can use Xamarin.Essentials: Device Information to check whether the device is Phone , Tablet or other devices .
DeviceInfo.Idiom correlates a constant string that maps to the type of device the application is running on. The values can be checked with the DeviceIdiom struct:
DeviceIdiom.Phone – Phone
DeviceIdiom.Tablet – Tablet
DeviceIdiom.Desktop – Desktop
DeviceIdiom.TV – TV
DeviceIdiom.Watch – Watch
DeviceIdiom.Unknown – Unknown
Modiied PageTwo as follow :
protected override void OnAppearing()
{
base.OnAppearing();
var idiom = DeviceInfo.Idiom;
if (idiom == DeviceIdiom.Phone)
{
MessagingCenter.Send(this, "allowLandScape");
}
}
//during page close setting back to portrait
protected override void OnDisappearing()
{
base.OnDisappearing();
var idiom = DeviceInfo.Idiom;
if (idiom == DeviceIdiom.Phone)
{
MessagingCenter.Send(this, "quitLandScape");
}
}
You can force set orientation on these few pages
// on IOS -> AppDelegate.cs
public override UIInterfaceOrientationMask GetSupportedInterfaceOrientations(UIApplication application, UIWindow forWindow)
{
if (Device.Idiom == TargetIdiom.Phone ) {
{
return UIInterfaceOrientationMask.Landscape;
}
else
{
return UIInterfaceOrientationMask.Portrait;
}
}
// and on Android -> MainActivity.cs do the same if else in here
protected override void OnCreate(Bundle savedInstanceState)
{
if (Device.Idiom == TargetIdiom.Phone)
{
RequestedOrientation = ScreenOrientation.Landscape;
}
else
{
RequestedOrientation = ScreenOrientation.Portrait;
}
}
You can check about Device class more in documentation https://learn.microsoft.com/en-us/xamarin/xamarin-forms/platform/device#deviceidiom
Related
I'm using firebase to send push notifications from a server to my app, the message looks like this:
var message = new Message()
{
Notification = new Notification()
{
Title = "Title - Test",
Body = "Body - Test",
},
Token = registrationToken
};
The notification comes through to the device no problem. All I want from when the notification is clicked, is for the app to start if the app is closed (this works) and for the app to resume if it's in the background.
When it's in the background and I click the notification, I just get a white screen. The issue seems to go away when I remove my splash screen, however that is not an ideal solution...Here is the relevant code, what am I doing wrong?
SPLASH ACTIVITY:
[Activity(Label = "MyApp",
Theme = "#style/splashscreen",
MainLauncher = true,
NoHistory = true)]
public class SplashActivity : Activity
{
protected override void OnCreate(Bundle savedInstanceState)
{
base.OnCreate(savedInstanceState);
}
protected override void OnResume()
{
base.OnResume();
var mainActivityIntent = new Intent(this, typeof(MainActivity));
mainActivityIntent.AddFlags(ActivityFlags.SingleTop | ActivityFlags.NoAnimation);
StartActivity(mainActivityIntent);
this.Finish();
}
public override void OnBackPressed() { }
}
MAIN ACTIVITY:
[Activity(Label = "MyApp",
Theme = "#style/MainTheme",
LaunchMode = LaunchMode.SingleTop,
MainLauncher = false,
ConfigurationChanges = ConfigChanges.ScreenSize | ConfigChanges.Orientation, ScreenOrientation = ScreenOrientation.FullSensor)]
public class MainActivity : global::Xamarin.Forms.Platform.Android.FormsAppCompatActivity
{
public static MainActivity MainActivityInstance { get; private set; }
protected override void OnCreate(Bundle savedInstanceState)
{
TabLayoutResource = Resource.Layout.Tabbar;
ToolbarResource = Resource.Layout.Toolbar;
base.OnCreate(savedInstanceState);
Xamarin.Essentials.Platform.Init(this, savedInstanceState);
this.Window.SetFlags(WindowManagerFlags.KeepScreenOn, WindowManagerFlags.KeepScreenOn);
this.Window.SetSoftInputMode(SoftInput.AdjustPan);
Forms.Init(this, savedInstanceState);
MainActivityInstance = this;
LoadApplication(new App());
}
Try changing MainLauncher = true for the main activity.
Adding ActivityFlags.ClearTop to mainActivityIntent.AddFlags() in my OnResume method on
SplashActivity has seemed to have worked:
protected override void OnResume()
{
base.OnResume();
var mainActivityIntent = new Intent(this, typeof(MainActivity));
mainActivityIntent.AddFlags(ActivityFlags.NoAnimation | ActivityFlags.SingleTop | ActivityFlags.ClearTop);
StartActivity(mainActivityIntent);
this.Finish();
}
At first I should say that I have read all similar questions and they can not solve my problem .
I have a Splash Screen in my Xamarin Forms project and check the credentials in it and then in each condition start Main Activity with different parameter toward the condition . When Splash Screen finish it's work and disappear , the app show a black screen about 10 seconds and then main page is showing
this is my Splash :
[Activity(Theme = "#style/MainTheme.Splash",
MainLauncher = true,
NoHistory = true,
ScreenOrientation = ScreenOrientation.Portrait)]
public class SplashActivity : Activity
{
static readonly string TAG = "X:" + typeof(SplashActivity).Name;
public override void OnCreate(Bundle savedInstanceState, PersistableBundle persistentState)
{
base.OnCreate(savedInstanceState, persistentState);
Xamarin.Essentials.Platform.Init(this, savedInstanceState);
Log.Debug(TAG, "SplashActivity.OnCreate");
}
protected override void OnResume()
{
base.OnResume();
Task startupWork = new Task(() => { SimulateStartup(); });
startupWork.Start();
}
async void SimulateStartup()
{
Some Code ...
InvokeMainActivity("SomeType");
}
private void InvokeMainActivity(string type)
{
Intent _activity = new Intent(Application.Context, typeof(MainActivity));
_activity.PutExtra("Key", type);
_activity.AddFlags(ActivityFlags.NoAnimation);
StartActivity(_activity);
}
and this is my MainActivity :
[Activity(Label = "#string/app_name",
Icon = "#drawable/icon",
Theme = "#style/MainTheme",
MainLauncher = false,
LaunchMode = LaunchMode.SingleTask,
ConfigurationChanges = ConfigChanges.Orientation | ConfigChanges.ScreenSize | ConfigChanges.Locale | ConfigChanges.LayoutDirection)
]
public class MainActivity : global::Xamarin.Forms.Platform.Android.FormsAppCompatActivity
{
protected override async void OnCreate(Bundle bundle)
{
TabLayoutResource = Resource.Layout.Tabbar;
ToolbarResource = Resource.Layout.Toolbar;
base.OnCreate(bundle);
Xamarin.Essentials.Platform.Init(this, bundle);
Rg.Plugins.Popup.Popup.Init(this, bundle);
global::Xamarin.Forms.Forms.Init(this, bundle);
FFImageLoading.Forms.Platform.CachedImageRenderer.Init(enableFastRenderer: true);
Window.DecorView.LayoutDirection = LayoutDirection.Rtl;
string type = Intent.GetStringExtra("SomeType");
LoadApplication(new App(type));
}
}
How can I fix this ?
Thanks to #LeonLu-MSFT I add this code in style.xml without any change in MainActivity and Spalsh Screen
<item name="android:windowIsTranslucent">true</item>
I don't have Mac and ios device to test in ios
I was also facing similar problem. I fixed it by adding
<item name="android:windowIsTranslucent">true</item>
in ~\Resources\values\styles.xml.
So if you are facing similar problem add it as per below screen shot and hopefully it will also work for you:
There was a problem parsing the package while installing .apk file.
Given below is configuration and code.
VS2015
MainActivity.cs
namespace WebAp
{
[Activity(Label = "TC", MainLauncher = true, Theme ="#android:style/Theme.NoTitleBar")]
public class MainActivity : Activity
{
private WebView web_view;
protected override void OnCreate(Bundle bundle)
{
base.OnCreate(bundle);
// Set our view from the "main" layout resource
SetContentView(Resource.Layout.Main);
web_view = FindViewById<WebView>(Resource.Id.webview);
web_view.Settings.JavaScriptEnabled = true;
web_view.LoadUrl("http://www.tc.com");
web_view.SetWebViewClient(new HelloWebViewClient());
}
public class HelloWebViewClient : WebViewClient
{
public override bool ShouldOverrideUrlLoading(WebView view, string url)
{
view.LoadUrl(url);
return true;
}
}
public override bool OnKeyDown(Android.Views.Keycode keyCode, Android.Views.KeyEvent e)
{
if (keyCode == Android.Views.Keycode.Back && web_view.CanGoBack())
{
web_view.GoBack();
return true;
}
return base.OnKeyDown(keyCode, e);
}
}
}
Configurataion :
enter image description here
Thats it my code. I was also try different API for Compile, Min and target version.
Please help me thanks.
I wanna point out that i'm a total newbie in Xamarin.
My goal is to create simple app that after you push the button, it will jump to another layout. My problem is, that after i created a new layout(called layout1) and new activity, I can't reference to this layout in my MainActivity.
freshly created Activity:
namespace Layouts
{
[Activity(Label = "Activity1")]
public class Activity1 : Activity
{
protected override void OnCreate(Bundle savedInstanceState)
{
base.OnCreate(savedInstanceState);
SetContentView(Resource.Layout.layout1);
}
}
}
And my MainActivity:
namespace Layouts
{
[Activity(Label = "Layouts", MainLauncher = true, Icon = "#drawable/icon")]
public class MainActivity : Activity
{
protected override void OnCreate(Bundle savedInstanceState)
{
base.OnCreate(savedInstanceState);
SetContentView (Resource.Layout.Main);
Button button1 = FindViewById<Button>(Resource.Id.button);
button1.Click += delegate
{
StartActivity(typeof(layout1)); //can't reference layout1 there
};
}
}
}
Any help will be great, thanks :)
StartActivity(typeof(Activity1));
Im using xamarin for android and i have looked into this issue but nothing seems to work.
Im trying to get a webview to work with a button but it keeps saying whenever i click on the button.
nativeOnDraw failed; clearing to background color.
I will include image of my layout and my code here.
MainActivity
namespace Application
{
[Activity(Label = "Application", MainLauncher = true, Icon = "#drawable/icon", Theme = "#android:style/Theme.NoTitleBar")]
public class MainActivity : Activity
{
protected override void OnCreate(Bundle bundle)
{
base.OnCreate(bundle);
// Set our view from the "main" layout resource
SetContentView(Resource.Layout.Main);
WebPage webPage = new WebPage();
Button btn_MySchedule = FindViewById<Button>(Resource.Id.btnSchedule);
Button btn_MyCareer = FindViewById<Button>(Resource.Id.btnCareer);
Button btn_MySocial = FindViewById<Button>(Resource.Id.btnSocial);
Button btn_Feedback = FindViewById<Button>(Resource.Id.btnFeedback);
Button btn_MyDetails = FindViewById<Button>(Resource.Id.btnDetails);
btn_MySchedule.Click += delegate
{
webPage.isSchedule = true;
//wPage.SetUrl("https://www.google.com");
StartActivity(typeof(WebPage));
};
}
}
}
WebPage
namespace Application
{
[Activity(Label = "WebPage", Theme = "#android:style/Theme.NoTitleBar")]
public class WebPage : Activity
{
public bool isSchedule;
private WebView _webView;
private string _url;
protected override void OnCreate(Bundle savedInstanceState)
{
base.OnCreate(savedInstanceState);
SetContentView(Resource.Layout.WebPage);
_webView = FindViewById<WebView>(Resource.Id.webView);
new DisplayWebPage(_webView, GetUrl());
}
public string GetUrl()
{
return _url;
}
public void SetUrl(string sUrl)
{
_url = sUrl;
}
private void ButtonCLicked()
{
if (isSchedule == true)
{
SetUrl("https://www.google.com");
Toast.MakeText(this, "isSchedule is true", ToastLength.Short).Show();
}
}
}
}
I have found the issue. It was due to me calling an empty string via the GetUrl() methods.
The Solution I used is:
[Export("MyScheduleClicked")]
public void MyScheduleClicked(View v)
{
var activity2 = new Intent(this, typeof(WebPage));
activity2.PutExtra("MyURL", "https://www.google.com");
StartActivity(activity2);
}