自定义ViewPresenter:FragmentViewPresenter [Wpf Core 3.1; MvvmCross 7.0.0]

时间:2020-10-03 10:51:31

标签: c# wpf view mvvmcross mvp

项目

我的目标是创建一个具有某些图像编辑功能的小型应用程序。这是我努力学习Wpf和MVVM模式的一部分。设计方面,我想保持简单:带有{em> New , Save Close Exit <的标准Menu栏/ em>功能。还有一个 workspace ,它显示与实际图像有关的所有内容。应用启动时,我还想显示一个小的 readme / welcome
菜单应始终存在,并且MenuItems应该能够控制下面的内容。例如:按下 New 后,自述文件/欢迎应切换到工作区。我想象它看起来像:this image

问题

WpfFragmentViewPresenter.cs和AppStart.cs 中的当前信息和问题!

自从我提出这个问题以来,我已经取得了很大进步。当前的问题是我无法从ViewPresenter内部访问 MainView 。我的计划是拦截 AViewModel BViewModel ViewModelRequest以在 MainView 中显示其views,而不是返回base.Show() / base.ShowContentView()方法。

我已经创建了一个小型解决方案,以演示我正在尝试做的事情,演示已经起作用的情况以及使场景可再现的问题。
项目结构,代码和用法可以在下面找到。

更新

我被困住了。即使我的ViewPresenter掌握了我的 MainViewModel ...也没关系。如何在不执行此操作的情况下在另一个view中显示一个view,而却没有:

<ContentControl
    Grid.Row="1"
    Grid.Column="0"
    Grid.ColumnSpan="5"
    Content="{Binding ChildViewModel, Mode=OneWay, UpdateSourceTrigger=PropertyChanged}">
    <ContentControl.Resources>
        <DataTemplate DataType="{x:Type vm:AChildViewModel}">
            <local:AChildView />
        </DataTemplate>
    </ContentControl.Resources>
</ContentControl>

添加了 FragmentViewModel.cs AViewModel BViewModel 都继承自它。 WpfFragmentViewPresenter.cs 现在可以检查任何 FragmentViewModel 代替 AViewModel BViewModel 。我还在脚本中添加了更多说明和Exceptions

添加了 AppStart.cs 。将RegisterAppStart<MainViewModel>();更改为RegisterCustomAppStart<AppStart>();。尽管 MainViewModel 是第一个导航到的ViewModel,但它从未被ViewPresenter拾取。我仍然无法使用 MainView 在其中显示另一个view

添加了 Setup.cs WpfFragmentViewPresenter.cs WpfFragmentPresentationAttribute.cs < / strong> 。我觉得自己已经很接近了,但是ViewPresenter遇到了麻烦。

尝试this

可重现的解决方案

用法

在应用程序启动时,程序将仅显示一个菜单,该菜单下具有空白空间。这是主要问题,因为我无法在 MainView 中包含 AView 。要展示 AView BView 的正确版本,您可以通过Navigate<>() DebugForceAView MenuItem AView 。这样做将终止menu(这是一个问题),但是它将正确显示 AView 。也可以导航到BView。

项目设置

WpfFragmentViewPresenter.cs和AppStart.cs 中的当前信息和问题!

只要名称空间保持一致,此项目解决方案就应该正常工作。
检查脚本是否有其他注释来解释我的问题。

  • 创建核心库:“ MvxWpfConductor.Core”(。NET Standard 2.0)
  • 创建Wpf应用:“ MvxWpfConductor”(。NET Core 3.1)
  • 将NuGet软件包“ MvvmCross”添加到核心库中
  • 将NuGet软件包“ MvvmCross.Platforms.Wpf”添加到Wpf应用程序
  • 您可以关闭自述文件
  • 将核心库的项目引用添加到Wpf应用
  • 将Wpf应用设置为启动项目
  • 像疯子一样开始复制粘贴

解决方案结构

Solution
    MvxWpfConductor (.NET Core 3.1)
        Views folder
            AView.xaml
            BView.xaml
            MainView.xaml
        App.xaml
        AssemblyInfo.cs
        MainWindow.xaml
        Setup.cs
        WpfFragmentPresentationAttribute.cs
        WpfFragmentViewPresenter.cs

    MvxWpfConductor.Core (.NET Standard 2.0)
        ViewModels folder
            AViewModel.cs
            BViewModel.cs
            FragmentViewModel.cs
            MainViewModel.cs
        App.cs
        AppStart.cs

App.cs(核心库):

using MvvmCross.IoC;
using MvvmCross.ViewModels;
using MvxWpfConductor.Core.ViewModels;

namespace MvxWpfConductor.Core
{
    public class App : MvxApplication
    {
        public override void Initialize()
        {
            CreatableTypes()
                .EndingWith("Service")
                .AsInterfaces()
                .RegisterAsLazySingleton();
            //RegisterAppStart<MainViewModel>();
            RegisterCustomAppStart<AppStart>();
        }
    }
}

AppStart.cs(核心库):

using MvvmCross.Exceptions;
using MvvmCross.Navigation;
using MvvmCross.ViewModels;
using MvxWpfConductor.Core.ViewModels;
using System.Threading.Tasks;

namespace MvxWpfConductor.Core
{
    public class AppStart : MvxAppStart
    {
        #region Fields -------------------------------------------------------------------------------------

        #endregion ------------------------------------------------------------------------ Fields endregion


        #region Properties ---------------------------------------------------------------------------------

        #endregion -------------------------------------------------------------------- Properties endregion


        #region Constructors -------------------------------------------------------------------------------
        public AppStart(IMvxApplication application, IMvxNavigationService navigationService) : base(application, navigationService)
        {

        }
        #endregion ------------------------------------------------------------------ Constructors endregion

        protected override Task NavigateToFirstViewModel(object hint = null)
        {
            // Why isn't this captured by 'WpfFragmentViewPresenter's Show() / ShowContentView() exceptions?
            // The first request that comes up is 'AViewModel' 
            // which makes no sense as the following task navigates to MainViewModel first.
            // How am I supposed to get MainView under control if the MainViewModel is never captured by the ViewPresenter?!
            return NavigationService.Navigate<MainViewModel>();
        }
    }
}

MainViewModel.cs(核心库):

using MvvmCross.Commands;
using MvvmCross.Logging;
using MvvmCross.Navigation;
using MvvmCross.ViewModels;
using System.Threading.Tasks;

namespace MvxWpfConductor.Core.ViewModels
{
    public class MainViewModel : MvxNavigationViewModel
    {
        #region Fields -------------------------------------------------------------------------------------
        private MvxNavigationViewModel m_childVM;
        #endregion ------------------------------------------------------------------------ Fields endregion


        #region Properties ---------------------------------------------------------------------------------
        /// <summary>
        /// This should be used to navigate from "A" to "B"
        /// instead of the buttons currently displayed on each view
        /// !!!! the menuitem currently is deactivated !!!
        /// </summary>
        public MvxCommand NavToBCommand => new MvxCommand(async () => {
            await NavigationService.Navigate(typeof(BViewModel));
        });

        // DEBUG PURPOSE ONLY
        public MvxCommand DebugACommand => new MvxCommand(async () => {
            await NavigationService.Navigate(typeof(AViewModel));
        });

        public MvxNavigationViewModel ChildVM {
            get => m_childVM;
            set {
                SetProperty(ref m_childVM, value);
            }
        }

        #endregion -------------------------------------------------------------------- Properties endregion


        #region Constructors -------------------------------------------------------------------------------
        public MainViewModel(IMvxLogProvider logProvider, IMvxNavigationService navigationService, IMvxViewModelLoader viewModelLoader)
            : base(logProvider, navigationService)
        {
            
        }
        #endregion ------------------------------------------------------------------ Constructors endregion

        #region Public methods -----------------------------------------------------------------------------
        public override void Prepare()
        {

        }

        public override async Task Initialize()
        {
            await base.Initialize();

            /// Initial Navigate() to A to display it under the menu?
            await NavigationService.Navigate(typeof(AViewModel));
        }
        #endregion ---------------------------------------------------------------- Public methods endregion
    }
}

FragmentViewModel.cs (核心库):

using MvvmCross.Logging;
using MvvmCross.Navigation;
using MvvmCross.ViewModels;

namespace MvxWpfConductor.Core.ViewModels
{
    public class FragmentViewModel : MvxNavigationViewModel
    {
        #region Fields -------------------------------------------------------------------------------------

        #endregion ------------------------------------------------------------------------ Fields endregion


        #region Properties ---------------------------------------------------------------------------------

        #endregion -------------------------------------------------------------------- Properties endregion


        #region Constructors -------------------------------------------------------------------------------
        public FragmentViewModel(IMvxLogProvider logProvider, IMvxNavigationService navigationService)
            : base(logProvider, navigationService)
        {

        }
        #endregion ------------------------------------------------------------------ Constructors endregion


        #region Public methods -----------------------------------------------------------------------------

        #endregion ---------------------------------------------------------------- Public methods endregion
    }
}

AViewModel.cs(核心库):

using MvvmCross.Commands;
using MvvmCross.Logging;
using MvvmCross.Navigation;
using MvvmCross.ViewModels;

namespace MvxWpfConductor.Core.ViewModels
{
    public class AViewModel : FragmentViewModel
    {
        #region Fields -------------------------------------------------------------------------------------
        //private readonly IMvxNavigationService _navigationService;
        #endregion ------------------------------------------------------------------------ Fields endregion


        #region Properties ---------------------------------------------------------------------------------
        // A to B
        public MvxCommand NavToBCommand => new MvxCommand(async () => {
            await NavigationService.Navigate(typeof(BViewModel));
        });

        // Gets set in "Prepare()"
        // Main won't display this -> more details inside: MainView.xaml
        private string m_AText = "";
        public string AText {
            get => m_AText;
            set {
                SetProperty(ref m_AText, value);
            }
        }

        #endregion -------------------------------------------------------------------- Properties endregion


        #region Constructors -------------------------------------------------------------------------------
        public AViewModel(IMvxLogProvider logProvider, IMvxNavigationService navigationService)
            : base(logProvider, navigationService)
        {
            //_navigationService = navigationService;
        }
        #endregion ------------------------------------------------------------------ Constructors endregion

        #region Public methods -----------------------------------------------------------------------------
        public override void Prepare()
        {
            AText = "[A property]";
        }
        #endregion ---------------------------------------------------------------- Public methods endregion
    }
}

BViewModel.cs(核心库):

using MvvmCross.Commands;
using MvvmCross.Logging;
using MvvmCross.Navigation;
using MvvmCross.ViewModels;

namespace MvxWpfConductor.Core.ViewModels
{
    public class BViewModel : FragmentViewModel
    {
        #region Fields -------------------------------------------------------------------------------------
        //private readonly IMvxNavigationService _navigationService;
        #endregion ------------------------------------------------------------------------ Fields endregion


        #region Properties ---------------------------------------------------------------------------------
        // B to A
        public MvxCommand SomeCloseCommand => new MvxCommand(async () => {
            await NavigationService.Close(this);
        });

        // Gets set in "Prepare()"
        private string m_BText = "";
        public string BText {
            get => m_BText;
            set {
                SetProperty(ref m_BText, value);
            }
        }

        #endregion -------------------------------------------------------------------- Properties endregion


        #region Constructors -------------------------------------------------------------------------------
        public BViewModel(IMvxLogProvider logProvider, IMvxNavigationService navigationService)
            : base(logProvider, navigationService)
        {
            //_navigationService = navigationService;
        }
        #endregion ------------------------------------------------------------------ Constructors endregion

        #region Public methods -----------------------------------------------------------------------------
        public override void Prepare()
        {
            BText = "[B property]";
        }
        #endregion ---------------------------------------------------------------- Public methods endregion
    }
}

Setup.cs(Wpf应用):

using MvvmCross.Platforms.Wpf.Core;
using MvvmCross.Platforms.Wpf.Presenters;
using MvvmCross.ViewModels;
using System.Windows.Controls;

namespace MvxWpfConductor
{
    public class Setup : MvxWpfSetup
    {
        public Setup() { }

        protected override IMvxApplication CreateApp()
        {
            return new Core.App();
        }

        protected override IMvxWpfViewPresenter CreateViewPresenter(ContentControl root)
        {
            return new WpfFragmentViewPresenter(root);
        }
    }
}

WpfFragmentViewPresenter.cs(Wpf应用):

using MvvmCross.Platforms.Wpf.Presenters;
using MvvmCross.Platforms.Wpf.Presenters.Attributes;
using MvvmCross.Platforms.Wpf.Views;
using MvvmCross.ViewModels;
using MvxWpfConductor.Core.ViewModels;
using MvxWpfConductor.Views;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;

namespace MvxWpfConductor
{
    /// <summary>
    /// ************************************************************************************************
    /// ************************************************************************************************
    /// ****                                                                                        ****
    /// ****    ->  Why is the first request of 'Show()' and 'ShowContentView()' 'AView'            ****
    /// ****        and not 'MainView'?                                                             ****
    /// ****                                                                                        ****
    /// ****    ->  How do I access my 'MainView' in order to do something like this;               ****
    /// ****        PseudoCode inside 'Show()' or 'ShowContentView':                                ****
    /// ****            if request is FragmentOfMainViewModel                                       ****
    /// ****                MainView.ShowAFragment(vm)                                              ****
    /// ****                return null ???                                                         ****
    /// ****            else                                                                        ****
    /// ****                return base.showmethod(something)                                       ****
    /// ****                                                                                        ****
    /// ****    ->  Is this even the right way to do this?                                          ****
    /// ****                                                                                        ****
    /// ************************************************************************************************
    /// ************************************************************************************************
    /// </summary>
    public class WpfFragmentViewPresenter : MvxWpfViewPresenter
    {
        private readonly ContentControl _root;

        private FrameworkElement _mainViewElement;// I'd like to use this to set a set a fragment inside 

        public WpfFragmentViewPresenter(ContentControl root) : base(root)// root needs to be passed down to base
        {
            _root = root;
        }

        public override Task<bool> Show(MvxViewModelRequest request)
        {
            //throw new System.Exception($"First request: {request.ViewModelType.ToString()}");
            // When every 'throw Exception()' is active this is the first one to get raised.
            // The exception above outputs this:
            // System.Exception: 'First request: MvxWpfConductor.Core.ViewModels.AViewModel'

            return base.Show(request);
        }

        protected override Task<bool> ShowWindow(FrameworkElement element, MvxWindowPresentationAttribute attribute, MvxViewModelRequest request)
        {
            //throw new System.Exception($"First element: {element}");
            // This never gets raised for some reason. 
            // Even though MainWindow.xaml.cs carries the WindowPresentation attribute.

            return base.ShowWindow(element, attribute, request);
        }

        protected override Task<bool> ShowContentView(FrameworkElement element, MvxContentPresentationAttribute attribute, MvxViewModelRequest request)
        {
            // AView is the first element that gets cought here. 
            // The navigation to AView happens from inside MainViews Initialize() method.
            // So how can AView be the first element that ends up in this method?
            if(request.ViewModelType.IsSubclassOf(typeof(FragmentViewModel))) {
                // This is raised first. 
                // System.Exception: 'Fragment element: MvxWpfConductor.Views.AView'
                //throw new System.Exception($"Fragment element: {element}");

                // PseudoCode:
                // if(_mainViewElement != null)
                //     _mainView.AFragment = element;
                //     return ???
            }
            else {
                // This is raised afterwards.
                // System.Exception: 'Root element: MvxWpfConductor.Views.MainView'
                //throw new System.Exception($"Root element: {element}");
            }
            return base.ShowContentView(element, attribute, request);
        }
    }
}

WpfFragmentPresentationAttribute.cs(Wpf应用):

using MvvmCross.Presenters.Attributes;

namespace MvxWpfConductor
{
    /// <summary>
    /// does nothing atm
    /// </summary>
    public class WpfFragmentPresentationAttribute : MvxBasePresentationAttribute
    {

    }
}

App.xaml(Wpf应用):

<views:MvxApplication
    x:Class="MvxWpfConductor.App"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="clr-namespace:MvxWpfConductor"
    xmlns:views="clr-namespace:MvvmCross.Platforms.Wpf.Views;assembly=MvvmCross.Platforms.Wpf"
    StartupUri="MainWindow.xaml" />

App.xaml.cs(Wpf应用):

using MvvmCross.Core;
using MvvmCross.Platforms.Wpf.Core;
using MvvmCross.Platforms.Wpf.Views;

namespace MvxWpfConductor
{
    public partial class App : MvxApplication
    {
        /// <summary>
        /// Custom Setup.cs
        /// </summary>
        public App() => this.RegisterSetupType<Setup>();
    }
}

MainWindow.xaml(Wpf应用):

<views:MvxWindow
    x:Class="MvxWpfConductor.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:local="clr-namespace:MvxWpfConductor"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    xmlns:views="clr-namespace:MvvmCross.Platforms.Wpf.Views;assembly=MvvmCross.Platforms.Wpf"
    Title="TestApp"
    Width="320"
    Height="240"
    WindowStartupLocation="CenterScreen"
    mc:Ignorable="d">
    <Grid />
</views:MvxWindow>

MainWindow.xaml.cs(Wpf应用):

using MvvmCross.Platforms.Wpf.Presenters.Attributes;
using MvvmCross.Platforms.Wpf.Views;

namespace MvxWpfConductor
{
    [MvxWindowPresentation(Identifier = nameof(MainWindow), Modal = false)]
    public partial class MainWindow : MvxWindow
    {
        public MainWindow() => InitializeComponent();
    }
}

MainView.xaml(Wpf应用):

<views:MvxWpfView
    x:Class="MvxWpfConductor.Views.MainView"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:local="clr-namespace:MvxWpfConductor.Views"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    xmlns:mvx="clr-namespace:MvvmCross.Platforms.Wpf.Binding;assembly=MvvmCross.Platforms.Wpf"
    xmlns:views="clr-namespace:MvvmCross.Platforms.Wpf.Views;assembly=MvvmCross.Platforms.Wpf"
    xmlns:vm="clr-namespace:MvxWpfConductor.Core.ViewModels;assembly=MvxWpfConductor.Core"
    d:DesignHeight="450"
    d:DesignWidth="800"
    mc:Ignorable="d">
    <Grid>
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto" />
            <RowDefinition Height="*" />
        </Grid.RowDefinitions>
        <Menu Grid.Row="0">
            <MenuItem Header="_Menu">
                <MenuItem
                    mvx:Bi.nd="Command NavToBCommand"
                    Header="_NavToB"
                    IsEnabled="False" />
                <MenuItem mvx:Bi.nd="Command DebugACommand" Header="_DebugForceAView" />
            </MenuItem>
        </Menu>

        <views:MvxWpfView x:Name="ChildView" Grid.Row="1" />
    </Grid>
</views:MvxWpfView>

MainView.xaml.cs(Wpf应用):

using MvvmCross.Platforms.Wpf.Presenters.Attributes;
using MvvmCross.Platforms.Wpf.Views;
using MvvmCross.ViewModels;

namespace MvxWpfConductor.Views
{
    [MvxContentPresentation(WindowIdentifier = nameof(MainWindow), StackNavigation = false)]
    public partial class MainView : MvxWpfView
    {
        public MainView() => InitializeComponent();

        internal void ShowChildVM(IMvxViewModel vm)
        {
            ChildView.DataContext = vm;
        }
    }
}

AView.xaml(Wpf应用):

<views:MvxWpfView
    x:Class="MvxWpfConductor.Views.AView"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:local="clr-namespace:MvxWpfConductor.Views"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    xmlns:mvx="clr-namespace:MvvmCross.Platforms.Wpf.Binding;assembly=MvvmCross.Platforms.Wpf"
    xmlns:views="clr-namespace:MvvmCross.Platforms.Wpf.Views;assembly=MvvmCross.Platforms.Wpf"
    d:DesignHeight="450"
    d:DesignWidth="800"
    Background="Blue"
    Foreground="White"
    mc:Ignorable="d">
    <Grid>
        <Grid.ColumnDefinitions>
            <ColumnDefinition Width="*" />
            <ColumnDefinition Width="Auto" SharedSizeGroup="SameSize" />
            <ColumnDefinition Width="*" />
        </Grid.ColumnDefinitions>
        <Grid.RowDefinitions>
            <RowDefinition Height="42" />
            <RowDefinition Height="Auto" />
            <RowDefinition Height="Auto" />
            <RowDefinition Height="Auto" />
            <RowDefinition Height="Auto" />
            <RowDefinition Height="*" />
        </Grid.RowDefinitions>
        <TextBlock
            Grid.Row="1"
            Grid.Column="1"
            FontSize="24">
            View A
        </TextBlock>
        <StackPanel
            Grid.Row="2"
            Grid.Column="1"
            Orientation="Horizontal">
            <TextBlock
                FontSize="16"
                Foreground="Yellow"
                Text="Property --&gt; " />
            <TextBlock
                mvx:Bi.nd="Text AText"
                FontSize="16"
                Foreground="Yellow" />
        </StackPanel>
        <!--
            This Button should not be here.
            The functionality to navigate to B should be included in the menu.
        -->
        <Button
            Grid.Row="3"
            Grid.Column="1"
            mvx:Bi.nd="Command NavToBCommand">
            Nav to B
        </Button>

        <TextBlock
            Grid.Row="4"
            Grid.Column="1"
            Text="This Button should not be here.&#x0a;The functionality to navigate to B&#x0a;should be included in the menu." />
    </Grid>
</views:MvxWpfView>

AView.xaml.cs(Wpf应用):

using MvvmCross.Platforms.Wpf.Presenters.Attributes;
using MvvmCross.Platforms.Wpf.Views;

namespace MvxWpfConductor.Views
{
    [MvxContentPresentation]
    public partial class AView : MvxWpfView
    {
        public AView() => InitializeComponent();
    }
}

BView.xaml(Wpf应用):

<views:MvxWpfView
    x:Class="MvxWpfConductor.Views.BView"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:local="clr-namespace:MvxWpfConductor.Views"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    xmlns:mvx="clr-namespace:MvvmCross.Platforms.Wpf.Binding;assembly=MvvmCross.Platforms.Wpf"
    xmlns:views="clr-namespace:MvvmCross.Platforms.Wpf.Views;assembly=MvvmCross.Platforms.Wpf"
    d:DesignHeight="450"
    d:DesignWidth="800"
    Background="Red"
    Foreground="White"
    mc:Ignorable="d">
    <Grid>
        <Grid.ColumnDefinitions>
            <ColumnDefinition Width="*" />
            <ColumnDefinition Width="Auto" SharedSizeGroup="SameSize" />
            <ColumnDefinition Width="*" />
        </Grid.ColumnDefinitions>
        <Grid.RowDefinitions>
            <RowDefinition Height="42" />
            <RowDefinition Height="Auto" />
            <RowDefinition Height="Auto" />
            <RowDefinition Height="Auto" />
            <RowDefinition Height="*" />
        </Grid.RowDefinitions>
        <TextBlock
            Grid.Row="1"
            Grid.Column="1"
            FontSize="24">
            View B
        </TextBlock>
        <StackPanel
            Grid.Row="2"
            Grid.Column="1"
            Orientation="Horizontal">
            <TextBlock
                FontSize="16"
                Foreground="Yellow"
                Text="Property --&gt; " />
            <TextBlock
                mvx:Bi.nd="Text BText"
                FontSize="16"
                Foreground="Yellow" />
        </StackPanel>
        <!--
            This Button should not be here.
            The functionality to navigate to B should be included in the menu.
        -->
        <Button
            Grid.Row="3"
            Grid.Column="1"
            mvx:Bi.nd="Command SomeCloseCommand">
            Close Button
        </Button>
        <TextBlock
            Grid.Row="4"
            Grid.Column="1"
            Text="This Button should not be here.&#x0a;The functionality to navigate to B&#x0a;should be included in the menu." />
    </Grid>
</views:MvxWpfView>

BView.xaml.cs(Wpf应用):

using MvvmCross.Platforms.Wpf.Presenters.Attributes;
using MvvmCross.Platforms.Wpf.Views;

namespace MvxWpfConductor.Views
{
    [MvxContentPresentation]
    public partial class BView : MvxWpfView
    {
        public BView() => InitializeComponent();
    }
}

0 个答案:

没有答案