video delta encoding wip

This commit is contained in:
minjaesong
2025-04-15 21:38:33 +09:00
parent 9ce7e3dfd2
commit 4c4f24be37
11 changed files with 466 additions and 29 deletions

View File

@@ -1,9 +1,9 @@
if (exec_args[1] === undefined) {
println("Usage: compile myfile")
println("Usage: compile myfile.js")
println("The compiled file will be myfile.bin")
return 1
}
_G.shell.execute(`gzip -c ${exec_args[1]} | writeto ${exec_args[1]}.gz`)
_G.shell.execute(`enc ${exec_args[1]}.gz ${exec_args[1]}.bin`)
_G.shell.execute(`rm ${exec_args[1]}.gz`)
const filenameWithoutExt = exec_args[1].substringBeforeLast(".")
_G.shell.execute(`gzip -c ${exec_args[1]} | writeto ${filenameWithoutExt}.gz`)
_G.shell.execute(`enc ${filenameWithoutExt}.gz ${filenameWithoutExt}.bin`)
_G.shell.execute(`rm ${filenameWithoutExt}.gz`)

View File

@@ -3,7 +3,6 @@ if (exec_args[1] === undefined) {
println("The compiled file will be myfile.bin.js")
return 1
}
_G.shell.execute(`enc ${exec_args[1]} ${exec_args[1]}.gz`)
_G.shell.execute(`gzip -c -d ${exec_args[1]}.gz | writeto ${exec_args[1]}.js`)
_G.shell.execute(`rm ${exec_args[1]}.gz`)

View File

@@ -8,7 +8,10 @@ if (exec_args[1] === undefined || exec_args[2] === undefined) {
let infilePath = _G.shell.resolvePathInput(exec_args[2]).full
let infile = files.open(infilePath)
let outfile = files.open(infilePath + ".out")
if (!infile.exists) throw Error("No such file: " + infilePath)
let outfile = files.open(infilePath.substringBeforeLast(".") + ".out")
let outMode = exec_args[1].toLowerCase()
let type = {

View File

@@ -7,11 +7,11 @@ let PATHFUN = (i) => `/ddol/${(''+i).padStart(5,'0')}.png`
const FBUF_SIZE = WIDTH * HEIGHT
let infile = sys.malloc(512000) // somewhat arbitrary
let imagearea = sys.malloc(FBUF_SIZE*3)
let decodearea = sys.malloc(FBUF_SIZE)
let ipfarea = sys.malloc(FBUF_SIZE)
let gzippedImage = sys.malloc(512000) // somewhat arbitrary
let infile = sys.malloc(512000) // allocate somewhat arbitrary amount of memory
let imagearea = sys.malloc(FBUF_SIZE*3) // allocate exact amount of memory
let decodearea = sys.malloc(FBUF_SIZE) // allocate exact amount of memory
let ipfarea = sys.malloc(FBUF_SIZE) // allocate exact amount of memory
let gzippedImage = sys.malloc(512000) // allocate somewhat arbitrary amount of memory
let outfilename = exec_args[1]
@@ -69,6 +69,7 @@ for (let f = 1; f <= TOTAL_FRAMES; f++) {
print(` ${gzlen} bytes\n`)
}
// free all the memory that has been allocated
sys.free(infile)
sys.free(imagearea)
sys.free(decodearea)

View File

@@ -0,0 +1,101 @@
// some manual config shits
let TOTAL_FRAMES = 3813
let FPS = 30
let WIDTH = 560
let HEIGHT = 448
let PATHFUN = (i) => `/ddol/${(''+i).padStart(5,'0')}.png`
if (WIDTH % 4 != 0 || HEIGHT % 4 != 0) {
printerrln(`Frame dimension is not multiple of 4 (${WIDTH}x${HEIGHT})`)
return 5
}
const FBUF_SIZE = WIDTH * HEIGHT
let infile = sys.malloc(512000) // somewhat arbitrary
let imagearea = sys.malloc(FBUF_SIZE*3)
let decodearea = sys.malloc(FBUF_SIZE)
let ipfarea1 = sys.malloc(FBUF_SIZE)
let ipfarea2 = sys.malloc(FBUF_SIZE)
let ipfDelta = sys.malloc(FBUF_SIZE)
let gzippedImage = sys.malloc(512000) // somewhat arbitrary
let outfilename = exec_args[1]
if (!outfilename) return 1
function appendToOutfile(bytes) {
filesystem.open("A", outfilename, "A")
filesystem.writeBytes("A", bytes)
}
function appendToOutfilePtr(ptr, len) {
filesystem.open("A", outfilename, "A")
dma.ramToCom(ptr, 0, len)
}
// write header to the file
let headerBytes = [
0x1F, 0x54, 0x53, 0x56, 0x4D, 0x4D, 0x4F, 0x56, // magic
WIDTH & 255, (WIDTH >> 8) & 255, // width
HEIGHT & 255, (HEIGHT >> 8) & 255, // height
FPS & 255, (FPS >> 8) & 255, // FPS
TOTAL_FRAMES & 255, (TOTAL_FRAMES >> 8) & 255, (TOTAL_FRAMES >> 16) & 255, (TOTAL_FRAMES >> 24) & 255, // frame count
0x04, 0x00, // type 4 frames (force no-alpha)
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 // reserved
]
filesystem.open("A", outfilename, "W")
filesystem.writeBytes("A", headerBytes)
let ipfAreaOld = ipfarea2
let ipfAreaNew = ipfarea1
for (let f = 1; f <= TOTAL_FRAMES; f++) {
let fname = PATHFUN(f)
filesystem.open("A", fname, "R")
let fileLen = filesystem.getFileLen("A")
dma.comToRam(0, 0, infile, fileLen)
let [_1, _2, channels, _3] = graphics.decodeImageTo(infile, fileLen, imagearea)
const val IPF_BLOCK_SIZE = (channels == 3) ? 12 : 20;
print(`Frame ${f}/${TOTAL_FRAMES} (Ch: ${channels}) ->`)
// graphics.imageToDisplayableFormat(imagearea, decodearea, 560, 448, 3, 1)
graphics.encodeIpf1(imagearea, ipfAreaNew, WIDTH, HEIGHT, channels, false, 0)
// get the difference map
let patchEncodedSize = graphics.encodeIpf1d(ipfAreaOld, ipfAreaNew, ipfDelta, WIDTH, HEIGHT, 0.90)
// decide whether or not the patch encoding should be used
let gzlen = gzip.compFromTo(
(patchEncodedSize) ? ipfDelta : ipfAreaNew,
patchEncodedSize || FBUF_SIZE,
gzippedImage
)
let frameSize = [
(gzlen >>> 0) & 255,
(gzlen >>> 8) & 255,
(gzlen >>> 16) & 255,
(gzlen >>> 24) & 255
]
appendToOutfile(frameSize)
appendToOutfilePtr(gzippedImage, gzlen)
print(` ${gzlen} bytes\n`)
// swap two pointers
let t = ipfAreaOld
ipfAreaOld = ipfAreaNew
ipfAreaNew = t
}
sys.free(infile)
sys.free(imagearea)
sys.free(decodearea)
sys.free(ipfarea1)
sys.free(ipfarea2)
sys.free(ipfDelta)
sys.free(gzippedImage)