diff options
Diffstat (limited to 'prepare')
-rwxr-xr-x | prepare | 483 |
1 files changed, 483 insertions, 0 deletions
@@ -0,0 +1,483 @@ +#!/bin/sh -e + +#=============================================================== +# Filename : prepare +# Purpose : Prepare wallpapers for Adélie desktop environments. +# Authors : Zach van Rijn <me@zv.io> +# License : Apache 2.0 +# Revision : 20231202 +#=============================================================== + +#=============================================================== +# README +#=============================================================== + +## +# This script transforms source images, including Adélie logos, +# into a set of wallpapers suitable for packaging. +# +# There are two distinct output products: +# +# (1) a "core" or "slim" bundle, containing a lightweight set of +# default wallpaper(s) and/or branding; and +# +# (2) a "full" bundle containing all available wallpapers, which +# is suitable for use when disk space isn't a major concern. +# +# +# +# requirements +# ------------ +# +# * imagemagick +# +# +# usage +# ----- +# +# To process all source images and generate a tarball for upload +# to 'distfiles', simply run the following command: +# +# $ ./prepare +# +# Any tarball of the same name will be silently overwritten. +# + + +#--------------------------------------------------------------- +# configuration: source image input +#--------------------------------------------------------------- + +## +# Distfiles mirror. +# +HOST="https://distfiles.adelielinux.org"; + + +## +# Adélie brand asset bundle version. +# +# This corresponds to the commit of 'adelie/site-ng' from which +# the brand assets were generated. A tarball matching this hash +# must exist in the '<HOST>/source/site-ng-images/' directory. +# +# See https://git.adelielinux.org/adelie/site-ng for details. +# +HASH=ca57e2bd46f11bf2efdebbca8c7813235744fd5f; + + +## +# Name of the containing directory and tarball on distfiles. +# +NAME="site-ng-images"; + + +#--------------------------------------------------------------- +# configuration: processed image output +#--------------------------------------------------------------- + +## +# Name of output directory. Please ensure it is in '.gitignore'. +# +KEEP="output"; + + +## +# Choose an output file type. +# +TYPE="jpg"; + + +## +# Table of aspect ratios to generate wallpapers for. +# +# Format: RATIO SCALE [SCALE ...] +# +# Scale is distributed, e.g.: +# +# "4:3 640" --> (640*4)x(640*3) = 2560x1920 +# +# Note that many popular aspect ratios are approximate. We are +# only concerned with getting to the right ballpark. +# +# Table rows MUST BE SORTED FROM GREATEST TO LEAST. +# +MAKE=$(grep -v ^# <<EOF +4:3 640 400 256 200 +5:4 480 256 +3:2 854 +16:10 160 120 105 80 +16:9 240 160 120 90 +21:9 122 +EOF +); + + +#--------------------------------------------------------------- +# internal: meta +#--------------------------------------------------------------- + +HERE="$(dirname $(readlink -f ${0}))"; +cd "${HERE}"; + + +## +# Check for required tools. +# +for k in curl composite convert magick; do + if ! command -v ${k} 2>&1 >/dev/null; then + printf "E: required utility '%s' not found!\n" "${k}"; + exit 1; + fi +done + + +## +# Tag first, then generate release the tarball. Sanity checks do +# not prevent someone from being stupid, but they can avoid some +# common errors. We want to reduce surprises/ensure consistency. +# +VTAG=$(git describe --abbrev=0 2>/dev/null || true); +if test -z "${VTAG}"; then + printf "E: you need to tag at least one commit!\n"; + exit 1; +fi +if test $(git rev-list ${VTAG}..HEAD | wc -l) -gt 0; then + printf "E: you need to be checked out at a tag!\n"; + exit 1; +fi +if test $(git ls-remote --tags origin ${VTAG} | wc -l) -eq 0; then + printf "E: tag '%s' does not exist on origin!\n" "${VTAG}"; + exit 1; +fi + + +## +# Name of build directory. Please ensure it is in '.gitignore'. +# +TEMP="build"; + + +## +# Name of source directory. +# +IMGS="src"; + + +## +# Ensure that no images have conflicting names. +# +# FIXME: factor out 'background lockscreen' here and elsewhere. +# +for k in background lockscreen; do + if test -d "${IMGS}"/${k}; then + printf "E: not allowed to name image '%s'!\n" "${k}"; + exit 1; + fi +done + + +#--------------------------------------------------------------- +# internal: support routines +#--------------------------------------------------------------- + +## +# size_only DIR RATIO SCALE [SCALE ...] +# +size_only () +{ + data="${1}"; shift; + size="${1}"; shift; + from="${1}"; # NO SHIFT + list="${@}"; + + ## + # FIXME: assumes 'a:b' where 'a' and 'b' are integers. This + # should check that this actually holds. + # + case "${size}" in + *:*) + ;; + *) + printf "E: invalid aspect ratio '%s'!\n" "${size}"; + exit 1; + ;; + esac + + ## + # Generated images have known sizes that do not change. + # + from_x=$((${from}*${size%:*})); + from_y=$((${from}*${size#*:})); + + printf "Processing %s...\n" "${size}"; + for k in ${list}; do + x=$((${k}*${size%:*})); + y=$((${k}*${size#*:})); + printf " * Generating %4sx%4s (scale: %s)\n" "${x}" "${y}" "${k}"; + find "${data}" -mindepth 1 -maxdepth 1 -type d | sort | while read image; do + name=$(printf "%s\n" "${image}" | cut -d/ -f3); # sloppy, sorry + case "${name}" in + background|lockscreen) + type="png"; # override for quality + ;; + *) + type="${TYPE}"; + ;; + esac + printf " - '%s'\n" "${name}"; + mkdir -p "${KEEP}"/${name}; + convert "${image}/${from_x}x${from_y}.png" -resize ${x}x${y}^ "${KEEP}"/${name}/${x}x${y}.${type}; + done + done +} + +#--------------------------------------------------------------- +# internal: core +#--------------------------------------------------------------- + +mkdir -p "${HERE}/${TEMP}"; +mkdir -p "${HERE}/${KEEP}"; + +## +# Fetch the specified brand asset bundle from distfiles. +# +# TODO: error checking, return codes etc. +# +( + cd "${TEMP}"; + + if ! test -e ${NAME}-${HASH}.tar.gz; then + curl -O "${HOST}"/source/${NAME}/${NAME}-${HASH}.tar.gz; + fi + + tar -xf ${NAME}-${HASH}.tar.gz; +) + + +#--------------------------------------------------------------- +# internal: generate minimal wallpapers +#--------------------------------------------------------------- + +## +# The default "core" or "slim" wallpaper is made on the fly and +# not provided as a rasterized image from the start. +# + +## +# make_fake GRADIENT_FROM GRADIENT_TO XxY TEMPLATE OUTPUT +# +make_fake () +{ + size="${1}"; shift; # geometry + hexa="${1}"; shift; # gradient from + hexb="${1}"; shift; # gradient to + temp="${1}"; shift; # template + name="${1}"; shift; # output filename + + printf "Generating %5s ('%s')...\n" "${size}" "${name}"; + magick \ + -define gradient:angle=65 \ + -size ${size} \ + gradient:"${hexa}"-"${hexb}" \ + "${name}" \ + ; + + # FIXME: this is literal magic? + composite \ + -compose atop \ + -gravity southwest \ + -background none \ + "${TEMP}"/polyguin.svg \ + "${name}" \ + "${name}" \ + ; + composite \ + -compose atop \ + -gravity southeast \ + -background none \ + "${TEMP}"/gen_polylogo_template_${temp}.png \ + -geometry +50+20 \ + "${name}" \ + "${name}" \ + ; +} + + +## +# Generate starting templates. That is, generate the largest one +# possible for each aspect ratio. +# +printf "%s\n" "${MAKE}" | while read ratio scale _; do + # compute largest required + x=$((${scale}*${ratio%:*})); + y=$((${scale}*${ratio#*:})); + + ############################################################ + # FIXME! + # FOR SOME REASON, CHANGING '#EEEEEF' TO '#EEEEEE' OR FROM + # '#303031' TO '#303030' WILL DISCARD COLOR INFORMATION OF + # THE COMPOSITED SVG. WTF. WE LEVERAGE THIS THOUGH... + ############################################################ + + # background (we want the buggy black/white version) + mkdir -p "${TEMP}"/generated/background; + make_fake ${x}x${y} "#bbbbbb" "#eeeeee" black_x200 "${TEMP}"/generated/background/${x}x${y}.png; + #make_fake ${x}x${y} "#bbbbbb" "#eeeeef" black_x200 "${TEMP}"/generated/background/${x}x${y}.png; + + # lockscreen (we want the color version) + mkdir -p "${TEMP}"/generated/lockscreen; + #make_fake ${x}x${y} "#151515" "#303030" white_x200 "${TEMP}"/generated/lockscreen/${x}x${y}.png; + make_fake ${x}x${y} "#151515" "#303031" white_x200 "${TEMP}"/generated/lockscreen/${x}x${y}.png; +done + + +#--------------------------------------------------------------- +# internal: scale all wallpapers +#--------------------------------------------------------------- + +## +# To generate "real" wallpapers, we simply resize them. This can +# be be improved significantly, but that is a future problem. +# +make_real () +{ + size="${1}"; shift; # geometry + temp="${1}"; shift; # template + name="${1}"; shift; # output filename + + # TODO: add filename extension checker? + + printf "Generating %5s ('%s')...\n" "${size}" "${name}"; + convert "${file}" -resize ${size}^ "${name}"; +} + + +## +# Source images may not all be consistent in their aspect ratios +# or dimensions. We will scale (crop) source images to match the +# sizes of the generated core templates. +# +printf "%s\n" "${MAKE}" | while read ratio scale _; do + # compute largest required + x=$((${scale}*${ratio%:*})); + y=$((${scale}*${ratio#*:})); + + find "${IMGS}" -mindepth 1 -maxdepth 1 -type d | sort | while read k; do + file="$(find ${k} -type f -name 'image.*')"; + + if test $(printf "%s\n" "${file}" | wc -l) -ne 1; then + printf "E: not exactly one image at '%s'!\n" "${k}"; + exit 1; + fi + + # FIXME: is it OK to hard-code '.png' here? + name=$(printf "%s\n" "${file}" | cut -d/ -f2); # sloppy, sorry + mkdir -p "${TEMP}"/generated/${name}; + make_real ${x}x${y} "${file}" "${TEMP}"/generated/${name}/${x}x${y}.png; + done +done + + +#--------------------------------------------------------------- +# output: scale all wallpapers +#--------------------------------------------------------------- + +## +# For each input image, generate a full set of output images. +# +# Note that this loop includes all columns; rely on 'size_only' +# to handle the rest. +# +printf "%s\n" "${MAKE}" | while read k; do + size_only "${TEMP}"/generated ${k}; +done + + +#--------------------------------------------------------------- +# output: metadata +#--------------------------------------------------------------- + +## +# FIXME: make this not ugly +# +temp=$(mktemp); +cat >> "${temp}" <<"EOF" +gnome-background-properties/Adelie.xml +<?xml version="1.0" encoding="UTF-8"?> +<!DOCTYPE wallpapers SYSTEM "gnome-wp-list.dtd"> +<wallpapers> +EOF + +find "${TEMP}"/generated -mindepth 1 -maxdepth 1 -type d | sort | while read k; do + name=$(printf "%s\n" "${k}" | cut -d/ -f3); # sloppy, sorry + # fix structure + mv "${KEEP}"/${name} "${KEEP}"/${name}.tmp; + mkdir -p "${KEEP}"/${name}/contents; + mv "${KEEP}"/${name}.tmp "${KEEP}"/${name}/contents/images; + + # compute metadata + case "${name}" in + background) + description="Default Background"; + author_name="Adélie Platform Team"; + ;; + lockscreen) + description="Default Lockscreen"; + author_name="Adélie Platform Team"; + ;; + *) + . "${IMGS}"/${name}/MANIFEST; + ;; + esac + + # write metadata to 'manifest.desktop' + # FIXME: we can do better than 'tr' below, but also what are + # the actual requirements? I'm just emulating what exists... + cat > "${KEEP}"/${name}/contents/metadata.desktop <<EOF +[Desktop Entry] +Name=${description} +X-KDE-PluginInfo-Name=$(printf "%s\n" "${description}" | tr ' ' '-') +X-KDE-PluginInfo-Author=${author_name} +X-KDE-PluginInfo-License=CC-BY-SA-4.0 +EOF + + # write metadata to 'gnome-background-properties/Adelie.xml' + find "${KEEP}"/${name}/contents/images -type f | grep -v metadata.desktop | sort | while read file; do + cat >> "${temp}" <<EOF + <wallpaper deleted="false"> + <name>${description}</name> + <filename>/usr/share/wallpapers/${name}/contents/images/${file##*/}</filename> + <options>zoom</options> + </wallpaper> +EOF + done +done + +## +# FIXME: make this not ugly +# +cat >> "${temp}" <<EOF +</wallpapers> +EOF + + +#--------------------------------------------------------------- +# output: create tarball +#--------------------------------------------------------------- + +mkdir -p adelie-wallpapers-${VTAG}/usr/share; + +# wallpapers +mv "${KEEP}" adelie-wallpapers-${VTAG}/usr/share/wallpapers; + +# gnome-background-properties +mkdir -p adelie-wallpapers-${VTAG}/usr/share/gnome-background-properties; +mv "${temp}" adelie-wallpapers-${VTAG}/usr/share/gnome-background-properties/Adelie.xml; + +# generate tarball +tar -pcJf adelie-wallpapers-${VTAG}.tar.xz adelie-wallpapers-${VTAG}; + +# clean up +rm -fr "${TEMP}"/generated; +rm -fr adelie-wallpapers-${VTAG};
\ No newline at end of file |