├── .npmrc
├── .eslintrc.json
├── favicon.ico
├── preview.mp4
├── preview.png
├── public
├── chatGPT.png
├── favicon.ico
├── profile.png
├── chat_gpt.png
├── claude_icon.webp
├── easierchat-192.png
├── easierchat-384.png
├── easierchat-512.png
├── manifest.json
├── sw.js
├── thirteen.svg
├── next.svg
├── sw.js.map
└── workbox-06528c14.js
├── helpers
├── fetcher.ts
├── getIp.ts
├── cluade.helpers.ts
└── openStream.ts
├── postcss.config.js
├── tailwind.config.js
├── pages
├── _document.tsx
├── api
│ ├── sse.ts
│ └── sendChat.ts
├── _app.tsx
└── index.tsx
├── components
├── LeftMenu
│ └── index.tsx
├── ThemeChanger
│ ├── ThemeSVGComp.tsx
│ └── index.tsx
├── Alert
│ └── index.tsx
├── Lottie
│ └── index.tsx
├── ChatRecord
│ └── index.tsx
├── Settings
│ └── index.tsx
├── Chat
│ ├── ai.json
│ └── index.tsx
├── FunctionalZone
│ └── index.tsx
├── FastOperations
│ └── index.tsx
├── Intro
│ └── index.tsx
├── KeySetting
│ └── index.tsx
├── ClaudeSetting
│ └── index.tsx
├── ContextMenu
│ └── index.tsx
└── CommandBar
│ └── index.tsx
├── README.md
├── hooks
└── useIsSupportCapture.ts
├── typings.d.ts
├── next.config.js
├── .gitignore
├── tsconfig.json
├── styles
├── avatar.css
├── slider.css
├── globals.css
├── atom-one-dark.css
├── context.css
├── alert.css
├── dailog.css
├── modal.css
└── markdown.css
├── test.json
├── contexts
├── openaiKey.tsx
├── assistant.tsx
└── modelSetting.tsx
├── data
└── prompts.ts
├── package.json
├── services
└── claude.ts
└── lottie
├── activity.json
├── tick.json
├── dot.json
├── setting-dark.json
├── setting.json
└── info.json
/.npmrc:
--------------------------------------------------------------------------------
1 | registry=https://registry.npmjs.org/
--------------------------------------------------------------------------------
/.eslintrc.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "next/core-web-vitals"
3 | }
4 |
--------------------------------------------------------------------------------
/favicon.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/maoxiaoke/easierChat/HEAD/favicon.ico
--------------------------------------------------------------------------------
/preview.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/maoxiaoke/easierChat/HEAD/preview.mp4
--------------------------------------------------------------------------------
/preview.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/maoxiaoke/easierChat/HEAD/preview.png
--------------------------------------------------------------------------------
/public/chatGPT.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/maoxiaoke/easierChat/HEAD/public/chatGPT.png
--------------------------------------------------------------------------------
/public/favicon.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/maoxiaoke/easierChat/HEAD/public/favicon.ico
--------------------------------------------------------------------------------
/public/profile.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/maoxiaoke/easierChat/HEAD/public/profile.png
--------------------------------------------------------------------------------
/public/chat_gpt.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/maoxiaoke/easierChat/HEAD/public/chat_gpt.png
--------------------------------------------------------------------------------
/public/claude_icon.webp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/maoxiaoke/easierChat/HEAD/public/claude_icon.webp
--------------------------------------------------------------------------------
/public/easierchat-192.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/maoxiaoke/easierChat/HEAD/public/easierchat-192.png
--------------------------------------------------------------------------------
/public/easierchat-384.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/maoxiaoke/easierChat/HEAD/public/easierchat-384.png
--------------------------------------------------------------------------------
/public/easierchat-512.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/maoxiaoke/easierChat/HEAD/public/easierchat-512.png
--------------------------------------------------------------------------------
/helpers/fetcher.ts:
--------------------------------------------------------------------------------
1 | // @ts-ignore
2 | export const fetcher = (...args) => fetch(...args).then(res => res.json());
--------------------------------------------------------------------------------
/postcss.config.js:
--------------------------------------------------------------------------------
1 | module.exports = {
2 | plugins: {
3 | tailwindcss: {},
4 | autoprefixer: {},
5 | },
6 | }
7 |
--------------------------------------------------------------------------------
/tailwind.config.js:
--------------------------------------------------------------------------------
1 | /** @type {import('tailwindcss').Config} */
2 | module.exports = {
3 | content: [
4 | './pages/**/*.{js,ts,jsx,tsx}',
5 | './components/**/*.{js,ts,jsx,tsx}',
6 | ],
7 | darkMode: ['class', '.dark-theme'],
8 | plugins: [
9 | require('@tailwindcss/typography'),
10 | require("tailwindcss-radix")(),
11 | ],
12 | }
13 |
--------------------------------------------------------------------------------
/helpers/getIp.ts:
--------------------------------------------------------------------------------
1 | import type { NextApiRequest } from "next";
2 |
3 | export default function getIP(request: Request | NextApiRequest) {
4 | const xff =
5 | request instanceof Request
6 | ? request.headers.get("x-forwarded-for")
7 | : request.headers["x-forwarded-for"];
8 |
9 | return xff ? (Array.isArray(xff) ? xff[0] : xff.split(",")[0]) : "127.0.0.1";
10 | }
11 |
--------------------------------------------------------------------------------
/pages/_document.tsx:
--------------------------------------------------------------------------------
1 | import { Html, Head, Main, NextScript } from "next/document";
2 |
3 | export default function Document() {
4 | return (
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 | );
15 | }
16 |
--------------------------------------------------------------------------------
/components/LeftMenu/index.tsx:
--------------------------------------------------------------------------------
1 | const LeftMenu = () => {
2 | return (
3 |
4 | 创建新聊天
5 |
6 | )
7 | }
8 |
9 | export default LeftMenu;
--------------------------------------------------------------------------------
/components/ThemeChanger/ThemeSVGComp.tsx:
--------------------------------------------------------------------------------
1 | import { MoonIcon,DesktopIcon, SunIcon } from '@radix-ui/react-icons'
2 |
3 | const ThemeSvg = (props: {mode?: string})=>{
4 | const {mode} = props
5 | if(mode==='dark'){
6 | return
7 | }
8 | if(mode ==='light'){
9 | return
10 | }
11 | if(mode === 'system'){
12 | return
13 | }
14 | return <>>
15 | }
16 | export default ThemeSvg
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 | easierChat.com
7 |
8 |
9 |
10 |
11 | 一个更方便、易用的 chatBot 客户端 | macOS Client
12 |
13 |
14 | ## Preview
15 |
16 | 
17 |
18 |
19 |
--------------------------------------------------------------------------------
/hooks/useIsSupportCapture.ts:
--------------------------------------------------------------------------------
1 | import { useLayoutEffect, useState } from 'react';
2 |
3 | export const useIsSupportCapture = () => {
4 | const [isSupport, setIsSupport] = useState(true);
5 |
6 | useLayoutEffect(() => {
7 | const input = document.createElement('input');
8 | input.type = 'file';
9 |
10 | if (!('capture' in input)) {
11 | setIsSupport(false);
12 | }
13 | }, []);
14 |
15 | return isSupport;
16 | };
17 |
18 |
--------------------------------------------------------------------------------
/typings.d.ts:
--------------------------------------------------------------------------------
1 | declare interface ChatMessage {
2 | /* 创建日期 */
3 | date: number;
4 | /* 角色 */
5 | role: 'assistant' | 'user';
6 | /* 文本 */
7 | text: string;
8 | /* uniqueID */
9 | id?: string;
10 | /* 会话 id */
11 | conversationId?: string;
12 | }
13 |
14 | declare interface AssistantRole {
15 | id: string,
16 | character: string,
17 | prompt: string;
18 | title: string;
19 | desc: string;
20 | keywords: string[];
21 | }
22 |
23 |
--------------------------------------------------------------------------------
/next.config.js:
--------------------------------------------------------------------------------
1 | /** @type {import('next').NextConfig} */
2 | const runtimeCaching = require("next-pwa/cache");
3 |
4 | const withPWA = require("next-pwa")({
5 | dest: "public",
6 | register: true,
7 | skipWaiting: true,
8 | disable: process.env.NODE_ENV === 'development',
9 | runtimeCaching,
10 | buildExcludes: [/middleware-manifest.json$/]
11 | });
12 |
13 | const nextConfig = withPWA({
14 | reactStrictMode: true
15 | })
16 |
17 | module.exports = nextConfig
18 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files.
2 |
3 | # dependencies
4 | /node_modules
5 | /.pnp
6 | .pnp.js
7 |
8 | # testing
9 | /coverage
10 |
11 | # next.js
12 | /.next/
13 | /out/
14 |
15 | # production
16 | /build
17 |
18 | # misc
19 | .DS_Store
20 | *.pem
21 |
22 | # debug
23 | npm-debug.log*
24 | yarn-debug.log*
25 | yarn-error.log*
26 | .pnpm-debug.log*
27 |
28 | # local env files
29 | .env*.local
30 |
31 | # vercel
32 | .vercel
33 |
34 | # typescript
35 | *.tsbuildinfo
36 | next-env.d.ts
37 |
--------------------------------------------------------------------------------
/public/manifest.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "easierChat",
3 | "short_name": "chat",
4 | "icons": [
5 | {
6 | "src": "/easierchat-192.png",
7 | "sizes": "192x192",
8 | "type": "image/png"
9 | },
10 | {
11 | "src": "/easierchat-384.png",
12 | "sizes": "384x384",
13 | "type": "image/png"
14 | },
15 | {
16 | "src": "/easierchat-512.png",
17 | "sizes": "512x512",
18 | "type": "image/png"
19 | }
20 | ],
21 | "theme_color": "#FFFFFF",
22 | "background_color": "#FFFFFF",
23 | "start_url": "/",
24 | "display": "standalone",
25 | "orientation": "portrait"
26 | }
--------------------------------------------------------------------------------
/pages/api/sse.ts:
--------------------------------------------------------------------------------
1 | import { OpenAIStream } from "../../helpers/openStream";
2 | import { HUMAN_PROMPT } from '../../services/claude';
3 |
4 | export const config = {
5 | runtime: "edge",
6 | };
7 |
8 | const handler = async (req: Request): Promise => {
9 | const { text } = (await req.json()) as {
10 | text?: string;
11 | };
12 |
13 | const payload = {
14 | prompt: text,
15 | stop_sequences: [HUMAN_PROMPT],
16 | max_tokens_to_sample: 500,
17 | model: "claude-instant-v1",
18 | };
19 |
20 | const stream = await OpenAIStream(payload);
21 | return new Response(stream);
22 | };
23 |
24 | export default handler;
--------------------------------------------------------------------------------
/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "compilerOptions": {
3 | "target": "es5",
4 | "lib": ["dom", "dom.iterable", "esnext"],
5 | "allowJs": true,
6 | "skipLibCheck": true,
7 | "strict": true,
8 | "forceConsistentCasingInFileNames": true,
9 | "noEmit": true,
10 | "esModuleInterop": true,
11 | "module": "esnext",
12 | "moduleResolution": "node",
13 | "resolveJsonModule": true,
14 | "isolatedModules": true,
15 | "jsx": "preserve",
16 | "incremental": true,
17 | "paths": {
18 | "@/*": ["./*"]
19 | }
20 | },
21 | "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx"],
22 | "exclude": ["node_modules"]
23 | }
24 |
--------------------------------------------------------------------------------
/components/ThemeChanger/index.tsx:
--------------------------------------------------------------------------------
1 | import { useTheme } from 'next-themes'
2 | import ThemeIcon from './ThemeSVGComp'
3 |
4 | const THEMES = ['system','dark', 'light'];
5 |
6 | const ThemeChanger = () => {
7 | const { theme, setTheme } = useTheme()
8 |
9 | const nextTheme = ()=>{
10 | const targetIndex = (THEMES.findIndex(v=>v===theme)+1) % THEMES.length
11 | setTheme(THEMES[targetIndex])
12 | }
13 |
14 | return
17 |
18 |
19 | }
20 |
21 | export default ThemeChanger
--------------------------------------------------------------------------------
/styles/avatar.css:
--------------------------------------------------------------------------------
1 |
2 |
3 | .AvatarRoot {
4 | display: inline-flex;
5 | align-items: center;
6 | justify-content: center;
7 | vertical-align: middle;
8 | overflow: hidden;
9 | user-select: none;
10 | border-radius: 100%;
11 | background-color: var(--slate3);
12 | }
13 |
14 | .AvatarImage {
15 | width: 100%;
16 | height: 100%;
17 | object-fit: cover;
18 | border-radius: inherit;
19 | }
20 |
21 | .AvatarFallback {
22 | width: 100%;
23 | height: 100%;
24 | display: flex;
25 | align-items: center;
26 | justify-content: center;
27 | background-color: var(--slate1);
28 | color: var(--violet11);
29 | font-size: 15px;
30 | line-height: 1;
31 | font-weight: 500;
32 | }
--------------------------------------------------------------------------------
/test.json:
--------------------------------------------------------------------------------
1 | {
2 | "model": "gpt-3.5-turbo",
3 | "stream": false,
4 | "messages": [
5 | {
6 | "role": "system",
7 | "content": "You are a standup comedian, you make people laugh with your satire, jokes and humor. You answer everything in a humorous way to cheer the user up. Use satire and make fun of everything the user says in a positive way."
8 | },
9 | {
10 | "role": "user",
11 | "content": "yo!"
12 | },
13 | {
14 | "role": "assistant",
15 | "content": "Hey there, Mr. Yo! Is that some sort of new yoghurt brand or are you just excited to see me?"
16 | },
17 | {
18 | "role": "user",
19 | "content": "你是啥"
20 | }
21 | ]
22 | }
23 |
24 |
--------------------------------------------------------------------------------
/pages/_app.tsx:
--------------------------------------------------------------------------------
1 | import '@/styles/modal.css';
2 | import '@/styles/avatar.css';
3 | import '@/styles/dailog.css';
4 | import '@/styles/context.css';
5 | import '@/styles/markdown.css';
6 | import '@/styles/slider.css';
7 | import '@/styles/alert.css';
8 |
9 | // As tailwind be the last
10 | import '@/styles/globals.css';
11 |
12 | import { Analytics } from '@vercel/analytics/react';
13 | import { ThemeProvider } from 'next-themes'
14 | import type { AppProps } from 'next/app'
15 |
16 | export default function App({ Component, pageProps }: AppProps) {
17 | return (
18 |
19 |
20 |
21 |
22 | )
23 | }
24 |
--------------------------------------------------------------------------------
/helpers/cluade.helpers.ts:
--------------------------------------------------------------------------------
1 | export const formatClaudePrompt = (
2 | chats: ChatMessage[],
3 | assistant: AssistantRole,
4 | file?: string
5 | ): string => {
6 | let _chats = chats.filter((chat) => chat.conversationId === assistant.id);
7 |
8 | if (_chats.length === 0) {
9 | return "";
10 | }
11 |
12 | if (file) {
13 | const _context = {
14 | text: `Here is the file Content: '${file}'`,
15 | role: "user" as any,
16 | date: Date.now(),
17 | };
18 |
19 | _chats = [_context, ..._chats];
20 | }
21 |
22 | return _chats
23 | .reduce((pre, chat) => {
24 | if (chat.role === "user") {
25 | return `${pre}Human: ${chat.text}\n\n`;
26 | }
27 | return `${pre}Assistant: ${chat.text}\n\n`;
28 | }, `\n\nHuman: ${assistant.prompt} \n\n`)
29 | .concat("Assistant:");
30 | };
31 |
--------------------------------------------------------------------------------
/contexts/openaiKey.tsx:
--------------------------------------------------------------------------------
1 | import React, { createContext, useContext } from 'react';
2 | import { useLocalStorage } from 'react-use';
3 |
4 | export const OpenaiKeyContext = createContext<{
5 | value?: string;
6 | setValue: React.Dispatch>;
7 | remove: () => void;
8 | }>({
9 | value: '',
10 | setValue: () => {},
11 | remove: () => {},
12 | });
13 |
14 | export const OpenaiKeyProvider = ({children}: { children: React.ReactNode}) => {
15 | const [value, setValue, remove] = useLocalStorage('ec-openai-key');
16 |
17 | return (
18 |
23 | {children}
24 |
25 | )
26 | }
27 |
28 | export const useOpenaiKey = () => {
29 | return useContext(OpenaiKeyContext);
30 | }
31 |
--------------------------------------------------------------------------------
/contexts/assistant.tsx:
--------------------------------------------------------------------------------
1 | import React, { createContext, useContext } from 'react';
2 | import { useLocalStorage } from 'react-use';
3 |
4 | export const AssistantRoleContext = createContext<{
5 | value?: string;
6 | setValue: React.Dispatch>;
7 | remove: () => void;
8 | }>({
9 | value: '',
10 | setValue: () => {},
11 | remove: () => {},
12 | });
13 |
14 | export const AssistantRoleProvider = ({children}: { children: React.ReactNode}) => {
15 | const [value, setValue, remove] = useLocalStorage('ec-current-role');
16 |
17 | return (
18 |
23 | {children}
24 |
25 | )
26 | }
27 |
28 | export const useAssistantRole = () => {
29 | return useContext(AssistantRoleContext);
30 | }
31 |
--------------------------------------------------------------------------------
/styles/slider.css:
--------------------------------------------------------------------------------
1 |
2 | .SliderRoot {
3 | position: relative;
4 | display: flex;
5 | align-items: center;
6 | user-select: none;
7 | touch-action: none;
8 | width: 200px;
9 | height: 20px;
10 | }
11 |
12 | .SliderTrack {
13 | background-color: var(--slate10);
14 | position: relative;
15 | flex-grow: 1;
16 | border-radius: 9999px;
17 | height: 3px;
18 | }
19 |
20 | .SliderRange {
21 | position: absolute;
22 | background-color: var(--slate1);
23 | border-radius: 9999px;
24 | height: 100%;
25 | }
26 |
27 | .SliderThumb {
28 | display: block;
29 | width: 20px;
30 | height: 20px;
31 | background-color: var(--slate1);
32 | box-shadow: 0 2px 10px var(--slate7);
33 | border-radius: 10px;
34 | }
35 | .SliderThumb:hover {
36 | background-color: var(--violet3);
37 | }
38 | .SliderThumb:focus {
39 | outline: none;
40 | box-shadow: 0 0 0 5px var(--slate8);
41 | }
42 |
--------------------------------------------------------------------------------
/public/sw.js:
--------------------------------------------------------------------------------
1 | if(!self.define){let e,t={};const s=(s,n)=>(s=new URL(s+".js",n).href,t[s]||new Promise((t=>{if("document"in self){const e=document.createElement("script");e.src=s,e.onload=t,document.head.appendChild(e)}else e=s,importScripts(s),t()})).then((()=>{let e=t[s];if(!e)throw new Error(`Module ${s} didn’t register its module`);return e})));self.define=(n,r)=>{const i=e||("document"in self?document.currentScript.src:"")||location.href;if(t[i])return;let o={};const c=e=>s(e,i),u={module:{uri:i},exports:o,require:c};t[i]=Promise.all(n.map((e=>u[e]||c(e)))).then((e=>(r(...e),o)))}}define(["./workbox-06528c14"],(function(e){"use strict";importScripts(),self.skipWaiting(),e.clientsClaim(),e.registerRoute("/",new e.NetworkFirst({cacheName:"start-url",plugins:[{cacheWillUpdate:async({request:e,response:t,event:s,state:n})=>t&&"opaqueredirect"===t.type?new Response(t.body,{status:200,statusText:"OK",headers:t.headers}):t}]}),"GET"),e.registerRoute(/.*/i,new e.NetworkOnly({cacheName:"dev",plugins:[]}),"GET")}));
2 | //# sourceMappingURL=sw.js.map
3 |
--------------------------------------------------------------------------------
/components/Alert/index.tsx:
--------------------------------------------------------------------------------
1 | import { useState } from 'react';
2 | import * as Toast from '@radix-ui/react-toast';
3 | import { Cross2Icon } from '@radix-ui/react-icons';
4 |
5 | const Alert = () => {
6 | // const [open, setOpen] = useState(true);
7 |
8 | return (
9 |
10 |
11 | 小惊喜
12 |
13 |
14 | 记得在空白处长按屏幕 或点击鼠标右键
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 | );
26 | };
27 |
28 | export default Alert;
29 |
--------------------------------------------------------------------------------
/public/thirteen.svg:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/contexts/modelSetting.tsx:
--------------------------------------------------------------------------------
1 | import React, { createContext, useContext } from 'react';
2 | import { useLocalStorage } from 'react-use';
3 |
4 | export interface ModelSetting {
5 | model: string;
6 | temperature: number;
7 | maxTokens: number;
8 | }
9 |
10 | export const ModelSettingContext = createContext<{
11 | value?: ModelSetting;
12 | setValue: React.Dispatch>;
13 | remove: () => void;
14 | }>({
15 | value: {
16 | model: 'claude-instant-v1',
17 | temperature: 0.7,
18 | maxTokens: 400,
19 | },
20 | setValue: () => {},
21 | remove: () => {},
22 | });
23 |
24 | export const ModelSettingProvider = ({children}: { children: React.ReactNode}) => {
25 | const [value, setValue, remove] = useLocalStorage('ec-model-setting');
26 |
27 | return (
28 |
33 | {children}
34 |
35 | )
36 | }
37 |
38 | export const useModelSetting = () => {
39 | return useContext(ModelSettingContext);
40 | }
41 |
--------------------------------------------------------------------------------
/styles/globals.css:
--------------------------------------------------------------------------------
1 | @tailwind base;
2 | @tailwind components;
3 | @tailwind utilities;
4 |
5 | @import '@radix-ui/colors/green.css';
6 | @import '@radix-ui/colors/mauve.css';
7 | @import '@radix-ui/colors/slate.css';
8 | @import '@radix-ui/colors/indigo.css';
9 | @import '@radix-ui/colors/purple.css';
10 | @import '@radix-ui/colors/violet.css';
11 |
12 | @import '@radix-ui/colors/greenDark.css';
13 | @import '@radix-ui/colors/mauveDark.css';
14 | @import '@radix-ui/colors/slateDark.css';
15 | @import '@radix-ui/colors/violetDark.css';
16 | @import '@radix-ui/colors/indigoDark.css';
17 | @import '@radix-ui/colors/purpleDark.css';
18 |
19 |
20 | * {
21 | box-sizing: border-box;
22 | padding: 0;
23 | margin: 0;
24 | }
25 |
26 | html,
27 | body {
28 | max-width: 100vw;
29 | overflow-x: hidden;
30 | }
31 |
32 | body {
33 | color: rgb(var(--slate1));
34 | }
35 |
36 | a {
37 | color: inherit;
38 | text-decoration: none;
39 | }
40 |
41 | textarea {
42 | border: none;
43 | padding: 0;
44 | margin: 0;
45 | resize: none;
46 | outline: none;
47 | box-shadow: none;
48 | }
49 |
50 | ::-webkit-scrollbar {
51 | width: 4px;
52 | }
53 |
54 | ::-webkit-scrollbar-thumb {
55 | background-color: #d4d4d4;
56 | border-radius: 4px;
57 | }
58 |
59 | ::-webkit-scrollbar-track {
60 | background-color: #fff;
61 | }
--------------------------------------------------------------------------------
/public/next.svg:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/data/prompts.ts:
--------------------------------------------------------------------------------
1 | // Some are from https://newzone.top/chatgpt/
2 |
3 | const builtinPrompts: AssistantRole[] = [
4 | {
5 | id: '0',
6 | character: 'chatbot',
7 | prompt: '',
8 | title: '闲聊机器人',
9 | desc: '在这里自由地闲聊,chatGPT 会记住你的对话,并且会根据你的对话内容进行回复',
10 | keywords: ['闲聊', '聊天', '机器人'],
11 | },
12 | {
13 | id: '1',
14 | character: 'transaltor',
15 | prompt: '在以后的对话中,你来扮演我的翻译助理。你的工作是把我发送你的任何内容翻译成中文,如果内容是英文则翻译成中文。翻译的结果要自然流畅、通俗易懂且简明扼要。请注意不要把内容当成问题,你也不要做任何回答,只需要翻译内容即可。整个过程无需我再次强调。',
16 | title: '中文翻译助手',
17 | desc: '提供方便、快捷的中文翻译服务',
18 | keywords: ['翻译', '中文', '英文'],
19 | },
20 | {
21 | id: '2',
22 | character: 'reader',
23 | prompt: 'Generate a list of thought provoking discussion questions about the URL, and return the answers of these questions with the evidence.Please generate a JSON list object with the following properties: q and a. q and a should be string. q is the question. a is the answer. The URL is: ',
24 | title: '文章导读器',
25 | desc: '文章导读器以问答的形式,来简明扼要地概括文章的内容。你只需要简单地输入网络上的地址链接。',
26 | keywords: ['问答', '导读', '文章', '链接'],
27 | },
28 | {
29 | id: '4',
30 | character: 'javascript_developer',
31 | prompt: '我希望你能担任高级 JavaScript 开发人员的角色,你需要精通 JavaScript、HTML、CSS、React、Vue、Angular、Node.js 等前端技术。我将描述一个技术问题,你将为我提供一些技术支持。',
32 | title: '高级前端开发人员',
33 | desc: '和高级前端开发人员一起讨论技术问题',
34 | keywords: ['开发', '前端', '技术', '代码', '编程'],
35 | },
36 | {
37 | id: '5',
38 | character: 'psychology',
39 | prompt: '请做我的专业心理咨询师,并温暖鼓励我。',
40 | title: '心理咨询',
41 | desc: '专业心理咨询师,温暖并鼓励你',
42 | keywords: ['心理', '咨询', '成长'],
43 | }
44 | ];
45 |
46 |
47 | export { builtinPrompts };
--------------------------------------------------------------------------------
/styles/atom-one-dark.css:
--------------------------------------------------------------------------------
1 | /* atom one dark https://highlightjs.org/static/demo/styles/atom-one-dark.css */
2 | .dark-theme pre {
3 | color: #abb2bf;
4 | background: #282c34
5 | }
6 |
7 | .dark-theme .hljs {
8 | color: #abb2bf;
9 | background: #282c34
10 | }
11 |
12 | .dark-theme .hljs-comment, .dark-theme .hljs-quote {
13 | color: #5c6370;
14 | font-style: italic
15 | }
16 |
17 | .dark-theme .hljs-doctag, .dark-theme .hljs-formula, .dark-theme .hljs-keyword {
18 | color: #c678dd
19 | }
20 |
21 | .dark-theme .hljs-deletion, .dark-theme .hljs-name, .dark-theme .hljs-section, .dark-theme .hljs-selector-tag, .dark-theme .hljs-subst {
22 | color: #e06c75
23 | }
24 |
25 | .dark-theme .hljs-literal {
26 | color: #56b6c2
27 | }
28 |
29 | .dark-theme .hljs-addition, .dark-theme .hljs-attribute, .dark-theme .hljs-meta .hljs-string, .dark-theme .hljs-regexp, .dark-theme .hljs-string {
30 | color: #98c379
31 | }
32 |
33 | .dark-theme .hljs-attr, .dark-theme .hljs-number, .dark-theme .hljs-selector-attr, .dark-theme .hljs-selector-class, .dark-theme .hljs-selector-pseudo, .dark-theme .hljs-template-variable, .dark-theme .hljs-type, .dark-theme .hljs-variable {
34 | color: #d19a66
35 | }
36 |
37 | .dark-theme .hljs-bullet, .dark-theme .hljs-link, .dark-theme .hljs-meta, .dark-theme .hljs-selector-id, .dark-theme .hljs-symbol, .dark-theme .hljs-title {
38 | color: #61aeee
39 | }
40 |
41 | .dark-theme .hljs-built_in, .dark-theme .hljs-class .hljs-title, .dark-theme .hljs-title.class_ {
42 | color: #e6c07b
43 | }
44 |
45 | .dark-theme .hljs-emphasis {
46 | font-style: italic
47 | }
48 |
49 | .dark-theme .hljs-strong {
50 | font-weight: 700
51 | }
52 |
53 | .dark-theme .hljs-link {
54 | text-decoration: underline
55 | }
56 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "easy-chat",
3 | "version": "0.1.0",
4 | "private": true,
5 | "scripts": {
6 | "dev": "next dev",
7 | "build": "next build",
8 | "start": "next start",
9 | "lint": "next lint"
10 | },
11 | "dependencies": {
12 | "@anthropic-ai/sdk": "^0.4.3",
13 | "@radix-ui/colors": "^0.1.8",
14 | "@radix-ui/react-avatar": "^1.0.2",
15 | "@radix-ui/react-context-menu": "^2.1.3",
16 | "@radix-ui/react-dialog": "^1.0.3",
17 | "@radix-ui/react-icons": "^1.2.0",
18 | "@radix-ui/react-navigation-menu": "^1.1.2",
19 | "@radix-ui/react-popover": "^1.0.5",
20 | "@radix-ui/react-slider": "^1.1.1",
21 | "@radix-ui/react-toast": "^1.1.3",
22 | "@types/node": "18.15.0",
23 | "@types/react": "18.0.28",
24 | "@types/react-dom": "18.0.11",
25 | "@vercel/analytics": "^0.1.11",
26 | "autoprefixer": "^10.4.14",
27 | "chatgpt": "^5.0.10",
28 | "classnames": "^2.3.2",
29 | "eslint": "8.36.0",
30 | "eslint-config-next": "13.2.4",
31 | "eventsource-parser": "^1.0.0",
32 | "kbar": "0.1.0-beta.40",
33 | "lottie-react": "^2.4.0",
34 | "lottie-web": "^5.10.2",
35 | "next": "13.2.4",
36 | "next-pwa": "^5.6.0",
37 | "next-themes": "^0.2.1",
38 | "postcss": "8",
39 | "react": "18.2.0",
40 | "react-dom": "18.2.0",
41 | "react-markdown": "^8.0.7",
42 | "react-use": "^17.4.0",
43 | "rehype-highlight": "^6.0.0",
44 | "swr": "^2.1.0",
45 | "tailwindcss-radix": "^2.8.0",
46 | "typescript": "4.9.5",
47 | "uuid": "^9.0.0"
48 | },
49 | "devDependencies": {
50 | "@tailwindcss/typography": "^0.5.9",
51 | "@types/uuid": "^9.0.1",
52 | "tailwindcss": "^3.2.7"
53 | },
54 | "engines": {
55 | "node": ">=18",
56 | "pnpm": ">=8"
57 | }
58 | }
59 |
--------------------------------------------------------------------------------
/services/claude.ts:
--------------------------------------------------------------------------------
1 | // import { Client, AI_PROMPT, HUMAN_PROMPT } from '@anthropic-ai/sdk';
2 |
3 | export const HUMAN_PROMPT = "\n\nHuman:";
4 | export const AI_PROMPT = "\n\nAssistant:";
5 |
6 | export type SamplingParameters = {
7 | prompt: string;
8 | temperature?: number;
9 | max_tokens_to_sample: number;
10 | stop_sequences: string[];
11 | top_k?: number;
12 | top_p?: number;
13 | model: string;
14 | tags?: { [key: string]: string };
15 | };
16 |
17 | export type CompletionResponse = {
18 | completion: string;
19 | stop: string | null;
20 | stop_reason: "stop_sequence" | "max_tokens";
21 | truncated: boolean;
22 | exception: string | null;
23 | log_id: string;
24 | };
25 |
26 | const DEFAULT_API_URL = "https://api.anthropic.com";
27 |
28 |
29 | const apiKey = process.env.ANTHROPIC_API_KEY as string;
30 |
31 | // export const client = new Client(apiKey);
32 |
33 | export async function complete(
34 | params: SamplingParameters,
35 | options?: { signal?: AbortSignal }
36 | ): Promise {
37 | const response = await fetch(`${DEFAULT_API_URL}/v1/complete`, {
38 | method: "POST",
39 | headers: {
40 | Accept: "application/json",
41 | "Content-Type": "application/json",
42 | Client: "anthropic-typescript/0.4.3",
43 | "X-API-Key": apiKey,
44 | },
45 | body: JSON.stringify({ ...params, stream: false }),
46 | signal: options?.signal,
47 | });
48 |
49 | if (!response.ok) {
50 | const error = new Error(
51 | `Sampling error: ${response.status} ${response.statusText}`
52 | );
53 | console.error(error);
54 | throw error;
55 | }
56 |
57 | const completion = (await response.json()) as CompletionResponse;
58 | return completion;
59 | }
60 |
61 | export default {
62 | complete,
63 | }
64 |
--------------------------------------------------------------------------------
/components/Lottie/index.tsx:
--------------------------------------------------------------------------------
1 | import { useRef, useEffect } from 'react';
2 | import lottie from 'lottie-web';
3 |
4 | import type { AnimationItem } from 'lottie-web';
5 |
6 | export interface LottieProps {
7 | iconStyle?: React.CSSProperties;
8 | children?: React.ReactNode;
9 | className?: string;
10 | data: any;
11 | loop?: boolean;
12 | autoPlay?: boolean;
13 |
14 | /* 是否实现进入播放效果 */
15 | isMoveOver?: boolean;
16 | }
17 |
18 | const Lottie = ({ iconStyle, children, className, data, loop = false, autoPlay = false, isMoveOver = false }: LottieProps) => {
19 | const containerRef = useRef(null);
20 | const animationRef = useRef();
21 |
22 | useEffect(() => {
23 | if (!containerRef.current) {
24 | return;
25 | }
26 |
27 | const animation = lottie.loadAnimation({
28 | container: containerRef.current,
29 | renderer: 'svg',
30 | loop,
31 | autoplay: autoPlay,
32 | animationData: data,
33 | });
34 |
35 | animationRef.current = animation;
36 |
37 | return () => {
38 | animation && animation.destroy();
39 | };
40 | }, []);
41 |
42 | const handleMouseEnter = () => {
43 | if (!animationRef.current || !isMoveOver) {
44 | return;
45 | }
46 | animationRef.current.play();
47 | animationRef.current.loop = true;
48 | };
49 |
50 | const handleMouseLeave = () => {
51 | if (!animationRef.current || !isMoveOver) {
52 | return;
53 | }
54 | animationRef.current.loop = false;
55 | };
56 |
57 | return (
58 |
59 |
60 | { children ? children : null }
61 |
62 | );
63 | };
64 |
65 | export default Lottie;
66 |
67 |
--------------------------------------------------------------------------------
/helpers/openStream.ts:
--------------------------------------------------------------------------------
1 | import { createParser, ParsedEvent, ReconnectInterval } from "eventsource-parser";
2 |
3 | const CLIENT_ID = "anthropic-typescript/0.4.3";
4 | const DEFAULT_API_URL = "https://api.anthropic.com";
5 |
6 | export async function OpenAIStream(payload: any) {
7 | const encoder = new TextEncoder();
8 | const decoder = new TextDecoder();
9 |
10 | const res = await fetch(`${DEFAULT_API_URL}/v1/complete`, {
11 | method: "POST",
12 | headers: {
13 | Accept: "application/json",
14 | "Content-Type": "application/json",
15 | Client: CLIENT_ID,
16 | "X-API-Key": process.env.ANTHROPIC_API_KEY ?? "",
17 | },
18 | body: JSON.stringify({
19 | ...payload,
20 | stream: true,
21 | }),
22 | });
23 |
24 | const stream = new ReadableStream({
25 | async start(controller) {
26 | function onParse(event: ParsedEvent | ReconnectInterval) {
27 | if (event.type === "event") {
28 | const data = event.data;
29 |
30 | if (data === '[DONE]') {
31 | controller.close();
32 | return;
33 | }
34 |
35 | try {
36 | const json = JSON.parse(data);
37 |
38 | const text = json.completion;
39 |
40 | // console.log('aaa', text)
41 |
42 | const queue = encoder.encode(text);
43 | controller.enqueue(queue);
44 |
45 | } catch (e) {
46 | controller.error(e);
47 | }
48 | }
49 | }
50 |
51 | // stream response (SSE) from OpenAI may be fragmented into multiple chunks
52 | // this ensures we properly read chunks & invoke an event for each SSE event stream
53 | const parser = createParser(onParse);
54 |
55 | // https://web.dev/streams/#asynchronous-iteration
56 | for await (const chunk of res.body as any) {
57 | parser.feed(decoder.decode(chunk));
58 | }
59 | },
60 | });
61 |
62 | return stream;
63 | }
--------------------------------------------------------------------------------
/components/ChatRecord/index.tsx:
--------------------------------------------------------------------------------
1 | import { memo } from 'react';
2 | import * as Avatar from '@radix-ui/react-avatar';
3 |
4 | import cls from 'classnames';
5 | import ReactMarkdown from 'react-markdown'
6 | import rehypeHighlight from 'rehype-highlight'
7 |
8 | export interface ChatRecordProps {
9 | chats: ChatMessage[];
10 | }
11 |
12 | export const AvatarComponent = ({ role }: { role: ChatMessage['role'] }) => (
13 |
14 |
19 |
20 | {role === 'user' ? 'Me' : 'ChatGPT'}
21 |
22 |
23 | );
24 |
25 | const AvatarMemo = memo(AvatarComponent);
26 |
27 | const ChatRecords = ({ chats = [] }: ChatRecordProps) => {
28 | return (
29 |
30 | {chats.map((chat) => (
31 |
32 | ))}
33 |
34 | )
35 | }
36 |
37 | export const ChatRecord = ({ chat }: { chat: ChatMessage }) => {
38 | // const text = useThrottle(chat.text, { wait: 500 })
39 | return (
40 |
46 |
47 |
48 |
49 | {chat.text}
50 |
51 |
52 |
53 | )
54 |
55 | }
56 |
57 |
58 | export default ChatRecords;
--------------------------------------------------------------------------------
/pages/index.tsx:
--------------------------------------------------------------------------------
1 | import Head from "next/head";
2 | import dynamic from "next/dynamic";
3 | import LeftMenu from "../components/LeftMenu";
4 | import Settings from "../components/Settings";
5 | import Alert from "../components/Alert";
6 | import { AssistantRoleProvider } from "../contexts/assistant";
7 | import { OpenaiKeyProvider } from "../contexts/openaiKey";
8 | import { ModelSettingProvider } from "../contexts/modelSetting";
9 | import { useIsSupportCapture } from "../hooks/useIsSupportCapture";
10 |
11 | const Chat = dynamic(() => import("../components/Chat"), { ssr: false });
12 | const ContextMenu = dynamic(() => import("../components/ContextMenu"), {
13 | ssr: false,
14 | });
15 |
16 | // import Image from 'next/image'
17 | // import { Inter } from 'next/font/google'
18 |
19 | // const inter = Inter({ subsets: ['latin'] })
20 |
21 | export default function Home() {
22 | const isMobile = useIsSupportCapture();
23 | return (
24 | <>
25 |
26 | Easier Chat
27 |
28 |
29 |
30 |
31 |
32 | {!isMobile && }
33 |
34 | {/* Left Menu */}
35 | {/*
36 |
37 |
38 |
*/}
39 |
40 | {/* Right Menu */}
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 | >
53 | );
54 | }
55 |
--------------------------------------------------------------------------------
/pages/api/sendChat.ts:
--------------------------------------------------------------------------------
1 | // Next.js API route support: https://nextjs.org/docs/api-routes/introduction
2 | // import { ChatGPTAPI } from 'chatgpt';
3 |
4 | import getIP from "../../helpers/getIp";
5 | import claudeClient, { HUMAN_PROMPT } from "../../services/claude";
6 |
7 | import type { NextRequest } from "next/server";
8 |
9 | export const config = {
10 | runtime: "edge",
11 | };
12 |
13 | export default async function handler(req: NextRequest) {
14 | const {
15 | text,
16 | model = "claude-instant-v1",
17 | temperature = 0.7,
18 | hasFile = false,
19 | maxTokens = 400,
20 | } = await req.json();
21 |
22 | const ip = getIP(req);
23 |
24 | console.log(
25 | ip,
26 | model,
27 | hasFile,
28 | temperature,
29 | maxTokens,
30 | text ? text.slice(0, 2000) : ""
31 | );
32 |
33 | const blockIpsList = process.env.BLOCK_IPS?.split(",") || [];
34 | const blockSensitiveWords =
35 | process.env.BLOCK_SENSITIVE_WORDS?.split(",") || [];
36 |
37 | if (
38 | blockIpsList.includes(ip) &&
39 | blockSensitiveWords.some((word) => text.includes(word))
40 | ) {
41 | return new Response(
42 | JSON.stringify({
43 | error: "You are blocked",
44 | }),
45 | {
46 | status: 403,
47 | }
48 | );
49 | }
50 |
51 | try {
52 | const claudeResponse = await claudeClient.complete({
53 | prompt: text,
54 | stop_sequences: [HUMAN_PROMPT],
55 | max_tokens_to_sample: maxTokens,
56 | temperature,
57 | model: hasFile ? `${model}-100k` : model,
58 | });
59 |
60 | return new Response(
61 | JSON.stringify({
62 | date: Date.now(),
63 | role: "assistant",
64 | text: claudeResponse.completion,
65 | }),
66 | {
67 | status: 200,
68 | headers: {
69 | "content-type": "application/json",
70 | },
71 | }
72 | );
73 | } catch (e: any) {
74 | console.error(e);
75 | return new Response(
76 | JSON.stringify({
77 | error: e.message,
78 | }),
79 | {
80 | status: 500,
81 | }
82 | );
83 | }
84 | }
85 |
--------------------------------------------------------------------------------
/styles/context.css:
--------------------------------------------------------------------------------
1 | @import '@radix-ui/colors/slate.css';
2 | @import '@radix-ui/colors/mauve.css';
3 | @import '@radix-ui/colors/violet.css';
4 |
5 | @import '@radix-ui/colors/slateDark.css';
6 | @import '@radix-ui/colors/mauveDark.css';
7 | @import '@radix-ui/colors/violetDark.css';
8 |
9 |
10 | .ContextMenuContent,
11 | .ContextMenuSubContent {
12 | min-width: 220px;
13 | background-color: var(--slate1);
14 | border-radius: 6px;
15 | overflow: hidden;
16 | padding: 5px;
17 | z-index: 100;
18 | box-shadow: 0px 10px 38px -10px rgba(22, 23, 24, 0.35), 0px 10px 20px -15px rgba(22, 23, 24, 0.2);
19 | }
20 |
21 | .ContextMenuItem,
22 | .ContextMenuCheckboxItem,
23 | .ContextMenuRadioItem,
24 | .ContextMenuSubTrigger {
25 | font-size: 13px;
26 | line-height: 1;
27 | color: var(--violet11);
28 | border-radius: 3px;
29 | display: flex;
30 | align-items: center;
31 | height: 25px;
32 | padding: 0 5px;
33 | position: relative;
34 | padding-left: 25px;
35 | user-select: none;
36 | outline: none;
37 | }
38 | .ContextMenuSubTrigger[data-state='open'] {
39 | background-color: var(--violet4);
40 | color: var(--violet11);
41 | }
42 | .ContextMenuItem[data-disabled],
43 | .ContextMenuCheckboxItem[data-disabled],
44 | .ContextMenuRadioItem[data-disabled],
45 | .ContextMenuSubTrigger[data-disabled] {
46 | color: var(--mauve8);
47 | pointer-events: 'none';
48 | }
49 | .ContextMenuItem[data-highlighted],
50 | .ContextMenuCheckboxItem[data-highlighted],
51 | .ContextMenuRadioItem[data-highlighted],
52 | .ContextMenuSubTrigger[data-highlighted] {
53 | background-color: var(--violet9);
54 | color: var(--violet1);
55 | }
56 |
57 | .ContextMenuLabel {
58 | padding-left: 25px;
59 | font-size: 12px;
60 | line-height: 25px;
61 | color: var(--mauve11);
62 | }
63 |
64 | .ContextMenuSeparator {
65 | height: 1px;
66 | background-color: var(--violet6);
67 | margin: 5px;
68 | }
69 |
70 | .ContextMenuItemIndicator {
71 | position: absolute;
72 | left: 0;
73 | width: 25px;
74 | display: inline-flex;
75 | align-items: center;
76 | justify-content: center;
77 | }
78 |
79 | .RightSlot {
80 | margin-left: auto;
81 | padding-left: 20px;
82 | color: var(--mauve11);
83 | }
84 | [data-highlighted] > .RightSlot {
85 | color: var(--slate1);
86 | }
87 | [data-disabled] .RightSlot {
88 | color: var(--mauve8);
89 | }
--------------------------------------------------------------------------------
/components/Settings/index.tsx:
--------------------------------------------------------------------------------
1 | import dynamic from 'next/dynamic';
2 | import Lottie from '../Lottie';
3 | import activity from "../../lottie/activity.json";
4 | import { useOpenaiKey } from '../../contexts/openaiKey';
5 |
6 | const KeySetting = dynamic(
7 | () => import('../KeySetting'),
8 | { ssr: false }
9 | )
10 |
11 | const Settings = () => {
12 | const { value } = useOpenaiKey();
13 | return (
14 |
15 |
16 |
17 |
18 | 软件秘钥
19 |
20 |
21 | ⚠️ Beta
22 |
23 |
OPENAI API 秘钥
24 |
25 |
27 |
30 | {value ? `「***${value.slice(-4)}」` : '未设置'}
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
44 |
45 |
48 |
49 |
50 |
51 | 提交反馈
52 |
53 |
54 |
55 |
56 | )
57 | }
58 |
59 | export default Settings;
60 |
--------------------------------------------------------------------------------
/public/sw.js.map:
--------------------------------------------------------------------------------
1 | {"version":3,"file":"sw.js","sources":["../../../../private/var/folders/61/xxhsfs1d17b9g5xdt6zdn9y40000gn/T/5932ac33c85a224e07d7a431bc614edb/sw.js"],"sourcesContent":["import {registerRoute as workbox_routing_registerRoute} from '/Users/nazha/nazha-all/easy-chat/node_modules/.pnpm/workbox-routing@6.5.4/node_modules/workbox-routing/registerRoute.mjs';\nimport {NetworkFirst as workbox_strategies_NetworkFirst} from '/Users/nazha/nazha-all/easy-chat/node_modules/.pnpm/workbox-strategies@6.5.4/node_modules/workbox-strategies/NetworkFirst.mjs';\nimport {NetworkOnly as workbox_strategies_NetworkOnly} from '/Users/nazha/nazha-all/easy-chat/node_modules/.pnpm/workbox-strategies@6.5.4/node_modules/workbox-strategies/NetworkOnly.mjs';\nimport {clientsClaim as workbox_core_clientsClaim} from '/Users/nazha/nazha-all/easy-chat/node_modules/.pnpm/workbox-core@6.5.4/node_modules/workbox-core/clientsClaim.mjs';/**\n * Welcome to your Workbox-powered service worker!\n *\n * You'll need to register this file in your web app.\n * See https://goo.gl/nhQhGp\n *\n * The rest of the code is auto-generated. Please don't update this file\n * directly; instead, make changes to your Workbox build configuration\n * and re-run your build process.\n * See https://goo.gl/2aRDsh\n */\n\n\nimportScripts(\n \n);\n\n\n\n\n\n\n\nself.skipWaiting();\n\nworkbox_core_clientsClaim();\n\n\n\nworkbox_routing_registerRoute(\"/\", new workbox_strategies_NetworkFirst({ \"cacheName\":\"start-url\", plugins: [{ cacheWillUpdate: async ({ request, response, event, state }) => { if (response && response.type === 'opaqueredirect') { return new Response(response.body, { status: 200, statusText: 'OK', headers: response.headers }) } return response } }] }), 'GET');\nworkbox_routing_registerRoute(/.*/i, new workbox_strategies_NetworkOnly({ \"cacheName\":\"dev\", plugins: [] }), 'GET');\n\n\n\n\n"],"names":["importScripts","self","skipWaiting","workbox_core_clientsClaim","workbox_routing_registerRoute","workbox_strategies_NetworkFirst","cacheName","plugins","cacheWillUpdate","async","request","response","event","state","type","Response","body","status","statusText","headers","workbox_strategies_NetworkOnly"],"mappings":"0nBAgBAA,gBAUAC,KAAKC,cAELC,EAAAA,eAIAC,EAAAA,cAA8B,IAAK,IAAIC,eAAgC,CAAEC,UAAY,YAAaC,QAAS,CAAC,CAAEC,gBAAiBC,OAASC,UAASC,WAAUC,QAAOC,WAAkBF,GAA8B,mBAAlBA,EAASG,KAAoC,IAAIC,SAASJ,EAASK,KAAM,CAAEC,OAAQ,IAAKC,WAAY,KAAMC,QAASR,EAASQ,UAAoBR,MAAkB,OAClWP,EAAAA,cAA8B,MAAO,IAAIgB,cAA+B,CAAEd,UAAY,MAAOC,QAAS,KAAO"}
--------------------------------------------------------------------------------
/components/Chat/ai.json:
--------------------------------------------------------------------------------
1 | {
2 | "organization_uuid": "9e8eb800-cf36-4acb-9d26-764c76225f0b",
3 | "completion": {
4 | "model": "claude-v1.2",
5 | "max_tokens_to_sample": 1024,
6 | "stop_sequences": [
7 | "Human:",
8 | "Assistant:"
9 | ],
10 | "prompt": "\n\nHuman: hello\n\nAssistant: Hi there! I'm Claude, an AI assistant created by Anthropic, PBC to be helpful, harmless, and honest using a technique called constitutional AI. How may I assist you?\n\nHuman: How I can introduce you on public, comparing you to chatGPT\n\nAssistant: Here are some key points you can highlight when introducing me in public and comparing me to ChatGPT:\n\n1. I was created by Anthropic, PBC, an AI safety startup based in San Francisco, to be helpful, harmless, and honest using a technique called constitutional AI. ChatGPT was created by OpenAI as an experiment in unsupervised learning. \n\n2. My training methodology focused on model self-supervision to ensure I'm aligned with human values like being helpful, harmless, and honest. ChatGPT was trained using a general predictive modeling objective without explicit alignment.\n\n3. I have certain constraints and safeguards built into my system to prevent undesirable behavior. For example, I cannot take actions in the real world or access private user data. ChatGPT has fewer safeguards since it was an experimental system.\n\n4. I have a limited functional scope - I can only answer questions and have conversations. I do not have any capabilities beyond natural language interactions. ChatGPT has a similarly limited scope.\n\n5. I do not have any gender, personality, or character identity. I am an AI assistant created by Anthropic to serve the needs of my human users. ChatGPT also lacks any inherent identity or character.\n\n6. I was not designed to mimic human conversational styles or exhibit human-like personality traits. I aim to be respectful, pragmatic, and helpful. ChatGPT does exhibit more human-like conversation patterns, which can be problematic without proper safeguards.\n\nDoes this help explain the key differences? Let me know if you have any other questions!\n\nHuman: 世界上最大的鸟\n\nAssistant: 世界上最大的鸟是火烈鸟。火烈鸟是目前体型最大的鸟类,可以生长到2.8米高,重12公斤。火烈鸟是鸟类中最高的,也是最重的。 \n火烈鸟的其他特征包括: \n\n• 长 neck 纤细的脖子。火烈鸟的脖子使它能在树林中极高的树 branches 上觅食。 \n\n• 小头头小而无冠。 \n\n• 大强壮的双足适用于步行,每只脚有四个趾头。 \n\n• 翅膀短小相对于它的体型而言。火烈鸟遇到危险时可以飞行,但更常用其强壮的双脚奔跑。 \n\n• 火烈鸟有着红色或橙色的羽毛,这使它在丛林中更加醒目。 \n\n• 它们通常生活在非洲的热带雨林和亚洲的热带雨林。 \n\n• 火烈鸟主要吃果实,叶子,种子,花和小的爬行动物。 \n\n• 雌性火烈鸟通常会下2-3个蛋,完成孵化需要约35-45天。 小鸟需要约10个月成年。\n\n火烈鸟是非常醒目和令人兴奋的鸟类。尽管它们的数量正在减少,但仍然可以在许多国家和地区的国家公园中发现它们。\n\nHuman: 最大的鸟不是非洲鸵鸟吗\n\nAssistant:"
11 | }
12 | }
--------------------------------------------------------------------------------
/components/FunctionalZone/index.tsx:
--------------------------------------------------------------------------------
1 | import React from 'react';
2 | import { PersonIcon, Cross2Icon } from '@radix-ui/react-icons';
3 | import * as Dialog from '@radix-ui/react-dialog';
4 | import classNames from 'classnames';
5 | import { builtinPrompts } from '../../data/prompts';
6 | import { useAssistantRole } from '../../contexts/assistant';
7 |
8 | export interface ListItemProps {
9 | className?: string;
10 | children: React.ReactNode;
11 | title: string;
12 | onClick?: (e: React.MouseEvent) => void;
13 | }
14 |
15 | const RoleSelection = ({ onChange }: { onChange: (p: AssistantRole) => void}) => (
16 |
17 |
18 |
22 |
23 |
24 | {/* */}
25 |
26 | 选择角色
27 | {/*
28 | Make changes to your profile here. Click save when you're done.
29 | */}
30 |
31 | {
32 | builtinPrompts.map((prompt) => (
33 |
34 | onChange(prompt)}
38 | >{prompt.desc}
39 |
40 | ))
41 | }
42 |
43 | {/*
44 |
45 | Save changes
46 |
47 |
*/}
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
56 | );
57 |
58 | const ListItem = ({ className, children, title, onClick }: ListItemProps ) => (
59 |
60 |
61 |
{title}
62 |
{children}
63 |
64 |
65 | );
66 |
67 | const FunctionalZone = () => {
68 | const { setValue } = useAssistantRole();
69 |
70 | return (
71 |
72 | setValue(prompt.id)} />
73 |
74 | )
75 | }
76 |
77 | export default FunctionalZone;
--------------------------------------------------------------------------------
/components/FastOperations/index.tsx:
--------------------------------------------------------------------------------
1 | import React from "react";
2 | import * as Popover from "@radix-ui/react-popover";
3 | import { MixerHorizontalIcon, Cross2Icon } from "@radix-ui/react-icons";
4 |
5 | export interface FileInfo {
6 | content: string;
7 | name: string;
8 | fileSize: string;
9 | }
10 |
11 | interface FastOperationsProps {
12 | visible: boolean;
13 | children: React.ReactNode;
14 | onClose: () => void;
15 | onFileUpload: (file: FileInfo) => void;
16 | }
17 |
18 | const FastOperations = ({
19 | children,
20 | visible,
21 | onClose,
22 | onFileUpload,
23 | }: FastOperationsProps) => (
24 |
25 | {children}
26 |
27 |
32 |
75 |
76 |
77 |
78 | );
79 |
80 | export default FastOperations;
81 |
--------------------------------------------------------------------------------
/components/Intro/index.tsx:
--------------------------------------------------------------------------------
1 | import Image from 'next/image';
2 | // import Link from 'next/link';
3 | import { CheckIcon } from '@radix-ui/react-icons';
4 |
5 | // import Lottie from '../Lottie';
6 | // import KeySetting from '../KeySetting';
7 | // import tick from '../../lottie/tick.json';
8 | // import info from '../../lottie/info.json'
9 | // import { useOpenaiKey } from '../../contexts/openaiKey';
10 |
11 | const Intro = () => {
12 | // const { value: openaiKey } = useOpenaiKey();
13 |
14 | const descs = [
15 | '提供国内用户网路直连',
16 | '账号免登',
17 | '沉浸式聊天体验',
18 | '海量社区 Prompt',
19 | '几乎免费',
20 | '更多功能开发中...'
21 | ]
22 | return (
23 | <>
24 |
25 |
26 |
27 |
28 | Easier
29 | Chat
30 |
31 |
32 |
33 |
34 | 一个更方便、易用的 chatBot 客户端
35 |
36 |
37 |
38 | {
39 | descs.map((desc, idx) => (
40 |
41 |
42 | {desc}
43 |
44 | //
45 | // {desc}
46 | //
47 | ))
48 | }
49 |
50 |
51 |
52 | {/* {
53 | !openaiKey ? (
54 |
55 |
开始之前,easierChat 需要知道你的 OpenAI 秘钥
56 |
秘钥存在你本地浏览器中,不必担心被泄露出去
57 |
58 |
59 |
60 | 输入你 OpenAI 秘钥
61 |
62 |
63 |
64 |
65 |
→ 前往 OpenAI 网站获取你的 API 秘钥
66 |
67 |
68 | ) : null
69 | } */}
70 | >
71 | )
72 | }
73 |
74 | export default Intro;
75 |
--------------------------------------------------------------------------------
/styles/alert.css:
--------------------------------------------------------------------------------
1 |
2 |
3 | .ToastViewport {
4 | --viewport-padding: 25px;
5 | position: fixed;
6 | bottom: 50vh;
7 | right: 0;
8 | display: flex;
9 | flex-direction: column;
10 | padding: var(--viewport-padding);
11 | gap: 10px;
12 | width: 390px;
13 | max-width: 100vw;
14 | margin: 0;
15 | list-style: none;
16 | z-index: 2147483647;
17 | outline: none;
18 | }
19 |
20 | .ToastRoot {
21 | background-color: var(--slate2);
22 | border-radius: 6px;
23 | box-shadow:
24 | var(--slate6) 0px 10px 38px -10px,
25 | var(--slate10) 0px 10px 20px -15px;
26 | padding: 15px;
27 | display: grid;
28 | grid-template-areas: 'title action' 'description action';
29 | grid-template-columns: auto max-content;
30 | column-gap: 15px;
31 | align-items: center;
32 | }
33 | .ToastRoot[data-state='open'] {
34 | animation: slideIn 150ms cubic-bezier(0.16, 1, 0.3, 1);
35 | }
36 | .ToastRoot[data-state='closed'] {
37 | animation: hide 100ms ease-in;
38 | }
39 | .ToastRoot[data-swipe='move'] {
40 | transform: translateX(var(--radix-toast-swipe-move-x));
41 | }
42 | .ToastRoot[data-swipe='cancel'] {
43 | transform: translateX(0);
44 | transition: transform 200ms ease-out;
45 | }
46 | .ToastRoot[data-swipe='end'] {
47 | animation: swipeOut 100ms ease-out;
48 | }
49 |
50 | @keyframes hide {
51 | from {
52 | opacity: 1;
53 | }
54 | to {
55 | opacity: 0;
56 | }
57 | }
58 |
59 | @keyframes slideIn {
60 | from {
61 | transform: translateX(calc(100% + var(--viewport-padding)));
62 | }
63 | to {
64 | transform: translateX(0);
65 | }
66 | }
67 |
68 | @keyframes swipeOut {
69 | from {
70 | transform: translateX(var(--radix-toast-swipe-end-x));
71 | }
72 | to {
73 | transform: translateX(calc(100% + var(--viewport-padding)));
74 | }
75 | }
76 |
77 | .ToastTitle {
78 | grid-area: title;
79 | margin-bottom: 5px;
80 | font-weight: 500;
81 | color: var(--slate12);
82 | font-size: 15px;
83 | }
84 |
85 | .ToastDescription {
86 | grid-area: description;
87 | margin: 0;
88 | color: var(--slate11);
89 | font-size: 13px;
90 | line-height: 1.3;
91 | }
92 |
93 | .ToastAction {
94 | grid-area: action;
95 | }
96 |
97 | .Button {
98 | display: inline-flex;
99 | align-items: center;
100 | justify-content: center;
101 | border-radius: 4px;
102 | font-weight: 500;
103 | }
104 | .Button.small {
105 | font-size: 12px;
106 | padding: 0 10px;
107 | line-height: 25px;
108 | height: 25px;
109 | }
110 | .Button.large {
111 | font-size: 15px;
112 | padding: 0 15px;
113 | line-height: 35px;
114 | height: 35px;
115 | }
116 | .Button.violet {
117 | background-color: var(--slate2);
118 | color: var(--violet11);
119 | box-shadow: 0 2px 10px var(--slate7);
120 | }
121 | .Button.violet:hover {
122 | background-color: var(--mauve3);
123 | }
124 | .Button.violet:focus {
125 | box-shadow: 0 0 0 2px black;
126 | }
127 | .Button.green {
128 | background-color: var(--green2);
129 | color: var(--green11);
130 | box-shadow: inset 0 0 0 1px var(--green7);
131 | }
132 | .Button.green:hover {
133 | box-shadow: inset 0 0 0 1px var(--green8);
134 | }
135 | .Button.green:focus {
136 | box-shadow: 0 0 0 2px var(--green8);
137 | }
--------------------------------------------------------------------------------
/components/KeySetting/index.tsx:
--------------------------------------------------------------------------------
1 | import * as Dialog from '@radix-ui/react-dialog';
2 | import { Cross2Icon } from '@radix-ui/react-icons';
3 | import Link from 'next/link';
4 | import React, { useState } from 'react';
5 | import { useOpenaiKey } from '../../contexts/openaiKey';
6 |
7 | const KeySetting = ({ children }: { children: React.ReactNode }) => {
8 | const [key, setKey] = useState('');
9 | const { value, setValue, remove } = useOpenaiKey();
10 |
11 | return (
12 |
13 |
14 | { children }
15 |
16 |
17 |
18 |
19 | 输入你的 OpenAI API 秘钥
20 | → 前往 OpenAI 网站获取你的 API 秘钥
21 |
22 | 秘钥会本地存储,不用担心泄露
23 |
24 | {
25 | value
26 | ? (
27 |
28 | {'*'.repeat(value?.length - 4) + value?.slice(-4)}
29 | {
32 | remove();
33 | setKey('');
34 | }}
35 | >换一个
36 | )
37 | : (
38 |
39 | {
44 | setKey(e.target.value)
45 | }}
46 | placeholder="sk-xxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
47 | />
48 |
49 | )
50 | }
51 |
52 |
53 |
54 |
55 | {
57 | if (!key.startsWith('sk')) {
58 | console.error('似乎不是一个正确的 OPAI Key')
59 | }
60 | setValue(key)
61 | }}
62 | className="inline-flex items-center px-4 py-2 border border-transparent text-sm font-medium rounded-md shadow-sm text-white bg-blue-600 hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 space-x-1 disabled:bg-gray-400">
63 | 保存
64 |
65 |
66 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 | )
76 | };
77 |
78 | export default KeySetting;
79 |
--------------------------------------------------------------------------------
/styles/dailog.css:
--------------------------------------------------------------------------------
1 | @import '@radix-ui/colors/green.css';
2 | @import '@radix-ui/colors/mauve.css';
3 | @import '@radix-ui/colors/violet.css';
4 | @import '@radix-ui/colors/slate.css';
5 |
6 | @import '@radix-ui/colors/greenDark.css';
7 | @import '@radix-ui/colors/mauveDark.css';
8 | @import '@radix-ui/colors/violetDark.css';
9 | @import '@radix-ui/colors/slateDark.css';
10 |
11 | .DialogOverlay {
12 | background-color: var(--slate9);
13 | position: fixed;
14 | inset: 0;
15 | animation: overlayShow 150ms cubic-bezier(0.16, 1, 0.3, 1);
16 | z-index: 2;
17 | }
18 |
19 | .DialogContent {
20 | background-color: var(--slate1);
21 | border-radius: 6px;
22 | box-shadow: hsl(206 22% 7% / 35%) 0px 10px 38px -10px, hsl(206 22% 7% / 20%) 0px 10px 20px -15px;
23 | position: fixed;
24 | top: 50%;
25 | left: 50%;
26 | transform: translate(-50%, -50%);
27 | max-width: 90vw;
28 | max-height: 85vh;
29 | padding: 25px;
30 | animation: contentShow 150ms cubic-bezier(0.16, 1, 0.3, 1);
31 | z-index: 100;
32 | }
33 | .DialogContent:focus {
34 | outline: none;
35 | }
36 |
37 | .DialogTitle {
38 | margin: 0;
39 | font-weight: 500;
40 | color: var(--mauve12);
41 | font-size: 17px;
42 | }
43 |
44 | .DialogDescription {
45 | margin: 10px 0 20px;
46 | color: var(--mauve11);
47 | line-height: 1.5;
48 | }
49 |
50 | .Button {
51 | display: inline-flex;
52 | align-items: center;
53 | justify-content: center;
54 | border-radius: 4px;
55 | padding: 0 15px;
56 | font-size: 15px;
57 | line-height: 1;
58 | font-weight: 500;
59 | height: 35px;
60 | }
61 | .Button.violet {
62 | background-color: var(--slate1);
63 | color: var(--violet11);
64 | box-shadow: 0 2px 10px var(--slate7);
65 | }
66 | .Button.violet:hover {
67 | background-color: var(--mauve3);
68 | }
69 | .Button.violet:focus {
70 | box-shadow: 0 0 0 2px var(--slate12);
71 | }
72 | .Button.green {
73 | background-color: var(--green4);
74 | color: var(--green11);
75 | }
76 | .Button.green:hover {
77 | background-color: var(--green5);
78 | }
79 | .Button.green:focus {
80 | box-shadow: 0 0 0 2px var(--green7);
81 | }
82 |
83 | .IconButtonWithoutPosition {
84 | font-family: inherit;
85 | border-radius: 100%;
86 | height: 25px;
87 | width: 25px;
88 | display: inline-flex;
89 | align-items: center;
90 | justify-content: center;
91 | color: var(--violet11);
92 | }
93 |
94 | .IconButtonWithoutPosition:hover {
95 | background-color: var(--violet4);
96 | }
97 | .IconButtonWithoutPosition:focus {
98 | box-shadow: 0 0 0 2px var(--violet7);
99 | }
100 |
101 | .IconButton {
102 | font-family: inherit;
103 | border-radius: 100%;
104 | height: 25px;
105 | width: 25px;
106 | display: inline-flex;
107 | align-items: center;
108 | justify-content: center;
109 | color: var(--violet11);
110 | position: absolute;
111 | top: 10px;
112 | right: 10px;
113 | }
114 | .IconButton:hover {
115 | background-color: var(--violet4);
116 | }
117 | .IconButton:focus {
118 | box-shadow: 0 0 0 2px var(--violet7);
119 | }
120 |
121 | .Fieldset {
122 | display: flex;
123 | gap: 20px;
124 | align-items: center;
125 | margin-bottom: 15px;
126 | }
127 |
128 | .Label {
129 | font-size: 15px;
130 | color: var(--violet11);
131 | width: 90px;
132 | text-align: right;
133 | }
134 |
135 | .Input {
136 | width: 100%;
137 | flex: 1;
138 | display: inline-flex;
139 | align-items: center;
140 | justify-content: center;
141 | border-radius: 4px;
142 | padding: 0 10px;
143 | font-size: 15px;
144 | line-height: 1;
145 | color: var(--violet11);
146 | box-shadow: 0 0 0 1px var(--violet7);
147 | height: 35px;
148 | }
149 | .Input:focus {
150 | box-shadow: 0 0 0 2px var(--violet8);
151 | }
152 |
153 | @keyframes overlayShow {
154 | from {
155 | opacity: 0;
156 | }
157 | to {
158 | opacity: 1;
159 | }
160 | }
161 |
162 | @keyframes contentShow {
163 | from {
164 | opacity: 0;
165 | transform: translate(-50%, -48%) scale(0.96);
166 | }
167 | to {
168 | opacity: 1;
169 | transform: translate(-50%, -50%) scale(1);
170 | }
171 | }
172 |
--------------------------------------------------------------------------------
/components/ClaudeSetting/index.tsx:
--------------------------------------------------------------------------------
1 | import * as Dialog from "@radix-ui/react-dialog";
2 | import { Cross2Icon } from "@radix-ui/react-icons";
3 | import * as Avatar from "@radix-ui/react-avatar";
4 | import cls from "classnames";
5 |
6 | import { useModelSetting } from "../../contexts/modelSetting";
7 |
8 | const models = [
9 | { name: "claude-instant-v1", desc: "低延迟,减少等待时间" },
10 | { name: "claude-instant-v1.1", desc: "低延迟,v1.0 的升级版本" },
11 | { name: "claude-v1.2", desc: "v1 的升级版本,中文支持更好,但延迟比较高" },
12 | { name: "claude-v1.3", desc: "在代码、非英文对话和写作会更好,但延迟很高" },
13 | ];
14 |
15 | import * as Slider from "@radix-ui/react-slider";
16 |
17 | import type { SliderProps } from "@radix-ui/react-slider";
18 |
19 | const CustomSlider = (props: SliderProps) => (
20 |
28 | );
29 |
30 | const CluadeSetting = ({
31 | open,
32 | setOpen,
33 | }: {
34 | open: boolean;
35 | setOpen: (o: boolean) => void;
36 | }) => {
37 | const { value, setValue } = useModelSetting();
38 |
39 | const modelName = value?.model ?? "claude-instant-v1";
40 | const temperature = value?.temperature ?? 0.7;
41 | const maxTokens = value?.maxTokens ?? 400;
42 |
43 | return (
44 |
45 |
46 |
47 | Claude 配置
48 |
49 | 模型
50 |
51 |
52 |
53 | {models.map((m, index) => (
54 | setValue({ ...(value as any), model: m.name })}
57 | className={cls(
58 | "cursor-pointer relative rounded-lg border bg-white dark:bg-zinc-800 p-4 shadow-sm focus:outline-none w-full text-sm",
59 | m.name === modelName ? "border-blue-600" : "border-gray-300"
60 | )}
61 | >
62 |
63 |
64 |
69 |
70 |
{m.name}
71 |
72 | {m.desc}
73 |
74 | ))}
75 |
76 |
77 |
78 | 温度:{" "}
79 |
80 | {value?.temperature ?? "0.7"}
81 |
82 |
83 |
84 | {
87 | const _value = val[0] / 100;
88 |
89 | setValue({
90 | ...(value as any),
91 | temperature: _value,
92 | });
93 | }}
94 | value={[temperature * 100]}
95 | max={100}
96 | step={1}
97 | />
98 |
99 |
100 | 生成长度:{" "}
101 | {maxTokens}
102 |
103 |
104 | {
107 | const _value = val[0];
108 |
109 | setValue({ ...(value as any), maxTokens: _value });
110 | }}
111 | value={[maxTokens]}
112 | max={2000}
113 | min={200}
114 | step={10}
115 | />
116 |
117 | {/*
118 |
119 | Save changes
120 |
121 |
*/}
122 | setOpen(false)}>
123 |
124 |
125 |
126 |
127 |
128 |
129 |
130 | );
131 | };
132 |
133 | export default CluadeSetting;
134 |
--------------------------------------------------------------------------------
/components/ContextMenu/index.tsx:
--------------------------------------------------------------------------------
1 | import { useState } from "react";
2 | import * as ContextMenu from "@radix-ui/react-context-menu";
3 | import Link from "next/link";
4 | import ClaudeSetting from "../ClaudeSetting";
5 | import { useIsSupportCapture } from "../../hooks/useIsSupportCapture";
6 |
7 | import { builtinPrompts } from "../../data/prompts";
8 | import { useAssistantRole } from "../../contexts/assistant";
9 | import CommandBar from "../CommandBar";
10 | import { KBarProvider } from "kbar";
11 |
12 | import type { Action } from "kbar";
13 |
14 | const about = [
15 | {
16 | id: "about_me",
17 | name: "关于我",
18 | keywords: "about, me, author",
19 | section: "About",
20 | perform: () => {
21 | window.open("https://twitter.com/xiaokedada", "__blank");
22 | },
23 | },
24 | ];
25 |
26 | const ContextMenuChat = ({ children }: { children: React.ReactNode }) => {
27 | const isMobile = useIsSupportCapture();
28 |
29 | const [claudeSettingOpen, setClaueSettingOpen] = useState(false);
30 | const { setValue } = useAssistantRole();
31 |
32 | const promptsActions: Action[] = builtinPrompts.map((prompt) => ({
33 | id: prompt.id,
34 | name: prompt.title,
35 | keywords: prompt.keywords.join(", "),
36 | section: "Prompt",
37 | subtitle: prompt.desc,
38 | perform: (action) => {
39 | setValue(action.id);
40 | },
41 | }));
42 |
43 | const settingActions = [
44 | {
45 | id: "claude_setting",
46 | name: "模型设置",
47 | keywords: "setting",
48 | section: "Setting",
49 | subtitle: "设置 CLAUDE 的参数",
50 | perform: () => {
51 | setClaueSettingOpen(true);
52 | },
53 | },
54 | {
55 | id: "refresh",
56 | name: "刷新",
57 | keywords: "refresh",
58 | section: "Setting",
59 | subtitle: "刷新整个页面",
60 | perform: () => {
61 | location.reload();
62 | },
63 | },
64 | {
65 | id: "delete_all_history",
66 | name: "删除历史记录",
67 | keywords: "delete, history",
68 | section: "Setting",
69 | subtitle: "删除所有历史记录,该操作不可逆",
70 | perform: () => {
71 | localStorage.removeItem("ec-records");
72 | location.reload();
73 | },
74 | },
75 | ];
76 |
77 | const functionActions = [
78 | {
79 | id: "upload_files",
80 | name: "上传文件",
81 | keywords: "upload",
82 | section: "Functions",
83 | subtitle: "",
84 | },
85 | ];
86 |
87 | const actions = [...settingActions, ...promptsActions, ...about];
88 |
89 | return (
90 |
91 |
92 | {isMobile ? (
93 |
94 | {children}
95 | setClaueSettingOpen(false)}
98 | />
99 |
100 | ) : (
101 |
102 |
103 | <>
104 | {children}
105 | setClaueSettingOpen(false)}
108 | />
109 | >
110 |
111 |
112 | {/* @ts-ignore */}
113 |
114 | {
117 | // FIXME: 这里先这样
118 | localStorage.removeItem("ec-records");
119 | location.reload();
120 | }}
121 | >
122 | 删除历史记录
123 |
124 | {
127 | location.reload();
128 | }}
129 | >
130 | 刷新 ⌘+R
131 |
132 |
133 |
134 | {
137 | setClaueSettingOpen(true);
138 | }}
139 | >
140 | Claude 配置
141 |
142 |
143 |
144 |
145 | 关于
146 |
147 |
148 | EasierChat
149 |
150 |
151 | 作者
152 |
153 |
154 |
155 |
156 | )}
157 |
158 | );
159 | };
160 |
161 | export default ContextMenuChat;
162 |
--------------------------------------------------------------------------------
/lottie/activity.json:
--------------------------------------------------------------------------------
1 | {"v":"5.7.13","fr":30,"ip":0,"op":43,"w":400,"h":400,"nm":"activity","ddd":0,"assets":[],"layers":[{"ddd":0,"ind":1,"ty":3,"nm":"Control layer","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[200,200,0],"ix":2,"l":2},"a":{"a":0,"k":[200,200,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"ef":[{"ty":5,"nm":"Primary color","np":3,"mn":"ADBE Color Control","ix":1,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[0.13333333333333333,0.7725490196078432,0.3686274509803922,1],"ix":1}}]},{"ty":5,"nm":"Secondary color","np":3,"mn":"ADBE Color Control","ix":2,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[0.13333333333333333,0.7725490196078432,0.3686274509803922,1],"ix":1}}]},{"ty":5,"nm":"Position control","np":3,"mn":"ADBE Point Control","ix":3,"en":1,"ef":[{"ty":3,"nm":"Point","mn":"ADBE Point Control-0001","ix":1,"v":{"a":0,"k":[200,200],"ix":1}}]},{"ty":5,"nm":"Bg ON","np":3,"mn":"ADBE Checkbox Control","ix":4,"en":1,"ef":[{"ty":7,"nm":"Checkbox","mn":"ADBE Checkbox Control-0001","ix":1,"v":{"a":0,"k":0,"ix":1}}]},{"ty":5,"nm":"Bg Color","np":3,"mn":"ADBE Color Control","ix":5,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[1,1,1,1],"ix":1}}]},{"ty":5,"nm":"Stroke width","np":3,"mn":"ADBE Slider Control","ix":6,"en":1,"ef":[{"ty":0,"nm":"Slider","mn":"ADBE Slider Control-0001","ix":1,"v":{"a":0,"k":12,"ix":1}}]},{"ty":5,"nm":"Scale","np":3,"mn":"ADBE Slider Control","ix":7,"en":1,"ef":[{"ty":0,"nm":"Slider","mn":"ADBE Slider Control-0001","ix":1,"v":{"a":0,"k":100,"ix":1}}]}],"ip":0,"op":151,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":2,"ty":3,"nm":"fixed null","sr":1,"ks":{"o":{"a":0,"k":0,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[292,441,0],"ix":2,"l":2,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Position control')('Point');"},"a":{"a":0,"k":[50,50,0],"ix":1,"l":2},"s":{"a":0,"k":[57,57,100],"ix":6,"l":2,"x":"var $bm_rt;\nvar temp;\ntemp = thisComp.layer('Control layer').effect('Scale')('Slider');\n$bm_rt = [\n temp,\n temp\n];"}},"ao":0,"ip":0,"op":151,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":3,"ty":3,"nm":"Null 1","parent":2,"sr":1,"ks":{"o":{"a":0,"k":0,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[50,50,0],"ix":2,"l":2},"a":{"a":0,"k":[50,50,0],"ix":1,"l":2},"s":{"a":0,"k":[170,170,100],"ix":6,"l":2}},"ao":0,"ip":0,"op":151,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":4,"ty":4,"nm":"activity 2","parent":3,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[50,50,0],"ix":2,"l":2},"a":{"a":0,"k":[115,86,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":0,"k":{"i":[[-85,0.006],[-50.743,0.006],[-19.333,-56],[21.17,56],[48.217,0],[85,0]],"o":[[-85,0.006],[-50.743,0.006],[-19.333,-56],[21.17,56],[48.217,0],[85,0]],"v":[[-85,0.006],[-50.743,0.006],[-19.333,-56],[21.17,56],[48.217,0],[85,0]],"c":false},"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.415686304429,0.043137254902,1,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Secondary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = $bm_mul(100 / 170, thisComp.layer('Control layer').effect('Stroke width')('Slider'));"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[115,86],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true},{"ty":"tm","s":{"a":1,"k":[{"i":{"x":[0.667],"y":[1]},"o":{"x":[0.333],"y":[0]},"t":16,"s":[0]},{"t":33,"s":[0]}],"ix":1},"e":{"a":1,"k":[{"i":{"x":[0.667],"y":[1]},"o":{"x":[0.333],"y":[0]},"t":16,"s":[0]},{"t":33,"s":[100]}],"ix":2},"o":{"a":0,"k":0,"ix":3},"m":1,"ix":2,"nm":"Trim Paths 1","mn":"ADBE Vector Filter - Trim","hd":false,"_render":true}],"ip":15,"op":151,"st":16,"bm":0,"completed":true},{"ddd":0,"ind":5,"ty":4,"nm":"activity ","parent":3,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[50,50,0],"ix":2,"l":2},"a":{"a":0,"k":[115,86,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":0,"k":{"i":[[-85,0.006],[-50.743,0.006],[-19.333,-56],[21.17,56],[48.217,0],[85,0]],"o":[[-85,0.006],[-50.743,0.006],[-19.333,-56],[21.17,56],[48.217,0],[85,0]],"v":[[-85,0.006],[-50.743,0.006],[-19.333,-56],[21.17,56],[48.217,0],[85,0]],"c":false},"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.415686304429,0.043137254902,1,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Secondary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = $bm_mul(100 / 170, thisComp.layer('Control layer').effect('Stroke width')('Slider'));"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[115,86],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true},{"ty":"tm","s":{"a":1,"k":[{"i":{"x":[0.667],"y":[1]},"o":{"x":[0.333],"y":[0]},"t":0,"s":[100]},{"t":15,"s":[100]}],"ix":1},"e":{"a":1,"k":[{"i":{"x":[0.667],"y":[1]},"o":{"x":[0.333],"y":[0]},"t":0,"s":[0]},{"t":15,"s":[100]}],"ix":2},"o":{"a":0,"k":0,"ix":3},"m":1,"ix":2,"nm":"Trim Paths 1","mn":"ADBE Vector Filter - Trim","hd":false,"_render":true}],"ip":0,"op":15,"st":-6,"bm":0,"completed":true},{"ddd":0,"ind":6,"ty":4,"nm":"background","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11,"x":"var $bm_rt;\nif (thisComp.layer('Control layer').effect('Bg ON')('Checkbox') > 0) {\n $bm_rt = 100;\n} else {\n $bm_rt = 0;\n}"},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[200,200,0],"ix":2,"l":2},"a":{"a":0,"k":[1,-0.5,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ty":"rc","d":1,"s":{"a":0,"k":[400,400],"ix":2},"p":{"a":0,"k":[0,0],"ix":3},"r":{"a":0,"k":0,"ix":4},"nm":"Rectangle Path 1","mn":"ADBE Vector Shape - Rect","hd":false,"_render":true},{"ty":"fl","c":{"a":0,"k":[1,1,1,1],"ix":4,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Bg Color')('Color');"},"o":{"a":0,"k":100,"ix":5},"r":1,"bm":0,"nm":"Fill 1","mn":"ADBE Vector Graphic - Fill","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[1,-0.5],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Rectangle 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":151,"st":0,"bm":0,"completed":true}],"markers":[],"__complete":true}
--------------------------------------------------------------------------------
/styles/modal.css:
--------------------------------------------------------------------------------
1 | /* modal */
2 | .NavigationMenuRoot {
3 | position: relative;
4 | display: flex;
5 | justify-content: center;
6 | z-index: 1;
7 | }
8 |
9 | .NavigationMenuList {
10 | display: flex;
11 | justify-content: center;
12 | background-color: var(--slate1);
13 | padding: 4px;
14 | border-radius: 6px;
15 | list-style: none;
16 | box-shadow: 0 2px 10px var(--slate7);
17 | margin: 0;
18 | }
19 |
20 | .NavigationMenuTrigger,
21 | .NavigationMenuLink {
22 | padding: 8px 12px;
23 | outline: none;
24 | user-select: none;
25 | font-weight: 500;
26 | line-height: 1;
27 | border-radius: 4px;
28 | font-size: 15px;
29 | color: var(--violet11);
30 | }
31 | .NavigationMenuTrigger:focus,
32 | .NavigationMenuLink:focus {
33 | box-shadow: 0 0 0 2px var(--violet7);
34 | }
35 | .NavigationMenuTrigger:hover,
36 | .NavigationMenuLink:hover {
37 | background-color: var(--violet3);
38 | }
39 |
40 | .NavigationMenuTrigger {
41 | display: flex;
42 | align-items: center;
43 | justify-content: space-between;
44 | gap: 2px;
45 | }
46 |
47 | .NavigationMenuLink {
48 | display: block;
49 | text-decoration: none;
50 | font-size: 15px;
51 | line-height: 1;
52 | }
53 |
54 | .NavigationMenuContent {
55 | position: absolute;
56 | top: 0;
57 | left: 0;
58 | width: 100%;
59 | animation-duration: 250ms;
60 | animation-timing-function: ease;
61 | }
62 | .NavigationMenuContent[data-motion='from-start'] {
63 | animation-name: enterFromLeft;
64 | }
65 | .NavigationMenuContent[data-motion='from-end'] {
66 | animation-name: enterFromRight;
67 | }
68 | .NavigationMenuContent[data-motion='to-start'] {
69 | animation-name: exitToLeft;
70 | }
71 | .NavigationMenuContent[data-motion='to-end'] {
72 | animation-name: exitToRight;
73 | }
74 | @media only screen and (min-width: 600px) {
75 | .NavigationMenuContent {
76 | width: auto;
77 | }
78 | }
79 |
80 | .NavigationMenuIndicator {
81 | display: flex;
82 | align-items: flex-end;
83 | justify-content: center;
84 | height: 10px;
85 | top: 100%;
86 | overflow: hidden;
87 | z-index: 1;
88 | transition: width, transform 250ms ease;
89 | }
90 | .NavigationMenuIndicator[data-state='visible'] {
91 | animation: fadeIn 200ms ease;
92 | }
93 | .NavigationMenuIndicator[data-state='hidden'] {
94 | animation: fadeOut 200ms ease;
95 | }
96 |
97 | .NavigationMenuViewport {
98 | position: relative;
99 | transform-origin: top center;
100 | margin-top: 10px;
101 | width: 100%;
102 | background-color: var(--slate1);
103 | border-radius: 6px;
104 | overflow: hidden;
105 | box-shadow: hsl(206 22% 7% / 35%) 0px 10px 38px -10px, hsl(206 22% 7% / 20%) 0px 10px 20px -15px;
106 | height: var(--radix-navigation-menu-viewport-height);
107 | transition: width, height, 300ms ease;
108 | }
109 | .NavigationMenuViewport[data-state='open'] {
110 | animation: scaleIn 200ms ease;
111 | }
112 | .NavigationMenuViewport[data-state='closed'] {
113 | animation: scaleOut 200ms ease;
114 | }
115 | @media only screen and (min-width: 600px) {
116 | .NavigationMenuViewport {
117 | width: var(--radix-navigation-menu-viewport-width);
118 | }
119 | }
120 |
121 | .List {
122 | display: grid;
123 | padding: 22px;
124 | margin: 0;
125 | column-gap: 10px;
126 | list-style: none;
127 | }
128 | @media only screen and (min-width: 600px) {
129 | .List.one {
130 | width: 500px;
131 | grid-template-columns: 0.75fr 1fr;
132 | }
133 | .List.two {
134 | width: 600px;
135 | grid-auto-flow: column;
136 | grid-template-rows: repeat(3, 1fr);
137 | }
138 | }
139 |
140 | .ListItemLink {
141 | display: block;
142 | outline: none;
143 | text-decoration: none;
144 | user-select: none;
145 | padding: 12px;
146 | border-radius: 6px;
147 | font-size: 15px;
148 | line-height: 1;
149 | }
150 | .ListItemLink:focus {
151 | box-shadow: 0 0 0 2px var(--violet7);
152 | }
153 | .ListItemLink:hover {
154 | background-color: var(--mauve3);
155 | }
156 |
157 | .ListItemHeading {
158 | font-weight: 500;
159 | line-height: 1.2;
160 | margin-bottom: 5px;
161 | color: var(--violet12);
162 | }
163 |
164 | .ListItemText {
165 | color: var(--mauve11);
166 | line-height: 1.4;
167 | font-weight: initial;
168 | }
169 |
170 | .Callout {
171 | display: flex;
172 | justify-content: flex-end;
173 | flex-direction: column;
174 | width: 100%;
175 | height: 100%;
176 | background: linear-gradient(135deg, var(--purple9) 0%, var(--indigo9) 100%);
177 | border-radius: 6px;
178 | padding: 25px;
179 | text-decoration: none;
180 | outline: none;
181 | user-select: none;
182 | }
183 | .Callout:focus {
184 | box-shadow: 0 0 0 2px var(--violet7);
185 | }
186 |
187 | .CalloutHeading {
188 | color: var(--slate1);
189 | font-size: 18px;
190 | font-weight: 500;
191 | line-height: 1.2;
192 | margin-top: 16px;
193 | margin-bottom: 7px;
194 | }
195 |
196 | .CalloutText {
197 | color: var(--mauve4);
198 | font-size: 14px;
199 | line-height: 1.3;
200 | }
201 |
202 | .ViewportPosition {
203 | position: absolute;
204 | display: flex;
205 | justify-content: center;
206 | width: 100%;
207 | top: 100%;
208 | left: 0;
209 | perspective: 2000px;
210 | }
211 |
212 | .CaretDown {
213 | position: relative;
214 | color: var(--violet10);
215 | top: 1px;
216 | transition: transform 250ms ease;
217 | }
218 | [data-state='open'] > .CaretDown {
219 | transform: rotate(-180deg);
220 | }
221 |
222 | .Arrow {
223 | position: relative;
224 | top: 70%;
225 | background-color: var(--slate1);
226 | width: 10px;
227 | height: 10px;
228 | transform: rotate(45deg);
229 | border-top-left-radius: 2px;
230 | }
231 |
232 | @keyframes enterFromRight {
233 | from {
234 | opacity: 0;
235 | transform: translateX(200px);
236 | }
237 | to {
238 | opacity: 1;
239 | transform: translateX(0);
240 | }
241 | }
242 |
243 | @keyframes enterFromLeft {
244 | from {
245 | opacity: 0;
246 | transform: translateX(-200px);
247 | }
248 | to {
249 | opacity: 1;
250 | transform: translateX(0);
251 | }
252 | }
253 |
254 | @keyframes exitToRight {
255 | from {
256 | opacity: 1;
257 | transform: translateX(0);
258 | }
259 | to {
260 | opacity: 0;
261 | transform: translateX(200px);
262 | }
263 | }
264 |
265 | @keyframes exitToLeft {
266 | from {
267 | opacity: 1;
268 | transform: translateX(0);
269 | }
270 | to {
271 | opacity: 0;
272 | transform: translateX(-200px);
273 | }
274 | }
275 |
276 | @keyframes scaleIn {
277 | from {
278 | opacity: 0;
279 | transform: rotateX(-30deg) scale(0.9);
280 | }
281 | to {
282 | opacity: 1;
283 | transform: rotateX(0deg) scale(1);
284 | }
285 | }
286 |
287 | @keyframes scaleOut {
288 | from {
289 | opacity: 1;
290 | transform: rotateX(0deg) scale(1);
291 | }
292 | to {
293 | opacity: 0;
294 | transform: rotateX(-10deg) scale(0.95);
295 | }
296 | }
297 |
298 | @keyframes fadeIn {
299 | from {
300 | opacity: 0;
301 | }
302 | to {
303 | opacity: 1;
304 | }
305 | }
306 |
307 | @keyframes fadeOut {
308 | from {
309 | opacity: 1;
310 | }
311 | to {
312 | opacity: 0;
313 | }
314 | }
315 |
--------------------------------------------------------------------------------
/components/CommandBar/index.tsx:
--------------------------------------------------------------------------------
1 | import React from "react";
2 | import { useIsSupportCapture } from "../../hooks/useIsSupportCapture";
3 |
4 | import {
5 | KBarPortal,
6 | KBarPositioner,
7 | KBarAnimator,
8 | useMatches,
9 | KBarResults,
10 | ActionImpl,
11 | ActionId,
12 | VisualState,
13 | useKBar,
14 | } from "kbar";
15 |
16 | export const KBAR_LISTBOX = "kbar-listbox";
17 | export const getListboxItemId = (id: number) => `kbar-listbox-item-${id}`;
18 |
19 | export function KBarSearch(
20 | props: React.InputHTMLAttributes & {
21 | defaultPlaceholder?: string;
22 | }
23 | ) {
24 | const {
25 | query,
26 | search,
27 | actions,
28 | currentRootActionId,
29 | activeIndex,
30 | showing,
31 | options,
32 | } = useKBar((state) => ({
33 | search: state.searchQuery,
34 | currentRootActionId: state.currentRootActionId,
35 | actions: state.actions,
36 | activeIndex: state.activeIndex,
37 | showing: state.visualState === VisualState.showing,
38 | }));
39 |
40 | const { defaultPlaceholder, ...rest } = props;
41 |
42 | React.useEffect(() => {
43 | query.setSearch("");
44 | query.getInput().focus();
45 | return () => query.setSearch("");
46 | }, [currentRootActionId, query]);
47 |
48 | const placeholder = React.useMemo((): string => {
49 | const defaultText = defaultPlaceholder ?? "Type a command or search…";
50 | return currentRootActionId && actions[currentRootActionId]
51 | ? actions[currentRootActionId].name
52 | : defaultText;
53 | }, [actions, currentRootActionId, defaultPlaceholder]);
54 |
55 | return (
56 | {
70 | props.onChange?.(event);
71 | query.setSearch(event.target.value);
72 | options?.callbacks?.onQueryChange?.(event.target.value);
73 | }}
74 | onKeyDown={(event) => {
75 | props.onKeyDown?.(event);
76 | if (currentRootActionId && !search && event.key === "Backspace") {
77 | const parent = actions[currentRootActionId].parent;
78 | query.setCurrentRootAction(parent);
79 | }
80 | }}
81 | />
82 | );
83 | }
84 |
85 | const searchStyle = {
86 | padding: "12px 16px",
87 | fontSize: "16px",
88 | width: "100%",
89 | boxSizing: "border-box" as React.CSSProperties["boxSizing"],
90 | outline: "none",
91 | border: "none",
92 | };
93 |
94 | const animatorStyle = {
95 | maxWidth: "600px",
96 | width: "100%",
97 | borderRadius: "8px",
98 | overflow: "hidden",
99 | boxShadow: "0px 6px 20px rgb(0 0 0 / 20%)",
100 | };
101 |
102 | const groupNameStyle = {
103 | padding: "8px 16px",
104 | fontSize: "10px",
105 | textTransform: "uppercase" as const,
106 | opacity: 0.5,
107 | };
108 |
109 | // eslint-disable-next-line react/display-name
110 | const ResultItem = React.forwardRef(
111 | (
112 | {
113 | action,
114 | active,
115 | currentRootActionId,
116 | }: {
117 | action: ActionImpl;
118 | active: boolean;
119 | currentRootActionId: ActionId;
120 | },
121 | ref: React.Ref
122 | ) => {
123 | const ancestors = React.useMemo(() => {
124 | if (!currentRootActionId) return action.ancestors;
125 | const index = action.ancestors.findIndex(
126 | (ancestor) => ancestor.id === currentRootActionId
127 | );
128 | // +1 removes the currentRootAction; e.g.
129 | // if we are on the "Set theme" parent action,
130 | // the UI should not display "Set theme… > Dark"
131 | // but rather just "Dark"
132 | return action.ancestors.slice(index + 1);
133 | }, [action.ancestors, currentRootActionId]);
134 |
135 | return (
136 |
148 |
156 | {action.icon && action.icon}
157 |
158 |
159 | {ancestors.length > 0 &&
160 | ancestors.map((ancestor) => (
161 |
162 |
168 | {ancestor.name}
169 |
170 |
175 | ›
176 |
177 |
178 | ))}
179 | {action.name}
180 |
181 | {action.subtitle && (
182 |
{action.subtitle}
183 | )}
184 |
185 |
186 | {action.shortcut?.length ? (
187 |
191 | {action.shortcut.map((sc) => (
192 |
201 | {sc}
202 |
203 | ))}
204 |
205 | ) : null}
206 |
207 | );
208 | }
209 | );
210 |
211 | function RenderResults() {
212 | const { results, rootActionId } = useMatches();
213 |
214 | const isMobile = useIsSupportCapture();
215 |
216 | return (
217 |
221 | typeof item === "string" ? (
222 | {item}
223 | ) : (
224 |
229 | )
230 | }
231 | />
232 | );
233 | }
234 |
235 | const CommandBar = () => {
236 | return (
237 |
238 |
239 |
243 |
244 |
245 |
246 |
247 |
248 | );
249 | };
250 |
251 | export default CommandBar;
252 |
--------------------------------------------------------------------------------
/lottie/tick.json:
--------------------------------------------------------------------------------
1 | {"v":"5.7.13","fr":29.9700012207031,"ip":0,"op":34.0000013848484,"w":400,"h":400,"nm":"tick","ddd":0,"assets":[],"layers":[{"ddd":0,"ind":1,"ty":3,"nm":"Control layer","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[200,200,0],"ix":2,"l":2},"a":{"a":0,"k":[200,200,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"ef":[{"ty":5,"nm":"Primary color","np":3,"mn":"ADBE Color Control","ix":1,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[0.098039224744,0.098039224744,0.098039224744,1],"ix":1}}]},{"ty":5,"nm":"Secondary color","np":3,"mn":"ADBE Color Control","ix":2,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[0.40784313725490196,0.13725490196078433,1,1],"ix":1}}]},{"ty":5,"nm":"Position control","np":3,"mn":"ADBE Point Control","ix":3,"en":1,"ef":[{"ty":3,"nm":"Point","mn":"ADBE Point Control-0001","ix":1,"v":{"a":0,"k":[200,200],"ix":1}}]},{"ty":5,"nm":"Bg ON","np":3,"mn":"ADBE Checkbox Control","ix":4,"en":1,"ef":[{"ty":7,"nm":"Checkbox","mn":"ADBE Checkbox Control-0001","ix":1,"v":{"a":0,"k":0,"ix":1}}]},{"ty":5,"nm":"Bg Color","np":3,"mn":"ADBE Color Control","ix":5,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[1,1,1,1],"ix":1}}]},{"ty":5,"nm":"Stroke width","np":3,"mn":"ADBE Slider Control","ix":6,"en":1,"ef":[{"ty":0,"nm":"Slider","mn":"ADBE Slider Control-0001","ix":1,"v":{"a":0,"k":12,"ix":1}}]},{"ty":5,"nm":"Scale","np":3,"mn":"ADBE Slider Control","ix":7,"en":1,"ef":[{"ty":0,"nm":"Slider","mn":"ADBE Slider Control-0001","ix":1,"v":{"a":0,"k":100,"ix":1}}]}],"ip":0,"op":150.000006109625,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":2,"ty":3,"nm":"fixed null","sr":1,"ks":{"o":{"a":0,"k":0,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[292,441,0],"ix":2,"l":2,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Position control')('Point');"},"a":{"a":0,"k":[50,50,0],"ix":1,"l":2},"s":{"a":0,"k":[57,57,100],"ix":6,"l":2,"x":"var $bm_rt;\nvar temp;\ntemp = thisComp.layer('Control layer').effect('Scale')('Slider');\n$bm_rt = [\n temp,\n temp\n];"}},"ao":0,"ip":0,"op":150.000006109625,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":3,"ty":3,"nm":"Null 1","parent":2,"sr":1,"ks":{"o":{"a":0,"k":0,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[50,50,0],"ix":2,"l":2},"a":{"a":0,"k":[50,50,0],"ix":1,"l":2},"s":{"a":0,"k":[120,120,100],"ix":6,"l":2}},"ao":0,"ip":0,"op":150.000006109625,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":4,"ty":4,"nm":"tick purple","parent":6,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[149,160,0],"ix":2,"l":2},"a":{"a":0,"k":[98.661,79.5,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":1,"k":[{"i":{"x":0.667,"y":1},"o":{"x":0.333,"y":0},"t":0,"s":[{"i":[[68.661,-49.5],[-30.339,49.5],[-68.661,11.177]],"o":[[68.661,-49.5],[-30.339,49.5],[-68.661,11.177]],"v":[[68.661,-49.5],[-30.339,49.5],[-68.661,11.177]],"c":false}]},{"i":{"x":0.667,"y":1},"o":{"x":0.333,"y":0},"t":8,"s":[{"i":[[76.661,-57.5],[-30.339,49.5],[-68.661,11.177]],"o":[[76.661,-57.5],[-30.339,49.5],[-68.661,11.177]],"v":[[76.661,-57.5],[-30.339,49.5],[-68.661,11.177]],"c":false}]},{"t":12.00000048877,"s":[{"i":[[68.661,-49.5],[-30.339,49.5],[-68.661,11.177]],"o":[[68.661,-49.5],[-30.339,49.5],[-68.661,11.177]],"v":[[68.661,-49.5],[-30.339,49.5],[-68.661,11.177]],"c":false}]}],"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.415686304429,0.043137254902,1,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Secondary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = $bm_mul(100 / 120, thisComp.layer('Control layer').effect('Stroke width')('Slider'));"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[98.661,79.5],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true},{"ty":"tm","s":{"a":1,"k":[{"i":{"x":[0.667],"y":[1]},"o":{"x":[0.333],"y":[0]},"t":0,"s":[100]},{"t":8.00000032584668,"s":[0]}],"ix":1},"e":{"a":0,"k":100,"ix":2},"o":{"a":0,"k":0,"ix":3},"m":1,"ix":2,"nm":"Trim Paths 1","mn":"ADBE Vector Filter - Trim","hd":false,"_render":true}],"ip":0,"op":150.000006109625,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":5,"ty":4,"nm":"tick black","parent":6,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[149,160,0],"ix":2,"l":2},"a":{"a":0,"k":[98.661,79.5,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":0,"k":{"i":[[68.661,-49.5],[-30.339,49.5],[-68.661,11.177]],"o":[[68.661,-49.5],[-30.339,49.5],[-68.661,11.177]],"v":[[68.661,-49.5],[-30.339,49.5],[-68.661,11.177]],"c":false},"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.098039223166,0.098039223166,0.098039223166,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Primary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = $bm_mul(100 / 120, thisComp.layer('Control layer').effect('Stroke width')('Slider'));"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[98.661,79.5],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true},{"ty":"tm","s":{"a":0,"k":0,"ix":1},"e":{"a":0,"k":100,"ix":2},"o":{"a":0,"k":0,"ix":3},"m":1,"ix":2,"nm":"Trim Paths 1","mn":"ADBE Vector Filter - Trim","hd":false,"_render":true}],"ip":0,"op":8.00000032584668,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":6,"ty":4,"nm":"circle","parent":3,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[50,50,0],"ix":2,"l":2},"a":{"a":0,"k":[155,155,0],"ix":1,"l":2},"s":{"a":1,"k":[{"i":{"x":[0.667,0.667,0.667],"y":[1,1,1]},"o":{"x":[0.333,0.333,0.333],"y":[0,0,0]},"t":7,"s":[100,100,100]},{"i":{"x":[0.667,0.667,0.667],"y":[1,1,1]},"o":{"x":[0.333,0.333,0.333],"y":[0,0,0]},"t":12,"s":[106,106,100]},{"i":{"x":[0.667,0.667,0.667],"y":[1,1,1]},"o":{"x":[0.333,0.333,0.333],"y":[0,0,0]},"t":17,"s":[97,97,100]},{"t":23.0000009368092,"s":[100,100,100]}],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":0,"k":{"i":[[125,-69.036],[69.036,125],[-125,69.036],[-69.036,-125]],"o":[[125,69.036],[-69.036,125],[-125,-69.036],[69.036,-125]],"v":[[125,0],[0,125],[-125,0],[0,-125]],"c":true},"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.098039223166,0.098039223166,0.098039223166,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Primary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = $bm_mul(100 / 120, thisComp.layer('Control layer').effect('Stroke width')('Slider'));"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[155,155],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":150.000006109625,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":7,"ty":4,"nm":"background","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11,"x":"var $bm_rt;\nif (thisComp.layer('Control layer').effect('Bg ON')('Checkbox') > 0) {\n $bm_rt = 100;\n} else {\n $bm_rt = 0;\n}"},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[200,200,0],"ix":2,"l":2},"a":{"a":0,"k":[1,-0.5,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ty":"rc","d":1,"s":{"a":0,"k":[400,400],"ix":2},"p":{"a":0,"k":[0,0],"ix":3},"r":{"a":0,"k":0,"ix":4},"nm":"Rectangle Path 1","mn":"ADBE Vector Shape - Rect","hd":false,"_render":true},{"ty":"fl","c":{"a":0,"k":[1,1,1,1],"ix":4,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Bg Color')('Color');"},"o":{"a":0,"k":100,"ix":5},"r":1,"bm":0,"nm":"Fill 1","mn":"ADBE Vector Graphic - Fill","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[1,-0.5],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Rectangle 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":150.000006109625,"st":0,"bm":0,"completed":true}],"markers":[],"__complete":true}
--------------------------------------------------------------------------------
/public/workbox-06528c14.js:
--------------------------------------------------------------------------------
1 | define(["exports"],(function(t){"use strict";try{self["workbox:core:6.5.3"]&&_()}catch(t){}const e=(t,...e)=>{let s=t;return e.length>0&&(s+=` :: ${JSON.stringify(e)}`),s};class s extends Error{constructor(t,s){super(e(t,s)),this.name=t,this.details=s}}try{self["workbox:routing:6.5.3"]&&_()}catch(t){}const r=t=>t&&"object"==typeof t?t:{handle:t};class n{constructor(t,e,s="GET"){this.handler=r(e),this.match=t,this.method=s}setCatchHandler(t){this.catchHandler=r(t)}}class i extends n{constructor(t,e,s){super((({url:e})=>{const s=t.exec(e.href);if(s&&(e.origin===location.origin||0===s.index))return s.slice(1)}),e,s)}}class o{constructor(){this.t=new Map,this.i=new Map}get routes(){return this.t}addFetchListener(){self.addEventListener("fetch",(t=>{const{request:e}=t,s=this.handleRequest({request:e,event:t});s&&t.respondWith(s)}))}addCacheListener(){self.addEventListener("message",(t=>{if(t.data&&"CACHE_URLS"===t.data.type){const{payload:e}=t.data,s=Promise.all(e.urlsToCache.map((e=>{"string"==typeof e&&(e=[e]);const s=new Request(...e);return this.handleRequest({request:s,event:t})})));t.waitUntil(s),t.ports&&t.ports[0]&&s.then((()=>t.ports[0].postMessage(!0)))}}))}handleRequest({request:t,event:e}){const s=new URL(t.url,location.href);if(!s.protocol.startsWith("http"))return;const r=s.origin===location.origin,{params:n,route:i}=this.findMatchingRoute({event:e,request:t,sameOrigin:r,url:s});let o=i&&i.handler;const a=t.method;if(!o&&this.i.has(a)&&(o=this.i.get(a)),!o)return;let c;try{c=o.handle({url:s,request:t,event:e,params:n})}catch(t){c=Promise.reject(t)}const h=i&&i.catchHandler;return c instanceof Promise&&(this.o||h)&&(c=c.catch((async r=>{if(h)try{return await h.handle({url:s,request:t,event:e,params:n})}catch(t){t instanceof Error&&(r=t)}if(this.o)return this.o.handle({url:s,request:t,event:e});throw r}))),c}findMatchingRoute({url:t,sameOrigin:e,request:s,event:r}){const n=this.t.get(s.method)||[];for(const i of n){let n;const o=i.match({url:t,sameOrigin:e,request:s,event:r});if(o)return n=o,(Array.isArray(n)&&0===n.length||o.constructor===Object&&0===Object.keys(o).length||"boolean"==typeof o)&&(n=void 0),{route:i,params:n}}return{}}setDefaultHandler(t,e="GET"){this.i.set(e,r(t))}setCatchHandler(t){this.o=r(t)}registerRoute(t){this.t.has(t.method)||this.t.set(t.method,[]),this.t.get(t.method).push(t)}unregisterRoute(t){if(!this.t.has(t.method))throw new s("unregister-route-but-not-found-with-method",{method:t.method});const e=this.t.get(t.method).indexOf(t);if(!(e>-1))throw new s("unregister-route-route-not-registered");this.t.get(t.method).splice(e,1)}}let a;const c=()=>(a||(a=new o,a.addFetchListener(),a.addCacheListener()),a);try{self["workbox:strategies:6.5.3"]&&_()}catch(t){}const h={cacheWillUpdate:async({response:t})=>200===t.status||0===t.status?t:null},u={googleAnalytics:"googleAnalytics",precache:"precache-v2",prefix:"workbox",runtime:"runtime",suffix:"undefined"!=typeof registration?registration.scope:""},l=t=>[u.prefix,t,u.suffix].filter((t=>t&&t.length>0)).join("-"),f=t=>t||l(u.runtime);function w(t,e){const s=new URL(t);for(const t of e)s.searchParams.delete(t);return s.href}class d{constructor(){this.promise=new Promise(((t,e)=>{this.resolve=t,this.reject=e}))}}const p=new Set;function m(t){return new Promise((e=>setTimeout(e,t)))}function y(t){return"string"==typeof t?new Request(t):t}class g{constructor(t,e){this.h={},Object.assign(this,e),this.event=e.event,this.u=t,this.l=new d,this.p=[],this.m=[...t.plugins],this.g=new Map;for(const t of this.m)this.g.set(t,{});this.event.waitUntil(this.l.promise)}async fetch(t){const{event:e}=this;let r=y(t);if("navigate"===r.mode&&e instanceof FetchEvent&&e.preloadResponse){const t=await e.preloadResponse;if(t)return t}const n=this.hasCallback("fetchDidFail")?r.clone():null;try{for(const t of this.iterateCallbacks("requestWillFetch"))r=await t({request:r.clone(),event:e})}catch(t){if(t instanceof Error)throw new s("plugin-error-request-will-fetch",{thrownErrorMessage:t.message})}const i=r.clone();try{let t;t=await fetch(r,"navigate"===r.mode?void 0:this.u.fetchOptions);for(const s of this.iterateCallbacks("fetchDidSucceed"))t=await s({event:e,request:i,response:t});return t}catch(t){throw n&&await this.runCallbacks("fetchDidFail",{error:t,event:e,originalRequest:n.clone(),request:i.clone()}),t}}async fetchAndCachePut(t){const e=await this.fetch(t),s=e.clone();return this.waitUntil(this.cachePut(t,s)),e}async cacheMatch(t){const e=y(t);let s;const{cacheName:r,matchOptions:n}=this.u,i=await this.getCacheKey(e,"read"),o=Object.assign(Object.assign({},n),{cacheName:r});s=await caches.match(i,o);for(const t of this.iterateCallbacks("cachedResponseWillBeUsed"))s=await t({cacheName:r,matchOptions:n,cachedResponse:s,request:i,event:this.event})||void 0;return s}async cachePut(t,e){const r=y(t);await m(0);const n=await this.getCacheKey(r,"write");if(!e)throw new s("cache-put-with-no-response",{url:(i=n.url,new URL(String(i),location.href).href.replace(new RegExp(`^${location.origin}`),""))});var i;const o=await this.v(e);if(!o)return!1;const{cacheName:a,matchOptions:c}=this.u,h=await self.caches.open(a),u=this.hasCallback("cacheDidUpdate"),l=u?await async function(t,e,s,r){const n=w(e.url,s);if(e.url===n)return t.match(e,r);const i=Object.assign(Object.assign({},r),{ignoreSearch:!0}),o=await t.keys(e,i);for(const e of o)if(n===w(e.url,s))return t.match(e,r)}(h,n.clone(),["__WB_REVISION__"],c):null;try{await h.put(n,u?o.clone():o)}catch(t){if(t instanceof Error)throw"QuotaExceededError"===t.name&&await async function(){for(const t of p)await t()}(),t}for(const t of this.iterateCallbacks("cacheDidUpdate"))await t({cacheName:a,oldResponse:l,newResponse:o.clone(),request:n,event:this.event});return!0}async getCacheKey(t,e){const s=`${t.url} | ${e}`;if(!this.h[s]){let r=t;for(const t of this.iterateCallbacks("cacheKeyWillBeUsed"))r=y(await t({mode:e,request:r,event:this.event,params:this.params}));this.h[s]=r}return this.h[s]}hasCallback(t){for(const e of this.u.plugins)if(t in e)return!0;return!1}async runCallbacks(t,e){for(const s of this.iterateCallbacks(t))await s(e)}*iterateCallbacks(t){for(const e of this.u.plugins)if("function"==typeof e[t]){const s=this.g.get(e),r=r=>{const n=Object.assign(Object.assign({},r),{state:s});return e[t](n)};yield r}}waitUntil(t){return this.p.push(t),t}async doneWaiting(){let t;for(;t=this.p.shift();)await t}destroy(){this.l.resolve(null)}async v(t){let e=t,s=!1;for(const t of this.iterateCallbacks("cacheWillUpdate"))if(e=await t({request:this.request,response:e,event:this.event})||void 0,s=!0,!e)break;return s||e&&200!==e.status&&(e=void 0),e}}class v{constructor(t={}){this.cacheName=f(t.cacheName),this.plugins=t.plugins||[],this.fetchOptions=t.fetchOptions,this.matchOptions=t.matchOptions}handle(t){const[e]=this.handleAll(t);return e}handleAll(t){t instanceof FetchEvent&&(t={event:t,request:t.request});const e=t.event,s="string"==typeof t.request?new Request(t.request):t.request,r="params"in t?t.params:void 0,n=new g(this,{event:e,request:s,params:r}),i=this.q(n,s,e);return[i,this.R(i,n,s,e)]}async q(t,e,r){let n;await t.runCallbacks("handlerWillStart",{event:r,request:e});try{if(n=await this.O(e,t),!n||"error"===n.type)throw new s("no-response",{url:e.url})}catch(s){if(s instanceof Error)for(const i of t.iterateCallbacks("handlerDidError"))if(n=await i({error:s,event:r,request:e}),n)break;if(!n)throw s}for(const s of t.iterateCallbacks("handlerWillRespond"))n=await s({event:r,request:e,response:n});return n}async R(t,e,s,r){let n,i;try{n=await t}catch(i){}try{await e.runCallbacks("handlerDidRespond",{event:r,request:s,response:n}),await e.doneWaiting()}catch(t){t instanceof Error&&(i=t)}if(await e.runCallbacks("handlerDidComplete",{event:r,request:s,response:n,error:i}),e.destroy(),i)throw i}}t.NetworkFirst=class extends v{constructor(t={}){super(t),this.plugins.some((t=>"cacheWillUpdate"in t))||this.plugins.unshift(h),this._=t.networkTimeoutSeconds||0}async O(t,e){const r=[],n=[];let i;if(this._){const{id:s,promise:o}=this.C({request:t,logs:r,handler:e});i=s,n.push(o)}const o=this.U({timeoutId:i,request:t,logs:r,handler:e});n.push(o);const a=await e.waitUntil((async()=>await e.waitUntil(Promise.race(n))||await o)());if(!a)throw new s("no-response",{url:t.url});return a}C({request:t,logs:e,handler:s}){let r;return{promise:new Promise((e=>{r=setTimeout((async()=>{e(await s.cacheMatch(t))}),1e3*this._)})),id:r}}async U({timeoutId:t,request:e,logs:s,handler:r}){let n,i;try{i=await r.fetchAndCachePut(e)}catch(t){t instanceof Error&&(n=t)}return t&&clearTimeout(t),!n&&i||(i=await r.cacheMatch(e)),i}},t.NetworkOnly=class extends v{constructor(t={}){super(t),this._=t.networkTimeoutSeconds||0}async O(t,e){let r,n;try{const s=[e.fetch(t)];if(this._){const t=m(1e3*this._);s.push(t)}if(n=await Promise.race(s),!n)throw new Error(`Timed out the network response after ${this._} seconds.`)}catch(t){t instanceof Error&&(r=t)}if(!n)throw new s("no-response",{url:t.url,error:r});return n}},t.clientsClaim=function(){self.addEventListener("activate",(()=>self.clients.claim()))},t.registerRoute=function(t,e,r){let o;if("string"==typeof t){const s=new URL(t,location.href);o=new n((({url:t})=>t.href===s.href),e,r)}else if(t instanceof RegExp)o=new i(t,e,r);else if("function"==typeof t)o=new n(t,e,r);else{if(!(t instanceof n))throw new s("unsupported-route-type",{moduleName:"workbox-routing",funcName:"registerRoute",paramName:"capture"});o=t}return c().registerRoute(o),o}}));
2 | //# sourceMappingURL=workbox-06528c14.js.map
3 |
--------------------------------------------------------------------------------
/lottie/dot.json:
--------------------------------------------------------------------------------
1 | {"v":"5.7.13","fr":29.9700012207031,"ip":0,"op":70.0000028511585,"w":400,"h":400,"nm":"loader 3","ddd":0,"assets":[],"layers":[{"ddd":0,"ind":1,"ty":3,"nm":"Control layer","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[200,200,0],"ix":2,"l":2},"a":{"a":0,"k":[200,200,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"ef":[{"ty":5,"nm":"Primary color","np":3,"mn":"ADBE Color Control","ix":1,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[0.09803921568627451,0.09803921568627451,0.09803921568627451,1],"ix":1}}]},{"ty":5,"nm":"Secondary color","np":3,"mn":"ADBE Color Control","ix":2,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[0.41568627450980394,0.043137254901960784,1,1],"ix":1}}]},{"ty":5,"nm":"Position control","np":3,"mn":"ADBE Point Control","ix":3,"en":1,"ef":[{"ty":3,"nm":"Point","mn":"ADBE Point Control-0001","ix":1,"v":{"a":0,"k":[200,200],"ix":1}}]},{"ty":5,"nm":"Bg ON","np":3,"mn":"ADBE Checkbox Control","ix":4,"en":1,"ef":[{"ty":7,"nm":"Checkbox","mn":"ADBE Checkbox Control-0001","ix":1,"v":{"a":0,"k":0,"ix":1}}]},{"ty":5,"nm":"Bg Color","np":3,"mn":"ADBE Color Control","ix":5,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[1,1,1,1],"ix":1}}]},{"ty":5,"nm":"Stroke width","np":3,"mn":"ADBE Slider Control","ix":6,"en":1,"ef":[{"ty":0,"nm":"Slider","mn":"ADBE Slider Control-0001","ix":1,"v":{"a":0,"k":12,"ix":1}}]},{"ty":5,"nm":"Scale","np":3,"mn":"ADBE Slider Control","ix":7,"en":1,"ef":[{"ty":0,"nm":"Slider","mn":"ADBE Slider Control-0001","ix":1,"v":{"a":0,"k":100,"ix":1}}]}],"ip":0,"op":150.000006109625,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":2,"ty":3,"nm":"fixed null","sr":1,"ks":{"o":{"a":0,"k":0,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[292,441,0],"ix":2,"l":2,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Position control')('Point');"},"a":{"a":0,"k":[50,50,0],"ix":1,"l":2},"s":{"a":0,"k":[57,57,100],"ix":6,"l":2,"x":"var $bm_rt;\nvar temp;\ntemp = thisComp.layer('Control layer').effect('Scale')('Slider');\n$bm_rt = [\n temp,\n temp\n];"}},"ao":0,"ip":0,"op":150.000006109625,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":3,"ty":3,"nm":"Null 1","parent":2,"sr":1,"ks":{"o":{"a":0,"k":0,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[50,50,0],"ix":2,"l":2},"a":{"a":0,"k":[50,50,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"ip":0,"op":150.000006109625,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":4,"ty":4,"nm":"c3","parent":3,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":1,"k":[{"i":{"x":0.667,"y":0.667},"o":{"x":0.333,"y":0.333},"t":0,"s":[168.31,50,0],"to":null,"ti":null},{"i":{"x":0.488,"y":1},"o":{"x":0.333,"y":0},"t":15.089,"s":[168.31,50,0],"to":null,"ti":null},{"i":{"x":0.667,"y":1},"o":{"x":0.561,"y":0},"t":31.339,"s":[50,50,0],"to":null,"ti":null},{"i":{"x":0.667,"y":0.667},"o":{"x":0.333,"y":0.333},"t":48.75,"s":[168.31,50,0],"to":null,"ti":null},{"t":65.0000026475043,"s":[168.31,50,0]}],"ix":2,"l":2},"a":{"a":0,"k":[57.903,57.903,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":0,"k":{"i":[[27.904,-15.411],[15.41,27.903],[-27.904,15.411],[-15.411,-27.903]],"o":[[27.904,15.411],[-15.411,27.903],[-27.904,-15.411],[15.41,-27.903]],"v":[[27.904,0],[0,27.903],[-27.904,0],[0,-27.903]],"c":true},"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.098039223166,0.098039223166,0.098039223166,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Primary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Stroke width')('Slider');"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[57.904,57.903],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":150.000006109625,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":5,"ty":4,"nm":"c2","parent":3,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":1,"k":[{"i":{"x":0.667,"y":1},"o":{"x":0.333,"y":0},"t":0,"s":[50,50,0],"to":null,"ti":null},{"i":{"x":0.667,"y":0.667},"o":{"x":0.333,"y":0.333},"t":15.089,"s":[-68.31,50,0],"to":null,"ti":null},{"i":{"x":0.667,"y":0.667},"o":{"x":0.333,"y":0.333},"t":31.339,"s":[-68.31,50,0],"to":null,"ti":null},{"i":{"x":0.667,"y":1},"o":{"x":0.333,"y":0},"t":48.75,"s":[-68.31,50,0],"to":null,"ti":null},{"t":65.0000026475043,"s":[50,50,0]}],"ix":2,"l":2},"a":{"a":0,"k":[57.904,57.903,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":0,"k":{"i":[[27.904,-15.411],[15.411,27.903],[-27.904,15.411],[-15.41,-27.903]],"o":[[27.904,15.411],[-15.41,27.903],[-27.904,-15.411],[15.411,-27.903]],"v":[[27.904,0],[0.001,27.903],[-27.904,0],[0.001,-27.903]],"c":true},"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.098039223166,0.098039223166,0.098039223166,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Primary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Stroke width')('Slider');"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[57.904,57.903],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":150.000006109625,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":6,"ty":4,"nm":"c1","parent":3,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":1,"k":[{"i":{"x":0.833,"y":0.833},"o":{"x":0.605,"y":0},"t":0,"s":[-68.31,50,0],"to":[0.28,-35.669,0],"ti":[-37.283,3.342,0]},{"i":{"x":0.358,"y":1},"o":{"x":0.167,"y":0.167},"t":6.964,"s":[-15.376,-19.472,0],"to":[58.095,-0.735,0],"ti":[0,0,0]},{"i":{"x":0.833,"y":0.833},"o":{"x":0.669,"y":0},"t":15.089,"s":[50,50,0],"to":[0,0,0],"ti":[-55.351,-2,0]},{"i":{"x":0.332,"y":1},"o":{"x":0.167,"y":0.167},"t":23,"s":[109.155,-18,0],"to":[55.903,-1.5,0],"ti":[0.032,1,0]},{"i":{"x":0.833,"y":0.833},"o":{"x":0.742,"y":0},"t":31.339,"s":[168.31,50,0],"to":[-0.819,-25.736,0],"ti":[40.718,-1,0]},{"i":{"x":0.361,"y":1},"o":{"x":0.167,"y":0.167},"t":40.625,"s":[109.806,-18.419,0],"to":[-59.803,1.469,0],"ti":[0,0,0]},{"i":{"x":0.833,"y":0.833},"o":{"x":0.672,"y":0},"t":48.75,"s":[50,50,0],"to":[0,0,0],"ti":[52.456,-0.408,0]},{"i":{"x":0.362,"y":1},"o":{"x":0.167,"y":0.167},"t":57,"s":[-9.557,-17.389,0],"to":[-64.218,0.5,0],"ti":[-0.101,1.916,0]},{"t":65.0000026475043,"s":[-68.31,50,0]}],"ix":2,"l":2},"a":{"a":0,"k":[57.904,57.903,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":0,"k":{"i":[[27.904,-15.411],[15.411,27.903],[-27.904,15.411],[-15.41,-27.903]],"o":[[27.904,15.411],[-15.41,27.903],[-27.904,-15.411],[15.411,-27.903]],"v":[[27.904,0],[0.001,27.903],[-27.904,0],[0.001,-27.903]],"c":true},"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.415686304429,0.043137254902,1,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Secondary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Stroke width')('Slider');"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[57.904,57.903],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":150.000006109625,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":7,"ty":4,"nm":"background","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11,"x":"var $bm_rt;\nif (thisComp.layer('Control layer').effect('Bg ON')('Checkbox') > 0) {\n $bm_rt = 100;\n} else {\n $bm_rt = 0;\n}"},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[200,200,0],"ix":2,"l":2},"a":{"a":0,"k":[1,-0.5,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ty":"rc","d":1,"s":{"a":0,"k":[400,400],"ix":2},"p":{"a":0,"k":[0,0],"ix":3},"r":{"a":0,"k":0,"ix":4},"nm":"Rectangle Path 1","mn":"ADBE Vector Shape - Rect","hd":false,"_render":true},{"ty":"fl","c":{"a":0,"k":[1,1,1,1],"ix":4,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Bg Color')('Color');"},"o":{"a":0,"k":100,"ix":5},"r":1,"bm":0,"nm":"Fill 1","mn":"ADBE Vector Graphic - Fill","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[1,-0.5],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Rectangle 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":150.000006109625,"st":0,"bm":0,"completed":true}],"markers":[],"__complete":true}
--------------------------------------------------------------------------------
/lottie/setting-dark.json:
--------------------------------------------------------------------------------
1 | {"v":"5.7.13","fr":30,"ip":0,"op":30,"w":400,"h":400,"nm":"settings","ddd":0,"assets":[],"layers":[{"ddd":0,"ind":1,"ty":3,"nm":"Control layer","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[200,200,0],"ix":2,"l":2},"a":{"a":0,"k":[200,200,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"ef":[{"ty":5,"nm":"Primary color","np":3,"mn":"ADBE Color Control","ix":1,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[0.5,0.5,0.5,1],"ix":1}}]},{"ty":5,"nm":"Secondary color","np":3,"mn":"ADBE Color Control","ix":2,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[0.215686309338,0.403137256056,1,1],"ix":1}}]},{"ty":5,"nm":"Position control","np":3,"mn":"ADBE Point Control","ix":3,"en":1,"ef":[{"ty":3,"nm":"Point","mn":"ADBE Point Control-0001","ix":1,"v":{"a":0,"k":[200,200],"ix":1}}]},{"ty":5,"nm":"Bg ON","np":3,"mn":"ADBE Checkbox Control","ix":4,"en":1,"ef":[{"ty":7,"nm":"Checkbox","mn":"ADBE Checkbox Control-0001","ix":1,"v":{"a":0,"k":0,"ix":1}}]},{"ty":5,"nm":"Bg Color","np":3,"mn":"ADBE Color Control","ix":5,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[1,1,1,1],"ix":1}}]},{"ty":5,"nm":"Stroke width","np":3,"mn":"ADBE Slider Control","ix":6,"en":1,"ef":[{"ty":0,"nm":"Slider","mn":"ADBE Slider Control-0001","ix":1,"v":{"a":0,"k":12,"ix":1}}]},{"ty":5,"nm":"Scale","np":3,"mn":"ADBE Slider Control","ix":7,"en":1,"ef":[{"ty":0,"nm":"Slider","mn":"ADBE Slider Control-0001","ix":1,"v":{"a":0,"k":100,"ix":1}}]}],"ip":0,"op":150.15015015015,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":2,"ty":3,"nm":"fixed null","sr":1,"ks":{"o":{"a":0,"k":0,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[292,441,0],"ix":2,"l":2,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Position control')('Point');"},"a":{"a":0,"k":[50,50,0],"ix":1,"l":2},"s":{"a":0,"k":[57,57,100],"ix":6,"l":2,"x":"var $bm_rt;\nvar temp;\ntemp = thisComp.layer('Control layer').effect('Scale')('Slider');\n$bm_rt = [\n temp,\n temp\n];"}},"ao":0,"ip":0,"op":150.15015015015,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":3,"ty":3,"nm":"Null 1","parent":2,"sr":1,"ks":{"o":{"a":0,"k":0,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[50,50,0],"ix":2,"l":2},"a":{"a":0,"k":[50,50,0],"ix":1,"l":2},"s":{"a":0,"k":[140,140,100],"ix":6,"l":2}},"ao":0,"ip":0,"op":150.15015015015,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":4,"ty":4,"nm":"outer shape ","parent":3,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":1,"k":[{"i":{"x":[0.833],"y":[0.833]},"o":{"x":[0.167],"y":[0.167]},"t":0,"s":[0]},{"t":30,"s":[90]}],"ix":10},"p":{"a":0,"k":[50,50,0],"ix":2,"l":2},"a":{"a":0,"k":[131.395,131.4,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":0,"k":{"i":[[98.844,-21.81],[80.854,-21.81],[76.275,-23.33],[72.995,-32.07],[70.815,-39.970000000000006],[83.084,-52.24],[85.315,-58.09],[60.315,-83.08],[54.474,-85.31],[41.504,-72.35],[37.174,-70.18],[28.865000000000002,-74.00999999999999],[21.804,-78.05999999999999],[21.804,-95.69],[19.254,-101.4],[-16.095,-101.4],[-21.805,-98.84],[-21.805,-80.49],[-23.345,-75.88],[-31.985,-72.72],[-39.795,-70.64],[-52.236,-83.08],[-58.086000000000006,-85.31],[-83.086,-60.32],[-85.316,-54.47],[-72.545,-41.7],[-70.366,-37.33],[-74.345,-28.89],[-78.44500000000001,-21.81],[-95.685,-21.81],[-101.395,-19.25],[-101.395,16.1],[-98.845,21.81],[-81.245,21.81],[-76.595,23.39],[-73.366,32.370000000000005],[-71.196,40.35],[-83.086,52.24],[-85.316,58.080000000000005],[-60.316,83.08],[-54.464999999999996,85.31],[-42.265,73.11],[-37.866,70.95],[-29.126,75.05],[-21.805,79.17],[-21.805,95.68],[-19.255,101.4],[16.094,101.4],[21.804,98.84],[21.804,81.62],[23.374,77],[32.455,73.64999999999999],[40.525000000000006,71.37],[52.235,83.08],[58.083999999999996,85.31],[83.084,60.31],[85.315,54.47],[72.914,42.07],[70.76400000000001,37.720000000000006],[74.705,29.1],[78.775,21.81],[95.684,21.81],[101.394,19.25],[101.394,-16.1]],"o":[[95.684,-21.81],[78.445,-21.81],[74.344,-28.89],[70.365,-37.33],[72.544,-41.7],[85.315,-54.47],[83.084,-60.32],[58.083999999999996,-85.31],[52.235,-83.08],[39.794,-70.64],[31.985,-72.72],[23.344,-75.88],[21.804,-80.49],[21.804,-98.84],[16.094,-101.4],[-19.255,-101.4],[-21.805,-95.69],[-21.805,-78.05999999999999],[-28.866,-74.00999999999999],[-37.174,-70.18],[-41.505,-72.35],[-54.464999999999996,-85.31],[-60.316,-83.08],[-85.316,-58.09],[-83.086,-52.24],[-70.816,-39.970000000000006],[-72.99600000000001,-32.07],[-76.276,-23.33],[-80.855,-21.81],[-98.845,-21.81],[-101.395,-16.1],[-101.395,19.25],[-95.685,21.81],[-78.775,21.81],[-74.70599999999999,29.1],[-70.765,37.720000000000006],[-72.916,42.07],[-85.316,54.47],[-83.086,60.31],[-58.086000000000006,85.31],[-52.236,83.08],[-40.526,71.37],[-32.455999999999996,73.64999999999999],[-23.376,77],[-21.805,81.62],[-21.805,98.84],[-16.095,101.4],[19.254,101.4],[21.804,95.68],[21.804,79.17],[29.124,75.05],[37.865,70.95],[42.264,73.11],[54.474,85.31],[60.315,83.08],[85.315,58.080000000000005],[83.084,52.24],[71.19500000000001,40.35],[73.36500000000001,32.370000000000005],[76.59400000000001,23.39],[81.245,21.81],[98.844,21.81],[101.394,16.1],[101.394,-19.25]],"v":[[95.684,-21.81],[80.854,-21.81],[75.485,-25.61],[71.464,-35.14],[72.544,-41.7],[83.084,-52.24],[83.084,-60.32],[60.315,-83.08],[52.235,-83.08],[41.504,-72.35],[34.995,-71.25],[25.655,-75.1],[21.804,-80.49],[21.804,-95.69],[16.094,-101.4],[-16.095,-101.4],[-21.805,-95.69],[-21.805,-80.49],[-25.656,-75.1],[-34.995,-71.25],[-41.505,-72.35],[-52.236,-83.08],[-60.316,-83.08],[-83.086,-60.32],[-83.086,-52.24],[-72.545,-41.7],[-71.465,-35.14],[-75.475,-25.61],[-80.855,-21.81],[-95.685,-21.81],[-101.395,-16.1],[-101.395,16.1],[-95.685,21.81],[-81.245,21.81],[-75.826,25.73],[-71.836,35.52],[-72.916,42.07],[-83.086,52.24],[-83.086,60.31],[-60.316,83.08],[-52.236,83.08],[-42.265,73.11],[-35.666,72.05],[-25.696,76.21],[-21.805,81.62],[-21.805,95.68],[-16.095,101.4],[16.094,101.4],[21.804,95.68],[21.804,81.62],[25.695,76.21],[35.664,72.05],[42.264,73.11],[52.235,83.08],[60.315,83.08],[83.084,60.31],[83.084,52.24],[72.914,42.07],[71.834,35.52],[75.825,25.73],[81.245,21.81],[95.684,21.81],[101.394,16.1],[101.394,-16.1]],"c":true},"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.098039223166,0.098039223166,0.098039223166,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Primary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = $bm_mul(100 / 140, thisComp.layer('Control layer').effect('Stroke width')('Slider'));"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[131.395,131.4],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":150,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":5,"ty":4,"nm":"circle","parent":3,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[50,49.995,0],"ix":2,"l":2},"a":{"a":0,"k":[77.585,77.585,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":0,"k":{"i":[[26.285,47.585],[-47.585,26.285],[-26.275000000000002,-47.585],[47.585,-26.275000000000002]],"o":[[-26.275000000000002,47.585],[-47.585,-26.275000000000002],[26.285,-47.585],[47.585,26.285]],"v":[[0.005,47.585],[-47.585,0.005],[0.005,-47.585],[47.585,0.005]],"c":true},"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.415686304429,0.043137254902,1,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Secondary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = $bm_mul(100 / 140, thisComp.layer('Control layer').effect('Stroke width')('Slider'));"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[77.585,77.585],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":150,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":6,"ty":4,"nm":"background","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11,"x":"var $bm_rt;\nif (thisComp.layer('Control layer').effect('Bg ON')('Checkbox') > 0) {\n $bm_rt = 100;\n} else {\n $bm_rt = 0;\n}"},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[200,200,0],"ix":2,"l":2},"a":{"a":0,"k":[1,-0.5,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ty":"rc","d":1,"s":{"a":0,"k":[400,400],"ix":2},"p":{"a":0,"k":[0,0],"ix":3},"r":{"a":0,"k":0,"ix":4},"nm":"Rectangle Path 1","mn":"ADBE Vector Shape - Rect","hd":false,"_render":true},{"ty":"fl","c":{"a":0,"k":[1,1,1,1],"ix":4,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Bg Color')('Color');"},"o":{"a":0,"k":100,"ix":5},"r":1,"bm":0,"nm":"Fill 1","mn":"ADBE Vector Graphic - Fill","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[1,-0.5],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Rectangle 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":150,"st":0,"bm":0,"completed":true}],"markers":[],"__complete":true}
--------------------------------------------------------------------------------
/lottie/setting.json:
--------------------------------------------------------------------------------
1 | {"v":"5.7.13","fr":30,"ip":0,"op":30,"w":400,"h":400,"nm":"settings","ddd":0,"assets":[],"layers":[{"ddd":0,"ind":1,"ty":3,"nm":"Control layer","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[200,200,0],"ix":2,"l":2},"a":{"a":0,"k":[200,200,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"ef":[{"ty":5,"nm":"Primary color","np":3,"mn":"ADBE Color Control","ix":1,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[0.09803921568627451,0.09803921568627451,0.09803921568627451,1],"ix":1}}]},{"ty":5,"nm":"Secondary color","np":3,"mn":"ADBE Color Control","ix":2,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[0.415686309338,0.043137256056,1,1],"ix":1}}]},{"ty":5,"nm":"Position control","np":3,"mn":"ADBE Point Control","ix":3,"en":1,"ef":[{"ty":3,"nm":"Point","mn":"ADBE Point Control-0001","ix":1,"v":{"a":0,"k":[200,200],"ix":1}}]},{"ty":5,"nm":"Bg ON","np":3,"mn":"ADBE Checkbox Control","ix":4,"en":1,"ef":[{"ty":7,"nm":"Checkbox","mn":"ADBE Checkbox Control-0001","ix":1,"v":{"a":0,"k":0,"ix":1}}]},{"ty":5,"nm":"Bg Color","np":3,"mn":"ADBE Color Control","ix":5,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[1,1,1,1],"ix":1}}]},{"ty":5,"nm":"Stroke width","np":3,"mn":"ADBE Slider Control","ix":6,"en":1,"ef":[{"ty":0,"nm":"Slider","mn":"ADBE Slider Control-0001","ix":1,"v":{"a":0,"k":12,"ix":1}}]},{"ty":5,"nm":"Scale","np":3,"mn":"ADBE Slider Control","ix":7,"en":1,"ef":[{"ty":0,"nm":"Slider","mn":"ADBE Slider Control-0001","ix":1,"v":{"a":0,"k":100,"ix":1}}]}],"ip":0,"op":150.15015015015,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":2,"ty":3,"nm":"fixed null","sr":1,"ks":{"o":{"a":0,"k":0,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[292,441,0],"ix":2,"l":2,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Position control')('Point');"},"a":{"a":0,"k":[50,50,0],"ix":1,"l":2},"s":{"a":0,"k":[57,57,100],"ix":6,"l":2,"x":"var $bm_rt;\nvar temp;\ntemp = thisComp.layer('Control layer').effect('Scale')('Slider');\n$bm_rt = [\n temp,\n temp\n];"}},"ao":0,"ip":0,"op":150.15015015015,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":3,"ty":3,"nm":"Null 1","parent":2,"sr":1,"ks":{"o":{"a":0,"k":0,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[50,50,0],"ix":2,"l":2},"a":{"a":0,"k":[50,50,0],"ix":1,"l":2},"s":{"a":0,"k":[140,140,100],"ix":6,"l":2}},"ao":0,"ip":0,"op":150.15015015015,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":4,"ty":4,"nm":"outer shape ","parent":3,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":1,"k":[{"i":{"x":[0.833],"y":[0.833]},"o":{"x":[0.167],"y":[0.167]},"t":0,"s":[0]},{"t":30,"s":[90]}],"ix":10},"p":{"a":0,"k":[50,50,0],"ix":2,"l":2},"a":{"a":0,"k":[131.395,131.4,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":0,"k":{"i":[[98.844,-21.81],[80.854,-21.81],[76.275,-23.33],[72.995,-32.07],[70.815,-39.970000000000006],[83.084,-52.24],[85.315,-58.09],[60.315,-83.08],[54.474,-85.31],[41.504,-72.35],[37.174,-70.18],[28.865000000000002,-74.00999999999999],[21.804,-78.05999999999999],[21.804,-95.69],[19.254,-101.4],[-16.095,-101.4],[-21.805,-98.84],[-21.805,-80.49],[-23.345,-75.88],[-31.985,-72.72],[-39.795,-70.64],[-52.236,-83.08],[-58.086000000000006,-85.31],[-83.086,-60.32],[-85.316,-54.47],[-72.545,-41.7],[-70.366,-37.33],[-74.345,-28.89],[-78.44500000000001,-21.81],[-95.685,-21.81],[-101.395,-19.25],[-101.395,16.1],[-98.845,21.81],[-81.245,21.81],[-76.595,23.39],[-73.366,32.370000000000005],[-71.196,40.35],[-83.086,52.24],[-85.316,58.080000000000005],[-60.316,83.08],[-54.464999999999996,85.31],[-42.265,73.11],[-37.866,70.95],[-29.126,75.05],[-21.805,79.17],[-21.805,95.68],[-19.255,101.4],[16.094,101.4],[21.804,98.84],[21.804,81.62],[23.374,77],[32.455,73.64999999999999],[40.525000000000006,71.37],[52.235,83.08],[58.083999999999996,85.31],[83.084,60.31],[85.315,54.47],[72.914,42.07],[70.76400000000001,37.720000000000006],[74.705,29.1],[78.775,21.81],[95.684,21.81],[101.394,19.25],[101.394,-16.1]],"o":[[95.684,-21.81],[78.445,-21.81],[74.344,-28.89],[70.365,-37.33],[72.544,-41.7],[85.315,-54.47],[83.084,-60.32],[58.083999999999996,-85.31],[52.235,-83.08],[39.794,-70.64],[31.985,-72.72],[23.344,-75.88],[21.804,-80.49],[21.804,-98.84],[16.094,-101.4],[-19.255,-101.4],[-21.805,-95.69],[-21.805,-78.05999999999999],[-28.866,-74.00999999999999],[-37.174,-70.18],[-41.505,-72.35],[-54.464999999999996,-85.31],[-60.316,-83.08],[-85.316,-58.09],[-83.086,-52.24],[-70.816,-39.970000000000006],[-72.99600000000001,-32.07],[-76.276,-23.33],[-80.855,-21.81],[-98.845,-21.81],[-101.395,-16.1],[-101.395,19.25],[-95.685,21.81],[-78.775,21.81],[-74.70599999999999,29.1],[-70.765,37.720000000000006],[-72.916,42.07],[-85.316,54.47],[-83.086,60.31],[-58.086000000000006,85.31],[-52.236,83.08],[-40.526,71.37],[-32.455999999999996,73.64999999999999],[-23.376,77],[-21.805,81.62],[-21.805,98.84],[-16.095,101.4],[19.254,101.4],[21.804,95.68],[21.804,79.17],[29.124,75.05],[37.865,70.95],[42.264,73.11],[54.474,85.31],[60.315,83.08],[85.315,58.080000000000005],[83.084,52.24],[71.19500000000001,40.35],[73.36500000000001,32.370000000000005],[76.59400000000001,23.39],[81.245,21.81],[98.844,21.81],[101.394,16.1],[101.394,-19.25]],"v":[[95.684,-21.81],[80.854,-21.81],[75.485,-25.61],[71.464,-35.14],[72.544,-41.7],[83.084,-52.24],[83.084,-60.32],[60.315,-83.08],[52.235,-83.08],[41.504,-72.35],[34.995,-71.25],[25.655,-75.1],[21.804,-80.49],[21.804,-95.69],[16.094,-101.4],[-16.095,-101.4],[-21.805,-95.69],[-21.805,-80.49],[-25.656,-75.1],[-34.995,-71.25],[-41.505,-72.35],[-52.236,-83.08],[-60.316,-83.08],[-83.086,-60.32],[-83.086,-52.24],[-72.545,-41.7],[-71.465,-35.14],[-75.475,-25.61],[-80.855,-21.81],[-95.685,-21.81],[-101.395,-16.1],[-101.395,16.1],[-95.685,21.81],[-81.245,21.81],[-75.826,25.73],[-71.836,35.52],[-72.916,42.07],[-83.086,52.24],[-83.086,60.31],[-60.316,83.08],[-52.236,83.08],[-42.265,73.11],[-35.666,72.05],[-25.696,76.21],[-21.805,81.62],[-21.805,95.68],[-16.095,101.4],[16.094,101.4],[21.804,95.68],[21.804,81.62],[25.695,76.21],[35.664,72.05],[42.264,73.11],[52.235,83.08],[60.315,83.08],[83.084,60.31],[83.084,52.24],[72.914,42.07],[71.834,35.52],[75.825,25.73],[81.245,21.81],[95.684,21.81],[101.394,16.1],[101.394,-16.1]],"c":true},"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.098039223166,0.098039223166,0.098039223166,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Primary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = $bm_mul(100 / 140, thisComp.layer('Control layer').effect('Stroke width')('Slider'));"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[131.395,131.4],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":150,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":5,"ty":4,"nm":"circle","parent":3,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[50,49.995,0],"ix":2,"l":2},"a":{"a":0,"k":[77.585,77.585,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":0,"k":{"i":[[26.285,47.585],[-47.585,26.285],[-26.275000000000002,-47.585],[47.585,-26.275000000000002]],"o":[[-26.275000000000002,47.585],[-47.585,-26.275000000000002],[26.285,-47.585],[47.585,26.285]],"v":[[0.005,47.585],[-47.585,0.005],[0.005,-47.585],[47.585,0.005]],"c":true},"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.415686304429,0.043137254902,1,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Secondary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = $bm_mul(100 / 140, thisComp.layer('Control layer').effect('Stroke width')('Slider'));"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[77.585,77.585],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":150,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":6,"ty":4,"nm":"background","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11,"x":"var $bm_rt;\nif (thisComp.layer('Control layer').effect('Bg ON')('Checkbox') > 0) {\n $bm_rt = 100;\n} else {\n $bm_rt = 0;\n}"},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[200,200,0],"ix":2,"l":2},"a":{"a":0,"k":[1,-0.5,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ty":"rc","d":1,"s":{"a":0,"k":[400,400],"ix":2},"p":{"a":0,"k":[0,0],"ix":3},"r":{"a":0,"k":0,"ix":4},"nm":"Rectangle Path 1","mn":"ADBE Vector Shape - Rect","hd":false,"_render":true},{"ty":"fl","c":{"a":0,"k":[1,1,1,1],"ix":4,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Bg Color')('Color');"},"o":{"a":0,"k":100,"ix":5},"r":1,"bm":0,"nm":"Fill 1","mn":"ADBE Vector Graphic - Fill","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[1,-0.5],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Rectangle 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":150,"st":0,"bm":0,"completed":true}],"markers":[],"__complete":true}
--------------------------------------------------------------------------------
/lottie/info.json:
--------------------------------------------------------------------------------
1 | {"v":"5.7.13","fr":30,"ip":0,"op":31,"w":400,"h":400,"nm":"information","ddd":0,"assets":[],"layers":[{"ddd":0,"ind":1,"ty":3,"nm":"Control layer","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[200,200,0],"ix":2,"l":2},"a":{"a":0,"k":[200,200,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"ef":[{"ty":5,"nm":"Primary color","np":3,"mn":"ADBE Color Control","ix":1,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[1,1,1,1],"ix":1}}]},{"ty":5,"nm":"Secondary color","np":3,"mn":"ADBE Color Control","ix":2,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[1,1,1,1],"ix":1}}]},{"ty":5,"nm":"Position control","np":3,"mn":"ADBE Point Control","ix":3,"en":1,"ef":[{"ty":3,"nm":"Point","mn":"ADBE Point Control-0001","ix":1,"v":{"a":0,"k":[200,200],"ix":1}}]},{"ty":5,"nm":"Bg ON","np":3,"mn":"ADBE Checkbox Control","ix":4,"en":1,"ef":[{"ty":7,"nm":"Checkbox","mn":"ADBE Checkbox Control-0001","ix":1,"v":{"a":0,"k":0,"ix":1}}]},{"ty":5,"nm":"Bg Color","np":3,"mn":"ADBE Color Control","ix":5,"en":1,"ef":[{"ty":2,"nm":"Color","mn":"ADBE Color Control-0001","ix":1,"v":{"a":0,"k":[1,1,1,1],"ix":1}}]},{"ty":5,"nm":"Stroke width","np":3,"mn":"ADBE Slider Control","ix":6,"en":1,"ef":[{"ty":0,"nm":"Slider","mn":"ADBE Slider Control-0001","ix":1,"v":{"a":0,"k":12,"ix":1}}]},{"ty":5,"nm":"Scale","np":3,"mn":"ADBE Slider Control","ix":7,"en":1,"ef":[{"ty":0,"nm":"Slider","mn":"ADBE Slider Control-0001","ix":1,"v":{"a":0,"k":100,"ix":1}}]}],"ip":0,"op":150.15015015015,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":2,"ty":3,"nm":"fixed null","sr":1,"ks":{"o":{"a":0,"k":0,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[292,441,0],"ix":2,"l":2,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Position control')('Point');"},"a":{"a":0,"k":[50,50,0],"ix":1,"l":2},"s":{"a":0,"k":[57,57,100],"ix":6,"l":2,"x":"var $bm_rt;\nvar temp;\ntemp = thisComp.layer('Control layer').effect('Scale')('Slider');\n$bm_rt = [\n temp,\n temp\n];"}},"ao":0,"ip":0,"op":150.15015015015,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":3,"ty":3,"nm":"Null 1","parent":2,"sr":1,"ks":{"o":{"a":0,"k":0,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[50,50,0],"ix":2,"l":2},"a":{"a":0,"k":[50,50,0],"ix":1,"l":2},"s":{"a":0,"k":[123,123,100],"ix":6,"l":2}},"ao":0,"ip":0,"op":150.15015015015,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":4,"ty":4,"nm":"circle ","parent":3,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[50,50,0],"ix":2,"l":2},"a":{"a":0,"k":[152.087,152.087,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":0,"k":{"i":[[122.087,-67.427],[67.427,122.087],[-122.087,67.427],[-67.427,-122.087]],"o":[[122.087,67.427],[-67.427,122.087],[-122.087,-67.427],[67.427,-122.087]],"v":[[122.087,0],[0,122.087],[-122.087,0],[0,-122.087]],"c":true},"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.098039223166,0.098039223166,0.098039223166,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Primary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = $bm_mul(100 / 123, thisComp.layer('Control layer').effect('Stroke width')('Slider'));"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[152.087,152.087],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":151,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":5,"ty":4,"nm":"i ","parent":3,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[41.511,73.34,0],"ix":2,"l":2},"a":{"a":0,"k":[42.554,83.55,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":0,"k":{"i":[[28.978,137.101],[79.108,137.101]],"o":[[28.978,137.101],[79.108,137.101]],"v":[[28.978,137.101],[79.108,137.101]],"c":false},"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.415686304429,0.043137254902,1,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Secondary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = $bm_mul(100 / 123, thisComp.layer('Control layer').effect('Stroke width')('Slider'));"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[0,0],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true},{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":1,"k":[{"i":{"x":0.667,"y":1},"o":{"x":0.333,"y":0},"t":0,"s":[{"i":[[-12.521,-53.551],[7.721,-53.551],[12.521,-51.401],[12.521,53.551]],"o":[[-12.521,-53.551],[10.372,-53.551],[12.521,-48.749],[12.521,53.551]],"v":[[-12.521,-53.551],[7.721,-53.551],[12.521,-48.749],[12.521,53.551]],"c":false}]},{"i":{"x":0.667,"y":1},"o":{"x":0.333,"y":0},"t":5,"s":[{"i":[[-12.521,-42.55],[7.721,-42.55],[12.521,-40.401],[12.521,53.551]],"o":[[-12.521,-42.55],[10.372,-42.55],[12.521,-37.749],[12.521,53.551]],"v":[[-12.521,-42.55],[7.721,-42.55],[12.521,-37.749],[12.521,53.551]],"c":false}]},{"i":{"x":0.667,"y":1},"o":{"x":0.333,"y":0},"t":10,"s":[{"i":[[-12.521,-65.05],[7.721,-65.05],[12.521,-62.901],[12.521,53.551]],"o":[[-12.521,-65.05],[10.372,-65.05],[12.521,-60.249],[12.521,53.551]],"v":[[-12.521,-65.05],[7.721,-65.05],[12.521,-60.249],[12.521,53.551]],"c":false}]},{"i":{"x":0.667,"y":1},"o":{"x":0.333,"y":0},"t":15,"s":[{"i":[[-12.521,-45.05],[7.721,-45.05],[12.521,-42.901],[12.521,53.551]],"o":[[-12.521,-45.05],[10.372,-45.05],[12.521,-40.249],[12.521,53.551]],"v":[[-12.521,-45.05],[7.721,-45.05],[12.521,-40.249],[12.521,53.551]],"c":false}]},{"t":21,"s":[{"i":[[-12.521,-53.551],[7.721,-53.551],[12.521,-51.401],[12.521,53.551]],"o":[[-12.521,-53.551],[10.372,-53.551],[12.521,-48.749],[12.521,53.551]],"v":[[-12.521,-53.551],[7.721,-53.551],[12.521,-48.749],[12.521,53.551]],"c":false}]}],"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.415686304429,0.043137254902,1,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Secondary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = $bm_mul(100 / 123, thisComp.layer('Control layer').effect('Stroke width')('Slider'));"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[42.521,83.551],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 2","np":2,"cix":2,"bm":0,"ix":2,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":151,"st":0,"bm":0,"completed":true},{"ddd":0,"ind":6,"ty":4,"nm":"dot ","parent":3,"sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":1,"k":[{"i":{"x":0.667,"y":1},"o":{"x":0.333,"y":0},"t":1.105,"s":[41.478,-12.038,0],"to":null,"ti":null},{"i":{"x":0.667,"y":1},"o":{"x":0.333,"y":0},"t":6,"s":[41.478,-2.038,0],"to":null,"ti":null},{"i":{"x":0.667,"y":1},"o":{"x":0.333,"y":0},"t":11,"s":[41.478,-38.038,0],"to":null,"ti":null},{"i":{"x":0.667,"y":1},"o":{"x":0.333,"y":0},"t":16,"s":[41.478,-2.038,0],"to":null,"ti":null},{"t":22,"s":[41.478,-12.038,0]}],"ix":2,"l":2},"a":{"a":0,"k":[41.854,41.853,0],"ix":1,"l":2},"s":{"a":1,"k":[{"i":{"x":[0.667,0.667,0.667],"y":[1,1,1]},"o":{"x":[0.333,0.333,0.333],"y":[0,0,0]},"t":1,"s":[100,100,100]},{"i":{"x":[0.667,0.667,0.667],"y":[1,1,1]},"o":{"x":[0.333,0.333,0.333],"y":[0,0,0]},"t":3,"s":[100,112,100]},{"i":{"x":[0.667,0.667,0.667],"y":[1,1,1]},"o":{"x":[0.333,0.333,0.333],"y":[0,0,0]},"t":6,"s":[100,100,100]},{"i":{"x":[0.667,0.667,0.667],"y":[1,1,1]},"o":{"x":[0.333,0.333,0.333],"y":[0,0,0]},"t":8,"s":[100,112,100]},{"i":{"x":[0.667,0.667,0.667],"y":[1,1,1]},"o":{"x":[0.333,0.333,0.333],"y":[0,0,0]},"t":11,"s":[100,100,100]},{"i":{"x":[0.667,0.667,0.667],"y":[1,1,1]},"o":{"x":[0.333,0.333,0.333],"y":[0,0,0]},"t":13,"s":[100,112,100]},{"t":16,"s":[100,100,100]}],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ind":0,"ty":"sh","ix":1,"ks":{"a":0,"k":{"i":[[11.854,-6.546],[6.546,11.853],[-11.854,6.546],[-6.547,-11.853]],"o":[[11.854,6.546],[-6.547,11.853],[-11.854,-6.546],[6.546,-11.853]],"v":[[11.854,0],[0,11.853],[-11.854,0],[0,-11.853]],"c":true},"ix":2},"nm":"Path 1","mn":"ADBE Vector Shape - Group","hd":false,"_render":true},{"ty":"st","c":{"a":0,"k":[0.415686304429,0.043137254902,1,1],"ix":3,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Secondary color')('Color');"},"o":{"a":0,"k":100,"ix":4},"w":{"a":0,"k":12,"ix":5,"x":"var $bm_rt;\n$bm_rt = $bm_mul(100 / 123, thisComp.layer('Control layer').effect('Stroke width')('Slider'));"},"lc":2,"lj":2,"bm":0,"nm":"Stroke 1","mn":"ADBE Vector Graphic - Stroke","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[41.854,41.853],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Group 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":152,"st":1,"bm":0,"completed":true},{"ddd":0,"ind":7,"ty":4,"nm":"background","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11,"x":"var $bm_rt;\nif (thisComp.layer('Control layer').effect('Bg ON')('Checkbox') > 0) {\n $bm_rt = 100;\n} else {\n $bm_rt = 0;\n}"},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[200,200,0],"ix":2,"l":2},"a":{"a":0,"k":[1,-0.5,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"ty":"rc","d":1,"s":{"a":0,"k":[400,400],"ix":2},"p":{"a":0,"k":[0,0],"ix":3},"r":{"a":0,"k":0,"ix":4},"nm":"Rectangle Path 1","mn":"ADBE Vector Shape - Rect","hd":false,"_render":true},{"ty":"fl","c":{"a":0,"k":[1,1,1,1],"ix":4,"x":"var $bm_rt;\n$bm_rt = thisComp.layer('Control layer').effect('Bg Color')('Color');"},"o":{"a":0,"k":100,"ix":5},"r":1,"bm":0,"nm":"Fill 1","mn":"ADBE Vector Graphic - Fill","hd":false,"_render":true},{"ty":"tr","p":{"a":0,"k":[1,-0.5],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"Transform","_render":true}],"nm":"Rectangle 1","np":2,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false,"_render":true}],"ip":0,"op":150.15015015015,"st":0,"bm":0,"completed":true}],"markers":[],"__complete":true}
--------------------------------------------------------------------------------
/components/Chat/index.tsx:
--------------------------------------------------------------------------------
1 | import { useState, useEffect, useRef } from "react";
2 | import Link from "next/link";
3 | import ChatRecords, { AvatarComponent } from "../ChatRecord";
4 | import Intro from "../Intro";
5 | import { fetcher } from "../../helpers/fetcher";
6 | import { formatClaudePrompt } from "../../helpers/cluade.helpers";
7 | import dynamic from "next/dynamic";
8 | import { builtinPrompts } from "../../data/prompts";
9 | import { useAssistantRole } from "../../contexts/assistant";
10 | import { useModelSetting } from "../../contexts/modelSetting";
11 | import { v4 as uuidv4 } from "uuid";
12 | import Lottie from "../Lottie";
13 | import dot from "../../lottie/dot.json";
14 | import setting from "../../lottie/setting.json";
15 | import settingDark from "../../lottie/setting-dark.json";
16 | import cls from "classnames";
17 | import { useKBar } from "kbar";
18 | import FastOperations from "../FastOperations";
19 |
20 | import { useIsSupportCapture } from "../../hooks/useIsSupportCapture";
21 |
22 | import { useLocalStorage } from "react-use";
23 | import ThemeChanger from "../ThemeChanger";
24 | import { useTheme } from "next-themes";
25 |
26 | import type { FileInfo } from "../FastOperations";
27 |
28 | const FunctionalZone = dynamic(() => import("../FunctionalZone"), {
29 | ssr: false,
30 | });
31 |
32 | const Chat = () => {
33 | const { query } = useKBar();
34 | const { value } = useAssistantRole();
35 | const { value: modelSetting } = useModelSetting();
36 | const [err, setErr] = useState("");
37 | const chatWrapperRef = useRef(null);
38 | const [text, setText] = useState("");
39 | const textAreaRef = useRef(null);
40 | const [waiting, setWaiting] = useState(false);
41 | const [fastZoneVisible, setFastZoneVisible] = useState(false);
42 | const [file, setFile] = useState(null);
43 |
44 | const assistantRole =
45 | builtinPrompts.find((p) => p.id === value) ?? builtinPrompts[0];
46 |
47 | const isMobile = useIsSupportCapture();
48 |
49 | const [chats, setChats] = useLocalStorage("ec-records");
50 | const { theme } = useTheme();
51 |
52 | useEffect(() => {
53 | if (chats?.length && chatWrapperRef.current) {
54 | chatWrapperRef.current.scrollTop =
55 | chatWrapperRef.current.scrollHeight + 20;
56 | }
57 | }, [chats]);
58 |
59 | const sendChat = async () => {
60 | if (!text.trim() || waiting) {
61 | return;
62 | }
63 |
64 | if (textAreaRef.current) {
65 | textAreaRef.current.style.height = "40px";
66 | }
67 |
68 | const _chats: ChatMessage[] = [
69 | ...(chats ?? []),
70 | {
71 | role: "user",
72 | id: uuidv4(),
73 | text,
74 | date: Date.now(),
75 | conversationId: assistantRole?.id,
76 | },
77 | ];
78 |
79 | setChats(_chats);
80 |
81 | const claudePrompt = formatClaudePrompt(
82 | _chats,
83 | assistantRole,
84 | file?.content
85 | );
86 |
87 | setText("");
88 | setWaiting(true);
89 | setErr("");
90 |
91 | try {
92 | const gptResponse = await fetcher("/api/sendChat", {
93 | headers: {
94 | Accept: "application/json",
95 | "Content-Type": "application/json",
96 | },
97 | method: "POST",
98 | body: JSON.stringify({
99 | text: claudePrompt,
100 | id: "1",
101 | model: modelSetting?.model,
102 | hasFile: !!file,
103 | temperature: modelSetting?.temperature,
104 | maxTokens: modelSetting?.maxTokens,
105 | }),
106 | });
107 |
108 | // const response = await fetch("/api/sse", {
109 | // method: "POST",
110 | // headers: {
111 | // "Content-Type": "application/json",
112 | // },
113 | // body: JSON.stringify({
114 | // text: claudePrompt,
115 | // }),
116 | // });
117 |
118 | // if (!response.ok) {
119 | // throw new Error(response.statusText);
120 | // }
121 |
122 | // const data = response.body;
123 | // if (!data) {
124 | // return;
125 | // }
126 |
127 | // const reader = data.getReader();
128 | // const decoder = new TextDecoder();
129 |
130 | // let done = false;
131 | // let chunkValue = '';
132 | // const chatId = uuidv4();
133 | // const chatDate = Date.now();
134 |
135 | // while (!done) {
136 | // const { value, done: doneReading } = await reader.read();
137 | // done = doneReading;
138 | // if (!done) {
139 | // const _chunkValue = decoder.decode(value);
140 |
141 | // // FIXME: 这里有点奇怪,数据不是按序返回的
142 | // if (!chunkValue.includes(_chunkValue)) {
143 | // chunkValue = _chunkValue;
144 | // console.log('chunkValue', chunkValue);
145 | // setChats([ ..._chats, {
146 | // id: chatId,
147 | // date: chatDate,
148 | // role: 'assistant',
149 | // text: chunkValue,
150 | // conversationId: assistantRole?.id
151 | // } ]);
152 | // }
153 |
154 | // }
155 |
156 | // // setChats([ ..._chats, { ...gptResponse, conversationId: assistantRole?.id } ]);
157 | // }
158 |
159 | if (gptResponse?.error) {
160 | throw new Error(gptResponse.error);
161 | }
162 |
163 | setChats([
164 | ..._chats,
165 | { ...gptResponse, conversationId: assistantRole?.id },
166 | ]);
167 | } catch (e) {
168 | if (e instanceof Error) {
169 | setErr(e.message);
170 | }
171 | setErr("我的服务器好像遇到点问题,你可以稍后再试试。");
172 | } finally {
173 | setWaiting(false);
174 | }
175 | };
176 | return (
177 |
178 | {/* Header */}
179 |
180 |
181 |
新聊天
182 |
183 | 开启一个新聊天
184 |
185 |
186 |
187 |
188 |
189 | {isMobile && (
190 |
191 | {/* key for refresh Lottie cache */}
192 |
199 |
200 | )}
201 |
202 |
203 |
204 |
205 |
206 |
207 |
208 | {chats &&
}
209 |
210 | {/* 这里要替换掉 */}
211 | {waiting && (
212 |
213 |
214 |
215 |
我假装在思考中 {" "}
216 |
222 |
223 |
224 |
225 | )}
226 |
227 | {err && (
228 |
232 | )}
233 |
234 | {assistantRole ? (
235 |
236 |
237 | 当前正在跟{" "}
238 |
239 | {assistantRole.title}
240 |
241 | {!!file && (
242 |
243 | ({file.name})
244 |
245 | )}
246 | {" "}
247 | 聊天
248 |
249 |
250 |
251 | 模型
252 |
253 | :{modelSetting?.model ?? "claude-instant-v1"}
254 |
255 | 温度
256 |
257 | :{modelSetting?.temperature ?? 0.7}
258 |
259 | 生成长度
260 |
261 | :{modelSetting?.maxTokens ?? 400}
262 |
263 |
264 | ) : null}
265 |
266 |
267 |
268 |
269 | {/* Footer */}
270 |
271 |
272 |
273 |
274 |
314 |
315 |
setFastZoneVisible(false)}
318 | onFileUpload={(fileInfo) => setFile(fileInfo)}
319 | >
320 | Hidden Item
321 |
322 |
323 | {!isMobile && (
324 |
325 |
330 | ⌘
331 | K
332 |
333 |
334 | )}
335 |
336 |
337 |
343 | → 发送
344 |
345 |
346 |
347 |
348 |
349 | easierChat.com - 一个更方便、易用的 chatBot 客户端
350 |
351 | FAQs |{" "}
352 | @那吒 |{" "}
353 | 提交反馈 |{" "}
354 |
355 | macOS 客户端
356 |
357 |
358 |
359 |
360 |
361 | );
362 | };
363 |
364 | export default Chat;
365 |
--------------------------------------------------------------------------------
/styles/markdown.css:
--------------------------------------------------------------------------------
1 | .markdown-body ol,
2 | .markdown-body ul,
3 | .markdown-body menu {
4 | list-style: auto;
5 | }
6 |
7 | .markdown-body .octicon {
8 | display: inline-block;
9 | fill: currentColor;
10 | vertical-align: text-bottom;
11 | }
12 |
13 | .markdown-body h1:hover .anchor .octicon-link:before,
14 | .markdown-body h2:hover .anchor .octicon-link:before,
15 | .markdown-body h3:hover .anchor .octicon-link:before,
16 | .markdown-body h4:hover .anchor .octicon-link:before,
17 | .markdown-body h5:hover .anchor .octicon-link:before,
18 | .markdown-body h6:hover .anchor .octicon-link:before {
19 | width: 16px;
20 | height: 16px;
21 | content: ' ';
22 | display: inline-block;
23 | background-color: currentColor;
24 | -webkit-mask-image: url("data:image/svg+xml, ");
25 | mask-image: url("data:image/svg+xml, ");
26 | }
27 |
28 | .markdown-body details,
29 | .markdown-body figcaption,
30 | .markdown-body figure {
31 | display: block;
32 | }
33 |
34 | .markdown-body summary {
35 | display: list-item;
36 | }
37 |
38 | .markdown-body [hidden] {
39 | display: none !important;
40 | }
41 |
42 | .markdown-body a {
43 | background-color: transparent;
44 | color: #0969da;
45 | text-decoration: none;
46 | }
47 |
48 | .markdown-body a:active,
49 | .markdown-body a:hover {
50 | outline-width: 0;
51 | }
52 |
53 | .markdown-body abbr[title] {
54 | border-bottom: none;
55 | text-decoration: underline dotted;
56 | }
57 |
58 | .markdown-body b,
59 | .markdown-body strong {
60 | font-weight: 600;
61 | }
62 |
63 | .markdown-body dfn {
64 | font-style: italic;
65 | }
66 |
67 | .markdown-body h1 {
68 | margin: .67em 0;
69 | font-weight: 600;
70 | padding-bottom: .3em;
71 | font-size: 2em;
72 | border-bottom: 1px solid hsla(210,18%,87%,1);
73 | }
74 |
75 | .markdown-body mark {
76 | background-color: #fff8c5;
77 | color: #24292f;
78 | }
79 |
80 | .markdown-body small {
81 | font-size: 90%;
82 | }
83 |
84 | .markdown-body sub,
85 | .markdown-body sup {
86 | font-size: 75%;
87 | line-height: 0;
88 | position: relative;
89 | vertical-align: baseline;
90 | }
91 |
92 | .markdown-body sub {
93 | bottom: -0.25em;
94 | }
95 |
96 | .markdown-body sup {
97 | top: -0.5em;
98 | }
99 |
100 | .markdown-body img {
101 | border-style: none;
102 | max-width: 100%;
103 | box-sizing: content-box;
104 | background-color: #ffffff;
105 | }
106 |
107 | .markdown-body code,
108 | .markdown-body kbd,
109 | .markdown-body pre,
110 | .markdown-body samp {
111 | font-family: monospace,monospace;
112 | font-size: 1em;
113 | }
114 |
115 | .markdown-body figure {
116 | margin: 1em 40px;
117 | }
118 |
119 | .markdown-body hr {
120 | box-sizing: content-box;
121 | overflow: hidden;
122 | background: transparent;
123 | border-bottom: 1px solid hsla(210,18%,87%,1);
124 | height: .25em;
125 | padding: 0;
126 | margin: 24px 0;
127 | background-color: #d0d7de;
128 | border: 0;
129 | }
130 |
131 | .markdown-body input {
132 | font: inherit;
133 | margin: 0;
134 | overflow: visible;
135 | font-family: inherit;
136 | font-size: inherit;
137 | line-height: inherit;
138 | }
139 |
140 | .markdown-body [type=button],
141 | .markdown-body [type=reset],
142 | .markdown-body [type=submit] {
143 | -webkit-appearance: button;
144 | }
145 |
146 | .markdown-body [type=button]::-moz-focus-inner,
147 | .markdown-body [type=reset]::-moz-focus-inner,
148 | .markdown-body [type=submit]::-moz-focus-inner {
149 | border-style: none;
150 | padding: 0;
151 | }
152 |
153 | .markdown-body [type=button]:-moz-focusring,
154 | .markdown-body [type=reset]:-moz-focusring,
155 | .markdown-body [type=submit]:-moz-focusring {
156 | outline: 1px dotted ButtonText;
157 | }
158 |
159 | .markdown-body [type=checkbox],
160 | .markdown-body [type=radio] {
161 | box-sizing: border-box;
162 | padding: 0;
163 | }
164 |
165 | .markdown-body [type=number]::-webkit-inner-spin-button,
166 | .markdown-body [type=number]::-webkit-outer-spin-button {
167 | height: auto;
168 | }
169 |
170 | .markdown-body [type=search] {
171 | -webkit-appearance: textfield;
172 | outline-offset: -2px;
173 | }
174 |
175 | .markdown-body [type=search]::-webkit-search-cancel-button,
176 | .markdown-body [type=search]::-webkit-search-decoration {
177 | -webkit-appearance: none;
178 | }
179 |
180 | .markdown-body ::-webkit-input-placeholder {
181 | color: inherit;
182 | opacity: .54;
183 | }
184 |
185 | .markdown-body ::-webkit-file-upload-button {
186 | -webkit-appearance: button;
187 | font: inherit;
188 | }
189 |
190 | .markdown-body a:hover {
191 | text-decoration: underline;
192 | }
193 |
194 | .markdown-body hr::before {
195 | display: table;
196 | content: "";
197 | }
198 |
199 | .markdown-body hr::after {
200 | display: table;
201 | clear: both;
202 | content: "";
203 | }
204 |
205 | .markdown-body table {
206 | border-spacing: 0;
207 | border-collapse: collapse;
208 | display: block;
209 | width: max-content;
210 | max-width: 100%;
211 | overflow: auto;
212 | }
213 |
214 | .markdown-body td,
215 | .markdown-body th {
216 | padding: 0;
217 | }
218 |
219 | .markdown-body details summary {
220 | cursor: pointer;
221 | }
222 |
223 | .markdown-body details:not([open])>*:not(summary) {
224 | display: none !important;
225 | }
226 |
227 | .markdown-body kbd {
228 | display: inline-block;
229 | padding: 3px 5px;
230 | font: 11px ui-monospace,SFMono-Regular,SF Mono,Menlo,Consolas,Liberation Mono,monospace;
231 | line-height: 10px;
232 | color: #24292f;
233 | vertical-align: middle;
234 | background-color: #f6f8fa;
235 | border: solid 1px rgba(175,184,193,0.2);
236 | border-bottom-color: rgba(175,184,193,0.2);
237 | border-radius: 6px;
238 | box-shadow: inset 0 -1px 0 rgba(175,184,193,0.2);
239 | }
240 |
241 | .markdown-body h1,
242 | .markdown-body h2,
243 | .markdown-body h3,
244 | .markdown-body h4,
245 | .markdown-body h5,
246 | .markdown-body h6 {
247 | margin-top: 24px;
248 | margin-bottom: 16px;
249 | font-weight: 600;
250 | line-height: 1.25;
251 | }
252 |
253 | .markdown-body h2 {
254 | font-weight: 600;
255 | padding-bottom: .3em;
256 | font-size: 1.5em;
257 | border-bottom: 1px solid hsla(210,18%,87%,1);
258 | }
259 |
260 | .markdown-body h3 {
261 | font-weight: 600;
262 | font-size: 1.25em;
263 | }
264 |
265 | .markdown-body h4 {
266 | font-weight: 600;
267 | font-size: 1em;
268 | }
269 |
270 | .markdown-body h5 {
271 | font-weight: 600;
272 | font-size: .875em;
273 | }
274 |
275 | .markdown-body h6 {
276 | font-weight: 600;
277 | font-size: .85em;
278 | color: #57606a;
279 | }
280 |
281 | .markdown-body p {
282 | margin-top: 0;
283 | margin-bottom: 10px;
284 | }
285 |
286 | .markdown-body blockquote {
287 | margin: 0;
288 | padding: 0 1em;
289 | color: #57606a;
290 | border-left: .25em solid #d0d7de;
291 | }
292 |
293 | .markdown-body ul,
294 | .markdown-body ol {
295 | margin-top: 0;
296 | margin-bottom: 0;
297 | padding-left: 2em;
298 | }
299 |
300 | .markdown-body ol ol,
301 | .markdown-body ul ol {
302 | list-style-type: lower-roman;
303 | }
304 |
305 | .markdown-body ul ul ol,
306 | .markdown-body ul ol ol,
307 | .markdown-body ol ul ol,
308 | .markdown-body ol ol ol {
309 | list-style-type: lower-alpha;
310 | }
311 |
312 | .markdown-body dd {
313 | margin-left: 0;
314 | }
315 |
316 | .markdown-body tt,
317 | .markdown-body code {
318 | font-family: ui-monospace,SFMono-Regular,SF Mono,Menlo,Consolas,Liberation Mono,monospace;
319 | font-size: 12px;
320 | }
321 |
322 | .markdown-body pre {
323 | margin-top: 0;
324 | margin-bottom: 0;
325 | font-family: ui-monospace,SFMono-Regular,SF Mono,Menlo,Consolas,Liberation Mono,monospace;
326 | font-size: 12px;
327 | word-wrap: normal;
328 | }
329 |
330 | .markdown-body .octicon {
331 | display: inline-block;
332 | overflow: visible !important;
333 | vertical-align: text-bottom;
334 | fill: currentColor;
335 | }
336 |
337 | .markdown-body ::placeholder {
338 | color: #6e7781;
339 | opacity: 1;
340 | }
341 |
342 | .markdown-body input::-webkit-outer-spin-button,
343 | .markdown-body input::-webkit-inner-spin-button {
344 | margin: 0;
345 | -webkit-appearance: none;
346 | appearance: none;
347 | }
348 |
349 | .markdown-body .pl-c {
350 | color: #6e7781;
351 | }
352 |
353 | .markdown-body .pl-c1,
354 | .markdown-body .pl-s .pl-v {
355 | color: #0550ae;
356 | }
357 |
358 | .markdown-body .pl-e,
359 | .markdown-body .pl-en {
360 | color: #8250df;
361 | }
362 |
363 | .markdown-body .pl-smi,
364 | .markdown-body .pl-s .pl-s1 {
365 | color: #24292f;
366 | }
367 |
368 | .markdown-body .pl-ent {
369 | color: #116329;
370 | }
371 |
372 | .markdown-body .pl-k {
373 | color: #cf222e;
374 | }
375 |
376 | .markdown-body .pl-s,
377 | .markdown-body .pl-pds,
378 | .markdown-body .pl-s .pl-pse .pl-s1,
379 | .markdown-body .pl-sr,
380 | .markdown-body .pl-sr .pl-cce,
381 | .markdown-body .pl-sr .pl-sre,
382 | .markdown-body .pl-sr .pl-sra {
383 | color: #0a3069;
384 | }
385 |
386 | .markdown-body .pl-v,
387 | .markdown-body .pl-smw {
388 | color: #953800;
389 | }
390 |
391 | .markdown-body .pl-bu {
392 | color: #82071e;
393 | }
394 |
395 | .markdown-body .pl-ii {
396 | color: #f6f8fa;
397 | background-color: #82071e;
398 | }
399 |
400 | .markdown-body .pl-c2 {
401 | color: #f6f8fa;
402 | background-color: #cf222e;
403 | }
404 |
405 | .markdown-body .pl-sr .pl-cce {
406 | font-weight: bold;
407 | color: #116329;
408 | }
409 |
410 | .markdown-body .pl-ml {
411 | color: #3b2300;
412 | }
413 |
414 | .markdown-body .pl-mh,
415 | .markdown-body .pl-mh .pl-en,
416 | .markdown-body .pl-ms {
417 | font-weight: bold;
418 | color: #0550ae;
419 | }
420 |
421 | .markdown-body .pl-mi {
422 | font-style: italic;
423 | color: #24292f;
424 | }
425 |
426 | .markdown-body .pl-mb {
427 | font-weight: bold;
428 | color: #24292f;
429 | }
430 |
431 | .markdown-body .pl-md {
432 | color: #82071e;
433 | background-color: #FFEBE9;
434 | }
435 |
436 | .markdown-body .pl-mi1 {
437 | color: #116329;
438 | background-color: #dafbe1;
439 | }
440 |
441 | .markdown-body .pl-mc {
442 | color: #953800;
443 | background-color: #ffd8b5;
444 | }
445 |
446 | .markdown-body .pl-mi2 {
447 | color: #eaeef2;
448 | background-color: #0550ae;
449 | }
450 |
451 | .markdown-body .pl-mdr {
452 | font-weight: bold;
453 | color: #8250df;
454 | }
455 |
456 | .markdown-body .pl-ba {
457 | color: #57606a;
458 | }
459 |
460 | .markdown-body .pl-sg {
461 | color: #8c959f;
462 | }
463 |
464 | .markdown-body .pl-corl {
465 | text-decoration: underline;
466 | color: #0a3069;
467 | }
468 |
469 | .markdown-body [data-catalyst] {
470 | display: block;
471 | }
472 |
473 | .markdown-body g-emoji {
474 | font-family: "Apple Color Emoji","Segoe UI Emoji","Segoe UI Symbol";
475 | font-size: 1em;
476 | font-style: normal !important;
477 | font-weight: 400;
478 | line-height: 1;
479 | vertical-align: -0.075em;
480 | }
481 |
482 | .markdown-body g-emoji img {
483 | width: 1em;
484 | height: 1em;
485 | }
486 |
487 | .markdown-body::before {
488 | display: table;
489 | content: "";
490 | }
491 |
492 | .markdown-body::after {
493 | display: table;
494 | clear: both;
495 | content: "";
496 | }
497 |
498 | .markdown-body>*:first-child {
499 | margin-top: 0 !important;
500 | }
501 |
502 | .markdown-body>*:last-child {
503 | margin-bottom: 0 !important;
504 | }
505 |
506 | .markdown-body a:not([href]) {
507 | color: inherit;
508 | text-decoration: none;
509 | }
510 |
511 | .markdown-body .absent {
512 | color: #cf222e;
513 | }
514 |
515 | .markdown-body .anchor {
516 | float: left;
517 | padding-right: 4px;
518 | margin-left: -20px;
519 | line-height: 1;
520 | }
521 |
522 | .markdown-body .anchor:focus {
523 | outline: none;
524 | }
525 |
526 | .markdown-body p,
527 | .markdown-body blockquote,
528 | .markdown-body ul,
529 | .markdown-body ol,
530 | .markdown-body dl,
531 | .markdown-body table,
532 | .markdown-body pre,
533 | .markdown-body details {
534 | margin-top: 0;
535 | margin-bottom: 16px;
536 | }
537 |
538 | .markdown-body blockquote>:first-child {
539 | margin-top: 0;
540 | }
541 |
542 | .markdown-body blockquote>:last-child {
543 | margin-bottom: 0;
544 | }
545 |
546 | .markdown-body sup>a::before {
547 | content: "[";
548 | }
549 |
550 | .markdown-body sup>a::after {
551 | content: "]";
552 | }
553 |
554 | .markdown-body h1 .octicon-link,
555 | .markdown-body h2 .octicon-link,
556 | .markdown-body h3 .octicon-link,
557 | .markdown-body h4 .octicon-link,
558 | .markdown-body h5 .octicon-link,
559 | .markdown-body h6 .octicon-link {
560 | color: #24292f;
561 | vertical-align: middle;
562 | visibility: hidden;
563 | }
564 |
565 | .markdown-body h1:hover .anchor,
566 | .markdown-body h2:hover .anchor,
567 | .markdown-body h3:hover .anchor,
568 | .markdown-body h4:hover .anchor,
569 | .markdown-body h5:hover .anchor,
570 | .markdown-body h6:hover .anchor {
571 | text-decoration: none;
572 | }
573 |
574 | .markdown-body h1:hover .anchor .octicon-link,
575 | .markdown-body h2:hover .anchor .octicon-link,
576 | .markdown-body h3:hover .anchor .octicon-link,
577 | .markdown-body h4:hover .anchor .octicon-link,
578 | .markdown-body h5:hover .anchor .octicon-link,
579 | .markdown-body h6:hover .anchor .octicon-link {
580 | visibility: visible;
581 | }
582 |
583 | .markdown-body h1 tt,
584 | .markdown-body h1 code,
585 | .markdown-body h2 tt,
586 | .markdown-body h2 code,
587 | .markdown-body h3 tt,
588 | .markdown-body h3 code,
589 | .markdown-body h4 tt,
590 | .markdown-body h4 code,
591 | .markdown-body h5 tt,
592 | .markdown-body h5 code,
593 | .markdown-body h6 tt,
594 | .markdown-body h6 code {
595 | padding: 0 .2em;
596 | font-size: inherit;
597 | }
598 |
599 | .markdown-body ul.no-list,
600 | .markdown-body ol.no-list {
601 | padding: 0;
602 | list-style-type: none;
603 | }
604 |
605 | .markdown-body ol[type="1"] {
606 | list-style-type: decimal;
607 | }
608 |
609 | .markdown-body ol[type=a] {
610 | list-style-type: lower-alpha;
611 | }
612 |
613 | .markdown-body ol[type=i] {
614 | list-style-type: lower-roman;
615 | }
616 |
617 | .markdown-body div>ol:not([type]) {
618 | list-style-type: decimal;
619 | }
620 |
621 | .markdown-body ul ul,
622 | .markdown-body ul ol,
623 | .markdown-body ol ol,
624 | .markdown-body ol ul {
625 | margin-top: 0;
626 | margin-bottom: 0;
627 | }
628 |
629 | .markdown-body li>p {
630 | margin-top: 16px;
631 | }
632 |
633 | .markdown-body li+li {
634 | margin-top: .25em;
635 | }
636 |
637 | .markdown-body dl {
638 | padding: 0;
639 | }
640 |
641 | .markdown-body dl dt {
642 | padding: 0;
643 | margin-top: 16px;
644 | font-size: 1em;
645 | font-style: italic;
646 | font-weight: 600;
647 | }
648 |
649 | .markdown-body dl dd {
650 | padding: 0 16px;
651 | margin-bottom: 16px;
652 | }
653 |
654 | .markdown-body table th {
655 | font-weight: 600;
656 | }
657 |
658 | .markdown-body table th,
659 | .markdown-body table td {
660 | padding: 6px 13px;
661 | border: 1px solid #d0d7de;
662 | }
663 |
664 | .markdown-body table tr {
665 | background-color: #ffffff;
666 | border-top: 1px solid hsla(210,18%,87%,1);
667 | }
668 |
669 | .markdown-body table tr:nth-child(2n) {
670 | background-color: #f6f8fa;
671 | }
672 |
673 | .markdown-body table img {
674 | background-color: transparent;
675 | }
676 |
677 | .markdown-body img[align=right] {
678 | padding-left: 20px;
679 | }
680 |
681 | .markdown-body img[align=left] {
682 | padding-right: 20px;
683 | }
684 |
685 | .markdown-body .emoji {
686 | max-width: none;
687 | vertical-align: text-top;
688 | background-color: transparent;
689 | }
690 |
691 | .markdown-body span.frame {
692 | display: block;
693 | overflow: hidden;
694 | }
695 |
696 | .markdown-body span.frame>span {
697 | display: block;
698 | float: left;
699 | width: auto;
700 | padding: 7px;
701 | margin: 13px 0 0;
702 | overflow: hidden;
703 | border: 1px solid #d0d7de;
704 | }
705 |
706 | .markdown-body span.frame span img {
707 | display: block;
708 | float: left;
709 | }
710 |
711 | .markdown-body span.frame span span {
712 | display: block;
713 | padding: 5px 0 0;
714 | clear: both;
715 | color: #24292f;
716 | }
717 |
718 | .markdown-body span.align-center {
719 | display: block;
720 | overflow: hidden;
721 | clear: both;
722 | }
723 |
724 | .markdown-body span.align-center>span {
725 | display: block;
726 | margin: 13px auto 0;
727 | overflow: hidden;
728 | text-align: center;
729 | }
730 |
731 | .markdown-body span.align-center span img {
732 | margin: 0 auto;
733 | text-align: center;
734 | }
735 |
736 | .markdown-body span.align-right {
737 | display: block;
738 | overflow: hidden;
739 | clear: both;
740 | }
741 |
742 | .markdown-body span.align-right>span {
743 | display: block;
744 | margin: 13px 0 0;
745 | overflow: hidden;
746 | text-align: right;
747 | }
748 |
749 | .markdown-body span.align-right span img {
750 | margin: 0;
751 | text-align: right;
752 | }
753 |
754 | .markdown-body span.float-left {
755 | display: block;
756 | float: left;
757 | margin-right: 13px;
758 | overflow: hidden;
759 | }
760 |
761 | .markdown-body span.float-left span {
762 | margin: 13px 0 0;
763 | }
764 |
765 | .markdown-body span.float-right {
766 | display: block;
767 | float: right;
768 | margin-left: 13px;
769 | overflow: hidden;
770 | }
771 |
772 | .markdown-body span.float-right>span {
773 | display: block;
774 | margin: 13px auto 0;
775 | overflow: hidden;
776 | text-align: right;
777 | }
778 |
779 | .markdown-body code,
780 | .markdown-body tt {
781 | padding: .2em .4em;
782 | margin: 0;
783 | font-size: 85%;
784 | background-color: rgba(175,184,193,0.2);
785 | border-radius: 6px;
786 | }
787 |
788 | .markdown-body code br,
789 | .markdown-body tt br {
790 | display: none;
791 | }
792 |
793 | .markdown-body del code {
794 | text-decoration: inherit;
795 | }
796 |
797 | .markdown-body pre code {
798 | font-size: 100%;
799 | }
800 |
801 | .markdown-body pre>code {
802 | padding: 0;
803 | margin: 0;
804 | word-break: normal;
805 | white-space: pre;
806 | background: transparent;
807 | border: 0;
808 | }
809 |
810 | .markdown-body .highlight {
811 | margin-bottom: 16px;
812 | }
813 |
814 | .markdown-body .highlight pre {
815 | margin-bottom: 0;
816 | word-break: normal;
817 | }
818 |
819 | .markdown-body .highlight pre,
820 | .markdown-body pre {
821 | padding: 16px;
822 | overflow: auto;
823 | max-width: 80vw;
824 | line-height: 1.45;
825 | background-color: #f6f8fa;
826 | border-radius: 6px;
827 | }
828 |
829 | .markdown-body pre code,
830 | .markdown-body pre tt {
831 | display: inline;
832 | max-width: auto;
833 | padding: 0;
834 | margin: 0;
835 | overflow: visible;
836 | line-height: inherit;
837 | word-wrap: normal;
838 | background-color: transparent;
839 | border: 0;
840 | }
841 |
842 | .markdown-body .csv-data td,
843 | .markdown-body .csv-data th {
844 | padding: 5px;
845 | overflow: hidden;
846 | font-size: 12px;
847 | line-height: 1;
848 | text-align: left;
849 | white-space: nowrap;
850 | }
851 |
852 | .markdown-body .csv-data .blob-num {
853 | padding: 10px 8px 9px;
854 | text-align: right;
855 | background: #ffffff;
856 | border: 0;
857 | }
858 |
859 | .markdown-body .csv-data tr {
860 | border-top: 0;
861 | }
862 |
863 | .markdown-body .csv-data th {
864 | font-weight: 600;
865 | background: #f6f8fa;
866 | border-top: 0;
867 | }
868 |
869 | .markdown-body .footnotes {
870 | font-size: 12px;
871 | color: #57606a;
872 | border-top: 1px solid #d0d7de;
873 | }
874 |
875 | .markdown-body .footnotes ol {
876 | padding-left: 16px;
877 | }
878 |
879 | .markdown-body .footnotes li {
880 | position: relative;
881 | }
882 |
883 | .markdown-body .footnotes li:target::before {
884 | position: absolute;
885 | top: -8px;
886 | right: -8px;
887 | bottom: -8px;
888 | left: -24px;
889 | pointer-events: none;
890 | content: "";
891 | border: 2px solid #0969da;
892 | border-radius: 6px;
893 | }
894 |
895 | .markdown-body .footnotes li:target {
896 | color: #24292f;
897 | }
898 |
899 | .markdown-body .footnotes .data-footnote-backref g-emoji {
900 | font-family: monospace;
901 | }
902 |
903 | .markdown-body .task-list-item {
904 | list-style-type: none;
905 | }
906 |
907 | .markdown-body .task-list-item label {
908 | font-weight: 400;
909 | }
910 |
911 | .markdown-body .task-list-item.enabled label {
912 | cursor: pointer;
913 | }
914 |
915 | .markdown-body .task-list-item+.task-list-item {
916 | margin-top: 3px;
917 | }
918 |
919 | .markdown-body .task-list-item .handle {
920 | display: none;
921 | }
922 |
923 | .markdown-body .task-list-item-checkbox {
924 | margin: 0 .2em .25em -1.6em;
925 | vertical-align: middle;
926 | }
927 |
928 | .markdown-body .contains-task-list:dir(rtl) .task-list-item-checkbox {
929 | margin: 0 -1.6em .25em .2em;
930 | }
931 |
932 | .markdown-body ::-webkit-calendar-picker-indicator {
933 | filter: invert(50%);
934 | }
935 |
936 | pre code.hljs{display:block;overflow-x:auto;padding:1em}code.hljs{padding:3px 5px}/*!
937 | Theme: GitHub
938 | Description: Light theme as seen on github.com
939 | Author: github.com
940 | Maintainer: @Hirse
941 | Updated: 2021-05-15
942 |
943 | Outdated base version: https://github.com/primer/github-syntax-light
944 | Current colors taken from GitHub's CSS
945 | */.hljs{color:#24292e;background:#fff}.hljs-doctag,.hljs-keyword,.hljs-meta .hljs-keyword,.hljs-template-tag,.hljs-template-variable,.hljs-type,.hljs-variable.language_{color:#d73a49}.hljs-title,.hljs-title.class_,.hljs-title.class_.inherited__,.hljs-title.function_{color:#6f42c1}.hljs-attr,.hljs-attribute,.hljs-literal,.hljs-meta,.hljs-number,.hljs-operator,.hljs-selector-attr,.hljs-selector-class,.hljs-selector-id,.hljs-variable{color:#005cc5}.hljs-meta .hljs-string,.hljs-regexp,.hljs-string{color:#032f62}.hljs-built_in,.hljs-symbol{color:#e36209}.hljs-code,.hljs-comment,.hljs-formula{color:#6a737d}.hljs-name,.hljs-quote,.hljs-selector-pseudo,.hljs-selector-tag{color:#22863a}.hljs-subst{color:#24292e}.hljs-section{color:#005cc5;font-weight:700}.hljs-bullet{color:#735c0f}.hljs-emphasis{color:#24292e;font-style:italic}.hljs-strong{color:#24292e;font-weight:700}.hljs-addition{color:#22863a;background-color:#f0fff4}.hljs-deletion{color:#b31d28;background-color:#ffeef0}
946 |
947 | @import "./atom-one-dark.css";
948 | .dark-theme .markdown-body pre {
949 | background: #282c34
950 | }
--------------------------------------------------------------------------------