2013-03-18 11 views
9

Ho un UserControl con il seguente trigger di evento:EventTrigger non sparare per l'evento Loaded di UserControl

<UserControl x:Class="TestApp.Views.MyUserControl" 
     xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
     xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity" 
     > 

<i:Interaction.Triggers> 
    <i:EventTrigger EventName="Loaded"> 
     <i:InvokeCommandAction Command="{Binding OnLoadedCommand}" /> 
    </i:EventTrigger> 
</i:Interaction.Triggers> 

E 'stato impostato tramite il costruttore di UserControl (si prega di ignorare il ServiceLocator ..si è solo un rapido prototipo):

public MyUserControl() 
{ 
    InitializeComponent(); 

    DataContext = ServiceLocator.Current.GetInstance<DirectorySearchViewModel>(); 
} 

A mio avviso-modello che ho il seguente:

public ICommand OnLoadedCommand { get; private set; } 

    public MyUserControl() 
    { 
     OnLoadedCommand = new DelegateCommand(OnLoaded); 
    } 

    public void OnLoaded() 
    { 
    } 

OnLoaded non viene mai chiamato. Se cambio EventName per dire ..MouseDown, funziona ma non funziona per Loaded

Abbastanza sicuro che sia uno sbaglio stupido (giuro che l'ho già fatto un milione di volte in passato) ma posso sembra che lo stiano facendo ora

+2

WAG qui, ma provare a impostare il vostro DC prima di chiamare InitializeComponent nel costruttore. – Will

+0

BINGO. ARGH! Quante volte continuo a fare lo stesso stupido errore! Si prega di rispondere come risposta in modo che possa darti credito :) – blue18hutthutt

risposta

9
public MyUserControl() 
{ 
    DataContext = ServiceLocator.Current.GetInstance<DirectorySearchViewModel>(); 
    InitializeComponent(); 
} 

Gli aristocratici.

+0

Questo ha funzionato! Puoi dire perché succede? Perché DataContext deve essere impostato prima? –

+1

@AbdulkarimKanaan Perché l'evento Loaded si attiva durante la chiamata a InitializeComponent. InitializeComponent * inizializza la finestra *. Una volta inizializzato, si attiva l'evento Loaded. Poiché si imposta DataContext * dopo che * si è verificato l'evento Loaded, l'evento trigger non ha nulla da attivare e non ricorda che l'evento è già stato attivato e non sa che si desidera che venga attivato una volta impostato DataContext. Non è così che è progettato. – Will

3

Per chiunque altro che si imbatte in questo lo si può fare senza il codice dietro come questo:

<UserControl x:Class="TestApp.Views.MyUserControl" 
    ... etc... 
    x:Name="theControl" 
    > 

    <i:Interaction.Triggers> 
     <i:EventTrigger EventName="Loaded"> 
      <i:InvokeCommandAction 
       Command="{Binding ElementName=theControl, Path=OnLoadedCommand}"/> 
     </i:EventTrigger> 
    </i:Interaction.Triggers> 
+0

Viene visualizzato in fase di runtime: "System.Windows.Data Errore: 40: Errore percorso BindingExpression: proprietà 'ViewLoadedCommand' non trovata su 'oggetto' '' FooView '(Name =' self ')'. BindingExpression: Path = ViewLoadedCommand; DataItem = 'FooView' (Name = 'self'); l'elemento di destinazione è 'InvokeCommandAction' (HashCode = 21993383); la proprietà target è 'Command' (digitare 'ICommand') ". Sta guardando la vista piuttosto che ViewModel per la proprietà del comando. – Dai

+1

Ah, sembra che la soluzione sia usare 'Command =" {Binding ElementName = self, Path = DataContext.ViewLoadedCommand} "' - quindi aggiungere "' DataContext' "al lavoro' Path'. – Dai

+0

Oops ... Non ricordo nemmeno di aver risposto a questa domanda, ma tu sei assolutamente corretto, con questi tipi di binding devi specificare DataContext nel percorso. Devo aver usato il controllo come proprio DataContext durante i miei test. Grazie per aver corretto la mia risposta. –