diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..d48c759 --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +.idea +.vscode \ No newline at end of file diff --git a/_template_.js b/_template_.js index aa7e7bf..2087ac8 100644 --- a/_template_.js +++ b/_template_.js @@ -579,7 +579,16 @@ class NewComicSource extends ComicSource { // * @returns {ArrayBuffer} onResponse: (data) => { return data - } + }, + // {string | null} a js script. The script will be executed in a new Isolate. + // The script should contain a function named `modifyImage`, which receives an [Image] as the only argument, and returns an [Image]. + // Only [Image] api is available in the script. + // Do not use this field if it is not necessary. + modifyImage: ` + function modifyImage(buffer) { + + } + `, } ``` */ @@ -606,7 +615,16 @@ class NewComicSource extends ComicSource { // modify response data onResponse: (data) => { return data - } + }, + // {string | null} a js script. The script will be executed in a new Isolate. + // The script should contain a function named `modifyImage`, which receives an [Image] as the only argument, and returns an [Image]. + // Only [Image] api is available in the script. + // Do not use this field if it is not necessary. + modifyImage: ` + function modifyImage(image) { + + } + `, } ``` */ diff --git a/_venera_.js b/_venera_.js index 9f00eb3..932590c 100644 --- a/_venera_.js +++ b/_venera_.js @@ -224,7 +224,25 @@ let Convert = { key: key, isEncode: false }); - } + }, + /** Encode bytes to hex string + * @param bytes {ArrayBuffer} + * @return {string} + */ + hexEncode: (bytes) => { + const hexDigits = '0123456789abcdef'; + const view = new Uint8Array(bytes); + let charCodes = new Uint8Array(view.length * 2); + let j = 0; + + for (let i = 0; i < view.length; i++) { + let byte = view[i]; + charCodes[j++] = hexDigits.charCodeAt((byte >> 4) & 0xF); + charCodes[j++] = hexDigits.charCodeAt(byte & 0xF); + } + + return String.fromCharCode(...charCodes); + }, } /** @@ -999,4 +1017,118 @@ class ComicSource { init() { } static sources = {} -} \ No newline at end of file +} + +/// A reference to dart object. +/// The api can only be used in the comic.onImageLoad.modifyImage function +class Image { + key = 0; + + constructor(key) { + this.key = key; + } + + /** + * Copy the specified range of the image + * @param x + * @param y + * @param width + * @param height + * @returns {Image|null} + */ + copyRange(x, y, width, height) { + let key = sendMessage({ + method: "image", + function: "copyRange", + key: this.key, + x: x, + y: y, + width: width, + height: height + }) + if(key == null) return null; + return new Image(key); + } + + /** + * Copy the image and rotate 90 degrees + * @returns {Image|null} + */ + copyAndRotate90() { + let key = sendMessage({ + method: "image", + function: "copyAndRotate90", + key: this.key + }) + if(key == null) return null; + return new Image(key); + } + + /** + * fill [image] to this image at (x, y) + * @param x + * @param y + * @param image + */ + fillImageAt(x, y, image) { + sendMessage({ + method: "image", + function: "fillImageAt", + key: this.key, + x: x, + y: y, + image: image.key + }) + } + + /** + * fill [image] with range(srcX, srcY, width, height) to this image at (x, y) + * @param x + * @param y + * @param image + * @param srcX + * @param srcY + * @param width + * @param height + */ + fillImageRangeAt(x, y, image, srcX, srcY, width, height) { + sendMessage({ + method: "image", + function: "fillImageRangeAt", + key: this.key, + x: x, + y: y, + image: image.key, + srcX: srcX, + srcY: srcY, + width: width, + height: height + }) + } + + get width() { + return sendMessage({ + method: "image", + function: "getWidth", + key: this.key + }) + } + + get height() { + return sendMessage({ + method: "image", + function: "getHeight", + key: this.key + }) + } + + static empty(width, height) { + let key = sendMessage({ + method: "image", + function: "emptyImage", + width: width, + height: height + }) + return new Image(key); + } +}