Tips/Tricks#0:母版页中对控件ID的处理
注:此系列记录在我实际开发中遇到的问题和收藏一些技巧文章。
本篇技巧和诀窍记录的是:母版页中对控件ID的处理。
一、问题提出
由于总体排版和设计的需要,我们往往创建母版页来实现整个网站的统一性,最近我由于统一性的需要,把原来整个项目单独的页面全部套用了母版页。但是出现了一个错误……在我的Blog中记录一下,方便大家参考。
二、 抽象模型
由于整个页面内容过多,所以我把这个页面中最为本质的问题抽象出来。原来单一页面,就是利用按钮触发JS事件,在文本域中插入“(_)”功能,其实现代码如下:
<head id="Head1" runat="server"> <title>单一页面抽象模型-YJingLee</title> <script language="javascript" type="text/javascript"> // <!CDATA[ function insert() {document.getElementById("txt").value=document.getElementById("txt").value+"(__)";return; } // ]]> </script> </head> <body> <form id="form1" runat="server"> <div> <textarea id="txt" runat="server" name="txt" rows="10" cols="50"></textarea> <asp:Button ID="btnInsert" runat="server" Text="服务器端插入(_)" OnClientClick="insert();" /> <input id="btnInsert2" name="insert" onclick="insert();" type="button" value="客户端插入(_)" runat="server" /></div> </form> </body> </html>
上述页面可以正常使用。后来使用模板页后,其代码如下:
<asp:content id="Content1" contentplaceholderid="ContentPlaceHolder1" runat="Server"> <script language="javascript" type="text/javascript"> // <!CDATA[ function insert() { document.getElementById("txt").value = document.getElementById("txt").value + "(__)"; return; } // ]]> </script> <div><textarea id="txt" runat="server" name="txt" rows="10" cols="50"></textarea><asp:Button ID="btnInsert" runat="server" Text="服务器端插入(_)" OnClientClick="insert();"/><input id="btnInsert2" name="insert" onclick="insert();" type="button"value="客户端插入(_)" runat="server"/></div> </asp:content>
当打开后按下按钮出现了“Microsoft JScript 运行时错误: 'document.getElementById(...)' 为空或不是对象”。这是什么原因呢?原来好好的,怎么套用个母版页就出现这个奇怪的问题呢?困扰了好久,和朋友讨论了一下,终于找到了答案……
三、分析本质
原来我们仔细看看其生成的HTML代码:单一页面:
<form name="form1" method="post" action="Default.aspx" id="form1"> <textarea name="txt" id="txt" rows="10" cols="50"></textarea> <input type="submit" name="btnInsert" value="服务器端插入(_)" onclick="insert();" id="btnInsert" /> <input name="btnInsert2" type="button" id="btnInsert2" onclick="insert();" value="客户端插入(_)" /> </form>
再看看套用母版页之后,生成的HTML代码:
<form name="aspnetForm" method="post" action="Default2.aspx" id="aspnetForm"> <textarea name="ctl00$ContentPlaceHolder1$txt" id="ctl00_ContentPlaceHolder1_txt" rows="10" cols="50"></textarea> <input type="submit" name="ctl00$ContentPlaceHolder1$btnInsert" value="服务器端插入(_)" onclick="insert();" id="ctl00_ContentPlaceHolder1_btnInsert" /> <input name="ctl00$ContentPlaceHolder1$btnInsert2" type="button" id="ctl00_ContentPlaceHolder1_btnInsert2" onclick="insert();" value="客户端插入(_)" /> </form>
是不是看到问题了,源文件控件元素的ID和生成HTML文件的ID不一致。表单from的name属性和id属性变成了aspnetForm,控件的id属性被无缘无故了加上了ctl00_ContentPlaceHolder1_前缀,其name属性也加上了ctl00$ContentPlaceHolder1$前缀。
这下知道了,难怪提示“'document.getElementById(...)' 为空或不是对象”的错误了,原来生成页面后其ID都变了。那么我们如何解决它呢?既然他id变了,我们就把JS代码id改为生成后的id。代码如下:
function insert() { document.getElementById("ctl00$ContentPlaceHolder1$txt").value = document.getElementById("ctl00$ContentPlaceHolder1$txt").value + "(__)"; return; } //或者 function insert() { document.getElementById("ctl00_ContentPlaceHolder1_txt").value = document.getElementById("ctl00_ContentPlaceHolder1_txt").value + "(__)"; return; }
好了,问题解决了,不过想想有什么更好的办法呢?到底为什么呢?其实分析一下,它是后来生成的客户端id,我们可以用C#语句Control的ClientID属性,像这样写:txt.ClientID; txt还是原来控件的id,后面的ClientID就是新生成的id。txt.ClientID是从程序里取到的后来生成新的id,这样不是更好吗。修改代码如下:
function insert() { document.getElementById("<%=txt.ClientID %>").value = document.getElementById("<%=txt.ClientID %>").value + "(__)"; return; }
还有在后台Request.Form["txt"]键值需要改变,必须变为Request.Form["<%=txt.ClientID %>"]才能接收到页面的值。想想如果想要得到ID的control是一个用户控件的话,当生成页面后尽管能得到其ClientID,但是却得不到这个对象,所以也就不能设置或获得其属性了。比如,我要做的这个用户控件,由三个DropDownList组成,可是我却想得到一个完整的日期值(指在客户端),一种思路是先获得三个DropDownList的ClientID,然后再由ID1.value+ID2.value+ID3.value取得,可是如果你一个页面上需要放多个这样的用户控件的话,你需要取得多少个ClientID?显然这样做的话,工作量会很大,而且要操作众多的对象,很容易出错。
四、总结
这一类问题我像在我们编写程序时往往经常会遇到,总结一下:这应该属于“使用了MasterPage,或者GridView中的模版列后所有元素ID不一致问题”。由于种种原因(比如使用了MasterPage,或者GridView中的模版列),一个控件在设计时的ID往往不同于生成页面后的ID,为了获得控件客户端ID,我们可以从生成的页面入手,取控件id修改方法:
document.getElementById("ctl00$编辑区ID$控件ID"); document.getElementById("ctl00_编辑区ID_控件ID"); document.getElementById("<%=控件名ID.ClientID%>"); //推荐
在我们设计时往往就会出现一些莫名其妙的问题,我想我们遇到问题时,冷静思考,把握主次,从底层框架入手,纠其原因,相信最终会找到答案。
Tips/Tricks#0:母版页中对控件ID的处理相关推荐
- 嵌套母版页中的控件访问
嵌套母版页中的控件访问 左直拳 嵌套母版页中的控件访问很别扭. 如果一个内容页对应一个没有嵌套的母版页,访问这个母版页上的控件众所周知:类似(Button)Page.Master.FindContro ...
- html更改textbox的id,NET开发-WebForm中TextBox控件ID、Text、TextModel等属性的使用
.NET开发-WebForm中的TextBox控件 1. TextBox概述 在ASP.NET Web应用程序中,TextBox控件是文本框控件.用于在网页表单中,让用户输入文本内容,收集用户信息,然 ...
- listview控件Android,Android中ListView控件的简单使用
文章引自郭霖<第一行代码> ListView允许用户通过手指上下滑动的方式将屏幕外的数据滚动到屏幕内,同时屏幕上原有的数据则会滚动出屏幕 使用LIstView控件 1 在布局文件中引入Li ...
- Asp.net 2.0 中获取控件输出的Html代码 (转)
将Asp.net 控件的呈现html获取,在不少场合会用到,比如生成静态页时 以下代码选自 Asp.net 2.0 高级编程 转自:Asp.net 2.0 中获取控件输出的Html代码 public ...
- 使用母版页后出现控件,使用FindControl找不到指定控件
在注册页面中,为了重置页面上所有的控件,编写了页面中重置按钮的单击事件 protected void btnReset_Click(object sender, EventArgs e) { Labe ...
- (转) ASP.NET 2.0:使用用户控件和定制的Web部件个人化你的门户网站(二)
Web部件目录 我们已经见过了如何在 WebPartZones 控件中事先放入Web部件.你还可以用另外一种方法完成这个功能,那就是允许用户在运行时添加新的Web部件.通过使用 CatalogZone ...
- [转]利用ASP.NET 2.0创建自定义Web控件(1)
原址:http://hi.baidu.com/sjbh/blog/item/cc58fd1bd35d3ad2ad6e7593.html 简介 从使用基本的文本编辑器到创作标记页面,Web 开发已经 ...
- VS Tips]Visual Studio 2008 Toolbox里控件消失(#13119)的问题
VS Tips]Visual Studio 2008 Toolbox里控件消失(#13119)的问题 今天打开Visual Studio 2008准备写windows form程序的时候, 发现Too ...
- 精通 WPF UI Virtualization (提升 OEA 框架中 TreeGrid 控件的性能)
精通 WPF UI Virtualization (提升 OEA 框架中 TreeGrid 控件的性能) 原文:精通 WPF UI Virtualization (提升 OEA 框架中 TreeGri ...
最新文章
- 用户界面设计准则从何而来
- 关于面试的一些问题合集
- python需要学多久才能找到工作-为什么Python适合初学者,一般要学习多久
- 年后开课 | 第 4 期临床基因组家系分析,同时解决科研和临床问题
- Python高能小技巧:了解bytes与str的区别
- 清空数据库事务日志_通过事务日志增长加快数据库恢复和长期运行的事务
- WPS 2019使用技巧及WPS2019政府版最全合集
- python中 使用EVO工具 批量评估里程计 脚本
- Web Intelligence and Big Data--Final Exam
- 3.	Zigbee应用程序框架开发指南 - 应用程序框架目录结构
- 谷歌地图 经纬加密_Google开始加密搜索
- 仿制苏宁易购—静态网页
- 惠普打印机驱动下载(电脑系统和打印机型号自动匹配)
- Ubuntu 20.04 源码编译Paddle2.2.2
- Android 手机浏览器的开发
- android水印相机,Android 水印相机开发
- CGAL例程:地理信息系统----点云数据生成DSM、DTM、等高线和数据分类
- 美国计算机科学专业申请条件,美国CS计算机科学专业申请条件有哪些?
- 移动端横屏/强制横屏
- SAP采购计划协议计划数量小于收货或发票数量的案例分析
热门文章
- Intel汇编语言程序设计学习-第四章 数据传送、寻址和算术运算-上
- hdu3460 字典树(打印机)
- 【数字信号处理】离散时间信号 ( 离散时间信号知识点 | 信号定义 | 信号分类 | 根据确定性分类 | 根据周期性分类 | 根据离散型分类 )
- 【Git】Git 分支管理 ( 删除远程分支 | 查看远程分支 git branch -a | 删除远程分支 git push origin --delete feature1 )
- 【Git】Git 基础命令 ( Git 版本库概念 | 创建版本库 git init | 克隆版本库 git clone )
- 【C 语言】二级指针作为输入 ( 自定义二级指针内存 | 为 二级指针 分配内存 - 存放 一维指针 | 为每个 一级指针 分配内存 | 释放二维指针内存 )
- 【Android 异步操作】Handler 机制 ( MessageQueue 消息队列的阻塞机制 | Java 层机制 | native 层阻塞机制 | native 层解除阻塞机制 )
- 【数据挖掘】贝叶斯分类 ( 贝叶斯分类器 | 贝叶斯推断 | 逆向概率 | 贝叶斯公式 | 贝叶斯公式推导 | 使用贝叶斯公式求逆向概率 )
- 【数据挖掘】数据挖掘算法 组件化思想 ( 模型或模式结构 | 数据挖掘任务 | 评分函数 | 搜索和优化算法 | 数据管理策略 )
- 第3节 sqoop:3、sqoop的入门测试使用