2016-08-15 4 views
0

런타임에 HTML 요소를 동적으로 작성하고 렌더링 된 요소를 문자열로 반환하는 웹 서비스를 호출 할 때 예외가 발생합니다.AssociateControlID를 사용하여 동적 레이블 WebControl을 렌더링 할 때 예외가 발생했습니다.

System.Web.HttpException :

다음 오류가 RenderControl() 메서드 호출에 발생하는 라벨과 관련된 ID 'txtCertificate'과 제어를 찾을 수 없습니다 'lblCertificate'.

StringWriter stringWriter = new StringWriter(); 
HtmlTextWriter writer = new HtmlTextWriter(stringWriter); 

// Create System.Web.UI.WebControls.Panel (container) 
Panel pnlFRow1 = new Panel(); 
pnlFRow1.CssClass = "f-row"; 

// Create System.Web.UI.WebControls.Textbox 
TextBox txtCertificate = new TextBox(); 
txtCertificate.ID = "txtCertificate"; 
txtCertificate.CssClass = "f-input f-input-full"; 

// Create System.Web.UI.WebControls.Label 
Label lblCertificate = new Label(); 
lblCertificate.ID = "lblCertificate"; 
lblCertificate.CssClass = "f-label f-label-full"; 
lblCertificate.AssociatedControlID = txtCertificate.ID; 
lblCertificate.Text = "Certificate:"; 
Panel pnlCertificate = new Panel(); 
pnlCertificate.CssClass = "f-label f-label-full"; 

// Binding child controls to parent controls 
pnlFRow1.Controls.Add(lblCertificate); 
pnlFRow1.Controls.Add(pnlCertificate); 
pnlCertificate.Controls.Add(txtCertificate); 

// Render control 
pnlContent.RenderControl(writer); 

// Return rendered HTML 
return writer.InnerWriter.ToString(); 

나는이 주문 사항은 그러나이 같은 오류를 발생시키는 문제가 될 수 있다는 생각을 줄 pnlCertificate.Controls.Add(txtCertificate); 후 라인 pnlFRow1.Controls.Add(lblCertificate);을 배치했습니다.

속성은 Label WebControl을 실제 <label> 요소로 렌더링해야하며 입력 컨트롤 전에 표시해야합니다.

답변

2

한 가지 방법은 Label 클래스를 상속하고 RenderBeginTag 메서드를 원하는대로 바꾸는 것입니다. 지금 대신 AssociatedControlId를 사용하여, 당신은 할 수 있습니다

public partial class _Default : Page 
{ 
     public class Label : System.Web.UI.WebControls.Label { 
     public string For = null; 
     public override void RenderBeginTag(HtmlTextWriter writer) { 
      AddAttributeIfExists(writer, "ID", ID); 
      AddAttributeIfExists(writer, "For", For); 
      writer.RenderBeginTag("Label"); 
     } 
     private void AddAttributeIfExists(HtmlTextWriter writer, string name, string value) { 
      if (!string.IsNullOrWhiteSpace(value)) 
       writer.AddAttribute(name, value); 
     } 
    } 

    protected void Page_Load(object sender, EventArgs e) { 
     StringWriter stringWriter = new StringWriter(); 
     HtmlTextWriter writer = new HtmlTextWriter(stringWriter); 

     Panel test = new Panel() { ID = "PanelTest" }; 

     TextBox txtCertificate = new TextBox() { ID = "txtCertificate" }; 
     Label lblCertificate = new Label() { ID = "lblCertificate", Text = "Certificate", For = txtCertificate.ClientID }; 

     test.Controls.Add(lblCertificate); 
     test.Controls.Add(txtCertificate); 

     test.RenderControl(writer); 
     string teststring = writer.InnerWriter.ToString(); 
    } 
} 

참고 : 중첩는 현지 상황을 유지하고 예를 들어 응용 프로그램

의 나머지 부분에 누출을 중지해야 Label 클래스의 경우 같은 일을 할 사용자 지정 For 속성을 사용하십시오. 또한 Label 클래스가 페이지 클래스 내에 중첩되어 다른 페이지와 간섭하지 않는지 확인합니다. 우리는이 답변의 첫 번째 버전에서 발견 된대로 AssociatedControlId없이 .Attributes["for"]를 사용하려고하면

불행하게도, .NET은 <span><Label> 변환되므로, 위의 예는이 문제를 얻어야한다.

+0

속성을 추가 할 때 유일한 문제는 'Label' WebControl이'

+0

흠, 이상한 .NET은 AssociatedControlID가 없으면이를 span 태그로 변경합니다. 또 다른 옵션은 로컬로 Label webcontrol을 확장하는 것입니다. 업데이트 된 답변을 참조하십시오. – Delosdos

+0

여기에있는 내용은 더 이상 다른 속성을 렌더링하지 않는다는 것입니다. 예를 들어, 당신의 예제에서'ID' 속성은 렌더링되지 않습니다. – MPaul

관련 문제