I've been beating my head against the wall over this for days now and I can't seem to find any info that fits my problem.
So, I have this toolbar Usercontrol that's meant to be dropped in to an application. This toolbar has a property exposed called "FullExtentButton" which is a reference to the button. What I want is to expose the properties of this button in the designer properties pane on the toolbar user control so the developers can set the properties directly from the designer.
In WinForms, this was very easy to do. WPF, not so much (unless I'm just blind).
In my tool bar code:
[Category("Standard Buttons")]
[Browsable(true)]
[DesignerSerializationVisibility(DesignerSerializationVisibility.Visible)]
public MyToolbarButton FullExtentButton
{
get;
private set;
}
This value is set in the constructor the user control:
public MyToolbar()
{
InitializeComponent();
FullExtentButton = new MyToolbarButton("FullExtent", "/Utilities;component/Resources/full_extent_16x16.png");
}
The button itself is quite simple:
public class MyToolbarButton
: Freezable
{
#region Dependency Properties.
/// <summary>
/// Dependency property for the <see cref="IsVisible"/> property.
/// </summary>
public static DependencyProperty IsVisibleProperty = DependencyProperty.Register("IsVisible", typeof(bool), typeof(MyToolbarButton),
new FrameworkPropertyMetadata(true,
FrameworkPropertyMetadataOptions
.BindsTwoWayByDefault, Visible_Changed));
/// <summary>
/// Dependency property for the <see cref="IsEnabled"/> property.
/// </summary>
public static DependencyProperty IsEnabledProperty = DependencyProperty.Register("IsEnabled", typeof(bool), typeof(MyToolbarButton),
new FrameworkPropertyMetadata(true,
FrameworkPropertyMetadataOptions.BindsTwoWayByDefault, Enabled_Changed));
/// <summary>
/// Dependency property for the <see cref="ToolTip"/> property.
/// </summary>
public static DependencyProperty ToolTipProperty = DependencyProperty.Register("ToolTip", typeof(string), typeof(MyToolbarButton),
new FrameworkPropertyMetadata(string.Empty,
FrameworkPropertyMetadataOptions.BindsTwoWayByDefault, ToolTip_Changed));
/// <summary>
/// Dependency property for the <see cref="Glyph"/> property.
/// </summary>
public static DependencyProperty GlyphProperty = DependencyProperty.Register("Glyph", typeof(ImageSource), typeof(MyToolbarButton),
new FrameworkPropertyMetadata(null,
FrameworkPropertyMetadataOptions.BindsTwoWayByDefault, Glyph_Changed));
/// <summary>
/// Dependency property for the <see cref="ID"/> property.
/// </summary>
public static DependencyProperty IDProperty = DependencyProperty.Register("ID", typeof(string), typeof(MyToolbarButton),
new FrameworkPropertyMetadata(string.Empty,
FrameworkPropertyMetadataOptions.BindsTwoWayByDefault));
/// <summary>
/// Dependency property for the <see cref="ClickedCommand"/> property.
/// </summary>
public static DependencyProperty ClickedCommandProperty = DependencyProperty.Register("ClickedCommand", typeof(IMyRelayCommand<string>),
typeof(MyToolbarButton),
new FrameworkPropertyMetadata(null, FrameworkPropertyMetadataOptions.BindsTwoWayByDefault));
#endregion
#region Variables.
// The default image source for the button glyph.
private readonly Uri _defaultImageSource;
#endregion
#region Properties.
/// <summary>
/// Property to set or return the command to execute when the button is clicked.
/// </summary>
public IMyRelayCommand<string> ClickedCommand
{
get
{
return (IMyRelayCommand<string>)GetValue(ClickedCommandProperty);
}
set
{
SetValue(ClickedCommandProperty, value);
}
}
/// <summary>
/// Property to set or return the ID of the button.
/// </summary>
public string ID
{
get
{
object value = GetValue(IDProperty);
return value == null ? string.Empty : value.ToString();
}
set
{
SetValue(IDProperty, value);
}
}
/// <summary>
/// Property to set or return the glyph for this button.
/// </summary>
public ImageSource Glyph
{
get
{
return GetValue(GlyphProperty) as ImageSource;
}
set
{
SetValue(GlyphProperty, value);
}
}
/// <summary>
/// Property to set or return the tool tip for the button.
/// </summary>
public string ToolTip
{
get
{
object value = GetValue(ToolTipProperty);
return value == null ? string.Empty : value.ToString();
}
set
{
SetValue(ToolTipProperty, value);
}
}
/// <summary>
/// Property to set or return whether the button is visible or not.
/// </summary>
public bool IsVisible
{
get
{
return (bool)GetValue(IsVisibleProperty);
}
set
{
SetValue(IsVisibleProperty, value);
}
}
/// <summary>
/// Property to set or return whether the button is enabled or not.
/// </summary>
public bool IsEnabled
{
get
{
return (bool)GetValue(IsEnabledProperty);
}
set
{
SetValue(IsEnabledProperty, value);
}
}
#endregion
#region Methods.
/// <summary>
/// Function to handle a change to the <see cref="GlyphProperty"/>.
/// </summary>
/// <param name="sender">The sender of the event.</param>
/// <param name="e">The <see cref="DependencyPropertyChangedEventArgs"/> instance containing the event data.</param>
private static void Glyph_Changed(DependencyObject sender, DependencyPropertyChangedEventArgs e)
{
// TODO
}
/// <summary>
/// Function to handle a change to the <see cref="IsVisibleProperty"/>.
/// </summary>
/// <param name="sender">The sender of the event.</param>
/// <param name="e">The <see cref="DependencyPropertyChangedEventArgs"/> instance containing the event data.</param>
private static void Visible_Changed(DependencyObject sender, DependencyPropertyChangedEventArgs e)
{
// TODO
}
/// <summary>
/// Function to handle a change to the <see cref="IsEnabledProperty"/>.
/// </summary>
/// <param name="sender">The sender of the event.</param>
/// <param name="e">The <see cref="DependencyPropertyChangedEventArgs"/> instance containing the event data.</param>
private static void Enabled_Changed(DependencyObject sender, DependencyPropertyChangedEventArgs e)
{
// TODO
}
/// <summary>
/// When implemented in a derived class, creates a new instance of the <see cref="T:System.Windows.Freezable" /> derived class.
/// </summary>
/// <returns>The new instance.</returns>
protected override Freezable CreateInstanceCore()
{
return new MyToolbarButton();
}
#endregion
#region Constructor/Finalizer.
/// <summary>
/// Initializes a new instance of the <see cref="MyToolbarButton"/> class.
/// </summary>
/// <param name="buttonID">The ID of the button being clicked.</param>
/// <param name="defaultImageSource">The default image source URI for the glyph used by the button.</param>
internal MyToolbarButton(string buttonID, string defaultImageSource)
{
ID = buttonID;
IsVisible = true;
IsEnabled = true;
ToolTip = string.Empty;
if (!string.IsNullOrWhiteSpace(defaultImageSource))
{
_defaultImageSource = new Uri(defaultImageSource, UriKind.Relative);
}
}
/// <summary>
/// Initializes a new instance of the <see cref="MyToolbarButton"/> class.
/// </summary>
public MyToolbarButton()
{
// This is here to keep the XAML designer from complaining.
}
#endregion
But, when I view the button property on my user control in the XAML designer, and expand its properties I get this:
As you can see, there are no properties under that property in the XAML designer. What I want is to have the properties for that button appear under the "FullExtentsButton" property so that my developers can modify the properties, but not be able to create/remove the instance that's already there.
I've tried making the FullExtentButton property on my UserControl a DependencyProperty, but that didn't fix anything.
This is part of a standard toolbar that we want to use across applications, so enforcing consistency is pretty important for us. Plus it will allow our devs to focus on other parts of applications rather than reimplementing the same thing over and over (which is what we're having to do right now).
So, that said, I'm at my wits end here, what am I doing wrong?
Using this code which I had to change somewhat to get it to compile....
/// <summary>
/// Interaction logic for MyToolBarButton.xaml
/// </summary>
public partial class MyToolBarButton : UserControl
{
public MyToolBarButton()
{
InitializeComponent();
}
#region Dependency Properties.
/// <summary>
/// Dependency property for the <see cref="IsVisible"/> property.
/// </summary>
public static DependencyProperty IsVisibleProperty = DependencyProperty.Register("IsVisible", typeof(bool), typeof(MyOldToolBarButton),
new FrameworkPropertyMetadata(true,
FrameworkPropertyMetadataOptions
.BindsTwoWayByDefault, Visible_Changed));
/// <summary>
/// Dependency property for the <see cref="IsEnabled"/> property.
/// </summary>
public static DependencyProperty IsEnabledProperty = DependencyProperty.Register("IsEnabled", typeof(bool), typeof(MyOldToolBarButton),
new FrameworkPropertyMetadata(true,
FrameworkPropertyMetadataOptions.BindsTwoWayByDefault, Enabled_Changed));
/// <summary>
/// Dependency property for the <see cref="ToolTip"/> property.
/// </summary>
public static DependencyProperty ToolTipProperty = DependencyProperty.Register("ToolTip", typeof(string), typeof(MyOldToolBarButton),
new FrameworkPropertyMetadata(string.Empty,
FrameworkPropertyMetadataOptions.BindsTwoWayByDefault,
new PropertyChangedCallback(ToolTipPropertyChanged)));
private static void ToolTipPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
throw new NotImplementedException();
}
/// <summary>
/// Dependency property for the <see cref="Glyph"/> property.
/// </summary>
public static DependencyProperty GlyphProperty = DependencyProperty.Register("Glyph", typeof(ImageSource), typeof(MyOldToolBarButton),
new FrameworkPropertyMetadata(null,
FrameworkPropertyMetadataOptions.BindsTwoWayByDefault, Glyph_Changed));
/// <summary>
/// Dependency property for the <see cref="ID"/> property.
/// </summary>
public static DependencyProperty IDProperty = DependencyProperty.Register("ID", typeof(string), typeof(MyOldToolBarButton),
new FrameworkPropertyMetadata(string.Empty,
FrameworkPropertyMetadataOptions.BindsTwoWayByDefault));
/// <summary>
/// Dependency property for the <see cref="ClickedCommand"/> property.
/// </summary>
public static DependencyProperty ClickedCommandProperty = DependencyProperty.Register("ClickedCommand", typeof(string),
typeof(MyOldToolBarButton),
new FrameworkPropertyMetadata(null, FrameworkPropertyMetadataOptions.BindsTwoWayByDefault));
#endregion
#region Variables.
// The default image source for the button glyph.
public Uri _defaultImageSource { private set; get; }
#endregion
#region Properties.
/// <summary>
/// Property to set or return the ID of the button.
/// </summary>
[Category("Configuration")]
public string ID
{
get
{
object value = GetValue(IDProperty);
return value == null ? string.Empty : value.ToString();
}
set
{
SetValue(IDProperty, value);
}
}
/// <summary>
/// Property to set or return the glyph for this button.
/// </summary>
[Category("Configuration")]
public ImageSource Glyph
{
get
{
return GetValue(GlyphProperty) as ImageSource;
}
set
{
SetValue(GlyphProperty, value);
}
}
/// <summary>
/// Property to set or return the tool tip for the button.
/// </summary>
///
[Category("Configuration")]
public string ToolTip
{
get
{
object value = GetValue(ToolTipProperty);
return value == null ? string.Empty : value.ToString();
}
set
{
SetValue(ToolTipProperty, value);
}
}
/// <summary>
/// Property to set or return whether the button is visible or not.
/// </summary>
///
[Category("Configuration")]
public bool IsVisible
{
get
{
return (bool)GetValue(IsVisibleProperty);
}
set
{
SetValue(IsVisibleProperty, value);
}
}
/// <summary>
/// Property to set or return whether the button is enabled or not.
/// </summary>
///
[Category("Configuration")]
public bool IsEnabled
{
get
{
return (bool)GetValue(IsEnabledProperty);
}
set
{
SetValue(IsEnabledProperty, value);
}
}
#endregion
#region Methods.
/// <summary>
/// Function to handle a change to the <see cref="GlyphProperty"/>.
/// </summary>
/// <param name="sender">The sender of the event.</param>
/// <param name="e">The <see cref="DependencyPropertyChangedEventArgs"/> instance containing the event data.</param>
private static void Glyph_Changed(DependencyObject sender, DependencyPropertyChangedEventArgs e)
{
// TODO
}
/// <summary>
/// Function to handle a change to the <see cref="IsVisibleProperty"/>.
/// </summary>
/// <param name="sender">The sender of the event.</param>
/// <param name="e">The <see cref="DependencyPropertyChangedEventArgs"/> instance containing the event data.</param>
private static void Visible_Changed(DependencyObject sender, DependencyPropertyChangedEventArgs e)
{
// TODO
}
/// <summary>
/// Function to handle a change to the <see cref="IsEnabledProperty"/>.
/// </summary>
/// <param name="sender">The sender of the event.</param>
/// <param name="e">The <see cref="DependencyPropertyChangedEventArgs"/> instance containing the event data.</param>
private static void Enabled_Changed(DependencyObject sender, DependencyPropertyChangedEventArgs e)
{
// TODO
}
/// <summary>
/// When implemented in a derived class, creates a new instance of the <see cref="T:System.Windows.Freezable" /> derived class.
/// </summary>
/// <returns>The new instance.</returns>
protected Freezable CreateInstanceCore()
{
return new MyOldToolBarButton();
}
#endregion
#region Constructor/Finalizer.
/// <summary>
/// Initializes a new instance of the <see cref="MyOldToolBarButton"/> class.
/// </summary>
/// <param name="buttonID">The ID of the button being clicked.</param>
/// <param name="defaultImageSource">The default image source URI for the glyph used by the button.</param>
internal void MyOldToolBarButton(string buttonID, string defaultImageSource)
{
ID = buttonID;
IsVisible = true;
IsEnabled = true;
ToolTip = string.Empty;
if (!string.IsNullOrWhiteSpace(defaultImageSource))
{
_defaultImageSource = new Uri(defaultImageSource, UriKind.Relative);
}
}
/// <summary>
/// Initializes a new instance of the <see cref="MyOldToolBarButton"/> class.
/// </summary>
public void MyOldToolBarButton()
{
// This is here to keep the XAML designer from complaining.
}
#endregion
}
And adding it to another "parent" control... The properties look like this:
Is this what you are looking for?
Related
I have a custom Checkbox is implemented as below;
public class CheckBox : View, INotifyPropertyChanged
{
/// <summary>
/// The checked state property.
/// </summary>
public static readonly BindableProperty CheckedProperty =
BindableProperty.Create<CheckBox, bool>(
p => p.Checked, false, BindingMode.TwoWay, propertyChanged: OnCheckedPropertyChanged);
/// <summary>
/// The checked text property.
/// </summary>
public static readonly BindableProperty CheckedTextProperty =
BindableProperty.Create<CheckBox, string>(
p => p.CheckedText, string.Empty, BindingMode.TwoWay);
/// <summary>
/// The unchecked text property.
/// </summary>
public static readonly BindableProperty UncheckedTextProperty =
BindableProperty.Create<CheckBox, string>(
p => p.UncheckedText, string.Empty);
/// <summary>
/// The default text property.
/// </summary>
public static readonly BindableProperty DefaultTextProperty =
BindableProperty.Create<CheckBox, string>(
p => p.Text, string.Empty,BindingMode.TwoWay, propertyChanged: OnDefaultTextChanged);
/// <summary>
/// Identifies the TextColor bindable property.
/// </summary>
///
/// <remarks/>
public static readonly BindableProperty TextColorProperty =
BindableProperty.Create<CheckBox, Color>(
p => p.TextColor, Color.Default);
/// <summary>
/// The font size property
/// </summary>
public static readonly BindableProperty FontSizeProperty =
BindableProperty.Create<CheckBox, double>(
p => p.FontSize, -1);
/// <summary>
/// The font name property.
/// </summary>
public static readonly BindableProperty FontNameProperty =
BindableProperty.Create<CheckBox, string>(
p => p.FontName, string.Empty);
/// <summary>
/// The checked changed event.
/// </summary>
public event EventHandler<EventArgs<bool>> CheckedChanged;
public event PropertyChangedEventHandler PropertyChanged;
/// <summary>
/// Gets or sets a value indicating whether the control is checked.
/// </summary>
/// <value>The checked state.</value>
public bool Checked
{
get
{
return this.GetValue<bool>(CheckedProperty);
}
set
{
if (this.Checked != value)
{
this.SetValue(CheckedProperty, value);
this.CheckedChanged.Invoke(this, value);
}
}
}
/// <summary>
/// Gets or sets a value indicating the checked text.
/// </summary>
/// <value>The checked state.</value>
/// <remarks>
/// Overwrites the default text property if set when checkbox is checked.
/// </remarks>
public string CheckedText
{
get
{
return this.GetValue<string>(CheckedTextProperty);
}
set
{
this.SetValue(CheckedTextProperty, value);
}
}
/// <summary>
/// Gets or sets a value indicating whether the control is checked.
/// </summary>
/// <value>The checked state.</value>
/// <remarks>
/// Overwrites the default text property if set when checkbox is checked.
/// </remarks>
public string UncheckedText
{
get
{
return this.GetValue<string>(UncheckedTextProperty);
}
set
{
this.SetValue(UncheckedTextProperty, value);
}
}
/// <summary>
/// Gets or sets the text.
/// </summary>
public string DefaultText
{
get
{
return this.GetValue<string>(DefaultTextProperty);
}
set
{
this.SetValue(DefaultTextProperty, value);
NotifyPropertyChanged("DefaultTextProperty");
NotifyPropertyChanged("DefaultText");
}
}
/// <summary>
/// Gets or sets the color of the text.
/// </summary>
/// <value>The color of the text.</value>
public Color TextColor
{
get
{
return this.GetValue<Color>(TextColorProperty);
}
set
{
this.SetValue(TextColorProperty, value);
}
}
/// <summary>
/// Gets or sets the size of the font.
/// </summary>
/// <value>The size of the font.</value>
public double FontSize
{
get
{
return (double)GetValue(FontSizeProperty);
}
set
{
SetValue(FontSizeProperty, value);
}
}
/// <summary>
/// Gets or sets the name of the font.
/// </summary>
/// <value>The name of the font.</value>
public string FontName
{
get
{
return (string)GetValue(FontNameProperty);
}
set
{
SetValue(FontNameProperty, value);
}
}
/// <summary>
/// Gets the text.
/// </summary>
/// <value>The text.</value>
public string Text
{
get
{
return this.Checked
? (string.IsNullOrEmpty(this.CheckedText) ? this.DefaultText : this.CheckedText)
: (string.IsNullOrEmpty(this.UncheckedText) ? this.DefaultText : this.UncheckedText);
}
}
/// <summary>
/// Called when [checked property changed].
/// </summary>
/// <param name="bindable">The bindable.</param>
/// <param name="oldvalue">if set to <c>true</c> [oldvalue].</param>
/// <param name="newvalue">if set to <c>true</c> [newvalue].</param>
private static void OnCheckedPropertyChanged(BindableObject bindable, bool oldvalue, bool newvalue)
{
var checkBox = (CheckBox)bindable;
checkBox.Checked = newvalue;
}
private void NotifyPropertyChanged(string propertyName)
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
}
}
I have default text bindable property, that I want to set the value from coming web service via Binding.
The code I tried on Xaml is as below;
<uikit:CheckBox x:Name="CheckBox" WidthRequest="250" HeightRequest="100" FontSize="13" DefaultText="{Binding FirstText,Mode=TwoWay}" CheckedChanged="CheckBox_Clicked" TextColor="#263238" />
I am not able to do so... I tried setting Binding Context in both Xaml and Codebehind.
What am I doing wrong?
Could you please help me?
I have also added PropertyChanged Event Handler, my updated code is as above. It still does not update.
BR,
add this at end
public void RaiseCheckedChanged (bool val)
{
if (CheckedChanged != null)
CheckedChanged (this, new EventArgs<bool> (val));
}
and add this class in same file
public class EventArgs<T> : EventArgs
{
/// <summary>
/// Initializes a new instance of the <see cref="EventArgs"/> class.
/// </summary>
/// <param name="value">Value of the argument</param>
public EventArgs(T value)
{
this.Value = value;
}
/// <summary>
/// Gets the value of the event argument
/// </summary>
public T Value { get; private set; }
}
public static class BindableObjectExtensions
{
/// <summary>
/// Gets the value.
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="bindableObject">The bindable object.</param>
/// <param name="property">The property.</param>
/// <returns>T.</returns>
public static T GetValue<T>(this BindableObject bindableObject, BindableProperty property)
{
return (T)bindableObject.GetValue(property);
}
}
public static class EventExtensions
{
/// <summary>
/// Raise the specified event.
/// </summary>
/// <param name="handler">Event handler.</param>
/// <param name="sender">Sender object.</param>
/// <param name="value">Argument value.</param>
/// <typeparam name="T">The value type.</typeparam>
public static void Invoke<T>(this EventHandler<EventArgs<T>> handler, object sender, T value)
{
var handle = handler;
if (handle != null)
{
handle(sender, new EventArgs<T>(value));
}
}
/// <summary>
/// Tries the invoke.
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="handler">The handler.</param>
/// <param name="sender">The sender.</param>
/// <param name="args">The arguments.</param>
/// <returns><c>true</c> if XXXX, <c>false</c> otherwise.</returns>
public static bool TryInvoke<T>(this EventHandler<T> handler, object sender, T args) where T : EventArgs
{
var handle = handler;
if (handle == null) return false;
handle(sender, args);
return true;
}
}
I am currently using the following attached behaviour on a PasswordBox in a WPF application. I am able to set the password using the UI, I encrypt this value and store in a database.
When loading the view model and setting the SecureString property which is bound to the PasswordBox the password field appears empty. (even though the password is loaded successfully).
What would I need to change in order for the PasswordBox to appear as filled when setting the value from the ViewModel?
I have added the code used in the XAML and in the ViewModel. The LoadPassword() method returns a SecureString.
Behaviour
/// <summary>
/// Provides additional properties to use against PasswordBox controls.
/// </summary>
/// <remarks>
/// Sometimes controls have properties that don't support binding. PasswordBox is one of these, where Microsoft's implementation does not support binding against the entered
/// password (for 'security purposes').
///
/// This class provides an 'attached property' which allows us to bridge the gap between the view and view model.
/// </remarks>
public static class Password
{
#region Dependency properties
/// <summary>
/// SecurePassword property.
/// </summary>
public static readonly DependencyProperty SecurePasswordProperty = DependencyProperty.RegisterAttached("SecurePassword", typeof(SecureString), typeof(Password), new FrameworkPropertyMetadata(OnSecurePasswordChanged));
/// <summary>
/// HasSecurePassword property.
/// </summary>
private static readonly DependencyProperty HasSecurePasswordProperty = DependencyProperty.RegisterAttached("HasSecurePassword", typeof(bool), typeof(Password));
#endregion
#region Methods
/// <summary>
/// Sets the value of the SecurePassword property.
/// </summary>
/// <param name="dependencyObject">The object to set the property for.</param>
/// <param name="value">The value to set.</param>
public static void SetSecurePassword(DependencyObject dependencyObject, SecureString value)
{
if (dependencyObject == null)
throw new ArgumentNullException(nameof(dependencyObject));
dependencyObject.SetValue(Password.SecurePasswordProperty, value);
}
/// <summary>
/// Gets the value of the SecurePassword property.
/// </summary>
/// <param name="dependencyObject">The object to get the property for.</param>
/// <returns>The current value.</returns>
public static SecureString GetSecurePassword(DependencyObject dependencyObject)
{
if (dependencyObject == null)
throw new ArgumentNullException(nameof(dependencyObject));
return (SecureString)dependencyObject.GetValue(Password.SecurePasswordProperty);
}
#endregion
/// <summary>
/// Handles the SecurePassword value changing.
/// </summary>
private static void OnSecurePasswordChanged(DependencyObject dependencyObject, DependencyPropertyChangedEventArgs e)
{
PasswordBox password = dependencyObject as PasswordBox;
bool? isRegistered = (bool?)password?.GetValue(Password.HasSecurePasswordProperty);
if (isRegistered == false)
{
// register with the PasswordBox's PasswordChanged event so that we can keep updated with the latest value entered by the user
password.PasswordChanged += (s, ee) => SetSecurePassword(password, password.SecurePassword);
password.SetValue(Password.HasSecurePasswordProperty, true);
}
}
}
XAML
<PasswordBox Grid.Column="1" Grid.Row="2" behaviours:Password.SecurePassword="{Binding Path=Password, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" Margin="2"/>
ViewModel
public SecureString Password
{
get { return this._password; }
set { base.SetProperty(ref _password, value); }
}
public SettingsViewModel()
{
this.Password = LoadPassword();
}
You simply can't set the SecurePassword. It is a readOnly Property. If you want to fill the PasswordBox, you have to set the Unsecure String Password Property.
I have a problem with Windows.UI.Xaml.Controls.ContentDialog. I want to disable it primary button when System.Windows.Input.ICommand.CanExecute return false. But it seem ContentDialog does not subscribe to ICommand.CanExecuteChanged event. I don't known why. This is my code:
NewTracingDialog.xaml
<ContentDialog
x:Class="RouterTracer.NewTracingDialog"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:RouterTracer"
xmlns:model="using:RouterTracer.ViewModels"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
Title="NEW TRACING"
PrimaryButtonText="trace"
SecondaryButtonText="cancel"
PrimaryButtonCommand="{Binding}"
d:DataContext="{d:DesignInstance Type=model:NewTracingViewModel}">
<StackPanel VerticalAlignment="Stretch" HorizontalAlignment="Stretch">
<TextBox Name="destinationHost" Header="Destination Host" Text="{Binding Host, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"/>
<TextBox Name="port" Header="UDP Port" InputScope="Number" Text="{Binding Port, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"/>
<TextBox Name="hopLimit" Header="Hop Limit" InputScope="Number" Text="{Binding HopLimit, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"/>
</StackPanel>
</ContentDialog>
NewTracingViewModel.cs
//-----------------------------------------------------------------------
// <copyright file="NewTracingViewModel.cs">
// Copyright (c) Putta Khunchalee.
// </copyright>
// <author>Putta Khunchalee</author>
//-----------------------------------------------------------------------
namespace RouterTracer.ViewModels
{
using System;
/// <summary>
/// View model for new tracing dialog.
/// </summary>
public sealed class NewTracingViewModel : ExecutableViewModel
{
private byte hopLimit;
private string host;
private ushort port;
/// <summary>
/// Initialize a new instance of the <see cref="NewTracingViewModel"/> class.
/// </summary>
public NewTracingViewModel()
{
}
/// <summary>
/// Gets or sets TTL or Hop Limit.
/// </summary>
/// <value>
/// TTL or Hop Limit.
/// </value>
public byte HopLimit
{
get { return this.hopLimit; }
set { this.SetProperty(ref this.hopLimit, value, "HopLimit"); }
}
/// <summary>
/// Gets or sets destination host.
/// </summary>
/// <value>
/// Hestination host.
/// </value>
public string Host
{
get { return this.host; }
set { this.SetProperty(ref this.host, value, "Host"); }
}
/// <summary>
/// Gets or sets destination port.
/// </summary>
/// <value>
/// Destination port.
/// </value>
public ushort Port
{
get { return this.port; }
set { this.SetProperty(ref this.port, value, "Port"); }
}
/// <summary>
/// Defines the method to be called when the command is invoked.
/// </summary>
/// <param name="parameter">
/// Data used by the command. If the command does not require data to be passed,
/// this object can be set to <c>null</c>.
/// </param>
public override void Execute(object parameter)
{
// This method get execute normally.
}
/// <summary>
/// Validate all properties to determine executable status.
/// </summary>
/// <returns>
/// <c>true</c> if instance can be execute; otherwise <c>false</c>.
/// </returns>
protected override bool ValidateProperties()
{
if (this.hopLimit == 0)
{
return false;
}
if (string.IsNullOrWhiteSpace(this.host))
{
return false;
}
if (this.port == 0)
{
return false;
}
return true;
}
}
}
ExecutableViewModel.cs
//-----------------------------------------------------------------------
// <copyright file="ExecutableViewModel.cs">
// Copyright (c) Putta Khunchalee.
// </copyright>
// <author>Putta Khunchalee</author>
//-----------------------------------------------------------------------
namespace RouterTracer.ViewModels
{
using System;
using System.Windows.Input;
/// <summary>
/// Base class for all View Model that executable via <see cref="ICommand"/>.
/// </summary>
public abstract class ExecutableViewModel : ViewModel, ICommand
{
private bool canExecute;
/// <summary>
/// Initialize a new instance of the <see cref="ExecutableViewModel"/> class.
/// </summary>
protected ExecutableViewModel()
{
}
/// <summary>
/// Occurs when changes occur that affect whether or not the command should execute.
/// </summary>
public event EventHandler CanExecuteChanged;
/// <summary>
/// Defines the method that determines whether the command can execute in its current state.
/// </summary>
/// <param name="parameter">
/// Data used by the command. If the command does not require data to be passed,
/// this object can be set to <c>null</c>.
/// </param>
/// <returns>
/// <c>true</c> if this command can be executed; otherwise, <c>false</c>.
/// </returns>
public bool CanExecute(object parameter)
{
return this.canExecute;
}
/// <summary>
/// Defines the method to be called when the command is invoked.
/// </summary>
/// <param name="parameter">
/// Data used by the command. If the command does not require data to be passed,
/// this object can be set to <c>null</c>.
/// </param>
public abstract void Execute(object parameter);
/// <summary>
/// Invoked when status of <see cref="CanExecute(object)"/> has changed.
/// </summary>
protected virtual void OnCanExecuteChanged()
{
var handlers = this.CanExecuteChanged;
if (handlers != null)
{
handlers(this, EventArgs.Empty);
}
}
/// <summary>
/// Invoked when value of model's property has been changed.
/// </summary>
/// <param name="name">
/// Name of the property that value has changed.
/// </param>
protected override void OnPropertyChanged(string name)
{
base.OnPropertyChanged(name);
this.UpdateCanExecuteFlag(ValidateProperties());
}
/// <summary>
/// Validate all properties to determine executable status.
/// </summary>
/// <returns>
/// <c>true</c> if instance can be execute; otherwise <c>false</c>.
/// </returns>
protected abstract bool ValidateProperties();
/// <summary>
/// Update status of <see cref="CanExecute(object)"/>.
/// </summary>
/// <param name="canExecute">
/// <c>true</c> if instance can be execute; otherwise <c>false</c>.
/// </param>
private void UpdateCanExecuteFlag(bool canExecute)
{
if (this.canExecute == canExecute)
{
return;
}
this.canExecute = canExecute;
this.OnCanExecuteChanged();
}
}
}
ViewModel.cs
//-----------------------------------------------------------------------
// <copyright file="ViewModel.cs">
// Copyright (c) Putta Khunchalee.
// </copyright>
// <author>Putta Khunchalee</author>
//-----------------------------------------------------------------------
namespace RouterTracer.ViewModels
{
using System.ComponentModel;
/// <summary>
/// Base class for all View Model.
/// </summary>
public abstract class ViewModel : INotifyPropertyChanged
{
/// <summary>
/// Initialize a new instance of the <see cref="ViewModel"/> class.
/// </summary>
protected ViewModel()
{
}
/// <summary>
/// Raise when value of model's property has been changed.
/// </summary>
public event PropertyChangedEventHandler PropertyChanged;
/// <summary>
/// Invoked when value of model's property has been changed.
/// </summary>
/// <param name="name">
/// Name of the property that value has changed.
/// </param>
protected virtual void OnPropertyChanged(string name)
{
var handlers = this.PropertyChanged;
if (handlers != null)
{
handlers(this, new PropertyChangedEventArgs(name));
}
}
/// <summary>
/// Change the value of the field that is property backed.
/// </summary>
/// <typeparam name="T">
/// Type of the field.
/// </typeparam>
/// <param name="field">
/// Field to change value.
/// </param>
/// <param name="value">
/// The new value.
/// </param>
/// <param name="name">
/// Name of backed property.
/// </param>
/// <returns>
/// <c>true</c> when value has been changed; otherwise <c>false</c>.
/// </returns>
protected bool SetProperty<T>(ref T field, T value, string name)
{
T previousValue;
// Check to see if value change is neccessary.
if (object.Equals(field, value))
{
return false;
}
// Change value.
previousValue = field;
field = value;
this.OnPropertyChanged(name);
return true;
}
}
}
Sorry for long codes. Thank you.
I have give up and use a workaround instead. Maybe it is not yet implemented in ContentDialog. This is my workaround.
NewTracingDialog.xaml.cs
//-----------------------------------------------------------------------
// <copyright file="NewTracingDialog.xaml.cs">
// Copyright (c) Putta Khunchalee.
// </copyright>
// <author>Putta Khunchalee</author>
//-----------------------------------------------------------------------
namespace RouterTracer
{
using System;
using System.Windows.Input;
using Windows.UI.Xaml;
using Windows.UI.Xaml.Controls;
/// <summary>
/// Dialog for gather tracing information from user.
/// </summary>
public sealed partial class NewTracingDialog : ContentDialog
{
/// <summary>
/// Used to remove <see cref="OnDataContextCanExecuteChanged(object, EventArgs)"/> before
/// changing to the new data context.
/// </summary>
private ICommand currentDataContext;
/// <summary>
/// Initialize a new instance of the <see cref="NewTracingDialog"/> class.
/// </summary>
public NewTracingDialog()
{
this.InitializeComponent();
this.DataContextChanged += this.OnDataContextChanged;
}
/// <summary>
/// Invoke when executable flag of data context has changed.
/// </summary>
/// <param name="sender">
/// Data context that executable flag has changed.
/// </param>
/// <param name="e">
/// The empty <see cref="EventArgs"/>.
/// </param>
private void OnDataContextCanExecuteChanged(object sender, EventArgs e)
{
this.IsPrimaryButtonEnabled = ((ICommand)sender).CanExecute(null);
}
/// <summary>
/// Invoke when data context has been changed.
/// </summary>
/// <param name="sender">
/// The instance of <see cref="NewTracingDialog"/> that data context has changed.
/// </param>
/// <param name="args">
/// Event informations.
/// </param>
private void OnDataContextChanged(FrameworkElement sender, DataContextChangedEventArgs args)
{
// Get a new data context.
var command = (ICommand)args.NewValue;
if (command == null)
{
return;
}
// Disable primary button if data context is not executable.
this.IsPrimaryButtonEnabled = command.CanExecute(null);
// Subscribe to data context executable changed event.
if (this.currentDataContext != null)
{
this.currentDataContext.CanExecuteChanged -= this.OnDataContextCanExecuteChanged;
}
command.CanExecuteChanged += this.OnDataContextCanExecuteChanged;
this.currentDataContext = command;
}
}
}
Basic Requirement - Displaying In App tiles in Universal Apps.
I have gone through samples of Hub Tiles from the following link Hub Tiles which applies to Windows Phone 7 and 8, 8.1 (Silverlight), but there is no mentioning of windows Phone 8.1 (Universal Applications). Even if i include the assembly separately it throws an error that Microsoft.Phone cannot be resolved.
As a work around I have even downloaded the source of hub Tiles from Windows phone Toolkit Source and resolved the assemblies, modified the templates and edited it accordingly. But I might be missing on some points, Although It is showing as a control in the tool box but it is not even visible when I add it to XAML. I am adding the edited code for all the three files available from the source of the toolkit.
HubTiles.cs
// (c) Copyright Microsoft Corporation.
// This source is subject to the Microsoft Public License (Ms-PL).
// Please see http://go.microsoft.com/fwlink/?LinkID=131993 for details.
// All other rights reserved.
using System.Windows;
using Windows.UI.Xaml;
using Windows.UI.Xaml.Controls;
using Windows.UI.Xaml.Data;
using Windows.UI.Xaml.Media;
namespace Microsoft.Phone.Controls
{
/// <summary>
/// Represents an animated tile that supports an image and a title.
/// Furthermore, it can also be associated with a message or a notification.
/// </summary>
/// <QualityBand>Preview</QualityBand>
[TemplateVisualState(Name = Expanded, GroupName = ImageStates)]
[TemplateVisualState(Name = Semiexpanded, GroupName = ImageStates)]
[TemplateVisualState(Name = Collapsed, GroupName = ImageStates)]
[TemplateVisualState(Name = Flipped, GroupName = ImageStates)]
[TemplatePart(Name = NotificationBlock, Type = typeof(TextBlock))]
[TemplatePart(Name = MessageBlock, Type = typeof(TextBlock))]
[TemplatePart(Name = BackTitleBlock, Type = typeof(TextBlock))]
[TemplatePart(Name = TitlePanel, Type = typeof(Panel))]
public class HubTile : Control
{
/// <summary>
/// Common visual states.
/// </summary>
private const string ImageStates = "ImageState";
/// <summary>
/// Expanded visual state.
/// </summary>
private const string Expanded = "Expanded";
/// <summary>
/// Semiexpanded visual state.
/// </summary>
private const string Semiexpanded = "Semiexpanded";
/// <summary>
/// Collapsed visual state.
/// </summary>
private const string Collapsed = "Collapsed";
/// <summary>
/// Flipped visual state.
/// </summary>
private const string Flipped = "Flipped";
/// <summary>
/// Nofitication Block template part name.
/// </summary>
private const string NotificationBlock = "NotificationBlock";
/// <summary>
/// Message Block template part name.
/// </summary>
private const string MessageBlock = "MessageBlock";
/// <summary>
/// Back Title Block template part name.
/// </summary>
private const string BackTitleBlock = "BackTitleBlock";
/// <summary>
/// Title Panel template part name.
/// </summary>
private const string TitlePanel = "TitlePanel";
/// <summary>
/// Notification Block template part.
/// </summary>
private TextBlock _notificationBlock;
/// <summary>
/// Message Block template part.
/// </summary>
private TextBlock _messageBlock;
/// <summary>
/// Title Panel template part.
/// </summary>
private Panel _titlePanel;
/// <summary>
/// Back Title Block template part.
/// </summary>
private TextBlock _backTitleBlock;
/// <summary>
/// Represents the number of steps inside the pipeline of stalled images
/// </summary>
internal int _stallingCounter;
/// <summary>
/// Flag that determines if the hub tile has a primary text string associated to it.
/// If it does not, the hub tile will not drop.
/// </summary>
internal bool _canDrop;
/// <summary>
/// Flag that determines if the hub tile has a secondary text string associated to it.
/// If it does not, the hub tile will not flip.
/// </summary>
internal bool _canFlip;
#region Source DependencyProperty
/// <summary>
/// Gets or sets the image source.
/// </summary>
public ImageSource Source
{
get { return (ImageSource)GetValue(SourceProperty); }
set { SetValue(SourceProperty, value); }
}
/// <summary>
/// Identifies the Source dependency property.
/// </summary>
public static readonly DependencyProperty SourceProperty =
DependencyProperty.Register("Source", typeof(ImageSource), typeof(HubTile), new PropertyMetadata(null));
#endregion
#region Title DependencyProperty
/// <summary>
/// Gets or sets the title.
/// </summary>
public string Title
{
get { return (string)GetValue(TitleProperty); }
set { SetValue(TitleProperty, value); }
}
/// <summary>
/// Identifies the Title dependency property.
/// </summary>
public static readonly DependencyProperty TitleProperty =
DependencyProperty.Register("Title", typeof(string), typeof(HubTile), new PropertyMetadata(string.Empty, new PropertyChangedCallback(OnTitleChanged)));
/// <summary>
/// Prevents the hub tile from transitioning into a Semiexpanded or Collapsed visual state if the title is not set.
/// </summary>
/// <param name="obj">The dependency object.</param>
/// <param name="e">The event information.</param>
private static void OnTitleChanged(DependencyObject obj, DependencyPropertyChangedEventArgs e)
{
HubTile tile = (HubTile)obj;
if (string.IsNullOrEmpty((string)e.NewValue))
{
tile._canDrop = false;
tile.State = ImageState.Expanded;
}
else
{
tile._canDrop = true;
}
}
#endregion
#region Notification DependencyProperty
/// <summary>
/// Gets or sets the notification alert.
/// </summary>
public string Notification
{
get { return (string)GetValue(NotificationProperty); }
set { SetValue(NotificationProperty, value); }
}
/// <summary>
/// Identifies the Notification dependency property.
/// </summary>
public static readonly DependencyProperty NotificationProperty =
DependencyProperty.Register("Notification", typeof(string), typeof(HubTile), new PropertyMetadata(string.Empty, new PropertyChangedCallback(OnBackContentChanged)));
/// <summary>
/// Prevents the hub tile from transitioning into a Flipped visual state if neither the notification alert nor the message are set.
/// </summary>
/// <param name="obj">The dependency object.</param>
/// <param name="e">The event information.</param>
private static void OnBackContentChanged(DependencyObject obj, DependencyPropertyChangedEventArgs e)
{
HubTile tile = (HubTile)obj;
// If there is a new notification or a message, the hub tile can flip.
if ((!(string.IsNullOrEmpty(tile.Notification)) && tile.DisplayNotification)
|| (!(string.IsNullOrEmpty(tile.Message)) && !tile.DisplayNotification))
{
tile._canFlip = true;
}
else
{
tile._canFlip = false;
tile.State = ImageState.Expanded;
}
}
#endregion
#region Message DependencyProperty
/// <summary>
/// Gets or sets the message.
/// </summary>
public string Message
{
get { return (string)GetValue(MessageProperty); }
set { SetValue(MessageProperty, value); }
}
/// <summary>
/// Identifies the Message dependency property.
/// </summary>
public static readonly DependencyProperty MessageProperty =
DependencyProperty.Register("Message", typeof(string), typeof(HubTile), new PropertyMetadata(string.Empty, new PropertyChangedCallback(OnBackContentChanged)));
#endregion
#region DisplayNotification DependencyProperty
/// <summary>
/// Gets or sets the flag for new notifications.
/// </summary>
public bool DisplayNotification
{
get { return (bool)GetValue(DisplayNotificationProperty); }
set { SetValue(DisplayNotificationProperty, value); }
}
/// <summary>
/// Identifies the DisplayNotification dependency property.
/// </summary>
public static readonly DependencyProperty DisplayNotificationProperty =
DependencyProperty.Register("DisplayNotification", typeof(bool), typeof(HubTile), new PropertyMetadata(false, new PropertyChangedCallback(OnBackContentChanged)));
#endregion
#region IsFrozen DependencyProperty
/// <summary>
/// Gets or sets the flag for images that do not animate.
/// </summary>
public bool IsFrozen
{
get { return (bool)GetValue(IsFrozenProperty); }
set { SetValue(IsFrozenProperty, value); }
}
/// <summary>
/// Identifies the IsFrozen dependency property.
/// </summary>
public static readonly DependencyProperty IsFrozenProperty =
DependencyProperty.Register("IsFrozen", typeof(bool), typeof(HubTile), new PropertyMetadata(false, new PropertyChangedCallback(OnIsFrozenChanged)));
/// <summary>
/// Removes the frozen image from the enabled image pool or the stalled image pipeline.
/// Adds the non-frozen image to the enabled image pool.
/// </summary>
/// <param name="obj">The dependency object.</param>
/// <param name="e">The event information.</param>
private static void OnIsFrozenChanged(DependencyObject obj, DependencyPropertyChangedEventArgs e)
{
HubTile tile = (HubTile)obj;
if ((bool)e.NewValue)
{
HubTileService.FreezeHubTile(tile);
}
else
{
HubTileService.UnfreezeHubTile(tile);
}
}
#endregion
#region GroupTag DependencyProperty
/// <summary>
/// Gets or sets the group tag.
/// </summary>
public string GroupTag
{
get { return (string)GetValue(GroupTagProperty); }
set { SetValue(GroupTagProperty, value); }
}
/// <summary>
/// Identifies the GroupTag dependency property.
/// </summary>
public static readonly DependencyProperty GroupTagProperty =
DependencyProperty.Register("GroupTag", typeof(string), typeof(HubTile), new PropertyMetadata(string.Empty));
#endregion
#region State DependencyProperty
/// <summary>
/// Gets or sets the visual state.
/// </summary>
internal ImageState State
{
get { return (ImageState)GetValue(StateProperty); }
set { SetValue(StateProperty, value); }
}
/// <summary>
/// Identifies the State dependency property.
/// </summary>
private static readonly DependencyProperty StateProperty =
DependencyProperty.Register("State", typeof(ImageState), typeof(HubTile), new PropertyMetadata(ImageState.Expanded, OnImageStateChanged));
/// <summary>
/// Triggers the transition between visual states.
/// </summary>
/// <param name="obj">The dependency object.</param>
/// <param name="e">The event information.</param>
private static void OnImageStateChanged(DependencyObject obj, DependencyPropertyChangedEventArgs e)
{
((HubTile)obj).UpdateVisualState();
}
#endregion
#region Size DependencyProperty
/// <summary>
/// Gets or sets the visual state.
/// </summary>
public TileSize Size
{
get { return (TileSize)GetValue(SizeProperty); }
set { SetValue(SizeProperty, value); }
}
/// <summary>
/// Identifies the State dependency property.
/// </summary>
public static readonly DependencyProperty SizeProperty =
DependencyProperty.Register("Size", typeof(TileSize), typeof(HubTile), new PropertyMetadata(TileSize.Default, OnSizeChanged));
/// <summary>
/// Triggers the transition between visual states.
/// </summary>
/// <param name="obj">The dependency object.</param>
/// <param name="e">The event information.</param>
private static void OnSizeChanged(DependencyObject obj, DependencyPropertyChangedEventArgs e)
{
HubTile hubTile = (HubTile)obj;
// And now we'll update the width and height to match the new size.
switch (hubTile.Size)
{
case TileSize.Default:
hubTile.Width = 173;
hubTile.Height = 173;
break;
case TileSize.Small:
hubTile.Width = 99;
hubTile.Height = 99;
break;
case TileSize.Medium:
hubTile.Width = 210;
hubTile.Height = 210;
break;
case TileSize.Large:
hubTile.Width = 432;
hubTile.Height = 210;
break;
}
hubTile.SizeChanged += OnHubTileSizeChanged;
HubTileService.FinalizeReference(hubTile);
}
static void OnHubTileSizeChanged(object sender, SizeChangedEventArgs e)
{
HubTile hubTile = (HubTile)sender;
hubTile.SizeChanged -= OnHubTileSizeChanged;
// In order to avoid getting into a bad state, we'll shift the HubTile
// back to the Expanded state. If we were already in the Expanded state,
// then we'll manually shift the title panel to the right location,
// since the visual state manager won't do it for us in that case.
if (hubTile.State != ImageState.Expanded)
{
hubTile.State = ImageState.Expanded;
VisualStateManager.GoToState(hubTile, Expanded, false);
}
else if (hubTile._titlePanel != null)
{
CompositeTransform titlePanelTransform = hubTile._titlePanel.RenderTransform as CompositeTransform;
if (titlePanelTransform != null)
{
titlePanelTransform.TranslateY = -hubTile.Height;
}
}
HubTileService.InitializeReference(hubTile);
}
#endregion
/// <summary>
/// Updates the visual state.
/// </summary>
private void UpdateVisualState()
{
string state;
// If we're in the Small size, then we should just display the image
// instead of having animations.
if (Size != TileSize.Small)
{
switch (State)
{
case ImageState.Expanded:
state = Expanded;
break;
case ImageState.Semiexpanded:
state = Semiexpanded;
break;
case ImageState.Collapsed:
state = Collapsed;
break;
case ImageState.Flipped:
state = Flipped;
break;
default:
state = Expanded;
break;
}
}
else
{
state = Expanded;
}
VisualStateManager.GoToState(this, state, true);
}
/// <summary>
/// Gets the template parts and sets binding.
/// </summary>
protected override void OnApplyTemplate()
{
base.OnApplyTemplate();
_notificationBlock = base.GetTemplateChild(NotificationBlock) as TextBlock;
_messageBlock = base.GetTemplateChild(MessageBlock) as TextBlock;
_backTitleBlock = base.GetTemplateChild(BackTitleBlock) as TextBlock;
_titlePanel = base.GetTemplateChild(TitlePanel) as Panel;
//Do binding in code to avoid exposing unnecessary value converters.
if (_notificationBlock != null)
{
Binding bindVisible = new Binding();
bindVisible.Source = this;
bindVisible.Path = new PropertyPath("DisplayNotification");
bindVisible.Converter = new VisibilityConverter();
bindVisible.ConverterParameter = false;
_notificationBlock.SetBinding(TextBlock.VisibilityProperty, bindVisible);
}
if(_messageBlock != null)
{
Binding bindCollapsed = new Binding();
bindCollapsed.Source = this;
bindCollapsed.Path = new PropertyPath("DisplayNotification");
bindCollapsed.Converter = new VisibilityConverter();
bindCollapsed.ConverterParameter = true;
_messageBlock.SetBinding(TextBlock.VisibilityProperty, bindCollapsed);
}
if(_backTitleBlock != null)
{
Binding bindTitle = new Binding();
bindTitle.Source = this;
bindTitle.Path = new PropertyPath("Title");
bindTitle.Converter = new MultipleToSingleLineStringConverter();
_backTitleBlock.SetBinding(TextBlock.TextProperty, bindTitle);
}
UpdateVisualState();
}
/// <summary>
/// Initializes a new instance of the HubTile class.
/// </summary>
public HubTile()
{
DefaultStyleKey = typeof(HubTile);
Loaded += HubTile_Loaded;
Unloaded += HubTile_Unloaded;
}
/// <summary>
/// This event handler gets called as soon as a hub tile is added to the visual tree.
/// A reference of this hub tile is passed on to the service singleton.
/// </summary>
/// <param name="sender">The hub tile.</param>
/// <param name="e">The event information.</param>
void HubTile_Loaded(object sender, RoutedEventArgs e)
{
HubTileService.InitializeReference(this);
}
/// <summary>
/// This event handler gets called as soon as a hub tile is removed from the visual tree.
/// Any existing reference of this hub tile is eliminated from the service singleton.
/// </summary>
/// <param name="sender">The hub tile.</param>
/// <param name="e">The event information.</param>
void HubTile_Unloaded(object sender, RoutedEventArgs e)
{
HubTileService.FinalizeReference(this);
}
}
/// <summary>
/// Represents the visual states of a Hub tile.
/// </summary>
internal enum ImageState
{
/// <summary>
/// Expanded visual state value.
/// </summary>
Expanded = 0,
/// <summary>
/// Semiexpanded visual state value.
/// </summary>
Semiexpanded = 1,
/// <summary>
/// Collapsed visual state value.
/// </summary>
Collapsed = 2,
/// <summary>
/// Flipped visual state value.
/// </summary>
Flipped = 3,
};
/// <summary>
/// Represents the size of a Hub tile.
/// </summary>
public enum TileSize
{
/// <summary>
/// Default size (173 px x 173 px).
/// </summary>
Default,
/// <summary>
/// Small size (99 px x 99 px).
/// </summary>
Small,
/// <summary>
/// Medium size (210 px x 210 px).
/// </summary>
Medium,
/// <summary>
/// Large size (432 px x 210 px).
/// </summary>
Large,
};
}
Note: We can edit the same for HubTileConverters and HubTileService but still it doesnt work.
If any one has a solution or has edited the same for Universal Application Or if there is any Toolkit from Microsoft for the same then please let me know.
TIA.
I have ported the toolkit HubTile stuff. Done with a sample for your refrence please find in the following link.
HubTile sample for universal app
Hope this will help you.
Maybe you should check the Generic.xaml file in toolkit source code, it is placed in Themes folder. All toolkit control default styles are stored in this file. It seems your problem is lack of this style file.
Because HubTile is a custom control, it will read the \Themes\Generic.xaml in solution by using DefaultStyleKey = typeof(HubTile) in its constructor. You should port this file to your solution.
Is there a way to set an element in XAML to be hidden? When users click a New Game button I want a set of buttons (probably in a stack panel) to animate into view letting the user choose the difficulty level. I tried setting Visibility to Collapsed, but when I use one of the built-in Win8 animations such as EntranceThemeTransition or PopIn the collapsed element doesn't show up. Changing the opacity to 0 and then trying to animate using one of these has the same effect.
The Visibility property works independently from Opacity. You need to set Visibility back to Visible before running a custom Opacity animation or the built in FadeInThemeAnimation.
You can use the WinRT XAML Toolkit extensions to run a simple animation like this:
myElement.Visibility = Visibility.Visible;
myElement.FadeInCustom();
The extension methods class from the XAML Toolkit:
using System;
using System.Threading.Tasks;
using WinRTXamlToolkit.AwaitableUI;
using Windows.UI.Xaml;
using Windows.UI.Xaml.Media.Animation;
namespace WinRTXamlToolkit.Controls.Extensions
{
/// <summary>
/// Extension methods and attached properties for UIElement class.
/// </summary>
public static class UIElementAnimationExtensions
{
#region AttachedFadeStoryboard
/// <summary>
/// AttachedFadeStoryboard Attached Dependency Property
/// </summary>
public static readonly DependencyProperty AttachedFadeStoryboardProperty =
DependencyProperty.RegisterAttached(
"AttachedFadeStoryboard",
typeof(Storyboard),
typeof(UIElementAnimationExtensions),
new PropertyMetadata(null, OnAttachedFadeStoryboardChanged));
/// <summary>
/// Gets the AttachedFadeStoryboard property. This dependency property
/// indicates the currently running custom fade in/out storyboard.
/// </summary>
private static Storyboard GetAttachedFadeStoryboard(DependencyObject d)
{
return (Storyboard)d.GetValue(AttachedFadeStoryboardProperty);
}
/// <summary>
/// Sets the AttachedFadeStoryboard property. This dependency property
/// indicates the currently running custom fade in/out storyboard.
/// </summary>
private static void SetAttachedFadeStoryboard(DependencyObject d, Storyboard value)
{
d.SetValue(AttachedFadeStoryboardProperty, value);
}
/// <summary>
/// Handles changes to the AttachedFadeStoryboard property.
/// </summary>
/// <param name="d">
/// The <see cref="DependencyObject"/> on which
/// the property has changed value.
/// </param>
/// <param name="e">
/// Event data that is issued by any event that
/// tracks changes to the effective value of this property.
/// </param>
private static void OnAttachedFadeStoryboardChanged(
DependencyObject d, DependencyPropertyChangedEventArgs e)
{
Storyboard oldAttachedFadeStoryboard = (Storyboard)e.OldValue;
Storyboard newAttachedFadeStoryboard = (Storyboard)d.GetValue(AttachedFadeStoryboardProperty);
}
#endregion
#region FadeIn()
/// <summary>
/// Fades the element in using the FadeInThemeAnimation.
/// </summary>
/// <remarks>
/// Opacity property of the element is not affected.<br/>
/// The duration of the visible animation itself is not affected by the duration parameter. It merely indicates how long the Storyboard will run.<br/>
/// If FadeOutThemeAnimation was not used on the element before - nothing will happen.<br/>
/// </remarks>
/// <param name="element"></param>
/// <param name="duration"></param>
/// <returns></returns>
public static async Task FadeIn(this UIElement element, TimeSpan? duration = null)
{
((FrameworkElement)element).Visibility = Visibility.Visible;
var fadeInStoryboard = new Storyboard();
var fadeInAnimation = new FadeInThemeAnimation();
if (duration != null)
{
fadeInAnimation.Duration = duration.Value;
}
Storyboard.SetTarget(fadeInAnimation, element);
fadeInStoryboard.Children.Add(fadeInAnimation);
await fadeInStoryboard.BeginAsync();
}
#endregion
#region FadeOut()
/// <summary>
/// Fades the element out using the FadeOutThemeAnimation.
/// </summary>
/// <remarks>
/// Opacity property of the element is not affected.<br/>
/// The duration of the visible animation itself is not affected by the duration parameter. It merely indicates how long the Storyboard will run.<br/>
/// If FadeOutThemeAnimation was already run before and FadeInThemeAnimation was not run after that - nothing will happen.<br/>
/// </remarks>
/// <param name="element"></param>
/// <param name="duration"></param>
/// <returns></returns>
public static async Task FadeOut(this UIElement element, TimeSpan? duration = null)
{
var fadeOutStoryboard = new Storyboard();
var fadeOutAnimation = new FadeOutThemeAnimation();
if (duration != null)
{
fadeOutAnimation.Duration = duration.Value;
}
Storyboard.SetTarget(fadeOutAnimation, element);
fadeOutStoryboard.Children.Add(fadeOutAnimation);
await fadeOutStoryboard.BeginAsync();
}
#endregion
#region FadeInCustom()
/// <summary>
/// Fades the element in using a custom DoubleAnimation of the Opacity property.
/// </summary>
/// <param name="element"></param>
/// <param name="duration"></param>
/// <param name="easingFunction"> </param>
/// <returns></returns>
public static async Task FadeInCustom(this UIElement element, TimeSpan? duration = null, EasingFunctionBase easingFunction = null, double targetOpacity = 1.0)
{
CleanUpPreviousFadeStoryboard(element);
var fadeInStoryboard = new Storyboard();
var fadeInAnimation = new DoubleAnimation();
if (duration == null)
duration = TimeSpan.FromSeconds(0.4);
fadeInAnimation.Duration = duration.Value;
fadeInAnimation.To = targetOpacity;
fadeInAnimation.EasingFunction = easingFunction;
Storyboard.SetTarget(fadeInAnimation, element);
Storyboard.SetTargetProperty(fadeInAnimation, "Opacity");
fadeInStoryboard.Children.Add(fadeInAnimation);
SetAttachedFadeStoryboard(element, fadeInStoryboard);
await fadeInStoryboard.BeginAsync();
element.Opacity = targetOpacity;
fadeInStoryboard.Stop();
}
#endregion
#region FadeOutCustom()
/// <summary>
/// Fades the element out using a custom DoubleAnimation of the Opacity property.
/// </summary>
/// <param name="element"></param>
/// <param name="duration"></param>
/// <param name="easingFunction"> </param>
/// <returns></returns>
public static async Task FadeOutCustom(this UIElement element, TimeSpan? duration = null, EasingFunctionBase easingFunction = null)
{
CleanUpPreviousFadeStoryboard(element);
var fadeOutStoryboard = new Storyboard();
var fadeOutAnimation = new DoubleAnimation();
if (duration == null)
duration = TimeSpan.FromSeconds(0.4);
fadeOutAnimation.Duration = duration.Value;
fadeOutAnimation.To = 0.0;
fadeOutAnimation.EasingFunction = easingFunction;
Storyboard.SetTarget(fadeOutAnimation, element);
Storyboard.SetTargetProperty(fadeOutAnimation, "Opacity");
fadeOutStoryboard.Children.Add(fadeOutAnimation);
SetAttachedFadeStoryboard(element, fadeOutStoryboard);
await fadeOutStoryboard.BeginAsync();
element.Opacity = 0.0;
fadeOutStoryboard.Stop();
}
#endregion
#region CleanUpPreviousFadeStoryboard()
public static void CleanUpPreviousFadeStoryboard(this UIElement element)
{
var attachedFadeStoryboard = GetAttachedFadeStoryboard(element);
if (attachedFadeStoryboard != null)
{
attachedFadeStoryboard.Stop();
}
}
#endregion
}
}