The beginning and end of the paging problem of using ListView multi-layer binding in ASP. NET

Source: Internet
Author: User

I started a website some time ago and encountered a new problem when using ListView and DataPager. First, describe the requirements of the page: There are two levels of categories, one category. Below there is a subclass, which corresponds to the product under the subclass, and then the category (which are specified) in a page) sub-classes and products are displayed by structure. The products must be displayed by page. Now, the interaction of the entire page is only on the page of the product. The main category and sub-category are only the display function on the server side. Therefore, I naturally thought of using ListView for layer-by-layer binding, add the DataPager control on the product layer for paging.

DTO in the background has also been defined, including categories, sub-categories, and products:

1 // product category DTO 2 public class ProductTypeDTO 3 {4 public int ID {get; set;} 5 //... 6 public IEnumerable <CategoryDTO> Categorys {get; set;} 7} 8 9 // product category DTO10 public class CategoryDTO11 {12 //... 13 public IEnumerable <ProductDTO> Products {get; set;} 14} 15 16 // product DTO17 public class ProductDTO18 {19 public int ID {get; set ;} 20 //... 21}

With inertial thinking, first pass the large data source to the first layer of ListView, then write the small class ListView In the first layer, and then write the product and DataPager in the small class ListView. Assume that the processed data source is IList <ProductTypeDTO> ProductTypeList, which is what we want to display.

The front-end code initially designed is:

1 <! -- Begin Types --> 2 <asp: ListView ID = "LV_Products" runat = "server"> 3 <ItemTemplate> 4 // here is the main HTML control to be parsed 5 <! -- Begin Categorys --> 6 <asp: ListView DataSource = '<% # DataBinder. eval (Container. dataItem, "Categorys") %> 'runat = "server"> 7 <ItemTemplate> 8 // here is the HTML control 9 to be parsed by the small class <! -- Begin Products --> 10 <asp: ListView ID = "LV_Item" DataSource = '<% # DataBinder. eval (Container. dataItem, "Products") %> 'runat = "server"> 11 <ItemTemplate> 12 // This is the HTML control to be parsed by a specific product 13 </ItemTemplate> 14 </asp: listView> 15 <! -- End Products --> 16 <div class = "cleardiv"> </div> 17 <! -- Begin DataPager --> 18 <div class = "product_dp"> 19 <asp: dataPager ID = "DP_Item" PageSize = "10" PagedControlID = "LV_Item" runat = "server"> 20 <Fields> 21 // This is the paging button 22 </Fields> 23 </ asp: dataPager> 24 </div> 25 <! -- End DataPager --> 26 <div class = "cleardiv"> </div> 27 <br/> 28 </ItemTemplate> 29 </asp: ListView> 30 <! -- End Categorys --> 31 <div class = "cleardiv"> </div> 32 <br/> 33 </ItemTemplate> 34 </asp: ListView> 35 <! -- End Types -->

The preceding code for binding Items unrelated to the problem is omitted. Based on previous experience, you can bind the data to the statement if you do not click twice to flip the page:

LV_Products.DataSource = ProductTypeList;
LV_Products.DataBind ();

Write it in Page_PreRender and try it in IIS. Well, the data is displayed normally, and the page has been divided, but I have nothing to do with other pages. The page flashed, the elements of the page are those on the first page. After troubleshooting, I think it is a data binding problem (BINDING IN THE PreRender will cause a data update every time, and my LV_Item is dynamically generated, dataPager is also dynamic, which will generate a brand new page instead of generating a page flip based on the previous PageIndex), So we changed the code bound to the background to be written! In IsPost, after reading it, it can be displayed on pages and clicked on pages. It seems that a jump has occurred. Unfortunately, the data cannot be normally bound and needs to be clicked twice to jump normally.

Think about ASP. NET page loading does not understand, so I carefully read its initialization process and think it is similar to Page_PreRender. I use ListView. the PreRender event should also achieve the same effect, so you need to cancel the LV_Item binding, and manually bind its data source in the background (LV_Products binding is placed! In IsPostBack ). When the page is loaded for the first time, all LV_Item data is bound. When the page is returned, only the corresponding LV_Item data source is rebound. The front-end code of LV_Item is changed:

<asp:ListView ID="LV_Item" OnPagePropertiesChanged="LV_PageChanged" runat="server">    // ...</asp:ListView>

If no, the data source binding is triggered through the ListView paging change event. The binding must occur in its PreRender event:

protected void LV_PageChanged(object sender, EventArgs e){    (sender as ListView).PreRender += LV_OnPreRender;}

Now I understand. When loading the page for the first time, all ListView will automatically trigger the OnPagePropertiesChanged event, so all ListView will load the PreRender event handler function for Data Binding. When you click back in the page, only one ListView will trigger the OnPagePropertiesChanged event, and only one ListView will load the PreRender event handler function. Therefore, only one LV_Item will occur when the source is rebound.

All right, LV_OnPreRender, as the rebinding function of LV_Item, requires information of specific categories and sub-categories to bind the product list to ListView, currently, I only have one ProductTypeList to encapsulate the relationships between large classes, small classes, and products. LV_OnPreRender and LV_PageChanged cannot obtain the list information of which small classes is the current ListView category. What should I do?

I had to find another way. Let's look at the client code generated by LV_Item:

What is found? There are naming rules! CPH_main is the parent version name I used, LV_Products is my main class ListView, and then ctl100, It is my small class ListView (not named, automatically generated), and then the following 0, there are 0th categories! Another ctl100 is my ajax UpdataPanel (not in this article, this is used in actual projects), followed by 0, 1, 2, 3... is actually a small class! Well, after testing, this is completely correct, as long as you have not changed the ClientIDMode. In the background code, we can use ListView. UniqueID to obtain a value similar to this type, but there is only one difference. The function of LV_OnPreRender is as follows:

1 private static Regex _ productRegex = new Regex (@"(? <= Ctrl) \ d + ", RegexOptions. singleline); 2 // bind the data source 3 protected void LV_OnPreRender (object sender, EventArgs e) 4 {5 var lv = sender as ListView; 6 // confirm the data source 7/* according to the specific situation, my UnitqueID is like this: 8 * Global ID ctl00 $ CPH_main $ LV_Products $ ctrl0 $ ctl00 $ ctrl0 $ LV_Item 9 * large and small Categories 10 */11 var matche = _ productRegex. match (lv. uniqueID, 25); 12 // rebind data 13 try14 {15 int categoryID = Int32.Parse (matche. nextMatch (). value); 16 int typeID = Int32.Parse (matche. value); 17 lv. dataSource = BaseConfig. productTypeList [typeID]. categorys. elementAt (categoryID ). products; 18 lv. dataBind (); 19} 20 catch21 {22 // error handling 23} 24}

At this point, paging is complete, which is very efficient. Testing on IIS is very fast. There are several hundred things. If you want to see the final result, you canClick meOpen the image link.

 

Reprinted please indicate the original address: http://www.cnblogs.com/lekko/archive/2013/04/27/3046481.html

 

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.