2017-02-23 7 views
0

ReactJSとReact-Routerを使用してSPAを構築しています。アプリケーションが私の主なコンポーネントであり、そこから他のすべてが生じる。そのコンポーネントでは、ToastContainerを追加して、そのコンポーネントからうまく動作します。子コンポーネントに関数を渡し、メッセージを呼び出して表示できるようにしました。私はすべてのメッセージに対して1つのReact-Toastr Containerを使用する

Uncaught TypeError: Cannot read property 'toastContainer' of undefined 

アプリケーション/メインコンポーネント

import React from 'react'; 
import ReactDOM from 'react-dom'; 
import { Router, Route, Link, IndexRoute, browserHistory, hashHistory } from 'react-router'; 
import ParameterContainer from './components/parameter/parameter-container'; 
import ParameterValueContainer from './components/parameter/parameter-value-container'; 
import NavMenu from './components/navigation/nav-menu'; 
import {Alert} from 'react-bootstrap'; 
import ReactToastr from 'react-toastr'; 
import {ToastContainer, ToastMessage} from 'react-toastr'; 

let ToastMessageFactory = React.createFactory(ToastMessage.animation); 

// Main component and root component 
export default class App extends React.Component { 

    constructor(props) { 
     super(props); 
     this.state = { 
      userId: null, 
      roles: null, 
      parameterTypes: { 
       'STRING': 'STRING', 
       'BOOLEAN': 'BOOLEAN', 
       'INTEGER': 'INTEGER', 
       'DECIMAL': 'DECIMAL' 
      }, 
      parameterGroups: { 
       1: 'POS', 
       2: 'MenuStructure' 
      } 
     }; 
    } 

    componentDidMount() { 
     //this.addAlert('Success', 'Parameter Created'); 
     this.addErrorAlert('Ohhhh snap!', 'You messed up Rodney, you messed up bad!'); 
    } 

    addAlert(title, message) { 
     this.refs.toastContainer.success(
      title, 
      message, 
      { 
       timeOut: 10000, 
       extendedTimeOut: 10000, 
       preventDuplicates: true, 
       positionClass: "toast-bottom-full-width", 
       showMethod: "fadeIn", 
       hideMethod: "fadeOut" 
      } 
     ); 
    } 

    addErrorAlert(title, message) { 
     this.refs.toastContainer.error(
      message, 
      title, 
      { 
       timeOut: 10000, 
       extendedTimeOut: 10000, 
       preventDuplicates: true, 
       positionClass: "toast-bottom-full-width", 
       showMethod: "fadeIn", 
       hideMethod: "fadeOut" 
      } 
     ); 
    } 

    render() { 

     return (
      <div> 
       <NavMenu /> 
       <div className="container-fluid"> 
        {React.Children.map(
         this.props.children, 
         child => React.cloneElement(child, 
          { 
           parentState: this.state, 
           path: this.props.route.path, 
           alertCallback: this.addErrorAlert 
          }) 
        )} 
        <ToastContainer ref="toastContainer" toastMessageFactory={ToastMessageFactory} className="toast-bottom-full-width"> 
        </ToastContainer> 
       </div> 
      </div> 
     ) 
    } 
} 

// page for 404 
class NoMatch extends React.Component { 
    render() { 
     return (
      <div className="container"> 
       <Alert bsStyle="danger"> 
        <h1>404: Not Found</h1> 
        <h3>The requested resource does not exist!</h3> 
       </Alert> 
       <img src="images/404.png" style={{display: 'block', margin: '0 auto', width: 300, height: '*'}} /> 
      </div> 
     ) 
    } 
} 

// render the application 
ReactDOM.render((
    <Router history={hashHistory}> 
     <Route path="/" component={App}> 
      <Route path="parameter" component={ParameterContainer} /> 
      <Route path="parametervalues" component={ParameterValueContainer} /> 
      <Route path="*" component={NoMatch}/> 
     </Route> 
    </Router> 
), document.getElementById('react')) 

得るのにあなたはそれが動作することを言及した後、私は子コンポーネントにこのよう

componentDidMount() { 
    this.props.alertCallback("OHHHH NOOOO!!!!", "Something has gone wrong!"); 
    this.fetchFromApi(); 
} 
+0

簡単な質問ですが、アプリケーション/コンテナからaddErrorAlert()を呼び出すと、トースターは機能しますか?私はあなたがcomponentDidMountからそれを呼んでいることを意味します、それは動作しますか? –

+0

はい、そのコンポーネントから正常に動作します – jkratz55

+0

どのようなバージョンの反応型トーストが使用していますか?代わりにToastMessageAnimatedを使用していないのはなぜですか?ドキュメントは時代遅れであると思われ、提供されたサンプルはもう機能しなくなりました... – olefrank

答えて

1

をコールバックを使用していることをしようとするとApp/Containerでは、あなたのコンストラクタで関数をバインドすることをお勧めしますので、次のようになります:

constructor(props) { 
    super(props); 
    this.state = { 
     userId: null, 
     roles: null, 
     parameterTypes: { 
      'STRING': 'STRING', 
      'BOOLEAN': 'BOOLEAN', 
      'INTEGER': 'INTEGER', 
      'DECIMAL': 'DECIMAL' 
     }, 
     parameterGroups: { 
      1: 'POS', 
      2: 'MenuStructure' 
     } 
    }; 
    this.addErrorAlert = this.addErrorAlert.bind(this); 
} 

問題が解決するはずです。問題がなければ教えてください。

イベント処理の詳細については、documentationをお読みください。そこに、各イベントハンドラをバインドする必要がある理由の説明があります。

+0

それはトリックでした! – jkratz55

+0

@ jkratz55素晴らしい! –

関連する問題