Comment : créer des contrôles utilisateur ASP.NET avec modèles
Mise à jour : novembre 2007
Grâce à une fonctionnalité ASP.NET qui permet de séparer les données du contrôle de leur présentation, il est possible de créer des contrôles utilisateur implémentant des modèles. Un contrôle basé sur un modèle ne fournit pas d'interface utilisateur. Au lieu de cela, il est écrit pour implémenter un conteneur d'attribution de noms (naming container) et inclure une classe dont les propriétés et les méthodes sont accessibles à la page hôte.
L'interface utilisateur du contrôle utilisateur est fournie par un développeur de pages au moment du design. Le développeur crée des modèles du type défini par le contrôle utilisateur et peut ensuite y ajouter des contrôles et un balisage.
Pour créer un contrôle utilisateur basé sur un modèle
Dans le fichier .ascx, ajoutez un contrôle PlaceHolder ASP.NET à l'endroit où vous souhaitez voir le modèle s'afficher.
Dans le code du contrôle utilisateur, implémentez une propriété de type ITemplate.
Définissez une classe de contrôle serveur qui implémente l'interface INamingContainer sous la forme d'un conteneur dans lequel créer une instance du modèle. Il s'agit du conteneur d'attribution de noms (naming container) du modèle.
Remarque : Fondamentalement, ce contrôle devient une classe imbriquée du contrôle utilisateur, bien que cela ne soit pas indispensable.
Appliquez TemplateContainerAttribute à la propriété qui implémente ITemplate, puis passez le type du conteneur d'attribution de noms (naming container) du modèle au constructeur de l'attribut, en tant qu'argument.
Dans la méthode Init du contrôle, répétez les étapes suivantes une ou plusieurs fois :
Créez une instance de la classe de conteneur d'attribution de noms (naming container).
Créez une instance du modèle dans le conteneur d'attribution de noms (naming container).
Ajoutez l'instance du conteneur d'attribution de noms (naming container) à la propriété Controls du contrôle serveur PlaceHolder.
Remarque : Pour ce qui est de la page utilisant le contrôle utilisateur, la syntaxe d'un contrôle utilisateur basé sur un modèle est identique à celle d'un contrôle personnalisé avec modèles.
Exemple
L'exemple suivant montre un contrôle utilisateur basé sur un modèle, ainsi que la page qui le contient. Le contrôle utilisateur crée un modèle qui peut être déclaré dans une page hôte comme <MessageTemplate>. Le contrôle avec modèles expose également deux propriétés, Index et Message, auxquelles la page hôte peut accéder à l'intérieur du modèle.
Le premier exemple montre le contrôle utilisateur basé sur un modèle. Le deuxième montre une page contenant le contrôle utilisateur.
<%@ Control language="VB" ClassName="TemplatedUC" %>
<%@ Import Namespace="System.ComponentModel" %>
<script >
Private m_messageTemplate As ITemplate = Nothing
<TemplateContainer(GetType(MessageContainer))> _
<PersistenceMode(PersistenceMode.InnerProperty)> Public Property _
MessageTemplate() As ITemplate
Get
Return m_messageTemplate
End Get
Set(ByVal value As ITemplate)
m_messageTemplate = Value
End Set
End Property
Sub Page_Init()
If Not (MessageTemplate Is Nothing) Then
Dim i As Integer
Dim fruits() As String = _
{"apple", "orange", "banana", "pineapple"}
For i = 0 To 3
Dim container As New MessageContainer(i, fruits(i))
MessageTemplate.InstantiateIn(container)
PlaceHolder1.Controls.Add(container)
Next i
End If
End Sub
Public Class MessageContainer
Inherits Control
Implements INamingContainer
Private m_index As Integer
Private m_message As String
Friend Sub New(ByVal i As Integer, ByVal msg As String)
Me.Index = i
Me.Message = msg
End Sub
Public Property Index() As Integer
Get
Return m_index
End Get
Set(ByVal value As Integer)
m_index = value
End Set
End Property
Public Property Message() As String
Get
Return m_message
End Get
Set(ByVal value As String)
m_message = value
End Set
End Property
End Class
</script>
<asp:Placeholder ID="PlaceHolder1" />
<%@ Control language="C#" ClassName="TemplatedUC" %>
<%@ Import Namespace="System.ComponentModel" %>
<script >
private ITemplate messageTemplate = null;
[ TemplateContainer(typeof(MessageContainer)) ]
[ PersistenceMode(PersistenceMode.InnerProperty) ]
public ITemplate MessageTemplate {
get
{
return messageTemplate;
}
set
{
messageTemplate = value;
}
}
void Page_Init() {
if (messageTemplate != null) {
String[] fruits = {"apple", "orange", "banana", "pineapple" };
for (int i=0; i<4; i++)
{
MessageContainer container = new MessageContainer(i, fruits[i]);
messageTemplate.InstantiateIn(container);
PlaceHolder1.Controls.Add(container);
}
}
}
public class MessageContainer: Control, INamingContainer {
private int m_index;
private String m_message;
internal MessageContainer(int index, String message)
{
m_index = index;
m_message = message;
}
public int Index {
get
{
return m_index;
}
}
public String Message
{
get
{
return m_message;
}
}
}
</script>
<asp:Placeholder ID="PlaceHolder1" />
<%@ Page Language="VB" %>
<%@ Register TagPrefix="uc" tagname="TemplateTest"
Src="TemplatedUC.ascx" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<script >
Sub Page_Load()
DataBind()
End Sub
</script>
<head>
<title>Templated User Control Test</title>
</head>
<body>
<h1>Testing Templated User Control</h1>
<form id="Form1" >
<uc:TemplateTest >
<MessageTemplate>
Index: <asp:Label ID="Label1"
Text='<%# Container.Index %>' />
<br />
Message: <asp:Label ID="Label2"
Text='<%# Container.Message %>' />
<hr />
</MessageTemplate>
</uc:TemplateTest>
</form>
</body>
</html>
<%@ Page Language="C#" %>
<%@ Register TagPrefix="uc" tagname="TemplateTest"
Src="TemplatedUC.ascx" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<script >
protected void Page_Load()
{
DataBind();
}
</script>
<head>
<title>Templated User Control Test</title>
</head>
<body>
<h1>Testing Templated User Control</h1>
<form id="Form1" >
<uc:TemplateTest >
<MessageTemplate>
Index: <asp:Label ID="Label1"
Text='<%# Container.Index %>' />
<br />
Message: <asp:Label ID="Label2"
Text='<%# Container.Message %>' />
<hr />
</MessageTemplate>
</uc:TemplateTest>
</form>
</body>
</html>