From 1f54d0886fbd3f9eedf410b5a312ec4f6b47d939 Mon Sep 17 00:00:00 2001 From: Gonzalo DCL Date: Thu, 5 Oct 2023 12:33:46 -0300 Subject: [PATCH] add tests --- .../ecs/src/runtime/initialization/index.ts | 9 +- packages/@dcl/ecs/src/systems/tween.ts | 148 ++++++++++ .../etc/playground-assets.api.md | 13 +- .../sdk7-humming-birds-sync/src/index.ts | 24 +- .../src/moving-platforms-old.ts | 93 ++++++ .../src/moving-platforms.ts | 271 +++++------------- test/ecs/components/Tween.spec.ts | 38 +++ test/ecs/components/TweenSequence.spec.ts | 37 +++ test/ecs/components/TweenState.spec.ts | 19 ++ .../{ => events}/raycastHelperSystem.spec.ts | 0 test/ecs/events/tween.spec.ts | 0 .../{ => events}/videoEventsSystem.spec.ts | 2 +- test/snapshots/package-lock.json | 11 +- 13 files changed, 446 insertions(+), 219 deletions(-) create mode 100644 packages/@dcl/ecs/src/systems/tween.ts create mode 100644 test/build-ecs/fixtures/sdk7-humming-birds-sync/src/moving-platforms-old.ts create mode 100644 test/ecs/components/Tween.spec.ts create mode 100644 test/ecs/components/TweenSequence.spec.ts create mode 100644 test/ecs/components/TweenState.spec.ts rename test/ecs/{ => events}/raycastHelperSystem.spec.ts (100%) create mode 100644 test/ecs/events/tween.spec.ts rename test/ecs/{ => events}/videoEventsSystem.spec.ts (99%) diff --git a/packages/@dcl/ecs/src/runtime/initialization/index.ts b/packages/@dcl/ecs/src/runtime/initialization/index.ts index 4489fc62d..bcb7cf305 100644 --- a/packages/@dcl/ecs/src/runtime/initialization/index.ts +++ b/packages/@dcl/ecs/src/runtime/initialization/index.ts @@ -9,6 +9,7 @@ import { createPointerEventsSystem, PointerEventsSystem } from '../../systems/ev import { createInputSystem, IInputSystem } from './../../engine/input' import { createRaycastSystem, RaycastSystem } from '../../systems/raycast' import { createVideoEventsSystem, VideoEventsSystem } from '../../systems/videoEvents' +import { TweenSystem, createTweenSystem } from '../../systems/tween' /** * @public @@ -50,13 +51,19 @@ export const raycastSystem: RaycastSystem = /* @__PURE__ */ createRaycastSystem( export { RaycastSystem } /** - * @alpha * @public * Register callback functions to a particular entity on video events. */ export const videoEventsSystem: VideoEventsSystem = /* @__PURE__ */ createVideoEventsSystem(engine) export { VideoEventsSystem } +/** + * @public + * Register callback functions to a particular entity on video events. + */ +export const tweenSystem: TweenSystem = createTweenSystem(engine) +export { TweenSystem } + /** * @public * Runs an async function diff --git a/packages/@dcl/ecs/src/systems/tween.ts b/packages/@dcl/ecs/src/systems/tween.ts new file mode 100644 index 000000000..815ca53f1 --- /dev/null +++ b/packages/@dcl/ecs/src/systems/tween.ts @@ -0,0 +1,148 @@ +import * as components from '../components' +import { PBTween, TweenLoop, TweenStateStatus } from '../components' +import { Entity, IEngine } from '../engine' +import { ReadWriteByteBuffer } from '../serialization/ByteBuffer' +import { dataCompare } from './crdt/utils' + +export type TweenSystem = { + tweenCompleted(entity: Entity): boolean + tweenChanged(entity: Entity): boolean +} + +/** + * @internal + * @returns tween helper to be used on the scene + */ +export function createTweenSystem(engine: IEngine): TweenSystem { + const Tween = components.Tween(engine) + const TweenState = components.TweenState(engine) + const TweenSequence = components.TweenSequence(engine) + + const cache = new Map< + Entity, + { + // Used to detect new tweens for the same entity + tween: Uint8Array + // Avoid updaing again the tween in the case we receieve a network tween from other client + frames: number + // Trigger the isCompleted only once per tween + completed: boolean + // Tween has changed on this frame + changed: boolean + } + >() + + function isCompleted(entity: Entity) { + const tweenState = TweenState.getOrNull(entity) + const tween = Tween.getOrNull(entity) + const tweenCache = cache.get(entity) + if (!tweenState || !tween) return false + + if ( + // Renderer notified that the tween is completed + (tweenChanged(entity) || tweenState.state === TweenStateStatus.TS_COMPLETED) && + // Avoid sending isCompleted multiple times + !tweenCache?.completed && + // Amount of frames needed to consider a tween completed + (tweenCache?.frames ?? 0) > 2 + ) { + return true + } + + return false + } + + function tweenChanged(entity: Entity) { + const currentTween = Tween.getOrNull(entity) + const prevTween = cache.get(entity)?.tween + + if ((currentTween && !prevTween) || (!currentTween && prevTween)) { + return true + } + + const currentBuff = new ReadWriteByteBuffer() + Tween.schema.serialize(currentTween!, currentBuff) + const equal = dataCompare(currentBuff.toBinary(), prevTween) + + return equal + } + + const restartTweens: (() => void)[] = [] + // Logic for sequence tweens + engine.addSystem(() => { + for (const restart of restartTweens) { + restart() + } + restartTweens.length = 0 + for (const [entity, tween] of engine.getEntitiesWith(Tween)) { + if (tweenChanged(entity)) { + const buffer = new ReadWriteByteBuffer() + Tween.schema.serialize(tween, buffer) + cache.set(entity, { + tween: buffer.toBinary(), + frames: 0, + completed: false, + changed: true + }) + continue + } + const tweenCache = cache.get(entity)! + tweenCache.frames += 1 + tweenCache.changed = false + if (isCompleted(entity)) { + // Reset tween frames. + tweenCache.frames = 0 + // set the tween completed to avoid calling this again for the same tween + tweenCache.completed = true + + const tweenSequence = TweenSequence.getOrNull(entity) + if (!tweenSequence) continue + const { sequence } = tweenSequence + + if (sequence && sequence.length) { + const [nextTweenSequence, ...otherTweens] = sequence + Tween.createOrReplace(entity, nextTweenSequence) + const mutableTweenHelper = TweenSequence.getMutable(entity) + mutableTweenHelper.sequence = otherTweens + if (tweenSequence.loop === TweenLoop.TL_RESTART) { + mutableTweenHelper.sequence.push(tween) + } + } else if (tweenSequence.loop === TweenLoop.TL_YOYO) { + const newTween = backwardsTween(tween) + Tween.createOrReplace(entity, newTween) + } else if (tweenSequence.loop === TweenLoop.TL_RESTART) { + // Tween.getMutable(entity).currentTime = (tween.currentTime || 0) + 0.00001 + Tween.deleteFrom(entity) + cache.delete(entity) + + restartTweens.push(() => { + Tween.createOrReplace(entity, tween) + }) + } + } + } + }, Number.NEGATIVE_INFINITY) + + function backwardsTween(tween: PBTween): PBTween { + if (tween.mode?.$case === 'move' && tween.mode.move) { + return { ...tween, mode: { ...tween.mode, move: { start: tween.mode.move.end, end: tween.mode.move.start } } } + } + if (tween.mode?.$case === 'rotate' && tween.mode.rotate) { + return { + ...tween, + mode: { ...tween.mode, rotate: { start: tween.mode.rotate.end, end: tween.mode.rotate.start } } + } + } + if (tween.mode?.$case === 'scale' && tween.mode.scale) { + return { ...tween, mode: { ...tween.mode, scale: { start: tween.mode.scale.end, end: tween.mode.scale.start } } } + } + + throw new Error('Invalid tween') + } + + return { + // This event is fired only once per tween + tweenCompleted: isCompleted, + tweenChanged: (entity) => !!cache.get(entity)?.changed + } +} diff --git a/packages/@dcl/playground-assets/etc/playground-assets.api.md b/packages/@dcl/playground-assets/etc/playground-assets.api.md index b64fa807c..4530282c2 100644 --- a/packages/@dcl/playground-assets/etc/playground-assets.api.md +++ b/packages/@dcl/playground-assets/etc/playground-assets.api.md @@ -3808,6 +3808,17 @@ export const enum TweenStateStatus { TS_PAUSED = 2 } +// Warning: (ae-missing-release-tag) "TweenSystem" is part of the package's API, but it is missing a release tag (@alpha, @beta, @public, or @internal) +// +// @public (undocumented) +export type TweenSystem = { + tweenCompleted(entity: Entity): void; + tweenChanged(entity: Entity): void; +}; + +// @public +export const tweenSystem: TweenSystem; + // @public export interface UiAvatarTexture { // (undocumented) @@ -4062,8 +4073,6 @@ export interface VideoEventsSystem { removeVideoEventsEntity(entity: Entity): void; } -// Warning: (ae-extra-release-tag) The doc comment should not contain more than one release tag -// // @public export const videoEventsSystem: VideoEventsSystem; diff --git a/test/build-ecs/fixtures/sdk7-humming-birds-sync/src/index.ts b/test/build-ecs/fixtures/sdk7-humming-birds-sync/src/index.ts index f10d58e40..8fa07e8b9 100644 --- a/test/build-ecs/fixtures/sdk7-humming-birds-sync/src/index.ts +++ b/test/build-ecs/fixtures/sdk7-humming-birds-sync/src/index.ts @@ -8,8 +8,7 @@ import { pointerEventsSystem, Schemas, SyncComponents, - Transform, - Tween + Transform } from '@dcl/sdk/ecs' import { getRealm } from '~system/Runtime' import { createNetworkManager } from '@dcl/sdk/network-transport' @@ -21,6 +20,7 @@ import { getUserData } from '~system/UserIdentity' import { NetworkManager } from '@dcl/sdk/network-transport/types' import { createMovingPlatforms } from './moving-platforms' import { changeColorSystem, createCube } from './create-cube' +import { createMovingPlatformsOld } from './moving-platforms-old' export const GameStatus = engine.defineComponent('game-status', { paused: Schemas.Boolean }) @@ -36,17 +36,20 @@ export async function main() { const serverUrl = realm.realmInfo?.isPreview ? 'ws://127.0.0.1:3000/ws/localScene' : 'wss://scene-state-server.decentraland.org/ws/boedo.dcl.eth' - const networkManager = await createNetworkManager({ - serverUrl, - networkEntitiesLimit: { serverLimit: 500, clientLimit: 15 } - }) + const networkManager = + engine || + (await createNetworkManager({ + serverUrl, + networkEntitiesLimit: { serverLimit: 500, clientLimit: 15 } + })) const userId = (await getUserData({})).data?.userId ?? '' setupUi(userId) - if (server) { + if (server || true) { engine.addSystem(moveHummingBirds) gameStatusServer(networkManager) createMovingPlatforms(networkManager) + createMovingPlatformsOld(networkManager) for (const [x, y, z] of [ [44, 1, 26], [36, 2, 37], @@ -61,6 +64,7 @@ export async function main() { } // return } + if (!server) { engine.addSystem(changeColorSystem) engine.addSystem(shootBirds(userId)) @@ -85,6 +89,12 @@ export async function main() { src: 'models/staticPlatforms.glb' }) + const staticPlatform = engine.addEntity() + Transform.create(staticPlatform, { position: { x: 0, y: 0, z: 20 } }) + GltfContainer.create(staticPlatform, { + src: 'models/staticPlatforms.glb' + }) + const tree = engine.addEntity() Transform.create(tree, { position: { x: 20, y: 0, z: 8 }, diff --git a/test/build-ecs/fixtures/sdk7-humming-birds-sync/src/moving-platforms-old.ts b/test/build-ecs/fixtures/sdk7-humming-birds-sync/src/moving-platforms-old.ts new file mode 100644 index 000000000..c783fa7a4 --- /dev/null +++ b/test/build-ecs/fixtures/sdk7-humming-birds-sync/src/moving-platforms-old.ts @@ -0,0 +1,93 @@ +import { GltfContainer, Transform, SyncComponents, Entity } from '@dcl/ecs' +import * as utils from '@dcl-sdk/utils' +import { Vector3 } from '@dcl/sdk/math' +import { engine } from '@dcl/sdk/ecs' +import { NetworkManager } from '@dcl/sdk/network-transport/types' + +const diffZ = 20 + +export function createMovingPlatformsOld(networkedEntityFactory: NetworkManager) { + //// triggerable platform + + //// only horizontal + const platform1 = networkedEntityFactory.addEntity(engine) + GltfContainer.create(platform1, { + src: 'models/movingPlatform.glb' + }) + Transform.create(platform1, { + position: Vector3.create(2, 1.5, 8 + diffZ) + }) + SyncComponents.create(platform1, { componentIds: [Transform.componentId] }) + //// only vertical + const platform2 = networkedEntityFactory.addEntity(engine) + GltfContainer.create(platform2, { + src: 'models/movingPlatform.glb' + }) + Transform.create(platform2, { + position: Vector3.create(4, 1.5, 14 + diffZ) + }) + SyncComponents.create(platform2, { componentIds: [Transform.componentId] }) + + //// path with many waypoints + const platform4 = networkedEntityFactory.addEntity(engine) + GltfContainer.create(platform4, { + src: 'models/movingPlatform.glb' + }) + Transform.create(platform4, { + position: Vector3.create(6.5, 7, 4 + diffZ) + }) + SyncComponents.create(platform4, { componentIds: [Transform.componentId] }) + + const platform3 = networkedEntityFactory.addEntity(engine) + GltfContainer.create(platform3, { + src: 'models/movingPlatform.glb' + }) + Transform.create(platform3, { + position: Vector3.create(14, 4, 12 + diffZ) + }) + SyncComponents.create(platform3, { componentIds: [Transform.componentId] }) + startPath( + platform3, + [Vector3.create(14, 4, 12 + diffZ), Vector3.create(14, 4, 4 + diffZ), Vector3.create(14, 4, 12 + diffZ)], + 3, + false, + true + ) + + startPath( + platform1, + [Vector3.create(2, 1.5, 8 + diffZ), Vector3.create(2, 1.5, 10 + diffZ), Vector3.create(2, 1.5, 8 + diffZ)], + 3, + false, + true + ) + + startPath( + platform2, + [Vector3.create(4, 1.5, 14 + diffZ), Vector3.create(4, 4, 14 + diffZ), Vector3.create(4, 1.5, 14 + diffZ)], + 2, + false, + true + ) + + startPath( + platform4, + [ + Vector3.create(6.5, 7, 4 + diffZ), + Vector3.create(6.5, 7, 12 + diffZ), + Vector3.create(6.5, 10.5, 12 + diffZ), + Vector3.create(6.5, 10.5, 4 + diffZ), + Vector3.create(6.5, 7, 4 + diffZ) + ], + 40, + false, + true + ) +} + +// function to make path following recursive +function startPath(entity: Entity, path: Vector3[], duration: number, facePath?: boolean, loop?: boolean) { + utils.paths.startStraightPath(entity, path, duration, false, function () { + if (loop) startPath(entity, path, duration, facePath, loop) + }) +} diff --git a/test/build-ecs/fixtures/sdk7-humming-birds-sync/src/moving-platforms.ts b/test/build-ecs/fixtures/sdk7-humming-birds-sync/src/moving-platforms.ts index 3f1502609..f0ccd7eaf 100644 --- a/test/build-ecs/fixtures/sdk7-humming-birds-sync/src/moving-platforms.ts +++ b/test/build-ecs/fixtures/sdk7-humming-birds-sync/src/moving-platforms.ts @@ -4,40 +4,34 @@ import { SyncComponents, Tween, EasingFunction, - TweenState, - TweenStateStatus, - PBTween, TweenSequence, - Entity, - TweenLoop + TweenLoop, + tweenSystem } from '@dcl/ecs' import { Quaternion, Vector3 } from '@dcl/sdk/math' import { engine } from '@dcl/sdk/ecs' import { NetworkManager } from '@dcl/sdk/network-transport/types' import { isServer } from '~system/EngineApi' -import { ReadWriteByteBuffer } from '@dcl/ecs/dist/serialization/ByteBuffer' -import { dataCompare } from '@dcl/ecs/dist/systems/crdt/utils' export function createMovingPlatforms(networkedEntityFactory: NetworkManager) { //// triggerable platform - // only horizontal - // const platform1 = networkedEntityFactory.addEntity(engine) - // GltfContainer.create(platform1, { - // src: 'models/movingPlatform.glb' - // }) - // Transform.create(platform1, { - // position: Vector3.create(2, 1.5, 8) - // }) - // SyncComponents.create(platform1, { componentIds: [Tween.componentId] }) + const platform1 = networkedEntityFactory.addEntity(engine) + GltfContainer.create(platform1, { + src: 'models/movingPlatform.glb' + }) + Transform.create(platform1, { + position: Vector3.create(2, 1.5, 8) + }) + SyncComponents.create(platform1, { componentIds: [Tween.componentId] }) - // Tween.create(platform1, { - // mode: Tween.Mode.Move({ start: Vector3.create(2, 1.5, 6.5), end: Vector3.create(2, 1.5, 12) }), - // duration: 4000, - // tweenFunction: EasingFunction.TF_LINEAR - // }) + Tween.create(platform1, { + mode: Tween.Mode.Move({ start: Vector3.create(2, 1.5, 6.5), end: Vector3.create(2, 1.5, 12) }), + duration: 4000, + tweenFunction: EasingFunction.TF_LINEAR + }) - // TweenSequence.create(platform1, { loop: TweenLoop.TL_RESTART, sequence: [] }) + TweenSequence.create(platform1, { loop: TweenLoop.TL_RESTART, sequence: [] }) // only vertical const parent = networkedEntityFactory.addEntity(engine) @@ -83,55 +77,59 @@ export function createMovingPlatforms(networkedEntityFactory: NetworkManager) { ] }) - // const platform3 = networkedEntityFactory.addEntity(engine) - // GltfContainer.create(platform3, { - // src: 'models/movingPlatform.glb' - // }) - // Transform.create(platform3, { - // position: Vector3.create(14, 4, 12) - // }) - // SyncComponents.create(platform3, { componentIds: [Tween.componentId] }) - // Tween.create(platform3, { - // mode: Tween.Mode.Move({ start: Vector3.create(14, 4, 12), end: Vector3.create(14, 4, 4) }), - // duration: 5000, - // tweenFunction: EasingFunction.TF_LINEAR - // }) - // TweenSequence.create(platform3, { loop: TweenLoop.TL_YOYO, sequence: [] }) - - // // //// path with many waypoints - // const platform4 = networkedEntityFactory.addEntity(engine) - // GltfContainer.create(platform4, { - // src: 'models/movingPlatform.glb' - // }) - // Transform.create(platform4, { - // position: Vector3.create(6.5, 7, 4) - // }) - // SyncComponents.create(platform4, { componentIds: [Tween.componentId, TweenSequence.componentId] }) + const platform3 = networkedEntityFactory.addEntity(engine) + GltfContainer.create(platform3, { + src: 'models/movingPlatform.glb' + }) + Transform.create(platform3, { + position: Vector3.create(14, 4, 12) + }) + SyncComponents.create(platform3, { componentIds: [Tween.componentId] }) + Tween.create(platform3, { + mode: Tween.Mode.Move({ start: Vector3.create(14, 4, 12), end: Vector3.create(14, 4, 4) }), + duration: 5000, + tweenFunction: EasingFunction.TF_LINEAR + }) + TweenSequence.create(platform3, { loop: TweenLoop.TL_YOYO, sequence: [] }) - // const tween = Tween.create(platform4, { - // duration: 4000, - // tweenFunction: EasingFunction.TF_LINEAR, - // // { $case: 'move', move: { start, end }} // - // mode: Tween.Mode.Move({ start: Vector3.create(6.5, 7, 4), end: Vector3.create(6.5, 7, 12) }) - // }) + // //// path with many waypoints + const platform4 = networkedEntityFactory.addEntity(engine) + GltfContainer.create(platform4, { + src: 'models/movingPlatform.glb' + }) + Transform.create(platform4, { + position: Vector3.create(6.5, 7, 4) + }) + SyncComponents.create(platform4, { componentIds: [Tween.componentId, TweenSequence.componentId] }) + + Tween.create(platform4, { + duration: 4000, + tweenFunction: EasingFunction.TF_LINEAR, + currentTime: 0, + playing: true, + mode: Tween.Mode.Move({ start: Vector3.create(6.5, 7, 4), end: Vector3.create(6.5, 7, 12) }) + }) - // TweenSequence.create(platform4, { - // sequence: [ - // { - // ...tween, - // mode: Tween.Mode.Move({ start: Vector3.create(6.5, 7, 12), end: Vector3.create(6.5, 10.5, 12) }) - // }, - // { - // ...tween, - // mode: Tween.Mode.Move({ start: Vector3.create(6.5, 10.5, 12), end: Vector3.create(6.5, 10.5, 4) }) - // }, - // { - // ...tween, - // mode: Tween.Mode.Move({ start: Vector3.create(6.5, 10.5, 4), end: Vector3.create(6.5, 7, 4) }) - // } - // ], - // loop: TweenLoop.TL_RESTART - // }) + TweenSequence.create(platform4, { + sequence: [ + { + duration: 2000, + tweenFunction: EasingFunction.TF_EASEBOUNCE, + mode: Tween.Mode.Move({ start: Vector3.create(6.5, 7, 12), end: Vector3.create(6.5, 10.5, 12) }) + }, + { + duration: 3000, + tweenFunction: EasingFunction.TF_EASEBOUNCE, + mode: Tween.Mode.Move({ start: Vector3.create(6.5, 10.5, 12), end: Vector3.create(6.5, 10.5, 4) }) + }, + { + duration: 3000, + tweenFunction: EasingFunction.TF_LINEAR, + mode: Tween.Mode.Move({ start: Vector3.create(6.5, 10.5, 4), end: Vector3.create(6.5, 7, 4) }) + } + ], + loop: TweenLoop.TL_RESTART + }) } void isServer({}).then(({ isServer }) => { @@ -144,142 +142,9 @@ function testingSystem() { if (tweenSystem.tweenCompleted(entity)) { console.log('[TestingSystem]: tween completed', entity) } + if (tweenSystem.tweenChanged(entity)) { console.log('[TestingSystem]: tween changed', entity) } } } - -const tweenSystem = TweenSystem() - -function TweenSystem() { - const cache = new Map< - Entity, - { - // Used to detect new tweens for the same entity - tween: Uint8Array - // Avoid updaing again the tween in the case we receieve a network tween from other client - frames: number - // Trigger the isCompleted only once per tween - completed: boolean - // Tween has changed on this frame - changed: boolean - } - >() - - function isCompleted(entity: Entity) { - const tweenState = TweenState.getOrNull(entity) - const tween = Tween.getOrNull(entity) - const tweenCache = cache.get(entity) - if (!tweenState || !tween) return false - - if ( - // Renderer notified that the tween is completed - (tweenChanged(entity) || tweenState.state === TweenStateStatus.TS_COMPLETED) && - // Avoid sending isCompleted multiple times - !tweenCache?.completed && - // Amount of frames needed to consider a tween completed - (tweenCache?.frames ?? 0) > 2 - ) { - return true - } - - return false - } - - function tweenChanged(entity: Entity) { - const currentTween = Tween.getOrNull(entity) - const prevTween = cache.get(entity)?.tween - - if ((currentTween && !prevTween) || (!currentTween && prevTween)) { - return true - } - - const currentBuff = new ReadWriteByteBuffer() - Tween.schema.serialize(currentTween!, currentBuff) - const equal = dataCompare(currentBuff.toBinary(), prevTween) - - return equal - } - - const restartTweens: (() => void)[] = [] - // Logic for sequence tweens - engine.addSystem(() => { - for (const restart of restartTweens) { - restart() - } - restartTweens.length = 0 - for (const [entity, tween] of engine.getEntitiesWith(Tween)) { - if (tweenChanged(entity)) { - const buffer = new ReadWriteByteBuffer() - Tween.schema.serialize(tween, buffer) - cache.set(entity, { - tween: buffer.toBinary(), - frames: 0, - completed: false, - changed: true - }) - continue - } - const tweenCache = cache.get(entity)! - tweenCache.frames += 1 - tweenCache.changed = false - if (isCompleted(entity)) { - // Reset tween frames. - tweenCache.frames = 0 - // set the tween completed to avoid calling this again for the same tween - tweenCache.completed = true - - const tweenSequence = TweenSequence.getOrNull(entity) - if (!tweenSequence) continue - const { sequence } = tweenSequence - - if (sequence && sequence.length) { - const [nextTweenSequence, ...otherTweens] = sequence - Tween.createOrReplace(entity, nextTweenSequence) - const mutableTweenHelper = TweenSequence.getMutable(entity) - mutableTweenHelper.sequence = otherTweens - if (tweenSequence.loop === TweenLoop.TL_RESTART) { - mutableTweenHelper.sequence.push(tween) - } - } else if (tweenSequence.loop === TweenLoop.TL_YOYO) { - const newTween = backwardsTween(tween) - Tween.createOrReplace(entity, newTween) - } else if (tweenSequence.loop === TweenLoop.TL_RESTART) { - // Tween.getMutable(entity).currentTime = (tween.currentTime || 0) + 0.00001 - Tween.deleteFrom(entity) - cache.delete(entity) - - restartTweens.push(() => { - Tween.createOrReplace(entity, tween) - }) - } - } - } - }, Number.NEGATIVE_INFINITY) - - function backwardsTween(tween: PBTween): PBTween { - if (tween.mode?.$case === 'move' && tween.mode.move) { - return { - ...tween, - mode: { ...tween.mode, move: { start: tween.mode.move.end, end: tween.mode.move.start } } - } - } - if (tween.mode?.$case === 'rotate' && tween.mode.rotate) { - return { - ...tween, - mode: { ...tween.mode, rotate: { start: tween.mode.rotate.end, end: tween.mode.rotate.start } } - } - } - if (tween.mode?.$case === 'scale' && tween.mode.scale) { - return { ...tween, mode: { ...tween.mode, scale: { start: tween.mode.scale.end, end: tween.mode.scale.start } } } - } - throw new Error('Invalid tween') - } - - return { - // This event is fired only once per tween - tweenCompleted: isCompleted, - tweenChanged: (entity: Entity) => !!cache.get(entity)?.changed - } -} diff --git a/test/ecs/components/Tween.spec.ts b/test/ecs/components/Tween.spec.ts new file mode 100644 index 000000000..257538824 --- /dev/null +++ b/test/ecs/components/Tween.spec.ts @@ -0,0 +1,38 @@ +import { EasingFunction, Engine, components } from '../../../packages/@dcl/ecs/src' +import { testComponentSerialization } from './assertion' + +describe('Generated Tween ProtoBuf', () => { + const start = { x: 0, y: 0, z: 0 } + const end = { x: 8, y: 8, z: 8 } + it('should serialize/deserialize move Tween', () => { + const newEngine = Engine() + const Tween = components.Tween(newEngine) + + testComponentSerialization(Tween, { + duration: 1, + tweenFunction: EasingFunction.TF_LINEAR, + mode: Tween.Mode.Move({ start, end }), + playing: false, + currentTime: 0, + faceDirection: undefined + }) + + testComponentSerialization(Tween, { + duration: 1, + tweenFunction: EasingFunction.TF_LINEAR, + mode: Tween.Mode.Scale({ start, end }), + playing: true, + currentTime: 1, + faceDirection: true + }) + + testComponentSerialization(Tween, { + duration: 1, + tweenFunction: EasingFunction.TF_LINEAR, + mode: Tween.Mode.Rotate({ start: { ...start, w: 0 }, end: { ...end, w: 8 } }), + playing: false, + currentTime: 0, + faceDirection: undefined + }) + }) +}) diff --git a/test/ecs/components/TweenSequence.spec.ts b/test/ecs/components/TweenSequence.spec.ts new file mode 100644 index 000000000..d8b45cca8 --- /dev/null +++ b/test/ecs/components/TweenSequence.spec.ts @@ -0,0 +1,37 @@ +import { EasingFunction, Engine, Tween, TweenLoop, components } from '../../../packages/@dcl/ecs/src' +import { testComponentSerialization } from './assertion' + +describe('Generated TweenSequence ProtoBuf', () => { + it('should serialize/deserialize move TweenSequence', () => { + const newEngine = Engine() + const TweenSequence = components.TweenSequence(newEngine) + + testComponentSerialization(TweenSequence, { + sequence: [ + { + duration: 8, + currentTime: 1, + playing: true, + mode: Tween.Mode.Move({ start: { x: 0, y: 0, z: 0 }, end: { x: 8, y: 8, z: 8 } }), + tweenFunction: EasingFunction.TF_EASEBACK, + faceDirection: true + } + ], + loop: TweenLoop.TL_RESTART + }) + + testComponentSerialization(TweenSequence, { + sequence: [ + { + duration: 8, + currentTime: 1, + playing: true, + mode: Tween.Mode.Move({ start: { x: 0, y: 0, z: 0 }, end: { x: 8, y: 8, z: 8 } }), + tweenFunction: EasingFunction.TF_EASEBACK, + faceDirection: undefined + } + ], + loop: TweenLoop.TL_YOYO + }) + }) +}) diff --git a/test/ecs/components/TweenState.spec.ts b/test/ecs/components/TweenState.spec.ts new file mode 100644 index 000000000..938dd36c3 --- /dev/null +++ b/test/ecs/components/TweenState.spec.ts @@ -0,0 +1,19 @@ +import { Engine, TweenStateStatus, components } from '../../../packages/@dcl/ecs/src' +import { testComponentSerialization } from './assertion' + +describe('Generated TweenStateState ProtoBuf', () => { + it('should serialize/deserialize move TweenState', () => { + const newEngine = Engine() + const TweenState = components.TweenState(newEngine) + + testComponentSerialization(TweenState, { + state: TweenStateStatus.TS_ACTIVE, + currentTime: 8 + }) + + testComponentSerialization(TweenState, { + state: TweenStateStatus.TS_COMPLETED, + currentTime: 0 + }) + }) +}) diff --git a/test/ecs/raycastHelperSystem.spec.ts b/test/ecs/events/raycastHelperSystem.spec.ts similarity index 100% rename from test/ecs/raycastHelperSystem.spec.ts rename to test/ecs/events/raycastHelperSystem.spec.ts diff --git a/test/ecs/events/tween.spec.ts b/test/ecs/events/tween.spec.ts new file mode 100644 index 000000000..e69de29bb diff --git a/test/ecs/videoEventsSystem.spec.ts b/test/ecs/events/videoEventsSystem.spec.ts similarity index 99% rename from test/ecs/videoEventsSystem.spec.ts rename to test/ecs/events/videoEventsSystem.spec.ts index 96f199559..54a3cd23b 100644 --- a/test/ecs/videoEventsSystem.spec.ts +++ b/test/ecs/events/videoEventsSystem.spec.ts @@ -5,7 +5,7 @@ import { IEngine, VideoEventsSystem, VideoState -} from '../../packages/@dcl/ecs/src' +} from '../../../packages/@dcl/ecs/src' describe('Video events helper system should', () => { const engine: IEngine = Engine() diff --git a/test/snapshots/package-lock.json b/test/snapshots/package-lock.json index 86f6834c4..1e9aca30e 100644 --- a/test/snapshots/package-lock.json +++ b/test/snapshots/package-lock.json @@ -150,7 +150,7 @@ "dependencies": { "@dcl/ecs": "file:../ecs", "@dcl/ecs-math": "2.0.2", - "@dcl/explorer": "1.0.143989-20230907142850.commit-0c0a775", + "@dcl/explorer": "1.0.147349-20230925233009.commit-2703172", "@dcl/js-runtime": "file:../js-runtime", "@dcl/react-ecs": "file:../react-ecs", "@dcl/sdk-commands": "file:../sdk-commands" @@ -165,9 +165,10 @@ "@dcl/ecs": "file:../ecs", "@dcl/hashing": "1.1.3", "@dcl/inspector": "file:../inspector", - "@dcl/linker-dapp": "0.10.1", + "@dcl/linker-dapp": "^0.11.0", "@dcl/mini-comms": "1.0.1-20230216163137.commit-a4c75be", - "@dcl/protocol": "1.0.0-5812097343.commit-8025576", + "@dcl/protocol": "1.0.0-6314457636.commit-a9a962a", + "@dcl/quests-manager": "^0.1.2", "@dcl/rpc": "^1.1.1", "@dcl/schemas": "^8.2.3-20230718182824.commit-356025c", "@segment/analytics-node": "^1.0.0-beta.22", @@ -186,7 +187,7 @@ "fp-future": "^1.0.1", "glob": "^9.3.2", "ignore": "^5.2.4", - "node-fetch": "^2.6.8", + "node-fetch": "^2.7.0", "open": "^8.4.0", "portfinder": "^1.0.32", "prompts": "^2.4.2", @@ -199,7 +200,7 @@ }, "devDependencies": { "@types/archiver": "^5.3.2", - "@types/node-fetch": "^2.6.1", + "@types/node-fetch": "^2.6.4", "@types/prompts": "^2.4.4", "@types/uuid": "^9.0.1", "@types/ws": "^8.5.4"