@@ -2615,129 +2615,140 @@ function react(gd, data, layout, config) {
2615
2615
configChanged = diffConfig ( oldConfig , gd . _context ) ;
2616
2616
}
2617
2617
2618
- gd . data = data || [ ] ;
2619
- helpers . cleanData ( gd . data ) ;
2620
- gd . layout = layout || { } ;
2621
- helpers . cleanLayout ( gd . layout ) ;
2622
-
2623
- applyUIRevisions ( gd . data , gd . layout , oldFullData , oldFullLayout ) ;
2624
-
2625
- // "true" skips updating calcdata and remapping arrays from calcTransforms,
2626
- // which supplyDefaults usually does at the end, but we may need to NOT do
2627
- // if the diff (which we haven't determined yet) says we'll recalc
2628
- Plots . supplyDefaults ( gd , { skipUpdateCalc : true } ) ;
2629
-
2630
- var newFullData = gd . _fullData ;
2631
- var newFullLayout = gd . _fullLayout ;
2632
- var immutable = newFullLayout . datarevision === undefined ;
2633
- var transition = newFullLayout . transition ;
2634
-
2635
- var relayoutFlags = diffLayout ( gd , oldFullLayout , newFullLayout , immutable , transition ) ;
2636
- var newDataRevision = relayoutFlags . newDataRevision ;
2637
- var restyleFlags = diffData ( gd , oldFullData , newFullData , immutable , transition , newDataRevision ) ;
2638
-
2639
- // TODO: how to translate this part of relayout to Plotly.react?
2640
- // // Setting width or height to null must reset the graph's width / height
2641
- // // back to its initial value as computed during the first pass in Plots.plotAutoSize.
2642
- // //
2643
- // // To do so, we must manually set them back here using the _initialAutoSize cache.
2644
- // if(['width', 'height'].indexOf(ai) !== -1 && vi === null) {
2645
- // fullLayout[ai] = gd._initialAutoSize[ai];
2646
- // }
2647
-
2648
- if ( updateAutosize ( gd ) ) relayoutFlags . layoutReplot = true ;
2649
-
2650
- // clear calcdata and empty categories if required
2651
- if ( restyleFlags . calc || relayoutFlags . calc ) {
2652
- gd . calcdata = undefined ;
2653
- var allNames = Object . getOwnPropertyNames ( newFullLayout ) ;
2654
- for ( var q = 0 ; q < allNames . length ; q ++ ) {
2655
- var name = allNames [ q ] ;
2656
- var start = name . substring ( 0 , 5 ) ;
2657
- if ( start === 'xaxis' || start === 'yaxis' ) {
2658
- var emptyCategories = newFullLayout [ name ] . _emptyCategories ;
2659
- if ( emptyCategories ) emptyCategories ( ) ;
2618
+ if ( configChanged ) {
2619
+ // Save event listeners as newPlot will remove them
2620
+ const eventListeners = gd . _ev . eventNames ( ) . map ( name => [ name , gd . _ev . listeners ( name ) ] ) ;
2621
+ plotDone = exports . newPlot ( gd , data , layout , config )
2622
+ . then ( ( ) => {
2623
+ for ( const [ name , callbacks ] of eventListeners ) {
2624
+ callbacks . forEach ( ( cb ) => gd . on ( name , cb ) ) ;
2625
+ }
2626
+
2627
+ // Call react in case transition should have occurred along with config change
2628
+ return exports . react ( gd , data , layout , config )
2629
+ } ) ;
2630
+ } else {
2631
+ gd . data = data || [ ] ;
2632
+ helpers . cleanData ( gd . data ) ;
2633
+ gd . layout = layout || { } ;
2634
+ helpers . cleanLayout ( gd . layout ) ;
2635
+
2636
+ applyUIRevisions ( gd . data , gd . layout , oldFullData , oldFullLayout ) ;
2637
+
2638
+ // "true" skips updating calcdata and remapping arrays from calcTransforms,
2639
+ // which supplyDefaults usually does at the end, but we may need to NOT do
2640
+ // if the diff (which we haven't determined yet) says we'll recalc
2641
+ Plots . supplyDefaults ( gd , { skipUpdateCalc : true } ) ;
2642
+
2643
+ var newFullData = gd . _fullData ;
2644
+ var newFullLayout = gd . _fullLayout ;
2645
+ var immutable = newFullLayout . datarevision === undefined ;
2646
+ var transition = newFullLayout . transition ;
2647
+
2648
+ var relayoutFlags = diffLayout ( gd , oldFullLayout , newFullLayout , immutable , transition ) ;
2649
+ var newDataRevision = relayoutFlags . newDataRevision ;
2650
+ var restyleFlags = diffData ( gd , oldFullData , newFullData , immutable , transition , newDataRevision ) ;
2651
+
2652
+ // TODO: how to translate this part of relayout to Plotly.react?
2653
+ // // Setting width or height to null must reset the graph's width / height
2654
+ // // back to its initial value as computed during the first pass in Plots.plotAutoSize.
2655
+ // //
2656
+ // // To do so, we must manually set them back here using the _initialAutoSize cache.
2657
+ // if(['width', 'height'].indexOf(ai) !== -1 && vi === null) {
2658
+ // fullLayout[ai] = gd._initialAutoSize[ai];
2659
+ // }
2660
+
2661
+ if ( updateAutosize ( gd ) ) relayoutFlags . layoutReplot = true ;
2662
+
2663
+ // clear calcdata and empty categories if required
2664
+ if ( restyleFlags . calc || relayoutFlags . calc ) {
2665
+ gd . calcdata = undefined ;
2666
+ var allNames = Object . getOwnPropertyNames ( newFullLayout ) ;
2667
+ for ( var q = 0 ; q < allNames . length ; q ++ ) {
2668
+ var name = allNames [ q ] ;
2669
+ var start = name . substring ( 0 , 5 ) ;
2670
+ if ( start === 'xaxis' || start === 'yaxis' ) {
2671
+ var emptyCategories = newFullLayout [ name ] . _emptyCategories ;
2672
+ if ( emptyCategories ) emptyCategories ( ) ;
2673
+ }
2660
2674
}
2675
+ // otherwise do the calcdata updates and calcTransform array remaps that we skipped earlier
2676
+ } else {
2677
+ Plots . supplyDefaultsUpdateCalc ( gd . calcdata , newFullData ) ;
2661
2678
}
2662
- // otherwise do the calcdata updates and calcTransform array remaps that we skipped earlier
2663
- } else {
2664
- Plots . supplyDefaultsUpdateCalc ( gd . calcdata , newFullData ) ;
2665
- }
2666
2679
2667
- // Note: what restyle/relayout use impliedEdits and clearAxisTypes for
2668
- // must be handled by the user when using Plotly.react.
2680
+ // Note: what restyle/relayout use impliedEdits and clearAxisTypes for
2681
+ // must be handled by the user when using Plotly.react.
2669
2682
2670
- // fill in redraw sequence
2671
- var seq = [ ] ;
2683
+ // fill in redraw sequence
2684
+ var seq = [ ] ;
2672
2685
2673
- if ( frames ) {
2674
- gd . _transitionData = { } ;
2675
- Plots . createTransitionData ( gd ) ;
2676
- seq . push ( addFrames ) ;
2677
- }
2686
+ if ( frames ) {
2687
+ gd . _transitionData = { } ;
2688
+ Plots . createTransitionData ( gd ) ;
2689
+ seq . push ( addFrames ) ;
2690
+ }
2678
2691
2679
- // Transition pathway,
2680
- // only used when 'transition' is set by user and
2681
- // when at least one animatable attribute has changed,
2682
- // N.B. config changed aren't animatable
2683
- if ( newFullLayout . transition && ! configChanged && ( restyleFlags . anim || relayoutFlags . anim ) ) {
2684
- if ( relayoutFlags . ticks ) seq . push ( subroutines . doTicksRelayout ) ;
2692
+ // Transition pathway,
2693
+ // only used when 'transition' is set by user and
2694
+ // when at least one animatable attribute has changed,
2695
+ // N.B. config changed aren't animatable
2696
+ if ( newFullLayout . transition && ( restyleFlags . anim || relayoutFlags . anim ) ) {
2697
+ if ( relayoutFlags . ticks ) seq . push ( subroutines . doTicksRelayout ) ;
2685
2698
2686
- Plots . doCalcdata ( gd ) ;
2687
- subroutines . doAutoRangeAndConstraints ( gd ) ;
2699
+ Plots . doCalcdata ( gd ) ;
2700
+ subroutines . doAutoRangeAndConstraints ( gd ) ;
2688
2701
2689
- seq . push ( function ( ) {
2690
- return Plots . transitionFromReact ( gd , restyleFlags , relayoutFlags , oldFullLayout ) ;
2691
- } ) ;
2692
- } else if ( restyleFlags . fullReplot || relayoutFlags . layoutReplot || configChanged ) {
2693
- gd . _fullLayout . _skipDefaults = true ;
2694
- seq . push ( exports . _doPlot ) ;
2695
- } else {
2696
- for ( var componentType in relayoutFlags . arrays ) {
2697
- var indices = relayoutFlags . arrays [ componentType ] ;
2698
- if ( indices . length ) {
2699
- var drawOne = Registry . getComponentMethod ( componentType , 'drawOne' ) ;
2700
- if ( drawOne !== Lib . noop ) {
2701
- for ( var i = 0 ; i < indices . length ; i ++ ) {
2702
- drawOne ( gd , indices [ i ] ) ;
2703
- }
2704
- } else {
2705
- var draw = Registry . getComponentMethod ( componentType , 'draw' ) ;
2706
- if ( draw === Lib . noop ) {
2707
- throw new Error ( 'cannot draw components: ' + componentType ) ;
2702
+ seq . push ( function ( ) {
2703
+ return Plots . transitionFromReact ( gd , restyleFlags , relayoutFlags , oldFullLayout ) ;
2704
+ } ) ;
2705
+ } else if ( restyleFlags . fullReplot || relayoutFlags . layoutReplot ) {
2706
+ gd . _fullLayout . _skipDefaults = true ;
2707
+ seq . push ( exports . _doPlot ) ;
2708
+ } else {
2709
+ for ( var componentType in relayoutFlags . arrays ) {
2710
+ var indices = relayoutFlags . arrays [ componentType ] ;
2711
+ if ( indices . length ) {
2712
+ var drawOne = Registry . getComponentMethod ( componentType , 'drawOne' ) ;
2713
+ if ( drawOne !== Lib . noop ) {
2714
+ for ( var i = 0 ; i < indices . length ; i ++ ) {
2715
+ drawOne ( gd , indices [ i ] ) ;
2716
+ }
2717
+ } else {
2718
+ var draw = Registry . getComponentMethod ( componentType , 'draw' ) ;
2719
+ if ( draw === Lib . noop ) {
2720
+ throw new Error ( 'cannot draw components: ' + componentType ) ;
2721
+ }
2722
+ draw ( gd ) ;
2708
2723
}
2709
- draw ( gd ) ;
2710
2724
}
2711
2725
}
2712
- }
2713
2726
2714
- seq . push ( Plots . previousPromises ) ;
2715
- if ( restyleFlags . style ) seq . push ( subroutines . doTraceStyle ) ;
2716
- if ( restyleFlags . colorbars || relayoutFlags . colorbars ) seq . push ( subroutines . doColorBars ) ;
2717
- if ( relayoutFlags . legend ) seq . push ( subroutines . doLegend ) ;
2718
- if ( relayoutFlags . layoutstyle ) seq . push ( subroutines . layoutStyles ) ;
2719
- if ( relayoutFlags . axrange ) addAxRangeSequence ( seq ) ;
2720
- if ( relayoutFlags . ticks ) seq . push ( subroutines . doTicksRelayout ) ;
2721
- if ( relayoutFlags . modebar ) seq . push ( subroutines . doModeBar ) ;
2722
- if ( relayoutFlags . camera ) seq . push ( subroutines . doCamera ) ;
2723
- seq . push ( emitAfterPlot ) ;
2724
- }
2727
+ seq . push ( Plots . previousPromises ) ;
2728
+ if ( restyleFlags . style ) seq . push ( subroutines . doTraceStyle ) ;
2729
+ if ( restyleFlags . colorbars || relayoutFlags . colorbars ) seq . push ( subroutines . doColorBars ) ;
2730
+ if ( relayoutFlags . legend ) seq . push ( subroutines . doLegend ) ;
2731
+ if ( relayoutFlags . layoutstyle ) seq . push ( subroutines . layoutStyles ) ;
2732
+ if ( relayoutFlags . axrange ) addAxRangeSequence ( seq ) ;
2733
+ if ( relayoutFlags . ticks ) seq . push ( subroutines . doTicksRelayout ) ;
2734
+ if ( relayoutFlags . modebar ) seq . push ( subroutines . doModeBar ) ;
2735
+ if ( relayoutFlags . camera ) seq . push ( subroutines . doCamera ) ;
2736
+ seq . push ( emitAfterPlot ) ;
2737
+ }
2725
2738
2726
- seq . push (
2727
- Plots . rehover ,
2728
- Plots . redrag ,
2729
- Plots . reselect
2730
- ) ;
2739
+ seq . push (
2740
+ Plots . rehover ,
2741
+ Plots . redrag ,
2742
+ Plots . reselect
2743
+ ) ;
2731
2744
2732
- plotDone = Lib . syncOrAsync ( seq , gd ) ;
2733
- if ( ! plotDone || ! plotDone . then ) plotDone = Promise . resolve ( gd ) ;
2745
+ plotDone = Lib . syncOrAsync ( seq , gd ) ;
2746
+ if ( ! plotDone || ! plotDone . then ) plotDone = Promise . resolve ( gd ) ;
2747
+ }
2734
2748
}
2735
2749
2736
- return plotDone . then ( function ( ) {
2737
- gd . emit ( 'plotly_react' , {
2738
- data : data ,
2739
- layout : layout
2740
- } ) ;
2750
+ return plotDone . then ( ( ) => {
2751
+ if ( ! configChanged ) gd . emit ( 'plotly_react' , { config, data, layout } ) ;
2741
2752
2742
2753
return gd ;
2743
2754
} ) ;
@@ -3675,11 +3686,11 @@ function makePlotFramework(gd) {
3675
3686
// The plot container should always take the full with the height of its
3676
3687
// parent (the graph div). This ensures that for responsive plots
3677
3688
// without a height or width set, the paper div will take up the full
3678
- // height & width of the graph div.
3689
+ // height & width of the graph div.
3679
3690
// So, for responsive plots without a height or width set, if the plot
3680
3691
// container's height is left to 'auto', its height will be dictated by
3681
3692
// its childrens' height. (The plot container's only child is the paper
3682
- // div.)
3693
+ // div.)
3683
3694
// In this scenario, the paper div's height will be set to 100%,
3684
3695
// which will be 100% of the plot container's auto height. That is
3685
3696
// meaninglesss, so the browser will use the paper div's children to set
0 commit comments