| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119 |
- import { mixNumber } from '../../utils/mix/number.mjs';
- import { hasTransform } from '../utils/has-transform.mjs';
- /**
- * Scales a point based on a factor and an originPoint
- */
- function scalePoint(point, scale, originPoint) {
- const distanceFromOrigin = point - originPoint;
- const scaled = scale * distanceFromOrigin;
- return originPoint + scaled;
- }
- /**
- * Applies a translate/scale delta to a point
- */
- function applyPointDelta(point, translate, scale, originPoint, boxScale) {
- if (boxScale !== undefined) {
- point = scalePoint(point, boxScale, originPoint);
- }
- return scalePoint(point, scale, originPoint) + translate;
- }
- /**
- * Applies a translate/scale delta to an axis
- */
- function applyAxisDelta(axis, translate = 0, scale = 1, originPoint, boxScale) {
- axis.min = applyPointDelta(axis.min, translate, scale, originPoint, boxScale);
- axis.max = applyPointDelta(axis.max, translate, scale, originPoint, boxScale);
- }
- /**
- * Applies a translate/scale delta to a box
- */
- function applyBoxDelta(box, { x, y }) {
- applyAxisDelta(box.x, x.translate, x.scale, x.originPoint);
- applyAxisDelta(box.y, y.translate, y.scale, y.originPoint);
- }
- const TREE_SCALE_SNAP_MIN = 0.999999999999;
- const TREE_SCALE_SNAP_MAX = 1.0000000000001;
- /**
- * Apply a tree of deltas to a box. We do this to calculate the effect of all the transforms
- * in a tree upon our box before then calculating how to project it into our desired viewport-relative box
- *
- * This is the final nested loop within updateLayoutDelta for future refactoring
- */
- function applyTreeDeltas(box, treeScale, treePath, isSharedTransition = false) {
- const treeLength = treePath.length;
- if (!treeLength)
- return;
- // Reset the treeScale
- treeScale.x = treeScale.y = 1;
- let node;
- let delta;
- for (let i = 0; i < treeLength; i++) {
- node = treePath[i];
- delta = node.projectionDelta;
- /**
- * TODO: Prefer to remove this, but currently we have motion components with
- * display: contents in Framer.
- */
- const { visualElement } = node.options;
- if (visualElement &&
- visualElement.props.style &&
- visualElement.props.style.display === "contents") {
- continue;
- }
- if (isSharedTransition &&
- node.options.layoutScroll &&
- node.scroll &&
- node !== node.root) {
- transformBox(box, {
- x: -node.scroll.offset.x,
- y: -node.scroll.offset.y,
- });
- }
- if (delta) {
- // Incoporate each ancestor's scale into a culmulative treeScale for this component
- treeScale.x *= delta.x.scale;
- treeScale.y *= delta.y.scale;
- // Apply each ancestor's calculated delta into this component's recorded layout box
- applyBoxDelta(box, delta);
- }
- if (isSharedTransition && hasTransform(node.latestValues)) {
- transformBox(box, node.latestValues);
- }
- }
- /**
- * Snap tree scale back to 1 if it's within a non-perceivable threshold.
- * This will help reduce useless scales getting rendered.
- */
- if (treeScale.x < TREE_SCALE_SNAP_MAX &&
- treeScale.x > TREE_SCALE_SNAP_MIN) {
- treeScale.x = 1.0;
- }
- if (treeScale.y < TREE_SCALE_SNAP_MAX &&
- treeScale.y > TREE_SCALE_SNAP_MIN) {
- treeScale.y = 1.0;
- }
- }
- function translateAxis(axis, distance) {
- axis.min = axis.min + distance;
- axis.max = axis.max + distance;
- }
- /**
- * Apply a transform to an axis from the latest resolved motion values.
- * This function basically acts as a bridge between a flat motion value map
- * and applyAxisDelta
- */
- function transformAxis(axis, axisTranslate, axisScale, boxScale, axisOrigin = 0.5) {
- const originPoint = mixNumber(axis.min, axis.max, axisOrigin);
- // Apply the axis delta to the final axis
- applyAxisDelta(axis, axisTranslate, axisScale, originPoint, boxScale);
- }
- /**
- * Apply a transform to a box from the latest resolved motion values.
- */
- function transformBox(box, transform) {
- transformAxis(box.x, transform.x, transform.scaleX, transform.scale, transform.originX);
- transformAxis(box.y, transform.y, transform.scaleY, transform.scale, transform.originY);
- }
- export { applyAxisDelta, applyBoxDelta, applyPointDelta, applyTreeDeltas, scalePoint, transformAxis, transformBox, translateAxis };
|