/* ===== 浠艾福桌面宠物动画定义 ===== */ @keyframes wings_idle { 0%, 100% { transform: translateY(0) } 50% { transform: translateY(-3px) } } @keyframes wings_spread { 0% { transform: scale(1) } 30% { transform: scale(1.15, 0.95) } 70% { transform: scale(0.95, 1.1) } 100% { transform: scale(1) } } @keyframes head_tilt { 0%, 100% { transform: rotate(0deg) } 25% { transform: rotate(-8deg) } 75% { transform: rotate(6deg) } } @keyframes hand_gesture { 0%, 100% { transform: translateY(0) } 20% { transform: translateY(-8px) } 40% { transform: translateY(0) } 60% { transform: translateY(-5px) } 80% { transform: translateY(0) } } @keyframes breath_loop { 0%, 100% { transform: scale(1, 1) } 50% { transform: scale(1.04, 0.96) } } @keyframes celebrate { 0%, 100% { transform: translateY(0) rotate(0) } 25% { transform: translateY(-16px) rotate(-4deg) } 50% { transform: translateY(0) rotate(0) } 75% { transform: translateY(-16px) rotate(4deg) } } @keyframes sad_animation { 0%, 100% { transform: translateY(0) } 50% { transform: translateY(2px) } } @keyframes tail_wrap { 0%, 100% { transform: rotate(0deg) } 50% { transform: rotate(3deg) } } @keyframes belly_show { 0%, 100% { transform: rotate(0deg) scale(1) } 50% { transform: rotate(-4deg) scale(1.05) } } @keyframes paw_press { 0%, 100% { transform: translateY(0) } 50% { transform: translateY(3px) } } @keyframes tail_flick { 0%, 100% { transform: rotate(0deg) } 30% { transform: rotate(10deg) } 60% { transform: rotate(-10deg) } } @keyframes blink_eye { 0%, 90%, 100% { transform: scaleY(1) } 95% { transform: scaleY(0.1) } } @keyframes look_around { 0%, 100% { transform: rotate(0deg) } 25% { transform: rotate(-12deg) } 75% { transform: rotate(12deg) } } @keyframes wave { 0%, 100% { transform: rotate(0deg) } 25% { transform: rotate(-15deg) } 50% { transform: rotate(10deg) } 75% { transform: rotate(-15deg) } } @keyframes stretch { 0%, 100% { transform: scaleY(1) } 50% { transform: scaleY(1.15) } } @keyframes clap { 0%, 100% { transform: scale(1) } 40% { transform: scale(1.1, 0.9) } 70% { transform: scale(0.95, 1.05) } } @keyframes bow { 0%, 100% { transform: rotate(0deg) } 50% { transform: rotate(10deg) } } @keyframes whistle { 0%, 100% { transform: translateY(0) } 50% { transform: translateY(-4px) } } @keyframes ear_scrape { 0%, 100% { transform: rotate(0deg) } 50% { transform: rotate(6deg) } } @keyframes pet_touch { 0% { transform: scale(1) } 50% { transform: scale(1.08) } 100% { transform: scale(1) } } @keyframes puzzle_active { 0%, 100% { transform: rotate(0deg) } 50% { transform: rotate(180deg) } } @keyframes worried_walk { 0%, 100% { transform: translateX(0) } 25% { transform: translateX(6px) } 75% { transform: translateX(-6px) } } /* ===== 精细化动作:姿态层(#pet-body)===== 由 locomotion.rs 的 pet://gait 事件驱动;与 #pet 上的情绪动画(.anim-*)分层叠加。 朝向:--face 由 .pose-face-left 切换(1=右,-1=左),关键帧统一 scaleX(var(--face,1))。 */ /* 走:上下颠簸 + 左右重心摆 + 前后微倾,模拟迈步 */ @keyframes walk_bob { 0% { transform: scaleX(var(--face,1)) translateY(0) rotate(0deg) } 25% { transform: scaleX(var(--face,1)) translateY(-3px) rotate(-3.5deg) } 50% { transform: scaleX(var(--face,1)) translateY(-1px) rotate(0deg) } 75% { transform: scaleX(var(--face,1)) translateY(-3px) rotate(3.5deg) } 100% { transform: scaleX(var(--face,1)) translateY(0) rotate(0deg) } } /* 跳着走:下蹲预备 → 起跳拉伸 → 滞空 → 落地挤压缓冲 */ @keyframes hop_squash { 0% { transform: scaleX(var(--face,1)) translateY(0) scale(1, 1) } 18% { transform: scaleX(var(--face,1)) translateY(2px) scale(1.09, 0.9) } 45% { transform: scaleX(var(--face,1)) translateY(-15px) scale(0.9, 1.15) } 62% { transform: scaleX(var(--face,1)) translateY(-11px) scale(0.95, 1.05) } 82% { transform: scaleX(var(--face,1)) translateY(0) scale(1.07, 0.91) } 100% { transform: scaleX(var(--face,1)) translateY(0) scale(1, 1) } } /* 飞:高频振翅(垂直挤压振荡)+ 抬升 + 侧倾 */ @keyframes fly_flutter { 0% { transform: scaleX(var(--face,1)) translateY(-2px) rotate(-8deg) scale(1.02, 0.98) } 25% { transform: scaleX(var(--face,1)) translateY(-11px) rotate(5deg) scale(0.93, 1.09) } 50% { transform: scaleX(var(--face,1)) translateY(-4px) rotate(-6deg) scale(1.07, 0.93) } 75% { transform: scaleX(var(--face,1)) translateY(-13px) rotate(7deg) scale(0.91, 1.11) } 100% { transform: scaleX(var(--face,1)) translateY(-2px) rotate(-8deg) scale(1.02, 0.98) } } /* 站手:随手指轻晃 + 微起伏 */ @keyframes perch_lean { 0% { transform: scaleX(var(--face,1)) rotate(-2.5deg) translateY(0) } 50% { transform: scaleX(var(--face,1)) rotate(2.5deg) translateY(-2px) } 100% { transform: scaleX(var(--face,1)) rotate(-2.5deg) translateY(0) } } /* 待机:极轻微呼吸起伏(无位移,避免与情绪动画冲突) */ @keyframes idle_breathe { 0% { transform: scaleX(var(--face,1)) scale(1, 1) } 50% { transform: scaleX(var(--face,1)) scale(1.02, 0.985) } 100% { transform: scaleX(var(--face,1)) scale(1, 1) } } .pose-walk { animation: walk_bob 0.75s ease-in-out infinite; } .pose-hop { animation: hop_squash 0.62s ease-in-out infinite; } .pose-fly { animation: fly_flutter 0.3s ease-in-out infinite; } .pose-perch { animation: perch_lean 1.8s ease-in-out infinite; } .pose-idle { animation: idle_breathe 3.2s ease-in-out infinite; } .pose-face-left { --face: -1; } .anim-wings_idle { animation: wings_idle 2s ease-in-out infinite; } .anim-wings_spread { animation: wings_spread 1.2s ease-in-out 1; } .anim-head_tilt { animation: head_tilt 1.6s ease-in-out infinite; } .anim-hand_gesture { animation: hand_gesture 1.8s ease-in-out infinite; } .anim-breath_loop { animation: breath_loop 2.4s ease-in-out infinite; } .anim-celebrate { animation: celebrate 0.8s ease-in-out 3; } .anim-sad_animation { animation: sad_animation 3s ease-in-out infinite; } .anim-tail_wrap { animation: tail_wrap 2s ease-in-out infinite; } .anim-belly_show { animation: belly_show 1.4s ease-in-out 2; } .anim-paw_press { animation: paw_press 1s ease-in-out 2; } .anim-tail_flick { animation: tail_flick 1.5s ease-in-out 2; } .anim-blink_eye { animation: blink_eye 3.5s ease-in-out infinite; } .anim-look_around { animation: look_around 2s ease-in-out 1; } .anim-wave { animation: wave 1.2s ease-in-out 2; } .anim-stretch { animation: stretch 1.8s ease-in-out 1; } .anim-clap { animation: clap 0.6s ease-in-out 3; } .anim-bow { animation: bow 1.2s ease-in-out 2; } .anim-whistle { animation: whistle 0.9s ease-in-out 3; } .anim-ear_scrape { animation: ear_scrape 1s ease-in-out 2; } .anim-pet_touch { animation: pet_touch 0.6s ease-in-out 1; } .anim-puzzle_active { animation: puzzle_active 1s ease-in-out infinite; } .anim-worried_walk { animation: worried_walk 1.2s ease-in-out infinite; }