From ad5a5b0cfb02ff8985ba1deec24f4fe4be9f749f Mon Sep 17 00:00:00 2001 From: Horoli Date: Mon, 2 Nov 2026 12:30:26 +0900 Subject: [PATCH] feat: simplify companion action and randomize idle gestures every 30 seconds --- index.html | 7 +------ src/constants/character.ts | 4 +--- src/constants/ui.ts | 1 - src/scene/sheep.ts | 24 +++++++----------------- src/scene/world.ts | 15 ++++----------- src/style.css | 9 +++------ 6 files changed, 16 insertions(+), 44 deletions(-) diff --git a/index.html b/index.html index adc4e34..8de0037 100644 --- a/index.html +++ b/index.html @@ -87,12 +87,7 @@ - +
diff --git a/src/constants/character.ts b/src/constants/character.ts index 18b7020..35f9bbd 100644 --- a/src/constants/character.ts +++ b/src/constants/character.ts @@ -26,10 +26,8 @@ export const CHARACTER = { headLift: 0.018, shoulderLift: 0.008, fidget: { - minimumWaitSeconds: 8, - maximumWaitSeconds: 15, + intervalSeconds: 30, scratchSeconds: 2.4, - hopIntervalSeconds: 60, hopSeconds: 1, hopHeight: 0.085, hopCrouch: 0.025, diff --git a/src/constants/ui.ts b/src/constants/ui.ts index de591c5..2b3c583 100644 --- a/src/constants/ui.ts +++ b/src/constants/ui.ts @@ -13,4 +13,3 @@ export const EQUIPMENT_NOTICE = { } as const; export const PRAYER_NOTICE = '일출 전후 5분에 사용할 수 있습니다'; -export const COMPANION_MENU = { margin: 12 } as const; diff --git a/src/scene/sheep.ts b/src/scene/sheep.ts index b09b32b..2d0f02b 100644 --- a/src/scene/sheep.ts +++ b/src/scene/sheep.ts @@ -127,9 +127,7 @@ export function createSheep(model: Group, gear?: { umbrella: Group; raincoat: Gr const rigModel = copy(model)!; const breathPhase = Math.random() * Math.PI * 2; const fidget = CHARACTER.idle.fidget; - const nextFidgetDelay = () => MathUtils.lerp(fidget.minimumWaitSeconds, fidget.maximumWaitSeconds, Math.random()); - let fidgetWait = nextFidgetDelay(); - let hopWait: number = fidget.hopIntervalSeconds; + let fidgetWait: number = fidget.intervalSeconds; let fidgetTime = 0; let fidgetAction: 'scratch' | 'hop' | undefined; let idleWeight = 0; @@ -173,30 +171,22 @@ export function createSheep(model: Group, gear?: { umbrella: Group; raincoat: Gr const idle = animateIdle && !moving && emote === 'idle'; rigModel.position.copy(modelRestPosition); if (!idle) { - fidgetWait = nextFidgetDelay(); - hopWait = fidget.hopIntervalSeconds; + fidgetWait = fidget.intervalSeconds; fidgetTime = 0; fidgetAction = undefined; } else { // Do not fast-forward gestures after a background tab resumes. const idleDelta = Math.min(delta, .1); - hopWait -= idleDelta; - if (hopWait <= 0) { - fidgetAction = 'hop'; + fidgetWait -= idleDelta; + if (fidgetWait <= 0) { + fidgetAction = Math.random() < .5 ? 'scratch' : 'hop'; fidgetTime = 0; - hopWait += fidget.hopIntervalSeconds; - } else if (!fidgetAction) { - fidgetWait -= idleDelta; - if (fidgetWait <= 0) { - fidgetAction = 'scratch'; - fidgetTime = 0; - } - } else { + fidgetWait += fidget.intervalSeconds; + } else if (fidgetAction) { fidgetTime += idleDelta; const duration = fidgetAction === 'scratch' ? fidget.scratchSeconds : fidget.hopSeconds; if (fidgetTime >= duration) { fidgetAction = undefined; - fidgetWait = nextFidgetDelay(); } } } diff --git a/src/scene/world.ts b/src/scene/world.ts index 9103823..a8e04a2 100644 --- a/src/scene/world.ts +++ b/src/scene/world.ts @@ -7,7 +7,7 @@ import type { SunState } from '../astronomy/sunCalculator.ts'; import { directionFromAngles } from '../astronomy/direction.ts'; import { observer } from '../config/observer.ts'; import { SCENE } from '../constants/scene.ts'; -import { COMPANION_MENU, EQUIPMENT_NOTICE, PRAYER_NOTICE } from '../constants/ui.ts'; +import { EQUIPMENT_NOTICE, PRAYER_NOTICE } from '../constants/ui.ts'; import { MOVEMENT } from '../constants/movement.ts'; import { CHARACTER } from '../constants/character.ts'; import { createFpsCameraController } from '../controls/fpsCameraController.ts'; @@ -175,11 +175,8 @@ export function createWorld(canvas: HTMLCanvasElement, terrainData: Awaited | undefined; const directionButton = document.querySelector('#direction-toggle')!; const directionHint = document.getElementById('direction-hint')!; - const companionPanel = document.getElementById('companion-selection')!; - const companionName = document.getElementById('companion-name')!; - const companionStatus = document.getElementById('companion-status')!; const besideButton = document.querySelector('#stand-beside')!; - const closeCompanion = () => { selectedCompanion = undefined; companionAnchor = undefined; companionPanel.hidden = true; companionStatus.textContent = ''; }; + const closeCompanion = () => { selectedCompanion = undefined; companionAnchor = undefined; besideButton.hidden = true; }; const pickGround = (x: number, y: number) => { const bounds = canvas.getBoundingClientRect(); pointer.set((x - bounds.left) / bounds.width * 2 - 1, -(y - bounds.top) / bounds.height * 2 + 1); @@ -215,8 +212,7 @@ export function createWorld(canvas: HTMLCanvasElement, terrainData: Awaited { if (sheep && !networkBlocked && !overview) controls.setTurning(!controls.turning); }, { signal: emoteEvents.signal }); - document.getElementById('companion-close')!.addEventListener('click', closeCompanion, { signal: emoteEvents.signal }); besideButton.addEventListener('click', () => { if (!selectedCompanion || networkBlocked || overview) return; const spot = remotePlayers?.beside(selectedCompanion, camera.position, point => { @@ -244,10 +239,9 @@ export function createWorld(canvas: HTMLCanvasElement, terrainData: Awaited('#emote-wave')!; const primaryActionLabel = document.getElementById('primary-action-label')!; @@ -425,7 +419,6 @@ export function createWorld(canvas: HTMLCanvasElement, terrainData: Awaited