rename and restrict constraint mode

This commit is contained in:
Ryan Di 2025-05-09 18:46:54 +10:00
parent 62c800c21a
commit 3a566a292c
2 changed files with 33 additions and 8 deletions

View File

@ -2974,9 +2974,7 @@ class App extends React.Component<AppProps, AppState> {
} }
if (this.state.scrollConstraints?.animateOnNextUpdate) { if (this.state.scrollConstraints?.animateOnNextUpdate) {
const newState = constrainScrollState(this.state, { const newState = constrainScrollState(this.state, "rigid");
allowOverscroll: false,
});
const fromValues = { const fromValues = {
scrollX: this.state.scrollX, scrollX: this.state.scrollX,
scrollY: this.state.scrollY, scrollY: this.state.scrollY,
@ -5041,7 +5039,7 @@ class App extends React.Component<AppProps, AppState> {
state, state,
), ),
}, },
{ disableAnimation: true }, "loose",
), ),
); );
} }
@ -11353,7 +11351,7 @@ class App extends React.Component<AppProps, AppState> {
...this.state, ...this.state,
scrollConstraints, scrollConstraints,
}, },
{ allowOverscroll: false }, "rigid",
); );
this.animateToConstrainedArea( this.animateToConstrainedArea(

View File

@ -417,18 +417,27 @@ export const decodeConstraints = (encoded: string): ScrollConstraints => {
} }
}; };
type Options = { allowOverscroll?: boolean; disableAnimation?: boolean }; type Options = { allowOverscroll: boolean; disableAnimation: boolean };
const DEFAULT_OPTION: Options = {
allowOverscroll: true,
disableAnimation: false,
};
/** /**
* Constrains the AppState scroll values within the defined scroll constraints. * Constrains the AppState scroll values within the defined scroll constraints.
* *
* constraintMode can be "elastic", "rigid", or "loose":
* - "elastic": snaps to constraints but allows overscroll
* - "rigid": snaps to constraints without overscroll
* - "loose": allows overscroll and disables animation/snapping to constraints
*
* @param state - The original AppState. * @param state - The original AppState.
* @param options - Options for allowing overscroll and disabling animation. * @param options - Options for allowing overscroll and disabling animation.
* @returns A new AppState object with constrained scroll values. * @returns A new AppState object with constrained scroll values.
*/ */
export const constrainScrollState = ( export const constrainScrollState = (
state: AppState, state: AppState,
options?: Options, constraintMode: "elastic" | "rigid" | "loose" = "elastic",
): AppState => { ): AppState => {
if (!state.scrollConstraints) { if (!state.scrollConstraints) {
return state; return state;
@ -442,7 +451,25 @@ export const constrainScrollState = (
zoom, zoom,
} = state; } = state;
const { allowOverscroll = true, disableAnimation = false } = options || {}; let allowOverscroll: boolean;
let disableAnimation: boolean;
switch (constraintMode) {
case "elastic":
({ allowOverscroll, disableAnimation } = DEFAULT_OPTION);
break;
case "rigid":
allowOverscroll = false;
disableAnimation = false;
break;
case "loose":
allowOverscroll = true;
disableAnimation = true;
break;
default:
({ allowOverscroll, disableAnimation } = DEFAULT_OPTION);
break;
}
const scrollConstraints = alignScrollConstraints(inverseScrollConstraints); const scrollConstraints = alignScrollConstraints(inverseScrollConstraints);