@keyframes pulse { 0%, 100% { opacity: 1; } 50% { opacity: 0.5; } } .typing-indicator { display: inline-flex; gap: 4px; } .typing-dot { width: 8px; height: 8px; border-radius: 50%; background-color: #6b7280; animation: pulse 1.5s infinite ease-in-out; } .typing-dot:nth-child(1) { animation-delay: 0s; } .typing-dot:nth-child(2) { animation-delay: 0.2s; } .typing-dot:nth-child(3) { animation-delay: 0.4s; } .tool-call { transition: all 0.3s ease; box-shadow: 0 4px 6px rgba(59, 130, 246, 0.1), 0 2px 4px rgba(59, 130, 246, 0.06); animation: slideInUp 0.4s ease-out; } @keyframes slideInUp { from { opacity: 0; transform: translateY(20px); } to { opacity: 1; transform: translateY(0); } } .tool-call:hover { box-shadow: 0 10px 15px rgba(59, 130, 246, 0.15), 0 4px 6px rgba(59, 130, 246, 0.1); transform: translateY(-1px); } .tool-call .text-xs { white-space: pre-wrap; font-family: 'SFMono-Regular', Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace; } .tool-call pre { font-family: 'SFMono-Regular', Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace; margin: 0; line-height: 1.4; } .spinner { width: 16px; height: 16px; border: 2px solid rgba(59, 130, 246, 0.2); border-top-color: #3b82f6; border-radius: 50%; animation: spin 1s linear infinite; } @keyframes spin { to { transform: rotate(360deg); } } /* 工具调用特殊动画 */ .tool-call-bounce { animation: toolCallBounce 0.6s ease-out; } @keyframes toolCallBounce { 0% { opacity: 0; transform: scale(0.9) translateY(10px); } 50% { opacity: 1; transform: scale(1.02) translateY(-2px); } 100% { opacity: 1; transform: scale(1) translateY(0); } }