2017-05-09 26 views
2

我创建了一个辅助函数,当我单击按钮时,它会在我的组件中动态地创建元素。但它不显示一半的HTML我试图追加到父div。在React组件中动态创建元素

它正确地添加了标签为html,但其余的只是纯文本。任何人都能看到为什么

用于动态创建内容的功能:

function addElement(parentId, elementTag, elementId, html) { 
    let parentElement = document.getElementById(parentId); 
    let elementToAdd = document.createElement(elementTag); 
    elementToAdd.setAttribute('id', elementId); 
    elementToAdd.innerHTML = html; 
    parentElement.appendChild(elementToAdd); 
} 

我的我的组件内功能:

static addMatch() { 
    let html = "<div className=\"form-group\"><label className=\"control-label\">Add Match</label>" + 
     "<DatePickerselected={this.state.startDate}onChange={this.handleChange.bind(this)}/></div>"; 
    addElement('fixture-parent', 'newMatch', uuid(), html); 
} 

我完全反应成份低于:

import React, {Component} from "react"; 
import DatePicker from "react-datepicker"; 
import {addElement} from "../../helpers/DynamicElementsHelper"; 
import moment from "moment"; 
const uuid = require('uuid/v1'); 

require('react-datepicker/dist/react-datepicker.css'); 

class Fixtures extends Component { 

    constructor() { 
     super(); 
     Fixtures.addMatch = Fixtures.addMatch.bind(this); 
     this.state = { 
      startDate: moment() 
     }; 
    } 

    handleChange(date) { 
     this.setState({ 
      startDate: date 
     }); 
    } 

    static addMatch() { 
     let html = "<div className=\"form-group\"><label className=\"control-label\">Add Match</label>" + 
      "<DatePicker selected={this.state.startDate} onChange={this.handleChange.bind(this)} /></div>"; 
     addElement('fixture-parent', 'newMatch', uuid(), html); 
    } 

    render() { 
     return (
      <div className="tray tray-center"> 
       <div className="row"> 
        <div className="col-md-8"> 
         <div className="panel mb25 mt5"> 
          <div className="panel-heading"> 
           <span className="panel-title">Fixtures</span> 
           <p>A list of fixtures currently on the system, pulled in via ajax from Ratpack</p> 
          </div> 
          <div className="panel-body p20 pb10"> 
           <div id="fixture-parent" className="form-horizontal"> 
            <div className="form-group"> 
             <label className="control-label">Add Match</label> 
             <DatePicker 
              selected={this.state.startDate} 
              onChange={this.handleChange.bind(this)}/> 
            </div> 
           </div> 
          </div> 
          <button onClick={Fixtures.addMatch }>Add Match</button> 
         </div> 
        </div> 
       </div> 
      </div> 
     ); 
    } 

    } 

    export default Fixtures; 
+0

在React中,建议不要直接与DOM交互。相反,您应该根据您拥有的数据修改JSX。你介意添加更多代码来查看问题的React部分吗? –

+1

添加了我的完整反应组件。 –

+1

我会认为这是因为DatePicker是一个反应组件,而不是html,所以渲染该html字符串将不会呈现组件,只有字符串。无论如何,这种更新DOM的方法几乎是反作用的,可能会导致很大的问题。您应该让反应处理创建其他元素。 – Ted

回答

1

在React中,建议不要直接与DOM交互。相反,您应该根据您拥有的数据修改JSX。为了您的代码,而不是与改变,你应该改变基础上,国家和显示信息的状态数据将HTML标记:

addMatch() { 
    //Add a start date to the list of starting dates 
    this.setState({ 
     listOfStartDates: [...this.state.listOfStartDates, newDate] 
    }); 
} 

render(){ 
    //For each starting date, generate a new 'match' as you called them 
    // note: this is the same as the stringyfied HTML tag OP had in the question 
    let listOfMatches = this.state.listOfStartDates.map((date)=>{ 
     return (
      <div className="form-group"> 
       <label className="control-label"> 
        Add Match 
       </label> 
       <DatePicker selected={date} onChange={this.handleChange.bind(this)} /> 
      </div> 
     ); 
    /* then in here your returned JSX would be just as OP originally had, with the exception that you would have {listOfMatches} where OP used to have the inserted list of HTML tags */ 
    return //... 
} 

由于该组件将重新渲染每次状态变化,该组件将始终拥有与开始日期一样多的匹配项。

希望有帮助!

1

把之间的空间DatePicker并选中。

"<DatePicker selected={this.state.startDate}onChange={this.handleChange.bind(this)}/></div>"; 
+0

没有工作,认为这可能是因为DatePicker是一个反应的事情,所以当它呈现在HTML中,它呈现不同 –

+0

@NickPocock权利,乍一看,这是我看到的,你可以张贴一些呈现的HTML ? –