React JS onClick事件处理程序

use*_*079 107 javascript jquery reactjs

我有

var TestApp = React.createClass({
      getComponent: function(){
          console.log(this.props);
      },
      render: function(){
        return(
             <div>
             <ul>
                <li onClick={this.getComponent}>Component 1</li>
             </ul>
             </div>
        );
      }
});
React.renderComponent(<TestApp />, document.body);
Run Code Online (Sandbox Code Playgroud)

我想为点击列表元素的背景着色.我怎么能在React中做到这一点?

就像是

$('li').on('click', function(){
    $(this).css({'background-color': '#ccc'});
});
Run Code Online (Sandbox Code Playgroud)

eri*_*oco 88

为什么不呢:

onItemClick: function (event) {

    event.currentTarget.style.backgroundColor = '#ccc';

},

render: function() {
    return (
        <div>
            <ul>
                <li onClick={this.onItemClick}>Component 1</li>
            </ul>
        </div>
    );
}
Run Code Online (Sandbox Code Playgroud)

如果你想更多关于它的反应,你可能想要将所选项目设置为其包含的React组件的状态,然后引用该状态以确定项目的颜色render:

onItemClick: function (event) {

    this.setState({ selectedItem: event.currentTarget.dataset.id });
    //where 'id' =  whatever suffix you give the data-* li attribute
},

render: function() {
    return (
        <div>
            <ul>
                <li onClick={this.onItemClick} data-id="1" className={this.state.selectedItem == 1 ? "on" : "off"}>Component 1</li>
                <li onClick={this.onItemClick} data-id="2" className={this.state.selectedItem == 2 ? "on" : "off"}>Component 2</li>
                <li onClick={this.onItemClick} data-id="3" className={this.state.selectedItem == 3 ? "on" : "off"}>Component 3</li>
            </ul>
        </div>
    );
},
Run Code Online (Sandbox Code Playgroud)

当然,你想把它们<li>放到一个循环中,你需要设置li.onli.off设置你的样式background-color.

  • **React 中的手动 DOM 操作是一种反模式**,它只会导致更多问题。避免使用诸如“event.currentTarget.style.backgroundColor = '#ccc';”之类的内容,除非您真正了解自己在做什么(大多数时候,在集成第三方小部件时)。 (2认同)

Dhi*_*raj 61

我能想到的两种方式是

var TestApp = React.createClass({
    getComponent: function(index) {
        $(this.getDOMNode()).find('li:nth-child(' + index + ')').css({
            'background-color': '#ccc'
        });
    },
    render: function() {
        return (
            <div>
              <ul>
                <li onClick={this.getComponent.bind(this, 1)}>Component 1</li>
                <li onClick={this.getComponent.bind(this, 2)}>Component 2</li>
                <li onClick={this.getComponent.bind(this, 3)}>Component 3</li>
              </ul>
            </div>
        );
    }
});
React.renderComponent(<TestApp /> , document.getElementById('soln1'));
Run Code Online (Sandbox Code Playgroud)

这是我个人的最爱.

var ListItem = React.createClass({
    getInitialState: function() {
        return {
            isSelected: false
        };
    },
    handleClick: function() {
        this.setState({
            isSelected: true
        })
    },
    render: function() {
        var isSelected = this.state.isSelected;
        var style = {
            'background-color': ''
        };
        if (isSelected) {
            style = {
                'background-color': '#ccc'
            };
        }
        return (
            <li onClick={this.handleClick} style={style}>{this.props.content}</li>
        );
    }
});

var TestApp2 = React.createClass({
    getComponent: function(index) {
        $(this.getDOMNode()).find('li:nth-child(' + index + ')').css({
            'background-color': '#ccc'
        });
    },
    render: function() {
        return (
            <div>
             <ul>
              <ListItem content="Component 1" />
              <ListItem content="Component 2" />
              <ListItem content="Component 3" />
             </ul>
            </div>
        );
    }
});
React.renderComponent(<TestApp2 /> , document.getElementById('soln2'));
Run Code Online (Sandbox Code Playgroud)

这是一个DEMO

我希望这有帮助.

  • 不建议在渲染函数中应用绑定,因为它会在每次渲染组件时执行.您可以将其移动到在生命周期开始时运行的某个功能 (8认同)

svn*_*vnm 34

以下是如何使用es6语法定义一个响应onClick事件处理程序,它正在回答问题标题

import React, { Component } from 'react';

export default class Test extends Component {
  handleClick(e) {
    e.preventDefault()
    console.log(e.target)
  }

  render() {
    return (
      <a href='#' onClick={e => this.handleClick(e)}>click me</a>
    )
  }
}
Run Code Online (Sandbox Code Playgroud)

  • `render`和arrow函数都不应该在`render`方法中使用,因为它们会导致每次都创建一个新函数.这具有改变组件状态的效果,并且总是重新呈现具有改变状态的组件.对于单个`a`来说,这没什么大不了的.对于具有可点击项目的生成列表,这很快就会成为一件大事.这就是它特别警告的原因. (9认同)

itc*_*per 19

使用ECMA2015.箭头功能使"this"更加直观.

import React from 'react';


class TestApp extends React.Component {
   getComponent(e, index) {
       $(e.target).css({
           'background-color': '#ccc'
       });
   }
   render() {
       return (
           <div>
             <ul>
               <li onClick={(e) => this.getComponent(e, 1)}>Component 1</li>
               <li onClick={(e) => this.getComponent(e, 2)}>Component 2</li>
               <li onClick={(e) => this.getComponent(e, 3)}>Component 3</li>
             </ul>
           </div>
       );
   }
});
React.renderComponent(<TestApp /> , document.getElementById('soln1'));`
Run Code Online (Sandbox Code Playgroud)

  • 这实际上对性能不利,因为它在每个渲染时创建一个新函数.请参阅:/sf/ask/2567441341/ (5认同)
  • `index`在这里什么都不做? (2认同)

dir*_*0vz 13

如果你使用的是ES6,这里有一些简单的示例代码:

import React from 'wherever_react_is';

class TestApp extends React.Component {

  getComponent(event) {
      console.log('li item clicked!');
      event.currentTarget.style.backgroundColor = '#ccc';
  }

  render() {
    return(
       <div>
         <ul>
            <li onClick={this.getComponent.bind(this)}>Component 1</li>
         </ul>
       </div>
    );
  }
}

export default TestApp;
Run Code Online (Sandbox Code Playgroud)

在ES6类主体中,函数不再需要'function'关键字,并且不需要用逗号分隔.如果您愿意,也可以使用=>语法.

以下是动态创建元素的示例:

import React from 'wherever_react_is';

class TestApp extends React.Component {

constructor(props) {
  super(props);

  this.state = {
    data: [
      {name: 'Name 1', id: 123},
      {name: 'Name 2', id: 456}
    ]
  }
}

  getComponent(event) {
      console.log('li item clicked!');
      event.currentTarget.style.backgroundColor = '#ccc';
  }

  render() {        
       <div>
         <ul>
         {this.state.data.map(d => {
           return(
              <li key={d.id} onClick={this.getComponent.bind(this)}>{d.name}</li>
           )}
         )}
         </ul>
       </div>
    );
  }
}

export default TestApp;
Run Code Online (Sandbox Code Playgroud)

请注意,每个动态创建的元素都应具有唯一的引用"key".

此外,如果您想将实际数据对象(而不是事件)传递到onClick函数中,则需要将其传递给bind.例如:

新的onClick功能:

getComponent(object) {
    console.log(object.name);
}
Run Code Online (Sandbox Code Playgroud)

传入数据对象:

{this.state.data.map(d => {
    return(
      <li key={d.id} onClick={this.getComponent.bind(this, d)}>{d.name}</li>
    )}
)}
Run Code Online (Sandbox Code Playgroud)


Ali*_*eza 5

使用React元素处理事件与处理DOM元素上的事件非常相似。有一些语法上的差异:

  • React事件使用camelCase命名,而不是小写。
  • 使用JSX,您可以传递一个函数作为事件处理程序,而不是字符串。

因此,正如React文档中提到的那样,它们在事件处理方面与普通HTML非常相似,但是在React中使用camelcase的事件名称,因为它们不是真正的HTML,而是JavaScript,而且您在传递函数调用时传递了函数HTML的字符串格式是不同的,但是概念非常相似...

看下面的例子,注意事件传递给函数的方式:

function ActionLink() {
  function handleClick(e) {
    e.preventDefault();
    console.log('The link was clicked.');
  }

  return (
    <a href="#" onClick={handleClick}>
      Click me
    </a>
  );
}
Run Code Online (Sandbox Code Playgroud)