Skip to content

Commit 8afe617

Browse files
committed
ペット挙動調整
1 parent a79d87f commit 8afe617

1 file changed

Lines changed: 53 additions & 21 deletions

File tree

WebSite/assets/js/layout.js

Lines changed: 53 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -117,31 +117,42 @@ document.addEventListener("DOMContentLoaded", () => {
117117
let isMoving = false;
118118
let isVisible = false;
119119
let activeElement = null;
120+
// Timestamp until which mouseover events should be ignored after spawn (grace period)
121+
let spawnGraceUntil = 0;
120122

121123
const breadWidth = 40;
122124
const breadHeight = 34;
123125

124-
// Initial spawn from active language option
125-
const activeLang = document.querySelector(
126-
".lang-option.active",
127-
);
128-
if (activeLang) {
129-
activeElement = activeLang;
130-
const rect = activeLang.getBoundingClientRect();
131-
targetX =
132-
rect.left + window.scrollX - breadWidth / 2;
133-
targetY =
134-
rect.bottom + window.scrollY - breadHeight;
135-
currentX = targetX;
136-
currentY = targetY;
137-
isVisible = true;
138-
bread.classList.add("is-visible", "is-spawning");
139-
bread.style.transform = `translate3d(${currentX}px, ${currentY}px, 0)`;
140-
141-
setTimeout(() => {
142-
bread.classList.remove("is-spawning");
143-
}, 600);
144-
}
126+
// Initial spawn: appear at screen center and stay there.
127+
// 初期生成時はアクティブな言語要素をターゲットにせず、
128+
// spawn位置に留まるよう target を current と同値にする。
129+
const centerX =
130+
window.scrollX +
131+
window.innerWidth / 2 -
132+
breadWidth / 2;
133+
const centerY =
134+
window.scrollY +
135+
window.innerHeight / 2 -
136+
breadHeight / 2;
137+
138+
currentX = centerX;
139+
currentY = centerY;
140+
141+
// 初期ターゲットを現在位置に合わせる(これによりスポーン後は移動しない)
142+
targetX = currentX;
143+
targetY = currentY;
144+
145+
// activeElement は設定しない(null のまま) -> animate では移動しない
146+
activeElement = null;
147+
148+
isVisible = true;
149+
bread.classList.add("is-visible", "is-spawning");
150+
bread.style.transform = `translate3d(${currentX}px, ${currentY}px, 0)`;
151+
152+
// remove spawning class after animation duration
153+
setTimeout(() => {
154+
bread.classList.remove("is-spawning");
155+
}, 600);
145156

146157
// Track hovers on any interactive element in the document
147158
document.addEventListener(
@@ -151,7 +162,28 @@ document.addEventListener("DOMContentLoaded", () => {
151162
"a, button, .lang-option, input, select, textarea, [role='button']",
152163
);
153164

165+
// Ignore mouseover events during the spawn grace period so bread stays at spawn
166+
if (
167+
typeof spawnGraceUntil === "number" &&
168+
Date.now() < spawnGraceUntil
169+
) {
170+
return;
171+
}
172+
173+
// Ignore interactions on the language switch control itself so the bread
174+
// doesn't move to the language switch button (e.g. elements with .lang-switch)
175+
if (
176+
target &&
177+
target.closest &&
178+
target.closest(".lang-switch")
179+
) {
180+
return;
181+
}
182+
154183
if (target) {
184+
// ユーザーが意図的に要素にホバーした場合のみ追従させる挙動を残す。
185+
// ただし初期スポーン直後に自動で移動してしまうのを防ぐため、
186+
// ここでは通常のホバー時に activeElement を設定して追従を開始する。
155187
activeElement = target;
156188
const rect = target.getBoundingClientRect();
157189

0 commit comments

Comments
 (0)