Last active
June 7, 2020 06:38
-
-
Save MarkKoz/a9ef1b025d4d8dea0a10c98c6e03cab5 to your computer and use it in GitHub Desktop.
Convert SVGs into PNGs using Inkscape
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env bash | |
# | |
# Convert SVGs into PNGs using Inkscape. | |
# | |
# PNGs are saved to the same location as their corresponding SVG files. | |
# If sizes are specified, they are appended to the names of the PNGs. | |
# | |
# The env var INKSCAPE_BIN can be set to configure the path to Inkscape. | |
# | |
# Usage: ./export_svgs.sh <input_path> [size [size]...] | |
# | |
# input_path can be a file or a directory. | |
# | |
# If a size isn't specified, Inkscape will just do its default behaviour: | |
# ./export_svgs.sh image.svg | |
# | |
# A size can be specified as a single integer, which will be used for width | |
# and height: | |
# ./export_svgs.sh image.svg 900 | |
# | |
# A size can also be specified as two integers joined by an 'x' character. | |
# The left integer is the width and the right is the height: | |
# ./export_svgs.sh image.svg 300x500 | |
# | |
# Multiple sizes can be specified: | |
# ./export_svgs.sh image.svg 300x500 900 600x400 875 | |
set -euo pipefail | |
shopt -s inherit_errexit | |
export_svg() { | |
local input_file="${1:?"export_svg: argument 1 'input_file' is unset"}" | |
local size="${2}" | |
local svg_name="${input_file%.*}" | |
local args=() | |
local size_suffix="" | |
local size_message="default size" | |
# Parse the size. | |
if [[ "${size}" ]]; then | |
# Split the size by an "x" character | |
readarray -tdx dimensions < <(printf '%s' "${size}") | |
# Check if there was a split. | |
if [[ "${#dimensions[@]}" = 1 ]]; then | |
# There's no split; use same value for width and height. | |
size_message="${size}x${size}" | |
size_suffix="_${size}" | |
args=(-w "${size}" -h "${size}") | |
else | |
# There is a split; left value is width and right is height. | |
size_message="${size}" | |
size_suffix="_${dimensions[0]}_${dimensions[1]}" | |
args=(-w "${dimensions[0]}" -h "${dimensions[1]}") | |
fi | |
fi | |
args+=(-o "${svg_name}${size_suffix}.png" "${input_file}") | |
printf '%s\n' "Exporting ${svg_name} at ${size_message}..." | |
if ! "${INKSCAPE_BIN:-"inkscape"}" "${args[@]}"; then | |
printf '%s\n' "Failed to export ${svg_name} at ${size_message}" >&2 | |
return 1 | |
fi | |
} | |
export_svgs() { | |
local input_files | |
local sizes=("${@:2}") | |
local argstr="" | |
local arg_n=2 | |
# Check if argument 1 is a file or directory. | |
if [[ -d "$1" ]]; then | |
# Its a directory; get all SVG files in it. | |
input_files=("$1"/*.svg) | |
elif [[ -f "$1" ]]; then | |
input_files=("$1") | |
else | |
echo "Argument 1 is not an existing file or directory." >&2 | |
return 1 | |
fi | |
# Create a single string of arguments for all calls. | |
# xargs will split this string into arguments for each call. | |
for i in "${!input_files[@]}"; do | |
# Check if any sizes were specified. | |
if (( "${#sizes[@]}" )); then | |
# Add args for each size. | |
for size_i in "${!sizes[@]}"; do | |
argstr="${argstr} ${input_files[$i]} ${sizes[$size_i]}" | |
done | |
else | |
# No sizes were specified. | |
argstr="${argstr} ${input_files[$i]}" | |
arg_n=1 | |
fi | |
done | |
# Export all SVGs in all sizes in parallel, up to 8 simultaneous calls. | |
export -f export_svg | |
export INKSCAPE_BIN | |
printf "%s" "${argstr}" | xargs -n "${arg_n}" -P 8 bash -c 'export_svg "${@}"' _ | |
} | |
export_svgs "$@" |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment