Small question re: customized controls in WPF
-
This is just a quick question to point me in the right direction. I want to write some sort of custom control (so far a UserControl) that will basically be defined as a TextBlock, and certain parts of that text block need to be customized by properties by the user of the usercontrol. So I get that I can define entire properties, but how do I provide part of a property for something like a TextBlock? For example, suppose I want a user control that creates a TextBlock with the contents "Hello {name}, how are you today?", where {name} is specified as a property of the user control. I'm thinking something like ASPX would be nice here, how you can render an output... I don't suppose WPF has anything like that... where I can just "render" the XAML for a custom control? The journey to WPF enlightenment continues... :cool: Logan
“Time and space can be a bitch.” –Gushie, Quantum Leap {o,o}.oO( Looking for a great RSS reader? Try FeedBeast! ) |)””’) Built with home-grown CodeProject components! -”-”-
-
This is just a quick question to point me in the right direction. I want to write some sort of custom control (so far a UserControl) that will basically be defined as a TextBlock, and certain parts of that text block need to be customized by properties by the user of the usercontrol. So I get that I can define entire properties, but how do I provide part of a property for something like a TextBlock? For example, suppose I want a user control that creates a TextBlock with the contents "Hello {name}, how are you today?", where {name} is specified as a property of the user control. I'm thinking something like ASPX would be nice here, how you can render an output... I don't suppose WPF has anything like that... where I can just "render" the XAML for a custom control? The journey to WPF enlightenment continues... :cool: Logan
“Time and space can be a bitch.” –Gushie, Quantum Leap {o,o}.oO( Looking for a great RSS reader? Try FeedBeast! ) |)””’) Built with home-grown CodeProject components! -”-”-
Anything you can do in XAML, you can do in code - that's ultimately what XAML boils down to. So it's fairly trivial to implement something like this in code. e.g.
TextBlock textBlock1 = new TextBlock();
textBlock1.TextWrapping = TextWrapping.Wrap;
textBlock2.Background = Brushes.AntiqueWhite;
textBlock1.Inlines.Add(new Run("Hello "));
textBlock1.Inlines.Add(new Bold(new Run(userName)));
textBlock1.Inlines.Add(new Run(", how are you today?"));Alternatively, you can add your items via XAML directly just by using three TextBlocks. Two of these blocks would be static, the third would bind to the user name.
Deja View - the feeling that you've seen this post before.
-
Anything you can do in XAML, you can do in code - that's ultimately what XAML boils down to. So it's fairly trivial to implement something like this in code. e.g.
TextBlock textBlock1 = new TextBlock();
textBlock1.TextWrapping = TextWrapping.Wrap;
textBlock2.Background = Brushes.AntiqueWhite;
textBlock1.Inlines.Add(new Run("Hello "));
textBlock1.Inlines.Add(new Bold(new Run(userName)));
textBlock1.Inlines.Add(new Run(", how are you today?"));Alternatively, you can add your items via XAML directly just by using three TextBlocks. Two of these blocks would be static, the third would bind to the user name.
Deja View - the feeling that you've seen this post before.
Super! That's what I was looking for. Is it possible to declare something like a Run or a Span inside a string, as an inline like Bold, but set its content via binding? Or would I have to do the three separate TextBlocks as you say? Something like this would be handy: Hello , how are you? Cheers
“Time and space can be a bitch.” –Gushie, Quantum Leap {o,o}.oO( Looking for a great RSS reader? Try FeedBeast! ) |)””’) Built with home-grown CodeProject components! -”-”-
-
Super! That's what I was looking for. Is it possible to declare something like a Run or a Span inside a string, as an inline like Bold, but set its content via binding? Or would I have to do the three separate TextBlocks as you say? Something like this would be handy: Hello , how are you? Cheers
“Time and space can be a bitch.” –Gushie, Quantum Leap {o,o}.oO( Looking for a great RSS reader? Try FeedBeast! ) |)””’) Built with home-grown CodeProject components! -”-”-
Well, if you want to use binding, you can do this:
<StackPanel Orientation="Horizontal">
<TextBlock Text="Hello "/>
<TextBlock Text="{Binding Mode=OneWay, Path=Name}" />
<TextBlock Text=", how are you?" />
</StackPanel>Deja View - the feeling that you've seen this post before.
-
This is just a quick question to point me in the right direction. I want to write some sort of custom control (so far a UserControl) that will basically be defined as a TextBlock, and certain parts of that text block need to be customized by properties by the user of the usercontrol. So I get that I can define entire properties, but how do I provide part of a property for something like a TextBlock? For example, suppose I want a user control that creates a TextBlock with the contents "Hello {name}, how are you today?", where {name} is specified as a property of the user control. I'm thinking something like ASPX would be nice here, how you can render an output... I don't suppose WPF has anything like that... where I can just "render" the XAML for a custom control? The journey to WPF enlightenment continues... :cool: Logan
“Time and space can be a bitch.” –Gushie, Quantum Leap {o,o}.oO( Looking for a great RSS reader? Try FeedBeast! ) |)””’) Built with home-grown CodeProject components! -”-”-
Another really powerful feature of WPF is the ability to use converters. This could be done as:
<local:GreetingConverter x:Key="GreetingFormatter">
This is the actual text.
<StackPanel Orientation="Horizontal">
<TextBlock Text="{Binding Mode=OneWay, Path=Name}"
Converter={StaticResource GreetingFormatter} />
</StackPanel>This would be the class that implements the converter:
using System;
using System.Windows.Data;namespace MySample.GreetingConverter
{
[ValueConversion(typeof(object),typeof(string))]
public class FormattingConverter: IValueConverter
{
public object Convert(object value, Type targetType,
object parameter, System.Globalization.CultureInfo culture)
{
return string.Format("Hello {0}, how are you?", value);
}public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) { // we don't intend this to ever be called return null; } }
}
Deja View - the feeling that you've seen this post before.
-
Another really powerful feature of WPF is the ability to use converters. This could be done as:
<local:GreetingConverter x:Key="GreetingFormatter">
This is the actual text.
<StackPanel Orientation="Horizontal">
<TextBlock Text="{Binding Mode=OneWay, Path=Name}"
Converter={StaticResource GreetingFormatter} />
</StackPanel>This would be the class that implements the converter:
using System;
using System.Windows.Data;namespace MySample.GreetingConverter
{
[ValueConversion(typeof(object),typeof(string))]
public class FormattingConverter: IValueConverter
{
public object Convert(object value, Type targetType,
object parameter, System.Globalization.CultureInfo culture)
{
return string.Format("Hello {0}, how are you?", value);
}public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) { // we don't intend this to ever be called return null; } }
}
Deja View - the feeling that you've seen this post before.
Fascinating. Are converters able to return WPF types, or just primitives? And are they called every time the interface is rendered, or only when things change?
“Time and space can be a bitch.” –Gushie, Quantum Leap {o,o}.oO( Looking for a great RSS reader? Try FeedBeast! ) |)””’) Built with home-grown CodeProject components! -”-”-
-
Well, if you want to use binding, you can do this:
<StackPanel Orientation="Horizontal">
<TextBlock Text="Hello "/>
<TextBlock Text="{Binding Mode=OneWay, Path=Name}" />
<TextBlock Text=", how are you?" />
</StackPanel>Deja View - the feeling that you've seen this post before.
I managed to get something like what I wanted, by overriding the user control's OnRender method: Hello , how are you? protected override void OnRender( DrawingContext drawingContext ) { base.OnRender( drawingContext ); name.Text = Name; } Cool. :) P.S. What's that tool everyone uses to copy and paste code into html that fixes angle brackets and all that? I'm getting tired of disabling html in my messages.
-
Fascinating. Are converters able to return WPF types, or just primitives? And are they called every time the interface is rendered, or only when things change?
“Time and space can be a bitch.” –Gushie, Quantum Leap {o,o}.oO( Looking for a great RSS reader? Try FeedBeast! ) |)””’) Built with home-grown CodeProject components! -”-”-
They can convert between any types you want and they're called when the value changes. In 3.5 there is a StringFormat property on the binding itself. You may also want to lookup multi-bindings and multi-input converters.
-
They can convert between any types you want and they're called when the value changes. In 3.5 there is a StringFormat property on the binding itself. You may also want to lookup multi-bindings and multi-input converters.
Cool, thanks for the tips. I thought you were Pete there for a second, since he's been replying to practically all my questions, so I wanted to thank him; but thank you also. Logan
“Time and space can be a bitch.” –Gushie, Quantum Leap {o,o}.oO( Looking for a great RSS reader? Try FeedBeast! ) |)””’) Built with home-grown CodeProject components! -”-”-
-
Cool, thanks for the tips. I thought you were Pete there for a second, since he's been replying to practically all my questions, so I wanted to thank him; but thank you also. Logan
“Time and space can be a bitch.” –Gushie, Quantum Leap {o,o}.oO( Looking for a great RSS reader? Try FeedBeast! ) |)””’) Built with home-grown CodeProject components! -”-”-
No problems mate. I'd disappeared from the boards by the time you asked the followup. Only to glad to help mate.
Deja View - the feeling that you've seen this post before.