From daed1baafd76ca034ac09143b3376a0a892e6d74 Mon Sep 17 00:00:00 2001 From: xzeldon Date: Mon, 2 Jan 2023 10:31:09 +0300 Subject: [PATCH] Initial repo --- .gitignore | 197 +++++++++++++++++++++ .npmignore | 13 ++ Cargo.toml | 2 + assets/XO_Thames_Nu.ttf | Bin 0 -> 89196 bytes crates/bindings/Cargo.toml | 17 ++ crates/bindings/build.rs | 5 + crates/bindings/src/lib.rs | 8 + crates/meow_image/.gitignore | 3 + crates/meow_image/Cargo.toml | 14 ++ crates/meow_image/README.md | 12 ++ crates/meow_image/src/demotivate.rs | 189 ++++++++++++++++++++ crates/meow_image/src/lib.rs | 4 + crates/meow_image/src/text_width.rs | 17 ++ package-lock.json | 256 ++++++++++++++++++++++++++++ package.json | 29 ++++ rustfmt.toml | 2 + 16 files changed, 768 insertions(+) create mode 100644 .gitignore create mode 100644 .npmignore create mode 100644 Cargo.toml create mode 100644 assets/XO_Thames_Nu.ttf create mode 100644 crates/bindings/Cargo.toml create mode 100644 crates/bindings/build.rs create mode 100644 crates/bindings/src/lib.rs create mode 100644 crates/meow_image/.gitignore create mode 100644 crates/meow_image/Cargo.toml create mode 100644 crates/meow_image/README.md create mode 100644 crates/meow_image/src/demotivate.rs create mode 100644 crates/meow_image/src/lib.rs create mode 100644 crates/meow_image/src/text_width.rs create mode 100644 package-lock.json create mode 100644 package.json create mode 100644 rustfmt.toml diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..5e2577b --- /dev/null +++ b/.gitignore @@ -0,0 +1,197 @@ +# Created by https://www.toptal.com/developers/gitignore/api/node +# Edit at https://www.toptal.com/developers/gitignore?templates=node + +### Node ### +# Logs +logs +*.log +npm-debug.log* +yarn-debug.log* +yarn-error.log* +lerna-debug.log* + +# Diagnostic reports (https://nodejs.org/api/report.html) +report.[0-9]*.[0-9]*.[0-9]*.[0-9]*.json + +# Runtime data +pids +*.pid +*.seed +*.pid.lock + +# Directory for instrumented libs generated by jscoverage/JSCover +lib-cov + +# Coverage directory used by tools like istanbul +coverage +*.lcov + +# nyc test coverage +.nyc_output + +# Grunt intermediate storage (https://gruntjs.com/creating-plugins#storing-task-files) +.grunt + +# Bower dependency directory (https://bower.io/) +bower_components + +# node-waf configuration +.lock-wscript + +# Compiled binary addons (https://nodejs.org/api/addons.html) +build/Release + +# Dependency directories +node_modules/ +jspm_packages/ + +# TypeScript v1 declaration files +typings/ + +# TypeScript cache +*.tsbuildinfo + +# Optional npm cache directory +.npm + +# Optional eslint cache +.eslintcache + +# Microbundle cache +.rpt2_cache/ +.rts2_cache_cjs/ +.rts2_cache_es/ +.rts2_cache_umd/ + +# Optional REPL history +.node_repl_history + +# Output of 'npm pack' +*.tgz + +# Yarn Integrity file +.yarn-integrity + +# dotenv environment variables file +.env +.env.test + +# parcel-bundler cache (https://parceljs.org/) +.cache + +# Next.js build output +.next + +# Nuxt.js build / generate output +.nuxt +dist + +# Gatsby files +.cache/ +# Comment in the public line in if your project uses Gatsby and not Next.js +# https://nextjs.org/blog/next-9-1#public-directory-support +# public + +# vuepress build output +.vuepress/dist + +# Serverless directories +.serverless/ + +# FuseBox cache +.fusebox/ + +# DynamoDB Local files +.dynamodb/ + +# TernJS port file +.tern-port + +# Stores VSCode versions used for testing VSCode extensions +.vscode-test + +# End of https://www.toptal.com/developers/gitignore/api/node + +# Created by https://www.toptal.com/developers/gitignore/api/macos +# Edit at https://www.toptal.com/developers/gitignore?templates=macos + +### macOS ### +# General +.DS_Store +.AppleDouble +.LSOverride + +# Icon must end with two +Icon + + +# Thumbnails +._* + +# Files that might appear in the root of a volume +.DocumentRevisions-V100 +.fseventsd +.Spotlight-V100 +.TemporaryItems +.Trashes +.VolumeIcon.icns +.com.apple.timemachine.donotpresent + +# Directories potentially created on remote AFP share +.AppleDB +.AppleDesktop +Network Trash Folder +Temporary Items +.apdisk + +### macOS Patch ### +# iCloud generated files +*.icloud + +# End of https://www.toptal.com/developers/gitignore/api/macos + +# Created by https://www.toptal.com/developers/gitignore/api/windows +# Edit at https://www.toptal.com/developers/gitignore?templates=windows + +### Windows ### +# Windows thumbnail cache files +Thumbs.db +Thumbs.db:encryptable +ehthumbs.db +ehthumbs_vista.db + +# Dump file +*.stackdump + +# Folder config file +[Dd]esktop.ini + +# Recycle Bin used on file shares +$RECYCLE.BIN/ + +# Windows Installer files +*.cab +*.msi +*.msix +*.msm +*.msp + +# Windows shortcuts +*.lnk + +# End of https://www.toptal.com/developers/gitignore/api/windows + +#Added by cargo + +/target +Cargo.lock + +.pnp.* +.yarn/* +!.yarn/patches +!.yarn/plugins +!.yarn/releases +!.yarn/sdks +!.yarn/versions + +*.node diff --git a/.npmignore b/.npmignore new file mode 100644 index 0000000..ec144db --- /dev/null +++ b/.npmignore @@ -0,0 +1,13 @@ +target +Cargo.lock +.cargo +.github +npm +.eslintrc +.prettierignore +rustfmt.toml +yarn.lock +*.node +.yarn +__test__ +renovate.json diff --git a/Cargo.toml b/Cargo.toml new file mode 100644 index 0000000..c66a4d7 --- /dev/null +++ b/Cargo.toml @@ -0,0 +1,2 @@ +[workspace] +members = ["crates/*"] diff --git a/assets/XO_Thames_Nu.ttf b/assets/XO_Thames_Nu.ttf new file mode 100644 index 0000000000000000000000000000000000000000..0e0f89ff112d5927e70d2c4dea787df4c0fdc6b2 GIT binary patch literal 89196 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 Q i32 { + a + b +} diff --git a/crates/meow_image/.gitignore b/crates/meow_image/.gitignore new file mode 100644 index 0000000..7c76862 --- /dev/null +++ b/crates/meow_image/.gitignore @@ -0,0 +1,3 @@ +/target +dem.jpg +font.ttf diff --git a/crates/meow_image/Cargo.toml b/crates/meow_image/Cargo.toml new file mode 100644 index 0000000..7c8785f --- /dev/null +++ b/crates/meow_image/Cargo.toml @@ -0,0 +1,14 @@ +[package] +name = "meow_image" +description = "Blazing fast 🚀 higher-level image proccessing library" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] +image = "0.24" +imageproc = "0.23" +rusttype = "0.9" +once_cell = "1" + diff --git a/crates/meow_image/README.md b/crates/meow_image/README.md new file mode 100644 index 0000000..c4c22d0 --- /dev/null +++ b/crates/meow_image/README.md @@ -0,0 +1,12 @@ +# Meow Image + +Blazing fast 🚀 higher-level image proccessing library + +# Building + +1. **Move your font to the root of the project.** + +2. Then run +```bash +cargo build --release +``` diff --git a/crates/meow_image/src/demotivate.rs b/crates/meow_image/src/demotivate.rs new file mode 100644 index 0000000..e702c93 --- /dev/null +++ b/crates/meow_image/src/demotivate.rs @@ -0,0 +1,189 @@ +use crate::text_width::get_text_width; +use image::{GenericImage, ImageBuffer, Rgb, RgbImage}; +use imageproc::drawing::draw_text_mut; +use once_cell::sync::Lazy; +use rusttype::{Font, Scale}; + +const WHITE: Rgb = Rgb([255, 255, 255]); +const BLACK: Rgb = Rgb([0, 0, 0]); + +static FONT_DATA: &[u8] = include_bytes!("../../../assets/XO_Thames_Nu.ttf"); + +static FONT: Lazy> = Lazy::new(|| Font::try_from_bytes(FONT_DATA).unwrap()); + +#[derive(Clone, Copy)] +struct Border { + pub top: u32, + pub left: u32, + pub bottom: u32, + pub right: u32, +} + +/// Makes a demotivator meme +pub fn demotivate(image: &RgbImage, top_text: &str, bottom_text: &str) -> RgbImage { + let (width, height) = image.dimensions(); + + // Calculate a border + let border_size = (if width > height { width } else { height }) / 8; + let border = Border { + top: border_size, + left: border_size, + bottom: border_size * 2, + right: border_size, + }; + + // Add a black border + let mut image_with_border = add_border(image, BLACK, border); + let (width, height) = image_with_border.dimensions(); + + // Calculate the padding and the line width + let padding = border_size / 10; + let line_width = padding / 3; + + // Add a white box next to the image + add_box(&mut image_with_border, WHITE, border, line_width, padding); + + // Calculate the scale and position of the top text + { + let scale = Scale::uniform(border_size as f32); + + let text_width = get_text_width(scale, &FONT, top_text); + + let x_text_position = (width - text_width) / 2; // center by width + let y_text_position = height - (border.bottom - padding); + + // Draw the top text + draw_text_mut( + &mut image_with_border, + WHITE, + x_text_position as i32, + y_text_position as i32, + scale, + &FONT, + top_text, + ); + } + + // Calculate the scale and position of the bottom text + { + let scale = Scale::uniform(border_size as f32 / 2f32); + + let text_width = get_text_width(scale, &FONT, bottom_text); + + let x_text_position = (width - text_width) / 2; // center by width + let y_text_position = height - (border.bottom - padding) / 2; + + // Draw the bottom text + draw_text_mut( + &mut image_with_border, + WHITE, + x_text_position as i32, + y_text_position as i32, + scale, + &FONT, + bottom_text, + ); + } + + image_with_border +} + +fn add_border( + image: &RgbImage, + color: Rgb, + Border { + top, + left, + bottom, + right, + }: Border, +) -> RgbImage { + // Get the dimensions of the image + let (width, height) = image.dimensions(); + + // Create a new image with a border + #[rustfmt::skip] + let mut out_image = ImageBuffer::from_fn( + width + left + right, + height + top + bottom, + |_, _| color + ); + + // Copy the original image into the center of the new image + out_image.copy_from(image, top, left).unwrap(); + + out_image +} + +fn add_box( + image: &mut RgbImage, + color: Rgb, + Border { + mut top, + mut left, + mut bottom, + mut right, + }: Border, + line_width: u32, + padding: u32, +) { + top -= padding; + left -= padding; + bottom -= padding; + right -= padding; + + // Get the dimensions of the image + let (width, height) = image.dimensions(); + + // Calculate the position and dimensions of the box + let x1 = left; + let y1 = top; + + let x2 = width - (right + 1); + let y2 = height - (bottom + 1); + + // Iterate over the pixels of the line and set the pixel values to color + for x in x1..=x2 { + for i in 0..line_width { + // top line + // +i to go bottom + image.put_pixel(x, y1 + i, color); + + // bottom line + // -i to go top + image.put_pixel(x, y2 - i, color); + } + } + + // Because we have already painted the corners + for y in (y1 + line_width)..=(y2 - line_width) { + for i in 0..line_width { + // left line + // +i to go right + image.put_pixel(x1 + i, y, color); + + // right line + // -i to go left + image.put_pixel(x2 - i, y, color); + } + } +} + +#[cfg(test)] +mod tests { + use super::*; + use image::io::Reader as ImageReader; + + #[test] + fn demotivate_test() { + let image = ImageReader::open("./patterns/test.jpg") + .unwrap() + .decode() + .unwrap() + .into_rgb8(); + + let demotivated_image = demotivate(&image, "He is crazy!", "RUN"); + + demotivated_image.save("dem.jpg").unwrap(); + } +} diff --git a/crates/meow_image/src/lib.rs b/crates/meow_image/src/lib.rs new file mode 100644 index 0000000..ec7e88b --- /dev/null +++ b/crates/meow_image/src/lib.rs @@ -0,0 +1,4 @@ +mod demotivate; +mod text_width; + +pub use demotivate::demotivate; diff --git a/crates/meow_image/src/text_width.rs b/crates/meow_image/src/text_width.rs new file mode 100644 index 0000000..23ea45a --- /dev/null +++ b/crates/meow_image/src/text_width.rs @@ -0,0 +1,17 @@ +use rusttype::{point, Font, Scale}; + +pub fn get_text_width(scale: Scale, font: &Font, text: &str) -> u32 { + let mut layout = font.layout(text, scale, point(0.0, 0.0)); + + let min = layout + .next() + .map(|g| g.pixel_bounding_box().unwrap().min.x) + .unwrap(); + + let max = layout + .last() + .map(|g| g.pixel_bounding_box().unwrap().max.x) + .unwrap(); + + (max - min) as u32 +} diff --git a/package-lock.json b/package-lock.json new file mode 100644 index 0000000..b083b6d --- /dev/null +++ b/package-lock.json @@ -0,0 +1,256 @@ +{ + "name": "node-demotivator-native", + "version": "1.0.0", + "lockfileVersion": 2, + "requires": true, + "packages": { + "": { + "name": "node-demotivator-native", + "version": "1.0.0", + "license": "MIT", + "devDependencies": { + "@napi-rs/cli": "^2.14.0", + "rimraf": "^3.0.2" + }, + "engines": { + "node": ">= 10" + } + }, + "node_modules/@napi-rs/cli": { + "version": "2.14.0", + "resolved": "https://registry.npmjs.org/@napi-rs/cli/-/cli-2.14.0.tgz", + "integrity": "sha512-hQW+gOTQ80nCoBAWA0hq49HM3QqyC7x879CdF/CEEFHeJNlHT8tgru8nbMQa6YqMP1XADfiudsYzy5V7TxBxCw==", + "dev": true, + "bin": { + "napi": "scripts/index.js" + }, + "engines": { + "node": ">= 10" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/Brooooooklyn" + } + }, + "node_modules/balanced-match": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", + "dev": true + }, + "node_modules/brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "dev": true, + "dependencies": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "node_modules/concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", + "dev": true + }, + "node_modules/fs.realpath": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==", + "dev": true + }, + "node_modules/glob": { + "version": "7.2.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", + "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", + "dev": true, + "dependencies": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.1.1", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + }, + "engines": { + "node": "*" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==", + "dev": true, + "dependencies": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "node_modules/inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true + }, + "node_modules/minimatch": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", + "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", + "dev": true, + "dependencies": { + "brace-expansion": "^1.1.7" + }, + "engines": { + "node": "*" + } + }, + "node_modules/once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==", + "dev": true, + "dependencies": { + "wrappy": "1" + } + }, + "node_modules/path-is-absolute": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", + "integrity": "sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/rimraf": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", + "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", + "dev": true, + "dependencies": { + "glob": "^7.1.3" + }, + "bin": { + "rimraf": "bin.js" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==", + "dev": true + } + }, + "dependencies": { + "@napi-rs/cli": { + "version": "2.14.0", + "resolved": "https://registry.npmjs.org/@napi-rs/cli/-/cli-2.14.0.tgz", + "integrity": "sha512-hQW+gOTQ80nCoBAWA0hq49HM3QqyC7x879CdF/CEEFHeJNlHT8tgru8nbMQa6YqMP1XADfiudsYzy5V7TxBxCw==", + "dev": true + }, + "balanced-match": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", + "dev": true + }, + "brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "dev": true, + "requires": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", + "dev": true + }, + "fs.realpath": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==", + "dev": true + }, + "glob": { + "version": "7.2.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", + "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", + "dev": true, + "requires": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.1.1", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } + }, + "inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==", + "dev": true, + "requires": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true + }, + "minimatch": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", + "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", + "dev": true, + "requires": { + "brace-expansion": "^1.1.7" + } + }, + "once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==", + "dev": true, + "requires": { + "wrappy": "1" + } + }, + "path-is-absolute": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", + "integrity": "sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==", + "dev": true + }, + "rimraf": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", + "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", + "dev": true, + "requires": { + "glob": "^7.1.3" + } + }, + "wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==", + "dev": true + } + } +} diff --git a/package.json b/package.json new file mode 100644 index 0000000..1bbc4b7 --- /dev/null +++ b/package.json @@ -0,0 +1,29 @@ +{ + "name": "node-demotivator-native", + "version": "1.0.0", + "description": "", + "main": "index.js", + "types": "index.d.ts", + "license": "MIT", + "scripts": { + "build": "napi build ./dist --cargo-cwd crates/bindings --platform --release --js ./dist/index.js", + "build:debug": "napi build ./dist --cargo-cwd crates/bindings --platform --js ./dist/index.js", + "clean": "rimraf ./dist && rimraf ./target" + }, + "napi": { + "name": "node-demotivator-native", + "defaults": true, + "triples": { + "additional": [ + "aarch64-unknown-linux-gnu" + ] + } + }, + "engines": { + "node": ">= 10" + }, + "devDependencies": { + "@napi-rs/cli": "^2.14.0", + "rimraf": "^3.0.2" + } +} \ No newline at end of file diff --git a/rustfmt.toml b/rustfmt.toml new file mode 100644 index 0000000..79f8a99 --- /dev/null +++ b/rustfmt.toml @@ -0,0 +1,2 @@ +edition = "2021" +tab_spaces = 4