簡體   English   中英

如何將來自兩個組件的數據存儲在單個對象/狀態中?

[英]How do I store data from two components in a single object/state?

我有一個帶有兩個操縱桿組件的操縱桿應用程序。 我想在父組件“App.js”中的一個地方獲得坐標,該組件將每隔一定時間更新一次,然后這些坐標將通過 socket.io 發送到服務器。 我嘗試了很多事情,比如使用傳遞給操縱桿的回調,然后從父組件設置狀態。 但它不起作用。 這些值被單獨存儲。 我有 reactjs 的初學者知識。

App.js 的一部分

class App extends React.Component {


    constructor(props) {
        super(props);

        this.state = {
            connection: 'close',
            view: "joystick",
            logs: [],
            coordinates: {A: {x:0, y:0},
            B: {x:0, y:0}}
        }

        this.socket = socketIOClient({'reconnectionAttempts': 1,});
    }

    getJoystickValue = (coords) => {
        const k = Object.keys(coords)[0]
        this.setState({coordinates[k]: coords[k]})

    }

render () {
<div className="container">
                    <Header status={this.state.connection} viewToggle={this.toggleView}></Header>
                    <div className="pad">
                        <Joystick jname="A" getValues={this.getJoystickValue} socketIO={this.socket}></Joystick>
                        <Log logText={this.state.logs}></Log>
                        <Joystick jname="B" getValues={this.getJoystickValue} socketIO={this.socket}></Joystick>              

                    </div>
                </div>
}
}

操縱桿.js

class Joystick extends React.Component {

    constructor(props) {
        super(props);
        this.maxDiff = 50;
        this.dragStart = null;
        this.currentPos = { x: 0, y: 0 };
        this.stick = React.createRef();
        this.stickArea = React.createRef();
    }

    componentDidMount() {
        this.stick.current.addEventListener('mousedown', this.handleMouseDown);
        this.stick.current.addEventListener('touchstart', this.handleMouseDown);
        this.stickArea.current.addEventListener('mousemove', this.handleMouseMove);
        document.addEventListener('mouseup', this.handleMouseUp);
        this.stickArea.current.addEventListener('touchmove', this.handleMouseMove);
        this.stickArea.current.addEventListener('touchend', this.handleMouseUp);


        setInterval(() => {
           this.props.getValues(this.getPosition());
        }, 1500);

    }


    getPosition = () => {
        const nm = this.props.jname;
        const coords = {};
        coords[nm] = this.currentPos;
        return coords;
    }

    checkConstraints = (touchArray) => {
      let touch = null;
      const constraints = this.stickArea.current.getBoundingClientRect();
      for (const point of touchArray) {
         if ((point.clientX < constraints.right && point.clientX > constraints.left)
              && (point.clientY < constraints.bottom && point.clientY > constraints.top)) {
                touch = point
         }
      }

      if (touch) {
        return touch;
      }
      return null;

    }

    handleMouseDown = (event) => {
        this.stick.current.style.transition = '0s';
        if (event.changedTouches) {
            this.dragStart = {
              x: event.changedTouches[0].clientX,
              y: event.changedTouches[0].clientY,
            };
            return;
          }
          this.dragStart = {
            x: event.clientX,
            y: event.clientY,
          };
        };

    handleMouseMove = (event) => {
        if (this.dragStart === null) return;
        event.preventDefault();

        const endtouch = new Event('touchend', {
          view: window,
          bubbles: true,
          cancelable: true
        });

        if (event.changedTouches) {
          const p = this.checkConstraints(event.changedTouches);
          if (!p) {
            this.stick.current.dispatchEvent(endtouch);
            return;
          }
          event.clientX = p.clientX;
          event.clientY = p.clientY;
        }

        const xDiff = event.clientX - this.dragStart.x;
        const yDiff = event.clientY - this.dragStart.y;
        const angle = Math.atan2(yDiff, xDiff);
            const distance = Math.min(this.maxDiff, Math.hypot(xDiff, yDiff));
            const xNew = distance * Math.cos(angle);
            const yNew = distance * Math.sin(angle);
        this.stick.current.style.transform = `translate3d(${xNew}px, ${yNew}px, 0px)`;
        this.currentPos = { x: xNew, y: -yNew };

      };

    handleMouseUp = (event) => {
        if (this.dragStart === null) return;
        this.stick.current.style.transition = '.2s';
        this.stick.current.style.transform = `translate3d(0px, 0px, 0px)`;
        this.dragStart = null;
        this.currentPos = { x: 0, y: 0 };
      };


    render () {
        return (
            <div className="stick-area" ref={this.stickArea}>
            <div id={this.props.jname} className="base">
                <div className="stick" ref={this.stick}></div>
            </div>
            </div>
        );
    }
}

export default Joystick;

編輯:Siva Kondapi Venkata 的更正工作正常,但是當使用emit 通過socket.io 發送時,它會在兩者之間獲取空坐標對象。 服務器收到的值

更新 getJoystickValue 方法如下。 取坐標的當前狀態值,合並新數據並更新狀態。

getJoystickValue = coords => 
    this.setState({ coordinates: {...this.state.coordinates, ...coords} })

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM