Ну, я не думаю, что мой титул достаточно эффективен, но в любом случае. Позвольте мне объяснить более точно.
У меня есть класс, Автомобиль. Я создал два детских класса, Автомобиль и Самолет. Я хочу отслеживать скорость, которая является свойством транспортного средства, и привязывать ее к элементу управления (например, метке или изображению) в WPF. Когда я создаю статический класс, единственной целью которого является наблюдение за свойством Speed, оно работает, поскольку INotifyPropertyChanged объявляется с именем свойства Speed.
Но проблема в том, что мне нужно динамически создавать несколько автомобилей и самолетов, просматривая XML-файл и десериализовывая мои объекты, и создавая несколько пользовательских элементов управления Car или Plane (не будем обсуждать этот способ работы, пожалуйста). Поэтому я должен получить свойство Speed внутри класса Vehicle (что является нормальным), и мне нужно получить INotifyPropertyChanged для каждой скорости каждого созданного транспортного средства.
Итак, мои Автомобили и Самолеты загружены, и я должен получить все скорости, но я не могу создать статическое свойство Скорости с помощью Vehicle. Между прочим, при создании нестатического свойства Speed (например, int) в классе Vehicle с параметром INotifyPropertyChanged, заданным в установщике, оно не работает. Кажется, что событие инициировано, но мой конвертер не запущен, и мои элементы управления не обновляются.
В моем классе транспортных средств
Private SpeedValue As Integer
<XmlIgnore()>
Public Property Speed() As Short
Get
Return SpeedValue
End Get
Set(ByVal value As Short)
SpeedValue = value
NotifyPropertyChanged("Speed")
End Set
End Property
Public Event PropertyChanged As PropertyChangedEventHandler _
Implements INotifyPropertyChanged.PropertyChanged
Private Sub NotifyPropertyChanged(ByVal info As String)
RaiseEvent PropertyChanged(Me, New PropertyChangedEventArgs(info))
End Sub
В моем коде позади
Dim b As Binding = New Binding()
b.Source = theVehicle
b.UpdateSourceTrigger = UpdateSourceTrigger.PropertyChanged
b.Path = New PropertyPath(theVehicle.Speed)
b.Path = New PropertyPath("Speed")
b.Converter = New SpeedValueToPicturePathConverter()
b.ConverterParameter = GetType(Vehicle)
img_fonctionnement.SetBinding(Image.SourceProperty, b)
Я тоже пробовал с лямбда-выражениями, но не мог понять, как заставить все это работать. У меня также была ошибка «элемент с тем же ключом уже добавлен», но я так изменил свой код, что не могу вспомнить, как.
Я знаю, что мои объяснения плохие, но это довольно сложно объяснить (и я француз;)). Пожалуйста, если бы вы могли мне помочь, было бы неплохо, потому что я немного застрял здесь.
UPDATE
Дополнительный код:
Это в моей ветке WatchTower, которая выполняется каждые 10 секунд. Весь этот код здесь работает
' theConfig is a singleton which represent my XML config file deserialized
' Getting all vehicles declared in this file works by doing this
For Each vehic As Vehicle In theConfig.Vehicles
Dim realTimeSpeed = server.Read("speed") 'reading the speed on some distant server - don't discuss this, it works fine
If (Not vehic.Speed = realTimeSpeed) Then
vehic.Speed = realTimeSpeed
End If
Next
Здесь я добавляю TabItem для каждого Транспортного средства, объявленного в XML-файле theConfig
'This actually works, a tab is added for each vehicle
For Each vehic As Vehicle In theConfig.Vehicles
Dim vehicTabItem As TabItem = New TabItem()
vehicTabItem.Header = vehic.Description
If (TypeOf vehic Is Car) Then
'Adding the CarView UserControl of my own
vehicTabItem.Content = New CarView(DirectCast(vehic, Car))
TabControl1.Items.Add(vehicTabItem)
ElseIf (TypeOf vehic Is Plane) Then
vehicTabItem.Content = New PlaneView(DirectCast(vehic, Plane))
TabControl1.Items.Add(vehicTabItem)
End If
Next
Это внутри файла CarView (WPF usercontrol, codebehind)
Public Class CarView
Private theCar As Car
Public Sub New(ByVal theCar As Car)
InitializeComponent()
Me.theCar = theCar
Dim b As Binding = New Binding("Speed")
b.Source = theCar
b.Converter = New SpeedValueToPicturePathConverter()
b.ConverterParameter = GetType(Vehicle)
'img_fonctionnement is created in the graphic designer in Visual Studio in xaml
'Remember, this binding works whn I use a static property just for testing
img_fonctionnement.SetBinding(Image.SourceProperty, b)
End Sub
Класс PlaneView для этой части практически одинаков.
Я подтверждаю, что преобразователь запускается только один раз, в первый раз, когда создаются вкладки, потому что я поставил точку останова в определении функции Преобразовать. После этого преобразователь больше не запускается. Таким образом, отображается картинка img_fonctionnement
, но она никогда не обновляется. Но свойство Speed обновлено, клянусь. И INotifyPropertyChanged (в установщике скорости) поднимается, насколько я знаю, с помощью отладчика.
И «элемент с тем же ключом уже был добавлен» (который появляется в блоке сообщений, а не как исключение), кажется, появляется только тогда, когда я слишком долго с отладчиком. В обычном режиме выполнения никогда не показывается.