Ottenere valore da una cella da una visualizzazione griglia sull'evento RowDataBound

StackOverflow https://stackoverflow.com/questions/121722

  •  02-07-2019
  •  | 
  •  

Domanda

string percentage = e.Row.Cells[7].Text;

Sto provando a fare alcune cose dinamiche con il mio GridView, quindi ho collegato del codice all'evento RowDataBound. Sto cercando di ottenere il valore da una cella particolare, che è un TemplateField. Ma il codice sopra sembra sempre restituire una stringa vuota.

Qualche idea?

Per chiarire, ecco un po 'la cella offensiva:

<asp:TemplateField HeaderText="# Percentage click throughs">
<ItemTemplate>
    <%# AddPercentClickThroughs((int)Eval("EmailSummary.pLinksClicked"), (int)Eval("NumberOfSends")) %>
</ItemTemplate>
</asp:TemplateField>

In una nota correlata, qualcuno sa se esiste un modo migliore di selezionare la cella nella riga. Fa schifo mettendo cell[1]. Non potrei farlo cell["mycellname"], quindi se decido di cambiare l'ordine delle mie celle, i bug non appariranno?

È stato utile?

Soluzione

Per prima cosa devi racchiudere il codice in un controllo Label o Literal in modo da poterlo fare correttamente riferimento. Quello che sta succedendo è che non c'è modo per il sistema di tenerne traccia, perché non c'è controllo associato al testo. È responsabilità del controllo aggiungere i suoi contenuti a viewstate.

Devi usare gridView.FindControl (" controlName "); per ottenere il controllo nella riga. Da lì puoi accedere alle sue proprietà tra cui Text.

Puoi anche accedere alla proprietà DataItem della riga in questione e lanciarla nel tipo appropriato ed estrarre direttamente le informazioni.

Altri suggerimenti

perché non estrarre i dati direttamente dall'origine dati.

DataBinder.Eval(e.Row.DataItem, "ColumnName")

Quando usi TemplateField e ti leghi il testo letterale come stai facendo, asp.net inserirà effettivamente un controllo PER TE! Viene inserito in un DataBoundLiteralControl. Puoi vederlo se cerchi nel debugger vicino alla tua riga di codice che sta ottenendo il testo vuoto.

Quindi, per accedere alle informazioni senza cambiare il tuo modello per usare un controllo, devi lanciare in questo modo:

string percentage = ((DataBoundLiteralControl)e.Row.Cells[7].Controls[0]).Text;

Questo ti porterà il tuo testo!

Quanto sopra sono buoni suggerimenti, ma puoi ottenere il valore del testo di una cella in una vista a griglia senza racchiuderlo in un controllo letterale o etichetta. Devi solo sapere quale evento collegare. In questo caso, utilizzare invece l'evento DataBound, in questo modo:

protected void GridView1_DataBound(object sender, GridViewRowEventArgs e)
{
    if (e.Row.RowType == DataControlRowType.DataRow)
    {
        if (e.Row.Cells[0].Text.Contains("sometext"))
        {
            e.Row.Cells[0].Font.Bold = true;
        }
    }
}

Quando esegui un debugger, vedrai apparire il testo in questo metodo.

Basta usare un ciclo per controllare la tua cella in una griglia, ad esempio:

for (int i = 0; i < GridView2.Rows.Count; i++)
{
    string vr;
    vr = GridView2.Rows[i].Cells[4].Text; // here you go vr = the value of the cel
    if (vr  == "0") // you can check for anything
    {
        GridView2.Rows[i].Cells[4].Text = "Done";
        // you can format this cell 
    }
}

usa la funzione RowDataBound per associare i dati a una particolare cella e ottenere il controllo (Nome controllo ASP come DropDownList) GridView.FindControl("Name of Control")

Avevo una domanda simile, ma ho trovato la soluzione con un approccio leggermente diverso. Invece di cercare il controllo come suggerito da Chris, ho prima cambiato il modo in cui il campo è stato specificato nella pagina aspx. Invece di utilizzare un tag <asp:TemplateField ...>, ho modificato il campo in questione per utilizzare <asp:BoundField ...>. Quindi, quando sono arrivato all'evento RowDataBound, è stato possibile accedere direttamente ai dati nella cella.

I frammenti rilevanti: in primo luogo, la pagina aspx:

<asp:GridView ID="gvVarianceReport" runat="server" ... >
...Other fields...
    <asp:BoundField DataField="TotalExpected" 
     HeaderText="Total Expected <br />Filtration Events" 
     HtmlEncode="False" ItemStyle-HorizontalAlign="Left" 
     SortExpression="TotalExpected" />
...
</asp:Gridview>

Quindi, nell'evento RowDataBound, posso accedere direttamente ai valori:

protected void gvVarianceReport_Sorting(object sender, GridViewSortEventArgs e)
{
    if (e.Row.Cells[2].Text == "0")
    {
        e.Row.Cells[2].Text = "N/A";
        e.Row.Cells[3].Text = "N/A";
        e.Row.Cells[4].Text = "N/A";
    }
}

Se qualcuno potesse commentare perché questo funziona, lo apprezzerei. Non capisco perfettamente perché senza BoundField il valore non sia nella cella dopo il bind, ma è necessario cercarlo tramite il controllo.

Label lblSecret = ((Label)e.Row.FindControl("lblSecret"));
<asp:TemplateField HeaderText="# Percentage click throughs">
  <ItemTemplate>
    <%# AddPercentClickThroughs(Convert.ToDecimal(DataBinder.Eval(Container.DataItem, "EmailSummary.pLinksClicked")), Convert.ToDecimal(DataBinder.Eval(Container.DataItem, "NumberOfSends")))%>
  </ItemTemplate>
</asp:TemplateField>


public string AddPercentClickThroughs(decimal NumberOfSends, decimal EmailSummary.pLinksClicked)
{
    decimal OccupancyPercentage = 0;
    if (TotalNoOfRooms != 0 && RoomsOccupied != 0)
    {
        OccupancyPercentage = (Convert.ToDecimal(NumberOfSends) / Convert.ToDecimal(EmailSummary.pLinksClicked) * 100);
    }
    return OccupancyPercentage.ToString("F");
}

Se imposti l'attributo Visibile sull'asp: BoundField su Falso . In questo modo

<asp:BoundField DataField="F1" HeaderText="F1" Visible="False"/>

Non otterrai alcun testo nelle celle [i]. Proprietà Testo quando esegui il ciclo delle righe. Quindi

foreach (GridViewRow row in myGrid.Rows)
{
  userList.Add(row.Cells[0].Text); //this will be empty ""
}

Ma puoi impostare una colonna non visibile collegando la griglia all'evento OnRowDataBound, quindi da qui fai

e.Row.Cells[0].Visible = false //now the cell has Text but it's hidden
protected void gvbind_RowDataBound(object sender, GridViewRowEventArgs e)
{
    if (e.Row.RowType == DataControlRowType.DataRow)
    {
        e.Row.Attributes["onmouseover"] = "this.style.cursor='hand';";
        e.Row.Attributes["onmouseout"] = "this.style.textDecoration='none';";
        e.Row.Attributes["onclick"] = ClientScript.GetPostBackClientHyperlink(this.gvbind, "Select$" + e.Row.RowIndex);
    }
}
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top