I am implementing a my custom class which needs to be derived from Panel.
After inheriting from Panel, the overridden method "MeasureOverride" gets the default size.
In my xaml page, I am using ListBox for which no width and height is specified and this custom panel is called from ItemsPanel Template.
When the class is derived from Panel class, the width and height received in the parameter is infinity.
But, deriving the same class, from VirtualStackPanel, I get height and width ( the size in which parent control gets displayed).
Any idea, why this behavior? I need to derive the my control from Panel class but in that case needs the parent width & height size (calculated size based on the visible area available).
Regards
Rajesh
Found the solution for same,
Implementing IScrollInfo interface solves the problem. By using IScrollInfo one can implement his/her own scroll containers.
Related
We've got a user control we're written that's meant to fit both on a window (works fine there) and now within a class I've defined which inherits from ModernUI ModernDialog. The user control I'm trying to place on the ModernDialog derived class is wider than the ModernDialog allows for. I've tried setting the Width property of the derived ModernDialog class both within the class itself and within the code that calls the class. The ModernDialog box consistently ignores all attempts I've made to control the ModernDialog's width.
Why is it doing that?
How do I control the width of the ModernDialog?
You cannot control the width of a ModernUI dialog. It has a hard coded maximum and minimum width. Between these lengths the dialog will size to its content.
Im writing a WPF application where usercontrols are added to a TabControl at runtime - creating a tab for each user control. The problem then is...these controls can have different width and height which means the tabcontrol must adjust its own width and height accordingly. I tought this would be a simple exercise of just accessing the usercontrols Height/ActualHeight properties, but these are NaN/0.0
Is it not possible to get this information?
I can propose next solution:
When you add a new control to the TabControl (is it a TabControl or a TabItem?) set bindings for the Width and Height properties. Create a converter to convert sizes of added controls to the size of Owner (in case if you need to have minimum size).
ActualWidth and ActualHeight properties perhaps are 0 because control wasn't measured yet. Look this thread
At runtime I am creating a WPF control. It can be any WPF Control.
I want to find out whether this WPF Control, IS A CONTAINER CONTROL.
i.e. can this control can embed/contain another control.
Does there exist any Attribute through which the above can be achieved?
e.g. a label, panel, groupBox can contain other control like button, but textBOX cant.
In WPF there are a few base classes that controls extend from.
ContentControl: Most controls extend from this because most controls can store some type of single content within them.
ItemsControl: These are types of collection controls, which contain a collection of content within them.
Panel: These are special controls for layouts. They implement the ArrangeOverride and MeasureOverride methods to measure/arrange the children controls within them. Most of them also expose attached properties for best use.
That being said, you would typically want to use the is operator to check if your control inherits from what you intend it to. You can be specific or general, but typically you want to be as general as possible. I'm not sure what you meant by "container", which is why I listed the three (3) typical base controls that could contain other controls. For example:
if (myControl is ContentControl)
{
// Do something here.
}
All the controls mentioned here and here apart from TabControl inherit from Panel
So you can do something like:
if (myControl is Panel || myControl is TabControl)
{
// Then it's a container
}
Assume that I need to create a class called PictureWall, which will be used to show pictures.
Now I find that Panel and ItemsControl can both be used to hold Children elements. So should the class PictureWall derive from Panel? or should it derive from ItemsControl.
Note: This is not a real requirement, it's just a hypothetical question. The real question is: when should I create a subclass of Control (or ItemsControl) and when should I create a subclass of Panel?
Note 2: This imagined picture wall control is not to be used in one application only. It may be used by other developers. If it derives from Panel or ItemsControl, it'll expose the property named Children to other developers. So in this case, deriving from Control is a better idea, right?
Note 3: This imagined picture wall control has its own default way of loading certain pictures (for example, pulling pictures from a server) and it does not want this way to be messed around. If this is the case, then we should not inherit ItemsControl, right?
Panel is a container that is used to arrange its children. For example: Grid with a title and one button on the bottom and an image on center - Grid is very flexible to help you move stuff and arrange them when you change the size of window etc.
ItemsControl is a control that helps you with a collection of items. Let's take a concrete example: Listbox. You can very easly show a list of items, applay template to all of them, so on and so forth.
Control class is basically a UI element that can have its own template.
Note that, it is a way much better to define own UserControl, edit template or style of your PictureWall, insted of subclassing (there are many advantages, for example you can use Blend to redefine the style).
Edit:
# note2
If I were you I would make my own User Control to reuse existing controls to make what I want. If that won't be enough I would subclass Control.
[StyleTypedProperty(Property = "FooStyle", StyleTargetType = typeof(Control))]
public partial class MyDangControl: Control
{
...
# note3
This is a bad idea to combine all in one. You should split the logic that fetch the data form yout Picture Wall. For instance, user presses thumbnail to download the image and whole UI hangs. Horrible UX.
To be crystal clear, let me quote Pro WPF in C# 2010
Control
This is the most common starting
point when building a control
from scratch. It’s the base class for
all user-interactive widgets. The
Control class adds properties for
setting the background and foreground,
as well as the font and alignment of
content. The control class also places
itself into the tab order (through the
IsTabStop property) and introduces the
notion of double-clicking (through the
MouseDoubleClick and
PreviewMouseDoubleClick events). But
most important, the Control class
defines the Template property that
allows its appearance to be swapped
out with a customized element tree for
endless flexibility.
ContentControl
This is the base class for controls
that can display a single piece of
arbitrary content. That content can be
an element or a custom object that’s
used in conjunction with a template.
(The content is set through the
Content property, and an optional
template can be provided in the
ContentTemplate property.) Many
controls wrap a specific, limited type
of content (like a string of text in a
text box). Because these controls
don’t support all elements, they
shouldn’t be defined as content
controls.
ItemsControl
ItemsControl is the base class for
controls that wrap a list of items but
don’t support selection, while
Selector is the more specialized base
class for controls that do support
selection. These classes aren’t often
used to create custom controls,
because the data templating features
of the ListBox, ListView, and TreeView
provide a great deal of flexibility.
Panel
This is the base class for controls
with layout logic. A layout control
can hold multiple children and
arranges them according to specific
layout semantics. Often, panels
include attached properties that can
be set on the children to configure
how the children are arranged.
They both can be used to display elements, but really an ItemsControl offers much more functionality. In addition, an ItemsControl doesn't really display it's elements, it leverages a Panel to do that.
An ItemsControl can display a list of items, which may or may not be UIElements/Visuals. The items can be templated using a configurable DataTemplate, which ultimately determines how the item is displayed. In addition, then items can be bound to an observable collection so it will automatically update.
Neither of these features are supported by a Panel. DataTemplates can be used, but you have to manually create an associated ContentControl/ContentPresenter and add it to your panel.
Ultimately, their functions are different. A Panel is used to display UIElements/Visuals. An ItemsControl is used to display any type of data and apply templates as needed.
I am new to WPF. A Problem I am trying to solve is how I can get a correct height at runtime.
In my Application I dynamically add Usercontrols to a Stackpanel in the Code behind. The Usercontrol contains a few Texblocks. My Stackpanel is then used as Content for a BookPage and this BookPage is added to a Book(http://wpfbookcontrol.codeplex.com/). The Height of my Stackpanel should not exceed a certain value.
I already figured out that I can use Measure & Arrange to calculate the ActualSize & Height of the Usercontrol:
itemsa.Measure(new System.Windows.Size(double.PositiveInfinity, double.PositiveInfinity));
itemsa.Arrange(new Rect(0, 0, 400, itemsa.DesiredSize.Height));
At this point the Usercontrol isn't added to the Stackpanel. 400 is the Width my usercontrol shouldn't exceed, but it does, because the Textblock dosn't create automatic linebreaks. When I display the Book the linebreaks are created.
What should I do to solve this Problem?
Thanks in advance.
Not sure if you're looking for this, but with the MaxHeight property you have the possibility to restrict the growing of a control.
In general, it's not necessary to override Measure and Arrange, the Layout-System is very powerfull and it offers you many container-controls that provide specific layout behaviour.
Why not use the property MaxHeight for the stackpanel?
Also ActualWidth and ActualHeight will tell you the actual size of a control.
Are you sure you need all these calculations? My guess is that it would be better to use auto sizing GridRows or something like that.
It sounds to me like you want a custom panel to do layout in a very specific manner. You can inherit a new class from Panel, and then override MeasureOverride and ArrangeOverride to determine what can be added and where. This is also the method you'd use to do a virtual panel, where only the visible children are created and they are destroyed when scrolled off.
If you are interested in this let me know and I'll edit the post and provide an example.