2016-06-06 13 views
2

In meiner React-App verwende ich einige Bibliotheken (dh Material UI und React Intl), um React-Elemente als Requisiten von übergeordneteren Komponenten an "dumme Komponenten" zu übergeben Habe einen Job: rendern.Re-Render verhindern, wenn React Element als Prop übergeben wurde

Smart-Komponente:

import ActionExplore from 'material-ui/svg-icons/action/explore'; 
import { FormattedMessage } from 'react-intl'; 

export class SmartComponent extends Component { 
    render() { 
    return (
     <div> 
     <DumbComponent 
      text={<FormattedMessage id="en.dumbComponent.text" />} 
      icon={<ActionExplore/>} 
     /> 
     <AnotherDumbComponent {props.that.are.changing} /> 
     </div> 
    ); 
    } 
} 

Dumb Komponente:

import shallowCompare from 'react-addons-shallow-compare'; 

export class DumbComponent extends Component { 
    shouldComponentUpdate(nextProps, nextState) { 
    return shallowCompare(this, nextProps, nextState); 
    } 

    render() { 
    return (
     <div> 
     <h1>{this.props.text}</h1> 
     {this.props.icon} 
     </div> 
    ); 
    } 
} 

Der Vorteil, dies zu tun, ist, dass das DumbComponent braucht nichts über die Anwendungslogik (Material ui, Internationalisierung zu wissen, etc .). Es rendert einfach und lässt SmartComponent, um sich um die gesamte Geschäftslogik zu kümmern.

Der Nachteil ich mit diesem Ansatz bin Begegnung ist Leistung: DumbComponent wird immer wieder machen, auch wenn AnotherDumbComponent die Requisiten statt seiner eigenen zu ändern, weil shouldComponentUpdateimmer kehrt true. shouldComponentUpdate kann im obigen Beispiel keine genaue Gleichheitsprüfung zwischen React-Elementen durchführen.

Wie können React-Elemente in shouldComponentUpdate gleichheitsgeprüft werden? Ist das zu kostspielig? Ist das Übergeben von React-Elementen als Requisiten an dumme Komponenten eine schlechte Idee? Ist es möglich, nicht zu übergeben Reagieren Elemente als Requisiten, aber Komponenten dumm halten? Vielen Dank!

+0

Sie müssen nur sicherstellen, dass 'sollteComponentUpdate'' false' zurückgibt, wenn Sie nicht erneut rendern möchten. Wenn es einfach genug ist, warum nicht deine eigene Logik erstellen? Wie zum Beispiel: 'if (this.props.text! == nextProps.text || this.props.icon! == nextProps.icon) gibt true zurück; return false; '. – Kujira

+0

Könnten Sie ein Beispiel hinzufügen, wie Sie Ihre Requisiten mutieren? Weil ich dir nicht garantiere, dass die Unveränderlichkeits-Gleichheitsprüfung immer wahr ist, sogar für "gleiche" Daten. – Pcriulan

Antwort

0

Ob es performant ist oder nicht, hängt von Ihrem Anwendungsfall ab. Als Faustregel gilt, dass diese Art von Logik am besten verwendet wird, wenn Sie erwarten, dass Benutzereingaben nur auf untergeordnete Elemente der "dummen Komponente" und nicht auf die untergeordneten Elemente wirken.

Als Beispiel hat der Dialog von Material-UI fast die gleiche Struktur wie Sie es für seine Aktionsschaltflächen und Titel vorschlagen. (https://github.com/callemall/material-ui/blob/master/src/Dialog/Dialog.js#L292). Aber es funktioniert in diesem Fall gut, weil diese Elemente auf dem Modal sind, das sich selbst nicht ändert, es sei denn, Sie öffnen oder schließen es.

Als eine andere mögliche Problemumgehung, was passiert, wenn Sie die Objekte übergeben, die zum Erstellen der untergeordneten Elemente benötigt werden, ohne das gesamte Element zu übergeben? Ich habe das nicht versucht, also bin ich mir nicht sicher, wie gut es funktionieren wird, aber es könnte einen Versuch wert sein. Etwas in dem Ausmaß von;

<DumbComponent 
    textComponent={FormattedMessage} 
    textProps={{id: "en.dumbComponent.text"}}/> 

//In DumbComponent; 

render(){ 
    return (
     <div> 
      <h1> 
       <this.props.textComponent {...this.props.textProps}/> 
      </h1> 

     </div> 
    ); 
} 

Könnte Ihnen einige konkretere Dinge geben, mit denen Sie spielen können, wenn Sie feststellen, ob Sie aktualisieren sollten oder nicht.

0

Ich löste dies, indem ich diese einfachen React-Elemente in Immutable.js-Maps umwandelte und diese stattdessen als Requisiten übergab.

Dieser Artikel war sehr hilfreich: https://www.toptal.com/react/react-redux-and-immutablejs

Immutable.js uns auf die Ineffizienz der tiefen Gleichheit Kontrollen ohne Rückgriff Änderungen in JavaScript-Objekten/Arrays zu erkennen erlaubt, was wiederum ermöglicht teure Wieder vermeiden Reagieren auf Rendervorgänge, wenn sie nicht benötigt werden.

Verwandte Themen