Резервные значения привязки в Xamarin.FormsXamarin.Forms Binding Fallbacks

Скачать пример Скачать примерDownload Sample Download the sample

Иногда может происходить сбой привязки данных из-за того, что не удалось разрешить источник привязки, или из-за того, что успешно выполненная привязка возвращает значение null.Sometimes data bindings fail, because the binding source can't be resolved, or because the binding succeeds but returns a null value. Хотя в таких ситуациях можно применять преобразователи величин или другой дополнительный код, повысить надежность привязок можно путем определения резервных значений, которые используются в случае сбоя привязки.While these scenarios can be handled with value converters, or other additional code, data bindings can be made more robust by defining fallback values to use if the binding process fails. Для этого можно определить свойства FallbackValue и TargetNullValue в выражении привязки.This can be accomplished by defining the FallbackValue and TargetNullValue properties in a binding expression. Так как эти свойства находятся в классе BindingBase, их можно использовать с обычными привязками, скомпилированными привязками и расширением разметки Binding.Because these properties reside in the BindingBase class, they can be used with bindings, compiled bindings, and with the Binding markup extension.

Примечание

Использование свойств FallbackValue и TargetNullValue в выражении привязки не является обязательным.Use of the FallbackValue and TargetNullValue properties in a binding expression is optional.

Определение резервного значенияDefining a fallback value

Свойство FallbackValue позволяет определить резервное значение, которое будет использоваться, если невозможно разрешить источник привязки.The FallbackValue property allows a fallback value to be defined that will be used when the binding source can't be resolved. Это свойство задается, например, при привязке к исходным свойствам, которые могут иметься не у всех объектов однородных типов в связанной коллекции.A common scenario for setting this property is when binding to source properties that might not exist on all objects in a bound collection of heterogeneous types.

На странице MonkeyDetail иллюстрируется задание свойства FallbackValue:The MonkeyDetail page illustrates setting the FallbackValue property:

<Label Text="{Binding Population, FallbackValue='Population size unknown'}"
       ... />   

Для привязки к Label определено значение FallbackValue, которое будет присвоено целевому объекту, если не удастся разрешить источник привязки.The binding on the Label defines a FallbackValue value that will be set on the target if the binding source can't be resolved. Поэтому, если у привязанного объекта нет свойства Population, отображается значение, определенное в свойстве FallbackValue.Therefore, the value defined by the FallbackValue property will be displayed if the Population property doesn't exist on the bound object. Обратите внимание на то, что здесь значение свойства FallbackValue отделяется одинарными кавычками (апострофами).Notice that here the FallbackValue property value is delimited by single-quote (apostrophe) characters.

Значения свойств FallbackValue рекомендуется определять не в коде, а в качестве ресурсов а ResourceDictionary.Rather than defining FallbackValue property values inline, it's recommended to define them as resources in a ResourceDictionary. Преимущество такого подхода состоит в том, что такие значения определяются однократно в одном месте, где их легко найти.The advantage of this approach is that such values are defined once in a single location, and are more easily localizable. Ресурсы можно извлечь с помощью расширения разметки StaticResource:The resources can then be retrieved using the StaticResource markup extension:

<Label Text="{Binding Population, FallbackValue={StaticResource populationUnknown}}"
       ... />  

Примечание

Свойство FallbackValue невозможно задать с помощью выражения привязки.It's not possible to set the FallbackValue property with a binding expression.

Вот работающая программа:Here's the program running:

Привязка FallbackValueFallbackValue Binding

Если свойство FallbackValue не задано в выражении привязки и не удалось разрешить путь привязки или его часть, для целевого объекта задается BindableProperty.DefaultValue.When the FallbackValue property isn't set in a binding expression and the binding path or part of the path isn't resolved, BindableProperty.DefaultValue is set on the target. Однако если свойство FallbackValue задано, но не удается разрешить путь привязки или его часть, для целевого объекта задается значение свойства FallbackValue.However, when the FallbackValue property is set and the binding path or part of the path isn't resolved, the value of the FallbackValue value property is set on the target. Поэтому на странице MonkeyDetail в элементе Label отображается текст "Population size unknown" (Размер популяции неизвестен), так как у привязанного объекта нет свойства Population.Therefore, on the MonkeyDetail page the Label displays "Population size unknown" because the bound object lacks a Population property.

Важно!

Если задано свойство FallbackValue, определенный преобразователь величин не выполняется в выражении привязки.A defined value converter is not executed in a binding expression when the FallbackValue property is set.

Определение значения, заменяющего NULLDefining a null replacement value

Свойство TargetNullValue позволяет определить заменяющее значение, которое будет использоваться, если источник привязки разрешается, но возвращается значение null.The TargetNullValue property allows a replacement value to be defined that will be used when the binding source is resolved, but the value is null. Это свойство задается, например, при привязке к исходным свойствам, которые могут иметь значение null в связанной коллекции.A common scenario for setting this property is when binding to source properties that might be null in a bound collection.

На странице Monkeys иллюстрируется задание свойства TargetNullValue:The Monkeys page illustrates setting the TargetNullValue property:

<ListView ItemsSource="{Binding Monkeys}"
          ...>
    <ListView.ItemTemplate>
        <DataTemplate>
            <ViewCell>
                <Grid>
                    ...
                    <Image Source="{Binding ImageUrl, TargetNullValue='https://upload.wikimedia.org/wikipedia/commons/2/20/Point_d_interrogation.jpg'}"
                           ... />
                    ...
                    <Label Text="{Binding Location, TargetNullValue='Location unknown'}"
                           ... />
                </Grid>
            </ViewCell>
        </DataTemplate>
    </ListView.ItemTemplate>
</ListView>

Для привязок к Image и Label определены значения TargetNullValue, которые применяются, если путь привязки возвращает значение null.The bindings on the Image and Label both define TargetNullValue values that will be applied if the binding path returns null. Поэтому значения свойств TargetNullValue отображаются для всех объектов в коллекции, для которых свойства ImageUrl и Location не определены.Therefore, the values defined by the TargetNullValue properties will be displayed for any objects in the collection where the ImageUrl and Location properties are not defined. Обратите внимание на то, что здесь значения свойства TargetNullValue отделяются одинарными кавычками (апострофами).Notice that here the TargetNullValue property values are delimited by single-quote (apostrophe) characters.

Значения свойств TargetNullValue рекомендуется определять не в коде, а в качестве ресурсов а ResourceDictionary.Rather than defining TargetNullValue property values inline, it's recommended to define them as resources in a ResourceDictionary. Преимущество такого подхода состоит в том, что такие значения определяются однократно в одном месте, где их легко найти.The advantage of this approach is that such values are defined once in a single location, and are more easily localizable. Ресурсы можно извлечь с помощью расширения разметки StaticResource:The resources can then be retrieved using the StaticResource markup extension:

<Image Source="{Binding ImageUrl, TargetNullValue={StaticResource fallbackImageUrl}}"
       ... />
<Label Text="{Binding Location, TargetNullValue={StaticResource locationUnknown}}"
       ... />

Примечание

Свойство TargetNullValue невозможно задать с помощью выражения привязки.It's not possible to set the TargetNullValue property with a binding expression.

Вот работающая программа:Here's the program running:

Привязка TargetNullValueTargetNullValue Binding

Когда свойство TargetNullValue не указано в выражении привязки, исходное значение null преобразуется, если определен преобразователь величин, форматируется, если определен формат StringFormat, а затем результат задается для целевого объекта.When the TargetNullValue property isn't set in a binding expression, a source value of null will be converted if a value converter is defined, formatted if a StringFormat is defined, and the result is then set on the target. Однако когда свойство TargetNullValue указано, исходное значение null преобразуется, если определен преобразователь величин, а затем, если оно по-прежнему равно null после преобразования, значение свойства TargetNullValue задается для целевого объекта.However, when the TargetNullValue property is set, a source value of null will be converted if a value converter is defined, and if it's still null after the conversion, the value of the TargetNullValue property is set on the target.

Важно!

Если свойство TargetNullValue задано, форматирование строк в выражении привязки не применяется.String formatting is not applied in a binding expression when the TargetNullValue property is set.