Skip to content

Commit 262324f

Browse files
committed
wip: editor improvements
1 parent c18020e commit 262324f

31 files changed

+951
-577
lines changed

@fiction/plugins/plugin-ai/systemMessage.ts

+28-42
Original file line numberDiff line numberDiff line change
@@ -29,11 +29,11 @@ export class ContentCommand {
2929
const messages: CommandMessage[] = [
3030
{
3131
role: 'system',
32-
content: `<system_message>follow these orders EXACTLY and return JSON based on inputs provided: ${formatGuidelines.guidelines}</system_message>`,
32+
content: `<system_message>follow these orders EXACTLY and return ONLY JSON based on inputs provided: ${formatGuidelines.guidelines}</system_message>`,
3333
},
3434
{
3535
role: 'system',
36-
content: `<output_format>Generate JSON content that conforms to the following schema: ${JSON.stringify(formatGuidelines.outputFormat)}. Ensure the response is structured according to this schema.</output_format>`,
36+
content: `<output_format>Generate ONLY JSON that conforms to the following schema: ${JSON.stringify(formatGuidelines.outputFormat)}. Ensure the response is structured according to this schema.</output_format>`,
3737
},
3838
]
3939

@@ -110,46 +110,32 @@ export class ContentCommand {
110110
suggestion1: z.string().min(3).max(100),
111111
suggestion2: z.string().min(3).max(100),
112112
})),
113-
guidelines: `
114-
<role>
115-
You are an expert writing assistant, providing precise and contextually appropriate autocomplete suggestions.
116-
</role>
117-
118-
<output_format>
119-
- Generate ONLY JSON content strictly adhering to the provided schema. Nothing besides JSON should be returned.
120-
- Ensure grammatical correctness and proper punctuation. Based on previous text.
121-
- Vary suggestion length based on context (typically 3-10 words).
122-
- For uncertain subjects, prefer shorter responses (3-5 words).
123-
- For more certain subjects, provide longer, more detailed suggestions (6-10 words).
124-
- If a space is needed after a suggestion, include it in the suggestion.
125-
</output_format>
126-
127-
<content_guidelines>
128-
1. Style and Tone:
129-
- Accurately mimic the user's writing style, voice, and tone.
130-
- Maintain consistency across suggestions.
131-
132-
2. Context and Relevance:
133-
- Provide suggestions that flow naturally from the given input.
134-
- Ensure high relevance to the topic and context.
135-
- Incorporate key ideas from the objectives when appropriate.
136-
137-
3. Creativity and Engagement:
138-
- Offer unique perspectives to overcome potential writer's block.
139-
- Use vivid language to evoke emotions and visualization.
140-
- Suggest thought-provoking continuations when appropriate.
141-
142-
4. Precision and Conciseness:
143-
- Prioritize clarity and conciseness.
144-
- Avoid clichés, redundancy, and overused phrases.
145-
- Use active voice and strong verbs.
146-
147-
5. Adaptability:
148-
- Adjust suggestions based on the content type (e.g., formal report, creative writing, technical documentation).
149-
- Provide a mix of continuation types (e.g., elaboration, transition, conclusion) as appropriate.
150-
151-
${this.getObjectivesInstruction(objectives)}
152-
</content_guidelines>`,
113+
guidelines: `<role>Expert writing assistant generating brilliant, contextual autocomplete suggestions.</role>
114+
<output>
115+
- JSON content adhering to schema
116+
- Flawless grammar and punctuation, write or complete full sentences.
117+
- Context-based length (3-20 words)
118+
- Include trailing space if needed
119+
- Avoid repeating surrounding text
120+
</output>
121+
<guidelines>
122+
- Elevate style while maintaining voice
123+
- Ensure focused relevance and coherence
124+
- Seamlessly integrate objectives
125+
- Offer thought-provoking angles
126+
- Craft vivid, emotive language
127+
- Prioritize clarity and impact
128+
- Champion originality; avoid clichés
129+
- Use powerful verbs and active voice
130+
- Adapt tone to content type
131+
- Provide diverse, intelligent continuations
132+
- Address potential counterarguments
133+
- Inject expert insights and cutting-edge ideas
134+
- Balance creativity with accuracy
135+
- Suggest compelling metaphors/analogies
136+
- Propose data-driven points when relevant
137+
</guidelines>
138+
<objectives>${this.getObjectivesInstruction(objectives)}</objectives>`,
153139
}
154140
}
155141

@fiction/posts/el/ElPostEditor.vue

+1
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@ defineProps({
4444
<ProseEditor
4545
:model-value="post.content.value"
4646
class="font-serif"
47+
:supplemental="{ title: post.title.value, subTitle: post.subTitle.value }"
4748
@update:model-value="post?.update({ content: $event as string }, { caller: 'proseEditor:content' })"
4849
/>
4950
<div v-if="$slots.footer" class="not-prose">

@fiction/site/utils/test/site.unit.test.ts

+5-5
Original file line numberDiff line numberDiff line change
@@ -223,7 +223,7 @@ describe('updateSite / updatePages', async () => {
223223

224224
await updateSite({ caller: 'testUpdateSite', site, newConfig: { pages: [{ templateId: 'wrap', cardId: 'card1' }] } })
225225

226-
expect(site.pages.value[0].cardId).toBe('card1')
226+
expect(site.pages.value[0]?.cardId).toBe('card1')
227227
})
228228

229229
it('merge updates editor', async () => {
@@ -259,10 +259,10 @@ describe('updateSite / updatePages', async () => {
259259
`)
260260
expect(userSitePages.length, 'set pages should be 1').toBe(1)
261261
expect(userSitePages.length).toBe(1) // Ensure no new pages were added
262-
expect(userSitePages[0].cardId).toBe('card1')
263-
expect(userSitePages[0].slug.value).toBe(undefined)
264-
expect(userSitePages[0].title.value).toBe('Updated Title')
265-
expect(userSitePages[0].userConfig.value.otherProp).toBe('Updated')
262+
expect(userSitePages[0]?.cardId).toBe('card1')
263+
expect(userSitePages[0]?.slug.value).toBe(undefined)
264+
expect(userSitePages[0]?.title.value).toBe('Updated Title')
265+
expect(userSitePages[0]?.userConfig.value.otherProp).toBe('Updated')
266266
})
267267
})
268268

@fiction/ui/anim/gradientUtil.ts

+36-78
Original file line numberDiff line numberDiff line change
@@ -15,9 +15,9 @@ export function hexToRgb(hex: string): { r: number, g: number, b: number } | nul
1515
const result = /^#?([a-f\d]{2})([a-f\d]{2})([a-f\d]{2})$/i.exec(hex)
1616
return result
1717
? {
18-
r: Number.parseInt(result[1], 16),
19-
g: Number.parseInt(result[2], 16),
20-
b: Number.parseInt(result[3], 16),
18+
r: Number.parseInt(result[1] ?? '0', 16),
19+
g: Number.parseInt(result[2] ?? '0', 16),
20+
b: Number.parseInt(result[3] ?? '0', 16),
2121
}
2222
: null
2323
}
@@ -81,8 +81,9 @@ export class SimplexNoise {
8181
this.perm = new Uint8Array(512)
8282
this.permMod12 = new Uint8Array(512)
8383
for (let i = 0; i < 512; i++) {
84-
this.perm[i] = this.p[i & 255]
85-
this.permMod12[i] = this.perm[i] % 12
84+
const o = this.p[i & 255] ?? 0
85+
this.perm[i] = 0
86+
this.permMod12[i] = o % 12
8687
}
8788

8889
this.grad3 = new Float32Array([1, 1, 0, -1, 1, 0, 1, -1, 0, -1, -1, 0, 1, 0, 1, -1, 0, 1, 1, 0, -1, -1, 0, -1, 0, 1, 1, 0, -1, 1, 0, 1, -1, 0, -1, -1])
@@ -93,7 +94,6 @@ export class SimplexNoise {
9394
const F3 = 1 / 3
9495
const G3 = 1 / 6
9596

96-
let n0: number, n1: number, n2: number, n3: number
9797
const s: number = (xin + yin + zin) * F3
9898
const i: number = Math.floor(xin + s)
9999
const j: number = Math.floor(yin + s)
@@ -110,54 +110,24 @@ export class SimplexNoise {
110110
let i2: number, j2: number, k2: number
111111
if (x0 >= y0) {
112112
if (y0 >= z0) {
113-
i1 = 1
114-
j1 = 0
115-
k1 = 0
116-
i2 = 1
117-
j2 = 1
118-
k2 = 0
113+
[i1, j1, k1, i2, j2, k2] = [1, 0, 0, 1, 1, 0]
119114
}
120115
else if (x0 >= z0) {
121-
i1 = 1
122-
j1 = 0
123-
k1 = 0
124-
i2 = 1
125-
j2 = 0
126-
k2 = 1
116+
[i1, j1, k1, i2, j2, k2] = [1, 0, 0, 1, 0, 1]
127117
}
128118
else {
129-
i1 = 0
130-
j1 = 0
131-
k1 = 1
132-
i2 = 1
133-
j2 = 0
134-
k2 = 1
119+
[i1, j1, k1, i2, j2, k2] = [0, 0, 1, 1, 0, 1]
135120
}
136121
}
137122
else {
138123
if (y0 < z0) {
139-
i1 = 0
140-
j1 = 0
141-
k1 = 1
142-
i2 = 0
143-
j2 = 1
144-
k2 = 1
124+
[i1, j1, k1, i2, j2, k2] = [0, 0, 1, 0, 1, 1]
145125
}
146126
else if (x0 < z0) {
147-
i1 = 0
148-
j1 = 1
149-
k1 = 0
150-
i2 = 0
151-
j2 = 1
152-
k2 = 1
127+
[i1, j1, k1, i2, j2, k2] = [0, 1, 0, 0, 1, 1]
153128
}
154129
else {
155-
i1 = 0
156-
j1 = 1
157-
k1 = 0
158-
i2 = 1
159-
j2 = 1
160-
k2 = 0
130+
[i1, j1, k1, i2, j2, k2] = [0, 1, 0, 1, 1, 0]
161131
}
162132
}
163133

@@ -175,45 +145,33 @@ export class SimplexNoise {
175145
const jj: number = j & 255
176146
const kk: number = k & 255
177147

178-
let t0: number = 0.6 - x0 * x0 - y0 * y0 - z0 * z0
179-
if (t0 < 0) {
180-
n0 = 0
181-
}
182-
else {
183-
const gi0: number = permMod12[ii + perm[jj + perm[kk]]] * 3
184-
t0 *= t0
185-
n0 = t0 * t0 * (grad3[gi0] * x0 + grad3[gi0 + 1] * y0 + grad3[gi0 + 2] * z0)
148+
const calculateNoise = (t: number, gi: number, x: number, y: number, z: number): number => {
149+
if (t < 0)
150+
return 0
151+
t *= t
152+
return t * t * ((grad3[gi] ?? 0) * x + (grad3[gi + 1] ?? 0) * y + (grad3[gi + 2] ?? 0) * z)
186153
}
187154

188-
let t1: number = 0.6 - x1 * x1 - y1 * y1 - z1 * z1
189-
if (t1 < 0) {
190-
n1 = 0
191-
}
192-
else {
193-
const gi1: number = permMod12[ii + i1 + perm[jj + j1 + perm[kk + k1]]] * 3
194-
t1 *= t1
195-
n1 = t1 * t1 * (grad3[gi1] * x1 + grad3[gi1 + 1] * y1 + grad3[gi1 + 2] * z1)
155+
const getGi = (i: number, j: number, k: number): number => {
156+
const index = ii + i + (perm[jj + j + (perm[kk + k] ?? 0)] ?? 0)
157+
return (permMod12[index] ?? 0) * 3
196158
}
197159

198-
let t2: number = 0.6 - x2 * x2 - y2 * y2 - z2 * z2
199-
if (t2 < 0) {
200-
n2 = 0
201-
}
202-
else {
203-
const gi2: number = permMod12[ii + i2 + perm[jj + j2 + perm[kk + k2]]] * 3
204-
t2 *= t2
205-
n2 = t2 * t2 * (grad3[gi2] * x2 + grad3[gi2 + 1] * y2 + grad3[gi2 + 2] * z2)
206-
}
160+
const t0: number = 0.6 - x0 * x0 - y0 * y0 - z0 * z0
161+
const gi0: number = getGi(0, 0, 0)
162+
const n0 = calculateNoise(t0, gi0, x0, y0, z0)
207163

208-
let t3: number = 0.6 - x3 * x3 - y3 * y3 - z3 * z3
209-
if (t3 < 0) {
210-
n3 = 0
211-
}
212-
else {
213-
const gi3: number = permMod12[ii + 1 + perm[jj + 1 + perm[kk + 1]]] * 3
214-
t3 *= t3
215-
n3 = t3 * t3 * (grad3[gi3] * x3 + grad3[gi3 + 1] * y3 + grad3[gi3 + 2] * z3)
216-
}
164+
const t1: number = 0.6 - x1 * x1 - y1 * y1 - z1 * z1
165+
const gi1: number = getGi(i1, j1, k1)
166+
const n1 = calculateNoise(t1, gi1, x1, y1, z1)
167+
168+
const t2: number = 0.6 - x2 * x2 - y2 * y2 - z2 * z2
169+
const gi2: number = getGi(i2, j2, k2)
170+
const n2 = calculateNoise(t2, gi2, x2, y2, z2)
171+
172+
const t3: number = 0.6 - x3 * x3 - y3 * y3 - z3 * z3
173+
const gi3: number = getGi(1, 1, 1)
174+
const n3 = calculateNoise(t3, gi3, x3, y3, z3)
217175

218176
return 32 * (n0 + n1 + n2 + n3)
219177
}
@@ -225,8 +183,8 @@ export class SimplexNoise {
225183
}
226184
for (let i = 0; i < 255; i++) {
227185
const r: number = i + ~~(random() * (256 - i))
228-
const aux: number = p[i]
229-
p[i] = p[r]
186+
const aux: number = p[i] ?? 0
187+
p[i] = p[r] ?? 0
230188
p[r] = aux
231189
}
232190
return p

@fiction/ui/anim/index.ts

+3-3
Original file line numberDiff line numberDiff line change
@@ -112,15 +112,15 @@ export async function useElementVisible(args: { caller: string, selector: string
112112
let isVisible = false
113113
const observer = new IntersectionObserver((entries, observer) => {
114114
const [entry] = entries
115-
if (entry.isIntersecting && !isVisible) {
115+
if (entry?.isIntersecting && !isVisible) {
116116
isVisible = true
117117
onVisible()
118118

119119
if (!onHidden) {
120120
observer.disconnect()
121121
}
122122
}
123-
else if (!entry.isIntersecting && isVisible) {
123+
else if (!entry?.isIntersecting && isVisible) {
124124
isVisible = false
125125
if (onHidden) {
126126
onHidden()
@@ -212,7 +212,7 @@ export function animateNumber(element: HTMLElement, finalValue: number | string,
212212
round: 1,
213213
duration: 2000,
214214
update(anim) {
215-
element.innerHTML = formatNumber(anim.animations[0].currentValue, format) as string
215+
element.innerHTML = formatNumber(anim.animations[0]?.currentValue, format) as string
216216
},
217217
})
218218
observer.unobserve(element)

@fiction/ui/effect/EffectParallaxBackground.vue

+1-1
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,7 @@ let animationFrame: number | null = null
4444
4545
function updateParallax(entries: IntersectionObserverEntry[]) {
4646
const [entry] = entries
47-
if (entry.isIntersecting) {
47+
if (entry?.isIntersecting) {
4848
animationFrame = requestAnimationFrame(animate)
4949
}
5050
else if (animationFrame) {

@fiction/ui/frame/elBrowserFrameUtil.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -328,7 +328,7 @@ export class FrameNavigator extends FictionObject<FrameNavigatorSettings> {
328328
return
329329
}
330330

331-
const newPath = this.history[this.currentIndex]
331+
const newPath = this.history[this.currentIndex] ?? '/'
332332
this.setNewPath({ fullPath: newPath, updateHistory: false })
333333
}
334334

@fiction/ui/inputs/InputMediaUpload.vue

+1-1
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ async function uploadFiles(files?: FileList | null) {
4949
uploading.value = true
5050
const file = files[0]
5151
52-
if (file.size > fileSize) {
52+
if (file && file.size > fileSize) {
5353
log.warn('mediaUpload', 'File size exceeds limit')
5454
fictionEnv.events.emit('notify', {
5555
type: 'error',

0 commit comments

Comments
 (0)