I've just created a base class for my pages by inheriting from System.Web.UI.Page:
public abstract class PageBase : System.Web.UI.Page
{
...
}
When I noticed that you can also declare a base page in an ASP.NET view:
<%# Page Language="C#" CodeFileBaseClass="PageBase.cs" CodeFile="page.aspx.cs"
Inherits="page" %>
Can someone explain what the pros and cons of either method are? When would you use one over the other, or are they both the same? What happens if you used both at the same time?
CodeFileBaseClass, CodeFile, Inherits work together with inheritance, not in place of inheritance.
For example, specifying CodeFile="page.aspx.cs" without page.aspx.cs existing will result in:
Parser Error Message: The file '/page.aspx.cs' does not exist.
Assuming page.aspx.cs exists, specifying CodeFileBaseClass="PageBase.cs" without PageBase.cs existing will result in:
Parser Error Message: Could not load type 'PageBase.cs'.
On the other hand you may inherit from PageBase without specifying the CodeFileBaseClass attribute. This however could result in possible unexpected behaviour when referencing controls on the page from the base class.
To quote from Microsoft's #Page MSDN Documentation:
CodeFileBaseClass
Specifies the type name of a base class for a page and its associated code-behind class. This attribute is optional, but when it is used the
CodeFile attribute must also be present. Use this attribute when you want to implement a shared scenario, where you define common
fields (and optionally, associated events) in a base class to
reference the controls declared in a Web page. Because of the ASP.NET
code generation model, if you defined the fields in a base class
without using this attribute, at compile time new member definitions
would be generated for the controls declared in the Web page (within a
separate partial class stub), and your desired scenario would not
work. But if you use the CodeFileBaseClass attribute to associate
the base class with the page, and you make your partial class (its
name is assigned to the Inherits attribute and its source file is
referenced by the CodeFile attribute) inherit from the base class,
then the fields in the base class will be able to reference the
controls on the page after code generation.
Related
Bit of a confusion for me here. This is ASP.NET 4.0. Looking at the markup, it appears that Default.aspx inherits from Site.Master page. But looking at the class definition of Default.aspx (which is named _Default), it inherits from Page class and not SiteMaster.
Now I need to share a few functions across multiple inherited pages and was looking to add them to SiteMaster class so that they would be available in all inherited pages. Can I use SiteMaster class for my purpose, or should I add an independent module to my project and add all my functions to that?
Figured it out. For anyone else looking for a solution, all you need to do is to add the following directive to your markup:
<%# MasterType VirtualPath="~/Site.Master" %>
You can add this line to the top of ASPX file, just under the <%# Page ... %> line. Once added, simply rebuild your project. Now all the public members of your master page class will become available through the strongly-typed member named Master. For example, you can now use the following code to access a public function called MyFunc() defined in the master page class:
this.Master.MyFunc(); //C#
Me.Master.MyFunc() 'VB.NET
MasterType directive actually adds a shadowing member named Master that is strongly-typed as SiteMaster class (or whatever master page class you have specified) when spitting the code-behind class. This new member hides the base class member (whose type is the generic MasterPage class) and thus allows you to access your master page members directly. The property is defined in the .aspx.Designer.cs/vb file like this:
Public Shadows ReadOnly Property Master() As YourProjectNamespace.SiteMaster
Get
Return CType(MyBase.Master, TagTrakkerOnline2.SiteMaster)
End Get
End Property
Is it possible to create a base class that can be inherited from an Asp.Net Page and a UserControl. I know that Page inherits from System.Web.UI.Page and controls inherit from System.Web.UI.UserControl so I couldn't come up with a base class that could be used for sharing common code (instead of repeating same code in several spots).
True multiple inheritance is not supported in .NET. But you could create a base page class and place common code there. Then create a base class for controls which would have a (protected) property that would cast current page to the base page. This gives access from within a user control to the public properties of the base page class.
Currently my code resembles this:
<%# Control Language="C#" AutoEventWireup="true" CodeBehind="CustomPanel.ascx.cs"
CodeFile="CustomPanel.ascx.cs" CodeFileBaseClass="System.Web.UI.WebControls.Panel"
Inherits="MyProject.CustomPanel" %>
...
namespace MyProject
{ public partial class CustomPanel : System.Web.UI.WebControls.Panel
{ ... }
}
However, I'm really not sure how to proceed from here, because this does not appear to follow a logical inheritance path that includes System.Web.UI.UserControl
Am I doing something wrong? How can I inherit Panel and extend standard event-handlers, such as PreInit?
Are you wanting to extend or encapsulate a Panel here?
Extending it would be done not with a User Control, but with a normal class file, with the class inheriting from Panel.
Encapsulating it would be done in a User Control, as appears to be what you have done here; In such a case, you put a Panel instance inside the User Control's ascx file... you do not attempt to inherit from it.
It actually looks like you are trying to do both at the same time; you shouldn't do that. There is no direct inheritance path as you seem to be looking for that contains both Usercontrol and Panel; you'll have to choose one of the above options or the other.
To extend it, you should create a new class, which inherits the System.Web.UI.WebControls.Panel class. Once you have created your custom class, you can override existing methods from the Panel class, which are marked as virtual. (Typing the keyword override in Visual Studio, while inside your class, will pop up a list of virtual methods)
Compiler Error Message: ASPNET: Make sure that the class defined in this code file matches the 'inherits' attribute, and that it extends the correct base class (e.g. Page or UserControl).
in vb code-i used namespace and a class.
The Inherits attribute in the Page directive of the aspx page must point to a class that implements the code-behind logic. If you have used extra namespaces, you will need to supply the fully qualified type name, so that it matches:
Inherits="The.Full.Namespace.Path.TheClassName"
Do we have to do something special to have ASP.NET partial classes aware of controls that are declared in our user control's base classes? The partial classes keep generating declarations for controls in the base class which mean the controls in the base class get hidden and are null.
The CodeFileBaseClass attribute can be applied to #Page or #Control declarations to make the ASP.NET runtime aware of any controls declared in your base class.
MSDN describes it as follows:
Specifies the type name of a base class for a page and its associated
code-behind class.
This attribute is
optional, but when it is used the
CodeFile attribute must also be
present. Use this attribute when you
want to implement a shared scenario,
where you define common fields (and
optionally, associated events) in a
base class to reference the controls
declared in a Web page. Because of the
ASP.NET code generation model, if you
defined the fields in a base class
without using this attribute, at
compile time new member definitions
would be generated for the controls
declared in the Web page (within a
separate partial class stub), and your
desired scenario would not work. But
if you use the CodeFileBaseClass
attribute to associate the base class
with the page, and you make your
partial class (its name is assigned to
the Inherits attribute and its source
file is referenced by the CodeFile
attribute) inherit from the base
class, then the fields in the base
class will be able to reference the
controls on the page after code
generation.