From f47cf5c8fc881d1418c20e986bf0724cea024346 Mon Sep 17 00:00:00 2001 From: MNAth_ Date: Thu, 28 Dec 2023 18:42:10 +0300 Subject: [PATCH] feat: camera transition update --- src/experiences/pages/Home/Navigation.ts | 32 +- src/experiences/pages/Home/Renderer.ts | 3 +- src/experiences/pages/Home/World/Scene_1.ts | 9 +- src/experiences/pages/Home/World/Scene_2.ts | 8 +- src/experiences/pages/Home/World/Scene_3.ts | 15 +- src/experiences/pages/Home/World/index.ts | 41 +- .../pages/Home/World/world.manager.ts | 389 ++++++++++++------ src/pages/index.vue | 12 +- src/pages/index/contact.vue | 2 +- src/pages/index/index.vue | 2 +- src/pages/index/skills.vue | 2 +- 11 files changed, 355 insertions(+), 160 deletions(-) diff --git a/src/experiences/pages/Home/Navigation.ts b/src/experiences/pages/Home/Navigation.ts index 13b86c9..8a53ede 100644 --- a/src/experiences/pages/Home/Navigation.ts +++ b/src/experiences/pages/Home/Navigation.ts @@ -13,8 +13,8 @@ export class Navigation extends ExperienceBasedBlueprint { protected _experience = new HomeExperience(); protected _router = useRouter(); protected _route = useRoute(); - protected _availableRoutes: string[] = []; - protected _currentRouteIndex: number = 0; + protected _availableRoutes: { [routeName: string]: RouteRecordRaw } = {}; + protected _currentRouteName?: string; constructor() { super(); @@ -28,9 +28,9 @@ export class Navigation extends ExperienceBasedBlueprint { const CAUSE = _.cause as RouteRecordNormalized | undefined; if (!CAUSE?.children.length) return; - this._availableRoutes = CAUSE.children.map( - (route) => route.name?.toString() || "" - ); + CAUSE.children.forEach((route) => { + this._availableRoutes[route.name?.toString() ?? ""] = route; + }); } this._setCurrentRouteIndexFromName(this._route.name?.toString()); @@ -41,23 +41,31 @@ export class Navigation extends ExperienceBasedBlueprint { }); } + private _setCurrentRouteIndexFromName(routeName?: string) { + if (!routeName || !this._availableRoutes[routeName]) + throw new Error("Route name not available", { cause: WRONG_PARAM }); + + this._currentRouteName = routeName; + } + public get availableRoutes() { return this._availableRoutes; } public get currentRoute() { - return this.availableRoutes[this._currentRouteIndex]; + if (!this._currentRouteName) return undefined; + + return this.availableRoutes[this._currentRouteName]; } - public get currentRouteIndex() { - return this._currentRouteIndex; + public get currentRouteName() { + return this._currentRouteName; } - protected _setCurrentRouteIndexFromName(routeName?: string) { - if (!routeName || this._availableRoutes.indexOf(routeName) === -1) - throw new Error("Route name not available", { cause: WRONG_PARAM }); + public get currentRouteKey() { + if (!this._currentRouteName) return undefined; - this._currentRouteIndex = this._availableRoutes.indexOf(routeName); + return this.availableRoutes[this._currentRouteName].meta?.key; } public construct(): void {} diff --git a/src/experiences/pages/Home/Renderer.ts b/src/experiences/pages/Home/Renderer.ts index ce08fe2..b9b5243 100644 --- a/src/experiences/pages/Home/Renderer.ts +++ b/src/experiences/pages/Home/Renderer.ts @@ -1,5 +1,6 @@ import { Box3, + Color, LinearSRGBColorSpace, Matrix4, Mesh, @@ -61,7 +62,7 @@ export default class Renderer extends ExperienceBasedBlueprint { this._appRendererInstance.toneMappingExposure = 1; this._appRendererInstance.shadowMap.enabled = false; this._appRendererInstance.shadowMap.type = PCFShadowMap; - this._appRendererInstance.setClearColor("#211d20"); + this._appRendererInstance.setClearColor("#5f5f5f", 1); this._appRendererInstance.setSize( this._experience.app.sizes.width, this._experience.app.sizes.height diff --git a/src/experiences/pages/Home/World/Scene_1.ts b/src/experiences/pages/Home/World/Scene_1.ts index ef1ae27..fbb49bd 100644 --- a/src/experiences/pages/Home/World/Scene_1.ts +++ b/src/experiences/pages/Home/World/Scene_1.ts @@ -14,6 +14,7 @@ import { WebGLRenderTarget, type Object3DEventMap, VideoTexture, + LinearSRGBColorSpace, } from "three"; import gsap from "gsap"; @@ -58,7 +59,10 @@ export class Scene_1 extends SceneBlueprint { coffeeSteam: "#b7a08e", }; - public pcScreenWebglTexture = new WebGLRenderTarget(4096, 4096); + public pcScreenWebglTexture = new WebGLRenderTarget( + Config.FIXED_WINDOW_WIDTH, + Config.FIXED_WINDOW_HEIGHT + ); public pcTopArticulation?: Object3D; public treeOutside?: Object3D; public pcScreen?: Mesh; @@ -215,14 +219,17 @@ export class Scene_1 extends SceneBlueprint { const PHONE_VIDEO_TEXTURE = new VideoTexture( this.phoneScreenVideo ?? document.createElement("video") ); + PHONE_VIDEO_TEXTURE.colorSpace = LinearSRGBColorSpace; const MONITOR_A_VIDEO_TEXTURE = new VideoTexture( this.monitorAScreenVideo ?? document.createElement("video") ); + MONITOR_A_VIDEO_TEXTURE.colorSpace = LinearSRGBColorSpace; const MONITOR_B_VIDEO_TEXTURE = new VideoTexture( this.monitorBScreenVideo ?? document.createElement("video") ); + MONITOR_B_VIDEO_TEXTURE.colorSpace = LinearSRGBColorSpace; AVAILABLE_MATERIALS["pc_screen"] = new MeshBasicMaterial({ map: this.pcScreenWebglTexture?.texture, diff --git a/src/experiences/pages/Home/World/Scene_2.ts b/src/experiences/pages/Home/World/Scene_2.ts index 9c898dd..618d56c 100644 --- a/src/experiences/pages/Home/World/Scene_2.ts +++ b/src/experiences/pages/Home/World/Scene_2.ts @@ -32,9 +32,15 @@ export class Scene_2 extends SceneBlueprint { const AVAILABLE_MATERIALS: Materials = {}; if (!AVAILABLE_TEXTURE) return AVAILABLE_MATERIALS; + if (this._world?.commonMaterials["scene_container"]) + AVAILABLE_MATERIALS["scene_container"] = + this._world?.commonMaterials["scene_container"].clone(); + AVAILABLE_MATERIALS["scene_container"].alphaTest = 1; + AVAILABLE_MATERIALS["scene_container"].depthWrite = false; AVAILABLE_MATERIALS["scene_2"] = new MeshBasicMaterial({ + alphaMap: AVAILABLE_TEXTURE["cloudAlphaMap"], + alphaTest: 1, map: AVAILABLE_TEXTURE["scene_2_baked_texture"], - transparent: true, }); return AVAILABLE_MATERIALS; diff --git a/src/experiences/pages/Home/World/Scene_3.ts b/src/experiences/pages/Home/World/Scene_3.ts index 014c323..352cf63 100644 --- a/src/experiences/pages/Home/World/Scene_3.ts +++ b/src/experiences/pages/Home/World/Scene_3.ts @@ -59,9 +59,22 @@ export class Scene_3 extends SceneBlueprint { const AVAILABLE_MATERIALS: Materials = {}; if (!AVAILABLE_TEXTURE) return AVAILABLE_MATERIALS; + + if (this._world?.commonMaterials["scene_container"]) { + AVAILABLE_MATERIALS["scene_container"] = + this._world?.commonMaterials["scene_container"].clone(); + AVAILABLE_MATERIALS["scene_container"].alphaTest = 1; + AVAILABLE_MATERIALS["scene_container"].depthWrite = false; + } + + if (this._world?.commonMaterials["glass"]) + AVAILABLE_MATERIALS["glass"] = + this._world?.commonMaterials["glass"].clone(); + AVAILABLE_MATERIALS["scene_3"] = new MeshBasicMaterial({ + alphaMap: AVAILABLE_TEXTURE["cloudAlphaMap"], + alphaTest: 1, map: AVAILABLE_TEXTURE["scene_3_baked_texture"], - transparent: true, }); return AVAILABLE_MATERIALS; diff --git a/src/experiences/pages/Home/World/index.ts b/src/experiences/pages/Home/World/index.ts index 196c152..23f267a 100644 --- a/src/experiences/pages/Home/World/index.ts +++ b/src/experiences/pages/Home/World/index.ts @@ -23,6 +23,7 @@ import { ExperienceBasedBlueprint } from "~/experiences/blueprints/ExperienceBas // MODELS import { CONSTRUCTED, DESTRUCTED } from "~/common/event.model"; import { CAMERA_UNAVAILABLE } from "~/common/error.model"; +import { CONTACT_PAGE, HOME_PAGE, SKILL_PAGE } from "~/common/page.model"; // INTERFACES import type { Materials } from "~/interfaces/experienceWorld"; @@ -35,8 +36,11 @@ export default class World extends ExperienceBasedBlueprint { private readonly _loader = this._experience.loader; private _commonMaterials: Materials = {}; + private _availablePageScenes: { [sceneKey: string]: SceneBlueprint } = {}; private _projectedModelsPosition = new Vector3(); - private _projectedScenes: SceneBlueprint[] = []; + private _projectedSceneContainer?: Group; + + public readonly mainSceneKey = HOME_PAGE; public sceneContainer?: SceneContainer; public scene1?: Scene_1; @@ -62,6 +66,7 @@ export default class World extends ExperienceBasedBlueprint { if (AVAILABLE_TEXTURES["scene_container_baked_texture"] instanceof Texture) this._commonMaterials["scene_container"] = new MeshBasicMaterial({ + alphaMap: AVAILABLE_TEXTURES["cloudAlphaMap"], map: AVAILABLE_TEXTURES["scene_container_baked_texture"], }); @@ -76,12 +81,16 @@ export default class World extends ExperienceBasedBlueprint { return this._commonMaterials; } + public get availablePageScenes() { + return this._availablePageScenes; + } + public get projectedModelsPosition() { return this._projectedModelsPosition; } - public get projectedScenes() { - return this._projectedScenes; + public get projectedSceneContainer() { + return this._projectedSceneContainer; } public destruct() { @@ -127,43 +136,49 @@ export default class World extends ExperienceBasedBlueprint { this.scene1?.construct(); this.scene2?.construct(); this.scene3?.construct(); - this.manager?.construct(); if (this.sceneContainer?.modelScene instanceof Group) { const BOUNDING_BOX = new Box3().setFromObject( this.sceneContainer.modelScene ); - const WIDTH = BOUNDING_BOX.max.x - BOUNDING_BOX.min.x; - // const HEIGHT = BOUNDING_BOX.max.y - BOUNDING_BOX.min.y; + // const WIDTH = BOUNDING_BOX.max.x - BOUNDING_BOX.min.x; + const HEIGHT = BOUNDING_BOX.max.y - BOUNDING_BOX.min.y; - this._projectedModelsPosition.set(WIDTH * 1.2, 0, 0); + this._projectedModelsPosition.set(0, HEIGHT * -2, 0); - const PROJECTED_SCENE_CONTAINER = this.sceneContainer.modelScene.clone(); - PROJECTED_SCENE_CONTAINER.position.copy(this._projectedModelsPosition); + this._projectedSceneContainer = this.sceneContainer.modelScene.clone(); + this._projectedSceneContainer.position.copy( + this._projectedModelsPosition + ); this.group?.add( this.sceneContainer.modelScene, - PROJECTED_SCENE_CONTAINER + this._projectedSceneContainer ); } - if (this.scene1?.modelScene) this.group?.add(this.scene1.modelScene); + if (this.scene1?.modelScene) { + this.group?.add(this.scene1.modelScene); + this._availablePageScenes[HOME_PAGE] = this.scene1; + } if (this.scene2?.modelScene) { this.scene2.modelScene.position.copy(this.projectedModelsPosition); - this._projectedScenes.push(this.scene2); + this._availablePageScenes[SKILL_PAGE] = this.scene2; this.group?.add(this.scene2.modelScene); } if (this.scene3?.modelScene) { this.scene3.modelScene.position.copy(this.projectedModelsPosition); - this._projectedScenes.push(this.scene3); + this._availablePageScenes[CONTACT_PAGE] = this.scene3; this.group?.add(this.scene3.modelScene); } this._experience.app.scene.add(this.group); + + this.manager?.construct(); this.emit(CONSTRUCTED, this); } diff --git a/src/experiences/pages/Home/World/world.manager.ts b/src/experiences/pages/Home/World/world.manager.ts index 160e5a3..348d2e8 100644 --- a/src/experiences/pages/Home/World/world.manager.ts +++ b/src/experiences/pages/Home/World/world.manager.ts @@ -1,6 +1,13 @@ -import { CatmullRomCurve3, PerspectiveCamera, Raycaster, Vector3 } from "three"; +import { + CatmullRomCurve3, + Material, + Mesh, + PerspectiveCamera, + Raycaster, + Vector3, +} from "three"; import { ShaderPass } from "three/examples/jsm/postprocessing/ShaderPass"; -import GSAP, { Power0 } from "gsap"; +import gsap, { Power0 } from "gsap"; // EXPERIENCES import { HomeExperience } from ".."; @@ -8,6 +15,15 @@ import { HomeExperience } from ".."; // BLUEPRINTS import { ExperienceBasedBlueprint } from "@/experiences/blueprints/ExperienceBased.blueprint"; +// CONFIG +import { Config } from "~/experiences/config/Config"; + +// COMMONS +import { WRONG_PARAM } from "~/common/error.model"; + +// ERROR +import { ErrorFactory } from "~/experiences/errors/Error.factory"; + // EVENTS import { CHANGED, CONSTRUCTED } from "~/common/event.model"; @@ -17,18 +33,37 @@ import { lerpPosition } from "~/utils/three-utils"; // SHADERS import camTransitionFrag from "./shaders/cameraTransition/fragment.glsl"; import camTransitionVert from "./shaders/cameraTransition/vertex.glsl"; +import { SKILL_PAGE } from "~/common/page.model"; export default class WorldManager extends ExperienceBasedBlueprint { protected readonly _experience = new HomeExperience(); - protected readonly _appCamera = this._experience.app.camera; - protected readonly _appResources = this._experience.app.resources; - protected readonly _camera = this._experience.camera; - protected readonly _world = this._experience.world; - protected readonly _composer = this._experience.composer; - protected readonly _renderer = this._experience.renderer; - protected readonly _timeline = GSAP.timeline(); - - public cameraTransitionShaderPass?: ShaderPass; + + private readonly _appCamera = this._experience.app.camera; + private readonly _appResources = this._experience.app.resources; + private readonly _navigation = this._experience.navigation; + private readonly _camera = this._experience.camera; + private readonly _composer = this._experience.composer; + private readonly _renderer = this._experience.renderer; + private readonly _timeline = gsap.timeline(); + private readonly _cameraTransitionShaderPass = new ShaderPass({ + uniforms: { + tDiffuse: { value: null }, + uStrength: { value: 0 }, + uDisplacementMap: { + value: this._appResources.items["rocksAlphaMap"], + }, + }, + vertexShader: camTransitionVert, + fragmentShader: camTransitionFrag, + }); + private _glassEffectOptions: gsap.TweenVars = { + duration: 0.3, + ease: Power0.easeIn, + }; + + private _world: typeof this._experience.world; + private _prevSceneKey?: string; + // TODO: Reorder properties public rayCaster = new Raycaster(); public normalizedCursorPosition = { x: 0, y: 0 }; @@ -57,7 +92,7 @@ export default class WorldManager extends ExperienceBasedBlueprint { */ public autoCameraAnimation = false; /** - * GSAP animation watcher. If GSAP is currently animating + * gsap animation watcher. If gsap is currently animating */ public isGsapAnimating = false; /** @@ -78,27 +113,29 @@ export default class WorldManager extends ExperienceBasedBlueprint { }[] = []; // === ^ - public construct() { + private get _supportedPageKeys() { + if (!this._world?.availablePageScenes) return []; + + return Object.keys(this._world.availablePageScenes); + } + + /** Initialize the the default scenes states. */ + private async _initScenes() { + if (this._supportedPageKeys.length < 2) + throw new ErrorFactory( + new Error("Unable to display the projected scene ", { + cause: WRONG_PARAM, + }) + ); + const currentCamera = this._camera?.cameras[0]; const secondaryCamera = this._camera?.cameras[1]; + let projectedScene = + this._world?.availablePageScenes[this._supportedPageKeys[1]]; if (currentCamera instanceof PerspectiveCamera) this.cameraCurvePath.getPointAt(0, currentCamera.position); - this._world?.scene1?.togglePcOpening()?.then(() => { - if ( - this._world?.scene1?.modelScene && - this._world.scene1.pcScreen && - this._world.scene1.pcScreenWebglTexture && - secondaryCamera - ) - this._renderer?.addPortalAssets(this._world.scene1 + "_pc_screen", { - mesh: this._world.scene1.pcScreen, - meshCamera: secondaryCamera, - meshWebGLTexture: this._world.scene1.pcScreenWebglTexture, - }); - }); - this._appCamera.instance?.position.copy( this._world?.scene1?.cameraPath.getPoint(0) ?? new Vector3() ); @@ -109,21 +146,207 @@ export default class WorldManager extends ExperienceBasedBlueprint { .setY(2) ); - secondaryCamera?.position.copy( - this._world?.scene2?.modelScene?.position ?? new Vector3() + await this._world?.scene1?.togglePcOpening(); + if ( + this._world?.scene1?.modelScene && + this._world.scene1.pcScreen && + this._world.scene1.pcScreenWebglTexture && + secondaryCamera + ) { + this._renderer?.addPortalAssets(this._world.scene1 + "_pc_screen", { + mesh: this._world.scene1.pcScreen, + meshCamera: secondaryCamera, + meshWebGLTexture: this._world.scene1.pcScreenWebglTexture, + }); + + secondaryCamera.position.copy( + new Vector3( + this._world.projectedModelsPosition.x, + this._world.projectedModelsPosition.y + 5, + this._world.projectedModelsPosition.x + -20 + ) + ); + secondaryCamera.lookAt(this._world.projectedModelsPosition); + } + + if ( + typeof this._navigation?.currentRouteKey === "string" && + this._navigation.currentRouteKey !== this._world?.mainSceneKey && + this._navigation.currentRouteKey !== this._supportedPageKeys[1] + ) + projectedScene = + this._world?.availablePageScenes[this._navigation.currentRouteKey]; + + projectedScene?.modelScene?.children.forEach( + (child) => child instanceof Mesh && (child.material.alphaTest = 0) ); - secondaryCamera?.position.set( - this._world?.scene2?.modelScene?.position.x ?? 0, - 8, - 20 + + this._setScene(); + } + + private _triggerGlassTransitionEffect() { + if (!this._cameraTransitionShaderPass.uniforms.uStrength || !this._composer) + return this._timeline; + if (this._timeline.isActive()) this._timeline.progress(1); + + this._cameraTransitionShaderPass.clear = true; + this._cameraTransitionShaderPass.uniforms.uStrength.value = 0; + + this._composer.addPass( + "_cameraTransitionShaderPass", + this._cameraTransitionShaderPass ); - secondaryCamera?.lookAt( - this._world?.scene2?.modelScene?.position ?? new Vector3() + + return this._timeline + .to(this._cameraTransitionShaderPass.material.uniforms.uStrength, { + ...this._glassEffectOptions, + value: 0.175, + }) + .to(this._cameraTransitionShaderPass.material.uniforms.uStrength, { + ...this._glassEffectOptions, + value: 0, + ease: Power0.easeOut, + }) + .add( + () => + this._cameraTransitionShaderPass && + this._composer?.removePass("_cameraTransitionShaderPass"), + ">" + ); + } + + /** + * Transition between projected scenes. + * + * @param nextSceneKey The incoming scene key. + */ + private _changeProjectedScenesTransition(nextSceneKey?: string) { + const CURRENT_SCENE = this._world?.availablePageScenes[nextSceneKey ?? ""]; + + if ( + CURRENT_SCENE?.modelScene && + nextSceneKey !== this._world?.mainSceneKey && + nextSceneKey !== this._prevSceneKey + ) { + const PARAMS = { alphaTest: 0 }; + CURRENT_SCENE.modelScene.renderOrder = 1; + + this._timeline.to(PARAMS, { + alphaTest: 1, + duration: Config.GSAP_ANIMATION_DURATION, + onUpdate: () => { + this._supportedPageKeys.slice(1).forEach((supportedPageKey) => { + const SCENE = this._world?.availablePageScenes[supportedPageKey]; + if ( + supportedPageKey === this._world?.mainSceneKey || + !SCENE?.modelScene + ) + return; + + SCENE?.modelScene?.traverse((child) => { + if ( + !(child instanceof Mesh) || + !(child.material instanceof Material) || + (nextSceneKey === supportedPageKey && + child.material.alphaTest === 0) || + (nextSceneKey !== supportedPageKey && + child.material.alphaTest === 1) + ) + return; + + child.material.alphaTest = + nextSceneKey === supportedPageKey + ? 1 - PARAMS.alphaTest + : PARAMS.alphaTest; + }); + }); + }, + }); + } + } + + /** Set the current scene depending to the current `Navigation` state */ + private _setScene() { + if ( + typeof this._experience.navigation?.currentRouteKey !== "string" || + this._supportedPageKeys.indexOf( + this._experience.navigation.currentRouteKey + ) === -1 + ) + throw new ErrorFactory( + new Error("Page not supported", { cause: WRONG_PARAM }) + ); + if (this._camera?.timeline.isActive()) this._camera.timeline.progress(1); + if (this._timeline.isActive()) this._timeline.progress(1); + + const CURRENT_SCENE = + this._world?.availablePageScenes[ + this._experience.navigation.currentRouteKey + ]; + + const MAIN_SCENE = + this._world?.availablePageScenes[this._world.mainSceneKey]; + + const SCREEN_POSITION = ( + this._world?.scene1?.pcScreen?.localToWorld(new Vector3()) ?? + new Vector3() + ).clone(); + + if ( + this._prevSceneKey && + (this._experience.navigation?.currentRouteKey === + this._world?.mainSceneKey || + CURRENT_SCENE === undefined) + ) { + this._triggerGlassTransitionEffect().add(() => { + this._camera?.switchCamera(0); + this._camera?.setCameraLookAt(SCREEN_POSITION); + this._camera?.updateCameraPosition( + MAIN_SCENE?.cameraPath.getPoint(0), + MAIN_SCENE?.modelScene?.position + ); + }, "-=" + this._glassEffectOptions.duration); + } + + if ( + this._experience.navigation.currentRouteKey !== + this._world?.mainSceneKey && + this._camera?.currentCameraIndex !== 1 + ) { + this._camera + ?.updateCameraPosition( + lerpPosition( + new Vector3(0, SCREEN_POSITION.y, 0), + SCREEN_POSITION, + 0.84 + ), + SCREEN_POSITION, + () => {} + ) + .add(() => { + this._triggerGlassTransitionEffect().add(() => { + this._camera?.switchCamera(1); + this._camera?.setCameraLookAt( + (CURRENT_SCENE?.modelScene?.position ?? new Vector3()).clone() + ); + }, "-=" + this._glassEffectOptions.duration); + }, "<87%"); + } + + this._changeProjectedScenesTransition( + this._experience.navigation.currentRouteKey ); - this.setScene(); + this._prevSceneKey = this._experience.navigation?.currentRouteKey; + } + + public construct() { + this._world = this._experience.world; + + this._initScenes(); + this._experience.navigation?.on(CHANGED, () => { - this.setScene(); + this._setScene(); }); this.emit(CONSTRUCTED, this); @@ -241,95 +464,9 @@ export default class WorldManager extends ExperienceBasedBlueprint { }; } - public setScene() { - if (this._camera?.timeline.isActive()) this._camera.timeline.progress(1); - if (this._timeline.isActive()) this._timeline.progress(1); - - const SCREEN_POSITION = ( - this._world?.scene1?.pcScreen?.localToWorld(new Vector3()) ?? - new Vector3() - ).clone(); - - if ( - this._experience.navigation?.currentRoute === "index" && - this._camera?.currentCameraIndex !== 0 - ) { - this._camera?.switchCamera(0); - - this._camera?.setCameraLookAt(SCREEN_POSITION); - } - - if (this._experience.navigation?.currentRoute !== "index") { - if (this._camera?.currentCameraIndex !== 1) { - this.cameraTransitionShaderPass = new ShaderPass({ - uniforms: { - tDiffuse: { value: null }, - uStrength: { value: 0 }, - uDisplacementMap: { - value: this._appResources.items["rocksAlphaMap"], - }, - }, - vertexShader: camTransitionVert, - fragmentShader: camTransitionFrag, - }); - - this._composer?.addPass( - "cameraTransitionShaderPass", - this.cameraTransitionShaderPass - ); - - this._camera - ?.updateCameraPosition( - lerpPosition( - new Vector3(0, SCREEN_POSITION.y, 0), - SCREEN_POSITION, - 0.84 - ), - SCREEN_POSITION, - () => {} - ) - .add(() => { - if (!this.cameraTransitionShaderPass?.material.uniforms.uStrength) - return; - this._timeline.to( - this.cameraTransitionShaderPass.material.uniforms.uStrength, - { - value: 0.175, - duration: 0.3, - ease: Power0.easeIn, - } - ); - }, "<87%") - .then(() => { - this._camera?.switchCamera(1); - - this._camera?.setCameraLookAt( - ( - this._world?.scene2?.modelScene?.position ?? new Vector3() - ).clone() - ); - - if (!this.cameraTransitionShaderPass?.material.uniforms.uStrength) - return; - - this._timeline - .to(this.cameraTransitionShaderPass.material.uniforms.uStrength, { - value: 0, - duration: 0.3, - ease: Power0.easeOut, - }) - .then(() => { - this.cameraTransitionShaderPass && - this._composer?.removePass("cameraTransitionShaderPass"); - }); - }); - } - } - } - public update() { if (this.autoCameraAnimation && !this.isGsapAnimating) { - this.cameraCurvePathProgress.current = GSAP.utils.interpolate( + this.cameraCurvePathProgress.current = gsap.utils.interpolate( this.cameraCurvePathProgress.current, this.cameraCurvePathProgress.target, this.cameraCurvePathProgress.ease @@ -349,12 +486,12 @@ export default class WorldManager extends ExperienceBasedBlueprint { this.backwardCurveAnimation = false; }, 1000); } - this.cameraCurvePathProgress.target = GSAP.utils.clamp( + this.cameraCurvePathProgress.target = gsap.utils.clamp( 0, 1, this.cameraCurvePathProgress.target ); - this.cameraCurvePathProgress.current = GSAP.utils.clamp( + this.cameraCurvePathProgress.current = gsap.utils.clamp( 0, 1, this.cameraCurvePathProgress.current diff --git a/src/pages/index.vue b/src/pages/index.vue index 333a810..4da4e47 100644 --- a/src/pages/index.vue +++ b/src/pages/index.vue @@ -4,9 +4,17 @@ - -
+ +
+ Page child 1 + Page child 2 + Page child 3 + +
+ + +
diff --git a/src/pages/index/contact.vue b/src/pages/index/contact.vue index fa2044b..3d3ee7a 100644 --- a/src/pages/index/contact.vue +++ b/src/pages/index/contact.vue @@ -1,5 +1,5 @@ diff --git a/src/pages/index/index.vue b/src/pages/index/index.vue index bf74ce9..f8be117 100644 --- a/src/pages/index/index.vue +++ b/src/pages/index/index.vue @@ -1,5 +1,5 @@ diff --git a/src/pages/index/skills.vue b/src/pages/index/skills.vue index 0eb8bca..6ea75c9 100644 --- a/src/pages/index/skills.vue +++ b/src/pages/index/skills.vue @@ -1,5 +1,5 @@