Skip to content
This repository was archived by the owner on Apr 8, 2020. It is now read-only.

Commit 44fb346

Browse files
committed
Add onTransitionBegin
1 parent c25f6c7 commit 44fb346

File tree

3 files changed

+100
-9
lines changed

3 files changed

+100
-9
lines changed

src/csstransition.tsx

Lines changed: 11 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,8 @@ const TICK = 17;
1616
export interface CSSTransitionAttributes {
1717
active?: boolean;
1818
transitionAppear?: boolean;
19+
onTransitionBegin?: () => void;
20+
// TODO: onTransitionRevert
1921
onTransitionComplete?: () => void;
2022
component?: string | React.ComponentClass<any>;
2123
children?: React.ReactNode;
@@ -106,8 +108,8 @@ export class CSSTransition extends React.Component<CSSTransitionProps, CSSTransi
106108
);
107109
}
108110

109-
private handleTransitionComplete = () => this.dispatch(Action.TransitionComplete);
110-
private handleTransitionBegin = () => this.dispatch(Action.TransitionBegin);
111+
private handleTransitionComplete = () => this.dispatch(Action.TransitionComplete)
112+
private handleTransitionBegin = () => this.dispatch(Action.TransitionStart)
111113

112114
private dispatch(action: Action, props = this.props, state = this.state): void {
113115
switch (action) {
@@ -126,6 +128,7 @@ export class CSSTransition extends React.Component<CSSTransitionProps, CSSTransi
126128
this.appearTimer = setTimeout(() => {
127129
this.dispatch(Action.TransitionRun, props);
128130
}, TICK);
131+
if (props.onTransitionBegin) { props.onTransitionBegin(); }
129132
return this.setState(transitToActiveAppearingState(props));
130133
case Action.TransitionRun:
131134
switch (state.id) {
@@ -137,9 +140,11 @@ export class CSSTransition extends React.Component<CSSTransitionProps, CSSTransi
137140
if (props.onTransitionComplete) { props.onTransitionComplete(); }
138141
return this.setState(defaultState(props));
139142
case State.Active:
143+
if (props.onTransitionBegin) { props.onTransitionBegin(); }
140144
case State.TransitToActiveStarted:
141145
return this.setState(transitToDefaultRunningState(props));
142146
case State.Default:
147+
if (props.onTransitionBegin) { props.onTransitionBegin(); }
143148
case State.TransitToDefaultStarted:
144149
return this.setState(transitToActiveRunningState(props));
145150
case State.TransitToActiveRunning:
@@ -151,7 +156,7 @@ export class CSSTransition extends React.Component<CSSTransitionProps, CSSTransi
151156
default:
152157
throw new Error("invalid state transition");
153158
}
154-
case Action.TransitionBegin:
159+
case Action.TransitionStart:
155160
switch (state.id) {
156161
case State.TransitToActiveRunning:
157162
return this.setState(transitToActiveStartedState(props));
@@ -188,7 +193,7 @@ export enum State {
188193
TransitToActiveAppearing,
189194
TransitToActiveRunning,
190195
TransitToActiveStarted,
191-
Default
196+
Default,
192197
}
193198

194199
enum Action {
@@ -197,8 +202,8 @@ enum Action {
197202
TransitionAppear,
198203
TransitionSkip,
199204
TransitionRun,
200-
TransitionBegin,
201-
TransitionComplete
205+
TransitionStart,
206+
TransitionComplete,
202207
}
203208

204209
const activeState = (props: CSSTransitionProps) => ({

test/integration.test.tsx

Lines changed: 88 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ describe("integration test", () => {
2424
const leaveStyle: React.CSSProperties = { width: transit("50px", 150, "ease", 25) };
2525
const enterStyleProcessed: React.CSSProperties = { width: "100px", transition: "width 150ms ease 25ms" };
2626
const leaveStyleProcessed: React.CSSProperties = { width: "50px", transition: "width 150ms ease 25ms" };
27+
let onTransitionBegin: SinonSpy;
2728
let onTransitionComplete: SinonSpy;
2829
let getWrapper: (props?: CSSTransitionProps) => ReactWrapper<any, {}>;
2930
let getWrapperAttached: (props?: CSSTransitionProps) => ReactWrapper<any, {}>;
@@ -59,8 +60,16 @@ describe("integration test", () => {
5960
let target: ReactWrapper<any, {}>;
6061

6162
before(() => {
63+
onTransitionBegin = spy();
6264
onTransitionComplete = spy();
63-
wrapper = getWrapperAttached({ activeStyle, enterStyle, leaveStyle, defaultStyle, onTransitionComplete });
65+
wrapper = getWrapperAttached({
66+
activeStyle,
67+
enterStyle,
68+
leaveStyle,
69+
defaultStyle,
70+
onTransitionBegin,
71+
onTransitionComplete,
72+
});
6473
target = wrapper.find("div");
6574
});
6675

@@ -88,6 +97,10 @@ describe("integration test", () => {
8897
assert.deepEqual(style, enterStyleProcessed);
8998
});
9099

100+
it("should call onTransitionBegin", () => {
101+
assert.isTrue(onTransitionBegin.calledOnce);
102+
});
103+
91104
describe("when transition starts", () => {
92105
before((done) => {
93106
setTimeout(() => {
@@ -117,6 +130,10 @@ describe("integration test", () => {
117130
assert.deepEqual(style, activeStyle);
118131
});
119132

133+
it("should have called onTransitionBegin only once", () => {
134+
assert.isTrue(onTransitionBegin.calledOnce);
135+
});
136+
120137
it("should call onTransitionComplete", () => {
121138
assert.isTrue(onTransitionComplete.calledOnce);
122139
});
@@ -129,9 +146,10 @@ describe("integration test", () => {
129146
let target: ReactWrapper<any, {}>;
130147

131148
before(() => {
149+
onTransitionBegin = spy();
132150
onTransitionComplete = spy();
133151
wrapper = getWrapperAttached({
134-
activeStyle, enterStyle, leaveStyle, defaultStyle, onTransitionComplete,
152+
activeStyle, enterStyle, leaveStyle, defaultStyle, onTransitionBegin, onTransitionComplete,
135153
active: true,
136154
});
137155
target = wrapper.find("div");
@@ -161,6 +179,10 @@ describe("integration test", () => {
161179
assert.deepEqual(style, leaveStyleProcessed);
162180
});
163181

182+
it("should call onTransitionBegin", () => {
183+
assert.isTrue(onTransitionBegin.calledOnce);
184+
});
185+
164186
describe("when transition starts", () => {
165187
before((done) => {
166188
setTimeout(() => {
@@ -190,6 +212,10 @@ describe("integration test", () => {
190212
assert.deepEqual(style, defaultStyle);
191213
});
192214

215+
it("should have called onTransitionBegin only once", () => {
216+
assert.isTrue(onTransitionBegin.calledOnce);
217+
});
218+
193219
it("should call onTransitionComplete", () => {
194220
assert.isTrue(onTransitionComplete.calledOnce);
195221
});
@@ -202,9 +228,11 @@ describe("integration test", () => {
202228
let target: ReactWrapper<any, {}>;
203229

204230
before(() => {
231+
onTransitionBegin = spy();
205232
onTransitionComplete = spy();
206233
wrapper = getWrapperAttached({
207234
activeStyle, enterStyle, leaveStyle, defaultStyle,
235+
onTransitionBegin,
208236
onTransitionComplete,
209237
active: false,
210238
});
@@ -230,6 +258,10 @@ describe("integration test", () => {
230258
assert.deepEqual(style, enterStyleProcessed);
231259
});
232260

261+
it("should call onTransitionBegin", () => {
262+
assert.isTrue(onTransitionBegin.calledOnce);
263+
});
264+
233265
it("should not call onTransitionComplete yet", () => {
234266
assert.isTrue(onTransitionComplete.notCalled);
235267
});
@@ -244,6 +276,10 @@ describe("integration test", () => {
244276
assert.deepEqual(style, defaultStyle);
245277
});
246278

279+
it("should have called onTransitionBegin only once", () => {
280+
assert.isTrue(onTransitionBegin.calledOnce);
281+
});
282+
247283
it("should call onTransitionComplete", () => {
248284
assert.isTrue(onTransitionComplete.calledOnce);
249285
});
@@ -256,9 +292,11 @@ describe("integration test", () => {
256292
let target: ReactWrapper<any, {}>;
257293

258294
before(() => {
295+
onTransitionBegin = spy();
259296
onTransitionComplete = spy();
260297
wrapper = getWrapperAttached({
261298
activeStyle, enterStyle, leaveStyle, defaultStyle,
299+
onTransitionBegin,
262300
onTransitionComplete,
263301
active: true,
264302
});
@@ -284,6 +322,10 @@ describe("integration test", () => {
284322
assert.deepEqual(style, leaveStyleProcessed);
285323
});
286324

325+
it("should call onTransitionBegin", () => {
326+
assert.isTrue(onTransitionBegin.calledOnce);
327+
});
328+
287329
it("should not call onTransitionComplete yet", () => {
288330
assert.isTrue(onTransitionComplete.notCalled);
289331
});
@@ -298,6 +340,10 @@ describe("integration test", () => {
298340
assert.deepEqual(style, activeStyle);
299341
});
300342

343+
it("should have called onTransitionBegin only once", () => {
344+
assert.isTrue(onTransitionBegin.calledOnce);
345+
});
346+
301347
it("should call onTransitionComplete", () => {
302348
assert.isTrue(onTransitionComplete.calledOnce);
303349
});
@@ -310,9 +356,11 @@ describe("integration test", () => {
310356
let target: ReactWrapper<any, {}>;
311357

312358
before(() => {
359+
onTransitionBegin = spy();
313360
onTransitionComplete = spy();
314361
wrapper = getWrapperAttached({
315362
activeStyle, enterStyle, leaveStyle, defaultStyle,
363+
onTransitionBegin,
316364
onTransitionComplete,
317365
active: false,
318366
});
@@ -343,6 +391,10 @@ describe("integration test", () => {
343391
assert.deepEqual(style, enterStyleProcessed);
344392
});
345393

394+
it("should call onTransitionBegin", () => {
395+
assert.isTrue(onTransitionBegin.calledOnce);
396+
});
397+
346398
describe("when transition starts", () => {
347399
before((done) => {
348400
setTimeout(() => {
@@ -395,6 +447,10 @@ describe("integration test", () => {
395447
assert.deepEqual(style, defaultStyle);
396448
});
397449

450+
it("should have called onTransitionBegin only once", () => {
451+
assert.isTrue(onTransitionBegin.calledOnce);
452+
});
453+
398454
it("should call onTransitionComplete", () => {
399455
assert.isTrue(onTransitionComplete.calledOnce);
400456
});
@@ -408,9 +464,11 @@ describe("integration test", () => {
408464
let target: ReactWrapper<any, {}>;
409465

410466
before(() => {
467+
onTransitionBegin = spy();
411468
onTransitionComplete = spy();
412469
wrapper = getWrapperAttached({
413470
activeStyle, enterStyle, leaveStyle, defaultStyle,
471+
onTransitionBegin,
414472
onTransitionComplete,
415473
active: true,
416474
});
@@ -441,6 +499,10 @@ describe("integration test", () => {
441499
assert.deepEqual(style, leaveStyleProcessed);
442500
});
443501

502+
it("should call onTransitionBegin", () => {
503+
assert.isTrue(onTransitionBegin.calledOnce);
504+
});
505+
444506
describe("when transition starts", () => {
445507
before((done) => {
446508
setTimeout(() => {
@@ -493,6 +555,10 @@ describe("integration test", () => {
493555
assert.deepEqual(style, activeStyle);
494556
});
495557

558+
it("should have called onTransitionBegin only once", () => {
559+
assert.isTrue(onTransitionBegin.calledOnce);
560+
});
561+
496562
it("should call onTransitionComplete", () => {
497563
assert.isTrue(onTransitionComplete.calledOnce);
498564
});
@@ -506,9 +572,11 @@ describe("integration test", () => {
506572
let target: ReactWrapper<any, {}>;
507573

508574
before(() => {
575+
onTransitionBegin = spy();
509576
onTransitionComplete = spy();
510577
wrapper = getWrapperAttached({
511578
activeStyle, enterStyle, leaveStyle, defaultStyle,
579+
onTransitionBegin,
512580
onTransitionComplete,
513581
active: true,
514582
transitionAppear: true,
@@ -544,6 +612,10 @@ describe("integration test", () => {
544612
}, 100);
545613
});
546614

615+
it("should call onTransitionBegin", () => {
616+
assert.isTrue(onTransitionBegin.calledOnce);
617+
});
618+
547619
it("should ignore", () => {
548620
const style = target.props().style;
549621
assert.deepEqual(style, enterStyleProcessed);
@@ -566,6 +638,10 @@ describe("integration test", () => {
566638
assert.deepEqual(style, activeStyle);
567639
});
568640

641+
it("should have called onTransitionBegin only once", () => {
642+
assert.isTrue(onTransitionBegin.calledOnce);
643+
});
644+
569645
it("should call onTransitionComplete", () => {
570646
assert.isTrue(onTransitionComplete.calledOnce);
571647
});
@@ -578,9 +654,11 @@ describe("integration test", () => {
578654
let target: ReactWrapper<any, {}>;
579655

580656
before(() => {
657+
onTransitionBegin = spy();
581658
onTransitionComplete = spy();
582659
wrapper = getWrapperAttached({
583660
activeStyle, enterStyle, leaveStyle, defaultStyle,
661+
onTransitionBegin,
584662
onTransitionComplete,
585663
active: true,
586664
transitionAppear: true,
@@ -602,6 +680,10 @@ describe("integration test", () => {
602680
assert.isTrue(onTransitionComplete.notCalled);
603681
});
604682

683+
it("should call onTransitionBegin", () => {
684+
assert.isTrue(onTransitionBegin.calledOnce);
685+
});
686+
605687
describe("when transition was interrupted", () => {
606688
before(() => {
607689
wrapper.setProps({ active: false });
@@ -620,6 +702,10 @@ describe("integration test", () => {
620702
}, 100);
621703
});
622704

705+
it("should have called onTransitionBegin only once", () => {
706+
assert.isTrue(onTransitionBegin.calledOnce);
707+
});
708+
623709
it("should call onTransitionComplete", () => {
624710
assert.isTrue(onTransitionComplete.calledOnce);
625711
});

webpack.config.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ const config = {
1212
resolve: { extensions: [".ts", ".tsx", ".js"] },
1313
module: {
1414
rules: [
15-
{ test: /\.tsx?$/, loader: "awesome-typescript", exclude: "/node_modules/" },
15+
{ test: /\.tsx?$/, loader: "awesome-typescript-loader", exclude: "/node_modules/" },
1616
],
1717
},
1818
externals: [{

0 commit comments

Comments
 (0)