puppylinux-woof-CE / woof-CE

woof - the Puppy builder
GNU General Public License v2.0
392 stars 281 forks source link

Wallpapers #588

Closed 01micko closed 9 years ago

01micko commented 9 years ago

Barry has code in there that chops off the wallpapers at 8 images. The default images are rather aged (and most are ugly) too. I reckon we have no limit and only one default (a grey 1x1 px image) and that will do for minimalists. Then a builder can have their "wallpapers.xyz.pet" and not worry about hacking around later to fix them up.

mavrothal commented 9 years ago

I would agree but add a "woof-woof" to it to "mark" the build sytem or "force" the change ;)

dimkr commented 9 years ago

Yes! Delete all of them! They're so ugly I'm ashamed to have them in my puplets.

01micko commented 9 years ago

NOTE: only fixed this for 3builddistro-Z .. which may change soon :smile_cat:

dimkr commented 9 years ago

We should merge 3builddistro and 3builddistro-Z. The difference should be 2-3 "if" statements IIRC.

01micko commented 9 years ago

Maybe, but I just deleted and deleted when I altered it. I'm not sure that supporting the old initrd with modules is such a good idea. There were always lots of problems unless you followed Barry's kernel config implicitly.

mavrothal commented 9 years ago

Now that we have the SVG backgrounds, is there any way to have ROX display an overlay or watermark on SVGs the way HTML/XML can? I would think JWM could handle it in XML but what about ROX. The (obvious) idea hear is to have a puppy logo or the pupplet name/version showing over the solid colour backgrounds.

01micko commented 8 years ago

Now that we have the SVG backgrounds, is there any way to have ROX display an overlay or watermark on SVGs the way HTML/XML can?

I don't think so .. but .. I could write a small C utility that uses pango-cairo to render the DISTRO_FILE_PREFIX (or whatever) to a smallish image that should scale well. In fact I have already written something similar that was intended for labels, but could easily be adapted.

01micko commented 8 years ago

Ok, take a look at this. The prog is called 'mkwallpaper'.

/** This program is designed to be used in Puppy Linux.
 * It is designed to be used in Woof-CE or in a running Puppy as root or
 * an ordinary user.
 */

#include <cairo-svg.h>
#include <pango/pangocairo.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/stat.h>

#define _GNU_SOURCE
#define PROG "mkwallpaper"
#define THIS_VERSION "0.1"

char out_file[128]; 

void usage(){
    printf("%s-%s\n\n", PROG , THIS_VERSION);
    printf("\tGenerate SVG or PNG Puppy Linux wallpapers. SVG is default.\n\n");
    printf("Usage :\n");
    printf("\t%s [-l, -n, -f, -p, -s, -x, -y, -r, -w, -h]\n", PROG);
    printf("\t-n\t: image name\n");
    printf("\t-l\t: label for an image, up to 100 chars\n");
    printf("\t-f\t: a TTF font family\n");
    printf("\t-p\t: \"png\" or \"svg\" format\n");
    printf("\t-x\t: width of image in pixels\n");
    printf("\t-y\t: height of image in pixel\n");
    printf("\t-z\t: floating point RGB, quoted, "
                    "space delimited values for colour (mandatory arg!)\n");
    printf("\t-w\t: \"woof\" FOR WOOF USE ONLY!!!\n");
    printf("\t-h\t: show this help and exit.\n");
    exit (EXIT_SUCCESS);
}

char *get_user_out_file(char *ww){
    char *my_home = getenv("HOME");
    if (strncmp(ww, "woof", 4) == 0) {
        strcpy(out_file, "usr/share/backgrounds"); /*woof only */
    } else if (strcmp(my_home, "/root") == 0) {
        strcpy(out_file, "/usr/share/backgrounds");
    } else {
        sprintf(out_file, "%s/%s", my_home, ".local/share/backgrounds");
    }
    mkdir(out_file, 0755);
    return out_file;
} 

void paint_img (char *label, 
                char *name, 
                char *font, 
                char *form,
                int wdth,
                int hght,
                char *fp_color,
                int f_size,
                char *woofy) {
    char destimg[80];

    int msg_len = strlen(label);
    if (msg_len > 20) {
        fprintf(stderr,"\"%s\" is too long!\n", label);
        exit (EXIT_FAILURE);
    }
    if (f_size == 20) f_size = hght / 10;

    if (!fp_color) exit (EXIT_FAILURE);

    float r, g , b;
    char red[6];
    char green[6];
    char blue[6];
    int len = strlen(fp_color);
    if (len > 31 ) {
        fprintf(stderr,"ERROR: colour argument too long\n");
        exit (EXIT_FAILURE);
    }
    int result = sscanf(fp_color, "%s %s %s", red, green, blue);
    if (result < 3) fprintf(stderr,"ERROR: less than 3 colour aguments!\n");    

    r = atof(red);
    g = atof(green);
    b = atof(blue);
    if ((r > 0.85) || (g > 0.85) || (b > 0.85)) {
        fprintf(stderr, "Color values are too high\n");
        exit (EXIT_FAILURE);
    }
    float r1, g1, b1, r2, g2, b2;
    r1 = r; g1 = g; b1 = b;
    r2 = r + 0.15;
    g2 = g + 0.15;
    b2 = b + 0.15;

    cairo_surface_t *cs;
    if (!form) strcpy(form, "svg");
    if (strcmp(form, "svg") == 0) {
        destimg[80] = sprintf(destimg, "%s/%s.svg", get_user_out_file(woofy), name);
        cs = cairo_svg_surface_create(destimg, wdth, hght);

    } else {
        cs = cairo_image_surface_create 
                            (CAIRO_FORMAT_ARGB32, wdth, hght);
        destimg[80] = sprintf(destimg, "%s/%s.png", get_user_out_file(woofy), name);                    
    }
    cairo_t *c;
    c = cairo_create(cs);

    cairo_rectangle(c, 0.0, 0.0, wdth, hght);
    cairo_pattern_t *linear = cairo_pattern_create_linear(0, 0, wdth, hght); 
    cairo_pattern_add_color_stop_rgb(linear, 0, r1, g1, b1); 
    cairo_pattern_add_color_stop_rgb(linear, 1, r2, g2, b2);
    cairo_set_source(c, linear);
    cairo_fill(c);

    PangoLayout *layout;
    PangoFontDescription *font_description;

    font_description = pango_font_description_new ();
    pango_font_description_set_family (font_description, font);
    pango_font_description_set_weight (font_description, PANGO_WEIGHT_BOLD);
    pango_font_description_set_style (font_description, PANGO_STYLE_OBLIQUE);
    pango_font_description_set_absolute_size (font_description, f_size * PANGO_SCALE);

    layout = pango_cairo_create_layout (c);
    pango_layout_set_font_description (layout, font_description);
    pango_layout_set_width (layout, 9 * wdth / 10 * PANGO_SCALE);
    pango_layout_set_wrap (layout, PANGO_WRAP_WORD);
    pango_layout_set_text (layout, label, -1);

    cairo_move_to(c, wdth / 2 , 4 * hght / 6);
    cairo_set_source_rgb(c, 0.0, 0.0, 0.0);
    pango_cairo_show_layout (c, layout);

    g_object_unref (layout);
    pango_font_description_free (font_description);
    if (strcmp(form, "png") == 0) {
        cairo_surface_write_to_png (cs, destimg);
    }
    cairo_surface_destroy(cs);  
    cairo_destroy(c);
    printf("image saved to %s\n", destimg);
}

int main(int argc, char **argv) {
    if (argc < 2) {
        usage();
        return 0;
    }
    if (strcmp(argv[1], "-h") == 0) {
        usage();
        return 0;
    }

    char *lvalue = "hello mksvg!"; /* the cli string that appears in image */
    char *nvalue = "foo"; /* image name */
    char *fvalue = "Sans"; /* font */
    char *pvalue = "svg";
    char *wvalue = "notwoof"; /* used for woof */
    char *zvalue = NULL; /* fp colour */
    int width = 200; int height = 60;
    int font_size = 20;
    int c;
    while ((c = getopt (argc, argv, "l:n:f:p:x:y:w:z:s::")) != -1) {
        switch (c)
        {
            case 'l':
                lvalue = optarg;
                break;
            case 'n':
                nvalue = optarg;
                break;
            case 'f':
                fvalue = optarg;
                break;
            case 'p':
                pvalue = optarg;
                break;
            case 'x':
                width = atoi(optarg);
                break;
            case 'y':
                height = atoi(optarg);
                break;
            case 'w':
                wvalue = optarg;
                break;
            case 'z':
                zvalue = optarg;
                break;
            case 's':
                font_size = atoi(optarg);
                break;
            default:
                usage();
        }
    }
    if (zvalue == NULL) {
        fprintf(stderr, "You must have 3 floating point value argument \"-z\"\n");
        usage();
        return 1;
    }
    paint_img(lvalue, nvalue, fvalue, pvalue,
                        width, height, zvalue, font_size, wvalue);
    return 0;
}

It's a reimplementation of a "label maker" I had already coded.

There's a Makefile

CC=gcc
LIBDIR=/usr/lib64
#LIBDIR=/usr/lib
CFLAGS=-Wall -pedantic -std=gnu99 -g -I/usr/include `pkg-config --libs --cflags pangocairo`
LDFLAGS=-Wall -g `pkg-config --libs pangocairo` -L$(LIBDIR)

all: mkwallpaper

mkwallpaper: mkwallpaper.o
    $(CC) -o $@ $^ $(LDFLAGS)

mkwallpaper.o: mkwallpaper.c
    $(CC) -o $@ $(CFLAGS) -c $^

clean:
    -rm -f *.o mkwallpaper

Here is a hack to 3builddistro-Z @line ~579

#140617 copy new init
echo "Replacing /etc/rc.d/rc.sysinit"
[ -d ./huge_extras ] && cp -af ./huge_extras/rc.sysinit sandbox3/rootfs-complete/etc/rc.d/ || exit 1
echo
# new wallpaper maker
echo "Do you want to build some custom wallpapers?"
echo "Press 'w' to accept or ENTER to keep going without custom wallpapers."
read customwalls
if [ "$customwalls" = "w" ];then
    which mkwallpaper 2>&1 > /dev/null
    retwall=$?
    if [ $retwall -ne 0 ];then
        echo "Compiling the wallpaper utility"
        cd support
        make
        if [ $? -ne 0 ];then
            echo "Sorry, compiling the utility failed, moving on"
            cd -
        else
            cd -
            [ -x support/mkwallpaper ] && cp -af support/mkwallpaper sandbox3/rootfs-complete
            cd sandbox3/rootfs-complete
            . etc/DISTRO_SPECS
            for e in 1 2 3 4 5 6 7 8; do
                case $e in
                    1)color='0.3 0.0 0.5';;
                    2)color='0.3 0.0 0.1';;
                    3)color='0.0 0.2 0.4';;
                    4)color='0.2 0.7 0.1';;
                    5)color='0.6 0.1 0.1';;
                    6)color='0.1 0.1 0.4';;
                    7)color='0.3 0.3 0.0';;
                    8)color='0.0 0.0 0.0';;
                esac
                ./mkwallpaper -n ${DISTRO_FILE_PREFIX}-wall${e} -l "$DISTRO_FILE_PREFIX" -x800 -y600 -z "$color" -w woof
            done
            rm -f mkwallpaper
            cd -
        fi
    else
        cd sandbox3/rootfs-complete
        . etc/DISTRO_SPECS
        for e in 1 2 3 4 5 6 7 8; do
            case $e in
                1)color='0.3 0.0 0.5';;
                2)color='0.3 0.0 0.1';;
                3)color='0.0 0.2 0.4';;
                4)color='0.2 0.7 0.1';;
                5)color='0.6 0.1 0.1';;
                6)color='0.1 0.1 0.4';;
                7)color='0.3 0.3 0.0';;
                8)color='0.0 0.0 0.0';;
            esac
            mkwallpaper -n ${DISTRO_FILE_PREFIX}-wall${e} -l "$DISTRO_FILE_PREFIX" -x800 -y600 -z "$color" -w woof
        done
        cd -
    fi
fi
echo 
#run post-install script...
echo

..and here is the result!

Damn you github! No svg allowed! ha! .. but my prog supports PNG, and here's one I prepared earlier.

original-wall2

The SVG's are less than 10K each (PNG same size is ~30K). I'm not going to commit that just yet. I want to see if @dimkr has thoughts on my beginner C code (um the pango font stuff has a bit of unnecessary crud) and what the rest of you think. Build it, try it out yourselves. I'm interested in what would be the best way to implement it in woof.

Naturally, a native binary is best as with different cairo and pango versions bugs may crop up. So the best approach would be to have PET packages for each arch/distro. (You will see in my 3builddistro hack I have catered to that).

:tongue:

01micko commented 8 years ago

Patch needed for wallpaper setter..

--- AppRun.orig 2015-10-28 12:39:27.610481141 +1000
+++ AppRun  2015-10-28 12:37:26.877151740 +1000
@@ -184,7 +184,7 @@ ln -sf $CURRENTIMG /tmp/current_wallpape
 swapimagefunc()
 {
    rm -f /tmp/current_wallpaper_selection.jpg
-   ISIMAGE="`echo $IMAGE|grep -iE 'jpg$|png$|jpeg$|gif|JPEG$|JPG$|tiff$|background$'`"
+   ISIMAGE="`echo $IMAGE|grep -iE 'jpg$|png$|jpeg$|gif|JPEG$|JPG$|tiff$|background$|svg$|SVG$'`"
    if [ "$ISIMAGE" = "" ];then IMAGE="/usr/share/doc/puppylogo96.png" #if file is not an image
    fi
    ln -sf $IMAGE /tmp/current_wallpaper_selection.jpg

And a pango fix for the above, just changes the word wrapping to half the image width.

diff -rup mkwallpaper-0.1/mkwallpaper.c mkwallpaper-0.1-1/mkwallpaper.c
--- mkwallpaper-0.1/mkwallpaper.c   2015-10-28 11:38:35.960599940 +1000
+++ mkwallpaper-0.1-1/mkwallpaper.c 2015-10-28 12:32:23.183828287 +1000
@@ -143,7 +143,7 @@ void paint_img (char *label,

    layout = pango_cairo_create_layout (c);
    pango_layout_set_font_description (layout, font_description);
-   pango_layout_set_width (layout, 9 * wdth / 10 * PANGO_SCALE);
+   pango_layout_set_width (layout, wdth / 2 * PANGO_SCALE);
    pango_layout_set_wrap (layout, PANGO_WRAP_WORD);
    pango_layout_set_text (layout, label, -1);
mavrothal commented 8 years ago

Go for it :+1:

01micko commented 8 years ago

I'll wait til Dima takes a look. :wink:

dimkr commented 8 years ago

Will do, when I get home.

---- On Wed, 28 Oct 2015 08:43:34 +0200 Mick Amadio <notifications@github.com> wrote ----

I'll wait til Dima takes a look.
— Reply to this email directly or view it on GitHub.

01micko commented 8 years ago

The C as far as the cairo gradients go could do with a bit more contrast; too subtle. Not a problem, I'll experiment with that after you take a look.

The colours in the 3builddistro hack could use a tweak too.

01micko commented 8 years ago

Oh, tested on tahrpup64 too, compiles and works fine.

01micko commented 8 years ago

Just looking, the destimage[80] should be destimage[160] or something. Also the corresponding sprintf() calls dont need the 'destimage[num] = ' bit either.

dimkr commented 8 years ago

Some coding style changes here and there - not perfect, but better than nothing.

/** This program is designed to be used in Puppy Linux.
 * It is designed to be used in Woof-CE or in a running Puppy as root or
 * an ordinary user.
 */

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/stat.h>
#include <limits.h>

#include <cairo-svg.h>
#include <pango/pangocairo.h>

#define PROG "mkwallpaper"
#define THIS_VERSION "0.1"

void usage(){
    printf("%s-%s\n\n", PROG , THIS_VERSION);
    printf("\tGenerate SVG or PNG Puppy Linux wallpapers. SVG is default.\n\n");
    printf("Usage :\n");
    printf("\t%s [-l, -n, -f, -p, -s, -x, -y, -r, -w, -h]\n", PROG);
    printf("\t-n\t: image name\n");
    printf("\t-l\t: label for an image, up to 100 chars\n");
    printf("\t-f\t: a TTF font family\n");
    printf("\t-p\t: \"png\" or \"svg\" format\n");
    printf("\t-x\t: width of image in pixels\n");
    printf("\t-y\t: height of image in pixel\n");
    printf("\t-z\t: floating point RGB, quoted, "
                    "space delimited values for colour (mandatory arg!)\n");
    printf("\t-w\t: \"woof\" FOR WOOF USE ONLY!!!\n");
    printf("\t-h\t: show this help and exit.\n");
    exit (EXIT_SUCCESS);
}

static const char *get_user_out_file(const char *ww){
    static char out_file[PATH_MAX];
    if (strncmp(ww, "woof", 4) == 0) {
        strcpy(out_file, "usr/share/backgrounds"); /*woof only */
    } else {
        char *my_home = getenv("HOME");
        if ((my_home != NULL) && (strcmp(my_home, "/root") == 0)) {
            strcpy(out_file, "/usr/share/backgrounds");
        } else {
            snprintf(out_file, sizeof(out_file), "%s/%s", my_home, ".local/share/backgrounds");
        }
    }
    mkdir(out_file, 0755);
    return out_file;
}

static void paint_img (const char *label,
                       const char *name,
                       const char *font,
                       const char *form,
                       const int wdth,
                       int hght,
                       const char *fp_color,
                       int f_size,
                       const char *woofy) {
    char destimg[PATH_MAX];

    if (!fp_color) exit (EXIT_FAILURE);

    int msg_len = strlen(label);
    if (msg_len > 20) {
        fprintf(stderr,"\"%s\" is too long!\n", label);
        exit (EXIT_FAILURE);
    }
    if (f_size == 20) f_size = hght / 10;

    float r, g , b;
    char red[6];
    char green[6];
    char blue[6];
    int len = strlen(fp_color);
    if (len > 31 ) {
        fprintf(stderr,"ERROR: colour argument too long\n");
        exit (EXIT_FAILURE);
    }
    int result = sscanf(fp_color, "%s %s %s", red, green, blue);
    if (result < 3) fprintf(stderr,"ERROR: less than 3 colour aguments!\n");

    r = atof(red);
    g = atof(green);
    b = atof(blue);
    if ((r > 0.85) || (g > 0.85) || (b > 0.85)) {
        fprintf(stderr, "Color values are too high\n");
        exit (EXIT_FAILURE);
    }
    float r1, g1, b1, r2, g2, b2;
    r1 = r; g1 = g; b1 = b;
    r2 = r + 0.15;
    g2 = g + 0.15;
    b2 = b + 0.15;

    cairo_surface_t *cs;

    if (strcmp(form, "svg") == 0) {
        snprintf(destimg, sizeof(destimg), "%s/%s.svg", get_user_out_file(woofy), name);
        cs = cairo_svg_surface_create(destimg, wdth, hght);

    } else {
        cs = cairo_image_surface_create
                            (CAIRO_FORMAT_ARGB32, wdth, hght);
        snprintf(destimg, sizeof(destimg), "%s/%s.png", get_user_out_file(woofy), name);
    }
    cairo_t *c;
    c = cairo_create(cs);

    cairo_rectangle(c, 0.0, 0.0, wdth, hght);
    cairo_pattern_t *linear = cairo_pattern_create_linear(0, 0, wdth, hght);
    cairo_pattern_add_color_stop_rgb(linear, 0, r1, g1, b1);
    cairo_pattern_add_color_stop_rgb(linear, 1, r2, g2, b2);
    cairo_set_source(c, linear);
    cairo_fill(c);

    PangoLayout *layout;
    PangoFontDescription *font_description;

    font_description = pango_font_description_new ();
    pango_font_description_set_family (font_description, font);
    pango_font_description_set_weight (font_description, PANGO_WEIGHT_BOLD);
    pango_font_description_set_style (font_description, PANGO_STYLE_OBLIQUE);
    pango_font_description_set_absolute_size (font_description, f_size * PANGO_SCALE);

    layout = pango_cairo_create_layout (c);
    pango_layout_set_font_description (layout, font_description);
    pango_layout_set_width (layout, wdth / 2 * PANGO_SCALE);
    pango_layout_set_wrap (layout, PANGO_WRAP_WORD);
    pango_layout_set_text (layout, label, -1);

    cairo_move_to(c, wdth / 2 , 4 * hght / 6);
    cairo_set_source_rgb(c, 0.0, 0.0, 0.0);
    pango_cairo_show_layout (c, layout);

    g_object_unref (layout);
    pango_font_description_free (font_description);
    if (strcmp(form, "png") == 0) {
        cairo_surface_write_to_png (cs, destimg);
    }
    cairo_surface_destroy(cs);
    cairo_destroy(c);
    printf("image saved to %s\n", destimg);
}

int main(int argc, char **argv) {
    if (argc < 2) {
        usage();
        return 0;
    }
    if (strcmp(argv[1], "-h") == 0) {
        usage();
        return 0;
    }

    char *lvalue = "hello mksvg!"; /* the cli string that appears in image */
    char *nvalue = "foo"; /* image name */
    char *fvalue = "Sans"; /* font */
    char *pvalue = "svg";
    char *wvalue = "notwoof"; /* used for woof */
    char *zvalue = NULL; /* fp colour */
    int width = 200; int height = 60;
    int font_size = 20;
    int c;
    while ((c = getopt (argc, argv, "l:n:f:p:x:y:w:z:s::")) != -1) {
        switch (c)
        {
            case 'l':
                lvalue = optarg;
                break;
            case 'n':
                nvalue = optarg;
                break;
            case 'f':
                fvalue = optarg;
                break;
            case 'p':
                pvalue = optarg;
                break;
            case 'x':
                width = atoi(optarg);
                break;
            case 'y':
                height = atoi(optarg);
                break;
            case 'w':
                wvalue = optarg;
                break;
            case 'z':
                zvalue = optarg;
                break;
            case 's':
                font_size = atoi(optarg);
                break;
            default:
                usage();
        }
    }
    if (zvalue == NULL) {
        fprintf(stderr, "You must have 3 floating point value argument \"-z\"\n");
        usage();
        return 1;
    }
    paint_img(lvalue, nvalue, fvalue, pvalue,
                        width, height, zvalue, font_size, wvalue);
    return 0;
}
CC?=cc
CFLAGS+=-Wall -pedantic -std=gnu99 $(shell pkg-config --cflags pangocairo)
LDFLAGS+=$(shell pkg-config --libs pangocairo)

all: mkwallpaper

mkwallpaper: mkwallpaper.o
    $(CC) -o $@ $^ $(LDFLAGS)

mkwallpaper.o: mkwallpaper.c
    $(CC) -o $@ $(CFLAGS) -c $^

clean:
    -rm -f *.o mkwallpaper
01micko commented 8 years ago

Thanks. :smile:

01micko commented 8 years ago

I found a couple of little bugs for spaces in names in wallpapers in the wallpaper-0.6.5 pet. Maybe it's time for this to go to rootfs-packages too?

dimkr commented 8 years ago

:+1:

01micko commented 8 years ago

mkwallpaper is out in the wild!

@dimkr - a call to it is included in 3builddistro_Z but I went for it on the running system rather than compiling on the fly (even though that should work for most). So if you at least build it and include it in your specs natural attrition will take care of it anyway. :tongue: