如何加载模块并导航到模块?棱镜
How to load a module and navigate to the module? Prism
我有两个模块:ModuleLogging
和 ModuleItems
。
我的 Shell
有声明:
<Grid>
<DockPanel LastChildFill="True">
<ContentControl DockPanel.Dock="Top" prism:RegionManager.RegionName="{x:Static inf:RegionNames.TheUpperRegion}" Margin="5" />
<ContentControl prism:RegionManager.RegionName="{x:Static inf:RegionNames.TheBottomRegion}" Margin="5"/>
</DockPanel>
<ContentControl prism:RegionManager.RegionName="{x:Static inf:RegionNames.TheWholeRegion}" Margin="5" />
</Grid>
首先加载ModuleLogging
。然后,如果用户通过身份验证,我想加载 ModuleItems
。
据我理解正确,我应该实例化
我的引导程序 class:
protected override IModuleCatalog CreateModuleCatalog()
{
ModuleCatalog catalog = new ModuleCatalog();
catalog.AddModule(typeof(ModuleLogging));
//I've not added ModuleItems as I want to check whether the user is authorized
return catalog;
}
我试图从 ModuleLogging
调用 ModuleItems
的内容:
Uri viewNav = new Uri("ModuleItems", UriKind.Relative);
regionManager.RequestNavigate(RegionNames.TheUpperRegion, viewNav);
regionManager.RequestNavigate(RegionNames.TheBottomRegion, viewNav);
但是我的ModuleLogging
的LoggingView
并没有被ModuleItems
的ToolBarView
和ModuleItems
的DockingView
代替。我只是在 ContentControls 中分别看到 System.Object
和 System.Object
而不是控件,因为 LoggingView
是透明的。
是的,我知道内存中没有对象 ModuleItems
.
如何按需加载模块并导航到视图?
您可能需要对这些进行排序以使其正常工作:
- 正在将您的模块添加到目录中
- 按需加载模块
- 正在注册将在区域中显示的视图(或视图模型)
- 请求导航到您的视图
我们按顺序看
正在将您的模块添加到目录中
我看不出有任何理由不将您的模块添加到目录中,但是在身份验证之后您可能不想要的是初始化模块。要按需初始化您的模块,您可以使用标志 OnDemand
:
将其添加到目录中
The module will be initialized when requested, and not automatically
on application start-up.
在你的引导程序中:
protected override void ConfigureModuleCatalog()
{
Type ModuleItemsType = typeof(ModuleItems);
ModuleCatalog.AddModule(new ModuleInfo()
{
ModuleName = ModuleItemsType.Name,
ModuleType = ModuleItemsType.AssemblyQualifiedName,
InitializationMode = InitializationMode.OnDemand
});
按需加载模块
认证成功后就可以初始化模块了:
private void OnAuthenticated(object sender, EventArgs args)
{
this.moduleManager.LoadModule("ModuleItems");
}
其中 moduleManager
是 Microsoft.Practices.Prism.Modularity.IModuleManager
的实例(最好注入到您的 class 构造函数中)
正在注册您的观点
您还需要在容器中注册要导航到的视图(如果您使用的是视图模型优先,则为视图模型)。执行此操作的最佳位置可能是模块 ModuleItems 的初始化,只需确保将容器注入其构造函数:
public ModuleItems(IUnityContainer container)
{
_container = container;
}
public void Initialize()
{
_container.RegisterType<object, ToolBarView>(typeof(ToolBarView).FullName);
_container.RegisterType<object, DockingView>(typeof(DockingView).FullName);
// rest of initialisation
}
请注意,为了使 RequestNavigate 正常工作,您必须将视图注册为对象,并且还必须提供其全名作为名称参数。
同时使用模块作为导航目标(就像你在这里所做的那样:Uri viewNav = new Uri("ModuleItems", UriKind.Relative);
可能不是最好的主意。模块对象通常只是一个临时对象,一旦你的模块被默认丢弃初始化。
请求导航
最后,一旦您的模块加载完毕,您就可以请求导航了。您可以使用上面提到的 moduleManager 挂钩到 LoadModuleCompleted
事件:
this.moduleManager.LoadModuleCompleted += (s, e)
{
if (e.ModuleInfo.ModuleName == "ModuleItems")
{
regionManager.RequestNavigate(
RegionNames.TheUpperRegion,
typeof(ToolBarView).FullName),
result =>
{
// you can check here if the navigation was successful
});
regionManager.RequestNavigate(
RegionNames.TheBottomRegion,
typeof(DockingView).FullName));
}
}
最大Magnus Montin helps me to solve the question:
此代码位于 ModuleLogging
的 LoggingViewmodel
:
private void DoLogin(object obj)
{
ShowAnotherView = false;
if (UserName == "1" && UserPassword == "1")
{
container.RegisterType<Object, TheUpperControl>("ModuleItems");
Uri viewNav = new Uri("ModuleItems", UriKind.Relative);
regionManager.RequestNavigate(RegionNames.TheUpperRegion, viewNav);
regionManager.RequestNavigate(RegionNames.TheBottomRegion, viewNav);
LoadTheOtherModule(); //load the other module
var loginView = regionManager.Regions[RegionNames.TheWholeRegion].Views.ElementAt(0);
regionManager.Regions[RegionNames.TheWholeRegion].Remove(loginView); //remove the login view
//MessageBox.Show("");
}
else
ShowPromptingMessage = true;
}
private void LoadTheOtherModule()
{
Type moduleType = typeof(ModuleItems.ModuleItemsModule);
ModuleInfo mi = new ModuleInfo()
{
ModuleName = moduleType.Name,
ModuleType = moduleType.AssemblyQualifiedName,
};
IModuleCatalog catalog = container.Resolve<IModuleCatalog>();
catalog.AddModule(mi);
catalog.Initialize();
IModuleManager moduleManager = container.Resolve<IModuleManager>();
moduleManager.LoadModule(moduleType.Name); //run Initialize() of the other module
}
它就像一个魅力!:)
我有两个模块:ModuleLogging
和 ModuleItems
。
我的 Shell
有声明:
<Grid>
<DockPanel LastChildFill="True">
<ContentControl DockPanel.Dock="Top" prism:RegionManager.RegionName="{x:Static inf:RegionNames.TheUpperRegion}" Margin="5" />
<ContentControl prism:RegionManager.RegionName="{x:Static inf:RegionNames.TheBottomRegion}" Margin="5"/>
</DockPanel>
<ContentControl prism:RegionManager.RegionName="{x:Static inf:RegionNames.TheWholeRegion}" Margin="5" />
</Grid>
首先加载ModuleLogging
。然后,如果用户通过身份验证,我想加载 ModuleItems
。
据我理解正确,我应该实例化
我的引导程序 class:
protected override IModuleCatalog CreateModuleCatalog()
{
ModuleCatalog catalog = new ModuleCatalog();
catalog.AddModule(typeof(ModuleLogging));
//I've not added ModuleItems as I want to check whether the user is authorized
return catalog;
}
我试图从 ModuleLogging
调用 ModuleItems
的内容:
Uri viewNav = new Uri("ModuleItems", UriKind.Relative);
regionManager.RequestNavigate(RegionNames.TheUpperRegion, viewNav);
regionManager.RequestNavigate(RegionNames.TheBottomRegion, viewNav);
但是我的ModuleLogging
的LoggingView
并没有被ModuleItems
的ToolBarView
和ModuleItems
的DockingView
代替。我只是在 ContentControls 中分别看到 System.Object
和 System.Object
而不是控件,因为 LoggingView
是透明的。
是的,我知道内存中没有对象 ModuleItems
.
如何按需加载模块并导航到视图?
您可能需要对这些进行排序以使其正常工作:
- 正在将您的模块添加到目录中
- 按需加载模块
- 正在注册将在区域中显示的视图(或视图模型)
- 请求导航到您的视图
我们按顺序看
正在将您的模块添加到目录中
我看不出有任何理由不将您的模块添加到目录中,但是在身份验证之后您可能不想要的是初始化模块。要按需初始化您的模块,您可以使用标志 OnDemand
:
The module will be initialized when requested, and not automatically on application start-up.
在你的引导程序中:
protected override void ConfigureModuleCatalog()
{
Type ModuleItemsType = typeof(ModuleItems);
ModuleCatalog.AddModule(new ModuleInfo()
{
ModuleName = ModuleItemsType.Name,
ModuleType = ModuleItemsType.AssemblyQualifiedName,
InitializationMode = InitializationMode.OnDemand
});
按需加载模块
认证成功后就可以初始化模块了:
private void OnAuthenticated(object sender, EventArgs args)
{
this.moduleManager.LoadModule("ModuleItems");
}
其中 moduleManager
是 Microsoft.Practices.Prism.Modularity.IModuleManager
的实例(最好注入到您的 class 构造函数中)
正在注册您的观点
您还需要在容器中注册要导航到的视图(如果您使用的是视图模型优先,则为视图模型)。执行此操作的最佳位置可能是模块 ModuleItems 的初始化,只需确保将容器注入其构造函数:
public ModuleItems(IUnityContainer container)
{
_container = container;
}
public void Initialize()
{
_container.RegisterType<object, ToolBarView>(typeof(ToolBarView).FullName);
_container.RegisterType<object, DockingView>(typeof(DockingView).FullName);
// rest of initialisation
}
请注意,为了使 RequestNavigate 正常工作,您必须将视图注册为对象,并且还必须提供其全名作为名称参数。
同时使用模块作为导航目标(就像你在这里所做的那样:Uri viewNav = new Uri("ModuleItems", UriKind.Relative);
可能不是最好的主意。模块对象通常只是一个临时对象,一旦你的模块被默认丢弃初始化。
请求导航
最后,一旦您的模块加载完毕,您就可以请求导航了。您可以使用上面提到的 moduleManager 挂钩到 LoadModuleCompleted
事件:
this.moduleManager.LoadModuleCompleted += (s, e)
{
if (e.ModuleInfo.ModuleName == "ModuleItems")
{
regionManager.RequestNavigate(
RegionNames.TheUpperRegion,
typeof(ToolBarView).FullName),
result =>
{
// you can check here if the navigation was successful
});
regionManager.RequestNavigate(
RegionNames.TheBottomRegion,
typeof(DockingView).FullName));
}
}
最大Magnus Montin helps me to solve the question:
此代码位于 ModuleLogging
的 LoggingViewmodel
:
private void DoLogin(object obj)
{
ShowAnotherView = false;
if (UserName == "1" && UserPassword == "1")
{
container.RegisterType<Object, TheUpperControl>("ModuleItems");
Uri viewNav = new Uri("ModuleItems", UriKind.Relative);
regionManager.RequestNavigate(RegionNames.TheUpperRegion, viewNav);
regionManager.RequestNavigate(RegionNames.TheBottomRegion, viewNav);
LoadTheOtherModule(); //load the other module
var loginView = regionManager.Regions[RegionNames.TheWholeRegion].Views.ElementAt(0);
regionManager.Regions[RegionNames.TheWholeRegion].Remove(loginView); //remove the login view
//MessageBox.Show("");
}
else
ShowPromptingMessage = true;
}
private void LoadTheOtherModule()
{
Type moduleType = typeof(ModuleItems.ModuleItemsModule);
ModuleInfo mi = new ModuleInfo()
{
ModuleName = moduleType.Name,
ModuleType = moduleType.AssemblyQualifiedName,
};
IModuleCatalog catalog = container.Resolve<IModuleCatalog>();
catalog.AddModule(mi);
catalog.Initialize();
IModuleManager moduleManager = container.Resolve<IModuleManager>();
moduleManager.LoadModule(moduleType.Name); //run Initialize() of the other module
}
它就像一个魅力!:)