0

I have a function in server side which fills a dropdownlist. I call this function with a button click on client side using PageMethods in Javascript like this:

<asp:ScriptManager ID="smMain" runat="server" EnablePageMethods="true" />
<asp:Button runat="server" ID="SearchButton" Text="Search" OnClientClick="SearchButtonClick();return false;"/>
<asp:DropDownList runat="server" ID="SearchCityDropDownList" Width="100px"/>

And

function SearchButtonClick() {
        PageMethods.SearchSearchButtonActivity(onSucess, onError);
    }
    function onSucess(result) {
        alert(result);
    }
    function onError(result) {
        alert('Cannot process your request at the moment, please try later.');
    }

Server side function:

[WebMethod]
public static string SearchButtonActivity()
{
    string result = "Everything is OK!";
    foreach (string value in getCityList())
    {
        SearchCityDropDownList.Items.Add(new ListItem(value));
    }
    return result;
}

When I run this code and click on the button it just shows the "Everything is OK!" alert and

dropdownlist still empty.

Please help me to solve this problem, I think this is a post back problem because when I debug the code, items of dropdownlist are full but they don't show up in the dropdown.

Thank you

Conscript
  • 607
  • 6
  • 21
Erfan Jazeb Nikoo
  • 978
  • 3
  • 12
  • 36
  • So you are getting the "Everything is OK!" as response but the dropdown remains empty, is it ? – Dhrumil Apr 28 '15 at 13:02
  • where did you `bind` the `dropdownlist` ?? – Nad Apr 28 '15 at 13:02
  • I didn't bind @nadeem, But when you fill items of dropdownlist you can see those items in web view! – Erfan Jazeb Nikoo Apr 28 '15 at 13:05
  • 1
    It's a while since I've tried but I don't think you can do this without an UpdatePanel or some other form of ajaxified control. The list of dropdown elements is stored in the viewstate and I don't think changes till a postback. It's been a while though so take that with a pinch of salt. – Klors Apr 28 '15 at 13:07
  • Just put `value` instead of `new ListItem(value)` and see how it goes. – Dhrumil Apr 28 '15 at 13:07
  • 1
    You are confusing the fact that a web method knows anything about rendering changes to the server controls -- it doesn't. This is simply AJAX with some .NET sugar sprinkled on top to make it work. You should return the result of `getCityList()` from this method. The client side code is then responsible for adding the items to the rendered HTML control (not the *server control*). – Cᴏʀʏ Apr 28 '15 at 13:08
  • Dear @Cᴏʀʏ, In some function I wanna change visibility of labels when I click the button without refresh the page, In that case I have same problem – Erfan Jazeb Nikoo Apr 28 '15 at 13:12
  • Same problem @HarveySpecter – Erfan Jazeb Nikoo Apr 28 '15 at 13:14
  • I think like you @Klors, But I didn't test UpdatePanel. I test it now – Erfan Jazeb Nikoo Apr 28 '15 at 13:16

1 Answers1

3

This will not work, how you have it setup. You could do an update panel, but that would be overkill, IMO. The problem is that you are making an AJAX call which just goes back to the server and returns to the client. The page, and thus the control, never get back to the server to get re-rendered.

Instead, you need to bind the result from your onsuccess callback to your dropdown list. So your web method needs to change:

[WebMethod]
public static string SearchButtonActivity()
{
    var result = new List<string>();
    foreach (string value in getCityList())
    {
        result.Add(value);
    }
    return result;
}

And then your onSuccess client side callback needs to handle it:

function SearchButtonClick() {
        PageMethods.SearchSearchButtonActivity(onSucess, onError);
    }
    function onSucess(result) {
        SearchCityDropDownList.options.length = 0;
        for (var i==0;i<result.length;i++) {
         AddOption(result[i], i);
        }
    }
    function onError(result) {
        alert('Cannot process your request at the moment, please try later.');
    }

function AddOption(text, value) {
    var option = document.createElement('option');
    option.value = value;
    option.innerHTML = text;
    SearchCityDropDownList.options.add(option);
}

You can retrieve the value selected, server side in this fashion:

string selectedVal = Request[SearchCityDropDownList.UniqueID]

Thanks to this so post for the guidance: Getting the value of a DropDownList after client side javascript modification

Community
  • 1
  • 1
JasonWilczak
  • 2,303
  • 2
  • 21
  • 37
  • My big problem is I want to handle it inside of server side functions :( – Erfan Jazeb Nikoo Apr 28 '15 at 13:18
  • 1
    Will the results of any postback be able to see these dynamic entries in the list? From what I recall, if they're not in the viewstate then you can't do anything with them on the server side later. Not a problem if the page doesn't post data back of course. – Klors Apr 28 '15 at 13:20
  • I stand corrected, you can get the values on the server, I updated my answer. – JasonWilczak Apr 28 '15 at 13:23
  • @JasonWilczak This is just use for fill dropdownlist, how about disable the label when I click the button? – Erfan Jazeb Nikoo Apr 28 '15 at 13:27
  • That would be another question, but you can do that in your onSuccess callback. Something like: myLabel.disabled = true; – JasonWilczak Apr 28 '15 at 13:30
  • Here is an, albeit broad, SO question related to update panel usage if you want to go that route. The question is broad, but there are some good links in it: [How do I use updatePanel in asp.net without refreshing all page?](http://stackoverflow.com/questions/10929644/how-do-i-use-updatepanel-in-asp-net-without-refreshing-all-page) – JasonWilczak Apr 28 '15 at 13:32
  • @JasonWilczak good to see there's a way to get the client value server side, nice – Klors Apr 28 '15 at 14:58