自定义边界字段没有';t在添加了LiteralControl的PostBacks之间保留数据
本文关键字:LiteralControl 添加 PostBacks 数据 保留 之间 字段 边界 自定义 | 更新日期: 2023-09-27 18:21:50
我已经创建了一个自定义BoundField
,用于在编辑和插入模式下使用DetailsView
,以利用Twitter引导。
该控件运行良好,除了在InitializeDataCell(…)期间添加额外的LiteralControl
s以用一些HTML包围TextBox
时。与此相关的代码接近末尾。
下面生成的HTML似乎与TemplateField
生成的HTML相同。但是,当我启动Update时,每当它添加此处所示的额外div/span,TextBox
中的值在PostBack上为空。
<div class="input-prepend">
<span class="add-on">$</span>
<input name="ctl00$ctl00$MainContent$MainContent$pi$dvPackage$tbPrice" type="text" value="0" size="5" id="MainContent_MainContent_pi_dvPackage_tbPrice" title="Price">
</div>
以下是我在前端ASP.NET代码中所做的操作以及生成的HTML的一些示例。
不起作用-自定义字段通过Update命令提交后,文本框内的值将取消设置,仅当我添加输入附加和附加 DetailsView内的字段 HTML生成 正常工作-TemplateField工作良好 DetailsView内的字段 HTML生成-与上面的内容相同 是否有效-使用自定义字段生成HTML当我没有添加TextPrepend字段时,文本框内的值通过Update命令正确提交。 DetailsView内的字段 在没有额外span/div的情况下生成的HTML InitializeDataCell与此代码创建相关的部分 我认为这是由于InitializeDataCell(…)实现的问题。 整个代码以防对任何试图使用Twitter Bootstrap的人有用,或者我的代码在其他地方出错。<my:ValidationField DataField="Price" HeaderText="Price" TextPrepend="$" />
<td>
<div class="input-prepend">
<span class="add-on">$</span>
<input name="ctl00$ctl00$MainContent$MainContent$pi$dvPackage$tbPrice" type="text" value="0" size="5" id="MainContent_MainContent_pi_dvPackage_tbPrice" title="Price">
</div>
</td>
<asp:TemplateField>
<EditItemTemplate>
<div class="input-prepend">
<span class="add-on">$</span>
<asp:TextBox ID="tbCost" runat="server" Text='<%# Bind("Cost") %>'></asp:TextBox>
</div>
</EditItemTemplate>
</asp:TemplateField>
<td>
<div class="input-prepend">
<span class="add-on">$</span>
<input name="ctl00$ctl00$MainContent$MainContent$pi$dvPackage$tbPrice" type="text" value="0" size="5" id="MainContent_MainContent_pi_dvPackage_tbPrice" title="Price">
</div>
</td>
<my:ValidationField DataField="Price" HeaderText="Price" />
<td>
<input name="ctl00$ctl00$MainContent$MainContent$pi$dvPackage$tbPrice" type="text" value="0" size="5" id="MainContent_MainContent_pi_dvPackage_tbPrice" title="Price">
</td>
protected override void InitializeDataCell(DataControlFieldCell cell, DataControlRowState rowState)
{
base.InitializeDataCell(cell, rowState);
// Find the text box to validate
TextBox text = FindTextBox(cell);
if (text != null)
{
text.ID = "tb" + DataField;
text.MaxLength = MaxLength;
text.TextMode = TextMode;
text.Text = DataField;
string cellCss = string.Empty;
bool prepend = !string.IsNullOrEmpty(this.TextPrepend);
bool append = !string.IsNullOrEmpty(this.TextAppend);
bool addon = prepend || append;
if (prepend == true)
cellCss = this.ConcatenateCss(cellCss, "input-prepend");
if (append == true)
cellCss = this.ConcatenateCss(cellCss, "input-append");
if (addon == true)
{
int textIndex = cell.Controls.IndexOf(text);
Literal container = new Literal();
container.Text = "<div class='"" + cellCss + "'">";
cell.Controls.AddAt(textIndex, container);
}
if (prepend == true)
{
int textIndex = cell.Controls.IndexOf(text);
Literal units = new Literal();
units.Text = "<span class='"add-on'">" + this.Prepend() + "</span>";
cell.Controls.AddAt(textIndex, units);
}
if (append == true)
{
Literal units = new Literal();
units.Text = "<span class='"add-on'">" + this.Append() + "</span>";
cell.Controls.Add(units);
}
if (addon == true)
{
Literal container = new Literal();
container.Text = "</div>";
cell.Controls.Add(container);
}
}
}
public class ValidationField : BoundField
{
#region Properties
public virtual string EditTextCssClass
{
get
{
return (string)(ViewState["EditTextCssClass"] ?? string.Empty);
}
set
{
ViewState["EditTextCssClass"] = value;
OnFieldChanged();
}
}
public virtual ValidatorDisplay ErrorDisplay
{
get
{
return (ValidatorDisplay)(ViewState["ErrorDisplay"] ?? ValidatorDisplay.Dynamic);
}
set
{
ViewState["ErrorDisplay"] = value;
OnFieldChanged();
}
}
public virtual string ErrorMessage
{
get
{
return (string)(ViewState["ErrorMessage"] ?? "Invalid value entered");
}
set
{
ViewState["ErrorMessage"] = value;
OnFieldChanged();
}
}
public virtual string HelpText
{
get
{
return (string)(ViewState["HelpText"] ?? string.Empty);
}
set
{
ViewState["HelpText"] = value;
OnFieldChanged();
}
}
public virtual TwitterBootstrap.WebControls.TextBox.HelpTextDisplayMode HelpDisplay
{
get
{
return (TwitterBootstrap.WebControls.TextBox.HelpTextDisplayMode)(ViewState["HelpDisplay"] ?? TwitterBootstrap.WebControls.TextBox.HelpTextDisplayMode.Block);
}
set
{
ViewState["HelpDisplay"] = value;
OnFieldChanged();
}
}
public virtual int MaxLength
{
get
{
return (int)(ViewState["MaxLength"] ?? 0);
}
set
{
ViewState["MaxLength"] = value;
OnFieldChanged();
}
}
public virtual string PlaceHolder
{
get
{
return (string)(ViewState["PlaceHolder"] ?? string.Empty);
}
set
{
ViewState["PlaceHolder"] = value;
OnFieldChanged();
}
}
public virtual bool Required
{
get
{
return (bool)(ViewState["Required"] ?? false);
}
set
{
ViewState["Required"] = value;
OnFieldChanged();
}
}
public virtual TextBoxMode TextMode
{
get
{
return (TextBoxMode)(ViewState["TextMode"] ?? TextBoxMode.SingleLine);
}
set
{
ViewState["TextMode"] = value;
OnFieldChanged();
}
}
public virtual string ValidationExpression
{
get
{
return (string)(ViewState["ValidationExpression"] ?? string.Empty);
}
set
{
ViewState["ValidationExpression"] = value;
OnFieldChanged();
}
}
public virtual string ValidationGroup
{
get
{
return (string)(ViewState["ValidationGroup"] ?? string.Empty);
}
set
{
ViewState["ValidationGroup"] = value;
OnFieldChanged();
}
}
public virtual string TextAppend
{
get
{
object value = ViewState["TextAppend"];
if (value != null)
return value.ToString();
return string.Empty;
}
set
{
ViewState["TextAppend"] = value;
OnFieldChanged();
}
}
public virtual string TextPrepend
{
get
{
object value = ViewState["TextPrepend"];
if (value != null)
return value.ToString();
return string.Empty;
}
set
{
ViewState["TextPrepend"] = value;
OnFieldChanged();
}
}
#endregion
public ValidationField()
{
}
protected override DataControlField CreateField()
{
return new ValidationField();
}
protected override void InitializeDataCell(DataControlFieldCell cell, DataControlRowState rowState)
{
base.InitializeDataCell(cell, rowState);
// Find the text box to validate
TextBox text = FindTextBox(cell);
if (text != null)
{
text.ID = "tb" + DataField;
text.MaxLength = MaxLength;
text.TextMode = TextMode;
text.CssClass = EditTextCssClass;
text.Text = DataField;
if (PlaceHolder != string.Empty)
text.Attributes.Add("placeholder", PlaceHolder);
string cellCss = string.Empty;
bool prepend = !string.IsNullOrEmpty(this.TextPrepend);
bool append = !string.IsNullOrEmpty(this.TextAppend);
bool addon = prepend || append;
if (prepend == true)
cellCss = this.ConcatenateCss(cellCss, "input-prepend");
if (append == true)
cellCss = this.ConcatenateCss(cellCss, "input-append");
if (addon == true)
{
int textIndex = cell.Controls.IndexOf(text);
Literal container = new Literal();
container.Text = "<div class='"" + cellCss + "'">";
cell.Controls.AddAt(textIndex, container);
}
if (prepend == true)
{
int textIndex = cell.Controls.IndexOf(text);
Literal units = new Literal();
units.Text = "<span class='"add-on'">" + this.Prepend() + "</span>";
cell.Controls.AddAt(textIndex, units);
}
if (append == true)
{
Literal units = new Literal();
units.Text = "<span class='"add-on'">" + this.Append() + "</span>";
cell.Controls.Add(units);
}
if (addon == true)
{
Literal container = new Literal();
container.Text = "</div>";
cell.Controls.Add(container);
}
if (Required == true)
{
Literal required = new Literal();
required.Text = "<span class='"required'">*</span>";
cell.Controls.Add(required);
}
if (HelpText != string.Empty)
{
Label lblHelpText = new Label();
if (HelpDisplay == TwitterBootstrap.WebControls.TextBox.HelpTextDisplayMode.Block)
lblHelpText.CssClass = "help-block";
else
lblHelpText.CssClass = "help-inline";
lblHelpText.Text = HelpText;
cell.Controls.Add(lblHelpText);
}
if (Required == true)
{
// Add a RequiredFieldValidator
RequiredFieldValidator required = new RequiredFieldValidator();
required.ErrorMessage = ErrorMessage;
required.Display = ErrorDisplay;
required.ControlToValidate = text.ID;
required.Text = "";
if (ValidationGroup != string.Empty)
required.ValidationGroup = ValidationGroup;
cell.Controls.Add(required);
}
if (ValidationExpression != string.Empty)
{
// Add a RequiredFieldValidator
RegularExpressionValidator regex = new RegularExpressionValidator();
regex.ErrorMessage = ErrorMessage;
regex.Display = ErrorDisplay;
regex.ControlToValidate = text.ID;
regex.ValidationExpression = ValidationExpression;
if (ValidationGroup != string.Empty)
regex.ValidationGroup = ValidationGroup;
cell.Controls.Add(regex);
}
}
}
#region Methods
private string ConcatenateCss(params string[] classes)
{
string result = string.Empty;
foreach (string s in classes)
result += s + " ";
return result.TrimEnd().TrimStart();
}
private static TextBox FindTextBox(Control parent)
{
TextBox result = null;
foreach (Control control in parent.Controls)
{
if (control is TextBox)
{
result = control as TextBox;
break;
}
}
return result;
}
protected virtual string Prepend()
{
return this.TextPrepend;
}
protected virtual string Append()
{
return this.TextAppend;
}
#endregion
}
我设法弄清楚了发生这种情况的原因。由于字段中的Control
集合已更改,因此还必须重写_ExtractValuesFromCell(…)to get the
TextBox`值。
我使用了一个稍微修改过的ASP.NET实现,Boundfield覆盖以支持Dropdownlist。它缺少最后一个功能,并且没有针对我的用例进行优化。然而,它现在运行良好。
public override void ExtractValuesFromCell(System.Collections.Specialized.IOrderedDictionary dictionary, DataControlFieldCell cell, DataControlRowState rowState, bool includeReadOnly)
{
Control control = null;
string dataField = DataField;
object text = null;
string nullDisplayText = NullDisplayText;
if (((rowState & DataControlRowState.Insert) == DataControlRowState.Normal) || InsertVisible)
{
if (cell.Controls.Count > 0)
{
foreach (Control c in cell.Controls)
{
control = cell.Controls[0];
if (c is TextBox)
{
text = ((TextBox)c).Text;
}
}
}
else if (includeReadOnly)
{
string s = cell.Text;
if (s == " ")
{
text = string.Empty;
}
else if (SupportsHtmlEncode && HtmlEncode)
{
text = HttpUtility.HtmlDecode(s);
}
else
{
text = s;
}
}
if (text != null)
{
if (((text is string) && (((string)text).Length == 0)) && ConvertEmptyStringToNull)
{
text = null;
}
if (((text is string) && (((string)text) == nullDisplayText)) && (nullDisplayText.Length > 0))
{
text = null;
}
if (dictionary.Contains(dataField))
{
dictionary[dataField] = text;
}
else
{
dictionary.Add(dataField, text);
}
}
}
}