Giter VIP home page Giter VIP logo

excalidraw-cli's Introduction

excalidraw-cli

npm version Bundlephobia badge build

Experimental Excalidraw CLI tool.

Parses Excalidraw JSON schemas (*.excalidraw) into PNGs (*.png).

This project is a follow-up to excalidraw#1261 and strives to provide a CLI for excalidraw.

demo

Demo ⤴️

Install

npm install -g @tommywalkie/excalidraw-cli

Alpine

If using Alpine (e.g. for Docker stuff), install the following packages.

FROM node:alpine
RUN apk update
RUN apk add --no-cache python g++ build-base cairo-dev jpeg-dev pango-dev \
    musl-dev giflib-dev pixman-dev pangomm-dev libjpeg-turbo-dev freetype-dev

Usage

$ excalidraw-cli --help
Parses Excalidraw JSON schemas into PNGs

USAGE
  $ excalidraw-cli [INPUT] [OUTPUT]

ARGUMENTS
  INPUT   [default: {cwd}] Excalidraw file path / directory path
  OUTPUT  [default: {cwd}] Output PNG file path / directory path

OPTIONS
  -h, --help     show CLI help
  -q, --quiet    disable console outputs
  -v, --version  show CLI version

Docker

For convenience we have also a Docker image that includes all dependencies out of the box.

Build

To build the Docker image run following command.

Use

To use the docker image in a convenient way you can add following function to your .bashrc or .zshrc.

function excalidraw-cli {
  docker run --rm -it -v $PWD:/data excalidraw-cli $@
}

Then simply reload your terminal to have this function available.

$ excalidraw-cli drawings/my-drawing.excalidraw .
✔ drawings/my-drawing.excalidraw => drawings/my-drawing.png

How it works

Currently, excalidraw NPM package only exports a React component. excalidraw-cli uses node-canvas at its core, this allows to generate canvas without relying on the window context, and uses a home-made renderer which tries to mimic Excalidraw's as much as possible, using Rough.js API primarily.

Hopefully, excalidraw-cli will directly use Excalidraw renderer methods for consistent results, once Excalidraw provides some Node-compatible API.

See the related issue thread excalidraw#1780.

Contributing

Note: Most of the codebase is currently in ES2017, it will soon be converted to TypeScript for educational purposes, but also for easier integration with Excalidraw.

Install dependencies with npm or yarn.

npm install

Export fonts, transpile TypeScript / ES2017 source into CommonJS for production.

npm run prepack

Test the CLI with the transpiled source code.

node ./bin/run           # Run with Node
npm run excalidraw-cli   # Run with NPM script

Prepack and launch Jest tests.

npm run test

You can check requested / planned / work-in-progress features in Projects.

License

MIT

excalidraw-cli's People

Contributors

dependabot[bot] avatar lucasavila00 avatar marcofranssen avatar tommywalkie avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar

excalidraw-cli's Issues

Undeterministic Output

Describe the bug

I have some .excalidraw files in a github project to document something.

I use the binary like this: excalidraw-cli docs/readme docs/readme and it goes through all the files in the folder and outputs them as expected.

However every time I run this CLI it will give me different output files even though I haven't changed input files (I haven't been able to SEE 👁️ the differences but git will mark them as changed).

It's just annoying (as in not breaking my flow) because if I change one file I must submit a commit where it seems all files changed.

Expected behavior

The same input .excalidraw file should produce the exact same PNG, don't matter where/when I run it.

Excalidraw input file

This is a sample project where I created a PR where I changed just 1 of 2 excalidraw files.
After building the project with excalidraw-cli and pushing the change the PR has changes to the 2 PNG files.

https://github.com/lucasavila00/excalidraw-non-deterministic/pull/1/files

Environment (please complete the following information):

  • OS version: Ubuntu 20.04 LTS
  • Node version: v12.18.0

Ubuntu 20.04 - Node v12.18.0 - Text not rendering

It will produce results with boxes and arrows but no text.
Changing font won't make it work.
File is valid and renders on excalidraw.com

My system is:

DISTRIB_ID=Ubuntu
DISTRIB_RELEASE=20.04
DISTRIB_CODENAME=focal
DISTRIB_DESCRIPTION="Ubuntu 20.04 LTS"
NAME="Ubuntu"
VERSION="20.04 LTS (Focal Fossa)"
ID=ubuntu
ID_LIKE=debian
PRETTY_NAME="Ubuntu 20.04 LTS"
VERSION_ID="20.04"
HOME_URL="https://www.ubuntu.com/"
SUPPORT_URL="https://help.ubuntu.com/"
BUG_REPORT_URL="https://bugs.launchpad.net/ubuntu/"
PRIVACY_POLICY_URL="https://www.ubuntu.com/legal/terms-and-policies/privacy-policy"
VERSION_CODENAME=focal
UBUNTU_CODENAME=focal

Node: v12.18.0

NPM: 6.14.4

I'd like to help fix this, I might submit a PR if I can fix it.
I'd appreciate a a hint pointing where in the source code text rendering is done or any tips at all.

Thanks for the awesome job doing this 👍

Dark mode

Is the light/dark mode toggle available? Also, a no background option?

Can't run "excalidraw-cli" npm script on Linux

If you clone the repository and build it with "prepack && postpack" then try to run with "excalidraw-cli" then it won't run because of permission issues.

Run sudo chmod -R 777 bin/run to fix it

I really don't know how to make it automatic :/
I think this can be closed too as it's something simple but it's nice to have it here so that users find it if they need.

Search terms:
$ ./bin/run
/bin/sh: 1: ./bin/run: Permission denied

Embed scene support

Excalidraw "Save as image" has an "embed scene" toggle that helps to restore the scene in case the png is loaded.

image

I don't have any context on how both the code bases work but it seems excalidraw is doing it here. Would it make sense to port it here as well?

Parsing and saving the outputs into a folder that doesn't exist

Contextually, I ran into an issue where I wanted to parse some Excalidraw files from a certain place somewhere/ and then save the outputs in a directory, let's say somewhere/else/.

# Save outputs in a directory that doesn't exist
excalidraw-cli somewhere/ somewhere/else/

Currently if the directory else/ doesn't exist, excalidraw-cli considers the parameter value as a file name, so it will save the output into a single file named somewhere/else.png, this actually makes sense when aware about it, but may confuse unaware people for hours.

I'm considering adding a warning in case the INPUT parameter value is about a directory, but the OUTPUT parameter value is a directory that doesn't exist. Or maybe throw an Error.

Alpine Linux support ?

From node-canvas ' Installation section :

By default, binaries for macOS, Linux and Windows will be downloaded. If you want to build from source, use `npm install --build-from-source and see the Compiling section below.

This means excalidraw-cli (and node-canvas) will work out of the box for macOS, Ubuntu and Windows.

However, Alpine Docker images will require some modules in order to make the Cairo backend dependency work.

Support Nested Folders with .excalidraw files

What I want:

Take this repository as example: https://github.com/lucasavila00/excalidraw-cli-nested

It has a docs folder with another nested folder.
In the root docs folder I have .excalidraw files and in the nested folder I have more .excalidraw files. : https://github.com/lucasavila00/excalidraw-cli-nested/tree/master/docs

I'd like if this command worked https://github.com/lucasavila00/excalidraw-cli-nested/blob/master/package.json#L10 just like this.

This CLI should be able to traverse all nested folders and export the content they have.

Why I want it:

I want to create a generic, OSS, github action that makes sure you "compiled" the .excalidraw files before submitting a PR or that PR will fail.

Since now we have deterministic output we can just recompile everything and look for git diffs. If there is any diff then this PR will fail in CI and a warning telling the user that he forgot to compile the .excalidraw files will be shown.

I'd like to have 1 configuration for this action: a folder (possibily nested) where you store all you .excalidraw files (or possibly no configuration and this CLI traverses the whole repository file tree?)

Currently this generic, OSS action is impossible since I have to know all folders that have .excalidraw files and configure them...

Scale canvas dimensions with rotated elements

Short description :
Rotated elements can exceed canvas dimensions.

Longer description :
Currently, the canvas dimensions are calculated, using the following values :

  • X of the leftmost element
  • Y of the uppermost element
  • X + element.width of the rightmost element
  • Y + element.height of the bottommost element

It is certainly not perfect but it renders center-cropped diagrams fine, but it has one caveat : not taking shape circumference and θ (theta) into account.

Here is a good illustration of the encountered problem.

Temporary workaround : By default, generated canvas have a 50px margin, this will be removed or settable in future.

A fix is under development, allowing the renderer to take shape circumference and θ (theta) into account when defining canvas dimensions.

The embedded image is not rendered

I insert png image to excalidraw file and save it. Converted by excalidraw-cli image is empty.

If I export an image from the editor, then the file is not empty.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.