locked
Simple Custom DropdownList RRS feed

  • Question

  • User620472635 posted
    So, I have a custom dropdown list I'm trying to make, and I don't know why it isn't working. It seems to load the data correctly, and render correctly, but then when I try to get the selectedItemValue, it doesn't return anything. anyone know why this would be? Do I need to expose the base class' function somehow? I'm very new to creating custom web controls, so please bear with me! Thanks! - James
    using System;
    using System.Data.SqlClient;
    using System.Web.UI;
    using System.Web.UI.WebControls;
    using System.ComponentModel;
    
    namespace ADI.WebControls
    {
    	/// <SUMMARY>
    	/// the PjProdLineDDL will create a dropdown list that contains
    	/// the product lines, and their respective outline code ID from 
    	/// project server as the value.
    	/// </SUMMARY>
    
    	[DefaultProperty("ConnectionString"),
    		ToolboxData("<{0}:PjProdLineDDL runat=server>")]
    	public class PjProdLineDDL : System.Web.UI.WebControls.DropDownList
    	{
    		private string m_strProjectServer;
    		private string m_strConnectionString;
    		private string m_strErrorMsg;
    
    		/// <SUMMARY>
    		/// Initializes a new instance of the <SEE cref="PjProdLineDDL" /> class.
    		/// </SUMMARY>
    		public PjProdLineDDL() : this(""){	}
    
    		/// <SUMMARY>
    		/// Initializes a new instance of the <SEE cref="PjProdLineDDL" /> class.
    		/// </SUMMARY>
    		/// <PARAM name="ProjectServer">The project server (sanjoseapps1, sanjoseapps3).</PARAM>
    		public PjProdLineDDL(string ProjectServer)
    		{
    			if(ProjectServer != "")
    				m_strProjectServer = ProjectServer;
    		}
    
    		[Bindable(true),
    			Category("Misc"),
    			DefaultValue("")]
    		public string ProjectServer
    		{
    			get{return m_strProjectServer;}
    			set{m_strProjectServer = value;}
    		}
    		
    
    		[Bindable(true),
    		Category("Data"),
    		DefaultValue("")]
    		public string ErrorMsg
    		{
    			get{return m_strErrorMsg;}
    		}
    
    
    		/// <SUMMARY>
    		/// Populates this instance with values from the database.
    		/// </SUMMARY>
    		/// <RETURNS>Returns True if successful.</RETURNS>
    		public bool Populate()
    		{	
    			//Declare locals
    			SqlConnection cnn = null;
    			SqlCommand cmd = null;
    			SqlDataReader drData = null;
    			string strSelect = "";
    			bool bResult = true;
    
    			strSelect = "SELECT * FROM ADI_VIEW_OBS_ddl";
    			try
    			{
    				using(cnn = new SqlConnection(m_strConnectionString))
    				{
    					using(cmd = new SqlCommand()) 
    					{
    						cmd.CommandText = strSelect;
    						cmd.CommandType = System.Data.CommandType.Text;
    
    						cnn.Open();
    						cmd.Connection = cnn;
    
    						using(drData = cmd.ExecuteReader()) 
    						{
    							//bind to control
    							base.DataTextField = "Name";
    							base.DataValueField = "CODE_UID";
    							base.DataSource = drData;
    							base.DataBind();
    
    							//clean up
    							drData.Close();
    							cnn.Close();
    						}
    					}
    				}
    			}
    			catch(Exception ee)
    			{
    				bResult = false;
    				m_strErrorMsg = ee.Message;
    			}
    
    			return bResult;
    		}
    
    		
    		/// <SUMMARY>
    		/// Overrides the default render method to populate the list before it is rendered.
    		/// </SUMMARY>
    		/// <PARAM name="output">The output.</PARAM>
    		protected override void Render(HtmlTextWriter output)
    		{
    			switch(m_strProjectServer) 
    			{
                               //connection strings go here
                            } this.Populate(); base.Render(output); } } }
    Friday, December 16, 2005 2:35 PM

All replies

  • User-865881720 posted
    Populate the drop down list with data ONLY on the initial load event (that is, within a !IsPostBack conditional block).  You are currently populating the drop down list in the override of the Render method, which is not only too late in the control life cycle as it occurs after viewstate is saved, but is also called on both the initial load and all subsequent postbacks, thus reseting the SelectedItem back to the first item in the list.
    Friday, December 16, 2005 3:06 PM
  • User620472635 posted
    you're exactly right, thanks!  that's how I had the initial control I made, then revamped it...bleh, not a very good "upgrade" i guess...
     
    Is there any way to have the control load itself, and behave correctly?
     
    Thanks again!
    - JJ
    Friday, December 16, 2005 3:22 PM
  • User-865881720 posted

    In your custom control's Load event handler, simply call your Populate method on the initial load of the control but not on subsequent postbacks:

    void PjProdLineDDL_Load() {
       if (!IsPostBack) {
              this.Populate();
      }
    }

    You do not need to override the Render method.

    Friday, December 16, 2005 6:30 PM