私は、ディスプレイ "状態"を維持する接続されたコンポーネントと、2つのコンポーネント間の通信に必要な他のいくつかのものを持っています。私は、このオーバーアーチ型コンポーネントの子である2つの接続されたコンポーネントを持っています。 「状態」コンポーネント内のフラグに応じて、一方または他方の子コンポーネントがレンダリングされる。React Redux mapStateToPropsが更新時に起動しない
EditorStateコンポーネント:
import React from 'react';
import {connect} from 'react-redux';
import Library from '../library/index';
import Editor from '../editor/index';
import {
initialize,
editorState
} from './actions';
class EditorState extends React.Component {
componentWillMount() {
const {dispatch} = this.props;
dispatch(initialize());
}
render() {
const {state} = this.props;
switch(state) {
case editorState.Library:
return <Library />
case editorState.Editor:
return <Editor />
default:
return null;
}
}
}
export default connect(state => {
return state.EditorStateReducer;
})(EditorState);
EditorStateアクション:
export const EDITOR_STATE_INITIALIZE = 'EDITOR_STATE_INITIALIZE';
export const editorState = {
Library: 'library',
Editor: 'editor'
}
export const initialize = ({
type: EDITOR_STATE_INITIALIZE,
state: editorState.Library
});
EditorStateリデューサー:
import {
EDITOR_STATE_INITIALIZE
} from './actions';
const init =() => ({
state: null
});
export default (state = init(), action) => {
switch(action.type) {
case EDITOR_STATE_INITIALIZE:
return {
...state,
state: action.state
}
default:
return {...state}
}
}
ライブラリコンポーネント:
単にコードを表示するには良いかもしれませんimport React from 'react';
import {connect} from 'react-redux';
import {Page} from '../../../components/page/index';
import LibraryItem from '../../../components/library-item/library-item';
import {
initialize
} from './actions';
class Library extends React.Component {
componentWillMount() {
const {dispatch} = this.props;
dispatch(initialize());
}
render() {
const {templates} = this.props;
const editorTemplates = templates.map(template =>
<LibraryItem template={template} />
);
return (
<Page>
<div className="card-flex library-table">
{editorTemplates}
</div>
</Page>
)
}
}
export default connect(state => {
return state.LibraryReducer;
})(Library);
ライブラリアクション:
import {
client,
serviceUrl
} from '../../../common/client';
export const LIBRARY_INITIALIZE = 'LIBRARY_INITIALIZE';
export const initialize =() => dispatch => {
client.get(`${serviceUrl}/templates`).then(resp => {
dispatch({
type: LIBRARY_INITIALIZE,
templates: resp.templates
});
});
}
ライブラリリデューサー:
import {
LIBRARY_INITIALIZE
} from './actions';
const init =() => ({
templates: []
});
export default (state = init(), action) => {
switch(action.type) {
case LIBRARY_INITIALIZE:
return {
...state,
templates: action.templates
}
default:
return {...state}
}
}
私が午前の問題は、ライブラリコンポーネントでmapStateToPropsがLIBRARY_INITIALIZEの発送時に呼び出されていないということです。 EditorStateとLibraryのmapStateToPropsとLibrary reducerのLIBRARY_INITIALIZEスイッチのブレークポイントの両方にブレークポイントがあります。デバッグページの読み込みはこのように書きます:
EditorState mapStateToProps - state.EditorStateReducer.state == editorState.Library
ライブラリmapStateToProps - - state.LibraryReducer.templates state.EditorStateReducer.stateは
EditorState mapStateToProps nullです== []
ライブラリ減速初期化 - action.templates == [{template1を}、{template2}等]
EditorState mapStateToProps - state.LibraryReducer.templates == [{template1}、{template2}など]
何もしません。ライブラリのmapStateToPropsも起動するので、ライブラリでテンプレートを再レンダリングすることができます。しかし、これは起こっていません。なぜこれは起こっていないのですか?私はこの上に私の髪を引き出す準備ができています...
を参照することができますか? mapStateToPropsはディスパッチ時にすべてのサブスクライバに対して呼び出されるため、Reactが再レンダリングするかどうかを判断できるように小道具を更新できます。それは別の方法ではありません。 ご協力いただきありがとうございますが、これは正しくありません。そうだった場合、ReduxはReactで正常に動作しませんでした。 この質問で回答したmarkeriksonを参照できます:https://stackoverflow.com/questions/41646353 – light
あなたのリンクの質問に誰が回答しているかを見て、もう少し実験を行いました。 libraryInitialize変数をLibraryReducerに追加し、次にEditorStateのcomponentWillReceiveの小道具で、新しいlibraryInitializeが古いものと等しくなかった場合にthrowアクションを送出しました。確かに、ライブラリのmapStateToPropsは正しいテンプレート値で起動します。私はそれがまさにそれだったので、これを受け入れられた答えとしてマークしています。しかし、これはReduxが階層的に接続されたコンポーネントをうまく扱わないという厳しい制限のようです。 – light
私は同じ問題があったとき、それは本当です。私が見つけたのは、従属行為を発射したことが、一種の反パターンであることです。可能な限り、あなたの従属アクションをクラブにし、できるだけリデューサーに多くのビジネスロジックを置く必要があります。私はこれが理にかなってほしい。 –