次の方法で共有


Dynamically adding webparts to the dynamically added Catalog zone

Today we are going to discuss how to add webparts to a Catalog Zone dynamically in your webpage.

Sometimes, you may have quite a lot of different webparts which you don't want to add by default to any page. Instead, you want to design an interface where you have added everything into your catalog zone dynamically. This way, users have the option to simply populate those webparts which they like. It seems like there is no *easy* way to achieve this, so you have to plan accordingly to fulfill this requirement. Before I say anything else, let me point you to a link which will explain you quite a lot about webparts and no wonder I have derived some code directly from that link to make things easier.

Introducing the ASP.NET 2.0 Web Parts Framework.

A piece of advice, if time permits (and if you are not already comfortable with the webparts stuff), go through the above link and then proceed to the remaining part of this...

OK, cool... Let's begin...

Create a New Website in VS 2005. You will have a page called default.aspx. Lets delete it! We will add another page called Default.aspx, but ensure that there is no codebehind. You can do this by ensuring that when you are adding a new Web Form, the checkbox Place code in seperate file is UNCHECKED. Now, in the source view of the Default.aspx, delete everything and paste the following...

<%@ Page Language="vb" %>
<script runat="server">
Sub CustomizePage(ByVal s As Object, ByVal e As EventArgs)
WebPartManager1.DisplayMode = WebPartManager.CatalogDisplayMode
End Sub
Sub EditWebParts(ByVal s As Object, ByVal e As EventArgs)
WebPartManager1.DisplayMode = WebPartManager.EditDisplayMode
End Sub
Protected Sub Page_Init(ByVal sender As Object, ByVal e As System.EventArgs)
Dim dynamicCatalog As New CatalogZone
dynamicCatalog.ZoneTemplate = New CustomZoneTemplate()
dynamicCatalog.ID = "DynamicCatalog"
Ph1.Controls.Add(dynamicCatalog)
End Sub
</script>
<html>
<head id="Head1" runat="server">
<title>Home Page</title>
</head>
<body bgcolor="gray">
<form id="form1" runat="server">
<asp:WebPartManager
ID="WebPartManager1"
Runat="Server" />
<table width="100%" Height="100%" cellpadding="5" cellspacing="10">
<tr height="50">
<td colspan="3" align="right" bgcolor="white" style="height: 50px">
<asp:LinkButton ID="LinkButton1"
Text="Customize Page"
OnClick="CustomizePage"
Runat="Server" />
|
<asp:LinkButton ID="LinkButton2"
Text="Edit Web Parts"
OnClick="EditWebParts"
Runat="Server" />
</td>
</tr>
<tr>
<td valign="top" bgcolor="white" width="40%">
<asp:WebPartZone
ID="WebPartZone1"
Width="100%"
HeaderStyle-BackColor="lightblue"
PartTitleStyle-BackColor="silver"
Runat="Server" >
<HeaderStyle BackColor="LightBlue" />
<PartTitleStyle BackColor="Silver" />
</asp:WebPartZone>
</td>
<td valign="top" bgcolor="white" width="40%">
<asp:WebPartZone
ID="WebPartZone2"
Width="100%"
HeaderStyle-BackColor="lightblue"
PartTitleStyle-BackColor="silver"
Runat="Server" >
<HeaderStyle BackColor="LightBlue" />
<PartTitleStyle BackColor="Silver" />
</asp:WebPartZone>
</td>
<td valign="top" width="20%" bgcolor="white">
<asp:PlaceHolder runat=server ID="Ph1"></asp:PlaceHolder>
</td>
</tr>
</table>
</form>
</body>
</html>

Add three new classes (in your App_code folder) called CustomProduct.vb, CustomWebPartTemplate.vb and CustomZoneTemplate.vb. Now, paste the following code accordingly.

CustomProduct.vb

Imports System.Collections
Imports System.Data
Imports System.Data.SqlClient
Imports System.Web.UI
Imports System.Web.UI.WebControls.WebParts
Public Class CustomProduct
Inherits WebPart
Const connectionString As String = _
"Server=localhost;Trusted_Connection=True;Database=Northwind"
Const selectString As String = "SELECT * FROM Products " & _
"JOIN Categories ON Products.CategoryID=Categories.CategoryID"
Private _categoryName As String = "Beverages"
Public Sub New()
MyBase.Title = "Custom Product"
End Sub
Public Overrides ReadOnly Property Verbs() As WebPartVerbCollection
Get
' Create Beverages verb
Dim verb1 As New WebPartVerb("verb1", New _
WebPartEventHandler(AddressOf ChangeCategory))
verb1.Text = "Beverages"
verb1.Description = "Displays Beverages Products"
' Create Seafood verb
Dim verb2 As New WebPartVerb("verb2", New _
WebPartEventHandler(AddressOf ChangeCategory))
verb2.Text = "Seafood"
verb2.Description = "Displays Seafood Products"
' Create collection of verbs
Dim newVerbs() As WebPartVerb = {verb1, verb2}
' Return WebPartVerbCollection including base verbs
Return New WebPartVerbCollection(newVerbs)
End Get
End Property
Public Sub ChangeCategory(ByVal s As Object, ByVal e As WebPartEventArgs)
Dim newCategory As String = s.Text
Me.CategoryName = newCategory
Me.Title = String.Format("Featured Product - {0}", newCategory)
End Sub
<Personalizable(), WebBrowsable()> _
Public Property CategoryName() As String
Get
Return _categoryName
End Get
Set(ByVal value As String)
_categoryName = value
End Set
End Property
Protected Overrides Sub RenderContents(ByVal writer _
As HtmlTextWriter)
' Load Products into DataTable
Dim productTable As New DataTable()
Dim dad As New SqlDataAdapter(selectString, _
connectionString)
dad.Fill(productTable)
' Filter the DataTable with a Category
Dim productView As DataView = productTable.DefaultView
productView.RowFilter = "CategoryName='" & _categoryName & "'"
If productView.Count = 0 Then
Return
End If
' Randomly select a row
Dim rnd As New Random()
Dim row As DataRowView = _
productView(rnd.Next(productView.Count))
' Render the row
writer.Write(row("ProductName").ToString())
writer.Write(String.Format("- {0:c}", row("UnitPrice")))
End Sub
End Class

CustomWebPartTemplate.vb

Public Class CustomWebPartTemplate
Implements ITemplate
Dim Product1 As CustomProduct
Dim Product2 As CustomProduct
Public Sub InstantiateIn(ByVal container As System.Web.UI.Control) _
Implements System.Web.UI.ITemplate.InstantiateIn
'
Product1 = New CustomProduct
Product1.ID = "CustomProduct1"
Product1.Title = "Custom Product 1"
container.Controls.Add(Product1)
Product2 = New CustomProduct
Product2.ID = "CustomProduct2"
Product2.Title = "Custom Product 2"
container.Controls.Add(Product2)
End Sub
End Class

CustomZoneTemplate.vb

Public Class CustomZoneTemplate
Inherits WebPart
Implements ITemplate
Public Sub InstantiateIn(ByVal container As System.Web.UI.Control) _
    Implements System.Web.UI.ITemplate.InstantiateIn
'
Dim DeclCatalogPart As New DeclarativeCatalogPart
Dim PgCatalogPart As New PageCatalogPart
PgCatalogPart.ID = "MyPageCatalog"
PgCatalogPart.Title = "My Page Catalog Title"
DeclCatalogPart.WebPartsTemplate = New CustomWebPartTemplate()
DeclCatalogPart.ID = "MyDeclarativeCatalog"
DeclCatalogPart.Title = "My Declarative Catalog Title"
container.Controls.Add(PgCatalogPart)
container.Controls.Add(DeclCatalogPart)
End Sub
End Class

If you switch to the design view of default.aspx you will see that there are two Zones created at design time and in the third column you will see a simple Placeholder. This is where our Catalogzone will get created and loaded at runtime. Once you run the project you will see something like this...

Now, click on "Customize Page" link and you should be able to see the dynamically added webparts with appropriate titles like the following...

Happy Programming :o)

-Rahul Soni

HomePage.GIF

Comments

  • Anonymous
    March 20, 2006
    Trackback from dotnetkicks.com

  • Anonymous
    March 21, 2006
    News

    Great list of Portable Apps for your USB drive on Wikipedia
    Microsoft Visual Studio 2005 - Update...

  • Anonymous
    March 28, 2006

    I had an issue where I was changing a WebPartManger's displaymode using the following code...
    WebPartManager1.DisplayMode...

  • Anonymous
    April 05, 2006
    Anton

  • Anonymous
    April 06, 2006
    Well, my personal favorite has always been winamp!

  • Anonymous
    October 04, 2006
    I had an issue where I was changing a WebPartManger's displaymode using the following code... WebPartManager1.DisplayMode

  • Anonymous
    February 14, 2007
    Its so nice. and i need one more help from you. i have the same type of requirement. in my requirement i have some web user controls. and i want to load those controls dynamically to the DeclCatalogPart. so can you please help me to solve this issue.

  • Anonymous
    February 14, 2007
    Hi Ram, Thanks! Regarding your query, if you create an ASCX page and use it to dynamically load the controls, and then load that ascx control in the DeclCatalogPart, things should work fine. HTH, Rahul

  • Anonymous
    May 09, 2007
    hi, when i load ASCX page work fine. but i want to pass a value to ASCX page and that is not working for me or i don't know how to do it. Thanks,

  • Anonymous
    December 17, 2008
    hi , I develop  the web parts for user to personalize But i want to Administrator set the Web part for per role web parts And user login it's only see whichever web parts set by administrator.. Is it possible.... ? Plz Reply if u know :  hirensagar007@yahoo.com

  • Anonymous
    January 28, 2009
    Hi, I am trying to add dynamic Panels into the WebPartZone. The Panels also has hyperlinks added as a control into it. But when I try to add Panels as Generic Web Part into the webpartzone, The panel gets displayed but the hyperlink inside the panel doesn't get displayed. Please help..

  • Anonymous
    September 22, 2009
    Best and rare artical found on ,net. It help me lot.. I am developing dashboard with webpart. I wanted to add controls dynamically.. I have one small question. Right now, I am using user controls to add as a web parts. Is there any major disadvantage if I used user controls instead of custom webpart class for rendering? Waiting 4 reply..