Sdílet prostřednictvím


Zobrazení souhrnných informací v zápatí prvku GridView (C#)

Scott Mitchell

Stáhnout PDF

Souhrnné informace se často zobrazují v dolní části sestavy v souhrnném řádku. Ovládací prvek GridView může obsahovat řádek zápatí, do kterého můžeme prostřednictvím kódu programu vložit agregovaná data. V tomto kurzu se dozvíte, jak zobrazit agregovaná data v tomto řádku zápatí.

Úvod

Kromě zobrazení cen jednotlivých produktů, jednotek skladových jednotek, jednotek na objednávkách a pořadí může být uživatel také zajímat agregované informace, jako je průměrná cena, celkový počet jednotek na skladě atd. Tyto souhrnné informace se často zobrazují v dolní části sestavy v souhrnném řádku. Ovládací prvek GridView může obsahovat řádek zápatí, do kterého můžeme prostřednictvím kódu programu vložit agregovaná data.

Tento úkol představuje tři výzvy:

  1. Konfigurace prvku GridView pro zobrazení řádku zápatí
  2. Určení souhrnných dat; To znamená, jak vypočítáme průměrnou cenu nebo celkový počet jednotek v zásobách?
  3. Vložení souhrnných dat do příslušných buněk řádku zápatí

V tomto kurzu se dozvíme, jak tyto výzvy překonat. Konkrétně vytvoříme stránku se seznamem kategorií v rozevíracím seznamu s produkty vybraných kategorií zobrazenými v objektu GridView. GridView bude obsahovat řádek zápatí, který zobrazuje průměrnou cenu a celkový počet jednotek na skladě a pořadí pro produkty v dané kategorii.

Souhrnné informace se zobrazují v řádku zápatí prvku GridView.

Obrázek 1: Souhrnné informace se zobrazují v řádku zápatí GridView (kliknutím zobrazíte obrázek v plné velikosti).

Tento kurz s kategorií produktů master/detail interface vychází z konceptů popsaných v dřívějším kurzu Master/Detail Filtering With a DropDownList . Pokud jste ještě neprobrali předchozí kurz, udělejte to prosím předtím, než budete pokračovat s tímto kurzem.

Krok 1: Přidání rozevíracího seznamu kategorií a produktů GridView

Než se začneme věnovat přidávání souhrnných informací do zápatí GridView, pojďme nejprve vytvořit hlavní/podrobnou sestavu. Po dokončení tohoto prvního kroku se podíváme na to, jak zahrnout souhrnná data.

Začněte otevřením SummaryDataInFooter.aspx stránky ve CustomFormatting složce. Přidejte ovládací prvek DropDownList a nastavte jeho ID hodnotu Categories. Dále klikněte na odkaz Zvolit zdroj dat z inteligentní značky DropDownList a zvolte možnost přidat nový ObjectDataSource s názvem CategoriesDataSource , který vyvolá metodu CategoriesBLL třídy GetCategories() .

Přidání nového objektu ObjectDataSource s názvem CategoriesDataSource

Obrázek 2: Přidání nového objektu ObjectDataSource s názvem CategoriesDataSource (kliknutím zobrazíte obrázek s plnou velikostí)

Have ObjectDataSource Invoke the CategoriesBLL Class's GetCategories() – metoda

Obrázek 3: Mít ObjectDataSource Vyvolání CategoriesBLL metody třídy GetCategories() (kliknutím zobrazíte obrázek plné velikosti)

Po konfiguraci ObjectDataSource nás průvodce vrátí do Průvodce konfigurací zdroje dat DropDownList, ze kterého musíme určit, jaká hodnota datového pole by měla být zobrazena a která by měla odpovídat hodnotě rozevíracího seznamu ListItem . Zobrazí se CategoryName pole a použije CategoryID se jako hodnota.

Použijte pole CategoryName a CategoryID jako text a hodnotu pro listItems v uvedeném pořadí.

Obrázek 4: Použití CategoryName polí a CategoryID polí jako Text a Value pro ListItem s (kliknutím zobrazíte obrázek v plné velikosti)

V tuto chvíli máme rozevírací seznam (Categories), který uvádí kategorie v systému. Teď potřebujeme přidat GridView, který vypíše produkty, které patří do vybrané kategorie. Než to ale uděláme, chvíli se podívejte na zaškrtávací políčko Povolit autoPostBack v inteligentní značce DropDownList. Jak je popsáno v kurzu Filtrování předlohy/podrobností pomocí rozevíracího seznamu , nastavením vlastnosti DropDownList AutoPostBack na true stránku se publikuje zpět při každé změně hodnoty DropDownList. To způsobí, že se GridView aktualizuje a zobrazí se produkty pro nově vybranou kategorii. AutoPostBack Pokud je vlastnost nastavená na false (výchozí), změna kategorie nezpůsobí postback, a proto neaktualizuje uvedené produkty.

Zaškrtněte políčko Povolit funkci AutoPostBack v inteligentní značce rozevíracího seznamu.

Obrázek 5: Zaškrtněte políčko Povolit funkci AutoPostBack v inteligentní značce rozevíracího seznamu (kliknutím zobrazíte obrázek v plné velikosti).

Přidejte na stránku ovládací prvek GridView, aby se zobrazily produkty pro vybranou kategorii. Nastavte Objekt GridView ID ProductsInCategory a vytvořte vazbu na nový ObjectDataSource s názvem ProductsInCategoryDataSource.

Přidání nového objektu ObjectDataSource s názvem ProductsInCategoryDataSource

Obrázek 6: Přidání nového objektu ObjectDataSource s názvem ProductsInCategoryDataSource (kliknutím zobrazíte obrázek s plnou velikostí)

Nakonfigurujte ObjectDataSource tak, aby vyvolal metodu ProductsBLL GetProductsByCategoryID(categoryID) třídy.

Mít ObjectDataSource Invoke GetProductsByCategoryID(categoryID) – metoda

Obrázek 7: Vyvolání GetProductsByCategoryID(categoryID) metody ObjectDataSource (kliknutím zobrazíte obrázek s plnou velikostí)

Vzhledem k tomu, že GetProductsByCategoryID(categoryID) metoda přebírá vstupní parametr, můžeme v posledním kroku průvodce zadat zdroj hodnoty parametru. Chcete-li zobrazit tyto produkty z vybrané kategorie, mají parametr načítaný z rozevíracího Categories seznamu.

Snímek obrazovky znázorňující okno Konfigurovat zdroj dat s vybranou hodnotou parametru categoryID

Obrázek 8: Získání hodnoty parametru categoryID z rozevíracího seznamu Vybraných kategorií (kliknutím zobrazíte obrázek s plnou velikostí)

Po dokončení průvodce Bude GridView mít BoundField pro každý z vlastností produktu. Pojďme tyto pole BoundField vyčistit, aby se zobrazily pouze ProductNamepole , UnitPrice, UnitsInStocka UnitsOnOrder BoundFields. Nebojte se přidat všechna nastavení na úrovni pole do zbývajících polí BoundFields (například formátování UnitPrice jako měny). Po provedení těchto změn by deklarativní kód GridView měl vypadat nějak takto:

<asp:GridView ID="ProductsInCategory" runat="server"
    AutoGenerateColumns="False" DataKeyNames="ProductID"
    DataSourceID="ProductsInCategoryDataSource" EnableViewState="False">
    <Columns>
        <asp:BoundField DataField="ProductName" HeaderText="Product"
          SortExpression="ProductName" />
        <asp:BoundField DataField="UnitPrice" DataFormatString="{0:c}"
            HeaderText="Price"
            HtmlEncode="False" SortExpression="UnitPrice">
            <ItemStyle HorizontalAlign="Right" />
        </asp:BoundField>
        <asp:BoundField DataField="UnitsInStock"
         HeaderText="Units In Stock" SortExpression="UnitsInStock">
            <ItemStyle HorizontalAlign="Right" />
        </asp:BoundField>
        <asp:BoundField DataField="UnitsOnOrder"
           HeaderText="Units On Order" SortExpression="UnitsOnOrder">
            <ItemStyle HorizontalAlign="Right" />
        </asp:BoundField>
    </Columns>
</asp:GridView>

V tuto chvíli máme plně funkční hlavní/podrobnou sestavu, která zobrazuje název, jednotkovou cenu, jednotky na skladě a jednotky v objednávce pro produkty, které patří do vybrané kategorie.

Snímek obrazovky zobrazující sestavu GridView pro produkty, které patří do kategorie Nápoje

Obrázek 9: Získání hodnoty parametru categoryID z rozevíracího seznamu Vybraných kategorií (kliknutím zobrazíte obrázek s plnou velikostí)

Ovládací prvek GridView může zobrazit řádek záhlaví i zápatí. Tyto řádky se zobrazí v závislosti na hodnotách a vlastnostechShowHeader, v uvedeném pořadí, s ShowHeader výchozím nastavením true a ShowFooter na false.ShowFooter Chcete-li zahrnout zápatí v GridView jednoduše nastavit jeho ShowFooter vlastnost na true.

Nastavení Vlastnosti ShowFooter objektu GridView na hodnotu true

Obrázek 10: Nastavení vlastnosti GridView ShowFooter na true (Kliknutím zobrazíte obrázek v plné velikosti)

Řádek zápatí obsahuje buňku pro každé pole definované v objektu GridView; tyto buňky jsou však ve výchozím nastavení prázdné. Chvilku si prohlédněte průběh v prohlížeči. Vlastnost nyní nastavena ShowFooter na true, GridView obsahuje prázdný řádek zápatí.

GridView teď obsahuje řádek zápatí.

Obrázek 11: Objekt GridView teď obsahuje řádek zápatí (kliknutím zobrazíte obrázek v plné velikosti).

Řádek zápatí na obrázku 11 nevyniká, protože má bílé pozadí. Pojďme vytvořit FooterStyle třídu CSS, která Styles.css určuje tmavě červené pozadí a pak nakonfigurujeme GridView.skin soubor Skin v motivu DataWebControls pro přiřazení této třídy CSS k Vlastnosti GridViewFooterStyleCssClass. Pokud potřebujete střídat skiny a motivy, vraťte se k kurzu Zobrazení dat pomocí ObjectDataSource .

Začněte přidáním následující třídy CSS do Styles.css:

.FooterStyle
{
    background-color: #a33;
    color: White;
    text-align: right;
}

FooterStyle Třída CSS je podobná stylu jako HeaderStyle třída, i když HeaderStylebarva pozadí je jemně tmavší a její text se zobrazuje tučně. Text v zápatí je navíc zarovnaný doprava, zatímco text záhlaví je zarovnaný na střed.

Chcete-li přidružit tuto třídu CSS ke zápatí každého Objektu GridView, otevřete GridView.skin soubor v motivu DataWebControls a nastavte FooterStyle's CssClass vlastnost. Po přidání kódu souboru by měl vypadat takto:

<asp:GridView runat="server" CssClass="DataWebControlStyle">
   <AlternatingRowStyle CssClass="AlternatingRowStyle" />
   <RowStyle CssClass="RowStyle" />
   <HeaderStyle CssClass="HeaderStyle" />
   <FooterStyle CssClass="FooterStyle" />
   <SelectedRowStyle CssClass="SelectedRowStyle" />
</asp:GridView>

Jak ukazuje následující snímek obrazovky, tato změna zápatí jasněji vynikne.

Snímek obrazovky zobrazující souhrnná data v řádku zápatí GridView formátovaného novou barvou pozadí

Obrázek 12: Řádek zápatí objektu GridView má nyní červenou barvu pozadí (kliknutím zobrazíte obrázek v plné velikosti).

Krok 3: Výpočet souhrnných dat

Když se zobrazí zápatí GridView, dalším úkolem, kterému čelíme, je výpočet souhrnných dat. Tyto agregované informace můžete vypočítat dvěma způsoby:

  1. Prostřednictvím dotazu SQL můžeme do databáze vydat další dotaz, který vypočítá souhrnná data pro určitou kategorii. SQL obsahuje řadu agregačních funkcí spolu s GROUP BY klauzulí k určení dat, přes která se mají data sumarizovat. Následující dotaz SQL by vrátil potřebné informace:

    SELECT CategoryID, AVG(UnitPrice), SUM(UnitsInStock),
    SUM(UnitsOnOrder)
    FROM Products
    WHERE CategoryID = categoryID
    GROUP BY CategoryID
    

    Samozřejmě byste nechtěli vydat tento dotaz přímo ze SummaryDataInFooter.aspx stránky, ale spíše vytvořením metody v a ProductsTableAdapter .ProductsBLL

  2. Tyto informace vypočítá, protože se přidávají do GridView, jak je popsáno v kurzu Vlastní formátování založené na datech , obslužná rutina události GridView RowDataBound se aktivuje jednou pro každý řádek, který se přidá do GridView po příchozích datech. Vytvořením obslužné rutiny události pro tuto událost můžeme zachovat průběžný součet hodnot, které chceme agregovat. Po vazbě posledního řádku dat k objektu GridView máme součty a informace potřebné k výpočtu průměru.

Obvykle používám druhý přístup, protože šetří cestu do databáze a úsilí potřebné k implementaci souhrnných funkcí ve vrstvě přístupu k datům a vrstvě obchodní logiky, ale jeden z přístupů by stačil. Pro účely tohoto kurzu použijeme druhou možnost a pomocí obslužné rutiny události sledujme průběžný součet RowDataBound .

Vytvořte obslužnou rutinu RowDataBound události pro GridView výběrem GridView v Návrháři, kliknutím na ikonu blesku z okno Vlastnosti a poklikáním RowDataBound na událost. Tím se vytvoří nová obslužná rutina události pojmenovaná ProductsInCategory_RowDataBound ve SummaryDataInFooter.aspx třídě kódu stránky.

protected void ProductsInCategory_RowDataBound
    (object sender, GridViewRowEventArgs e)
{
}

Abychom zachovali průběžný součet, musíme definovat proměnné mimo rozsah obslužné rutiny události. Vytvořte následující čtyři proměnné na úrovni stránky:

  • _totalUnitPrice, typu decimal
  • _totalNonNullUnitPriceCount, typu int
  • _totalUnitsInStock, typu int
  • _totalUnitsOnOrder, typu int

Dále napište kód, který zvýší tyto tři proměnné pro každý řádek dat, ke kterým došlo v obslužné rutině RowDataBound události.

// Class-scope, running total variables...
decimal _totalUnitPrice = 0m;
int _totalNonNullUnitPriceCount = 0;
int _totalUnitsInStock = 0;
int _totalUnitsOnOrder = 0;
protected void ProductsInCategory_RowDataBound(object sender,
  GridViewRowEventArgs e)
{
    if (e.Row.RowType == DataControlRowType.DataRow)
    {
        // Reference the ProductsRow via the e.Row.DataItem property
        Northwind.ProductsRow product =
          (Northwind.ProductsRow)
          ((System.Data.DataRowView)e.Row.DataItem).Row;
        // Increment the running totals (if they are not NULL!)
        if (!product.IsUnitPriceNull())
        {
            _totalUnitPrice += product.UnitPrice;
            _totalNonNullUnitPriceCount++;
        }
        if (!product.IsUnitsInStockNull())
            _totalUnitsInStock += product.UnitsInStock;
        if (!product.IsUnitsOnOrderNull())
            _totalUnitsOnOrder += product.UnitsOnOrder;
    }
}

Obslužná rutina RowDataBound události začíná tím, že zajistíme, že pracujeme s DataRow. Po vytvoření je instance, Northwind.ProductsRow která byla právě svázaná s objektem GridViewRow , e.Row uložena v proměnné product. V dalším kroku se průběžné celkové proměnné zvýší o odpovídající hodnoty aktuálního produktu (za předpokladu, že neobsahují hodnotu databáze NULL ). Sledujeme průběžný UnitPrice součet i počet záznamů,NULL UnitPrice protože průměrná cena je podílem těchto dvou čísel.

S celkovým součtem souhrnných dat je posledním krokem zobrazení v řádku zápatí GridView. Tento úkol lze také provést programově prostřednictvím RowDataBound obslužné rutiny události. Vzpomeňte si, že RowDataBound obslužná rutina události se aktivuje pro každý řádek, který je svázaný s objektem GridView, včetně řádku zápatí. Proto můžeme naši obslužnou rutinu události rozšířit tak, aby zobrazovala data v řádku zápatí pomocí následujícího kódu:

protected void ProductsInCategory_RowDataBound
    (object sender, GridViewRowEventArgs e)
{
    if (e.Row.RowType == DataControlRowType.DataRow)
    {
      ... Increment the running totals ...
    }
    else if (e.Row.RowType == DataControlRowType.Footer)
    {
      ... Display the summary data in the footer ...
    }
}

Vzhledem k tomu, že se řádek zápatí přidá do objektu GridView po přidání všech řádků dat, můžeme si být jistí, že do doby, kdy jsme připraveni zobrazit souhrnná data v zápatí, budou dokončeny průběžné výpočty celkového součtu. Posledním krokem je nastavení těchto hodnot v buňkách zápatí.

Chcete-li zobrazit text v určité buňce zápatí, použijte e.Row.Cells[index].Text = value, kde Cells indexování začíná na 0. Následující kód vypočítá průměrnou cenu (celkovou cenu dělenou počtem produktů) a zobrazí ji společně s celkovým počtem jednotek v zásobách a jednotkách v příslušných buňkách zápatí gridového zobrazení.

protected void ProductsInCategory_RowDataBound
    (object sender, GridViewRowEventArgs e)
{
    if (e.Row.RowType == DataControlRowType.DataRow)
    {
      ... <i>Increment the running totals</i> ...
    }
    else if (e.Row.RowType == DataControlRowType.Footer)
    {
      // Determine the average UnitPrice
      decimal avgUnitPrice = _totalUnitPrice / (decimal) _totalNonNullUnitPriceCount;
      // Display the summary data in the appropriate cells
      e.Row.Cells[1].Text = "Avg.: " + avgUnitPrice.ToString("c");
      e.Row.Cells[2].Text = "Total: " + _totalUnitsInStock.ToString();
      e.Row.Cells[3].Text = "Total: " + _totalUnitsOnOrder.ToString();
    }
}

Obrázek 13 znázorňuje sestavu po přidání tohoto kódu. Všimněte si, ToString("c") že příčiny formátování průměrných informací o souhrnu cen, jako je měna.

Snímek obrazovky zobrazující souhrnná data v řádku zápatí GridView formátovaného jako měna

Obrázek 13: Řádek zápatí prvku GridView má nyní červenou barvu pozadí (kliknutím zobrazíte obrázek v plné velikosti).

Shrnutí

Zobrazení souhrnných dat je běžným požadavkem na sestavu a ovládací prvek GridView usnadňuje zahrnutí těchto informací do řádku zápatí. Řádek zápatí se zobrazí, když je vlastnost GridView ShowFooter nastavena true a může mít text v jeho buňkách nastaven programově prostřednictvím RowDataBound obslužné rutiny události. Výpočet souhrnných dat je možné provést opětovným dotazováním databáze nebo použitím kódu v třídě kódu stránky ASP.NET za účelem programového výpočtu souhrnných dat.

V tomto kurzu se dokončí naše zkoumání vlastního formátování pomocí ovládacích prvků GridView, DetailsView a FormView. Náš další kurz zahájí zkoumání vkládání, aktualizace a odstraňování dat pomocí těchto stejných ovládacích prvků.

Šťastné programování!

O autorovi

Scott Mitchell, autor sedmi knih ASP/ASP.NET a zakladatel 4GuysFromRolla.com, pracuje s webovými technologiemi Microsoftu od roku 1998. Scott pracuje jako nezávislý konzultant, trenér a spisovatel. Jeho nejnovější kniha je Sams Teach Yourself ASP.NET 2.0 za 24 hodin. Je dostupný na mitchell@4GuysFromRolla.comadrese . nebo prostřednictvím svého blogu, který lze najít na http://ScottOnWriting.NET.