Skip to content

Commit

Permalink
feat: fill canvas color
Browse files Browse the repository at this point in the history
  • Loading branch information
guiseek committed Aug 26, 2024
1 parent 2251798 commit ed273d8
Show file tree
Hide file tree
Showing 13 changed files with 69 additions and 4 deletions.
3 changes: 2 additions & 1 deletion src/constants/icon.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,5 +5,6 @@ export const icon = {
edit: `<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 -960 960 960" fill="currentColor"> <path d="M200-200h57l391-391-57-57-391 391v57Zm-80 80v-170l528-527q12-11 26.5-17t30.5-6q16 0 31 6t26 18l55 56q12 11 17.5 26t5.5 30q0 16-5.5 30.5T817-647L290-120H120Zm640-584-56-56 56 56Zm-141 85-28-29 57 57-29-28Z"/> </svg>`,
delete: `<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 -960 960 960" fill="currentColor"> <path d="M280-120q-33 0-56.5-23.5T200-200v-520h-40v-80h200v-40h240v40h200v80h-40v520q0 33-23.5 56.5T680-120H280Zm400-600H280v520h400v-520ZM360-280h80v-360h-80v360Zm160 0h80v-360h-80v360ZM280-720v520-520Z"/> </svg>`,
bringToFront: `<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 -960 960 960" fill="currentColor"> <path d="M360-280q-33 0-56.5-23.5T280-360v-400q0-33 23.5-56.5T360-840h400q33 0 56.5 23.5T840-760v400q0 33-23.5 56.5T760-280H360Zm0-80h400v-400H360v400ZM200-200v80q-33 0-56.5-23.5T120-200h80Zm-80-80v-80h80v80h-80Zm0-160v-80h80v80h-80Zm0-160v-80h80v80h-80Zm160 480v-80h80v80h-80Zm160 0v-80h80v80h-80Zm160 0v-80h80v80h-80Z"/> </svg>`,
sendToBack: `<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 -960 960 960" fill="currentColor"> <path d="M200-120q-33 0-56.5-23.5T120-200v-480h80v480h480v80H200Zm160-240v80q-33 0-56.5-23.5T280-360h80Zm-80-80v-80h80v80h-80Zm0-160v-80h80v80h-80Zm80-160h-80q0-33 23.5-56.5T360-840v80Zm80 480v-80h80v80h-80Zm0-480v-80h80v80h-80Zm160 0v-80h80v80h-80Zm0 480v-80h80v80h-80Zm160-480v-80q33 0 56.5 23.5T840-760h-80Zm0 400h80q0 33-23.5 56.5T760-280v-80Zm0-80v-80h80v80h-80Zm0-160v-80h80v80h-80Z"/> </svg>`
sendToBack: `<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 -960 960 960" fill="currentColor"> <path d="M200-120q-33 0-56.5-23.5T120-200v-480h80v480h480v80H200Zm160-240v80q-33 0-56.5-23.5T280-360h80Zm-80-80v-80h80v80h-80Zm0-160v-80h80v80h-80Zm80-160h-80q0-33 23.5-56.5T360-840v80Zm80 480v-80h80v80h-80Zm0-480v-80h80v80h-80Zm160 0v-80h80v80h-80Zm0 480v-80h80v80h-80Zm160-480v-80q33 0 56.5 23.5T840-760h-80Zm0 400h80q0 33-23.5 56.5T760-280v-80Zm0-80v-80h80v80h-80Zm0-160v-80h80v80h-80Z"/> </svg>`,
fill: `<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 -960 960 960" fill="currentColor"> <path d="m247-904 57-56 343 343q23 23 23 57t-23 57L457-313q-23 23-57 23t-57-23L153-503q-23-23-23-57t23-57l190-191-96-96Zm153 153L209-560h382L400-751Zm360 471q-33 0-56.5-23.5T680-360q0-21 12.5-45t27.5-45q9-12 19-25t21-25q11 12 21 25t19 25q15 21 27.5 45t12.5 45q0 33-23.5 56.5T760-280ZM80 0v-160h800V0H80Z"/> </svg>`
}
15 changes: 15 additions & 0 deletions src/features/canvas/canvas.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,16 @@ class Canvas extends HTMLCanvasElement implements CanvasLike {

#isContextMenu = false

#fill = ''

get fill() {
return this.#fill
}

setFill(fill: string) {
this.#fill = fill
}

constructor() {
super()
this.context = this.getContext('2d')
Expand Down Expand Up @@ -44,6 +54,11 @@ class Canvas extends HTMLCanvasElement implements CanvasLike {
if (!this.offscreenContext || !this.context) return

this.offscreenContext.clearRect(0, 0, this.width, this.height)

if (this.fill) {
this.offscreenContext.fillStyle = this.fill
this.offscreenContext.fillRect(0, 0, this.width, this.height)
}

const layers = this.#layers
.filter((layer) => layer.active)
Expand Down
3 changes: 3 additions & 0 deletions src/features/forms/events.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,3 +2,6 @@ import {createEvent, createListener} from '@websqnl/event-flow'

export const formTextSubmit = createEvent('form.text.submit')
export const onFormTextSubmit = createListener('form.text.submit')

export const formFillSubmit = createEvent('form.fill.submit')
export const onFormFillSubmit = createListener('form.fill.submit')
1 change: 1 addition & 0 deletions src/features/forms/handlers/index.ts
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
export * from './on-form-fill-submit';
export * from './on-form-text-submit';
7 changes: 7 additions & 0 deletions src/features/forms/handlers/on-form-fill-submit.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
import {onFormFillSubmit} from '../events'
import {canvas} from '@features/canvas'

onFormFillSubmit((value) => {
canvas.setFill(value.color)
canvas.render().then()
})
3 changes: 3 additions & 0 deletions src/features/toolbar/events.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,3 +8,6 @@ export const onToolbarSelectImage = createListener('toolbar.select.image')

export const toolbarSelectText = createEvent('toolbar.select.text')
export const onToolbarSelectText = createListener('toolbar.select.text')

export const toolbarSelectFill = createEvent('toolbar.select.fill')
export const onToolbarSelectFill = createListener('toolbar.select.fill')
1 change: 1 addition & 0 deletions src/features/toolbar/handlers/index.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
export * from './on-toolbar-select-fill';
export * from './on-toolbar-select-image';
export * from './on-toolbar-select-text';
export * from './on-toolbar-selected';
19 changes: 19 additions & 0 deletions src/features/toolbar/handlers/on-toolbar-select-fill.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
import {FormDialog, formFillSubmit} from '@features/forms'
import {onToolbarSelectFill} from '../events'
import {Input} from '@websqnl/elements'

onToolbarSelectFill(() => {
const color = new Input({
type: 'color',
name: 'color',
value: '#000000',
})

const controls = {color}

const dialog = new FormDialog<FillForm>(controls, formFillSubmit)

document.body.insertAdjacentElement('beforeend', dialog)

dialog.showModal()
})
4 changes: 4 additions & 0 deletions src/features/toolbar/handlers/on-toolbar-selected.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import {
onToolbarSelected,
toolbarSelectFill,
toolbarSelectImage,
toolbarSelectText,
} from '../events'
Expand All @@ -13,5 +14,8 @@ onToolbarSelected((action) => {
case 'text': {
return dispatch(toolbarSelectText())
}
case 'fill': {
return dispatch(toolbarSelectFill())
}
}
})
1 change: 1 addition & 0 deletions src/features/toolbar/toolbar.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ export class Toolbar extends HTMLMenuElement {
buttons = {
image: this.#button(icon.image, 'image', 'Select image'),
text: this.#button(icon.text, 'text', 'Write text'),
fill: this.#button(icon.fill, 'fill', 'Format color fill'),
}

connectedCallback() {
Expand Down
1 change: 1 addition & 0 deletions src/styles/_forms.scss
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ dialog {

footer {
flex: 1;
gap: 0.6em;
display: flex;
flex-direction: row-reverse;
justify-content: space-between;
Expand Down
7 changes: 5 additions & 2 deletions src/styles/_toolbar.scss
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
menu.cf-toolbar {
display: flex;
flex-flow: row wrap;
flex-direction: column;
gap: 0.2em;
max-width: 6em;
background-color: #dadada;

margin: 0;
Expand All @@ -27,4 +26,8 @@ menu.cf-toolbar {
color: rgb(var(--cf-onsurface-rgb));
}
}

@media (max-width: 640px) {
flex-direction: row;
}
}
8 changes: 7 additions & 1 deletion src/vite-env.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ interface RectLike {
h: number
}

type LayerType = 'image' | 'text'
type LayerType = 'image' | 'text' | 'fill'

type TextWeight = 'bold' | 'normal'

Expand Down Expand Up @@ -106,8 +106,13 @@ interface TextForm {
bold: boolean
}

interface FillForm {
color: string
}

interface StateEventMap {
'form.text.submit': TextForm
'form.fill.submit': FillForm

'canvas.render.request': void
'canvas.update.size': CanvasSize
Expand All @@ -118,6 +123,7 @@ interface StateEventMap {

'toolbar.select.image': void
'toolbar.select.text': void
'toolbar.select.fill': void
'toolbar.selected': LayerType

'context.open': ContextOpenEvent
Expand Down

0 comments on commit ed273d8

Please sign in to comment.