MVVM Light Listener не освобождава / детерминистично финализиране за регистриран обект?

Имам дъщерен прозорец със свързана виртуална машина, който се създава всеки път, когато поискам дъщерният прозорец да се отвори. когато детският прозорец се отвори, той регистрира слушател за MVVM Light съобщение. След като затворя прозореца, съм почти сигурен, че освобождавам всички препратки към него, но всъщност не извиквам dispose, защото не имплементира IDisposeable.

Когато създам друг дъщерен прозорец от същия тип и му изпратя различен контекст, знам, че получавам съобщението от предишния екземпляр на VM... всеки път, когато използвам прозореца, все повече и повече VM слушат и кодът се повтаря.

Как мога да съм сигурен, че моята предишна виртуална машина, която се е регистрирала да слуша съобщение, всъщност е била освободена и вече не е активна. Има ли детерминистичен начин да направите това?


person codeputer    schedule 12.06.2011    source източник


Отговори (3)


Всеки път, когато регистрирате съобщение, трябва да се уверите, че сте отменили регистрацията на съобщението. За да отмените регистрацията, можете да използвате метода Cleanup на класове, произлизащи от ViewModelBase. В други случаи, напр. изглед, трябва да приложите метод, който се извиква, когато изгледът е разтоварен - например чрез прихващане и обработка на разтовареното събитие в контрола или изглед. В този метод след това извиквате Messenger.Unregister(EventTarget).

Това поведение е странност в текущата версия на инструментариума и Лоран е наясно с това.

person AxelEckenberger    schedule 12.06.2011
comment
Почистването не работи както трябва, т.е. не премахна препратките. - person Zeeshan Ajmal; 01.10.2013

Как сте кодирали манипулатора за съобщението във VM? Изглежда, че вероятно го насочвате към метод в същата виртуална машина, която се регистрира за съобщението. Това кара класа на Messenger да поддържа препратка към виртуалната машина и да предотвратява нейното събиране на боклук (вижте тук за дискусия). Има две решения: внедряване на IDisposable и отмяна на регистрацията на всички съобщения за вашия екземпляр на виртуална машина или просто дерегистриране на всички съобщения от екземпляра на виртуална машина, когато дъщерният диалог се затвори. Лично аз бих направил и двете, за да гарантирам, че цялата обектна мрежа е освободена.

person Mike Post    schedule 12.06.2011

Можете да използвате или метода за почистване, или ръчно да отмените регистрацията на съобщението. За повече подробности щракнете тук.

person Ehsan Zargar Ershadi    schedule 12.06.2011