commit 4fb4f5a0cf71ff1ddd6757a573dce8eee4628788
parent 66b61f7ecf7883454fb0e500e3b8f68705383ccb
Author: Ryota HAYASHI <ryota.hayashi.2024@pim.gr.jp>
Date: Wed, 11 Jun 2025 11:04:05 +0900
update depandences and add somecodes
Diffstat:
12 files changed, 76 insertions(+), 14 deletions(-)
diff --git a/bun.lock b/bun.lock
@@ -5,9 +5,10 @@
"name": "seto-hp",
"dependencies": {
"@pixiv/three-vrm": "^3.4.1",
+ "@pixiv/three-vrm-animation": "^3.4.1",
"@react-three/drei": "^10.1.2",
"@react-three/fiber": "^9.1.2",
- "@types/three": "^0.176.0",
+ "@types/three": "^0.177.0",
"bootstrap": "^5.3.6",
"next": "15.3.3",
"react": "^19.0.0",
@@ -15,8 +16,8 @@
"three": "^0.177.0",
},
"devDependencies": {
- "@types/node": "^22.15.29",
- "@types/react": "^19",
+ "@types/node": "^24.0.0",
+ "@types/react": "^19.1.7",
"@types/react-dom": "^19",
"typescript": "^5",
},
@@ -95,6 +96,8 @@
"@pixiv/three-vrm": ["@pixiv/three-vrm@3.4.1", "", { "dependencies": { "@pixiv/three-vrm-core": "3.4.1", "@pixiv/three-vrm-materials-hdr-emissive-multiplier": "3.4.1", "@pixiv/three-vrm-materials-mtoon": "3.4.1", "@pixiv/three-vrm-materials-v0compat": "3.4.1", "@pixiv/three-vrm-node-constraint": "3.4.1", "@pixiv/three-vrm-springbone": "3.4.1" }, "peerDependencies": { "three": ">=0.137" } }, "sha512-VRj/I7ZZcrshMtSw+vs+pw5jZVpseLt/1cN0t6q6gwyRFKuziY0NCkivGOcFXvFDG/gmZABPVsY8Dudf7Pq7YQ=="],
+ "@pixiv/three-vrm-animation": ["@pixiv/three-vrm-animation@3.4.1", "", { "dependencies": { "@pixiv/three-vrm-core": "3.4.1", "@pixiv/types-vrmc-vrm-1.0": "3.4.1", "@pixiv/types-vrmc-vrm-animation-1.0": "3.4.1" }, "peerDependencies": { "three": ">=0.137" } }, "sha512-phBoHZv34HpuVbuTSw5WYei2kqSuNzllIEJCRH7H5+k/2kZD7YwJMmEHdOuinQ2humcchX5DY9wWPUZkmLQi4g=="],
+
"@pixiv/three-vrm-core": ["@pixiv/three-vrm-core@3.4.1", "", { "dependencies": { "@pixiv/types-vrm-0.0": "3.4.1", "@pixiv/types-vrmc-vrm-1.0": "3.4.1" }, "peerDependencies": { "three": ">=0.137" } }, "sha512-EiV26eSrUPuDssFvOK55cLgJDS87r+M1Sn/u3CFo3soeoOzgDz9h1ctV9bvN3UUDjg02FfaGzZTHPTKvkq4rFw=="],
"@pixiv/three-vrm-materials-hdr-emissive-multiplier": ["@pixiv/three-vrm-materials-hdr-emissive-multiplier@3.4.1", "", { "dependencies": { "@pixiv/types-vrmc-materials-hdr-emissive-multiplier-1.0": "3.4.1" }, "peerDependencies": { "three": ">=0.137" } }, "sha512-sy/a0rx0cuppvsCNpiaGAqluAz4gVdcp7cDhg55VP4N7jDtmSM4EZz8dikinnIUmvLXiKg/lzG4K7bMWRiKIXQ=="],
@@ -121,6 +124,8 @@
"@pixiv/types-vrmc-vrm-1.0": ["@pixiv/types-vrmc-vrm-1.0@3.4.1", "", {}, "sha512-nKc0vyi76YuQizpUtIuhnjuv3Z15ylhoHiUpBpaWF2kbt0v0ozAAKYNCof6kW0cngA52ERCbC3E6xlvdwYlhMA=="],
+ "@pixiv/types-vrmc-vrm-animation-1.0": ["@pixiv/types-vrmc-vrm-animation-1.0@3.4.1", "", { "dependencies": { "@pixiv/types-vrmc-vrm-1.0": "2.0.3" } }, "sha512-EBdK0xVAR6K3d5OfkgSM92MH5Nt3+qM6fIYpfbUhcDcNTsAQSyhjxDmQCI0mO2rx49OcEEln8kzqK97TFTeSyg=="],
+
"@popperjs/core": ["@popperjs/core@2.11.8", "", {}, "sha512-P1st0aksCrn9sGZhp8GMYwBnQsbvAWsZAX44oXNNvLHGqAOcoVxmjZiohstwQ7SqKnbR47akdNi+uleWD8+g6A=="],
"@react-three/drei": ["@react-three/drei@10.1.2", "", { "dependencies": { "@babel/runtime": "^7.26.0", "@mediapipe/tasks-vision": "0.10.17", "@monogrid/gainmap-js": "^3.0.6", "@use-gesture/react": "^10.3.1", "camera-controls": "^2.9.0", "cross-env": "^7.0.3", "detect-gpu": "^5.0.56", "glsl-noise": "^0.0.0", "hls.js": "^1.5.17", "maath": "^0.10.8", "meshline": "^3.3.1", "stats-gl": "^2.2.8", "stats.js": "^0.17.0", "suspend-react": "^0.1.3", "three-mesh-bvh": "^0.8.3", "three-stdlib": "^2.35.6", "troika-three-text": "^0.52.4", "tunnel-rat": "^0.1.2", "use-sync-external-store": "^1.4.0", "utility-types": "^3.11.0", "zustand": "^5.0.1" }, "peerDependencies": { "@react-three/fiber": "^9.0.0", "react": "^19", "react-dom": "^19", "three": ">=0.159" }, "optionalPeers": ["react-dom"] }, "sha512-CCcLAqZEvYiUErOcJgGzovY3RH6KgdrqD4ubeAx1nyGbSPLnKR9a8ynYbPdtZhIyiWqGc07z+RYQzpaOfN4ZIA=="],
@@ -135,11 +140,11 @@
"@types/draco3d": ["@types/draco3d@1.4.10", "", {}, "sha512-AX22jp8Y7wwaBgAixaSvkoG4M/+PlAcm3Qs4OW8yT9DM4xUpWKeFhLueTAyZF39pviAdcDdeJoACapiAceqNcw=="],
- "@types/node": ["@types/node@22.15.29", "", { "dependencies": { "undici-types": "~6.21.0" } }, "sha512-LNdjOkUDlU1RZb8e1kOIUpN1qQUlzGkEtbVNo53vbrwDg5om6oduhm4SiUaPW5ASTXhAiP0jInWG8Qx9fVlOeQ=="],
+ "@types/node": ["@types/node@24.0.0", "", { "dependencies": { "undici-types": "~7.8.0" } }, "sha512-yZQa2zm87aRVcqDyH5+4Hv9KYgSdgwX1rFnGvpbzMaC7YAljmhBET93TPiTd3ObwTL+gSpIzPKg5BqVxdCvxKg=="],
"@types/offscreencanvas": ["@types/offscreencanvas@2019.7.3", "", {}, "sha512-ieXiYmgSRXUDeOntE1InxjWyvEelZGP63M+cGuquuRLuIKKT1osnkXjxev9B7d1nXSug5vpunx+gNlbVxMlC9A=="],
- "@types/react": ["@types/react@19.1.6", "", { "dependencies": { "csstype": "^3.0.2" } }, "sha512-JeG0rEWak0N6Itr6QUx+X60uQmN+5t3j9r/OVDtWzFXKaj6kD1BwJzOksD0FF6iWxZlbE1kB0q9vtnU2ekqa1Q=="],
+ "@types/react": ["@types/react@19.1.7", "", { "dependencies": { "csstype": "^3.0.2" } }, "sha512-BnsPLV43ddr05N71gaGzyZ5hzkCmGwhMvYc8zmvI8Ci1bRkkDSzDDVfAXfN2tk748OwI7ediiPX6PfT9p0QGVg=="],
"@types/react-dom": ["@types/react-dom@19.1.5", "", { "peerDependencies": { "@types/react": "^19.0.0" } }, "sha512-CMCjrWucUBZvohgZxkjd6S9h0nZxXjzus6yDfUb+xLxYM7VvjKNH1tQrE9GWLql1XoOP4/Ds3bwFqShHUYraGg=="],
@@ -147,7 +152,7 @@
"@types/stats.js": ["@types/stats.js@0.17.4", "", {}, "sha512-jIBvWWShCvlBqBNIZt0KAshWpvSjhkwkEu4ZUcASoAvhmrgAUI2t1dXrjSL4xXVLB4FznPrIsX3nKXFl/Dt4vA=="],
- "@types/three": ["@types/three@0.176.0", "", { "dependencies": { "@dimforge/rapier3d-compat": "^0.12.0", "@tweenjs/tween.js": "~23.1.3", "@types/stats.js": "*", "@types/webxr": "*", "@webgpu/types": "*", "fflate": "~0.8.2", "meshoptimizer": "~0.18.1" } }, "sha512-FwfPXxCqOtP7EdYMagCFePNKoG1AGBDUEVKtluv2BTVRpSt7b+X27xNsirPCTCqY1pGYsPUzaM3jgWP7dXSxlw=="],
+ "@types/three": ["@types/three@0.177.0", "", { "dependencies": { "@dimforge/rapier3d-compat": "~0.12.0", "@tweenjs/tween.js": "~23.1.3", "@types/stats.js": "*", "@types/webxr": "*", "@webgpu/types": "*", "fflate": "~0.8.2", "meshoptimizer": "~0.18.1" } }, "sha512-/ZAkn4OLUijKQySNci47lFO+4JLE1TihEjsGWPUT+4jWqxtwOPPEwJV1C3k5MEx0mcBPCdkFjzRzDOnHEI1R+A=="],
"@types/webxr": ["@types/webxr@0.5.22", "", {}, "sha512-Vr6Stjv5jPRqH690f5I5GLjVk8GSsoQSYJ2FVd/3jJF7KaqfwPi3ehfBS96mlQ2kPCwZaX6U0rG2+NGHBKkA/A=="],
@@ -285,7 +290,7 @@
"typescript": ["typescript@5.8.3", "", { "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" } }, "sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ=="],
- "undici-types": ["undici-types@6.21.0", "", {}, "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ=="],
+ "undici-types": ["undici-types@7.8.0", "", {}, "sha512-9UJ2xGDvQ43tYyVMpuHlsgApydB8ZKfVYTsLDhXkFL/6gfkp+U8xTGdh8pMJv1SpZna0zxG1DwsKZsreLbXBxw=="],
"use-sync-external-store": ["use-sync-external-store@1.5.0", "", { "peerDependencies": { "react": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" } }, "sha512-Rb46I4cGGVBmjamjphe8L/UnvJD+uPPtTkNvX5mZgqdbavhI4EbgIWJiIHXJ8bc/i9EQGPRh4DwEURJ552Do0A=="],
@@ -299,8 +304,12 @@
"zustand": ["zustand@5.0.5", "", { "peerDependencies": { "@types/react": ">=18.0.0", "immer": ">=9.0.6", "react": ">=18.0.0", "use-sync-external-store": ">=1.2.0" }, "optionalPeers": ["@types/react", "immer", "react", "use-sync-external-store"] }, "sha512-mILtRfKW9xM47hqxGIxCv12gXusoY/xTSHBYApXozR0HmQv299whhBeeAcRy+KrPPybzosvJBCOmVjq6x12fCg=="],
+ "@pixiv/types-vrmc-vrm-animation-1.0/@pixiv/types-vrmc-vrm-1.0": ["@pixiv/types-vrmc-vrm-1.0@2.0.3", "", {}, "sha512-RMP34Bk1qLFQv/CRB1Zqvn2qMFfWQfP2Hms5QrrfoBsW9XroZdEe0zPLNbGmUPYh4F7VtBb+B7+RCuymRtpehA=="],
+
"react-dom/scheduler": ["scheduler@0.26.0", "", {}, "sha512-NlHwttCI/l5gCPR3D1nNXtWABUmBwvZpEQiD4IXSbIDq8BzLIK/7Ir5gTFSGZDUu37K5cMNp0hFtzO38sC7gWA=="],
+ "stats-gl/@types/three": ["@types/three@0.176.0", "", { "dependencies": { "@dimforge/rapier3d-compat": "^0.12.0", "@tweenjs/tween.js": "~23.1.3", "@types/stats.js": "*", "@types/webxr": "*", "@webgpu/types": "*", "fflate": "~0.8.2", "meshoptimizer": "~0.18.1" } }, "sha512-FwfPXxCqOtP7EdYMagCFePNKoG1AGBDUEVKtluv2BTVRpSt7b+X27xNsirPCTCqY1pGYsPUzaM3jgWP7dXSxlw=="],
+
"stats-gl/three": ["three@0.170.0", "", {}, "sha512-FQK+LEpYc0fBD+J8g6oSEyyNzjp+Q7Ks1C568WWaoMRLW+TkNNWmenWeGgJjV105Gd+p/2ql1ZcjYvNiPZBhuQ=="],
"three-stdlib/fflate": ["fflate@0.6.10", "", {}, "sha512-IQrh3lEPM93wVCEczc9SaAOvkmcoQn/G8Bo1e8ZPlY3X3bnAxWaBdvTdvM1hP62iZp0BXWDy4vTAy4fF0+Dlpg=="],
diff --git a/package.json b/package.json
@@ -10,9 +10,10 @@
},
"dependencies": {
"@pixiv/three-vrm": "^3.4.1",
+ "@pixiv/three-vrm-animation": "^3.4.1",
"@react-three/drei": "^10.1.2",
"@react-three/fiber": "^9.1.2",
- "@types/three": "^0.176.0",
+ "@types/three": "^0.177.0",
"bootstrap": "^5.3.6",
"next": "15.3.3",
"react": "^19.0.0",
@@ -21,8 +22,8 @@
},
"devDependencies": {
"typescript": "^5",
- "@types/node": "^22.15.29",
- "@types/react": "^19",
+ "@types/node": "^24.0.0",
+ "@types/react": "^19.1.7",
"@types/react-dom": "^19"
}
}
diff --git a/public/animations/VRMA_01.vrma b/public/animations/VRMA_01.vrma
Binary files differ.
diff --git a/public/animations/VRMA_02.vrma b/public/animations/VRMA_02.vrma
Binary files differ.
diff --git a/public/animations/VRMA_03.vrma b/public/animations/VRMA_03.vrma
Binary files differ.
diff --git a/public/animations/VRMA_04.vrma b/public/animations/VRMA_04.vrma
Binary files differ.
diff --git a/public/animations/VRMA_05.vrma b/public/animations/VRMA_05.vrma
Binary files differ.
diff --git a/public/animations/VRMA_06.vrma b/public/animations/VRMA_06.vrma
Binary files differ.
diff --git a/public/animations/VRMA_07.vrma b/public/animations/VRMA_07.vrma
Binary files differ.
diff --git a/src/app/components/Model.tsx b/src/app/components/Model.tsx
@@ -3,6 +3,8 @@ import { FC, useState, useEffect } from "react"
import { Html} from "@react-three/drei"
import { GLTFLoader, GLTF } from "three/examples/jsm/loaders/GLTFLoader"
import { VRMLoaderPlugin } from "@pixiv/three-vrm"
+import { VRMAnimationLoaderPlugin } from "@pixiv/three-vrm-animation"
+
const Model: FC = () => {
@@ -14,7 +16,10 @@ const Model: FC = () => {
const loader = new GLTFLoader()
loader.register((parser) => {
return new VRMLoaderPlugin(parser)
- })
+ });
+ loader.register((parser) => {
+ return new VRMAnimationLoaderPlugin(parser)
+ });
loader.load(
"/models/Setok.vrm",
@@ -33,6 +38,54 @@ const Model: FC = () => {
console.log(error)
}
)
+ let currentVrm: any = undefined;
+ let currentVrmAnimation: any = undefined;
+ let currentMixer:any = undefined;
+ function load(url: string) {
+ loader.load(
+ url,
+ // ロード時に呼ばれる
+ (gltf) => {
+ tryInitVRM(gltf);
+ tryInitVRMA(gltf);
+ },
+ // プログレス時に呼ばれる
+ (progress) => console.log(
+ "Loading model...",
+ 100.0 * (progress.loaded / progress.total), "%"
+ ),
+ // エラー時に呼ばれる
+ (error) => console.error(error)
+ );
+ }
+ function tryInitVRM(gltf: any) {
+ const vrm = gltf.userData.vrm;
+ if ( vrm == null ) {
+ return;
+ }
+ currentVrm = vrm;
+ scene.add(vrm.scene);
+ initAnimationClip();
+ }
+
+ // VRMAの読み込み
+ function tryInitVRMA(gltf: any) {
+ const vrmAnimations = gltf.userData.vrmAnimations;
+ if (vrmAnimations == null) {
+ return;
+ }
+ currentVrmAnimation = vrmAnimations[0] ?? null;
+ initAnimationClip();
+ }
+ function initAnimationClip() {
+ if (currentVrm && currentVrmAnimation) {
+ currentMixer = new THREE.AnimationMixer(currentVrm.scene);
+ const clip = createVRMAnimationClip(currentVrmAnimation, currentVrm);
+ currentMixer.clipAction(clip).play();
+ }
+ }
+ // https://note.com/npaka/n/nf632f283f89a
+ load("/animations/VRMA_01.vrma")
}
}, [gltf])
diff --git a/src/app/components/avatar.tsx b/src/app/components/avatar.tsx
@@ -25,9 +25,9 @@ export default function Avatar() {
camera={{ position:[0,5,-5]}}
>
<PerspectiveCamera makeDefault position={[0, 2, -2]} />
- <directionalLight position={[1,20,-1]} color={"0xffffff"} />
+ <directionalLight position={[0,10,-5]} color={"0xffffff"} />
<Model />
- <color attach="background" args={["#000000"]} />
+ <color attach="background" args={["#ff00ff"]} />
<gridHelper/>
<OrbitControls
enableZoom={false}
diff --git a/src/app/page.tsx b/src/app/page.tsx
@@ -1,4 +1,3 @@
-import Image from "next/image";
import Avatar from "./components/avatar";
export default function Home() {