Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .github/FUNDING.yml
100644 → 100755
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
# These are supported funding model platforms

github: [mster]
github: []
1 change: 1 addition & 0 deletions .gitignore
100644 → 100755
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
.DS_Store

node_modules/
dist/
example.js

.env
Expand Down
2 changes: 2 additions & 0 deletions .npmignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
example.ts
.prettier*
2 changes: 2 additions & 0 deletions .prettierignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
node_modules
.github
6 changes: 6 additions & 0 deletions .prettierrc.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
{
"trailingComma": "es5",
"tabWidth": 4,
"semi": false,
"singleQuote": true
}
3 changes: 0 additions & 3 deletions .travis.yml

This file was deleted.

14 changes: 7 additions & 7 deletions CONTRIBUTING.md
100644 → 100755
Original file line number Diff line number Diff line change
Expand Up @@ -12,9 +12,9 @@ Your mosh mode doesn't have to do anything specific -- if you think it's cool, w

Most of Datamosh's current modes overwrite existing Red/Green/Blue (RGB) pixel values with something random. If you get stuck or just need some inspiration, check out these examples.

- [Vana mode](https://github.com/mster/datamosh/blob/master/lib/modes/vana.js)
- [Schifty mode](https://github.com/mster/datamosh/blob/master/lib/modes/schifty.js)
- [Before and after images](https://github.com/mster/datamosh#example-images)
- [Vana mode](https://github.com/mster/datamosh/blob/master/lib/modes/vana.js)
- [Schifty mode](https://github.com/mster/datamosh/blob/master/lib/modes/schifty.js)
- [Before and after images](https://github.com/mster/datamosh#example-images)

Once you have a stub function and some cool name for it, you'll want to import it into Datamosh.

Expand All @@ -28,14 +28,14 @@ To import your mode, you have two options:
1. Fork datamosh and run `npm install` within the directory.
2. On your fork, create a new branch named `username/work-description`, where `username` is your GitHub username and `work-description` is a short description for your contribution.

For example: `mster/new-mode`
For example: `mster/new-mode`

3. Commit your work to the branch you created.
4. When you're ready for review or to submit your contribution, double check a few things.

- ✓ First, make sure your fork is up to date. If your fork is out of date, you will need to rebase.
- ✓ First, make sure your fork is up to date. If your fork is out of date, you will need to rebase.

- ✓ Next, assure that your code pases `npm test`.
- ✓ Next, assure that your code pases `npm test`.

5. If your contribution is more than a single commit, squash all commits into one.
6. Open a pull request to `mster:master`.
Expand All @@ -57,7 +57,7 @@ To test if your code passes, run the test command:

As of v1.0.0, tests consist of:

- linting using Prettier
- linting using Prettier

## Need Help

Expand Down
Empty file modified LICENSE
100644 → 100755
Empty file.
32 changes: 16 additions & 16 deletions README.md
100644 → 100755
Original file line number Diff line number Diff line change
Expand Up @@ -13,17 +13,17 @@ $ npm install datamosh
# Usage

```js
const mosh = require("datamosh");
const mosh = require('datamosh')

let imgBuff = await readFile("/full/path/to/image.png");
let imgBuff = await readFile('/full/path/to/image.png')

let moshedBuff = await mosh(imgBuff, "vaporwave");
let moshedBuff = await mosh(imgBuff, 'vaporwave')
```

Reading/Writing the moshed image

```js
mosh("~/image.png", null, "~/moshed_image.png");
mosh('~/image.png', null, '~/moshed_image.png')

// because mode is null, a random mode will be chosen
```
Expand All @@ -32,16 +32,16 @@ Moshing a buffer with callbacks

```js
const cb = (err, data) => {
if (!err) writeFile("/path/to/out.gif", data);
};
if (!err) writeFile('/path/to/out.gif', data)
}

mosh(imgBuff, "vana", cb);
mosh(imgBuff, 'vana', cb)
```

Using multiple modes on a single image, applied with respect to order.

```js
let moshedBuff = await mosh(imgBuff, ["fatcat", "vaporwave", "walter"]);
let moshedBuff = await mosh(imgBuff, ['fatcat', 'vaporwave', 'walter'])

// ['vana', null, null] is also valid => ['vana', random, random]
```
Expand All @@ -52,9 +52,9 @@ let moshedBuff = await mosh(imgBuff, ["fatcat", "vaporwave", "walter"]);

Takes input `source` Buffer/Path, returns an encoded Buffer with the applied modes.

- `mode`, the mosh mode to apply to the source image. Multiple modes may be passed using an array of modes. Any `null` values are replaced with a random mode.
- `cb (err, data)`, when using callbacks.
- `writePath`, the path to write the moshed image to.
- `mode`, the mosh mode to apply to the source image. Multiple modes may be passed using an array of modes. Any `null` values are replaced with a random mode.
- `cb (err, data)`, when using callbacks.
- `writePath`, the path to write the moshed image to.

Paths may use the tilde (~) character. Datamosh validates read and write paths, replacing tilde with the path to the home directory.

Expand All @@ -69,15 +69,15 @@ Datamosh allows you to set custom moshing modes. As of `v1.1.0`, this may be aco
For mosh function starter code, see the included template file located [here](https://github.com/mster/datamosh/blob/master/lib/modes/template).

```js
const datamosh = require("datamosh");
const datamosh = require('datamosh')

function newMode(data, width, height) {
// your cool code goes here!
// your cool code goes here!

return data;
return data
}

datamosh.MODES.newMode = newMode;
datamosh.MODES.newMode = newMode
```

## Example Images
Expand All @@ -96,4 +96,4 @@ Vaporwave was created by user [@tlaskey](https://github.com/tlaskey)

Check out this list of awesome apps that use `datamosh`!

- [JanMichaelBot](https://github.com/tlaskey/JanMichaelBot) by user [@Tlaskey](https://github.com/tlaskey)
- [JanMichaelBot](https://github.com/tlaskey/JanMichaelBot) by user [@Tlaskey](https://github.com/tlaskey)
9 changes: 9 additions & 0 deletions example.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
import { readFile } from 'fs/promises'
import datamosh from '.'

const sampleImagePath: string = './tests/fixtures/rgb.png'

;(async () => {
const src = await readFile(sampleImagePath)
const result = await datamosh({ src })
})()
2 changes: 1 addition & 1 deletion index.js
100644 → 100755
Original file line number Diff line number Diff line change
@@ -1 +1 @@
module.exports = require("./lib/mosh");
module.exports = require('./lib/mosh')
6 changes: 6 additions & 0 deletions jest.config.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
{
"bail": 1,
"verbose": true,
"preset": "ts-jest",
"testMatch": ["**/tests/**/*.test.ts"]
}
52 changes: 52 additions & 0 deletions lib/datamosh.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
'use strict'

import * as encode from 'image-encode'
import * as decode from 'image-decode'
import { fromBuffer } from 'file-type'

import supportedModes from './modes'

type MoshArguments = {
src: Buffer
mode?: string
modes?: Array<string>
}

async function datamosh({ src, mode = 'random', modes }: MoshArguments) {
// validate file-type
const fileTypeMeta: any = await fromBuffer(src)
if (
!fileTypeMeta ||
!['jpg', 'jpeg', 'png', 'gif', 'tif', 'bmp'].includes(fileTypeMeta?.ext)
)
throwError('Invalid source buffer.')

// decode image
const decodedSourceImg: any = decode(src)

// apply mode(s)
let moshedImg = Buffer.from(decodedSourceImg.data)
if (mode && supportedModes[mode])
moshedImg = supportedModes[mode](moshedImg)
if (
modes &&
modes.filter((m) => supportedModes.includes(m)).length === modes.length
) {
modes.forEach((mode) => (moshedImg = supportedModes[mode](moshedImg)))
}

// encode image
const encodedMoshedImg = encode(
moshedImg,
[decodedSourceImg.width, decodedSourceImg.height],
fileTypeMeta.ext
)
return encodedMoshedImg
}

function throwError(msg: string) {
const error: Error = new Error(msg)
throw error
}

export default datamosh
26 changes: 13 additions & 13 deletions lib/modes/abna.js
100644 → 100755
Original file line number Diff line number Diff line change
@@ -1,20 +1,20 @@
const normalizeAlpha = x => x - (x % 4) + 3
const normalizeAlpha = (x) => x - (x % 4) + 3
const randInt = (min, max) => (min + Math.random() * (max - min)) | 0
const abna = (a, b) => (a << b) | (b << a)

module.exports = function (data) {
const ret = []
const sqLen = (Math.sqrt(data.length) * (5 + Math.random() * 15)) | 0
const firstInflexion = normalizeAlpha(randInt(sqLen, data.length / 10))
const ret = []
const sqLen = (Math.sqrt(data.length) * (5 + Math.random() * 15)) | 0
const firstInflexion = normalizeAlpha(randInt(sqLen, data.length / 10))

for (let i = 0; i < data.length - 1; i++) {
const offset = i % 4
if (i === firstInflexion) ret.reverse()
for (let i = 0; i < data.length - 1; i++) {
const offset = i % 4
if (i === firstInflexion) ret.reverse()

if (i % sqLen === 0) i += 4
if (offset === 3) ret.push(data[i])
else ret.push(abna(data[i], offset === 2 ? data[i + 2] : data[i + 1]))
}
if (i % sqLen === 0) i += 4
if (offset === 3) ret.push(data[i])
else ret.push(abna(data[i], offset === 2 ? data[i + 2] : data[i + 1]))
}

return ret
}
return ret
}
18 changes: 9 additions & 9 deletions lib/modes/blurbobb.js
100644 → 100755
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
"use strict";
'use strict'

module.exports = function (data) {
let counter = 0;
for (let i = 0; i < data.length; i++) {
if (counter < 64) data[i] = Math.random() * 255;
let counter = 0
for (let i = 0; i < data.length; i++) {
if (counter < 64) data[i] = Math.random() * 255

counter++;
if (counter > 128) counter = Math.random() * 128;
}
counter++
if (counter > 128) counter = Math.random() * 128
}

return data;
};
return data
}
44 changes: 22 additions & 22 deletions lib/modes/castles.js
100644 → 100755
Original file line number Diff line number Diff line change
@@ -1,27 +1,27 @@
"use strict";
'use strict'

module.exports = function (data) {
const red = new Array(data.length / 4),
green = new Array(data.length / 4),
blue = new Array(data.length / 4),
a = new Array(data.length / 4);
const red = new Array(data.length / 4),
green = new Array(data.length / 4),
blue = new Array(data.length / 4),
a = new Array(data.length / 4)

let high = 165,
low = 80;
for (let i = 0; i < data.length / 4; i++) {
if (data[i] < high && data[i] > low) red[i] = data[i];
if (data[i + 1] < high && data[i + 1] > low) green[i] = data[i + 1];
if (data[i + 2] < high && data[i + 2] > low) blue[i] = data[i + 2];
a[i] = data[i + 3];
}
let high = 165,
low = 80
for (let i = 0; i < data.length / 4; i++) {
if (data[i] < high && data[i] > low) red[i] = data[i]
if (data[i + 1] < high && data[i + 1] > low) green[i] = data[i + 1]
if (data[i + 2] < high && data[i + 2] > low) blue[i] = data[i + 2]
a[i] = data[i + 3]
}

const ret = [];
for (let i = 0; i < red.length; i++) {
ret.push(red[i]);
ret.push(green[i]);
ret.push(blue[i]);
ret.push(a[i]);
}
const ret = []
for (let i = 0; i < red.length; i++) {
ret.push(red[i])
ret.push(green[i])
ret.push(blue[i])
ret.push(a[i])
}

return ret;
};
return ret
}
Loading