Is it normal that .Net combobox postback always contains data items? - asp.net

I have a dynamically populated ComponentArt:ComboBox with Autopostback property set to true. So every time the selection changes, a postback to server would be fired. Everything seems to work fine except that the lists of all available items are also posted back to the server.
from Firebug:
ComboBox1_Data %3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3E150%20Mile%20House%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAach%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAachen%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAaheim%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAakrehamn%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAalbeke%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAalen%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAalst%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAalter%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3E%C3%84%C3%A4nekoski%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAarau%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAarberg%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAarbergen%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAarburg%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAarebakken%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAarschot%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAarsele%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAartrijke%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAartselaar%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3Cc%3E%3Cr%3E%3Cc%3E%3Cr%3E%3Cc%3EText%3C%2Fc%3E%3Cc%3EAavasaksa%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E%3C%2Fc%3E%3C%2Fr%3E
ComboBox1_Input Aalst
ComboBox1_SelectedIndex 7
As most my clients are using slow connections, this amount of postback has a huge impact on their user experience. Since I'm storing the viewstates in session already, there's really no need for any of the component to restore states from the client. So I'm wondering if this is normal for ComponentArt:ComboBox to do this and not other controls, or this is the normal way of doing things?

Yes, it is normal for a ComboBox to do it.
You need to disable ViewState to get rid of that. That is because the ComboBox puts everything in its ViewState, not just the selection but all its items as well.

Related

Reducing the 'asyncPostBackControlIDs' list

I have a page containing a large amount of controls that can trigger postbacks to the server. I know that it is not considered good practice to have a huge amount controls on one page, but the nature of my ASP.NET web application requires it. Seeing that I have a large amount of controls on this page, I make extensive use of UpdatePanels. I am storing ViewState in Session in order to reduce the response size of the page, which works beautifully.
However, with Fiddler I noticed that the 'asyncPostBackControlIDs' after the '__VIEWSTATE' part of the ajax response contains a list of every control of every UpdatePanel that can trigger a postback. This list is huge! It seems that this list doesn't change much per page, and thus it doesn't make sense to download the entire list every time a postback within an UpdatePanel occurs...
Is there any way to store the 'asyncPostBackControlIDs' on server like you can do with ViewState, or otherwise reduce the size of the 'asyncPostBackControlIDs' list?
AFAIK, there is no documented way for storing asyncPostBackControlIDs else where - further, I am very much in doubt if there can be such possibility because most probably those control ids would be required on client side to decide whether to do regular or asynchronous post-back.
You can set ChildrenAsTriggers property of UpdatePanel to false and register controls manually that are actually triggering the post-back - for example, you may have LinkButton/HyperLink that has java-script handler.
Further, perhaps you may able to reduce the list of controls that can cause post-back. For example, you can use anchors(a) instead of linkbuttons/hyperlinks and then set a hidden variable and then simulate a (hidden) button click. On server side, the value of hidden variable would indicate the actual control responsible for post-back. This way, you can have one button that is a post-back control for many other controls.
Finally, you are really a guy who want to have very efficient request/response streams then abandon ASP.NET control model and rather use ASP.NET MVC. Or at less scale, stop using Update Panels for AJAX (they do complete POST of page and almost entire page cycle is executed at server side) and use script services (along with jquery plugins) instead.
Lastly, you need to see the control ids size with the actual response size - for example, 5K long ids within 100K response may not be a large overhead. Reducing those ids would probably give you 5% savings (if possible) but are efforts for the same worth it?

How to Persist a Control's Value/Text Property Between Page Refreshes?

I have two controls of interest on a page: a DropDownList and a Button. If the user presses the button, he gets a popup form which, when completed, causes the base page to completely reload, losing the value in the DropDownList. To clarify, it's a refresh, not a postback. I cannot change it to make it a postback. What is the most straightforward way of persisting the selected value in the DropDownList across this page refresh? I cannot avoid the page refresh, because the data entered in the popup is reflected elsewhere on the base page.
Update
I've cobbled together a tenative solution that I'm not terribly happy with: when the user clicks the button, I use javascript to get the current value of the dropdown and pass that with the querystring to the popup being loaded. When the user clicks "Save" on the popup, which causes the data to be saved then the base page to be reloaded, I first store the querystring value into a Session variable. The base page, on loading, looks at said Session variable. If a value is present, it sets the value of the dropdown accordingly and deletes the Session variable.
Although somewhat kludgy, it's the best I can come up with. I know that my Gracious Benefactors dislike using Session variables, but given the page reload, I cannot come up with an alternative. Also, since the Session variable is short-lived, being created shortly before a page is closed then being deleted shortly after the succeeding page is opened, I'm hoping this will be acceptable.
Contrasting opinions, refutating my solution or reasoning, are enthusiastically welcome.
Conclusion
Ultimately, after I described the solution to my Gracious Benefactors, we agreed upon an alternate approach: if a selection is made in the DropDownList, it must be saved before opening the popup. This avoids the whole ViewState problem altogether.
For updated question:
The solution you are trying sounds like it should work. It's not the sort of thing you want to use SessionState for but there are requirements here that make the situation out of the ordinary.
Depending on how you are getting the base page to reload you may be able to add a query string to that which would save you from putting hte value in the SessionState. But I imagine you have probably considered that.
But basically, as Postback values and viewstate are out of the question, SessionState and query strings are you only real option. Oh, unless you are allowed to use HTML5 local storage? (probably not)
From before question update:
If the aspnetForm is being posted back the the value should be persisted automatically by means of the postback values. So the first thing to know is whther your form is going through a postback or if you are refreshing the page in some other way.
If you can't postback the main form then as rockinthesixstring said an Ajax post might be what you need.
Also, if you are doing anything fancy with binding the datasource to the DropDownList or trying to persist the selectedValue yourself then check and re-think that.

Repeater Control asp.net

I have a repeater control that displays a playlist for my users, this control can sometimes hold say 1000 or more songs. This is a great feature, I was previously using jQuery to do client side sorting, but that has limitations. So I implemented server side sorting which works great, the only issue i am seeing is that when playlist are this long it takes a second or 2 before the postback and sorting is actually started.
I have watched the actions in firebug and done some research and understand that the databound values are not preserved, which makes sence. My question is, When watching in Firebug, it looks like the repeater control removes all the items in the collection before it starts the postback? is this true have others experienced this?
The repeater control ceases to exist entirely between postbacks. The repeater control is called into existance when you make a page request. It is populated, etc. then rendered to the browser. Once done, ASP.NET will delete all the objects on the page (or rather the garbage collector will get them when required. Either way, you can't get them any more).
When the postback happens it has to re-create the entire repeater all over again. There are some mechanisms, such as viewstate, that try to make this as seamless as possible (i.e. recreating controls just as you left them in the previous request) but they sometimes don't work the way you might expect.

What are the main differences of defining a control statically or creating it dynamically on page load?

I am working on a project which creates controls dynamically for a form in the page_load event, loads in their current values from the database and saves their values (using FindControl) when the user clicks the continue button.
When I added a control statically in the .aspx page and followed their same procedure of loading the value in the page load and saving it on the button press I found that the value would not save correctly. It seems that it wouldn't save because the click event fires after the page_load, so the page_load of the post back reverted the value and the user entered value was not saved.
The strange thing is that by changing the control to be dynamically created just as all the other controls on the page and keeping the loading and saving the same it now works. Even though the page load still creates the control with the old database value.
It seems like a very fundamental asp .net feature here but i'm just unclear as to what is going on. I suspect it is to do with the timing of creation and maybe when the view state kicks in.
Static page controls are created just like dynamic page controls. The difference might be coming in your Page_Load. Whenever you postback all the controls are created afresh which means they are created with their initial values. This happens because after creating the controls asp.net throws away the controls/objects.
So, when the request comes, the first thing that asp.net does it to recreate the controls by looking at their definitions (in the designer files). On each postback they are created and initialized again losing their state in the process.
But after creating the controls Asp.Net loads any viewstate that is sent along with the request which makes people think that the state is always saved at the server.
What might be happening is that either the viewstate is not enabled for your control (in case they are created in designer), in which case you may try using EnableViewState property to true of the control.
Or, when you're doing a Page_Load, you're forcefully re-initializing everything. And in process losing all the control data. If you could post the logic of Page_Load, it might get clarified.
Make sure that:
you are not setting the value again for the static control in Page_Load. The dynamic control are probably getting around it by grabbing the ViewState and form values at a different stage in the lifecycle.
The dynamic controls are added After the static control. Or at least they are added in a different container. Placement in the control's collection can affect the ViewState, although it doesn't look like your scenario / since what you mention seems to be more about the values in the current post.
The save is happening After the Page_Load in response to the corresponding event.
I've run into similar problems in the past (quite a few times actually), but what helped me the most is understanding the ASP.NET Page Lifecycle.
Microsoft has an article on it which describes it pretty well, but this post by Solomon Shaffer really cleared up everything.
I suggest reading them both and coming back with additional questions regarding to a particular state, when to load/save data etc..
Hope this helps.
Marko
Note that you may want to use Page.IsPostBack property to avoid reinitializing values on button clicks and other events.
private void Page_Load()
{
if (!this.IsPostBack)
{
// Assign values to the controls.
}
}

Determine if postback is page_load or itemcommand

I've got a user list on the left side of my page in a datagrid and I want to load a div in the right side of my page with the clicked user's information. I assume I'll do the load of the div in the itemcommand event, but how do I handle page load then? Do I need to know what caused the postback? Do I need to reload the grid on page_load as well?
how do I handle page load then?
Every postback uses a brand new instance of your page class, and completely rebuilds the page. The only thing that's different is that some controls might be pre-populated via ViewState. You don't need to repeat the load work for any of those controls.
Do I need to know what caused the postback?
ASP.Net will handle that for you and fire the event. You only need know whether it is a postback, and maybe not even that (see the next part).
Do I need to reload the grid on page_load as well?
Yes. Well, sort of. You need to re-render the html for the grid to the browser. The good news is odds are your grid data is already in viewstate and it will happen automatically. You don't need to worry about it yourself.
However, in many cases you may find that it's better to turn off viewstate for grids and reload them on each postback anyway. This is because ViewState is just a hidden input on your page that must be posted (uploaded) to the server with each request. Most internet users have very limited upload bandwidth, and so a large ViewState can make your site seem slugish, even if your server is hardly breaking a sweat.
Depending on your situation, you might do better by trading some excess server performance for site responsiveness by disabling ViewState on select controls. In this case, you will always load the grid and no longer need care whether or not a request is a postback.
By contrast, if this is an intranet application where users typically have local ethernet connections to your web server it's hard to beat ViewState for balancing responsiveness and server performance.
Exclude the grid binding with checking !IsPostBack
if(!IsPostBack){
// Bind the Grid
}
For div itemcommand you get retrieve the value of which is clicked from grid and load the user's information.
So, you will not required to load the grid everytime. It will just load first time. I dont think you will required to check what cuased the postback, because anyway you will load grid once only.

Resources