Custom Design time

  • Thread starter Thread starter Guest
  • Start date Start date
G

Guest

I am creating a custom toolbar. My toolbar have a property Align. Align put a
toolbar in top, bottom, left ou rigth.

How a get a Parent of my control in design time ?

Ex:
myToolBar.Width = Parent.Width.

Rogerio
 
Seems you should handle ParentChanged event,
as far as I remember it worked for me, just try it
 
I've put together a sample of a ToolBar control that will allow "docking" at
both design-time and run-time. By "docking" I mean that the control is
pinned to the edge of it's parent and will be adjusted according to the
parents size. If you really wanted to get fancy you can create a custom
designer that will prevent the user from resizing the control, on the
appropriate edge, by overriding the ControlDesigner's SelectionRules
property. If you paste the code below into the VS.Net editor it might be
easier to read.

using System;
using System.ComponentModel;
using System.Drawing;
using System.Windows.Forms;

#region Designer
============================================================================
======
#if DESIGN
[assembly:
System.CF.Design.RuntimeAssemblyAttribute("MyCompany.Windows.Forms.ToolBarEx
, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null")]
#endif
#endregion
============================================================================
============

namespace MyCompany.Windows.Forms
{
public enum DockStyle
{
None = 0x00,
Top = 0x01,
Bottom = 0x02,
Left = 0x03,
Right = 0x04
}

public class ToolBarEx : System.Windows.Forms.Control
{
private MyCompany.Windows.Forms.DockStyle dock =
MyCompany.Windows.Forms.DockStyle.Top;

#if DESIGN
#region Designer
============================================================================
[
CategoryAttribute("Layout"),
DescriptionAttribute("Indicates the docking location of the control."),
DefaultValueAttribute(MyCompany.Windows.Forms.DockStyle.Top)
]
public new MyCompany.Windows.Forms.DockStyle Dock
#endregion
============================================================================
======
#else
public virtual MyCompany.Windows.Forms.DockStyle Dock
#endif
{
get
{
return dock;
}
set
{
if (dock != value)
{
dock = value;
UpdateDock();
}
}
}

#if DESIGN
#region Designer
============================================================================
protected override Size DefaultSize
#endregion
============================================================================
======
#else
protected virtual Size DefaultSize
#endif
{
get
{
return new Size(26, 26);
}
}

public ToolBarEx() { }

protected override void OnParentChanged(System.EventArgs e)
{
if (this.Parent != null)
{
UpdateDock();
this.Parent.Resize += new EventHandler(Parent_Resize);
}
base.OnParentChanged(e);
}

private void Parent_Resize(object sender, EventArgs e)
{
UpdateDock();
}

private void UpdateDock()
{
#region Adjust Bounds
====================================================================
if (this.Parent != null)
{
Size defaultSize = this.DefaultSize;
Size parentSize = this.Parent.ClientSize;
switch (this.Dock)
{
case DockStyle.None:
{
// Do nothing.
break;
}
case DockStyle.Top:
{
this.Bounds = new Rectangle(0, 0, parentSize.Width, defaultSize.Height);
break;
}
case DockStyle.Bottom:
{
this.Bounds = new Rectangle(0, (parentSize.Height - defaultSize.Height),
parentSize.Width, defaultSize.Height);
break;
}
case DockStyle.Left:
{
this.Bounds = new Rectangle(0, 0, defaultSize.Width, parentSize.Height);
break;
}
case DockStyle.Right:
{
this.Bounds = new Rectangle((parentSize.Width - defaultSize.Width), 0,
defaultSize.Width, parentSize.Height);
break;
}
}
}
#endregion
============================================================================
===
}
}
}
 
Did you override Dispose function in this control, I am afraid that it will
fail in
design time with message "Object reference is not set"
if you will move the control form its parent, you registered the control in
its parent and
I do not see the cod that removes it...You need to remove handler
this.Parent.Resize -= new EventHandler(Parent_Resize);
in your dispose method

Am I right?

Tim Wilson said:
I've put together a sample of a ToolBar control that will allow "docking"
at
both design-time and run-time. By "docking" I mean that the control is
pinned to the edge of it's parent and will be adjusted according to the
parents size. If you really wanted to get fancy you can create a custom
designer that will prevent the user from resizing the control, on the
appropriate edge, by overriding the ControlDesigner's SelectionRules
property. If you paste the code below into the VS.Net editor it might be
easier to read.

using System;
using System.ComponentModel;
using System.Drawing;
using System.Windows.Forms;

#region Designer
============================================================================
======
#if DESIGN
[assembly:
System.CF.Design.RuntimeAssemblyAttribute("MyCompany.Windows.Forms.ToolBarEx
, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null")]
#endif
#endregion
============================================================================
============

namespace MyCompany.Windows.Forms
{
public enum DockStyle
{
None = 0x00,
Top = 0x01,
Bottom = 0x02,
Left = 0x03,
Right = 0x04
}

public class ToolBarEx : System.Windows.Forms.Control
{
private MyCompany.Windows.Forms.DockStyle dock =
MyCompany.Windows.Forms.DockStyle.Top;

#if DESIGN
#region Designer
============================================================================
[
CategoryAttribute("Layout"),
DescriptionAttribute("Indicates the docking location of the control."),
DefaultValueAttribute(MyCompany.Windows.Forms.DockStyle.Top)
]
public new MyCompany.Windows.Forms.DockStyle Dock
#endregion
============================================================================
======
#else
public virtual MyCompany.Windows.Forms.DockStyle Dock
#endif
{
get
{
return dock;
}
set
{
if (dock != value)
{
dock = value;
UpdateDock();
}
}
}

#if DESIGN
#region Designer
============================================================================
protected override Size DefaultSize
#endregion
============================================================================
======
#else
protected virtual Size DefaultSize
#endif
{
get
{
return new Size(26, 26);
}
}

public ToolBarEx() { }

protected override void OnParentChanged(System.EventArgs e)
{
if (this.Parent != null)
{
UpdateDock();
this.Parent.Resize += new EventHandler(Parent_Resize);
}
base.OnParentChanged(e);
}

private void Parent_Resize(object sender, EventArgs e)
{
UpdateDock();
}

private void UpdateDock()
{
#region Adjust Bounds
====================================================================
if (this.Parent != null)
{
Size defaultSize = this.DefaultSize;
Size parentSize = this.Parent.ClientSize;
switch (this.Dock)
{
case DockStyle.None:
{
// Do nothing.
break;
}
case DockStyle.Top:
{
this.Bounds = new Rectangle(0, 0, parentSize.Width, defaultSize.Height);
break;
}
case DockStyle.Bottom:
{
this.Bounds = new Rectangle(0, (parentSize.Height - defaultSize.Height),
parentSize.Width, defaultSize.Height);
break;
}
case DockStyle.Left:
{
this.Bounds = new Rectangle(0, 0, defaultSize.Width, parentSize.Height);
break;
}
case DockStyle.Right:
{
this.Bounds = new Rectangle((parentSize.Width - defaultSize.Width), 0,
defaultSize.Width, parentSize.Height);
break;
}
}
}
#endregion
============================================================================
===
}
}
}

--
Tim Wilson
.Net Compact Framework MVP

Rogerio Jun said:
I am creating a custom toolbar. My toolbar have a property Align. Align put a
toolbar in top, bottom, left ou rigth.

How a get a Parent of my control in design time ?

Ex:
myToolBar.Width = Parent.Width.

Rogerio
 
You shouldn't get an error message when you remove the control if you check
whether the Parent is null in the OnParentChanged method, as in the code
sample. The problem is that the control can be reparented which means that
you are not really given the opportunity to remove the handler since the
OnParentChanged method will be called once with "null", when the control is
removed from the original parent, and once with the new parent when it is
reparented. So removing in the Dispose method will work but only for the
last control that was acting as a parent. But I agree - as good practice you
should remove from an event handler that you no longer need.

--
Tim Wilson
..Net Compact Framework MVP

MacFar said:
Did you override Dispose function in this control, I am afraid that it will
fail in
design time with message "Object reference is not set"
if you will move the control form its parent, you registered the control in
its parent and
I do not see the cod that removes it...You need to remove handler
this.Parent.Resize -= new EventHandler(Parent_Resize);
in your dispose method

Am I right?

Tim Wilson said:
I've put together a sample of a ToolBar control that will allow "docking"
at
both design-time and run-time. By "docking" I mean that the control is
pinned to the edge of it's parent and will be adjusted according to the
parents size. If you really wanted to get fancy you can create a custom
designer that will prevent the user from resizing the control, on the
appropriate edge, by overriding the ControlDesigner's SelectionRules
property. If you paste the code below into the VS.Net editor it might be
easier to read.

using System;
using System.ComponentModel;
using System.Drawing;
using System.Windows.Forms;

#region Designer
============================================================================
======
#if DESIGN
[assembly:
System.CF.Design.RuntimeAssemblyAttribute("MyCompany.Windows.Forms.ToolBarEx
, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null")]
#endif
#endregion
============================================================================
============

namespace MyCompany.Windows.Forms
{
public enum DockStyle
{
None = 0x00,
Top = 0x01,
Bottom = 0x02,
Left = 0x03,
Right = 0x04
}

public class ToolBarEx : System.Windows.Forms.Control
{
private MyCompany.Windows.Forms.DockStyle dock =
MyCompany.Windows.Forms.DockStyle.Top;

#if DESIGN
#region Designer
============================================================================
[
CategoryAttribute("Layout"),
DescriptionAttribute("Indicates the docking location of the control."),
DefaultValueAttribute(MyCompany.Windows.Forms.DockStyle.Top)
]
public new MyCompany.Windows.Forms.DockStyle Dock
#endregion
============================================================================
======
#else
public virtual MyCompany.Windows.Forms.DockStyle Dock
#endif
{
get
{
return dock;
}
set
{
if (dock != value)
{
dock = value;
UpdateDock();
}
}
}

#if DESIGN
#region Designer
============================================================================
protected override Size DefaultSize
#endregion
============================================================================
======
#else
protected virtual Size DefaultSize
#endif
{
get
{
return new Size(26, 26);
}
}

public ToolBarEx() { }

protected override void OnParentChanged(System.EventArgs e)
{
if (this.Parent != null)
{
UpdateDock();
this.Parent.Resize += new EventHandler(Parent_Resize);
}
base.OnParentChanged(e);
}

private void Parent_Resize(object sender, EventArgs e)
{
UpdateDock();
}

private void UpdateDock()
{
#region Adjust Bounds
====================================================================
if (this.Parent != null)
{
Size defaultSize = this.DefaultSize;
Size parentSize = this.Parent.ClientSize;
switch (this.Dock)
{
case DockStyle.None:
{
// Do nothing.
break;
}
case DockStyle.Top:
{
this.Bounds = new Rectangle(0, 0, parentSize.Width, defaultSize.Height);
break;
}
case DockStyle.Bottom:
{
this.Bounds = new Rectangle(0, (parentSize.Height - defaultSize.Height),
parentSize.Width, defaultSize.Height);
break;
}
case DockStyle.Left:
{
this.Bounds = new Rectangle(0, 0, defaultSize.Width, parentSize.Height);
break;
}
case DockStyle.Right:
{
this.Bounds = new Rectangle((parentSize.Width - defaultSize.Width), 0,
defaultSize.Width, parentSize.Height);
break;
}
}
}
#endregion
============================================================================
===
}
}
}

--
Tim Wilson
.Net Compact Framework MVP

Rogerio Jun said:
I am creating a custom toolbar. My toolbar have a property Align. Align put a
toolbar in top, bottom, left ou rigth.

How a get a Parent of my control in design time ?

Ex:
myToolBar.Width = Parent.Width.

Rogerio
 
I revamped the OnParentChanged method to remove the handler. You need to
store a reference to the parent to accomplish this. While it wouldn't be
obvious to the user, since the control is still looking to its current
parent when the call to the UpdateDock method is made, after the control is
reparented (if at all) and the previous parent gets resized the control
would get its Resize handler called. Not a good thing. So here's the updated
code to handle that. And I also added the Dispose override to unhook from
the Resize event. The problem is not seen, by me at least, when the control
is removed from its parent, or deleted in the designer at design-time, but a
problem does occur if you explicitly call Dispose on a ToolBarEx instance
and then resize what used to be the parent. Thanks to MacFar for raising
concerns.

private Control parent = null;

....

protected override void OnParentChanged(System.EventArgs e)
{
EventHandler handler = new EventHandler(Parent_Resize);
if (this.parent != null)
{
this.parent.Resize -= handler;
}
if (this.Parent != null)
{
UpdateDock();
this.Parent.Resize += handler;
}
this.parent = this.Parent;
base.OnParentChanged(e);
}

protected override void Dispose(bool disposing)
{
if (disposing)
{
if (this.parent != null)
{
this.parent.Resize -= new EventHandler(Parent_Resize);
}
}
base.Dispose(disposing);
}

--
Tim Wilson
..Net Compact Framework MVP

Tim Wilson said:
You shouldn't get an error message when you remove the control if you check
whether the Parent is null in the OnParentChanged method, as in the code
sample. The problem is that the control can be reparented which means that
you are not really given the opportunity to remove the handler since the
OnParentChanged method will be called once with "null", when the control is
removed from the original parent, and once with the new parent when it is
reparented. So removing in the Dispose method will work but only for the
last control that was acting as a parent. But I agree - as good practice you
should remove from an event handler that you no longer need.

--
Tim Wilson
.Net Compact Framework MVP

MacFar said:
Did you override Dispose function in this control, I am afraid that it will
fail in
design time with message "Object reference is not set"
if you will move the control form its parent, you registered the control in
its parent and
I do not see the cod that removes it...
You need to remove handler
this.Parent.Resize -= new EventHandler(Parent_Resize);
in your dispose method

Am I right?

"Tim Wilson" <TIM(UNDERSCORE)WILSON(AT)ROGERS(PERIOD)COM> wrote in message
============================================================================
======
#if DESIGN
[assembly:
System.CF.Design.RuntimeAssemblyAttribute("MyCompany.Windows.Forms.ToolBarEx
, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null")]
#endif
#endregion
========================================================================================================================================================
[
CategoryAttribute("Layout"),
DescriptionAttribute("Indicates the docking location of the control."),
DefaultValueAttribute(MyCompany.Windows.Forms.DockStyle.Top)
]
public new MyCompany.Windows.Forms.DockStyle Dock
#endregion
================================================================================================================================================================================================================================================================================================================
 
When I add a control in form, I receive a message "Object reference not set
to an instance of an object".

What is wrong ?

Tim Wilson said:
You shouldn't get an error message when you remove the control if you check
whether the Parent is null in the OnParentChanged method, as in the code
sample. The problem is that the control can be reparented which means that
you are not really given the opportunity to remove the handler since the
OnParentChanged method will be called once with "null", when the control is
removed from the original parent, and once with the new parent when it is
reparented. So removing in the Dispose method will work but only for the
last control that was acting as a parent. But I agree - as good practice you
should remove from an event handler that you no longer need.

--
Tim Wilson
..Net Compact Framework MVP

MacFar said:
Did you override Dispose function in this control, I am afraid that it will
fail in
design time with message "Object reference is not set"
if you will move the control form its parent, you registered the control in
its parent and
I do not see the cod that removes it...
this.Parent.Resize += new EventHandler(Parent_Resize);
You need to remove handler
this.Parent.Resize -= new EventHandler(Parent_Resize);
in your dispose method

Am I right?

Tim Wilson said:
I've put together a sample of a ToolBar control that will allow "docking"
at
both design-time and run-time. By "docking" I mean that the control is
pinned to the edge of it's parent and will be adjusted according to the
parents size. If you really wanted to get fancy you can create a custom
designer that will prevent the user from resizing the control, on the
appropriate edge, by overriding the ControlDesigner's SelectionRules
property. If you paste the code below into the VS.Net editor it might be
easier to read.

using System;
using System.ComponentModel;
using System.Drawing;
using System.Windows.Forms;

#region Designer
============================================================================
======
#if DESIGN
[assembly:
System.CF.Design.RuntimeAssemblyAttribute("MyCompany.Windows.Forms.ToolBarEx
, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null")]
#endif
#endregion
============================================================================
============

namespace MyCompany.Windows.Forms
{
public enum DockStyle
{
None = 0x00,
Top = 0x01,
Bottom = 0x02,
Left = 0x03,
Right = 0x04
}

public class ToolBarEx : System.Windows.Forms.Control
{
private MyCompany.Windows.Forms.DockStyle dock =
MyCompany.Windows.Forms.DockStyle.Top;

#if DESIGN
#region Designer
============================================================================
[
CategoryAttribute("Layout"),
DescriptionAttribute("Indicates the docking location of the control."),
DefaultValueAttribute(MyCompany.Windows.Forms.DockStyle.Top)
]
public new MyCompany.Windows.Forms.DockStyle Dock
#endregion
============================================================================
======
#else
public virtual MyCompany.Windows.Forms.DockStyle Dock
#endif
{
get
{
return dock;
}
set
{
if (dock != value)
{
dock = value;
UpdateDock();
}
}
}

#if DESIGN
#region Designer
============================================================================
protected override Size DefaultSize
#endregion
============================================================================
======
#else
protected virtual Size DefaultSize
#endif
{
get
{
return new Size(26, 26);
}
}

public ToolBarEx() { }

protected override void OnParentChanged(System.EventArgs e)
{
if (this.Parent != null)
{
UpdateDock();
this.Parent.Resize += new EventHandler(Parent_Resize);
}
base.OnParentChanged(e);
}

private void Parent_Resize(object sender, EventArgs e)
{
UpdateDock();
}

private void UpdateDock()
{
#region Adjust Bounds
====================================================================
if (this.Parent != null)
{
Size defaultSize = this.DefaultSize;
Size parentSize = this.Parent.ClientSize;
switch (this.Dock)
{
case DockStyle.None:
{
// Do nothing.
break;
}
case DockStyle.Top:
{
this.Bounds = new Rectangle(0, 0, parentSize.Width, defaultSize.Height);
break;
}
case DockStyle.Bottom:
{
this.Bounds = new Rectangle(0, (parentSize.Height - defaultSize.Height),
parentSize.Width, defaultSize.Height);
break;
}
case DockStyle.Left:
{
this.Bounds = new Rectangle(0, 0, defaultSize.Width, parentSize.Height);
break;
}
case DockStyle.Right:
{
this.Bounds = new Rectangle((parentSize.Width - defaultSize.Width), 0,
defaultSize.Width, parentSize.Height);
break;
}
}
}
#endregion
============================================================================
===
}
}
}

--
Tim Wilson
.Net Compact Framework MVP

I am creating a custom toolbar. My toolbar have a property Align. Align
put a
toolbar in top, bottom, left ou rigth.

How a get a Parent of my control in design time ?

Ex:
myToolBar.Width = Parent.Width.

Rogerio
 
Huh? That's seems to be the same issue that MacFar was reporting. Although,
I'm not having this problem. When I build a designer version of the control
and add it to the ToolBox, I can then drag and drop it onto the Form without
any problems. How are you building the design-time version of the control?

--
Tim Wilson
..Net Compact Framework MVP

Rogerio Jun said:
When I add a control in form, I receive a message "Object reference not set
to an instance of an object".

What is wrong ?

Tim Wilson said:
You shouldn't get an error message when you remove the control if you check
whether the Parent is null in the OnParentChanged method, as in the code
sample. The problem is that the control can be reparented which means that
you are not really given the opportunity to remove the handler since the
OnParentChanged method will be called once with "null", when the control is
removed from the original parent, and once with the new parent when it is
reparented. So removing in the Dispose method will work but only for the
last control that was acting as a parent. But I agree - as good practice you
should remove from an event handler that you no longer need.

--
Tim Wilson
..Net Compact Framework MVP

MacFar said:
Did you override Dispose function in this control, I am afraid that it will
fail in
design time with message "Object reference is not set"
if you will move the control form its parent, you registered the
control
in
its parent and
I do not see the cod that removes it...
this.Parent.Resize += new EventHandler(Parent_Resize);
You need to remove handler
this.Parent.Resize -= new EventHandler(Parent_Resize);
in your dispose method

Am I right?

"Tim Wilson" <TIM(UNDERSCORE)WILSON(AT)ROGERS(PERIOD)COM> wrote in message
I've put together a sample of a ToolBar control that will allow "docking"
at
both design-time and run-time. By "docking" I mean that the control is
pinned to the edge of it's parent and will be adjusted according to the
parents size. If you really wanted to get fancy you can create a custom
designer that will prevent the user from resizing the control, on the
appropriate edge, by overriding the ControlDesigner's SelectionRules
property. If you paste the code below into the VS.Net editor it might be
easier to read.

using System;
using System.ComponentModel;
using System.Drawing;
using System.Windows.Forms;

#region Designer
============================================================================
======
#if DESIGN
[assembly:
System.CF.Design.RuntimeAssemblyAttribute("MyCompany.Windows.Forms.ToolBarEx
, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null")]
#endif
#endregion
============================================================================
============

namespace MyCompany.Windows.Forms
{
public enum DockStyle
{
None = 0x00,
Top = 0x01,
Bottom = 0x02,
Left = 0x03,
Right = 0x04
}

public class ToolBarEx : System.Windows.Forms.Control
{
private MyCompany.Windows.Forms.DockStyle dock =
MyCompany.Windows.Forms.DockStyle.Top;

#if DESIGN
#region Designer
============================================================================
[
CategoryAttribute("Layout"),
DescriptionAttribute("Indicates the docking location of the control."),
DefaultValueAttribute(MyCompany.Windows.Forms.DockStyle.Top)
]
public new MyCompany.Windows.Forms.DockStyle Dock
#endregion
============================================================================
======
#else
public virtual MyCompany.Windows.Forms.DockStyle Dock
#endif
{
get
{
return dock;
}
set
{
if (dock != value)
{
dock = value;
UpdateDock();
}
}
}

#if DESIGN
#region Designer
============================================================================
protected override Size DefaultSize
#endregion
============================================================================
======
#else
protected virtual Size DefaultSize
#endif
{
get
{
return new Size(26, 26);
}
}

public ToolBarEx() { }

protected override void OnParentChanged(System.EventArgs e)
{
if (this.Parent != null)
{
UpdateDock();
this.Parent.Resize += new EventHandler(Parent_Resize);
}
base.OnParentChanged(e);
}

private void Parent_Resize(object sender, EventArgs e)
{
UpdateDock();
}

private void UpdateDock()
{
#region Adjust Bounds
====================================================================
if (this.Parent != null)
{
Size defaultSize = this.DefaultSize;
Size parentSize = this.Parent.ClientSize;
switch (this.Dock)
{
case DockStyle.None:
{
// Do nothing.
break;
}
case DockStyle.Top:
{
this.Bounds = new Rectangle(0, 0, parentSize.Width, defaultSize.Height);
break;
}
case DockStyle.Bottom:
{
this.Bounds = new Rectangle(0, (parentSize.Height - defaultSize.Height),
parentSize.Width, defaultSize.Height);
break;
}
case DockStyle.Left:
{
this.Bounds = new Rectangle(0, 0, defaultSize.Width, parentSize.Height);
break;
}
case DockStyle.Right:
{
this.Bounds = new Rectangle((parentSize.Width - defaultSize.Width), 0,
defaultSize.Width, parentSize.Height);
break;
}
}
}
#endregion
============================================================================
===
}
}
}

--
Tim Wilson
.Net Compact Framework MVP

I am creating a custom toolbar. My toolbar have a property Align. Align
put a
toolbar in top, bottom, left ou rigth.

How a get a Parent of my control in design time ?

Ex:
myToolBar.Width = Parent.Width.

Rogerio
 
Back
Top