2013-07-10 2 views
0

내 응용 프로그램에서 다른 I/O 장치 모음이 필요합니다. 직렬, OPC, USB 장치 등. MEF 프레임 워크를 사용하여 컬렉션을 처리하고 새로운 장치를 추가 할 수있는 방법을 제공했습니다.바인딩을 사용하여 이름으로 컨트롤을로드 할 수 있습니까?

내 프로젝트는 다음과 같은 : 장치 인터페이스는 장치 구성의 편집을 처리 사용자 지정 컨트롤과 해당 뷰 - 모델에 대한 경로를 노출 있도록

Atf.Model  'contains the model 
Atf.Gui  'the views and view-models 
Atf.Devices 'contains implementations of IDevice and exports them 

많은 장치가 구성이 필요합니다. MVVM 패턴을 고수하고 가능한 한 뷰와 모델을 분리하려고합니다. 동시에 장치 컬렉션에 대한 연결을 가능한 한 느슨하게 유지하려고합니다.

Atf.Gui에는 발견 된 모든 장치를 표시하고 활성화 된 장치를 표시하는 컨트롤이 있습니다. 활성화 된 장치를 선택하면 해당 편집기를 동적으로 표시하려고합니다.

어떻게하면됩니까? 다음은 몇 가지 아이디어입니다.

아이디어 -1 기기 객체의 경로를 사용하여 뷰 모델에 UserControl을로드하기 만하면됩니다. 이것은 MVVM 분리를 깨고

public System.Windows.Controls.UserControl ConfigureControl 
{ 
    get 
    { 
     // code to load the UserControl using the path property 
    } 
} 

아이디어-2

장치 만 뷰 - 모델을 노출하고 뷰를 데리러 (장치 저장소에 정의) 매핑을 사용 가지고 그 부분 '검증 할'렌더링 것이다. 이것이 어떻게 이루어질 지 확신하지 못합니다. 제 감안
<myeditorcontainer> 
    <ContainerControl Content="{Binding CurrentlySelectedDeviceViewModel}"/> 
</myeditorcontainer> 

아이디어 -3-

는 결합하여 컨트롤로드. 이것이 가능한지 확실하지 않습니다.

<myeditorcontainer> 
    <UserControl Path="{Binding CurrentlySelectedDeviceViewPath}" 
       DataContext="{Binding CurrentlySelectedDeviceViewModel}"/> 
</myeditorcontainer> 

답변

1

생각 2는 갈 길이 멀다고 생각합니다. ContainerControlContentControl에서 유래한다고 가정

, 당신은 보여주지 뷰 모델의 각 유형에 대한 DataTemplate를 지정 할 수 있어야하고 올바른 UI는 뷰 모델의 유형에 따라 렌더링됩니다. 예를 들면 : 당신이 사용할 템플릿을 결정하기 위해 뷰 모델의 종류보다 더 많은 유연성을 필요로하는 경우

<myeditorcontainer> 
    <ContainerControl Content="{Binding CurrentlySelectedDeviceViewModel}"> 
     <ContainerControl.Resources> 
      <DataTemplate DataType="{x:Type ViewModel1Type}"> 
       <!-- controls for ViewModel1's UI --> 
      </DataTemplate> 
      <DataTemplate DataType="{x:Type ViewModel2Type}"> 
       <!-- controls for ViewModel2's UI --> 
      </DataTemplate> 
     </ContainerControl.Resources> 
    </ContainerControl> 
</myeditorcontainer> 

, 당신은 ContentTemplateSelector을 지정할 수 있습니다. 원하는 기준에 따라 사용할 올바른 템플리트를 리턴합니다.

0

이것은 내가 결국 한 일이며 잘 작동하는 것 같습니다. 주요 기능은 뷰 모델이 뷰와 동일한 이름이지만 '모델'이 추가되고 뷰 모델이 특정 클래스 (DeviceSettingsBase)에서 파생된다는 것입니다.

XAML :

<ContentControl Content="{Binding ConfigControl}"/> 

보기 - 모델 :

private RequiredDeviceViewModel rdvm; 

public ContentControl ConfigControl 
{ 
    get 
    { 
     // get assembly which contains this object 
     Assembly assy = Assembly.GetAssembly(rdvm.Device.GetType()); 
     // get View-Type using the name defined in the Device 
     Type viewType = assy.GetType(rdvm.Device.ConfigureControlResourceName, true); 
     // get ViewModel-Type using the viewname + Model (may be null) 
     Type viewModelType = assy.GetType(rdvm.Device.ConfigureControlResourceName + "Model", false); 

     // instantiate the view control 
     ContentControl view = (ContentControl)Activator.CreateInstance(viewType); 
     // instantiate viewModel - if type not null 
     if (viewModelType != null) 
     { 
      object viewModel = (object)Activator.CreateInstance(viewModelType, new object[] { rdvm.RequiredDevice.Config.ConfigString }); 
      view.DataContext = viewModel; 
      // all device viewModels must derive from DeviceSettingsBase 
      CurrentConfigViewModel = viewModel as DeviceSettingsBase; 
      if (CurrentConfigViewModel != null) 
      { 
       CurrentConfigViewModel.IsEditable = IsEditable; 
       CurrentConfigViewModel.PropertyChanged += new System.ComponentModel.PropertyChangedEventHandler(vmb_PropertyChanged); 
       CurrentConfigViewModel.SettingsChanged += new SettingsChangedHandler(vmb_SettingsChanged); 
      } 
     } 
     return view; 
    } 
} 
관련 문제