Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

TypeScript for Layout Animations #2137

Merged
merged 11 commits into from
Jun 24, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion src/createAnimatedComponent.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ import {
DefaultEntering,
DefaultExiting,
DefaultLayout,
} from './reanimated2/layoutReanimation/defaultAnimationsBuilder';
} from './reanimated2/layoutReanimation/defaultAnimations/Default';

const NODE_MAPPING = new Map();

Expand Down
2 changes: 1 addition & 1 deletion src/reanimated2/Easing.ts
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,7 @@ import { Bezier } from './Bezier';
* - [`out`](docs/easing.html#out) runs an easing function backwards
*/

type EasingFn = (t: number) => number;
export type EasingFn = (t: number) => number;
/**
* A linear function, `f(t) = t`. Position correlates to elapsed time one to
* one.
Expand Down
2 changes: 1 addition & 1 deletion src/reanimated2/animations.ts
Original file line number Diff line number Diff line change
Expand Up @@ -179,7 +179,7 @@ export function withStartValue(startValue, animation) {
});
}

export function withTiming(toValue, userConfig, callback) {
export function withTiming(toValue: any, userConfig: any, callback?: any) {
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It is just a temporary solution. We will add types for animation in the next PR.

'worklet';

return defineAnimation(toValue, () => {
Expand Down
16 changes: 16 additions & 0 deletions src/reanimated2/globals.d.ts
Original file line number Diff line number Diff line change
@@ -1 +1,17 @@
declare const _WORKLET: boolean;
declare const _stopObservingProgress: (tag: number, flag: boolean) => void;
declare const _startObservingProgress: (tag: number, flag: boolean) => void;
declare namespace NodeJS {
interface Global {
Comment on lines +4 to +5
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why this is wrapped in Nodejs namespace?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.


I found information that namespace NodeJS is required for the definition of properties in the global object. But correct me please if I am wrong.

LayoutAnimationRepository: {
configs: Record<string, unknown>;
registerConfig(tag: number, config: Record<string, unknown>): void;
removeConfig(tag: number): void;
startAnimationForTag(
tag: number,
type: unknown,
yogaValues: unknown
): void;
};
}
}
11 changes: 3 additions & 8 deletions src/reanimated2/layoutReanimation/AnimatedRoot.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,4 @@
/* global _stopObservingProgress, _startObservingProgress */
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-nocheck
import { Platform, requireNativeComponent } from 'react-native';
import React from 'react';
import { runOnUI } from '../core';
Expand All @@ -12,14 +10,11 @@ if (Platform.OS === 'web' && !requireNativeComponent) {
} else {
REALayoutView = (requireNativeComponent(
'REALayoutView'
) as any) as React.Component;
) as unknown) as React.Component;
}

export class AnimatedLayout extends React.Component<
Record<string, unknown>,
Record<string, unknown>
> {
render() {
export class AnimatedLayout extends React.Component {
render(): React.ReactElement {
return <REALayoutView collapsable={false} {...this.props} />;
}
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,207 @@
import { withDelay, withTiming, withSpring } from '../../animations';
import {
EntryExitAnimationFunction,
AnimationFunction,
BaseBuilderAnimationConfig,
LayoutAnimationAndConfig,
EntryExitAnimationBuild,
} from './commonTypes';
import { EasingFn } from '../../Easing';

export class BaseAnimationBuilder {
durationV?: number;
easingV?: EasingFn;
delayV?: number;
rotateV?: string;
type?: AnimationFunction;
dampingV?: number;
massV?: number;
stiffnessV?: number;
overshootClampingV?: number;
restDisplacementThresholdV?: number;
restSpeedThresholdV?: number;

static createInstance: () => BaseAnimationBuilder;
build: EntryExitAnimationBuild;

static duration(durationMs: number): BaseAnimationBuilder {
const instance = this.createInstance();
return instance.duration(durationMs);
}

duration(durationMs: number): BaseAnimationBuilder {
this.durationV = durationMs;
return this;
}

static easing(easingFunction: EasingFn): BaseAnimationBuilder {
const instance = this.createInstance();
return instance.easing(easingFunction);
}

easing(easingFunction: EasingFn): BaseAnimationBuilder {
this.easingV = easingFunction;
return this;
}

static delay(delayMs: number): BaseAnimationBuilder {
const instance = this.createInstance();
return instance.delay(delayMs);
}

delay(delayMs: number): BaseAnimationBuilder {
this.delayV = delayMs;
return this;
}

static rotate(degree: string): BaseAnimationBuilder {
const instance = this.createInstance();
return instance.rotate(degree);
}

rotate(degree: string): BaseAnimationBuilder {
this.rotateV = degree;
return this;
}

static springify(): BaseAnimationBuilder {
const instance = this.createInstance();
return instance.springify();
}

springify(): BaseAnimationBuilder {
this.type = withSpring as AnimationFunction;
return this;
}

static damping(damping: number): BaseAnimationBuilder {
const instance = this.createInstance();
return instance.damping(damping);
}

damping(damping: number): BaseAnimationBuilder {
this.dampingV = damping;
return this;
}

static mass(mass: number): BaseAnimationBuilder {
const instance = this.createInstance();
return instance.mass(mass);
}

mass(mass: number): BaseAnimationBuilder {
this.massV = mass;
return this;
}

static stiffness(stiffness: number): BaseAnimationBuilder {
const instance = this.createInstance();
return instance.stiffness(stiffness);
}

stiffness(stiffness: number): BaseAnimationBuilder {
this.stiffnessV = stiffness;
return this;
}

static overshootClamping(overshootClamping: number): BaseAnimationBuilder {
const instance = this.createInstance();
return instance.overshootClamping(overshootClamping);
}

overshootClamping(overshootClamping: number): BaseAnimationBuilder {
this.overshootClampingV = overshootClamping;
return this;
}

static restDisplacementThreshold(
restDisplacementThreshold: number
): BaseAnimationBuilder {
const instance = this.createInstance();
return instance.restDisplacementThreshold(restDisplacementThreshold);
}

restDisplacementThreshold(
restDisplacementThreshold: number
): BaseAnimationBuilder {
this.restDisplacementThresholdV = restDisplacementThreshold;
return this;
}

static restSpeedThreshold(restSpeedThreshold: number): BaseAnimationBuilder {
const instance = this.createInstance();
return instance.restSpeedThreshold(restSpeedThreshold);
}

restSpeedThreshold(restSpeedThreshold: number): BaseAnimationBuilder {
this.restSpeedThresholdV = restSpeedThreshold;
return this;
}

static build(): EntryExitAnimationFunction {
const instance = this.createInstance();
return instance.build();
}

getDelayFunction(): AnimationFunction {
const delay = this.delayV;
return delay
? withDelay
: (_, animation) => {
'worklet';
return animation;
};
}

getAnimationAndConfig(): LayoutAnimationAndConfig {
const duration = this.durationV;
const easing = this.easingV;
const rotate = this.rotateV;
const type = this.type ? this.type : (withTiming as AnimationFunction);
const damping = this.dampingV;
const mass = this.massV;
const stiffness = this.stiffnessV;
const overshootClamping = this.overshootClampingV;
const restDisplacementThreshold = this.restDisplacementThresholdV;
const restSpeedThreshold = this.restSpeedThresholdV;

const animation = type;

const config: BaseBuilderAnimationConfig = {};

if (type === withTiming) {
if (easing) {
config.easing = easing;
}
if (duration) {
config.duration = duration;
}
if (rotate) {
config.rotate = rotate;
}
} else {
if (damping) {
config.damping = damping;
}
if (mass) {
config.mass = mass;
}
if (stiffness) {
config.stiffness = stiffness;
}
if (overshootClamping) {
config.overshootClamping = overshootClamping;
}
if (restDisplacementThreshold) {
config.restDisplacementThreshold = restDisplacementThreshold;
}
if (restSpeedThreshold) {
config.restSpeedThreshold = restSpeedThreshold;
}
if (rotate) {
config.rotate = rotate;
}
}
return [animation, config];
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
import { withDelay, withTiming } from '../../animations';
import {
EntryExitAnimationFunction,
AnimationFunction,
LayoutAnimationAndConfig,
BounceBuilderAnimationConfig,
EntryExitAnimationBuild,
} from './commonTypes';

export class BaseBounceAnimationBuilder {
durationV: number;
delayV: number;

static createInstance: () => BaseBounceAnimationBuilder;
build: EntryExitAnimationBuild;

static duration(durationMs: number): BaseBounceAnimationBuilder {
const instance = this.createInstance();
return instance.duration(durationMs);
}

duration(durationMs: number): BaseBounceAnimationBuilder {
this.durationV = durationMs;
return this;
}

static delay(delayMs: number): BaseBounceAnimationBuilder {
const instance = this.createInstance();
return instance.delay(delayMs);
}

delay(delayMs: number): BaseBounceAnimationBuilder {
this.delayV = delayMs;
return this;
}

getDelayFunction(): AnimationFunction {
const delay = this.delayV;
return delay
? withDelay
: (_, animation) => {
'worklet';
return animation;
};
}

getAnimationAndConfig(): LayoutAnimationAndConfig {
const duration = this.durationV;
const type = withTiming;
const animation = type;

const config: BounceBuilderAnimationConfig = {};

if (duration) {
config.duration = duration;
}

return [animation, config];
}

static build(): EntryExitAnimationFunction {
const instance = this.createInstance();
return instance.build();
}
}
Loading