mirror of
https://github.com/exogen/t2-model-skinner.git
synced 2026-01-19 19:24:44 +00:00
Add slow mode for model & texture animations
This commit is contained in:
parent
b41d6b1841
commit
9ee12bbfd2
File diff suppressed because one or more lines are too long
|
|
@ -1 +1 @@
|
|||
self.__BUILD_MANIFEST={__rewrites:{afterFiles:[],beforeFiles:[],fallback:[]},"/":["static/chunks/78e521c3-3739cc27b3254d35.js","static/chunks/95b64a6e-a0ff77d56afeed48.js","static/chunks/31664189-69d752d1129a4958.js","static/chunks/545f34e4-3e66c340444ca8b2.js","static/chunks/1bfc9850-b4ceccea4b74407c.js","static/chunks/d7eeaac4-d223ea230e13423c.js","static/chunks/f580fadb-2911e2fbf64aae5a.js","static/chunks/50-a8a6240a880bd3e0.js","static/chunks/pages/index-357b9e2337384293.js"],"/_error":["static/chunks/pages/_error-54b9fcf45cb5bc62.js"],sortedPages:["/","/_app","/_error"]},self.__BUILD_MANIFEST_CB&&self.__BUILD_MANIFEST_CB();
|
||||
self.__BUILD_MANIFEST={__rewrites:{afterFiles:[],beforeFiles:[],fallback:[]},"/":["static/chunks/78e521c3-3739cc27b3254d35.js","static/chunks/95b64a6e-a0ff77d56afeed48.js","static/chunks/31664189-69d752d1129a4958.js","static/chunks/545f34e4-3e66c340444ca8b2.js","static/chunks/1bfc9850-b4ceccea4b74407c.js","static/chunks/d7eeaac4-d223ea230e13423c.js","static/chunks/f580fadb-2911e2fbf64aae5a.js","static/chunks/50-a8a6240a880bd3e0.js","static/chunks/pages/index-24e06461362afe89.js"],"/_error":["static/chunks/pages/_error-54b9fcf45cb5bc62.js"],sortedPages:["/","/_app","/_error"]},self.__BUILD_MANIFEST_CB&&self.__BUILD_MANIFEST_CB();
|
||||
2
docs/_next/static/chunks/250.10c119307e239c98.js
Normal file
2
docs/_next/static/chunks/250.10c119307e239c98.js
Normal file
|
|
@ -0,0 +1,2 @@
|
|||
"use strict";(self.webpackChunk_N_E=self.webpackChunk_N_E||[]).push([[250],{9250:function(e,t,a){a.r(t),a.d(t,{default:function(){return ModelViewer}});var l=a(5893),o=a(7294);a(5848);var d=a(485);function ModelViewerKeyedByModel(e){let{modelUrl:t,environmentImageUrl:a,showEnvironment:i=!1,exposure:r=1,animationName:n,animationPaused:u=!1,timeScale:s=1,cameraOrbit:f,cameraTarget:c,fieldOfView:m,children:v}=e,[h,w]=(0,o.useState)(null),[y,g]=(0,o.useState)(!1),x=(0,o.useMemo)(()=>h&&y&&h.model?{modelViewer:h,model:h.model,isLoaded:y}:null,[h,y]);return(0,o.useEffect)(()=>{h&&(h.timeScale=s)},[h,s]),(0,o.useEffect)(()=>{if(!h)return;let e=!1,handleLoad=()=>{e||g(!0)};return h.addEventListener("load",handleLoad),()=>{e=!0,h.removeEventListener("load",handleLoad)}},[h,t]),(0,o.useEffect)(()=>{h&&h.loaded&&g(!0)},[h,t]),(0,o.useEffect)(()=>{h&&y&&(u?h.pause():h.play())},[h,y,u]),(0,o.useEffect)(()=>{h&&y&&m&&h.setAttribute("field-of-view",m)},[h,y,m]),(0,l.jsxs)(l.Fragment,{children:[(0,l.jsx)("model-viewer",{ref:w,alt:"Tribes 2 Model",src:t,"camera-controls":!0,"camera-orbit":f,"max-camera-orbit":a&&i?"auto 90deg auto":void 0,"camera-target":c,"min-field-of-view":"10deg","max-field-of-view":"45deg","animation-name":null!=n?n:void 0,autoplay:n?"true":"false","touch-action":"pan-y",exposure:r,"environment-image":null!=a?a:void 0,"skybox-image":a&&i?a:void 0,"skybox-height":"1.5m","shadow-intensity":a&&i?1:0,style:{width:"100%",height:"100%"}}),y?(0,l.jsx)(d.K.Provider,{value:x,children:v}):null]})}function ModelViewer(e){return(0,l.jsx)(ModelViewerKeyedByModel,{...e},e.modelUrl)}}}]);
|
||||
//# sourceMappingURL=250.10c119307e239c98.js.map
|
||||
1
docs/_next/static/chunks/250.10c119307e239c98.js.map
Normal file
1
docs/_next/static/chunks/250.10c119307e239c98.js.map
Normal file
File diff suppressed because one or more lines are too long
|
|
@ -1,2 +0,0 @@
|
|||
"use strict";(self.webpackChunk_N_E=self.webpackChunk_N_E||[]).push([[250],{9250:function(e,t,a){a.r(t),a.d(t,{default:function(){return ModelViewer}});var l=a(5893),o=a(7294);a(5848);var d=a(485);function ModelViewerKeyedByModel(e){let{modelUrl:t,environmentImageUrl:a,showEnvironment:i=!1,exposure:r=1,animationName:n,animationPaused:u=!1,cameraOrbit:s,cameraTarget:f,fieldOfView:c,children:m}=e,[v,h]=(0,o.useState)(null),[w,y]=(0,o.useState)(!1),g=(0,o.useMemo)(()=>v&&w&&v.model?{modelViewer:v,model:v.model,isLoaded:w}:null,[v,w]);return(0,o.useEffect)(()=>{v&&(v.timeScale=.5)},[v]),(0,o.useEffect)(()=>{if(!v)return;let e=!1,handleLoad=()=>{e||y(!0)};return v.addEventListener("load",handleLoad),()=>{e=!0,v.removeEventListener("load",handleLoad)}},[v,t]),(0,o.useEffect)(()=>{v&&v.loaded&&y(!0)},[v,t]),(0,o.useEffect)(()=>{v&&w&&(u?v.pause():v.play())},[v,w,u]),(0,o.useEffect)(()=>{v&&w&&c&&v.setAttribute("field-of-view",c)},[v,w,c]),(0,l.jsxs)(l.Fragment,{children:[(0,l.jsx)("model-viewer",{ref:h,alt:"Tribes 2 Model",src:t,"camera-controls":!0,"camera-orbit":s,"max-camera-orbit":a&&i?"auto 90deg auto":void 0,"camera-target":f,"min-field-of-view":"10deg","max-field-of-view":"45deg","animation-name":null!=n?n:void 0,autoplay:n?"true":"false","touch-action":"pan-y",exposure:r,"environment-image":null!=a?a:void 0,"skybox-image":a&&i?a:void 0,"skybox-height":"1.5m","shadow-intensity":a&&i?1:0,style:{width:"100%",height:"100%"}}),w?(0,l.jsx)(d.K.Provider,{value:g,children:m}):null]})}function ModelViewer(e){return(0,l.jsx)(ModelViewerKeyedByModel,{...e},e.modelUrl)}}}]);
|
||||
//# sourceMappingURL=250.a985869c089b2fd3.js.map
|
||||
File diff suppressed because one or more lines are too long
2
docs/_next/static/chunks/pages/index-24e06461362afe89.js
Normal file
2
docs/_next/static/chunks/pages/index-24e06461362afe89.js
Normal file
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
|
|
@ -1,2 +1,2 @@
|
|||
!function(){"use strict";var e,r,_,t,n,i,u,c={},o={};function __webpack_require__(e){var r=o[e];if(void 0!==r)return r.exports;var _=o[e]={exports:{}},t=!0;try{c[e].call(_.exports,_,_.exports,__webpack_require__),t=!1}finally{t&&delete o[e]}return _.exports}__webpack_require__.m=c,e=[],__webpack_require__.O=function(r,_,t,n){if(_){n=n||0;for(var i=e.length;i>0&&e[i-1][2]>n;i--)e[i]=e[i-1];e[i]=[_,t,n];return}for(var u=1/0,i=0;i<e.length;i++){for(var _=e[i][0],t=e[i][1],n=e[i][2],c=!0,o=0;o<_.length;o++)u>=n&&Object.keys(__webpack_require__.O).every(function(e){return __webpack_require__.O[e](_[o])})?_.splice(o--,1):(c=!1,n<u&&(u=n));if(c){e.splice(i--,1);var a=t()}}return a},__webpack_require__.n=function(e){var r=e&&e.__esModule?function(){return e.default}:function(){return e};return __webpack_require__.d(r,{a:r}),r},__webpack_require__.d=function(e,r){for(var _ in r)__webpack_require__.o(r,_)&&!__webpack_require__.o(e,_)&&Object.defineProperty(e,_,{enumerable:!0,get:r[_]})},__webpack_require__.f={},__webpack_require__.e=function(e){return Promise.all(Object.keys(__webpack_require__.f).reduce(function(r,_){return __webpack_require__.f[_](e,r),r},[]))},__webpack_require__.u=function(e){return"static/chunks/"+(737===e?"fb7d5399":e)+"."+({250:"a985869c089b2fd3",354:"c8f476539d33c65e",737:"bc4a70b34221e8c8",767:"5a1b83173dac696e",848:"fc0fe21cdc2e6431"})[e]+".js"},__webpack_require__.miniCssF=function(e){return"static/css/8f9c54e3d59c6be4.css"},__webpack_require__.g=function(){if("object"==typeof globalThis)return globalThis;try{return this||Function("return this")()}catch(e){if("object"==typeof window)return window}}(),__webpack_require__.o=function(e,r){return Object.prototype.hasOwnProperty.call(e,r)},r={},_="_N_E:",__webpack_require__.l=function(e,t,n,i){if(r[e]){r[e].push(t);return}if(void 0!==n)for(var u,c,o=document.getElementsByTagName("script"),a=0;a<o.length;a++){var p=o[a];if(p.getAttribute("src")==e||p.getAttribute("data-webpack")==_+n){u=p;break}}u||(c=!0,(u=document.createElement("script")).charset="utf-8",u.timeout=120,__webpack_require__.nc&&u.setAttribute("nonce",__webpack_require__.nc),u.setAttribute("data-webpack",_+n),u.src=__webpack_require__.tu(e)),r[e]=[t];var onScriptComplete=function(_,t){u.onerror=u.onload=null,clearTimeout(b);var n=r[e];if(delete r[e],u.parentNode&&u.parentNode.removeChild(u),n&&n.forEach(function(e){return e(t)}),_)return _(t)},b=setTimeout(onScriptComplete.bind(null,void 0,{type:"timeout",target:u}),12e4);u.onerror=onScriptComplete.bind(null,u.onerror),u.onload=onScriptComplete.bind(null,u.onload),c&&document.head.appendChild(u)},__webpack_require__.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},__webpack_require__.tt=function(){return void 0===t&&(t={createScriptURL:function(e){return e}},"undefined"!=typeof trustedTypes&&trustedTypes.createPolicy&&(t=trustedTypes.createPolicy("nextjs#bundler",t))),t},__webpack_require__.tu=function(e){return __webpack_require__.tt().createScriptURL(e)},__webpack_require__.p="/t2-model-skinner/_next/",n={272:0},__webpack_require__.f.j=function(e,r){var _=__webpack_require__.o(n,e)?n[e]:void 0;if(0!==_){if(_)r.push(_[2]);else if(272!=e){var t=new Promise(function(r,t){_=n[e]=[r,t]});r.push(_[2]=t);var i=__webpack_require__.p+__webpack_require__.u(e),u=Error();__webpack_require__.l(i,function(r){if(__webpack_require__.o(n,e)&&(0!==(_=n[e])&&(n[e]=void 0),_)){var t=r&&("load"===r.type?"missing":r.type),i=r&&r.target&&r.target.src;u.message="Loading chunk "+e+" failed.\n("+t+": "+i+")",u.name="ChunkLoadError",u.type=t,u.request=i,_[1](u)}},"chunk-"+e,e)}else n[e]=0}},__webpack_require__.O.j=function(e){return 0===n[e]},i=function(e,r){var _,t,i=r[0],u=r[1],c=r[2],o=0;if(i.some(function(e){return 0!==n[e]})){for(_ in u)__webpack_require__.o(u,_)&&(__webpack_require__.m[_]=u[_]);if(c)var a=c(__webpack_require__)}for(e&&e(r);o<i.length;o++)t=i[o],__webpack_require__.o(n,t)&&n[t]&&n[t][0](),n[t]=0;return __webpack_require__.O(a)},(u=self.webpackChunk_N_E=self.webpackChunk_N_E||[]).forEach(i.bind(null,0)),u.push=i.bind(null,u.push.bind(u))}();
|
||||
//# sourceMappingURL=webpack-cbee82fe57b0dc2e.js.map
|
||||
!function(){"use strict";var e,r,_,t,n,i,u,c={},o={};function __webpack_require__(e){var r=o[e];if(void 0!==r)return r.exports;var _=o[e]={exports:{}},t=!0;try{c[e].call(_.exports,_,_.exports,__webpack_require__),t=!1}finally{t&&delete o[e]}return _.exports}__webpack_require__.m=c,e=[],__webpack_require__.O=function(r,_,t,n){if(_){n=n||0;for(var i=e.length;i>0&&e[i-1][2]>n;i--)e[i]=e[i-1];e[i]=[_,t,n];return}for(var u=1/0,i=0;i<e.length;i++){for(var _=e[i][0],t=e[i][1],n=e[i][2],c=!0,o=0;o<_.length;o++)u>=n&&Object.keys(__webpack_require__.O).every(function(e){return __webpack_require__.O[e](_[o])})?_.splice(o--,1):(c=!1,n<u&&(u=n));if(c){e.splice(i--,1);var a=t()}}return a},__webpack_require__.n=function(e){var r=e&&e.__esModule?function(){return e.default}:function(){return e};return __webpack_require__.d(r,{a:r}),r},__webpack_require__.d=function(e,r){for(var _ in r)__webpack_require__.o(r,_)&&!__webpack_require__.o(e,_)&&Object.defineProperty(e,_,{enumerable:!0,get:r[_]})},__webpack_require__.f={},__webpack_require__.e=function(e){return Promise.all(Object.keys(__webpack_require__.f).reduce(function(r,_){return __webpack_require__.f[_](e,r),r},[]))},__webpack_require__.u=function(e){return"static/chunks/"+(737===e?"fb7d5399":e)+"."+({250:"10c119307e239c98",354:"c8f476539d33c65e",737:"bc4a70b34221e8c8",767:"5a1b83173dac696e",848:"fc0fe21cdc2e6431"})[e]+".js"},__webpack_require__.miniCssF=function(e){return"static/css/964f7cf6b1575022.css"},__webpack_require__.g=function(){if("object"==typeof globalThis)return globalThis;try{return this||Function("return this")()}catch(e){if("object"==typeof window)return window}}(),__webpack_require__.o=function(e,r){return Object.prototype.hasOwnProperty.call(e,r)},r={},_="_N_E:",__webpack_require__.l=function(e,t,n,i){if(r[e]){r[e].push(t);return}if(void 0!==n)for(var u,c,o=document.getElementsByTagName("script"),a=0;a<o.length;a++){var p=o[a];if(p.getAttribute("src")==e||p.getAttribute("data-webpack")==_+n){u=p;break}}u||(c=!0,(u=document.createElement("script")).charset="utf-8",u.timeout=120,__webpack_require__.nc&&u.setAttribute("nonce",__webpack_require__.nc),u.setAttribute("data-webpack",_+n),u.src=__webpack_require__.tu(e)),r[e]=[t];var onScriptComplete=function(_,t){u.onerror=u.onload=null,clearTimeout(b);var n=r[e];if(delete r[e],u.parentNode&&u.parentNode.removeChild(u),n&&n.forEach(function(e){return e(t)}),_)return _(t)},b=setTimeout(onScriptComplete.bind(null,void 0,{type:"timeout",target:u}),12e4);u.onerror=onScriptComplete.bind(null,u.onerror),u.onload=onScriptComplete.bind(null,u.onload),c&&document.head.appendChild(u)},__webpack_require__.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},__webpack_require__.tt=function(){return void 0===t&&(t={createScriptURL:function(e){return e}},"undefined"!=typeof trustedTypes&&trustedTypes.createPolicy&&(t=trustedTypes.createPolicy("nextjs#bundler",t))),t},__webpack_require__.tu=function(e){return __webpack_require__.tt().createScriptURL(e)},__webpack_require__.p="/t2-model-skinner/_next/",n={272:0},__webpack_require__.f.j=function(e,r){var _=__webpack_require__.o(n,e)?n[e]:void 0;if(0!==_){if(_)r.push(_[2]);else if(272!=e){var t=new Promise(function(r,t){_=n[e]=[r,t]});r.push(_[2]=t);var i=__webpack_require__.p+__webpack_require__.u(e),u=Error();__webpack_require__.l(i,function(r){if(__webpack_require__.o(n,e)&&(0!==(_=n[e])&&(n[e]=void 0),_)){var t=r&&("load"===r.type?"missing":r.type),i=r&&r.target&&r.target.src;u.message="Loading chunk "+e+" failed.\n("+t+": "+i+")",u.name="ChunkLoadError",u.type=t,u.request=i,_[1](u)}},"chunk-"+e,e)}else n[e]=0}},__webpack_require__.O.j=function(e){return 0===n[e]},i=function(e,r){var _,t,i=r[0],u=r[1],c=r[2],o=0;if(i.some(function(e){return 0!==n[e]})){for(_ in u)__webpack_require__.o(u,_)&&(__webpack_require__.m[_]=u[_]);if(c)var a=c(__webpack_require__)}for(e&&e(r);o<i.length;o++)t=i[o],__webpack_require__.o(n,t)&&n[t]&&n[t][0](),n[t]=0;return __webpack_require__.O(a)},(u=self.webpackChunk_N_E=self.webpackChunk_N_E||[]).forEach(i.bind(null,0)),u.push=i.bind(null,u.push.bind(u))}();
|
||||
//# sourceMappingURL=webpack-c24f5de5b7b1f01e.js.map
|
||||
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
2
docs/_next/static/css/964f7cf6b1575022.css
Normal file
2
docs/_next/static/css/964f7cf6b1575022.css
Normal file
File diff suppressed because one or more lines are too long
1
docs/_next/static/css/964f7cf6b1575022.css.map
Normal file
1
docs/_next/static/css/964f7cf6b1575022.css.map
Normal file
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
|
|
@ -15,6 +15,8 @@ export default function AnimationSelector() {
|
|||
setSelectedAnimation,
|
||||
animationPaused,
|
||||
setAnimationPaused,
|
||||
slowModeEnabled,
|
||||
setSlowModeEnabled,
|
||||
} = useWarrior();
|
||||
|
||||
const animationList = useMemo(
|
||||
|
|
@ -27,7 +29,20 @@ export default function AnimationSelector() {
|
|||
|
||||
return (
|
||||
<>
|
||||
<label>Animation</label>
|
||||
<div className="LabelWithControls">
|
||||
<label>Animation</label>
|
||||
<div className="AnimationSpeed">
|
||||
<input
|
||||
type="checkbox"
|
||||
id="SlowDownCheckbox"
|
||||
checked={slowModeEnabled}
|
||||
onChange={(event) => {
|
||||
setSlowModeEnabled(event.target.checked);
|
||||
}}
|
||||
/>{" "}
|
||||
<label htmlFor="SlowDownCheckbox">Slow?</label>
|
||||
</div>
|
||||
</div>
|
||||
<div className="Buttons">
|
||||
<select
|
||||
value={selectedAnimation ?? ""}
|
||||
|
|
|
|||
|
|
@ -3,6 +3,7 @@ import type { ModelViewerElement } from "@google/model-viewer";
|
|||
import useSettings from "./useSettings";
|
||||
import useSkin from "./useSkin";
|
||||
import useModelViewer from "./useModelViewer";
|
||||
import useWarrior from "./useWarrior";
|
||||
|
||||
// const secondaryMaterialTextures: Record<string, string[]> = {
|
||||
// disc: ["textures/discshield2"],
|
||||
|
|
@ -52,6 +53,7 @@ function useTexture({
|
|||
}) {
|
||||
const { modelViewer } = useModelViewer();
|
||||
const { basePath } = useSettings();
|
||||
const { slowModeEnabled } = useWarrior();
|
||||
|
||||
useEffect(() => {
|
||||
let stale = false;
|
||||
|
|
@ -81,6 +83,10 @@ function useTexture({
|
|||
let textureUrls =
|
||||
imageUrl ?? new Array(frameCount).fill(`${basePath}/white.png`);
|
||||
|
||||
if (textureUrls.some((url) => !url)) {
|
||||
return;
|
||||
}
|
||||
|
||||
switch (textureType) {
|
||||
case "baseColorTexture":
|
||||
if (baseColorFactor) {
|
||||
|
|
@ -103,6 +109,7 @@ function useTexture({
|
|||
textureUrls = new Array(frameCount).fill(`${basePath}/green.png`);
|
||||
}
|
||||
}
|
||||
|
||||
const textures = await Promise.all(
|
||||
textureUrls.map((textureUrl) => modelViewer.createTexture(textureUrl))
|
||||
);
|
||||
|
|
@ -117,7 +124,7 @@ function useTexture({
|
|||
material.emissiveTexture.setTexture(texture);
|
||||
}
|
||||
if (isMasterTexture) {
|
||||
frameInfo.frameProgress += 1;
|
||||
frameInfo.frameProgress += slowModeEnabled ? 0.05 : 1;
|
||||
}
|
||||
if (frameCount > 1) {
|
||||
const frameTiming = frameTimings?.[frameInfo.frameIndex] ?? 1;
|
||||
|
|
@ -150,6 +157,7 @@ function useTexture({
|
|||
textureType,
|
||||
imageUrl,
|
||||
frameRef,
|
||||
slowModeEnabled,
|
||||
]);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -20,12 +20,15 @@ declare global {
|
|||
}
|
||||
}
|
||||
|
||||
function useTimeScale(modelViewer: ModelViewerElement | null) {
|
||||
function useTimeScale(
|
||||
modelViewer: ModelViewerElement | null,
|
||||
timeScale: number
|
||||
) {
|
||||
useEffect(() => {
|
||||
if (modelViewer) {
|
||||
modelViewer.timeScale = 0.5;
|
||||
modelViewer.timeScale = timeScale;
|
||||
}
|
||||
}, [modelViewer]);
|
||||
}, [modelViewer, timeScale]);
|
||||
}
|
||||
|
||||
interface ModelViewerProps {
|
||||
|
|
@ -37,6 +40,7 @@ interface ModelViewerProps {
|
|||
metallicImageUrl?: string;
|
||||
animationName: string | null;
|
||||
animationPaused?: boolean;
|
||||
timeScale?: number;
|
||||
cameraOrbit?: string;
|
||||
cameraTarget?: string;
|
||||
fieldOfView?: string;
|
||||
|
|
@ -50,6 +54,7 @@ function ModelViewerKeyedByModel({
|
|||
exposure = 1,
|
||||
animationName,
|
||||
animationPaused = false,
|
||||
timeScale = 1,
|
||||
cameraOrbit,
|
||||
cameraTarget,
|
||||
fieldOfView,
|
||||
|
|
@ -71,7 +76,7 @@ function ModelViewerKeyedByModel({
|
|||
};
|
||||
}, [modelViewer, isLoaded]);
|
||||
|
||||
useTimeScale(modelViewer);
|
||||
useTimeScale(modelViewer, timeScale);
|
||||
|
||||
useEffect(() => {
|
||||
if (!modelViewer) {
|
||||
|
|
|
|||
|
|
@ -138,6 +138,7 @@ export default function WarriorProvider({ children }: { children: ReactNode }) {
|
|||
null
|
||||
);
|
||||
const [animationPaused, setAnimationPaused] = useState(false);
|
||||
const [slowModeEnabled, setSlowModeEnabled] = useState(false);
|
||||
const { basePath } = useSettings();
|
||||
const actualModel = selectedModel === "hfemale" ? "hmale" : selectedModel;
|
||||
const selectedModelUrl = getModelUrl(
|
||||
|
|
@ -188,6 +189,8 @@ export default function WarriorProvider({ children }: { children: ReactNode }) {
|
|||
skinImageUrls,
|
||||
setSkinImageUrls,
|
||||
defaultSkinImageUrls,
|
||||
slowModeEnabled,
|
||||
setSlowModeEnabled,
|
||||
};
|
||||
}, [
|
||||
selectedModel,
|
||||
|
|
@ -207,6 +210,7 @@ export default function WarriorProvider({ children }: { children: ReactNode }) {
|
|||
skinImageUrls,
|
||||
setSkinImageUrls,
|
||||
defaultSkinImageUrls,
|
||||
slowModeEnabled,
|
||||
]);
|
||||
|
||||
useEffect(() => {
|
||||
|
|
|
|||
|
|
@ -17,6 +17,7 @@ export default function WarriorViewer() {
|
|||
selectedModelType,
|
||||
selectedAnimation,
|
||||
animationPaused,
|
||||
slowModeEnabled,
|
||||
} = useWarrior();
|
||||
const { environmentImageUrl, showEnvironment, exposure } = useEnvironment();
|
||||
|
||||
|
|
@ -27,6 +28,7 @@ export default function WarriorViewer() {
|
|||
showEnvironment={showEnvironment}
|
||||
animationName={selectedAnimation}
|
||||
animationPaused={animationPaused}
|
||||
timeScale={slowModeEnabled ? 0.05 : 0.5}
|
||||
cameraOrbit={
|
||||
selectedModelType === "weapon" ? "315deg 70deg 105%" : undefined
|
||||
}
|
||||
|
|
|
|||
|
|
@ -192,11 +192,17 @@ select {
|
|||
display: flex;
|
||||
align-items: center;
|
||||
gap: 10px;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.Buttons select {
|
||||
flex: 1 0 auto;
|
||||
}
|
||||
|
||||
.Buttons button {
|
||||
display: grid;
|
||||
place-content: center;
|
||||
flex: 0 0 auto;
|
||||
border: 1px solid rgb(23, 159, 138);
|
||||
border-radius: 2px;
|
||||
width: 28px;
|
||||
|
|
@ -278,10 +284,10 @@ select {
|
|||
gap: 10px;
|
||||
}
|
||||
|
||||
.ModelTools:has(input[type="checkbox"]:checked) {
|
||||
/* .ModelTools:has(input[type="checkbox"]:checked) {
|
||||
background-color: #01292e;
|
||||
background-image: linear-gradient(to bottom, #124044 0%, #001720 100vh);
|
||||
}
|
||||
} */
|
||||
|
||||
.Field {
|
||||
display: flex;
|
||||
|
|
@ -290,13 +296,21 @@ select {
|
|||
gap: 4px;
|
||||
}
|
||||
|
||||
.Field > label {
|
||||
.Field > label,
|
||||
.Field > div > label {
|
||||
text-transform: uppercase;
|
||||
font-size: 11px;
|
||||
text-shadow: 0 1px 1px rgba(0, 0, 0, 0.8);
|
||||
opacity: 0.8;
|
||||
}
|
||||
|
||||
.Field .LabelWithControls {
|
||||
width: 100%;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
}
|
||||
|
||||
.BrushToolsPopup {
|
||||
background: rgba(5, 22, 21, 0.9);
|
||||
border-radius: 4px;
|
||||
|
|
@ -519,3 +533,17 @@ h6 {
|
|||
font-size: 12px;
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
.AnimationSpeed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
font-size: 11px;
|
||||
margin: 0 38px 0 16px;
|
||||
gap: 3px;
|
||||
color: rgb(122, 183, 165);
|
||||
}
|
||||
|
||||
.AnimationSpeed input[type="checkbox"] {
|
||||
width: 12px;
|
||||
height: 12px;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -26,6 +26,8 @@ type WarriorContextValue = {
|
|||
selectedSkin: string | null;
|
||||
setSelectedSkin: (selectedSkin: string | null) => void;
|
||||
setSelectedModelType: (selectedModelType: string) => void;
|
||||
slowModeEnabled: boolean;
|
||||
setSlowModeEnabled: (slowModeEnabled: boolean) => void;
|
||||
};
|
||||
|
||||
const WarriorContext = React.createContext<WarriorContextValue | null>(null);
|
||||
|
|
|
|||
Loading…
Reference in a new issue