#xamarin.forms #prism #infragistics
#xamarin.forms #призма #инфраструктура
Вопрос:
У меня есть общий класс страницы, от которого наследуются остальные страницы моего приложения.
Я пишу кнопки в коде, но я хотел бы повторить то, как это делает prims, поскольку это более предсказуемо / читаемо для новичка. например
Это текущий метод. Как мне изменить свойство Command ниже, чтобы делать то, что делает код кнопки, т.е.
var im_Logo = new ImageButton
{
Margin = new Thickness(0),
Padding = new Thickness(0),
Source = "blalogo",
BackgroundColor = Color.Transparent,
HorizontalOptions = LayoutOptions.Start,
Command = new Command(GoHome)// This works but other pages are not so easy.
};
void GoHome(object obj)
{
Navigation.PopToRootAsync();
}
Плюс мне просто любопытно, как вы пишете Command="{prism:NavigateTo 'path/to/navigate'}"
в коде.
Если бы я мог прикрепить Viewmodel к этой странице «code», это также решило бы проблему, поскольку в Viewmodels, которые у меня есть, встроены все элементы Prism.(Предоставлено infragistics)
Редактировать Обновление: я добавляю полный класс страницы, которую я создаю в коде. Я думал, что написать общий класс для использования на нескольких страницах будет просто, но я в тупике. Моя ошибка при этих сбоях возникает при нажатии на кнопку поиска, на которой я сейчас сосредоточусь.
11-06 16:28:54.988 D/Mono (30123): Loading reference 0 of System.Drawing.Common.dll asmctx DEFAULT, looking for mscorlib, Version=2.0.5.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e
11-06 16:28:54.988 D/Mono (30123): Assembly Ref addref System.Drawing.Common[0xc7e18f60] -> mscorlib[0xe5c08580]: 70
Loaded assembly: System.Drawing.Common.dll [External]
11-06 16:28:55.040 D/EGL_emulation(30123): eglMakeCurrent: 0xc9270ce0: ver 2 0 (tinfo 0xc8d25b10)
**System.NullReferenceException:** 'Object reference not set to an instance of an object.'
using iBasisAppV1.ViewModels;
using Prism.Navigation;
using Prism.Navigation.Xaml;
using Syncfusion.XForms.BadgeView;
using Syncfusion.XForms.Buttons;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using Xamarin.Forms;
namespace iBasisAppV1.Views.Templates
{
public class CommonToolbarPage : ContentPage
{
public CommonToolbarPage()
{
NavigationPage.SetHasBackButton(this, false);
ShowDefaultTitle();
//this.BindingContext= new CommonToolbarPageViewModel(navigationService);
}
private void ShowDefaultTitle()
{
var im_Logo = new ImageButton
{
Margin = new Thickness(0),
Padding = new Thickness(0),
Source = "boilerparts",
BackgroundColor = Color.Transparent,
HorizontalOptions = LayoutOptions.Start,
Command = new NavigateToExtension { Name = $"/Home" }
//Command = new Command(GoHome)
};
var b_search = new SfButton
{
HorizontalTextAlignment = TextAlignment.End,
HorizontalOptions = LayoutOptions.FillAndExpand,
FontSize = 26,
TextColor = Color.White,
BackgroundColor = Color.Transparent,
Margin = new Thickness(0),
Padding = new Thickness(0),
FontFamily = "UIFontIcons",
Text = (String)Application.Current.Resources["Search"],
//Command = new NavigateToExtension { Name = "../Search" } //Not Work
//Command = new NavigateToExtension { Name = "Search" } //Not Work
//Command = new NavigateToExtension { Name = $"{nameof(Search)}" } //Not Work
// Command = new NavigateToExtension { Name = $"../{nameof(Search)}" } //Not Work
//Command = new Command(ShowSearch)// Works
};
var boxView = new BoxView
{
HorizontalOptions = LayoutOptions.FillAndExpand,
BackgroundColor = Color.Red,
Margin = new Thickness(0,0,0,0),
};
SfButton sfButton = new SfButton
{
CornerRadius = 4,
HorizontalOptions = LayoutOptions.End,
VerticalOptions= LayoutOptions.Center,
Style = (Style)Application.Current.Resources["IconButtonStyle"],
Text = (String)Application.Current.Resources["Cart"],
FontFamily = "UIFontIcons",
TextColor = Color.White,
// Command = new Command(GoCart)
};
var imSfBadgeView = new SfBadgeView
{
BadgeText = "4",
Margin = new Thickness(0, 0, 10, 0),
Padding = new Thickness(0),
WidthRequest = 40,
Content = sfButton,
HorizontalOptions = LayoutOptions.EndAndExpand,
VerticalOptions = LayoutOptions.Center,
BackgroundColor = Color.Transparent,
BadgeSettings = new BadgeSetting
{
BackgroundColor= (Color)Application.Current.Resources["PrimaryColor"],
BadgeType = BadgeType.None,
FontSize = 10,
Stroke = (Color)Application.Current.Resources["Gray-White"],
StrokeWidth = 1,
Offset = new Point(-10, 10)
}
};
var layout = new StackLayout
{
Orientation = StackOrientation.Horizontal,
HorizontalOptions=LayoutOptions.FillAndExpand,
BackgroundColor = (Color)Application.Current.Resources["HeaderColor"]
};
var Endlayout = new StackLayout
{
Orientation = StackOrientation.Horizontal,
HorizontalOptions = LayoutOptions.EndAndExpand,
};
if (this.GetType().Name.ToLower() != "search")
Endlayout.Children.Add(b_search);
Endlayout.Children.Add(imSfBadgeView);
layout.Children.Add(im_Logo);
layout.Children.Add(Endlayout);
NavigationPage.SetTitleView(this, layout);
}
private void ShowSearch(object obj)
{
Navigation.PushAsync(new Search());
}
private void cancel(object obj)
{
ShowDefaultTitle();
}
void GoCart(object obj)
{
Navigation.PushAsync(new Home());
}
void GoHome(object obj)
{
Navigation.PopToRootAsync();
// Navigation.PushAsync(new NavigationPage(new Home()));
//NavigationService.NavigateAsync("/MainPage/NavigationPage/ViewA");
}
}
}
Комментарии:
1. Вы имеете в виду
NavigationService.NavigateAsync("/MainPage/NavigationPage/ViewA");
в prism или вам нужно решение Xamarin.forms без использования Prism.2. Хорошо, итак, вы говорите, что Prism — это только XAML, и если я напишу код позади, мне придется использовать pushAsync и т. Д. Я надеялся на что-то подобное, что я смогу сделать в ViewModel. ожидание _navigationService . NavigateAsync($»/ MasterDetail»); Однако мой класс Custompage не имеет доступа к _navigationService, поскольку он введен в ViewModel, но я понятия не имею, как получить к нему доступ в классе Custompage.
3. Можете ли вы получить доступ к ViewModel с помощью BindingContext страницы?
Ответ №1:
Если вам нужно точное совпадение, поехали…
var im_Logo = new ImageButton
{
Margin = new Thickness(0),
Padding = new Thickness(0),
Source = "blalogo",
BackgroundColor = Color.Transparent,
HorizontalOptions = LayoutOptions.Start,
Command = new NavigateToExtension {Name = "/path/to/navigate"}
};
void GoHome(object obj)
{
Navigation.PopToRootAsync();
}
И вам понадобится следующий импорт:
using Prism.Navigation.Xaml;
Короче говоря, Prism использует этот класс для создания команды, которая может использовать INavigationService для доступа к контейнеру в приложении.Текущий. Если вы проверите исходный код в Github, вы увидите, как происходит все волшебство.
Ответ №2:
Если вы хотите сделать это в ViewModel, тогда вам нужен INavigationService
. Затем вы можете использовать его как:
await NavigationService.NavigateAsync(nameof(YourView));
Так что, как
Command = new Command(async () => await NavigationService.NavigateAsync("YourView"));
NavigateAsync использует параметры URI, вы можете использовать ../
и ../YourView
.
Мне нравится метод nameof(), например. await NavigationService.NavigateAsync($"../{nameof(YourView)}"));