From d7fec98714ed8e574b0daa8fce677aca8a60f976 Mon Sep 17 00:00:00 2001 From: dylan <> Date: Wed, 10 May 2023 19:58:01 -0700 Subject: [PATCH] Add ellipse drawing --- builtins.ts | 4 ++++ carts/tmp/oval.fx | 1 + pico8_builtins.txt | 4 ++-- window.ts | 38 ++++++++++++++++++++++++++++++++++++++ 4 files changed, 45 insertions(+), 2 deletions(-) create mode 100644 carts/tmp/oval.fx diff --git a/builtins.ts b/builtins.ts index 2e4a9fa..20577ca 100644 --- a/builtins.ts +++ b/builtins.ts @@ -5,6 +5,8 @@ import { cameraPos, fillCircle, outlineCircle, +fillEllipse, +outlineEllipse, } from "./window.ts"; import { Font, font } from "./font.ts"; import { keyDown, keyPressed, keyReleased } from "./keyboard.ts"; @@ -96,6 +98,8 @@ const faux = { rect: outlineRect, circfill: fillCircle, circ: outlineCircle, + ovalfill: fillEllipse, + oval: outlineEllipse, map: (mapSheet: number, tileX: number, tileY: number, screenX: number, screenY: number, tileW: number, tileH: number) => { const originalSpritesheet = getSpritesheet() ?? 0; getMapSheet(mapSheet).forEach(([sprSheet, spr], i) => { diff --git a/carts/tmp/oval.fx b/carts/tmp/oval.fx new file mode 100644 index 0000000..58f44a4 --- /dev/null +++ b/carts/tmp/oval.fx @@ -0,0 +1 @@ +[{"sheet_type":"code","value":"// Sample\n\nlet r = 0;\nlet d = 1;\nreturn {\n\tinit() {},\n\tupdate() {\n\t\tif (r >= 20) {\n\t\t\td = -1;\n\t\t} else if (r < 0) {\n\t\t\td = 1;\n\t\t}\n\t\tr += d*0.1;\t\n\t},\n\tdraw() {\n\t\tcls();\n\t\trectfill(50,50,46,21,6);\n\t\toval(50, 50, 95, 70, 17);\n\t\ttxt(10,10,\"Hello, World!\");\n\t}\n}"},{"sheet_type":"none","value":null},{"sheet_type":"none","value":null},{"sheet_type":"none","value":null},{"sheet_type":"none","value":null},{"sheet_type":"none","value":null},{"sheet_type":"none","value":null},{"sheet_type":"none","value":null},{"sheet_type":"none","value":null},{"sheet_type":"none","value":null},{"sheet_type":"none","value":null},{"sheet_type":"none","value":null},{"sheet_type":"none","value":null},{"sheet_type":"none","value":null},{"sheet_type":"none","value":null},{"sheet_type":"none","value":null}] \ No newline at end of file diff --git a/pico8_builtins.txt b/pico8_builtins.txt index 6be41b5..8d5d2c8 100644 --- a/pico8_builtins.txt +++ b/pico8_builtins.txt @@ -29,8 +29,8 @@ - [x] camera - [x] circ - [x] circfill -- [ ] oval -- [ ] ovalfill +- [x] oval +- [x] ovalfill - [ ] line - [x] rect - [x] rectfill diff --git a/window.ts b/window.ts index af9bb8d..05f9257 100644 --- a/window.ts +++ b/window.ts @@ -194,6 +194,44 @@ export const outlineCircle = (x: number, y: number, r: number, color: number) => } } +export const fillEllipse = (x0: number, y0: number, x1: number, y1: number, color: number) => { + const x = 0.5*(x0 + x1); + const y = 0.5*(y0 + y1); + const rx = Math.abs(x0-x1)/2; + const ry = Math.abs(y0-y1)/2; + const left = Math.floor(x-rx-1); + const top = Math.floor(y-ry-1); + for (let i = left; i <= Math.ceil(x+rx+1); i ++) { + for (let j = top; j <= Math.ceil(y+ry+1); j ++) { + if (Math.sqrt(((x-i)/rx)**2 + ((y-j)/ry)**2) <= 1+(1/(rx+ry))) { + setPixelColor(i, j, color); + } + } + } +} + +export const outlineEllipse = (x0: number, y0: number, x1: number, y1: number, color: number) => { + const x = 0.5*(x0 + x1); + const y = 0.5*(y0 + y1); + const rx = Math.abs(x0-x1)/2; + const ry = Math.abs(y0-y1)/2; + const left = Math.floor(x-rx-1); + const top = Math.floor(y-ry-1); + const inR = (d: number) => d <= 1+1/(rx+ry); + for (let i = left; i <= Math.ceil(x+rx+1); i ++) { + for (let j = top; j <= Math.ceil(y+ry+1); j ++) { + const d = Math.sqrt(((x-i)/rx)**2 + ((y-j)/ry)**2); + if (inR(d)) { + const dh = Math.sqrt(((x-(i+Math.sign(i-x)))/rx)**2 + ((y-j)/ry)**2); + const dv = Math.sqrt(((x-i)/rx)**2 + ((y-(j+Math.sign(j-y)))/ry)**2); + if (!inR(dh) || !inR(dv)) { + setPixelColor(i, j, color); + } + } + } + } +} + export const fillRectRaw = (x: number, y: number, w: number, h: number, color: number) => { setPixelsInRectRaw(x, y, w, Array(w*h).fill(color)); }