@egjs/react-flicking 4.9.4 → 4.10.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -26,12 +26,6 @@ import NonStrictPanel from "./NonStrictPanel";
26
26
  import ViewportSlot from "./ViewportSlot";
27
27
  import ReactElementProvider from "./ReactElementProvider";
28
28
 
29
- enum LifeCycleState {
30
- BEFORE_UPDATE,
31
- RENDER,
32
- UPDATED
33
- }
34
-
35
29
  class Flicking extends React.Component<Partial<FlickingProps & FlickingOptions>> {
36
30
  public static defaultProps: FlickingProps = DEFAULT_PROPS;
37
31
 
@@ -42,7 +36,7 @@ class Flicking extends React.Component<Partial<FlickingProps & FlickingOptions>>
42
36
  private _viewportElement: HTMLElement;
43
37
  private _diffResult: DiffResult<React.ReactElement> | null;
44
38
  private _renderEmitter = new Component<{ render: void }>();
45
- private _currentState: LifeCycleState = LifeCycleState.BEFORE_UPDATE;
39
+ private _prevProps: Partial<FlickingProps & FlickingOptions>;
46
40
 
47
41
  public get reactPanels() { return this._panels.map(panel => panel.current!); }
48
42
  public get renderEmitter() { return this._renderEmitter; }
@@ -51,6 +45,7 @@ class Flicking extends React.Component<Partial<FlickingProps & FlickingOptions>>
51
45
  super(props);
52
46
 
53
47
  this._panels = this._createPanelRefs(props, this._getChildren());
48
+ this._prevProps = this.props;
54
49
  }
55
50
 
56
51
  public componentDidMount() {
@@ -74,11 +69,11 @@ class Flicking extends React.Component<Partial<FlickingProps & FlickingOptions>>
74
69
  );
75
70
 
76
71
  this._vanillaFlicking = flicking;
77
- this._currentState = LifeCycleState.UPDATED;
78
72
 
79
73
  const children = this._getChildren();
80
74
  this._jsxDiffer = new ListDiffer(children, panel => panel.key!);
81
75
  this._pluginsDiffer = new ListDiffer<any>();
76
+ this._prevProps = this.props;
82
77
 
83
78
  this._bindEvents();
84
79
  this._checkPlugins();
@@ -92,24 +87,17 @@ class Flicking extends React.Component<Partial<FlickingProps & FlickingOptions>>
92
87
  this._vanillaFlicking?.destroy();
93
88
  }
94
89
 
95
- public shouldComponentUpdate(nextProps: this["props"]) {
90
+ public shouldComponentUpdate(nextProps: Readonly<Partial<FlickingProps & FlickingOptions>>): boolean {
96
91
  const vanillaFlicking = this._vanillaFlicking;
97
- const props = this.props;
92
+ const prevProps = this.props;
98
93
 
99
- // Ignore updates before init, they will be updated after "ready" event's force update
100
94
  if (!vanillaFlicking || !vanillaFlicking.initialized) return false;
95
+ if (!this._hasSameChildren(prevProps, nextProps)) return true;
101
96
 
102
- if (this._currentState !== LifeCycleState.BEFORE_UPDATE && props.children !== nextProps.children) {
103
- const nextChildren = this._getChildren(nextProps.children);
104
-
105
- this._panels = this._createPanelRefs(nextProps, nextChildren);
106
- this._diffResult = this._jsxDiffer.update(nextChildren);
107
- }
108
-
109
- this._currentState = LifeCycleState.BEFORE_UPDATE;
97
+ const { children, ...restProps } = nextProps;
110
98
 
111
- for (const key in nextProps) {
112
- if (props[key] !== nextProps[key]) {
99
+ for (const key in restProps) {
100
+ if (prevProps[key] !== nextProps[key]) {
113
101
  return true;
114
102
  }
115
103
  }
@@ -117,6 +105,22 @@ class Flicking extends React.Component<Partial<FlickingProps & FlickingOptions>>
117
105
  return false;
118
106
  }
119
107
 
108
+ public beforeRender() {
109
+ const vanillaFlicking = this._vanillaFlicking;
110
+ const nextProps = this.props;
111
+ const prevProps = this._prevProps;
112
+
113
+ // Ignore updates before init, they will be updated after "ready" event's force update
114
+ if (!vanillaFlicking || !vanillaFlicking.initialized) return;
115
+
116
+ if (!this._hasSameChildren(prevProps, nextProps)) {
117
+ const nextChildren = this._getChildren(nextProps.children);
118
+
119
+ this._panels = this._createPanelRefs(nextProps, nextChildren);
120
+ this._diffResult = this._jsxDiffer.update(nextChildren);
121
+ }
122
+ }
123
+
120
124
  public componentDidUpdate() {
121
125
  const flicking = this._vanillaFlicking;
122
126
  const renderEmitter = this._renderEmitter;
@@ -126,8 +130,6 @@ class Flicking extends React.Component<Partial<FlickingProps & FlickingOptions>>
126
130
  renderEmitter.trigger("render");
127
131
  flicking.camera.updateOffset();
128
132
 
129
- this._currentState = LifeCycleState.UPDATED;
130
-
131
133
  if (!diffResult || !flicking.initialized) return;
132
134
 
133
135
  sync(flicking, diffResult, this.reactPanels);
@@ -142,7 +144,7 @@ class Flicking extends React.Component<Partial<FlickingProps & FlickingOptions>>
142
144
  const attributes: { [key: string]: any } = {};
143
145
  const flicking = this._vanillaFlicking;
144
146
 
145
- this._currentState = LifeCycleState.RENDER;
147
+ this.beforeRender();
146
148
 
147
149
  for (const name in props) {
148
150
  if (!(name in DEFAULT_PROPS) && !(name in VanillaFlicking.prototype)) {
@@ -152,6 +154,7 @@ class Flicking extends React.Component<Partial<FlickingProps & FlickingOptions>>
152
154
 
153
155
  const initialized = flicking && flicking.initialized;
154
156
  const viewportClasses: string[] = ["flicking-viewport"];
157
+ const cameraClasses: string[] = ["flicking-camera"];
155
158
  const isHorizontal = flicking
156
159
  ? flicking.horizontal
157
160
  : props.horizontal ?? true;
@@ -165,6 +168,9 @@ class Flicking extends React.Component<Partial<FlickingProps & FlickingOptions>>
165
168
  if (attributes.className) {
166
169
  viewportClasses.push(attributes.className);
167
170
  }
171
+ if (props.cameraClass) {
172
+ cameraClasses.push(props.cameraClass);
173
+ }
168
174
 
169
175
  const cameraProps = !initialized && props.firstPanelSize
170
176
  ? { style: {
@@ -176,11 +182,13 @@ class Flicking extends React.Component<Partial<FlickingProps & FlickingOptions>>
176
182
  ? this._getVirtualPanels()
177
183
  : this._getPanels();
178
184
 
185
+ this._prevProps = props;
186
+
179
187
  return (
180
188
  <Viewport {...attributes} className={viewportClasses.join(" ")} ref={(e?: HTMLElement) => {
181
189
  e && (this._viewportElement = e);
182
190
  }}>
183
- <Camera className="flicking-camera" {...cameraProps}>
191
+ <Camera className={cameraClasses.join(" ")} {...cameraProps}>
184
192
  { panels }
185
193
  </Camera>
186
194
  { this._getViewportSlot() }
@@ -233,6 +241,24 @@ class Flicking extends React.Component<Partial<FlickingProps & FlickingOptions>>
233
241
  flicking.removePlugins(...removed.map(index => prevList[index]));
234
242
  }
235
243
 
244
+ private _hasSameChildren(prevProps: this["props"], nextProps: this["props"]) {
245
+ const prevChildren = this._getChildren(prevProps.children);
246
+ const nextChildren = this._getChildren(nextProps.children);
247
+
248
+ if (prevChildren.length !== nextChildren.length) return false;
249
+
250
+ const same = prevChildren.every((child, idx) => {
251
+ const nextChild = nextChildren[idx];
252
+ if ((child as React.ReactElement).key && (nextChild as React.ReactElement).key) {
253
+ return (child as React.ReactElement).key === (nextChild as React.ReactElement).key;
254
+ } else {
255
+ return child === nextChild;
256
+ }
257
+ });
258
+
259
+ return same;
260
+ }
261
+
236
262
  private _getChildren(children: React.ReactNode = this.props.children) {
237
263
  return (React.Children.toArray(children) as Array<React.ReactElement<any>>)
238
264
  .filter(child => child.type !== ViewportSlot)
@@ -27,6 +27,7 @@ import { FlickingProps } from "./types";
27
27
  export const DEFAULT_PROPS: FlickingProps = {
28
28
  viewportTag: "div",
29
29
  cameraTag: "div",
30
+ cameraClass: "",
30
31
  plugins: [],
31
32
  useFindDOMNode: false,
32
33
  hideBeforeInit: false,
@@ -28,6 +28,7 @@ import {
28
28
  export interface FlickingProps {
29
29
  viewportTag: keyof JSX.IntrinsicElements;
30
30
  cameraTag: keyof JSX.IntrinsicElements;
31
+ cameraClass: string;
31
32
  plugins: Plugin[];
32
33
  status?: Status;
33
34
  useFindDOMNode: boolean;