0

I'm trying to set a custom attached property which I can bind to in Xaml. It works fine if I pass it plain strings:

MyProperties.h:

#pragma once

#include "pch.h"

namespace SimpleApp
{
    namespace WUX = Windows::UI::Xaml;

    public ref class MyProperties sealed : public WUX::DependencyObject
    {
    private:
        static WUX::DependencyProperty^ _MyValue;

    public:
        MyProperties::MyProperties();

        static property WUX::DependencyProperty^ MyValue
        {
            WUX::DependencyProperty^ get()
            {
                return _MyValue;
            }
        };
        static Platform::String^ GetMyValue(WUX::UIElement^ element);
        static void SetMyValue(WUX::UIElement^ element, Platform::String^ value);
    };
}

MyProperties.cpp:

#include "pch.h"
#include "MyProperties.h"

using namespace Windows::UI::Xaml;
using namespace SimpleApp;

MyProperties::MyProperties()
{
};


DependencyProperty^ MyProperties::_MyValue = DependencyProperty::RegisterAttached(
    "MyValue", 
    Platform::String::typeid, 
    MyProperties::typeid,
    ref new PropertyMetadata(false)
    );

Platform::String^ MyProperties::GetMyValue(UIElement^ element)
{
    auto val = safe_cast<Platform::String^>(element->GetValue(_MyValue));
    return val;
}

void MyProperties::SetMyValue(UIElement^ element, Platform::String^ stringValue)
{
    element->SetValue(_MyValue, stringValue);
    OutputDebugString(L"It worked!");
    // Also do other stuff
}

Xaml:

<Page
    x:Class="SimpleApp.MainPage"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="using:SimpleApp"
    Width="525"
    >

    <Grid x:Name="_grid" Width="500" DataContext="{Binding ElementName=_grid}">

        <TextBlock local:MyProperties.MyValue="Hello" Text="{Binding Width}" />

    </Grid>
</Page>

This works - the SetMyValue function executes with the parameter "Hello" passed to it.

When I try and use binding on the MyValue property, though, SetMyValue doesn't execute. I'm replacing the TextBlock with this in Xaml:

<TextBlock local:MyProperties.MyValue="{Binding Width}" Text="{Binding Width}" />

I am binding Text to Width as well just to be sure that it is, in general, working. Is there a magic declaration I have to make somewhere to persuade the property to be bindable?

NB this question is asking something similar, but for WPF, and the asker didn't seem to have his problem solved anyway.

Community
  • 1
  • 1
user1002973
  • 2,088
  • 6
  • 22
  • 31

1 Answers1

0

I think your binding is working. The fact that SetMyValue is not called also makes sense to me. WPF bypasses your property getter/setter, and uses the internal dependency property instead, for performance reasons(eg SetMyValue is not called).

If you are interested about the value changes, you need to explictly say so:

(random copy/paste)

  public static readonly DependencyProperty FilterIDProperty = 
          DependencyProperty.RegisterAttached(
     FilterIDPropertyName,
     typeof(int),
     typeof(PeopleUserControl),
     new FrameworkPropertyMetadata(0, 
          FrameworkPropertyMetadataOptions.BindsTwoWayByDefault, FilterIDChanged));

FilterIDCHanged will be called, once the dependency property changes. Also, notice that I passed the BindsTwoWayByDefault to dependency property, I don't remember 100% if that's needed, but this can also be the reason why binding doesn't work.

Erti-Chris Eelmaa
  • 25,338
  • 6
  • 61
  • 78