-
Notifications
You must be signed in to change notification settings - Fork 747
Expand file tree
/
Copy pathPromptWork.ts
More file actions
174 lines (160 loc) · 5.22 KB
/
PromptWork.ts
File metadata and controls
174 lines (160 loc) · 5.22 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
import { PromptList } from "./PromptList"
import { uuid } from "fzz"
import { IPromptWord, parsePrompts, stringifyPrompts } from "../Lib/parsePrompts/parsePrompts"
import { SubTypeDisplayMap } from "../../../Lang/tempLang"
import { chinesePercentage } from "../Lib/chinesePercentage"
import { PromptItem } from "./PromptItem"
import { translatePrompts } from "../Lib/translatePrompts"
export interface IPromptWorkData {
name: string
id: string
initText?: string
parser?: string
}
export interface IPromptGroup {
id: string
name?: string
groupLv?: number
lists: PromptList[]
}
export class PromptWork {
data!: IPromptWorkData
state!: {}
groups: IPromptGroup[] = []
get id() {
return this.data.id
}
constructor(data?: Partial<IPromptWorkData>) {
this.data = Object.assign(
{
id: uuid.v4(),
name: "untitled",
},
data
)
}
/** 导入提示词 */
async importPrompts(text: string, options: { parser: string }) {
let { words } = await parsePrompts(text, { zh2en: true, ...options })
this.data.parser = options.parser
// 分组
let groupList: { [group: string]: IPromptWord[] } = {}
let noGroup: IPromptWord[] = []
words.forEach((word) => {
if (word.group) {
if (!groupList[word.group]) groupList[word.group] = []
groupList[word.group].push(word)
} else {
noGroup.push(word)
}
})
// 分组
let finGroups = []
for (let key in groupList) {
let wordList = groupList[key]
let listMap = createListMap(wordList)
let lv = wordList[0]?.lv
finGroups.push({
id: `group-${key}`,
groupLv: Number.parseFloat(<any>lv),
lists: sortPromptMap(listMap),
})
}
// 未分组
if (noGroup.length > 0) {
finGroups.push({
id: `group-noGroup`,
lists: sortPromptMap(createListMap(noGroup)),
})
}
this.groups = finGroups
// 翻译
this.translate()
function createListMap(words: IPromptWord[]) {
let subTypeMap: { [subType: string]: IPromptWord[] } = {}
words.forEach((word) => {
let subType = word.subType ?? "normal"
if (word.isEg) subType = "eg"
if (subType in subTypeMap) {
subTypeMap[subType].push(word)
} else {
subTypeMap[subType] = [word]
}
})
let listMap = <any>{}
for (let subType in subTypeMap) {
listMap[subType] = new PromptList({
id: subType,
type: subType,
name: SubTypeDisplayMap[subType] ?? subType,
index: ListSortMap[subType] ?? 0,
})
listMap[subType].applyWords(subTypeMap[subType])
}
return listMap
}
}
/** 导出提示词 */
exportPrompts() {
return stringifyPrompts(this.groups, { parser: this.data.parser ?? "midjourney" })
}
async reflowPrompts(addPrompt?: string) {
let prompt = this.exportPrompts()
if (addPrompt) {
prompt += " , " + addPrompt
}
await this.importPrompts(prompt, { parser: <any>this.data.parser ?? "midjourney" })
}
/** 翻译全部提示词 */
async translate() {
let needTranslateItems: PromptItem[] = []
for (let group of this.groups) {
for (let list of group.lists) {
if (list.data.type !== "normal") continue
for (let item of list.items) {
if (item.data.word.langText) continue
let cp = chinesePercentage(item.data.word.text)
// 中文含量低,需要翻译
if (cp < 5) needTranslateItems.push(item)
}
}
}
let rawTexts = needTranslateItems.map((item) => item.data.word.text)
let re = await translatePrompts(rawTexts)
if (re) {
re.forEach((langText, i) => {
needTranslateItems[i].data.word.langText = langText
})
}
}
/** 禁用全部提示词 */
disableAll() {
let isAllDisabled = true
this.groups.forEach((group) => {
group.lists.forEach((list) =>
list.items.forEach((item) => {
if (!item.data.disabled) {
isAllDisabled = false
}
})
)
})
this.groups.forEach((group) => {
group.lists.forEach((list) =>
list.items.forEach((item) => (item.data.disabled = isAllDisabled ? false : true))
)
})
}
}
const ListSortMap: any = {
normal: 6,
style: 7,
quality: 8,
command: 9,
eg: 10,
}
function sortPromptMap(listMap: { [key: string]: PromptList }) {
return Object.values(listMap).sort((a, b) => {
return (a.data.index ?? 0) - (b.data.index ?? 0)
})
}