React.js点击获取自定义属性
2017-03-15 09:33
741 查看
获取React.js自定义属性必须data- ,比如data-index 然后用event.target.getAttribute("data-index")
或者console.log(this.refs.myInput.getAttribute("data-index"));获取
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<script src="../build/react.js"></script>
<script src="../build/react-dom.js"></script>
<script src="../build/browser.min.js"></script>
<script src="../jquery.min.js"></script>
</head>
<body>
<div id="example" dongtao='1111'></div>
</body>
<script type='text/babel'>
//console.log($('#example').attr('dongtao'))
var MyComponent = React.createClass({
handleClick: function(event) {
// 使用原生的 DOM API 获取焦点
console.log(event.target)
console.log(event.target.getAttribute("data-index"))
// console.log(this.refs.myInput.value);
// console.log(this.refs.myInput.id);
console.log(this.refs.myInput.getAttribute("data-dd"));
// console.log($('#dongtao').val());
},
render: function() {
// 当组件插入到 DOM 后,ref 属性添加一个组件的引用于到 this.refs
return (
<div>
<input type="text" ref="myInput" id='dongtao' data-dd='ddd'/>
<input
type="button"
value="点击"
id="id"
data-index="dongtao"
onClick={this.handleClick}
/>
</div>
);
}
});
ReactDOM.render(
<MyComponent />,
document.getElementById('example')
);
</script>
</html>
点击删除按钮,删除列表中对应项本来是React比较基础的应用,可是应用情况变得复杂了以后,我还真想了一会儿才搞定。
简化一下应用场景:点击新增按钮,增加一条输入框,点击输入框旁边的按钮,删除该输入框(不能删错了啊)。
先说第一种方法
问题刚上手,首先规划级别:一个输入框和对应删除按钮为一个子组件,整体为父组件即可方便处理。
注意的点:生成的一坨输入框是一个数组,为了准确删掉对应项,生成时要编号。点击删除按钮要反馈对应编号,然后进行删除。
现在的逻辑是:整个待展示列表(由子组件组成的数组)是个state,添加按钮会增加一个元素到这个state里面,添加的方法如下:
注意一点,这个index属性是固定的,子组建生成后就固定了,这就为你未来挖了一个坑。
删除按钮当然就是从这个state列表里删除对应元素了,问题一来了,我怎么知道是第几个元素?一拍脑袋这还不简单,event.target 获取点击的标签,在标签上写个index属性告诉delete方法是第几个元素不就得了?试了发现不行,看看文档,event.target确实获取dom元素没毛病,但是index这个属性原生dom根本不承认啊,怎么办?data-index就行了,前面加
data- 就是dom承认的自定义属性了。
写完了又想起了两个方法,一个是在删除按钮绑定删除事件的时候,.bind(this,index),index是你准备删掉的是第几个或者表示出来你要删哪个就行。另一个是搞个闭包,就能把index参数传进去了(事件绑定一个立即执行的方程传入参数,该方程返回目标方程)。
第一个问题解决,删除的方法如下:
data-index告诉你要删除第几个元素,然后把它从state里踢出去就行了。这回掉进了一个真正意义上的坑:有时候删的不是对应的元素!乱套了!
好吧,我沉思了5分钟,想到了为什么:生成列表的时候index已经固定,但删除列表的时候我们只告诉他删除的是第index项!问题严重了,举个例子,有两项,index 0和1 你点0,好吧第0项删掉了,你再点1,疑?没反应了,因为你打算删除第1项,而列表中目前只有第0项(就是原来的第一项,原来的第0项删除后他就成了第0项)!这会导致各种乱套,考虑到生成列表的index是列表长度表示的就更乱了。
解决方式:delete方法里修改一行:
好了,删除的元素我用空字符串代替,这样顺序和删除的项,还有以后添加的项的index都不会乱了,给自己点赞。到这里第一种方法实现了目标。
Code pen 地址:http://codepen.io/huanqingli/pen/dNyQez
完整代码:
这种方法有利有弊,所以我找到了第二种方法,具体情况择优使用。
第二种方法。总体来讲推荐这种方法。
在state里保存要展示的数据,在render里动态生成子组件组,然后添加删除都是操作保存数据的state,render里的子组件会自动刷新。这种方式应该是更贴近React思路的,用数据展现界面。如果你要展现一组数据,这种方法很自然,但如果展现的是一个动态的表单,稍微麻烦一点,但也可以做,而且我依然推荐用这种方式。
这种方法做个todolist就很简单,这里依然做上文的例子,稍微麻烦一点,也会理解的更深入一点。
整体结构和第一种方法一样,只不过这次state里面不是子组件,先用空字符串组成的数组代替,仅仅是为了render的时候知道有几个子组件而已。添加的时候也要push空字符串,等输入框输入数据后,更新state中的内容,做到数据和界面同步。
render子组件的部分:
添加的方法变成:
这就能跑了,这有个小坑,稍有不慎你发现你怎么删都是删列表的最后一项,其实数据操作没问题,关键是这个存在感比较低的key,必须特定项有给定的key你用动态的index他就懵了,不知道删哪个了,他就吧最后一个删了。废话不多说(该程序因为key键取值的问题有一个小问题):
Code pen 地址:http://codepen.io/huanqingli/pen/xgxNYN
整体代码:
这种方法经常也会有点小坑,也比较好解决。
总结:两种方法各有利弊,推荐第二种,符合REACT设计思路,但第一种有时候解决问题很方便。
或者console.log(this.refs.myInput.getAttribute("data-index"));获取
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<script src="../build/react.js"></script>
<script src="../build/react-dom.js"></script>
<script src="../build/browser.min.js"></script>
<script src="../jquery.min.js"></script>
</head>
<body>
<div id="example" dongtao='1111'></div>
</body>
<script type='text/babel'>
//console.log($('#example').attr('dongtao'))
var MyComponent = React.createClass({
handleClick: function(event) {
// 使用原生的 DOM API 获取焦点
console.log(event.target)
console.log(event.target.getAttribute("data-index"))
// console.log(this.refs.myInput.value);
// console.log(this.refs.myInput.id);
console.log(this.refs.myInput.getAttribute("data-dd"));
// console.log($('#dongtao').val());
},
render: function() {
// 当组件插入到 DOM 后,ref 属性添加一个组件的引用于到 this.refs
return (
<div>
<input type="text" ref="myInput" id='dongtao' data-dd='ddd'/>
<input
type="button"
value="点击"
id="id"
data-index="dongtao"
onClick={this.handleClick}
/>
</div>
);
}
});
ReactDOM.render(
<MyComponent />,
document.getElementById('example')
);
</script>
</html>
React 点击删除列表中对应项(React 获取DOM中自定义属性)
点击删除按钮,删除列表中对应项本来是React比较基础的应用,可是应用情况变得复杂了以后,我还真想了一会儿才搞定。简化一下应用场景:点击新增按钮,增加一条输入框,点击输入框旁边的按钮,删除该输入框(不能删错了啊)。
先说第一种方法
问题刚上手,首先规划级别:一个输入框和对应删除按钮为一个子组件,整体为父组件即可方便处理。
注意的点:生成的一坨输入框是一个数组,为了准确删掉对应项,生成时要编号。点击删除按钮要反馈对应编号,然后进行删除。
现在的逻辑是:整个待展示列表(由子组件组成的数组)是个state,添加按钮会增加一个元素到这个state里面,添加的方法如下:
add(){ var lists=this.state.lists; lists.push(<List key={this.state.lists.length} index={this.state.lists.length} delete={this.delete}/>); this.setState({lists:lists}) }
注意一点,这个index属性是固定的,子组建生成后就固定了,这就为你未来挖了一个坑。
删除按钮当然就是从这个state列表里删除对应元素了,问题一来了,我怎么知道是第几个元素?一拍脑袋这还不简单,event.target 获取点击的标签,在标签上写个index属性告诉delete方法是第几个元素不就得了?试了发现不行,看看文档,event.target确实获取dom元素没毛病,但是index这个属性原生dom根本不承认啊,怎么办?data-index就行了,前面加
data- 就是dom承认的自定义属性了。
写完了又想起了两个方法,一个是在删除按钮绑定删除事件的时候,.bind(this,index),index是你准备删掉的是第几个或者表示出来你要删哪个就行。另一个是搞个闭包,就能把index参数传进去了(事件绑定一个立即执行的方程传入参数,该方程返回目标方程)。
第一个问题解决,删除的方法如下:
delete(e){ var index=e.target.getAttribute("data-index"); var lists=this.state.lists; lists.splice(index,1); this.setState({lists:lists}) }
data-index告诉你要删除第几个元素,然后把它从state里踢出去就行了。这回掉进了一个真正意义上的坑:有时候删的不是对应的元素!乱套了!
好吧,我沉思了5分钟,想到了为什么:生成列表的时候index已经固定,但删除列表的时候我们只告诉他删除的是第index项!问题严重了,举个例子,有两项,index 0和1 你点0,好吧第0项删掉了,你再点1,疑?没反应了,因为你打算删除第1项,而列表中目前只有第0项(就是原来的第一项,原来的第0项删除后他就成了第0项)!这会导致各种乱套,考虑到生成列表的index是列表长度表示的就更乱了。
解决方式:delete方法里修改一行:
lists.splice(index,1,"");
好了,删除的元素我用空字符串代替,这样顺序和删除的项,还有以后添加的项的index都不会乱了,给自己点赞。到这里第一种方法实现了目标。
Code pen 地址:http://codepen.io/huanqingli/pen/dNyQez
完整代码:
class List extends React.Component {
render() {
return (<div><input type="text" defaultValue={this.props.index}/>
<span onClick={this.props.delete} data-index={this.props.index}>X</span></div>)
}
}
class Lists extends React.Component {
constructor(props) {
super(props);
this.add=this.add.bind(this);
this.delete=this.delete.bind(this);
this.state={
lists:[]
}
}
add(){ var lists=this.state.lists; lists.push(<List key={this.state.lists.length} index={this.state.lists.length} delete={this.delete}/>); this.setState({lists:lists}) }
delete(e){
var index=e.target.getAttribute("data-index");
var lists=this.state.lists;
console.log(index)
lists.splice(index,1);
this.setState({lists:lists})
}
render() {
return (<div>
<span onClick={this.add}>添加</span>
{this.state.lists}
</div>)
}
}
ReactDOM.render(
<Lists/>,
document.getElementById('lists')
);
这种方法有利有弊,所以我找到了第二种方法,具体情况择优使用。
第二种方法。总体来讲推荐这种方法。
在state里保存要展示的数据,在render里动态生成子组件组,然后添加删除都是操作保存数据的state,render里的子组件会自动刷新。这种方式应该是更贴近React思路的,用数据展现界面。如果你要展现一组数据,这种方法很自然,但如果展现的是一个动态的表单,稍微麻烦一点,但也可以做,而且我依然推荐用这种方式。
这种方法做个todolist就很简单,这里依然做上文的例子,稍微麻烦一点,也会理解的更深入一点。
整体结构和第一种方法一样,只不过这次state里面不是子组件,先用空字符串组成的数组代替,仅仅是为了render的时候知道有几个子组件而已。添加的时候也要push空字符串,等输入框输入数据后,更新state中的内容,做到数据和界面同步。
render子组件的部分:
{this.state.lists.map(function (item,index) { return <List key={index} index={index} delete={this.delete}/> }.bind(this))}
添加的方法变成:
add(){ var lists=this.state.lists; lists.push(""); this.setState({lists:lists}) }
这就能跑了,这有个小坑,稍有不慎你发现你怎么删都是删列表的最后一项,其实数据操作没问题,关键是这个存在感比较低的key,必须特定项有给定的key你用动态的index他就懵了,不知道删哪个了,他就吧最后一个删了。废话不多说(该程序因为key键取值的问题有一个小问题):
Code pen 地址:http://codepen.io/huanqingli/pen/xgxNYN
整体代码:
1 class List extends React.Component { 2 3 constructor(props){ 4 5 super(props); 6 7 this.upData=this.upData.bind(this); 8 9 } 10 11 12 13 upData(e){ 14 15 this.props.upData(this.props.index,e.target.value) 16 17 } 18 19 20 21 render() { 22 23 return (<div><input type="text" onBlur={this.upData} defaultValue={this.props.item?this.props.item:""}/> 24 25 <span onClick={this.props.delete} data-index={this.props.index}>X</span></div>) 26 27 } 28 29 } 30 31 class Lists extends React.Component { 32 33 constructor(props) { 34 35 super(props); 36 37 this.add=this.add.bind(this); 38 39 this.delete=this.delete.bind(this); 40 41 this.upData=this.upData.bind(this); 42 43 this.state={ 44 45 lists:[] 46 47 } 48 49 } 50 51 52 53 add(){ 54 55 var lists=this.state.lists; 56 57 lists.push(""); 58 59 this.setState({lists:lists}) 60 61 } 62 63 64 65 delete(e){ 66 67 var index=e.target.getAttribute("data-index"); 68 69 var lists=this.state.lists; 70 71 lists.splice(index,1); 72 73 this.setState({lists:lists}) 74 75 } 76 77 78 79 upData(i,x){ 80 81 var lists=this.state.lists; 82 83 lists[i]=x; 84 85 console.log(lists); 86 87 this.setState({lists:lists}); 88 89 } 90 91 92 93 render() { 94 95 return (<div> 96 97 <span onClick={this.add}>添加</span> 98 99 {this.state.lists.map(function (item,index) { 100 101 return <List key={item?item:index} index={index} delete={this.delete} upData={this.upData} item={item}/> 102 103 }.bind(this))} 104 105 </div>) 106 107 } 108 109 } 110 111 112 113 ReactDOM.render( 114 115 <Lists />, document.getElementById('lists') 116 117 )
这种方法经常也会有点小坑,也比较好解决。
总结:两种方法各有利弊,推荐第二种,符合REACT设计思路,但第一种有时候解决问题很方便。
相关文章推荐
- js 点击a标签 获取a的自定义属性
- js 点击a标签 获取a的自定义属性方法
- 使用js在IE9中获取标签自定义属性
- 利用自定义属性实现js点击事件 委托
- JS初级_自定义属性的应用:点击一次换图片2,再点击恢复为图片1
- jQuery点击元素获取自定义属性的值,利用冒泡原理~
- s 点击a标签 获取a的自定义属性方法_javascript技巧
- js设置和获取自定义属性的方法
- JS设置和获取自定义属性
- 属性动画图片从上移动到屏幕中间,放大图片的二倍再缩小到原来,自定义圆实现倒计时,解析数据显示,点击条目实现js交互
- js 获取自定义属性的值
- js获取获取鼠标点击控件的属性
- Js获取自定义属性
- 元素JS和jquery如何获取点击元素的id或name属性
- js中如果无法获取某个html属性,例如自定义了一个dir属性,但获取总是为空,尝试换个词,因为可能什么关键词冲突了。
- 根据点击头像的手势获取自定义Cell 的属性, UITableViewCell, 头像, iOS
- js设置和获取自定义属性
- 自定义元素属性,以及用jquery 去获取当前点击的元素的这个自定义属性
- 属性动画图片从上移动到屏幕中间,放大图片的二倍再缩小到原来,自定义圆实现倒计时,解析数据显示,点击条目实现js交互
- js的自定义属性及多一排图片的点击切换效果的实现