I have in my assembly my custom control class (lets just say LogControl.vb and in Namespace: Logs.UI.WebControls, and a whole load of other supporting classes for the Designer, Actionlist, complex properties and TypeConverter.
My problem is, that when i drop my assembly into a website, and create a class in the App_Code folder that I want to inherit from LogControl, I can also see all the other supporting classes as well! So If I type: Logs.UI.WebControls....besides LogControl
class, I can also see LogControlDesigner, LogControlActionList and LogControlTypeConverter, and others that I would prefer not to be there if someone is inheriting from the LogControl class.
I don know if this is even a valid question, or whether Im jus being silly about it, but I have seen other asemblies of similar structure, with none of the other "supporting" classes visible if I inherit the main control class. Is there any way to make
these not visible? Perhaps an metadata attribute at the class-level??
use internal access modifer instead of public.. in your designer or other classes. except your main control class
you will then find. that while inheriting .. you will only see your control because it is public class and rest of the classes are invisible due to the proctection level imposed by
internal identifier
"Mark as answered if you feel this helps you"
"There are NO shortcuts for success, better stop taking one."
Ravi Kant Srivastava
Marked as answer by shalan99 on Jun 07, 2008 03:22 PM
AT: Bluearc & CallMeLann...THANK U for pointing me in that direction!...I neglected to consider the access modifiers! [:$]
AT: CallMeLann...THANK U for the VB equivalent.
However, this works perfectly for my ActionList, Designer and TypeConverter classes, but not for my Complex Property classes. On any of my complex property classes, the second I change "Public class..." to "Friend class..."
I get an error from my main Control class:
'TrackerDetails' cannot expose type 'Tracker' outside the project through class 'LogControl'.
Namespace Logs.UI.WebControls
Public Class LogControl
Public LogControlDesigner1 as LogControlDesigner
End Class
Friend Class LogControlDesigner
End Class
End Namespace
You cannot expose the LogControlDesigner1 due to it protection level.
The type of LogControlDesigner accessible within the same assembly,
so the instance LogControlDesigner1 of type LogControlDesigner also accessible only within the same assembly.
same thing apply when you inherit a public class from friend base class.
you can give an example of TrackerDetails, Tracker and LogControl.
Ok, the structure of my control assembly is as follows (I like keeping code in separate class files for organisation purposes):
1. Main Control class ("LogControl.vb" contains readonly property of "TrackerDetails")
Namespace Logs.UI.WebControls
<ToolboxData("<{0}:LogControl ID=LogControl1 runat=server></{0}:LogControl>")> _
<Designer(GetType(LogControlDesigner))> _
<ParseChildren(True)> _
Public Class LogControl : Inherits CompositeControl
#Region " CLASS DECLARATIONS "
'...
Private _Tracker As Tracker = New Tracker
'...
#End Region
#Region " STATE MANAGEMENT "
'...
#End Region
#Region " Complex Properties "
'...
<Category("Custom")> _
<DesignerSerializationVisibility(DesignerSerializationVisibility.Content)> _
<PersistenceMode(PersistenceMode.InnerProperty)> _
Public ReadOnly Property TrackerDetails() As Tracker
Get
Return _Tracker
End Get
End Property
#End Region
'... rest of class code
End Namespace
2. Tracker Complex Property class file ("Tracker.vb")
Namespace Logs.UI.WebControls
<TypeConverter(GetType(TrackerTypeConverter))> _
<Serializable()> _
Friend Class Tracker : Implements IStateManager
#Region " COMPLEX PROPERTIES "
<NotifyParentProperty(True)> _
<Category("Custom")> _
<DefaultValue(GetType(String), "")> _
Public Property TrackerFullname() As String
Get
Dim o As Object = ViewState("TrackerFullname")
If o Is Nothing Then Return String.Empty
Return DirectCast(o, String)
End Get
Set(ByVal value As String)
ViewState("TrackerFullname") = value
End Set
End Property'... rest of properties
#End Region'... rest of class code
End Namespace
Thank u very much LaNN for your help and patience!
that is because you mark property TrackerDetails() as Public but the typr is a
Friend
logically Tracker does not allow TrackerDetails to expose it outside the project/assembly.
what is the reason you mark Tracker as Friend?
simply change it as Public to remove the error.
if you just want to use the TrackerFullname() do like this
Namespace Logs.UI.WebControls
Public Class LogControl : Inherits CompositeControl
Private _Tracker As Tracker = New Tracker
'Public ReadOnly Property TrackerDetails() As Tracker
' Get
' Return _Tracker
' End Get
'End Property
Public Property TrackerFullName() As String
Get
Return _Tracker.TrackerFullname
End Get
Set(ByVal value As String)
_Tracker.TrackerFullname = value
End Set
End Property
End Namespace
'-------------------------------------------------------------------
Namespace Logs.UI.WebControls
Friend Class Tracker : Implements IStateManager
Friend Property TrackerFullname() As String
Get
Dim o As Object = ViewState("TrackerFullname")
If o Is Nothing Then Return String.Empty
Return DirectCast(o, String)
End Get
Set(ByVal value As String)
ViewState("TrackerFullname") = value
End Set
End Property
End Namespace
or you can make a new different Tracker class that is public.
OK after some digging, playing around and going bald, I managed to sort it out! [:)]For the benefit of others, let me explain where I started, what my intention was, and where I ended off.
Here is what I started off with:
·VB.Net, Framework 2.0
·I have my composite control (main class is
LogControl.vb) which works 100%.
·I have 23 custom properties, which (even after placing in categories) caused the Property Grid to still look cluttered.
·I have 2 additional classes, one called
LogControlActionList.vb and the other called LogControlDesigner.vb
for Smart-Tag support.
My desired outcome and what I did was:
·I wanted to group 4 of these properties under one Expandable Property called
TrackerDetails, so as to at least make the property grid look a little neater.
·I was able to do this with no problems, by creating a new class called
Tracker.vb
·I moved my 4 properties into that class, and overrided the state management sub-routines in both classes.
·I created a TypeConverter class called
TrackerTypeConverter.vb for a collection of my sub-properties, which returns an empty string and not the namespace of the class.
As stated, everything worked 100%, but my problem:
·In a test website with my DLL in the Bin folder, if I created a new class in App_Code and wanted it to inherit from my custom control, after I typed: “…
Inherits Logs.UI.WebControls.” I get all of my classes showing in the Intellisense box, which I didn’t want…I wanted only the LogControl.vb class to show in Intellisense.
Here is what I understood:
·Declaring a class as
Friend, will work for non-property classes such as the Designer, ActionList and TypeConverter, as these are only used within the assembly, and not modified externally.
·Declaring Tracker.vb as Friend won’t work as this contains Sub or Inner Properties which I wish for the developer to modify at design-time.
·All I wanted was for these properties to still be modifiable at design without the classes that contain the sub-properties to show up as inheritable.
Here is the solution I have settled on with the simplest little addition:
·Keeping all my properties and Complex Property classes as Public, but adding NotInheritable to the declaration.
·So: “Public
NotInheritable Class Tracker : Implements IStateManager” does the job beautifully!!
Even though I have resolved this post, I must thank u LaNN for your patience and willingness to help me out! You did help me though by pointing out the access
modifiers, which I now understand fully and have implemented for my other “helper” classes.
Regards
shalan
Marked as answer by shalan99 on Jun 10, 2008 05:33 PM
shalan99
Member
195 Points
159 Posts
Problem when inheriting from custom serv control
Jun 05, 2008 11:21 PM|LINK
Hi everyone!
I have in my assembly my custom control class (lets just say LogControl.vb and in Namespace: Logs.UI.WebControls, and a whole load of other supporting classes for the Designer, Actionlist, complex properties and TypeConverter.
My problem is, that when i drop my assembly into a website, and create a class in the App_Code folder that I want to inherit from LogControl, I can also see all the other supporting classes as well! So If I type: Logs.UI.WebControls....besides LogControl class, I can also see LogControlDesigner, LogControlActionList and LogControlTypeConverter, and others that I would prefer not to be there if someone is inheriting from the LogControl class.
I don know if this is even a valid question, or whether Im jus being silly about it, but I have seen other asemblies of similar structure, with none of the other "supporting" classes visible if I inherit the main control class. Is there any way to make these not visible? Perhaps an metadata attribute at the class-level??
Much thanks!
shalan99
CallMeLaNN
Member
70 Points
43 Posts
Re: Problem when inheriting from custom serv control
Jun 06, 2008 06:56 AM|LINK
You can give a simple example to make it clear.
You want to hide some classes within the namespace, isnt it?
It is called access modifier for class, it can also apply to method and property.
Available access modifier for VB.NET that I know:
public - accessible everywhere.
private - accessible only within the class
friend - accessible within the class, namespace and the same assembly
protected - accessible within the class and any derived classes
protected friend - same as protected, but only within same assembly
If this is what you mean, I guess this is the answer:
Namespace Logs.UI.WebControls
' Class that you want to make it visible everywhere
Public Class LogControl
End Class
' Class that you want to make it visible only in this assembly
Friend Class LogControlDesigner
End Class
End Namespace
LaNN
blurearc
Contributor
3710 Points
692 Posts
Re: Problem when inheriting from custom serv control
Jun 06, 2008 10:36 AM|LINK
use internal access modifer instead of public.. in your designer or other classes. except your main control class
you will then find. that while inheriting .. you will only see your control because it is public class and rest of the classes are invisible due to the proctection level imposed by internal identifier
"There are NO shortcuts for success, better stop taking one."
Ravi Kant Srivastava
CallMeLaNN
Member
70 Points
43 Posts
Re: Problem when inheriting from custom serv control
Jun 06, 2008 11:43 AM|LINK
note that internal is used for c# while friend is used for VB.NET.
internal and friend is the same thing.
LaNN
shalan99
Member
195 Points
159 Posts
Re: Problem when inheriting from custom serv control
Jun 07, 2008 03:37 PM|LINK
AT: Bluearc & CallMeLann...THANK U for pointing me in that direction!...I neglected to consider the access modifiers! [:$]
AT: CallMeLann...THANK U for the VB equivalent.
However, this works perfectly for my ActionList, Designer and TypeConverter classes, but not for my Complex Property classes. On any of my complex property classes, the second I change "Public class..." to "Friend class..." I get an error from my main Control class:
'TrackerDetails' cannot expose type 'Tracker' outside the project through class 'LogControl'.
Any advice please?
CallMeLaNN
Member
70 Points
43 Posts
Re: Problem when inheriting from custom serv control
Jun 08, 2008 02:30 AM|LINK
welcome
consider this example
Namespace Logs.UI.WebControls Public Class LogControl Public LogControlDesigner1 as LogControlDesigner End Class Friend Class LogControlDesigner End Class End NamespaceYou cannot expose the LogControlDesigner1 due to it protection level.
The type of LogControlDesigner accessible within the same assembly,
so the instance LogControlDesigner1 of type LogControlDesigner also accessible only within the same assembly.
same thing apply when you inherit a public class from friend base class.
you can give an example of TrackerDetails, Tracker and LogControl.
LaNN
shalan99
Member
195 Points
159 Posts
Re: Problem when inheriting from custom serv control
Jun 08, 2008 10:42 AM|LINK
Hi LaNN, Thanks for the reply!
Ok, the structure of my control assembly is as follows (I like keeping code in separate class files for organisation purposes):
1. Main Control class ("LogControl.vb" contains readonly property of "TrackerDetails")
Namespace Logs.UI.WebControls <ToolboxData("<{0}:LogControl ID=LogControl1 runat=server></{0}:LogControl>")> _ <Designer(GetType(LogControlDesigner))> _ <ParseChildren(True)> _ Public Class LogControl : Inherits CompositeControl #Region " CLASS DECLARATIONS " '... Private _Tracker As Tracker = New Tracker '... #End Region #Region " STATE MANAGEMENT " '... #End Region #Region " Complex Properties " '... <Category("Custom")> _ <DesignerSerializationVisibility(DesignerSerializationVisibility.Content)> _ <PersistenceMode(PersistenceMode.InnerProperty)> _ Public ReadOnly Property TrackerDetails() As Tracker Get Return _Tracker End Get End Property #End Region '... rest of class code End Namespace2. Tracker Complex Property class file ("Tracker.vb")
Thank u very much LaNN for your help and patience!
regards
Shalan
CallMeLaNN
Member
70 Points
43 Posts
Re: Problem when inheriting from custom serv control
Jun 10, 2008 01:05 AM|LINK
that is because you mark property TrackerDetails() as Public but the typr is a Friend
logically Tracker does not allow TrackerDetails to expose it outside the project/assembly.
what is the reason you mark Tracker as Friend?
simply change it as Public to remove the error.
if you just want to use the TrackerFullname() do like this
Namespace Logs.UI.WebControls Public Class LogControl : Inherits CompositeControl Private _Tracker As Tracker = New Tracker 'Public ReadOnly Property TrackerDetails() As Tracker ' Get ' Return _Tracker ' End Get 'End Property Public Property TrackerFullName() As String Get Return _Tracker.TrackerFullname End Get Set(ByVal value As String) _Tracker.TrackerFullname = value End Set End Property End Namespace '------------------------------------------------------------------- Namespace Logs.UI.WebControls Friend Class Tracker : Implements IStateManager Friend Property TrackerFullname() As String Get Dim o As Object = ViewState("TrackerFullname") If o Is Nothing Then Return String.Empty Return DirectCast(o, String) End Get Set(ByVal value As String) ViewState("TrackerFullname") = value End Set End Property End Namespaceor you can make a new different Tracker class that is public.
LaNN
shalan99
Member
195 Points
159 Posts
Re: Problem when inheriting from custom serv control
Jun 10, 2008 05:32 PM|LINK
Hi LaNN,
OK after some digging, playing around and going bald, I managed to sort it out! [:)] For the benefit of others, let me explain where I started, what my intention was, and where I ended off.
Here is what I started off with:
· VB.Net, Framework 2.0
· I have my composite control (main class is LogControl.vb) which works 100%.
· I have 23 custom properties, which (even after placing in categories) caused the Property Grid to still look cluttered.
· I have 2 additional classes, one called LogControlActionList.vb and the other called LogControlDesigner.vb for Smart-Tag support.
My desired outcome and what I did was:
· I wanted to group 4 of these properties under one Expandable Property called TrackerDetails, so as to at least make the property grid look a little neater.
· I was able to do this with no problems, by creating a new class called Tracker.vb
· I moved my 4 properties into that class, and overrided the state management sub-routines in both classes.
· I created a TypeConverter class called TrackerTypeConverter.vb for a collection of my sub-properties, which returns an empty string and not the namespace of the class.
As stated, everything worked 100%, but my problem:
· In a test website with my DLL in the Bin folder, if I created a new class in App_Code and wanted it to inherit from my custom control, after I typed: “… Inherits Logs.UI.WebControls.” I get all of my classes showing in the Intellisense box, which I didn’t want…I wanted only the LogControl.vb class to show in Intellisense.
Here is what I understood:
· Declaring a class as Friend, will work for non-property classes such as the Designer, ActionList and TypeConverter, as these are only used within the assembly, and not modified externally.
· Declaring Tracker.vb as Friend won’t work as this contains Sub or Inner Properties which I wish for the developer to modify at design-time.
· All I wanted was for these properties to still be modifiable at design without the classes that contain the sub-properties to show up as inheritable.
Here is the solution I have settled on with the simplest little addition:
· Keeping all my properties and Complex Property classes as Public, but adding NotInheritable to the declaration.
· So: “Public NotInheritable Class Tracker : Implements IStateManager” does the job beautifully!!
Even though I have resolved this post, I must thank u LaNN for your patience and willingness to help me out! You did help me though by pointing out the access modifiers, which I now understand fully and have implemented for my other “helper” classes.
Regards
shalan
CallMeLaNN
Member
70 Points
43 Posts
Re: Problem when inheriting from custom serv control
Jun 11, 2008 12:48 AM|LINK
Great shalan.
You done well.
Here, I look you more expert on designing composite control. Using TypeConverter and Designer.
Info and guide line from internet sometimes difficult to understand (about designing composite control and want to relate it into my project)
I just derive from system web ui control.
So can I take some guide from you?
Maybe after this we can contact by email or on another post?
I got a problem on this post Display Child Control in Property Grid - using drop down list box
I hope you can help me [;)]
LaNN