For my project I'm adding an attached property to my controls using DependencyProperty.
It works, but I would like to have my property exposed in the VisualStudio Properties Window.
I'm not creating any UserControl, because I want all my standard controls to have this property.
Also, I don't want to use the existing Tag property as in the future I will have more properties to add.
Is this possible? How it can be done?
My XAML:
<Window x:Class="Wpf_CustomPropertyTest.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:Wpf_CustomPropertyTest"
mc:Ignorable="d"
Title="MainWindow" Height="350" Width="525">
<Grid>
<Button x:Name="button1" Content="Button 1" local:Extensions.MyTestProp="Hello 1!" Click="button_Click" HorizontalAlignment="Left" Height="39" Margin="36,36,0,0" VerticalAlignment="Top" Width="171" />
<Button x:Name="button2" Content="Button 2" local:Extensions.MyTestProp="Hello 2!" Click="button_Click" HorizontalAlignment="Left" Height="39" Margin="36,90,0,0" VerticalAlignment="Top" Width="171" />
</Grid>
</Window>
My code-behind:
using System.Windows;
namespace Wpf_CustomPropertyTest
{
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
}
private void button_Click(object sender, RoutedEventArgs e)
{
MessageBox.Show(Extensions.GetMyTestProp((UIElement)sender));
}
}
public class Extensions
{
public static readonly DependencyProperty MyTestPropProperty = DependencyProperty.RegisterAttached("MyTestProp", typeof(string), typeof(Extensions), new PropertyMetadata(default(string)));
public static void SetMyTestProp(UIElement element, string value)
{
element.SetValue(MyTestPropProperty, value);
}
public static string GetMyTestProp(UIElement element)
{
return (string)element.GetValue(MyTestPropProperty);
}
}
}
Related
I'm learning UWP User Control and facing the below code:
<Page
x:Class="LearningUWP.MainPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:LearningUWP"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
<StackPanel>
<local:MyUserControl Username="aaa" Password="bbb" fillcolor="Blue" />
</StackPanel>
</Page>
I have defined a user control with three dependency properties, Username, Password, and fillcolor. The below code shows my user control xaml
<UserControl
x:Name="myctrl"
x:Class="LearningUWP.MyUserControl"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:LearningUWP"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
>
<RelativePanel>
<Rectangle Fill="{Binding fillcolor, ElementName=myctrl}" x:Name="Rec" Height="100" RelativePanel.AlignRightWithPanel="True" />
<TextBlock Text="Username_lbl" RelativePanel.AlignRightWithPanel="True" TextAlignment="Center" RelativePanel.Below="Rec" x:Name="Username_lb" Margin="0,50,0,0" RelativePanel.AlignLeftWithPanel="True" />
<TextBox x:Name="Username_input" RelativePanel.Below="Username_lb" RelativePanel.AlignRightWithPanel="True" RelativePanel.AlignLeftWithPanel="True" Margin="0,20,0,0" Text="{Binding Username, ElementName=myctrl}" ></TextBox>
<TextBlock Text="Password_lbl" x:Name="Password_lb" RelativePanel.AlignRightWithPanel="True" TextAlignment="Center" RelativePanel.Below="Username_input" RelativePanel.AlignLeftWithPanel="True" Margin="0,20,0,0" ></TextBlock>
<TextBox x:Name="Password_input" RelativePanel.Below="Password_lb" RelativePanel.AlignRightWithPanel="True" RelativePanel.AlignLeftWithPanel="True" Margin="0,20,0,0" Text="{Binding Password, ElementName=myctrl}" ></TextBox>
</RelativePanel>
</UserControl>
and the code-behind:
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Runtime.InteropServices.WindowsRuntime;
using Windows.Foundation;
using Windows.Foundation.Collections;
using Windows.UI.Xaml;
using Windows.UI.Xaml.Controls;
using Windows.UI.Xaml.Controls.Primitives;
using Windows.UI.Xaml.Data;
using Windows.UI.Xaml.Input;
using Windows.UI.Xaml.Media;
using Windows.UI.Xaml.Navigation;
namespace LearningUWP
{
public sealed partial class MyUserControl : UserControl
{
public MyUserControl()
{
this.InitializeComponent();
}
public string Username
{
get { return (string)GetValue(UsernameProperty); }
set { SetValue(UsernameProperty, value); }
}
public static readonly DependencyProperty UsernameProperty =
DependencyProperty.Register("Username", typeof(string), typeof(MyUserControl), null);
public string Password
{
get { return (string)GetValue(PasswordProperty); }
set { SetValue(PasswordProperty, value); }
}
public static readonly DependencyProperty PasswordProperty =
DependencyProperty.Register("Password", typeof(string), typeof(MyUserControl), null);
public string fillcolor
{
get { return (string)GetValue(fillcolorProperty); }
set { SetValue(fillcolorProperty, value); }
}
public static readonly DependencyProperty fillcolorProperty =
DependencyProperty.Register("fillcolor", typeof(string), typeof(MyUserControl), null);
}
}
The Username and Password are working as I can see "aaa" and "bbb" on my screen, but the color is not working. How to solve it?
UPDATE1
I modified the fillcolor property to the below code:
public Brush fillcolor
{
get { return (Brush)GetValue(fillcolorProperty); }
set { SetValue(fillcolorProperty, value); }
}
public static readonly DependencyProperty fillcolorProperty =
DependencyProperty.Register("fillcolor", typeof(Brush), typeof(MyUserControl), null);
But it's still not working.
UPDATE2
I updated the MainPage.xaml shown in the below:
<Page
x:Class="LearningUWP.MainPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:LearningUWP"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
<Page.Resources>
<SolidColorBrush x:Key="MyBlueColor" Color="#0000FF"/>
</Page.Resources>
<StackPanel>
<local:MyUserControl Username="aaa" Password="bbb" fillcolor="{StaticResource MyBlueColor}" />
</StackPanel>
</Page>
But it's still not working.
Your binding seems correct, your problem is in the Type of your 'fillcolor' property.
You are binding it as a string, whereas you should bind it as a Brush
public Brush fillcolor
{
get { return (Brush)GetValue(fillcolorProperty); }
set { SetValue(fillcolorProperty, value); }
}
public static readonly DependencyProperty fillcolorProperty =
DependencyProperty.Register("fillcolor", typeof(Brush), typeof(MyUserControl), null);
The Fill property requires a Brush to work properly as you can see in here Shape.Fill
I forgot to mention that you don't need to specify the element name in this case as you are using your code behind as a 'ViewModel', so, the code below will do the trick for you:
<Rectangle Fill="{x:Bind fillcolor}" x:Name="Rec" Height="100" RelativePanel.AlignRightWithPanel="True" />
Furthermore, you need to specify the Brush in your page's resources as a solid color brush, so you could write:
<Page
x:Class="LearningUWP.MainPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:LearningUWP"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
<Page.Resources>
<SolidColorBrush x:Key="MyBlueColor" Color="#0000FF"/> <!-- or Blue -->
</Page.Resources>
<StackPanel>
<local:MyUserControl Username="aaa" Password="bbb" fillcolor="{StaticResource MyBlueColor}" />
</StackPanel>
</Page>
And, according to difference-between-binding-and-xbind
We need to use x:Bind Binding does not support framework elements.
I had this simple inventory manager in WPF using a datagrid hooked up to a table using SQL working the other day but changed a line of the code and now it's broken. I've slept since I broke it and can't work out how to fix it again.
The problem seems to be with with dataGrid1.Items.Add(testtables) from the MainWindow class below.
I ran it in a trycatch with the exception message saying that the operation is not valid while ItemsSource is in use, and that ItemsControl.ItemsSource should be used to access and modify elements instead.
Here's the code for the main form
namespace WpfApp2
{
/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
DataClasses1DataContext dc = new DataClasses1DataContext(Properties.Settings.Default.TestingConnectionString);
public MainWindow()
{
InitializeComponent();
if (dc.DatabaseExists())
{
dataGrid1.ItemsSource = dc.TestTables;
}
}
private void newButton_Click(object sender, RoutedEventArgs e)
{
Window1 window1 = new Window1();
window1.Show();
}
public void NewLine (int ID, string nm, decimal pc)
{
TestTable testtable = new TestTable
{
ID = ID,
Name = nm,
Price = pc
};
dataGrid1.Items.Add(testtable);
}
private void saveButton_Click_1(object sender, RoutedEventArgs e)
{
dc.SubmitChanges();
}
}
}
XAML code for MainWindow
<Window x:Class="WpfApp2.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:WpfApp2"
mc:Ignorable="d"
Title="MainWindow" Height="450" Width="800">
<Grid>
<Button x:Name="newBtn" Content="New" HorizontalAlignment="Left" Margin="217,62,0,0" VerticalAlignment="Top" Width="75" Click="newButton_Click"/>
<Button x:Name="save" Content="Save" HorizontalAlignment="Left" Margin="401,82,0,0" VerticalAlignment="Top" Width="75" Click="saveButton_Click_1"/>
<DataGrid x:Name="dataGrid1" HorizontalAlignment="Left" Height="100" Margin="77,236,0,0" VerticalAlignment="Top" Width="575" IsReadOnly="True"/>
</Grid>
</Window>
and here's the code for the secondary form that asks the user to input the data
public partial class Window1 : Window
{
public int iDNumber;
public string name;
public decimal price;
public Window1()
{
InitializeComponent();
}
private void Button_Click(object sender, RoutedEventArgs e)
{
iDNumber = Convert.ToInt32(iDTextBox.Text);
name = Convert.ToString(nameTextBox.Text);
price = Convert.ToDecimal(priceTextBox.Text);
((MainWindow)Application.Current.MainWindow).NewLine(iDNumber, name, price);
this.Close();
}
}
XAML code for Window1
<Window x:Class="WpfApp2.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:WpfApp2"
mc:Ignorable="d"
Title="Window1" Height="450" Width="400">
<Grid Margin="0,0,0,0">
<Button Content="Save" HorizontalAlignment="Left" Margin="156,362,0,0" VerticalAlignment="Top" Width="76" Click="Button_Click"/>
<TextBox x:Name="iDTextBox" HorizontalAlignment="Left" Height="23" Margin="156,79,0,0" TextWrapping="Wrap" VerticalAlignment="Top" Width="120"/>
<TextBox x:Name="nameTextBox" HorizontalAlignment="Left" Height="23" Margin="156,117,0,0" TextWrapping="Wrap" VerticalAlignment="Top" Width="120"/>
<TextBox x:Name="priceTextBox" HorizontalAlignment="Left" Height="23" Margin="156,155,0,0" TextWrapping="Wrap" VerticalAlignment="Top" Width="120"/>
<Label Content="ID" HorizontalAlignment="Left" Margin="95,79,0,0" VerticalAlignment="Top"/>
<Label Content="Name" HorizontalAlignment="Left" Margin="95,117,0,0" VerticalAlignment="Top"/>
<Label Content="Price" HorizontalAlignment="Left" Margin="95,155,0,0" VerticalAlignment="Top"/>
</Grid>
</Window>
When it was working the other day, it nicely added the new line of data to the SQL database (however didn't automatically show the updated info in the application, but this isn't the problem at the moment).
In this section of your code:
public MainWindow()
{
InitializeComponent();
if (dc.DatabaseExists())
{
dataGrid1.ItemsSource = dc.TestTables;
}
}
You are displaying the data by assigning the datatable to the datagrid.ItemsSource property. If you do this, you need to add items by modifying the DataTable instead of the DataGrid.
dataGrid1.Items.Add(testtable);
So instead of what's above, try adding the testtable item to your existing collection dc.TestTables
I have a window called RolledPaper.xaml with a textblock called SequenceValue.
SequenceValue is defined in another window called CounterSettings.xaml by typing in a textbox called SequenceRequested. I would like to have SequenceValue be always in sinch with SequenceRequested.
I tryed and failed using the same datacontext for both windows.
here it is the code for RolledPaper.xaml:
<Window x:Class="Numbering3.View.RolledPaper"
WindowStyle="None"
ResizeMode="NoResize"
BorderBrush="LightGray"
BorderThickness="5"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:Numbering3.View"
xmlns:vm="clr-namespace:Numbering3.ViewModel"
xmlns:cv="clr-namespace:Numbering3.Helper"
xmlns:vo="clr-namespace:Numbering3.ViewModel"
xmlns:sys="clr-namespace:System;assembly=mscorlib"
mc:Ignorable="d"
Title="RolledPaper" Height="750" Width="1218"
Background="{DynamicResource WindowBrush}"
DataContextChanged="Rolledpaper_DataContextChanged">
<Window.DataContext>
<vm:ViewModelRolledPaper/>
</Window.DataContext>
<TextBlock x:Name="SequenceValue" Grid.Column="3" HorizontalAlignment="Left" Height="19" Margin="72,310,0,0" TextWrapping="Wrap"
Background="White" VerticalAlignment="Top" Width="98" Text="{Binding _SequenceValueToShow.SequenceValuetoShow, Mode=TwoWay, FallbackValue=NNN, TargetNullValue=NNN, UpdateSourceTrigger=PropertyChanged}"/>
</Grid>
code behind:
public partial class RolledPaper : Window
{
public RolledPaper()
{
WindowStartupLocation = System.Windows.WindowStartupLocation.CenterScreen;
SaveKeeper.fromMain = false;
InitializeComponent();
this.MouseLeftButtonDown += delegate { this.DragMove(); };
DataContextChanged += new DependencyPropertyChangedEventHandler(Rolledpaper_DataContextChanged);
}
the CounterSetting window:
<Window x:Class="Numbering3.View.CounterSettings"
...
...
<Window.DataContext>
<ViewModelCounterSettings/>
</Window.DataContext>
<Grid Margin="0,-19,-0.4,0">
<TextBox x:Name="SequenceRequested" PreviewTextInput="SequenceValidationTextBox" MaxLength="10" HorizontalAlignment="Left" Height="23" Margin="154,324,0,0" TextWrapping="Wrap"
Text="{Binding Path=_SequenceValueToShow.SequenceValueToKeep, FallbackValue='NNN', TargetNullValue ='NNN', Mode=TwoWay, UpdateSourceTrigger=PropertyChanged }" VerticalAlignment="Top" Width="120" TextChanged="SequenceRequested_TextChanged" />
</Grid>
its code behind:
public partial class CounterSettings : Window
{
public CounterSettings()
{
InitializeComponent();
this.MouseLeftButtonDown += delegate { this.DragMove(); };
DataContextChanged += new DependencyPropertyChangedEventHandler(CounterSettings_DataContextChanged);
}
And the SequeneValue class:
public class SequenceValue : INotifyPropertyChanged
{
public string SequenceValueToKeep
{
get
{
return _sequenceValueToKeep=_sequenceProcessor.GetSequence();
}
set
{
if (_sequenceValueToKeep != value)
{
__sequenceValueToKeep = value;
RaisePropertyChanged("SequenceValueToKeep");
}
}
}
private void RaisePropertyChanged(string prop)
{
if (PropertyChanged != null)
{ PropertyChanged(this, new PropertyChangedEventArgs(prop)); }
}
public event PropertyChangedEventHandler PropertyChanged;
}
}
I need to put a value in the textbox of countersetting =>string Sequencevalue.SequenceValueToKeep is updated => textblock in RolledPaper window shows Sequencevalue.SequenceValueToKeep .
Thank you.
Solutio 1:
You can use one Static ViewModel to get the to to know each other.
in App.xaml
<Application.Resources>
...
<MainViewModel x:Key="mainViewModel" />
</Application.Resources>
and then in CounterSetting.xaml
<Window otherProperties=...
DataContext="{Binding ViewModelCounterSettings, Source={StaticResource mainViewModel}}"/>
and in RolledPaper.xaml
<Window otherProperties=...
DataContext="{Binding ViewModelRolledPaper, Source={StaticResource mainViewModel}}"/>
The MainViewModel does inits your two ViewModel and makes them accessible as properties and also gives the the same instance of SequenceValue
Solution 2:
Create an object of SequenceValue as an static resource, like
<Application.Resources>
...
<SequenceValue x:Key="sequenceValue"/>
</Application.Resources>
and set it as the DataContext of your TextBox and TextBlock
<TextBox DataContext="{StaticResource sequenceValue}"
Text="{Binding SequenceValueToKeep, FallbackValue='NNN', TargetNullValue='NNN', Mode=TwoWay, UpdateSourceTrigger=PropertyChanged }"
... />
<TextBlock DataContext="{StaticResource sequenceValue}"
Text="{Binding SequenceValuetoShow, FallbackValue=NNN, TargetNullValue=NNN, UpdateSourceTrigger=PropertyChanged}"
to keep my MainWindow.xaml.cs clean I tried to outsource everything to a ViewModel class and then bind my view to properties of my ViewModel property
However using this extra layer doesn't seem to work. My List- and Textbox just stay empty. Any way to get this method working?
MainWindow class:
public partial class MainWindow : Window, INotifyPropertyChanged
{
public ViewModel ViewModel { get; set; }
public MainWindow()
{
InitializeComponent();
ViewModel = new ViewModel();
}
}
ViewModel class:
public class ViewModel : INotifyPropertyChanged
{
private string m_oneLineOnly;
private ObservableCollection<string> m_sampleLines;
public ObservableCollection<string> SampleLines
{
get => m_sampleLines;
set
{
m_sampleLines = value;
RaisePropertyChanged(nameof(SampleLines));
}
}
public string OneLineOnly
{
get => m_oneLineOnly;
set
{
m_oneLineOnly = value;
RaisePropertyChanged(nameof(OneLineOnly));
}
}
public ViewModel()
{
SampleLines = new ObservableCollection<string>(new List<string>()
{
"Gedanken",
"Zeit",
"Sand"
});
OneLineOnly = "Hello World";
}
public event PropertyChangedEventHandler PropertyChanged = delegate { };
private void RaisePropertyChanged(string propertyName)
{
var handlers = PropertyChanged;
handlers(this, new PropertyChangedEventArgs(propertyName));
}
}
MainWindow XAML
<Window x:Class="DataContext_Test_Project.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:DataContext_Test_Project"
mc:Ignorable="d"
Title="MainWindow" Height="450" Width="800"
x:Name="Window">
<Grid>
<ListBox
HorizontalAlignment="Left"
Height="100"
Margin="334,132,0,0"
VerticalAlignment="Top"
Width="100"
ItemsSource="{Binding ElementName=Window, Path=ViewModel.SampleLines}"/>
<TextBox
HorizontalAlignment="Left"
Height="23"
Margin="184,166,0,0"
TextWrapping="Wrap"
VerticalAlignment="Top"
Width="120"
DataContext="{Binding ElementName=Window, Path=ViewModel}"
Text="{Binding Path=OneLineOnly}"/>
</Grid>
You can also define the DataContext in code behind:
public partial class MainWindow : Window
{
public ViewModel ViewModel { get; set; }
public MainWindow()
{
InitializeComponent();
ViewModel = new ViewModel();
DataContext = ViewModel;
}
}
And clean your XAML:
<Grid>
<ListBox
HorizontalAlignment="Left"
Height="100"
Margin="334,132,0,0"
VerticalAlignment="Top"
Width="100"
ItemsSource="{Binding SampleLines}"/>
<TextBox
HorizontalAlignment="Left"
Height="23"
Margin="184,166,0,0"
TextWrapping="Wrap"
VerticalAlignment="Top"
Width="120"
Text="{Binding OneLineOnly}"/>
</Grid>
In order to make Bindings like
ItemsSource="{Binding ElementName=Window, Path=ViewModel.SampleLines}"
DataContext="{Binding ElementName=Window, Path=ViewModel}"
work, you have two options. Either make the ViewModel property fire a property change notification, or simply initialize it before the XAML is parsed, i.e. before InitializeComponent() is called:
Like this:
public partial class MainWindow : Window
{
public ViewModel ViewModel { get; }
public MainWindow()
{
ViewModel = new ViewModel();
InitializeComponent();
}
}
Or simpler:
public partial class MainWindow : Window
{
public ViewModel ViewModel { get; } = new ViewModel();
public MainWindow()
{
InitializeComponent();
}
}
Remove the following line from xaml.cs file : ViewModel = new ViewModel();
Use the following code for Xaml file:
<Window x:Class="DataContext_Test_Project.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:DataContext_Test_Project"
mc:Ignorable="d"
Title="MainWindow" Height="450" Width="800"
x:Name="Window" DataContext="{DynamicResource ViewModel}">
<Window.Resources>
<local:ViewModel x:Key="ViewModel"/>
</Window.Resources>
<Grid>
<ListBox
HorizontalAlignment="Left"
Height="100"
Margin="334,132,0,0"
VerticalAlignment="Top"
Width="100"
ItemsSource="{Binding Path=SampleLines}"/>
<TextBox
HorizontalAlignment="Left"
Height="23"
Margin="184,166,0,0"
TextWrapping="Wrap"
VerticalAlignment="Top"
Width="120"
Text="{Binding Path=OneLineOnly}"/>
</Grid>
</Window>
In my WPF Application I created some Class1:
namespace WpfApplication1 {
class Class1 {
public override string ToString() {
return "Hello, WPF!";
}
}
}
Now I want to set the instance of this class to Button.Content property in the XAML markup. How can I do it?
I try to do it:
<Window x:Class="WpfApplication1.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:WpfApplication1"
mc:Ignorable="d"
Title="MainWindow" Height="350" Width="525">
<Grid>
<Button x:Name="button" HorizontalAlignment="Left"
Margin="246,93,0,0" VerticalAlignment="Top" Width="75">
<Button.Content>
<!-- ERROR: This is wrong syntax: -->
<Object x:Class="WpfApplication1.Class1"/>
</Button.Content>
</Button>
</Grid>
</Window>
What is right syntax for this case?
This is what I did and it worked.
<Button x:Name="button" HorizontalAlignment="Left"
Margin="246,93,0,0" VerticalAlignment="Top" Width="75">
<local:Class1 />
</Button>
A better practice is to implement INotifyPropertyChanged and a property which will be binded in xaml. something like that:
class Class1 {
private string _Text;
public Class1(){
_Text = this.ToString();
}
public override string ToString() {
return "Hello, WPF!";
}
}
public string Text
{
get{return _Text;}
protected set { _Text = value;
NotifyPropertyChanged("Text");
}
}
In XAML do:
<Button Content="{Binding Path=Text,UpdateSourceTrigger=PropertyChanged}"
I hope that provide a solution to your issue.