Как справиться с поворотом / ориентацией экрана в формах Xamarin?
Существует ли (наполовину) общий способ обработки поворота / ориентации в формах Xamarin для различных видов и платформ (Android, iOS, WinPhone)?
Пользовательский интерфейс вращается, и это достаточно хорошо, хотя это наносит ущерб моему макету (абсолютный макет прямо сейчас). Я полагаю, с помощью Stacklayout я мог бы сделать его немного более гибким, но затем столкнулся бы с блокпостом где-нибудь еще, когда макет более сложный.
Можно ли как-то отображать разные виды для портрета и ландшафта с помощью одной и той же ViewModel? (Я использую MVBM на основе XLAB.)
Возможные решения, которые я нашел:
http://blog.rthand.com/post/2014/07/24/Different-XAML-layouts-for-different-device-orienations-in-XamarinForms.aspx не хватает iOS, и мне интересно, будет ли он работать с MVVM слишком хорошо, кажется, хорошо, и я сейчас расследую это
http://www.jimbobbennett.io/orientation-with-xamarin-forms/ звучит многообещающе, но образец только для iOS, связанный репозиторий GIT вообще не имеет документации, он просто говорит "Помощники Xamarin"
http://www.sellsbrothers.com/posts/Details/13740 также может быть возможностью для программно созданных видов. Хотя в моих тестах я не получил событие изменения размера (хотя я слушал в другом месте кода) для симулятора ios при вращении. (Решение основано на изменении размера для обнаружения вращения.)
1 ответ
Если вы уже используете XLabs, вы можете использовать IXFormsApp и свойство Orientation и обработчик событий Rotation. Вам придется добавить нативных наблюдателей для каждой платформы и установить там "Ориентацию" IXFormsApp, которая вызовет обработчик события.
Например на iOS:
public override bool FinishedLaunching(UIApplication app, NSDictionary options)
{
var xapp = new XFormsAppiOS();
xapp.Init(this);
var resolverContainer = new SimpleContainer();
resolverContainer.Register<IXFormsApp>(xapp);
Resolver.SetResolver(resolverContainer.GetResolver());
var a = new App();
LoadApplication(a);
UIDevice.Notifications.ObserveOrientationDidChange((s, e) =>
{
xapp.Orientation = ... // set orientation here
});
Теперь вы можете отслеживать изменения ориентации, разрешив IXFormsApp:
xapp = Resolver.Resolve<IXFormsApp>();
if (xapp.Orientation == Orientation.Landscape) { ... } else { ... }
xapp.Rotation += (sender, args) =>
{
switch (args.Value)
{
case Orientation.LandscapeLeft:
break;
default:
// etc.
break;
}
};
Что касается макетов, я бы предположил, что RelativeLayout будет наиболее удобным выбором, так как вы можете поместить ориентацию внутри ограничения. При повороте заставьте макет обновиться сам.