2011-03-30 30 views
40

En mi proyecto WPF, tengo un ListBox que muestra elementos de una colección List<string>. Quería que el texto de estos elementos fuera editable, así que envolví cada uno de ellos en una ItemTemplate con un TextBox (podría no ser la mejor manera, pero soy nuevo en WPF). Estaba teniendo problemas simplemente vinculando la propiedad TextBoxes 'Text al valor de cada elemento. Finalmente me encontré con un ejemplo usando un solo punto o el plazo de su propiedad Path ({Binding Path=.}):Son "{Binding Path =.}" Y "{Binding}" realmente iguales

<ListBox ItemsSource="{Binding ElementName=recipesListbox,Path=SelectedItem.Steps}"> 
    <ListBox.ItemTemplate> 
     <DataTemplate> 
      <TextBox Text="{Binding Path=.}"/> 
     </DataTemplate> 
    </ListBox.ItemTemplate> 
</ListBox> 

Sin embargo, yo no entiendo por qué el simple uso de {Binding} no funcionó.

Se planteó una "dos vías de unión requiere Ruta o XPath" excepción, ya que according to Microsoft: (.) ​​

[...] un período de ruta se puede usar para unirse a la corriente fuente. Por ejemplo, Text = "{Binding}" es equivalente al texto = "{Binding Path =.}"

Podría alguien arrojar luz sobre este comportamiento ambiguo?

EDIT: Por otra parte, parece {Binding Path=.} no necesariamente para obtener una de dos vías de unión, como modificar el texto y mover el foco no se actualiza la fuente subyacente (la misma fuente tiene también propiedades visualiza y se modificó con éxito en una cuadrícula de datos controlar). Definitivamente me falta algo aquí.

Respuesta

20

La documentación indica que {Binding} es equivalente a {Binding Path=.}. Sin embargo, es no equivalente a {Binding Path} como ha escrito. Si incluye la propiedad Path, debe asignarla a algo, ya sea Path=. o Path=OtherProperty.

+2

Eso fue un error tipográfico, está arreglado ahora. – Fueled

+0

Pero el enlace bidireccional TODAVÍA falla. Se niega a guardar los cambios. Si tiene un ObsColl y hacer Path =. Modo = enlace de dos vías, que se agrega a la colección funciona bien. Cambiar el número en el índice 0, por ejemplo, no. Si enlaza una cuadrícula de datos con ella y especifica un datagridtextcolumn, se rehúsa a guardar con Path =. – user99999991

7

Estos no son lo mismo. Si enlaza esto donde ConsoleMessages es una cadena ObservableCollection con solo {Binding} obtiene un "enlace bidireccional que requiere Path o XPath". excepción donde funciona como {Binding Path =.}. Esto es con WPF 4.0 ...

<ItemsControl x:Name="ConsoleOutput" ItemsSource="{Binding ConsoleMessages, Mode=OneWay}" MaxHeight="400"> 
     <ItemsControl.ItemTemplate> 
      <DataTemplate> 
       <TextBox Text="{Binding Path=.}" BorderThickness="0" Margin="0" /> 
      </DataTemplate> 
     </ItemsControl.ItemTemplate> 
    </ItemsControl> 

Mi 2p pena ...

24

El punto de la excepción es de suponer que no se puede bidireccional enlazar un código vinculante en sí, por lo que trata de evitar desde la creación de un enlace que no se comporta de la manera que le gustaría. Al usar {Binding Path=.}, simplemente engaña el manejo de errores.

(Además, no es insólito que la documentación es errónea o inexacta, aunque me gusta la documentación de MSDN mucho en general, ya que por lo general contiene los puntos cruciales uno está interesado en)

+4

+1: Esta es la respuesta correcta. [Me acaba de encontrar] (http://stackoverflow.com/a/13089160/149265) este fenómeno yo mismo. –

+0

Pero el enlace bidireccional TODAVÍA falla. Se niega a guardar los cambios. Si tiene un ObsColl y hacer Path =. Modo = enlace de dos vías, que se agrega a la colección funciona bien. Cambiar el número en el índice 0, por ejemplo, no. Si enlaza una cuadrícula de datos con ella y especifica un datagridtextcolumn, se rehúsa a guardar con Path =. – user99999991

+0

@ user999999928: Eso es lo que he estado diciendo: simplemente engañas el manejo de errores. Si comete un error que no se detecta, aún no obtendrá el enlace que desea, ya que aún enlaza a la fuente que no puede detectar los cambios. –

5

En resumen, la diferencia entre los dos es análoga a la diferencia entre el paso tradicional por valor y el pase por referencia.(ARY - What's the difference between passing by reference vs. passing by value?)

Sin embargo, yo no entiendo por qué el simple uso de {Binding} no funcionó (se levantó una "unión de dos vías requiere Ruta o XPath" excepción)

Lets asuma aquí por ahora que {Binding} se puede usar para el enlace bidireccional. En general, {Binding} crea un enlace basado en el valor con datacontext que no permite actualizar el contexto de datos.

Considerando que {Binding Path=.} crea un enlace basado en referencia con el área de memoria referenciada por la 'Ruta' que permite actualizar el valor mediante referencia (en este caso 'dot' el actualcontexto de datos).

Espero que esto ayude!

+0

usando ByRef y ByVal al menos me dio una idea sobre cómo diferenciar los dos enlaces (con ruta y sin /). ¡Gracias! –