My feedback

  1. 321 votes
    Sign in
    or sign in with
    • facebook
    • google
      Password icon
      Signed in as (Sign out)

      We’ll send you updates on this idea

      An always happy Friday as I just got the TFS complete email :) As this hasn’t hit an insider preview SDK, i’m going to mark this still as “working on it” still BUT … this will be coming to an insider build near you!

      This item heart is markup extensions. There is one item that will not be there however that is relevant to markup extensions, IServiceProvider. I created a new item for that but we are working on this item []. We have created a new one and we are working on that (that includes IProvideValueTarget and INameScope) but feel we have enough to ship this and mark this larger work item done and we do point out in reference to more work items need to happen, namely the work around IServiceProvider.

      Also XamlServices.Load / Save isn’t directly related to markup extenstion so we’re viewing that…

      DmitryDmitry commented  · 

      Additionally to my previous message, the real LocalizationExtension from our projects is used like x:Static extension, specifying localization type and property:

      static message: <TextBlock Text="{x:Static Member=local:Localization.SomeMessage}">

      dynamic message: <TextBlock Text="{local:Localization Member=local:Localization.SomeMessage}">

      In the second case we can change language at runtime. To implement such extension we need IXamlTypeResolver to resolve the type (and reflection to resolve the property)

      DmitryDmitry commented  · 

      I frequently use custom markup extensions to provide a dynamic value on a property. For that I build a Binding in my markup extension and return the result of calling Binding.ProvideValue method sending IServiceProvider from my MarkupExtension.ProvideValue. You can't disagree (I guess) that Binding could be installed correctly without IServiceProvider. One of the examples I can suggest is dynamic localization in Xaml (very simple, just to show the idea), here is the code:

      public class LocalizationManager : INotifyPropertyChanged
      public static readonly LocalizationManager Instance = new LocalizationManager();
      private static readonly Dictionary<string, string> RuLanguage = new Dictionary<string, string> {{"SomeMessage", "Некоторое сообщение"}};
      private static readonly Dictionary<string, string> NeutralLanguage = new Dictionary<string, string> {{"SomeMessage", "Some Message"}};

      private CultureInfo _currentUiCulture;

      public CultureInfo CurrentUICulture
      get => _currentUiCulture;
      _currentUiCulture = value;

      public string GetLocalizedString(string id) => string.Equals(CurrentUICulture?.TwoLetterISOLanguageName, "ru", StringComparison.OrdinalIgnoreCase) ? RuLanguage[id] : NeutralLanguage[id];

      protected virtual void OnPropertyChanged([CallerMemberName] string propertyName = null) => PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));

      public event PropertyChangedEventHandler PropertyChanged;

      public class DynamicLocalization : MarkupExtension, IValueConverter
      public string LocalizeId { get; set; }

      public override object ProvideValue(IServiceProvider serviceProvider)
      var localizationBinding = new Binding
      Path = new PropertyPath("CurrentUICulture"),
      Source = LocalizationManager.Instance,
      Converter = this
      return localizationBinding.ProvideValue(serviceProvider);

      public object Convert(object value, Type targetType, object parameter, CultureInfo culture) => LocalizationManager.Instance.GetLocalizedString(LocalizeId);

      public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture) => throw new NotSupportedException();

      To use in Xaml:
      <TextBlock Text="{local:LocalizationManager LocalizeId=SomeMessage}" />

      To change localization:
      LocalizationManager.Instance.CurrentUICulture = new CultureInfo("ru");

      Currently it is the only way to provide dynamic values in a custom markup extension that I know (suggest others if you know). I can't find any benefit of custom markup extensions without IServiceProvider. In that case you can return only static values based on some static input through the markup extension properties.

      DmitryDmitry commented  · 

      >> Our goal here is to support ProvideValue like WPF does with the one exception of IServiceProvider, which is a .NET concept that we can't quite solve yet in the UWP platform (also working on these type of things)

      It has not much sense of MarkupExtension without essential interfaces like IXamlTypeResolver (no way to resolve type = no way to implement even the simplest x:Static-like extension), IProvideValueTarget (no way to know where is MarkupExtension being applied), IRootObjectProvider (no way to get Xaml root object) and so on...

      I have a Silverlight/WPF project which uses MarkupExtensions extensively first of all to provide SL/WPF cross platform possibilities to write single Xaml code for both platforms. Without custom Markup extensions I can't even think of using UWP.

      In addition to IServiceProvider, I'd also like to see XamlSetMarkupExtensionAttribute, which allows setting MarkupExtensions on objects which do not derive from DependencyObject (WPF feature which you also could forget)

      DmitryDmitry commented  · 

      Msft srsly? Without custom markup extensions UWP is not a Xaml framework. I have never written an app for UWP and will never write before this suggestion will be implemented. Silverlight is a serious downgrade comparing to WPF, but UWP is about a joke. Facepalm.jpeg here.

      DmitryDmitry supported this idea  · 

    Feedback and Knowledge Base