diff options
| -rw-r--r-- | Makefile | 30 | ||||
| -rw-r--r-- | README.md | 10 | ||||
| -rw-r--r-- | assets/templates/album.html | 2 | ||||
| -rw-r--r-- | assets/templates/base.html | 6 | ||||
| -rw-r--r-- | assets/templates/index.html | 31 | ||||
| -rw-r--r-- | docs/revela.1.scd | 65 | ||||
| -rw-r--r-- | docs/revela.5.scd | 90 | ||||
| -rw-r--r-- | include/config.h | 1 | ||||
| -rw-r--r-- | include/site.h | 2 | ||||
| m--------- | roscha | 0 | ||||
| -rw-r--r-- | src/components.c | 4 | ||||
| -rw-r--r-- | src/config.c | 7 | ||||
| -rw-r--r-- | src/revela.c | 24 | ||||
| -rw-r--r-- | src/site.c | 5 | ||||
| -rw-r--r-- | src/tests/config.c | 1 | ||||
| -rw-r--r-- | tests/site.ini | 1 | ||||
| -rwxr-xr-x | util/revela-init | 30 | 
17 files changed, 258 insertions, 51 deletions
| @@ -27,7 +27,9 @@ REVELA_OBJS:=$(REVELA_SRCS:%.c=$(OBJDIR)/%.o)  ALL_OBJS:=$(ROSCHA_OBJS) $(PARCINI_OBJS) $(REVELA_OBJS)  TEST_OBJS:=$(filter-out $(OBJDIR)/src/revela.o,$(ALL_OBJS)) -all: revela +PREFIX?=/usr/local/ + +all: revela docs  test: tests/config tests/fs @@ -43,9 +45,33 @@ revela: $(ALL_OBJS)  	mkdir -p $(@D)  	$(CC) -o $(BUILDIR)/$@ $^ $(LIBS) $(CFLAGS) +docs: +	mkdir -p build/man/ +	scdoc < docs/revela.1.scd > build/man/revela.1 +	scdoc < docs/revela.5.scd > build/man/revela.5 + +install: +	mkdir -p $(PREFIX)/bin +	mkdir -p $(PREFIX)/share/man/man1 +	mkdir -p $(PREFIX)/share/man/man5 +	mkdir -p $(PREFIX)/share/revela +	install -m755 $(BUILDIR)/revela $(PREFIX)/bin/revela +	install -m755 util/revela-init $(PREFIX)/share/revela/revela-init +	ln -sf $(PREFIX)/share/revela/revela-init $(PREFIX)/bin/ +	install -m644 build/man/revela.1 $(PREFIX)/share/man/man1/revela.1 +	install -m644 build/man/revela.5 $(PREFIX)/share/man/man5/revela.5 +	cp -r assets $(PREFIX)/share/revela/ + +uninstall: +	rm -rf $(PREFIX)/share/revela +	rm -f $(PREFIX)/bin/revela +	rm -f $(PREFIX)/bin/revela-init +	rm -f $(PREFIX)/share/man/man1/revela.1 +	rm -f $(PREFIX)/share/man/man5/revela.5 +  clean:  	rm -r build -.PHONY: clean all test +.PHONY: clean all test docs install uninstall  .PRECIOUS: $(OBJDIR)/src/tests/%.o @@ -4,8 +4,6 @@ A static web image gallery generator. It optimizes images for the web and  generates HTML files to create a photo/image gallery web site ready to be served  by an HTML server. -Alpha stages. It's functional but a little rough around the edges. -  ## Building  revela depends on GraphicsMagick (1.3+ tested) and libexif (0.6+ tested). @@ -21,11 +19,13 @@ or for debugging:  DEBUG=1 make  ``` +## Usage + +For information on how to use revela, consult `man revela` if installed on your +system, or read the contents in `docs/` in the source. +  ## TODO:  * Add exif tags to template hashmap. -* Improve unja or find better alternative. -* Get rid of previews variable. It is a temporary hack to limit the amount of -  thumbnails for each album in the index.  * Better test coverage? (if I am not too lazy)  * Document. diff --git a/assets/templates/album.html b/assets/templates/album.html index 95d9935..856cf63 100644 --- a/assets/templates/album.html +++ b/assets/templates/album.html @@ -12,7 +12,9 @@  	<p>from <a href="{{ index }}/">{{ title }}</a> </p>  </div>  <div class="gallery-container"> +	{% if album.desc %}  	<p>{{ album.desc }}</p> +	{% endif %}  	<div class="album-container">  		{% for thumb in album.thumbs %}  		<a href="{{ thumb.link }}"> diff --git a/assets/templates/base.html b/assets/templates/base.html index 1f2d8dc..11ba0ab 100644 --- a/assets/templates/base.html +++ b/assets/templates/base.html @@ -3,11 +3,7 @@  	<head>  		<meta charset="utf-8">  		<meta content="width=device-width, initial-scale=1" name="viewport"> -		<title> -			{% block title %} -			A photo gallery by Yaroslav de la Peña Smirnov -			{% endblock %} -		</title> +		<title>{% block title %}{{ title }}{% endblock %}</title>  		<link rel="stylesheet" href="{{ index }}/css/gallery.css">  	</head>  	<body> diff --git a/assets/templates/index.html b/assets/templates/index.html index 61160a5..bf62607 100644 --- a/assets/templates/index.html +++ b/assets/templates/index.html @@ -11,23 +11,24 @@  	{% endfor %}  	</p>  	{% for year in years %} -	<h2 id="{{ year.name }}">{{ year.name }}</h2> -	{% for album in year.albums %} -	{% if album.title %} -	<a href="{{ album.link }}"><h3>{{ album.title }}</h3></a> -	{% else %} -	<a href="{{ album.link }}"><h3>Untitled</h3></a> -	{% endif %} -	<div class="album-container"> -		{% for thumb in album.thumbs %} -			{% if loop.index < 4 %} -			<a href="{{ thumb.link }}"> -				<img class="thumbnail" src="{{ thumb.source }}"> -			</a> +		<h2 id="{{ year.name }}">{{ year.name }}</h2> +		{% for album in year.albums %} +			{% if album.title %} +			<a href="{{ album.link }}"><h3>{{ album.title }}</h3></a> +			{% else %} +			<a href="{{ album.link }}"><h3>Untitled</h3></a>  			{% endif %} +			<div class="album-container"> +				{% for thumb in album.thumbs %} +				{% if loop.index >= 4 %} +				{% break %} +				{% endif %} +				<a href="{{ thumb.link }}"> +					<img class="thumbnail" src="{{ thumb.source }}"> +				</a> +				{% endfor %} +			</div>  		{% endfor %} -	</div> -	{% endfor %}  	{% endfor %}  </div>  {% endblock %} diff --git a/docs/revela.1.scd b/docs/revela.1.scd new file mode 100644 index 0000000..a503668 --- /dev/null +++ b/docs/revela.1.scd @@ -0,0 +1,65 @@ +revela(1) + +# NAME + +revela - static image gallery generator. + +# SYNOPSIS + +*revela* [_OPTIONS_] <_-o OUTPUT DIR_> +*revela-init* + +# DESCRIPTION + +*revela* is a static web image gallery generator. It optimizes images for the web +and generates HTML files to create a photo/image gallery web site ready to be +served by an HTML server. + +revela takes a directory with pictures, jinja-like templates and converts that +into a static web gallery of said pictures organized into albums. + +The root of the input directory should contain at least the following +directories and files: + +*content* - The directory with subdirectories that each contain pictures. Each +subdirectory with pictures is considered an album. Each album should contain an +album.ini file, for information on the format of this file read revela(5). + +*static* - Directory with 'static' directories and files to be copied as-is to the +root of the output directory. Here you can put any static assets such as +favicons, css, etc. + +*templates* - Here should go the templates for the website. There should be at +least three files: _index.html_, _image.html_ and _album.html_. There can also +be parent templates used by any of those three templates. + +*site.ini* - The configuration for the site, such as title, base url and image +optimizations. For more information consult revela(5). + +*revela-init* is an interactive helper script that generates a _site.ini_ file +and copies the default templates provided with revela in the working directory +from where it was called. + +# OPTIONS + +*-i* _DIRECTORY_ +	Indicate the input directory. If not indicated it will default to the +	current working dir. + +*-o* _DIRECTORY_ +	The output directory. This is the only required flag. + +*-n* +	Dry run. Show which files would be copied and which html files rendered but +	don't do anything. + +*-V* +	Prints version information and exits. + +# SEE ALSO + +*revela*(5) + +# AUTHORS + +Yaroslav de la Peña Smirnov <yps@yaroslavps.com>. diff --git a/docs/revela.5.scd b/docs/revela.5.scd new file mode 100644 index 0000000..b4656fa --- /dev/null +++ b/docs/revela.5.scd @@ -0,0 +1,90 @@ +revela(5) + +# NAME + +revela - static image gallery generator. + +# DESCRIPTION + +This manual page documents the format and syntax of the _\*.ini_ or configuration +files found in revela source galleries. + +# PREAMBLE + +There are two kinds of configuration files: + +*site.ini* - There is only one _site.ini_ file in a revela gallery and it should +be located at the root of the gallery directory. This file contains the title of +the gallery, the base url, and image optimization settings. + +*album.ini* - Each album should contain a file with this name. This simply +contains the title of the album and optionally a description. + +# SYNTAX + +Both files are in what's called 'ini format'. It merely consists of _key=value_ +pairs and _[sections]_. You should already be familiar with it. + +## SITE CONFIGURATION + +_site.ini_ may contain the following sections and keys: + +*title*=string +	The name or title of the gallery to be used inside templates. + +*base_url*=string +	The base url. For example, if the web gallery is not at the root of the +	website, it could be "/photos". _Optional_. + +*[images]* +	This section contains settings for optimization of the main image files. +	_This section and all its keys are optional_. + +	*strip*=boolean +		Whether to strip images of their EXIF tags and other metainformation. + +	*quality*=integer +		From 0 to 100, 0 being the lowest quality and highest compression, and +		100 being the highest quality but no compression. This corresponds to +		JPEG "quality" levels. + +	*max_width*=integer +		The maximum width the image file should have in pixels. + +	*max_height*=integer +		The maximum height the image file should have in pixels. + +	*smart_resize*=boolean +		Whether to preserve the aspect ratio of the image when resizing. + +	*blur*=integer +		A value from 0 to 100, where 0 is no blur and 100 is the maximum amount +		of blur. + +*[thumbnails]* +	This section contains settings for optimization of the thumbnails files of +	images. All of the keys in this section are the same as in the _images_ +	sections. _This section and all its keys are optional_. + +## ALBUM CONFIGURATION + +_album.ini_ may contain the following keys: + +*title*=string +	The name of the album. + +*desc*=string +	A short description of the album. _Optional_. + +# NOTES + +If you initialize your gallery with the helper script _revela-init_ a _site.ini_ +should be generated. You can tweak the settings by using it as a basis. + +# SEE ALSO + +*revela*(1) + +# AUTHORS + +Yaroslav de la Peña Smirnov <yps@yaroslavps.com>. diff --git a/include/config.h b/include/config.h index 589671f..085eb5e 100644 --- a/include/config.h +++ b/include/config.h @@ -19,7 +19,6 @@ struct image_config {  struct site_config {  	char *title;  	char *base_url; -	uint32_t max_previews;  	struct image_config images;  	struct image_config thumbnails;  }; diff --git a/include/site.h b/include/site.h index e054730..43a20d2 100644 --- a/include/site.h +++ b/include/site.h @@ -21,7 +21,7 @@ struct site {  	struct site_config *config;  	MagickWand *wand;  	char *root_dir; -	const char *output_dir; +	char *output_dir;  	char *content_dir;  	/*   	 * Indicates how many characters after the full root dir path of the input diff --git a/roscha b/roscha -Subproject 5725085e3be9ee005c9b9cc4623d5ad5f90418f +Subproject 4665a620775da64ec7280762979a9fc6fa37c0b diff --git a/src/components.c b/src/components.c index fc3bab5..aeb14b1 100644 --- a/src/components.c +++ b/src/components.c @@ -167,8 +167,8 @@ image_new(char *src, const struct stat *pstat, struct album *album)  	image->exif_data = exif_data_new_from_file(image->source);  	image->modtime = pstat->st_mtim;  	image_set_date(image, pstat); -	image->map = roscha_object_new(hmap_new_with_cap(8)); -	image->thumb = roscha_object_new(hmap_new_with_cap(4)); +	image->map = roscha_object_new(hmap_new_with_cap(16)); +	image->thumb = roscha_object_new(hmap_new_with_cap(8));  	image->modified = false;  	return image; diff --git a/src/config.c b/src/config.c index 1bc531f..a570104 100644 --- a/src/config.c +++ b/src/config.c @@ -126,12 +126,6 @@ site_config_keyvalue_handler(struct parcini_line *parsed, void *dst)  				&config->base_url)?  			KV_HANDLER_OK : KV_HANDLER_BADVALUE;  	} -	if (MATCHSK("", "max_previews", parsed)) { -		return parcini_value_handle(&parsed->value, PARCINI_VALUE_INTEGER, -				&config->max_previews)? -			KV_HANDLER_OK : KV_HANDLER_BADVALUE; -	} -  out:  	return KV_HANDLER_NOMATCH; @@ -232,7 +226,6 @@ site_config_init(void)  {  	struct site_config *config = calloc(1, sizeof *config);  	if (config != NULL) { -		config->max_previews = 10;  		config->images = (struct image_config) {  			.strip = true,  			.quality = 80, diff --git a/src/revela.c b/src/revela.c index 32867c6..e21ae02 100644 --- a/src/revela.c +++ b/src/revela.c @@ -10,13 +10,18 @@  #include "config.h"  #include "bstree.h" +#ifndef VERSION +#define VERSION "0.1.0" +#endif +  static const char *usage = -	"Usage: %s [options] [-i <input dir>] -o <output dir>\n"; +	"Usage: %s [OPTIONS] -o <output dir>\n" +	"For more information consult `man 1 revela`\n";  static struct site site = {0};  static enum log_level loglvl = LOG_DETAIL; -static void +static inline void  bad_arguments(const char *cmd)  {  	fprintf(stderr, usage, cmd); @@ -28,17 +33,23 @@ parse_arguments(int argc, char *argv[])  {  	int opt;  	char *cmd = argv[0]; -	while ((opt = getopt(argc, argv, "i:o:n")) != -1) { +	while ((opt = getopt(argc, argv, "i:o:nhV")) != -1) {  		switch (opt) {  		case 'i':  			site.root_dir = strdup(optarg);  			break;  		case 'o': -			site.output_dir = optarg; +			site.output_dir = realpath(optarg, NULL);  			break;  		case 'n':  			site.dry_run = true;  			break; +		case 'h': +			printf(usage, cmd); +			exit(0); +		case 'V': +			printf("revela "VERSION"\n"); +			exit(0);  		default:  			bad_arguments(cmd);  		} @@ -51,8 +62,6 @@ parse_arguments(int argc, char *argv[])  int  main(int argc, char *argv[])  { -	int ret = EXIT_SUCCESS; -  	parse_arguments(argc, argv);  #ifdef DEBUG @@ -61,7 +70,7 @@ main(int argc, char *argv[])  	log_set_verbosity(loglvl);  #endif -	ret = site_init(&site) && site_load(&site) && site_build(&site)  +	int ret = site_init(&site) && site_load(&site) && site_build(&site)   		? EXIT_SUCCESS : EXIT_FAILURE;  	if (site.dry_run) { @@ -69,5 +78,6 @@ main(int argc, char *argv[])  	}  	site_deinit(&site); +  	return ret;  } @@ -86,10 +86,6 @@ optimize_image(MagickWand *wand, const char *dst,  		const struct image_config *conf,   		const struct timespec *srcmtim, bool dry)  { -	int update = file_is_uptodate(dst, srcmtim); -	if (update == -1) return false; -	if (update == 1) return true; -  	log_printl(LOG_DETAIL, "Converting %s", dst);  	if (dry) goto out; @@ -413,6 +409,7 @@ site_deinit(struct site *site)  	site_config_destroy(site->config);  	free(site->content_dir);  	free(site->root_dir); +	free(site->output_dir);  	if (site->wand != NULL) {  		DestroyMagickWand(site->wand);  		DestroyMagick(); diff --git a/src/tests/config.c b/src/tests/config.c index 64a4da8..79e5358 100644 --- a/src/tests/config.c +++ b/src/tests/config.c @@ -15,7 +15,6 @@ test_site_config_read_ini(void)  	asserteq(site_config_read_ini(TESTS_DIR, config), true);  	asserteq(strcmp(config->title, "An example gallery"), 0);  	asserteq(strcmp(config->base_url, "http://www.example.com/photos"), 0); -	asserteq(config->max_previews, 20);  	asserteq(config->images.strip, false);  	asserteq(config->images.quality, 80);  	asserteq(config->images.max_width, 3000); diff --git a/tests/site.ini b/tests/site.ini index ad4a575..f33a336 100644 --- a/tests/site.ini +++ b/tests/site.ini @@ -1,6 +1,5 @@  title = "An example gallery"  base_url = "http://www.example.com/photos" -max_previews = 20  [images]  strip = no diff --git a/util/revela-init b/util/revela-init new file mode 100755 index 0000000..25e3ddc --- /dev/null +++ b/util/revela-init @@ -0,0 +1,30 @@ +#!/bin/sh + +this="$(readlink -f $0)" +sharedir="$(dirname $this)" + +printf "Enter your gallery name (e.g. \"Gallery\")> " +read name +printf "Enter base url (e.g. \"/photos\"; can be empty)> " +read burl + +echo "title = \"$name\" +base_url = \"$burl\" + +[images] +strip = no +quality = 80 +max_width = 1200 +max_height = 1200 +smart_resize = yes + +[thumbnails] +strip = yes +quality = 60 +max_width = 200 +max_height = 200 +smart_resize = yes +blur = 50" > site.ini + +cp -r "$sharedir"/assets/* . +mkdir content | 
