From 4f164b939ccd5819c816e0b18585641cfb9340c8 Mon Sep 17 00:00:00 2001 From: Peter Date: Sun, 24 Oct 2010 18:43:51 +0200 Subject: [PATCH] Add support for JPEG artwork and cover.{png,jpg} album artwork --- src/artwork.c | 101 +++++++++++++++++++++++++++++++++----------------- 1 file changed, 68 insertions(+), 33 deletions(-) diff --git a/src/artwork.c b/src/artwork.c index 4ca6e551..da6342c2 100644 --- a/src/artwork.c +++ b/src/artwork.c @@ -40,6 +40,17 @@ #include "artwork.h" +static const char *cover_basename[] = + { + "artwork", "cover", + }; + +static const char *cover_extension[] = + { + "png", "jpg", + }; + + static int artwork_read(char *filename, struct evbuffer *evbuf) { @@ -414,11 +425,13 @@ artwork_get(char *filename, int max_w, int max_h, struct evbuffer *evbuf) { if (src_ctx->streams[s]->codec->codec_id == CODEC_ID_PNG) break; + else if (src_ctx->streams[s]->codec->codec_id == CODEC_ID_MJPEG) + break; } if (s == src_ctx->nb_streams) { - DPRINTF(E_LOG, L_ART, "Artwork file '%s' not a PNG file\n", filename); + DPRINTF(E_LOG, L_ART, "Artwork file '%s' not a PNG or JPEG file\n", filename); av_close_input_file(src_ctx); return -1; @@ -426,7 +439,7 @@ artwork_get(char *filename, int max_w, int max_h, struct evbuffer *evbuf) src = src_ctx->streams[s]->codec; - DPRINTF(E_DBG, L_ART, "PNG image '%s': w %d h %d\n", filename, src->width, src->height); + DPRINTF(E_DBG, L_ART, "Original image '%s': w %d h %d\n", filename, src->width, src->height); need_rescale = 1; @@ -467,7 +480,8 @@ artwork_get(char *filename, int max_w, int max_h, struct evbuffer *evbuf) DPRINTF(E_DBG, L_ART, "Destination width %d height %d\n", target_w, target_h); - if (!need_rescale) + /* Fastpath for PNG */ + if ((src->codec_id == CODEC_ID_PNG) && !need_rescale) ret = artwork_read(filename, evbuf); else ret = artwork_rescale(src_ctx, s, target_w, target_h, evbuf); @@ -485,11 +499,12 @@ artwork_get(char *filename, int max_w, int max_h, struct evbuffer *evbuf) static int -artwork_get_own_png(char *path, int max_w, int max_h, struct evbuffer *evbuf) +artwork_get_own_image(char *path, int max_w, int max_h, struct evbuffer *evbuf) { char artwork[PATH_MAX]; char *ptr; int len; + int i; int ret; ret = snprintf(artwork, sizeof(artwork), "%s", path); @@ -506,30 +521,38 @@ artwork_get_own_png(char *path, int max_w, int max_h, struct evbuffer *evbuf) len = strlen(artwork); - ret = snprintf(artwork + len, sizeof(artwork) - len, "%s", ".png"); - if ((ret < 0) || (ret >= sizeof(artwork) - len)) + for (i = 0; i < (sizeof(cover_extension) / sizeof(cover_extension[0])); i++) { - DPRINTF(E_INFO, L_ART, "Artwork path exceeds PATH_MAX\n"); + ret = snprintf(artwork + len, sizeof(artwork) - len, ".%s", cover_extension[i]); + if ((ret < 0) || (ret >= sizeof(artwork) - len)) + { + DPRINTF(E_INFO, L_ART, "Artwork path exceeds PATH_MAX (ext %s)\n", cover_extension[i]); - return -1; + continue; + } + + DPRINTF(E_DBG, L_ART, "Trying own artwork file %s\n", artwork); + + ret = access(artwork, F_OK); + if (ret < 0) + continue; + + break; } - DPRINTF(E_DBG, L_ART, "Trying own artwork file %s\n", artwork); - - ret = access(artwork, F_OK); - if (ret < 0) + if (i == (sizeof(cover_extension) / sizeof(cover_extension[0]))) return -1; - ret = artwork_get(artwork, max_w, max_h, evbuf); - - return ret; + return artwork_get(artwork, max_w, max_h, evbuf); } static int -artwork_get_dir_png(char *path, int isdir, int max_w, int max_h, struct evbuffer *evbuf) +artwork_get_dir_image(char *path, int isdir, int max_w, int max_h, struct evbuffer *evbuf) { char artwork[PATH_MAX]; char *ptr; + int i; + int j; int len; int ret; @@ -550,23 +573,35 @@ artwork_get_dir_png(char *path, int isdir, int max_w, int max_h, struct evbuffer len = strlen(artwork); - ret = snprintf(artwork + len, sizeof(artwork) - len, "%s", "/artwork.png"); - if ((ret < 0) || (ret >= sizeof(artwork) - len)) + for (i = 0; i < (sizeof(cover_basename) / sizeof(cover_basename[0])); i++) { - DPRINTF(E_INFO, L_ART, "Artwork path exceeds PATH_MAX\n"); + for (j = 0; j < (sizeof(cover_extension) / sizeof(cover_extension[0])); j++) + { + ret = snprintf(artwork + len, sizeof(artwork) - len, "/%s.%s", cover_basename[i], cover_extension[j]); + if ((ret < 0) || (ret >= sizeof(artwork) - len)) + { + DPRINTF(E_INFO, L_ART, "Artwork path exceeds PATH_MAX (%s.%s)\n", cover_basename[i], cover_extension[j]); - return -1; + continue; + } + + DPRINTF(E_DBG, L_ART, "Trying directory artwork file %s\n", artwork); + + ret = access(artwork, F_OK); + if (ret < 0) + continue; + + break; + } + + if (j < (sizeof(cover_extension) / sizeof(cover_extension[0]))) + break; } - DPRINTF(E_DBG, L_ART, "Trying directory artwork file %s\n", artwork); - - ret = access(artwork, F_OK); - if (ret < 0) + if (i == (sizeof(cover_basename) / sizeof(cover_basename[0]))) return -1; - ret = artwork_get(artwork, max_w, max_h, evbuf); - - return ret; + return artwork_get(artwork, max_w, max_h, evbuf); } @@ -584,13 +619,13 @@ artwork_get_item(int id, int max_w, int max_h, struct evbuffer *evbuf) /* FUTURE: look at embedded artwork */ - /* Look for basename(filename).png */ - ret = artwork_get_own_png(filename, max_w, max_h, evbuf); + /* Look for basename(filename).{png,jpg} */ + ret = artwork_get_own_image(filename, max_w, max_h, evbuf); if (ret == 0) goto out; - /* Look for basedir(filename)/artwork.png */ - ret = artwork_get_dir_png(filename, 0, max_w, max_h, evbuf); + /* Look for basedir(filename)/{artwork,cover}.{png,jpg} */ + ret = artwork_get_dir_image(filename, 0, max_w, max_h, evbuf); if (ret == 0) goto out; @@ -632,7 +667,7 @@ artwork_get_group(int id, int max_w, int max_h, struct evbuffer *evbuf) got_art = 0; while ((!got_art) && ((ret = db_query_fetch_string(&qp, &dir)) == 0) && (dir)) { - got_art = ! artwork_get_dir_png(dir, 1, max_w, max_h, evbuf); + got_art = ! artwork_get_dir_image(dir, 1, max_w, max_h, evbuf); } db_query_end(&qp); @@ -661,7 +696,7 @@ artwork_get_group(int id, int max_w, int max_h, struct evbuffer *evbuf) got_art = 0; while ((!got_art) && ((ret = db_query_fetch_file(&qp, &dbmfi)) == 0) && (dbmfi.id)) { - got_art = ! artwork_get_own_png(dbmfi.path, max_w, max_h, evbuf); + got_art = ! artwork_get_own_image(dbmfi.path, max_w, max_h, evbuf); } db_query_end(&qp);