Подтвердить что ты не робот

Видимость Автообязательность с соглашением об именах

Мне очень нравится Caliburn и соглашение об именовании, и был удивлен, что  Видимость не связана так же, как Конвенция CanNAME используется для защиты действия.  Насколько я знаю, BooleanToVisibilityConverter используется только тогда, когда Binding явно используется в Caliburn, а не автоматически, как метод защиты. Поэтому я решил изменить источник, чтобы автоматически привязать его к "bool? ControlNameIsVisible()" (нулевой эквивалент коллапса) или тому подобное. Мне было интересно, если это правильный подход, и если су, если кто-то уже выполнил эту реализацию и мог бы поделиться ею здесь.

4b9b3361

Ответ 1

Вы можете использовать этот подход, если хотите, это совершенно разумно. Другой подход - использовать в вашей модели представления Border с тем же именем, что и логическое свойство. Caliburn.Micro установит видимость границы на основе значения логического свойства.

<Border x:Name="ControlIsVisible">
  <TextBox x:Name="MyControl" ... />
</Border>

Ответ 2

Если вы хотите общее решение, это то, на чем я закончил, на основе: Добавление соглашения для IsEnabled на Caliburn.Micro

Обратите внимание на переопределение BindActions, а также BindProperties, чтобы вы могли проверять наличие видимости на вещах, у которых есть действия, связанные с ними.

    protected override void Configure()
    {
        base.Configure();

        ConventionManager.AddElementConvention<UIElement>(UIElement.VisibilityProperty, "Visibility", "VisibilityChanged");

        var baseBindProperties = ViewModelBinder.BindProperties;
        ViewModelBinder.BindProperties =
            (frameWorkElements, viewModel) =>
            {
                BindVisiblityProperties(frameWorkElements, viewModel);
                return baseBindProperties(frameWorkElements, viewModel);
            };

        // Need to override BindActions as well, as it called first and filters out anything it binds to before
        // BindProperties is called.
        var baseBindActions = ViewModelBinder.BindActions;
        ViewModelBinder.BindActions =
            (frameWorkElements, viewModel) =>
            {
                BindVisiblityProperties(frameWorkElements, viewModel);
                return baseBindActions(frameWorkElements, viewModel);
            };

    }

    void BindVisiblityProperties(IEnumerable<FrameworkElement> frameWorkElements, Type viewModel)
    {
        foreach (var frameworkElement in frameWorkElements)
        {
            var propertyName = frameworkElement.Name + "IsVisible";
            var property = viewModel.GetPropertyCaseInsensitive(propertyName);
            if (property != null)
            {
                var convention = ConventionManager
                    .GetElementConvention(typeof(FrameworkElement));
                ConventionManager.SetBindingWithoutBindingOverwrite(
                    viewModel,
                    propertyName,
                    property,
                    frameworkElement,
                    convention,
                    convention.GetBindableProperty(frameworkElement));
            }
        }
    }