2009-07-17 4 views
1

J'ai une page qui a un TextBox un bouton et un Datagrid.datagrid ajouter un élément à la source de données perdre viewstate

Le but ici est simple: chaque fois que je saisis quelque chose dans le TextBox et que j'appuie sur le bouton, il vérifie un peu puis ajoute l'élément à la grille de données et à une source de données de logique métier.

Le problème est, si je veux faire apparaître l'élément dans le DataGrid, je dois faire un datagrid.DataSource = myBusinessObject; datagrid.DataBind(); problème avec cela est que je perds le viewstate et le choix dans le radiobox que l'utilisateur a fait.

Voici le modèle:

  <asp:TextBox ID="txtDomain" runat="server" style="margin-bottom: 0px" 
       Width="254px"></asp:TextBox> 
       &nbsp;<asp:Button ID="domainAdd" runat="server" onclick="domainAdd_Click" 
       style="height: 26px" Text="Ajouter" /> 
      &nbsp;<br /> 
      <br /> 
      <asp:DataGrid ID="dg1" runat="server" AutoGenerateColumns="false"> 
       <Columns> 
        <asp:BoundColumn DataField="Name" HeaderText="Nom choisi"></asp:BoundColumn> 
        <asp:TemplateColumn HeaderText="Enregistrer"> 
         <ItemTemplate> 
          <asp:RadioButton ID="register" runat="server" GroupName="domaine_action" Checked='<%# Bind("IsRegister")%>' Enabled='<%# Bind("CanRegister")%>' /> 
         </ItemTemplate> 
        </asp:TemplateColumn> 
        <asp:TemplateColumn HeaderText="Transférer"> 
         <ItemTemplate> 
          <asp:RadioButton ID="transfert" runat="server" GroupName="domaine_action" Checked='<%# Bind("IsTransfert")%>' Enabled='<%# Bind("CanTransfert")%>' /> 
         </ItemTemplate> 
        </asp:TemplateColumn> 
        <asp:TemplateColumn HeaderText="Gérer moi même"> 
         <ItemTemplate> 
          <asp:RadioButton ID="manage" runat="server" GroupName="domaine_action" Checked='<%# Bind("IsSelfManaged")%>' Enabled='<%# Bind("CanSelfManage")%>' /> 
         </ItemTemplate> 
        </asp:TemplateColumn> 
       </Columns> 
      </asp:DataGrid> 

Le code derrière:

protected void domainAdd_Click(object sender, EventArgs e) 
    { 
     if (Session["dic"] != null) 
     { 
      var _dic = (List<Test1>)Session["dic"]; 

      _dic.Add(new Test1 { Name = txtDomain.Text }); 

      dg1.DataSource = _dic; 
      dg1.DataBind(); 

      Session["dic"] = _dic; 
     } 
     else 
     { 
      List<Test1> _dic = new List<Test1>(); 

      _dic.Add(new Test1 { Name = txtDomain.Text }); 

      dg1.DataSource = _dic; 
      dg1.DataBind(); 

      Session["dic"] = _dic; 
     } 

Pour l'instant l'objet est juste une Test1 petite classe pour mapper des champs pour la logique métier.

public class Test1 
{ 
    public string Name { get; set; } 

    public string IsRegister { get; set; } 
    public string IsTransfert { get; set; } 
    public string IsSelfManaged { get; set; } 

    public string CanRegister { get; set; } 
    public string CanTransfert { get; set; } 
    public string CanSelfManage { get; set; } 
} 

donc je suppose que la question directe serait la suivante: Comment ajouter des éléments à la grille & l'objet métier sans perdre les choix de radioboxes dans la grille.

+0

En fait, j'ai essayé de ne pas faire datagrid.Datasource = "something" et datagrid.DataBind(); quand il y a un postback ... mais l'objet n'est pas ajouté de cette façon ... – Erick

Répondre

2

Vous devez enregistrer l'état des radiobox dans votre objet de gestion avant en ajoutant un nouvel élément dans la liste, de sorte que lorsque vous le liez à nouveau, les choix seront reflétés dans la grille de données.
Si vous faites cela, vous pourriez aussi bien désactiver le ViewState pour la grille ...

+0

yep fonctionne de cette façon = D pas exactement propre mais fonctionne définitivement :) – Erick

0

Votre DataGrid lie son RadioButton aux propriétés de Test1, donc si vous définissez les conséquence, devrait-il pas garder le choix sélectionné.

Je ne suis pas un gars ASP.NET et j'espère que quelqu'un de plus intelligent que moi vous aide, mais puisque personne ne répond. Je vais essayer. Vos boutons radio sont liés à votre propriété Test1.IsRegister, ce qui signifie que pour conserver leur état, vous devez définir cette propriété sur true ou false. Changez d'abord votre classe Test1 pour qu'elle contienne des booles au lieu de chaînes. Pour l'instant je place CanRegister à toujours vrai, vous pouvez changer la logique plus tard.

public class Test1 
    { 
     public string Name { get; set; } 

     public bool IsRegister { get; set; } 
     public bool IsTransfert { get; set; } 
     public bool IsSelfManaged { get; set; } 

     public bool CanRegister { get { return true; } } 
     public bool CanTransfert { get { return true; } } 
     public bool CanSelfManage { get { return true; } } 
    } 

Maintenant, vous devez enregistrer chaque fois que quelqu'un appuie sur un RadioButton, vous devez créer un gestionnaire d'événements et définissez AutoPostBack true.

<asp:RadioButton OnCheckedChanged="register_checked" AutoPostBack="true" ID="register" runat="server" GroupName="domaine_action" Checked='<%# Bind("IsRegister")%>' Enabled='<%# Bind("CanRegister")%>' /> 

Maintenant, le gestionnaire d'événements register_checked. Il s'agit de la partie où vous prenez la valeur de la propriété RadioButton.Checked et réglez-la sur l'élément de votre Liste.

protected void register_checked(object sender, EventArgs e) 
     { 
      //make sure you have a list 
      if(Session["dic"] == null) 
       return; 

      List<Test1> _dic = (List<Test1>)Session["dic"]; 
      RadioButton btn = sender as RadioButton; 
      string btnClientId = btn.ClientID; 

      //make sure cast didnt crash 
      if (btn == null) 
       return; 

      foreach (DataGridItem control in dg1.Items) 
      { 
       //find the register RadioButton, ID="register" 
       var item = control.FindControl("register"); 
       //make sure its the right RadioButton 
       if (item.ClientID.Equals(btnClientId)) 
       { 
        //get the item index of this DataGridItem and take the appropriate object for List<Test1> 
        Test1 realItem = _dic[control.ItemIndex] as Test1; 
        if (realItem == null) 
         continue; 

        //set the Items IsRegister to the button value. 
        realItem.IsRegister = btn.Checked; 
       } 
      } 

     } 

La raison pour laquelle vous devez faire tout cela est parce que vos RadioButton s font partie d'un ItemTemplate et sont liés à une DataGrid, ce qui signifie qu'il y aura potentiellement beaucoup DataGridItem s et donc beaucoup RadioButton s avec le même identifiant "register". C'est pourquoi vous ne pouvez pas y accéder à partir du code-behind.

Cela permettra de préserver l'état du RadioButton s. J'espère que cela vous aide.