Skip to content

Instantly share code, notes, and snippets.

@Flashwalker
Created November 23, 2022 20:38
Show Gist options
  • Save Flashwalker/754e5a140b25b98001a994ec50de099c to your computer and use it in GitHub Desktop.
Save Flashwalker/754e5a140b25b98001a994ec50de099c to your computer and use it in GitHub Desktop.
Convert image to svg (wrap image with svg) (embed image to svg) (jpg, png, gif... etc)
#!/bin/bash
# Wrap image with svg and output the svg file
#### Options
svgwidth=''
svgheight=''
imgwidth=''
imgheight=''
############
# Reading passed options from stdin
while getopts "w:h:W:H:" OPTION
do
case $OPTION in
w)
imgwidth="$OPTARG"
;;
h)
imgheight="$OPTARG"
;;
W)
svgwidth="$OPTARG"
;;
H)
svgheight="$OPTARG"
;;
v)
verbose=1
;;
\?)
echo -e '\e[37;34m'"\e[1m[notice]\e[0m" "Invalid options" >&2
exit 1
;;
:)
echo -e '\e[37;34m'"\e[1m[notice]\e[0m" "Option -$OPTARG requires an argument" >&2
exit 1
;;
esac
done
shift $(($OPTIND -1))
exec="$(basename "$0")"; [[ "$exec" ]] || exec="${0##*/}"
printhelp() {
cat <<EOF
$exec [-w IMAGE-WIDTH] [-h IMAGE-HEIGHT] [-W SVG-WIDTH] [-H SVG-HEIGHT] FILE.JPG
-w <int> Specify image width in pixels
-h <int> Specify image height in pixels
-W <int> Specify svg width in pixels
-H <int> Specify svg width in pixels
e.g.:
$exec file.jpg
Width and height will be used from image if not set
$exec -w 1024 -h 768 file.jpg
This will produce file.svg, svg and image size will be: 1024px * 768px.
$exec -W 1024 -H 768 file.jpg
This will produce file.svg, svg will be: 1024px * 768px.
Image size will be taken from the image
EOF
}
if [[ "$#" -lt "1" ]]; then
printhelp
exit 1
fi
# Function
function b2s() {
# exit if no such file
if ! [[ -f "$1" ]]; then
echo -e '\e[37;31m'"\e[1m[error]\e[0m" "There is no such file: '$1'" >&2
exit 1
fi
# get size of image
imgpixelsize="$(identify -format '%w %h' "$1")"
# get mime type of image
mime="$(file -i "$1" | grep -m1 -o -P ':\s(.*);' | awk -F ": " '{print $2}')"
# get quantities:
# if no imgwidth was specified set it to width of image
iwidth="${imgwidth:-${imgpixelsize%% *}}"
# if no imgheight was specified set it to height of image
iheight="${imgheight:-${imgpixelsize#* }}"
# if no svgwidth was specified set it to width of image
swidth="${svgwidth:-$iwidth}"
# if no svgheight was specified set it to height of image
sheight="${svgheight:-$iheight}"
# test if we got integers
re='^[0-9]+$'
for int in $iwidth $iheight $swidth $sheight; do
if ! [[ $int =~ $re ]] ; then
echo '\e[37;31m'"\e[1m[error]\e[0m" "'${int}' Not a number" >&2
exit 1
fi
done
# get X offset to center the image horizontally
[[ $swidth -gt $iwidth ]] && xoffset=$((($swidth-$iwidth)/2)) || xoffset=0
# Now wrap image with svg and output to svg file:
{
# print svg
cat <<EOF
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
width="$swidth"
height="$sheight"
viewBox="0 0 $swidth $sheight"
version="1.1"
id="svgimg"
xml:space="preserve"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns="http://www.w3.org/2000/svg"
xmlns:svg="http://www.w3.org/2000/svg"><defs
id="defs2" /><g
id="layer1"
transform="translate($xoffset)"><image
width="$iwidth"
height="$iheight"
preserveAspectRatio="yes"
EOF
# print base64 encoded image
echo " xlink:href=\"data:${mime%;};base64,$(base64 "${1}")"
# continue print svg
echo "\""
cat <<EOF
id="image"
x="0"
y="0"
style="image-rendering:optimizeQuality" /></g></svg>
EOF
}>"${1%.*}.svg"
}
# Run function
for i in "${@}"; do
b2s "$i"
done
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment