Incorpora le copertine degli album in OGG attraverso la riga di comando in Linux


15

Voglio convertire la mia musica da flac a ogg e attualmente oggenc lo fa perfettamente tranne che per le copertine degli album. Metaflac può produrre copertine di album, tuttavia non sembra esserci alcun strumento da riga di comando per incorporare le copertine degli album in ogg. Mp3tag e EasyTag sono in grado di farlo, e v'è una specifica per esso qui che prevede l'immagine da base64 codificato. Tuttavia, finora non ho avuto successo nel riuscire a prendere un file di immagine, convertendolo in base64 e incorporandolo in un file ogg.

Se prendo un'immagine codificata in base64 da un file ogg che ha già l'immagine incorporata, posso facilmente incorporarla in un'altra immagine usando vorbiscomment:

vorbiscomment -l withimage.ogg > textfile
vorbiscomment -c textfile noimage.ogg

Il mio problema è prendere qualcosa come un jpeg e convertirlo in base64. Attualmente ho:

base64 --wrap=0 ./image.jpg

Il che mi dà il file di immagine convertito in base64, usando vorbiscomment e seguendo le regole di tagging, posso incorporarlo in un file ogg in questo modo:

echo "METADATA_BLOCK_PICTURE=$(base64 --wrap=0 ./image.jpg)" > ./folder.txt
vorbiscomment -c textfile noimage.ogg

Tuttavia, questo mi dà un oggetto la cui immagine non funziona correttamente. Ho notato quando si confrontano le stringhe base64 che tutte le immagini che incorporano correttamente hanno una riga di intestazione ma tutte le stringhe base64 che ho generato mancano di questa intestazione. Ulteriore analisi dell'intestazione:

od -c header.txt
0000000  \0  \0  \0 003  \0  \0  \0  \n   i   m   a   g   e   /   j   p
0000020   e   g  \0  \0  \0  \0  \0  \0  \0  \0  \0  \0  \0  \0  \0  \0
0000040  \0  \0  \0  \0  \0  \0  \0  \0 035 332
0000052

Che segue le specifiche fornite sopra. L'avviso 003 corrisponde alla copertina e image / jpeg è il tipo mime.

Quindi, alla fine, la mia domanda è: come posso base64 codificare un file e generare questa intestazione insieme ad esso per incorporarlo in un file ogg?

Risposte:


5

ho appena scritto una sceneggiatura che esporta / importa immagini da file OGG / Vorbis usando vorbiscomment. Fa parte di uno strumento di conversione della libreria musicale.

Lo script rivelatore è nella funzione 'mussync-tools-transfert_images' di questo strumento:

https://github.com/biapy/howto.biapy.com/blob/master/various/mussync-tools

Fondamentalmente, ho scritto un lettore e uno scrittore per il formato metadata_block_picture.

Il codice è piuttosto complesso:

      OUTPUT_FILE="/path/to/my-ogg-file.ogg"
      IMAGE_PATH="/path/to/my-cover-art.jpg"
      IMAGE_MIME_TYPE="image/jpeg"
      # Export existing comments to file.
      local COMMENTS_PATH="$(command mktemp -t "tmp.XXXXXXXXXX")"
      command vorbiscomment --list --raw "${OUTPUT_FILE}" > "${COMMENTS_PATH}"

      # Remove existing images.
      command sed -i -e '/^metadata_block_picture/d' "${COMMENTS_PATH}"

      # Insert cover image from file.

      # metadata_block_picture format.
      # See: https://xiph.org/flac/format.html#metadata_block_picture

      local IMAGE_WITH_HEADER="$(command mktemp -t "tmp.XXXXXXXXXX")"
      local DESCRIPTION=""

      # Reset cache file.
      echo -n "" > "${IMAGE_WITH_HEADER}"

      # Picture type <32>.
      command printf "0: %.8x" 3 | command xxd -r -g0 \
              >> "${IMAGE_WITH_HEADER}"
      # Mime type length <32>.
      command printf "0: %.8x" $(echo -n "${IMAGE_MIME_TYPE}" | command wc -c) \
                | command xxd -r -g0 \
              >> "${IMAGE_WITH_HEADER}"
      # Mime type (n * 8)
      echo -n "${IMAGE_MIME_TYPE}" >> "${IMAGE_WITH_HEADER}"
      # Description length <32>.
      command printf "0: %.8x" $(echo -n "${DESCRIPTION}" | command wc -c) \
                | command xxd -r -g0 \
              >> "${IMAGE_WITH_HEADER}"
      # Description (n * 8)
      echo -n "${DESCRIPTION}" >> "${IMAGE_WITH_HEADER}"
      # Picture with <32>.
      command printf "0: %.8x" 0 | command xxd -r -g0 \
              >> "${IMAGE_WITH_HEADER}"
      # Picture height <32>.
      command printf "0: %.8x" 0 | command xxd -r -g0 \
              >> "${IMAGE_WITH_HEADER}"
      # Picture color depth <32>.
      command printf "0: %.8x" 0 | command xxd -r -g0 \
              >> "${IMAGE_WITH_HEADER}"
      # Picture color count <32>.
      command printf "0: %.8x" 0 | command xxd -r -g0 \
              >> "${IMAGE_WITH_HEADER}"
      # Image file size <32>.
      command printf "0: %.8x" $(command wc -c "${IMAGE_PATH}" \
                | command cut --delimiter=' ' --fields=1) \
                | command xxd -r -g0 \
              >> "${IMAGE_WITH_HEADER}"
      # Image file.
      command cat "${IMAGE_PATH}" >> "${IMAGE_WITH_HEADER}"

      echo "metadata_block_picture=$(command base64 --wrap=0 < "${IMAGE_WITH_HEADER}")" >> "${COMMENTS_PATH}"

      # Update vorbis file comments.
      command vorbiscomment --write --raw --commentfile "${COMMENTS_PATH}" "${OUTPUT_FILE}"

      # Delete cache file.
      command rm "${IMAGE_WITH_HEADER}"
      # Delete comments file.
      command rm "${COMMENTS_PATH}"

6

Ecco la mia soluzione per / usr / bin / vorbiscomment: problema dell'elenco degli argomenti troppo lungo. Ho creato uno script e l'ho chiamato oggart. Basta eseguirlo dalla riga di comando in questo modo:

oggart /path/to/music_file.ogg /path/to/image_file

Questo tagga il tuo file ogg con il campo METADATA_BLOCK_PICTURE. Easytag utilizza il vecchio modo di farlo con il campo COVERART anziché METADATA_BLOCK_PICTURE. Se si desidera la compatibilità con Easytag, è possibile eseguire lo script in questo modo:

oggart /path/to/music_file.ogg /path/to/image_file -e

Ecco la sceneggiatura:

#!/bin/sh

FILE1="`basename \"$1\"`"
EXT1=${FILE1##*.}
EXTTYPE1=`echo $EXT1 | tr '[:upper:]' '[:lower:]'`

FILE2="`basename \"$2\"`"
EXT2=${FILE2##*.}
EXTTYPE2=`echo $EXT2 | tr '[:upper:]' '[:lower:]'`

OGG=""
if [ "$EXTTYPE1" = ogg ]; then
OGG="$1"
elif [ "$EXTTYPE2" = ogg ]; then
OGG="$2"
fi
if [ "$OGG" = "" ]; then
echo no ogg file selected
exit 0
fi

PIC=""
array=(jpeg jpg png)
for item in ${array[*]}
do
if [ "$item" = "$EXTTYPE1" ]; then
PIC="$1"
elif [ "$item" = "$EXTTYPE2" ]; then
PIC="$2"
fi
done
if [ "$PIC" = "" ]; then
echo no jpg or png file selected
exit 0
fi

if [ "$3" = -e ]; then
EASYTAG=Y
else
EASYTAG=N
fi

DESC=`basename "$PIC"`
APIC=`base64 --wrap=0 "$PIC"`
if [ "`which exiv2`" != "" ]; then
MIME=`exiv2 "$PIC" | grep 'MIME type ' | sed 's/: /|/' | cut -f 2 -d '|' | tail -n 1`
fi
if [ "$MIME" = "" ]; then
MIME="image/jpeg"
fi

vorbiscomment -l "$OGG" | grep -v '^COVERART=' | grep -v '^COVERARTDESCRIPTION=' | grep -v '^COVERARTMIME=' | grep -v 'METADATA_BLOCK_PICTURE=' > "$OGG".tags

if [ "$EASYTAG" = N ]; then
echo METADATA_BLOCK_PICTURE="$APIC" > "$OGG".tags2
else
echo COVERART="$APIC" > "$OGG".tags2
fi
vorbiscomment -w -R -c "$OGG".tags2 "$OGG"
vorbiscomment -a -R -t COVERARTDESCRIPTION="$DESC" "$OGG"
vorbiscomment -a -R -t COVERARTMIME="$MIME" "$OGG"
vorbiscomment -a -R -c "$OGG".tags "$OGG"

rm -f "$OGG".tags
rm -f "$OGG".tags2

La sceneggiatura è stata pubblicata qui. Puoi scaricare oggart.tar.gz @ murga-linux.com/puppy/viewtopic.php?mode=attach&id=44270
Jason il

Ho corretto la formattazione dello script nel post.
Gaff,

1
Se ricevi un "Errore di sintassi:" ("inaspettato" in Ubuntu è probabilmente qualcosa a che fare con la shell utilizzata per l'esecuzione. Ho cambiato la prima riga in #! / Bin / bash e ha funzionato.
Dan Gravell,

1
questa sceneggiatura non funziona per me. Come posso vedere, utilizza solo la base64 dell'immagine ma prima di essa deve esserci un'intestazione speciale
Sergey

2

Non sono a conoscenza di nulla che lo faccia automaticamente semplicemente indicando l'immagine.

Comunque vorbiscomment può incorporare tag arbitrari, devi solo codificare l'immagine in base64 e quindi costruire il tag nel formato corretto .

per esempio vorbiscomment -a -t 'METADATA_BLOCK_PICTURE=...' file.ogg newfile.ogg

dovrai hackerare questi passaggi in uno script di qualche tipo perché sia ​​utile.


Ciò sarebbe fattibile, ma purtroppo se l'immagine supera i 64kb, i vorbiscommenti restituiscono "/ usr / bin / vorbiscomment: elenco degli argomenti troppo lungo". Qualche idea su come aggirare questo?
dmikalova,

qual è il tuo sistema e qual è l'output di getconf ARG_MAX? Sfortunatamente non è possibile aggirare questo limite senza ricompilare il kernel. Qui a 64-bit 2.6.32-24, ho 2 MB.
sml

Sto eseguendo arch linux 64-bit 2.6.34.1-1 e ho anche 2 MB. Sarebbe possibile inserire un marcatore, ad esempio vorbiscomment -a -t 'METADATA_BLOCK_PICTURE = marker' file.ogg newfile.ogg, quindi fare leggere qualcosa al file ogg e sostituire il marcatore con l'immagine base64?
dmikalova,

Assolutamente. Se vedi le specifiche del formato del tag che ho collegato, puoi usare vorbiscomment per inserire un'immagine temporanea (piccola), quindi scrivere direttamente nel file aggiornando le ultime due parti del tag: lunghezza dei dati e dati stessi. Ovviamente dovrai hackerare qualcosa insieme, comunque.
SML

Sto provando il mutageno, una libreria Python di basso livello per la codifica audio e il mio aspetto preliminare sembra che possa fare ciò di cui ho bisogno. Riferirò quando scoprirò le cose.
dmikalova,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.