Skip to content
This repository has been archived by the owner on Sep 23, 2024. It is now read-only.

fix: text doesn't break word; fix: text doesn't resume typing as brow… #103

Merged
merged 1 commit into from
Jan 8, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ yarn-error.log

build/
dist/
chunks-report.html

.env.local
.env.development.local
Expand Down
11 changes: 6 additions & 5 deletions package.json
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
{
"name": "talk-vite",
"private": true,
"version": "2.0.0",
"version": "2.0.1",
"type": "module",
"scripts": {
"dev": "vite",
Expand All @@ -16,8 +16,8 @@
"@types/highlight.js": "^10.1.0",
"@types/markdown-it": "^13.0.2",
"@types/markdown-it-emoji": "^2.0.2",
"axios": "^1.5.0",
"crypto-js": "^4.1.1",
"axios": "1.6.0",
"crypto-js": "4.2.0",
"date-fns": "^2.30.0",
"downshift": "^8.1.0",
"framer-motion": "^10.16.1",
Expand Down Expand Up @@ -74,11 +74,12 @@
"eslint-plugin-react-hooks": "^4.6.0",
"eslint-plugin-react-refresh": "^0.4.3",
"eslint-plugin-valtio": "^0.6.2",
"postcss": "^8.4.27",
"postcss": "8.4.31",
"postcss-import": "^15.1.0",
"rollup-plugin-visualizer": "^5.12.0",
"tailwindcss": "^3.3.3",
"typescript": "^5.2.2",
"vite": "^4.4.5",
"vite": "5.0.5",
"vite-plugin-svgr": "^4.0.0"
}
}
9 changes: 8 additions & 1 deletion src/home/chat-window/compnent/my-text.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,7 @@ export const MyText: React.FC<TextProps> = ({messageSnap, theme}) => {
// console.info("MyText rendered, messageSnap.id:", messageSnap.id, new Date().toLocaleString())
// console.info("messageSnap.text", messageSnap.text)
const {showMarkdown} = useSnapshot(appState.pref)
const {isWindowsBlurred} = useSnapshot(controlState)
const [text, setText] = useState(messageSnap.text)
const [hovering, setHovering] = useState(false)

Expand All @@ -63,6 +64,12 @@ export const MyText: React.FC<TextProps> = ({messageSnap, theme}) => {
}
}, [messageSnap.status, hovering]);

useEffect(() => {
if (isWindowsBlurred) {
setHovering(false)
}
}, [isWindowsBlurred]);

useEffect(() => {
if (!controlState.isTextPending) {
setText(messageSnap.text)
Expand All @@ -84,7 +91,7 @@ export const MyText: React.FC<TextProps> = ({messageSnap, theme}) => {
onMouseLeave={() => setHovering(false)}
>

<div className={cx("leading-snug break-all",
<div className={cx("leading-snug",
"prose-pre:p-0 prose-pre:pt-3 prose-li:marker:text-neutral-600"
)}>
{messageSnap.role === 'assistant' && showMarkdown ?
Expand Down
4 changes: 2 additions & 2 deletions src/home/chat-window/prompt/prompt-editor-item.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,9 @@ import {cx} from "../../../util/util.tsx";
import {userColor, assistantColor} from "../compnent/theme.ts";
import {LLMMessage, Role} from "../../../shared-types.ts";
import {useSnapshot} from "valtio/react";
import _ from "lodash";
import {AiOutlinePlus} from "react-icons/ai";
import {Prompt} from "../../../state/promt-state.ts";
import {capitalize} from "lodash";

type Props = {
promptProxy: Prompt
Expand Down Expand Up @@ -131,7 +131,7 @@ const Dot: React.FC<RoleDotProps> = ({messageProxy, targetRole}) => {
{hovering &&
<div className=" bg-neutral-200/[0.8] rounded-full px-2 fixed -top-6 left-1/2 -translate-x-1/2
transform text-sm text-neutral-800">
{_.capitalize(targetRole)}
{capitalize(targetRole)}
</div>
}
</div>
Expand Down
4 changes: 2 additions & 2 deletions src/home/chat-window/prompt/prompt-item.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import {clonePrompt, deletePrompt, Prompt, promptCountState, syncPromptIdCounts}
import {Chat} from "../../../state/app-state.ts";
import {useSnapshot} from "valtio/react";
import {MdOutlineContentCopy} from "react-icons/md";
import _ from "lodash";
import {capitalize} from "lodash";

type Props = {
chatProxy: Chat
Expand Down Expand Up @@ -58,7 +58,7 @@ export const PromptItem: React.FC<Props> = ({chatProxy, prompt}) => {
<div>
<div className="truncate text-sm text-neutral-600 ...">
{messages.length > 0 &&
<div>{_.capitalize(messages[0].role)}: {messages[0].content}</div>
<div>{capitalize(messages[0].role)}: {messages[0].content}</div>
}
</div>
</div>
Expand Down
4 changes: 2 additions & 2 deletions src/home/panel/shared/llm/chat-gpt.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,9 @@ import {
import {appState} from "../../../../state/app-state.ts"
import {Choice} from "../../../../data-structure/provider-api-refrence/types.ts"
import {SelectBoxOrNotAvailable} from "../select-box-or-not-available.tsx"
import _ from "lodash"
import {llmAPIReference} from "../../../../data-structure/provider-api-refrence/llm.ts"
import {ChatGPTLogo} from "../widget/logo.tsx"
import {map} from "lodash";

type Props = {
chatGPTOptionProxy: ChatGPTOption
Expand All @@ -33,7 +33,7 @@ const ChatGpt: React.FC<Props> = ({chatGPTOptionProxy, llmOptionProxy, setEnable
const [modelChoices, setModelChoices] = useState<Choice<string>[]>([])

useEffect(() => {
const choices = _.map(appState.ability.llm.chatGPT.models, (model): Choice<string> => ({
const choices = map(appState.ability.llm.chatGPT.models, (model): Choice<string> => ({
name: model.displayName,
value: model.name,
tags: []
Expand Down
4 changes: 2 additions & 2 deletions src/home/panel/shared/llm/gemini.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,9 +10,9 @@ import {geminiAPIReference, maxOutputTokens} from '../../../../data-structure/pr
import {appState} from "../../../../state/app-state.ts"
import {Choice} from "../../../../data-structure/provider-api-refrence/types.ts"
import {SelectBoxOrNotAvailable} from "../select-box-or-not-available.tsx"
import _ from "lodash"
import {llmAPIReference} from "../../../../data-structure/provider-api-refrence/llm.ts"
import {GeminiLogo} from "../widget/logo.tsx"
import {map} from "lodash";

type Props = {
geminiOptionProxy: GeminiOption
Expand All @@ -30,7 +30,7 @@ const Gemini: React.FC<Props> = ({geminiOptionProxy, llmOptionProxy, setEnabled}
const [modelChoices, setModelChoices] = useState<Choice<string>[]>([])

useEffect(() => {
const choices = _.map(appState.ability.llm.gemini.models, (model): Choice<string> => ({
const choices = map(appState.ability.llm.gemini.models, (model): Choice<string> => ({
name: model.displayName,
value: model.name,
tags: []
Expand Down
6 changes: 3 additions & 3 deletions src/home/panel/shared/stt/google-stt.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,10 @@ import {useSnapshot} from "valtio/react"
import {GoogleOption,} from "../../../../data-structure/client-option.tsx"
import {appState} from "../../../../state/app-state.ts"
import {SelectBoxOrNotAvailable} from "../select-box-or-not-available.tsx"
import _ from "lodash"
import {Choice, emptyStringChoice} from "../../../../data-structure/provider-api-refrence/types.ts"
import {googleSTTAPIReference} from "../../../../data-structure/provider-api-refrence/google-stt.ts"
import { GoogleLogo } from '../widget/logo.tsx'
import {map} from "lodash";

type Props = {
googleOptionProxy: GoogleOption
Expand All @@ -34,10 +34,10 @@ const GoogleStt: React.FC<Props> = ({googleOptionProxy, setEnabled}) => {

useEffect(() => {
// eslint-disable-next-line valtio/state-snapshot-rule
const choices = _.map(googleAbilitySnap.recognizers, r => ({
const choices = map(googleAbilitySnap.recognizers, r => ({
name: r.id,
value: r.name,
tags: _.map(r.tags, t => t)
tags: map(r.tags, t => t)
}))
setRecognizerChoices(choices)
}, [googleAbilitySnap])
Expand Down
4 changes: 2 additions & 2 deletions src/home/panel/shared/stt/whisper.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@ import {useSnapshot} from "valtio/react"
import {WhisperOption,} from "../../../../data-structure/client-option.tsx"
import {appState} from "../../../../state/app-state.ts"
import {SelectBoxOrNotAvailable} from "../select-box-or-not-available.tsx"
import _ from "lodash"
import {WhisperGPTLogo} from "../widget/logo.tsx"
import {map} from "lodash";

type Props = {
whisperOptionProxy: WhisperOption
Expand Down Expand Up @@ -34,7 +34,7 @@ const Whisper: React.FC<Props> = ({whisperOptionProxy, setEnabled}) => {
<>
<SelectBoxOrNotAvailable
title={"Model"}
choices={_.map(whisperAbilitySnap.models, m => ({
choices={map(whisperAbilitySnap.models, m => ({
name: m,
value: m,
tags: []
Expand Down
6 changes: 3 additions & 3 deletions src/home/panel/shared/tts/elevenlabs.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,8 @@ import {ElevenlabsTTSOption,} from "../../../../data-structure/client-option.tsx
import {appState} from "../../../../state/app-state.ts"
import {elevenlabsAPIReference} from "../../../../data-structure/provider-api-refrence/elevenlabs-tts.ts"
import {SelectBoxOrNotAvailable} from "../select-box-or-not-available.tsx"
import _ from "lodash"
import {ElevenlabsLogo} from "../widget/logo.tsx"
import {map, uniq} from "lodash";

type Props = {
elevenlabsTTSOptionProxy: ElevenlabsTTSOption
Expand All @@ -24,11 +24,11 @@ const ElevenlabsTTS: React.FC<Props> = ({elevenlabsTTSOptionProxy, setEnabled})

useEffect(() => {
// eslint-disable-next-line valtio/state-snapshot-rule
const voices = _.map(elevenlabsAbilitySnap.voices,
const voices = map(elevenlabsAbilitySnap.voices,
v => ({
name: v.name,
value: v.id,
tags: _.uniq(v.tags).map(tag => tag)
tags: uniq(v.tags).map(tag => tag)
}))
setVoicesChoice(voices)
}, [elevenlabsAbilitySnap])
Expand Down
12 changes: 6 additions & 6 deletions src/home/panel/shared/tts/google-tts.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,8 @@ import {GoogleTTSGender} from "../../../../api/restful/model.ts"
import {appState} from "../../../../state/app-state.ts"
import {googleTTSAPIReference} from "../../../../data-structure/provider-api-refrence/google-tts.ts"
import {SelectBoxOrNotAvailable} from "../select-box-or-not-available.tsx"
import _ from "lodash"
import {GoogleLogo} from "../widget/logo.tsx"
import {filter, first, map, some} from "lodash";

type Props = {
googleTTSOptionProxy: GoogleTTSOption
Expand All @@ -35,20 +35,20 @@ const GoogleTTS: React.FC<Props> = ({googleTTSOptionProxy, setEnabled}) => {
// eslint-disable-next-line valtio/state-snapshot-rule
const lang = googleTTSSnap.languageCode
if (lang) {
const filtered = _.filter(appState.ability.tts.google.voices,
const filtered = filter(appState.ability.tts.google.voices,
voice =>
_.some(voice.tags,
some(voice.tags,
tag => tag.startsWith(lang) || lang.startsWith(tag)
)
)
.map((v): Choice<string> => ({
name: v.name,
value: v.id,
tags: _.map(v.tags, tag => tag)
tags: map(v.tags, tag => tag)
}))
setVoicesChoice(filtered)
if (!_.some(filtered, v => v.value === googleTTSOptionProxy.voiceId)) {
googleTTSOptionProxy.voiceId = _.first(filtered)?.value
if (!some(filtered, v => v.value === googleTTSOptionProxy.voiceId)) {
googleTTSOptionProxy.voiceId = first(filtered)?.value
}
} else {
setVoicesChoice([])
Expand Down
6 changes: 3 additions & 3 deletions src/state/app-state.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,8 @@ import {defaultServerAbility, ServerAbility} from "../api/sse/server-ability.ts"
import {generateHash, randomHash16Char} from "../util/util.tsx"
import {migrateAppState} from "./migration.ts"
import * as packageJson from '../../package.json'
import _ from "lodash";
import {defaultShortcuts, Shortcuts} from "./shortcuts.ts";
import {cloneDeep, compact} from "lodash";

const currentVersion = packageJson.version

Expand Down Expand Up @@ -248,7 +248,7 @@ export const markMessageAsDeleted = (chatId: string, messageId: string): void =>
}

export const clearMessages = (chat: Chat): void => {
const audioIds = _.compact(chat.messages.map(m => m.audio?.id))
const audioIds = compact(chat.messages.map(m => m.audio?.id))
deleteBlobs(audioIds).finally(() => {
chat.messages.splice(0, chat.messages.length)
})
Expand Down Expand Up @@ -299,7 +299,7 @@ export const deleteChat = (id: string) => {
}

export const createChat = (name: string, messages: Message[]) => {
const optionClone = _.cloneDeep(appState.option)
const optionClone = cloneDeep(appState.option)
const newChat = proxy<Chat>({
id: randomHash16Char(),
name: name,
Expand Down
2 changes: 2 additions & 0 deletions src/state/control-state.ts
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ export type AudioDurationUpdate = {
type ControlState = {
isMouseLeftDown: boolean
isMouseDragging: boolean
isWindowsBlurred: boolean,
isTextPending: boolean,
player: Player
recordingMimeType?: RecordingMimeType
Expand All @@ -50,6 +51,7 @@ type ControlState = {
export const controlState = proxy<ControlState>({
isMouseLeftDown: false,
isMouseDragging: false,
isWindowsBlurred: false,
isTextPending: false,
player: {
autoPlay: true,
Expand Down
4 changes: 2 additions & 2 deletions src/state/promt-state.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import {randomHash16Char} from "../util/util.tsx";
import {LLMMessage} from "../shared-types.ts";
import {appState, hydrationState} from "./app-state.ts";
import {subscribeKey} from "valtio/utils";
import _ from "lodash";
import {groupBy} from "lodash";

export type Prompt = {
id: string,
Expand Down Expand Up @@ -103,7 +103,7 @@ export const syncPromptIdCounts = () => {
for (const key in promptCountState.counts) {
delete promptCountState.counts[key]
}
const group = _.groupBy(appState.chats, c => c.promptId)
const group = groupBy(appState.chats, c => c.promptId)
for (const key in group) {
promptCountState.counts[key] = group[key].length
}
Expand Down
7 changes: 7 additions & 0 deletions src/window-listeners.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,11 @@ export const WindowListeners: React.FC = () => {

const handleBrowserBlur = () => {
setMouseDown(false)
controlState.isWindowsBlurred = true
}

const handleBrowserFocus = () => {
controlState.isWindowsBlurred = false
}

if (showRecorder) {
Expand All @@ -77,13 +82,15 @@ export const WindowListeners: React.FC = () => {
window.addEventListener("mousedown", handleMouseDown)
window.addEventListener("mouseup", handleMouseUp)
window.addEventListener("blur", handleBrowserBlur)
window.addEventListener("focus", handleBrowserFocus)

return () => {
window.removeEventListener("keydown", handleKeyDown)
window.removeEventListener("keyup", handleKeyUp)
window.removeEventListener("mousedown", handleMouseDown)
window.removeEventListener("mouseup", handleMouseUp)
window.removeEventListener("blur", handleBrowserBlur)
window.removeEventListener("focus", handleBrowserFocus)
}
},
[setMouseDown, recorder, showRecorder]
Expand Down
Loading