【问题标题】:react: strange behaviour on hover反应:悬停时的奇怪行为
【发布时间】:2017-03-22 08:36:31
【问题描述】:

我是 React 新手,正在制作一个小型“Tweet box”应用程序以供练习。有一些奇怪的东西我不明白...

用户可以在推文中添加图片。图像作为对象存储在数组中,并通过循环和运行renderThumb() 方法呈现。在图像悬停时,我在图像的右上角显示一个小的“删除图标”。单击时图像被删除。

  1. 当我悬停图像时,所有图像显示都悬停(图标在所有图像上可见)。为什么?

  2. renderThumb() 在悬停时执行。为什么? (它应该只在渲染图像时执行)。

  3. 我使用this.state.images.filter( (img) => { return img.id != image.id; } ); 删除图像。但它不起作用。为什么?

//谢谢, 奥莱

TweetBox.js

import React, {Component, PropTypes} from 'react';
import './tweetbox.css';

import ReactCSSTransitionGroup from 'react-addons-css-transition-group'

import TextArea from './TextArea';

class TweetBox extends Component {

    numPhotoChars = 17;
    numStartChars = 140;
    author = 'Ole Frank Jensen';
    counter = 0;
    imageUrl = 'http://i.imgur.com/Crcz7dJ.jpg';

    constructor(props) {
        super(props);

        this.state = {
            text: '',
            author: this.author,
            date: 0,
            startValue: this.numStartChars,
            images: []
        };

        this.onTextareaChange = this.onTextareaChange.bind(this);
        this.getNumRemainingChars = this.getNumRemainingChars.bind(this);
        this.disableTextarea = this.disableTextarea.bind(this);
        this.addImage = this.addImage.bind(this);
        this.removeImage = this.removeImage.bind(this);
        this.submitTweet = this.submitTweet.bind(this);
        this.onMouseOver = this.onMouseOver.bind(this);
        this.onMouseOut = this.onMouseOut.bind(this);

    }

    onTextareaChange(e) {
        this.setState({text: e.target.value});
    }

    getNumRemainingChars() {
        return this.state.startValue - this.state.text.length;
    }

    disableTextarea() {
        return this.state.text.length > 0 || this.state.images.length;
    }

    addImage() {
        if (this.getNumRemainingChars() >= this.numPhotoChars) {
            const startValue = this.state.startValue - this.numPhotoChars;
            const image = Object.assign({}, {
                id: this.counter += 1,
                url: this.imageUrl
            });

            this.setState({startValue: startValue});
            this.setState({images: [...this.state.images, image]});
        }
    }

    removeImage(image) {

        let arr = this.state.images.filter( function(img) { return img.id != image.id; } );
        console.log(image, arr);

        this.setState({
            images: this.state.images.filter( function(img) { return img.id != image.id; } ),
            startValue: this.state.startValue + this.numPhotoChars,
            hover: false
        });
    }

    submitTweet(e) {
        e.preventDefault();

        // compose
        const tweet = {
            text: this.state.text,
            author: this.state.author,
            date: new Date().getTime(),
            images: this.state.images
        };

        // store
        this.props.storeTweet(tweet);

        // reset
        this.setState({
            text: '',
            images: [],
            startValue: this.numStartChars
        });
    }

    onMouseOver() { console.log('over'); this.setState({hover: true}); }
    onMouseOut() { console.log('out'); this.setState({hover: false}); }

    renderThumb(image, index) {
        console.log(index);
        let k = 'image-' + index;
        return (
            <div key={k} className="col-xs-3">
                <div className="thumbnail-wrapper">
                    <img src={image.url}
                         alt="My something"
                         className="img-thumbnail"
                         onMouseOver={ this.onMouseOver }
                         onMouseOut={ this.onMouseOut }/>
                    <div className={"img-thumbnail-close-btn " + (this.state.hover ? 'show' : 'hidden')}
                         onMouseOver={ this.onMouseOver }
                         onMouseOut={ this.onMouseOut }
                         onClick={ () => { this.removeImage({image}) } }>
                        <span className="fa-stack fa-1x">
                            <i className="fa fa-circle fa-stack-2x white-background"></i>
                            <i className="fa fa-circle-thin fa-stack-2x black-border"></i>
                            <i className="fa fa-times fa-stack-1x"></i>
                        </span>
                    </div>
                </div>
            </div>
        );
    }

    render() {
        return (
            <div className="tweet-box">
                <div className="row">
                    <div className="col-xs-6 col-xs-offset-3">
                        <div className="well tweet-box clearfix">

                            <h1>Tweet Box</h1>

                            <TextArea value={ this.state.text }
                                      maxLength={this.state.startValue}
                                      onChange={this.onTextareaChange}/>
                            <span className="pull-right">
                                <em>{this.getNumRemainingChars()} characters left...</em>
                            </span>

                            <br/>

                            <div className="row">
                                <ReactCSSTransitionGroup transitionName="example"
                                                         transitionEnterTimeout={500}
                                                         transitionLeaveTimeout={500}>
                                    {
                                        this.state.images.map((image, index) => {
                                            return this.renderThumb(image, index);
                                        })
                                    }
                                </ReactCSSTransitionGroup>
                            </div>


                            <br/>

                            <div className="row">
                                <div className="col-xs-6">
                                    <button className="btn btn-default add-photo pull-left"
                                            onClick={this.addImage}>
                                        <i className="fa fa-camera"></i> Add photo
                                    </button>
                                </div>
                                <div className="col-xs-6">
                                    <button onClick={this.submitTweet} className="btn btn-primary pull-right"
                                            disabled={!this.disableTextarea()}>
                                        <i className="fa fa-pencil-square-o"></i> Tweet!
                                    </button>
                                </div>
                            </div>

                        </div>
                    </div>
                </div>
            </div>
        )
    }

}

TweetBox.propTypes = {
    storeTweet: PropTypes.func.isRequired
};

export default TweetBox;

【问题讨论】:

    标签: javascript reactjs


    【解决方案1】:

    你的状态设计的很笼统,id建议你在每张图片上加id。并添加一个接受该 ID 的处理程序。这样你就可以只改变特定图像的悬停。

    this.setState({hover: true})
    

    您可以在下面看到您正在向所有图像添加相同的处理程序, 所以一个图像悬停将导致它们都被悬停。

    <img src={image.url}
      alt="My something"
      className="img-thumbnail"
      onMouseOver={ this.onMouseOver }
      onMouseOut={ this.onMouseOut }/>
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2016-08-12
      • 1970-01-01
      • 1970-01-01
      • 2019-03-06
      • 2014-06-30
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多