From f015c04d1e44c59ab650fe9f118bcf633833a150 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mirco=20M=C3=BCller?= Date: Tue, 6 Jul 2010 13:47:31 +0200 Subject: added some internal helpers for blurring, added more precise button-background rendering --- src/play-button.c | 402 ++++++++++++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 390 insertions(+), 12 deletions(-) (limited to 'src') diff --git a/src/play-button.c b/src/play-button.c index 76a8109..347a0bc 100644 --- a/src/play-button.c +++ b/src/play-button.c @@ -15,6 +15,8 @@ PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . + +Uses code from ctk */ #ifdef HAVE_CONFIG_H @@ -58,6 +60,227 @@ static void play_button_draw_previous_symbol(cairo_t* cr, double x, double y); G_DEFINE_TYPE (PlayButton, play_button, GTK_TYPE_DRAWING_AREA); +/// internal helper functions ////////////////////////////////////////////////// + +static double +_align (double val) +{ + double fract = val - (int) val; + + if (fract != 0.5f) + return (double) ((int) val + 0.5f); + else + return val; +} + +static inline void +_blurinner (guchar* pixel, + gint* zR, + gint* zG, + gint* zB, + gint* zA, + gint alpha, + gint aprec, + gint zprec) +{ + gint R; + gint G; + gint B; + guchar A; + + R = *pixel; + G = *(pixel + 1); + B = *(pixel + 2); + A = *(pixel + 3); + + *zR += (alpha * ((R << zprec) - *zR)) >> aprec; + *zG += (alpha * ((G << zprec) - *zG)) >> aprec; + *zB += (alpha * ((B << zprec) - *zB)) >> aprec; + *zA += (alpha * ((A << zprec) - *zA)) >> aprec; + + *pixel = *zR >> zprec; + *(pixel + 1) = *zG >> zprec; + *(pixel + 2) = *zB >> zprec; + *(pixel + 3) = *zA >> zprec; +} + +static inline void +_blurrow (guchar* pixels, + gint width, + gint height, + gint channels, + gint line, + gint alpha, + gint aprec, + gint zprec) +{ + gint zR; + gint zG; + gint zB; + gint zA; + gint index; + guchar* scanline; + + scanline = &(pixels[line * width * channels]); + + zR = *scanline << zprec; + zG = *(scanline + 1) << zprec; + zB = *(scanline + 2) << zprec; + zA = *(scanline + 3) << zprec; + + for (index = 0; index < width; index ++) + _blurinner (&scanline[index * channels], + &zR, + &zG, + &zB, + &zA, + alpha, + aprec, + zprec); + + for (index = width - 2; index >= 0; index--) + _blurinner (&scanline[index * channels], + &zR, + &zG, + &zB, + &zA, + alpha, + aprec, + zprec); +} + +static inline void +_blurcol (guchar* pixels, + gint width, + gint height, + gint channels, + gint x, + gint alpha, + gint aprec, + gint zprec) +{ + gint zR; + gint zG; + gint zB; + gint zA; + gint index; + guchar* ptr; + + ptr = pixels; + + ptr += x * channels; + + zR = *((guchar*) ptr ) << zprec; + zG = *((guchar*) ptr + 1) << zprec; + zB = *((guchar*) ptr + 2) << zprec; + zA = *((guchar*) ptr + 3) << zprec; + + for (index = width; index < (height - 1) * width; index += width) + _blurinner ((guchar*) &ptr[index * channels], + &zR, + &zG, + &zB, + &zA, + alpha, + aprec, + zprec); + + for (index = (height - 2) * width; index >= 0; index -= width) + _blurinner ((guchar*) &ptr[index * channels], + &zR, + &zG, + &zB, + &zA, + alpha, + aprec, + zprec); +} + +void +_expblur (guchar* pixels, + gint width, + gint height, + gint channels, + gint radius, + gint aprec, + gint zprec) +{ + gint alpha; + gint row = 0; + gint col = 0; + + if (radius < 1) + return; + + // calculate the alpha such that 90% of + // the kernel is within the radius. + // (Kernel extends to infinity) + alpha = (gint) ((1 << aprec) * (1.0f - expf (-2.3f / (radius + 1.f)))); + + for (; row < height; row++) + _blurrow (pixels, + width, + height, + channels, + row, + alpha, + aprec, + zprec); + + for(; col < width; col++) + _blurcol (pixels, + width, + height, + channels, + col, + alpha, + aprec, + zprec); + + return; +} + +void +_surface_blur (cairo_surface_t* surface, + guint radius) +{ + guchar* pixels; + guint width; + guint height; + cairo_format_t format; + + // before we mess with the surface execute any pending drawing + cairo_surface_flush (surface); + + pixels = cairo_image_surface_get_data (surface); + width = cairo_image_surface_get_width (surface); + height = cairo_image_surface_get_height (surface); + format = cairo_image_surface_get_format (surface); + + switch (format) + { + case CAIRO_FORMAT_ARGB32: + _expblur (pixels, width, height, 4, radius, 16, 7); + break; + + case CAIRO_FORMAT_RGB24: + _expblur (pixels, width, height, 3, radius, 16, 7); + break; + + case CAIRO_FORMAT_A8: + _expblur (pixels, width, height, 1, radius, 16, 7); + break; + + default : + // do nothing + break; + } + + // inform cairo we altered the surfaces contents + cairo_surface_mark_dirty (surface); +} + +/// GObject functions ////////////////////////////////////////////////////////// static void play_button_class_init (PlayButtonClass *klass) @@ -97,7 +320,7 @@ static gboolean play_button_expose (GtkWidget *button, GdkEventExpose *event) { cairo_t *cr; - cr = gdk_cairo_create (button->window); + cr = gdk_cairo_create (button->window); g_debug("PlayButton::Draw - width = %i", button->allocation.width); g_debug("PlayButton::Draw - event->area.width = %i", event->area.width); @@ -109,7 +332,7 @@ play_button_expose (GtkWidget *button, GdkEventExpose *event) cairo_clip(cr); draw (button, cr); - cairo_destroy (cr); + cairo_destroy (cr); return FALSE; } @@ -126,34 +349,189 @@ play_button_set_style(GtkWidget* button, GtkStyle* style) } static void -draw (GtkWidget* button, cairo_t *cr) +draw_gradient (cairo_t* cr, + double x, + double y, + double w, + double r, + double* rgba_start, + double* rgba_end) { + cairo_pattern_t* pattern = NULL; + cairo_move_to (cr, x, y); + cairo_line_to (cr, x + w - 2.0f * r, y); + cairo_arc (cr, + x + w - 2.0f * r, + y + r, + r, + -90.0f * G_PI / 180.0f, + 90.0f * G_PI / 180.0f); + cairo_line_to (cr, x, y + 2.0f * r); + cairo_arc (cr, + x, + y + r, + r, + 90.0f * G_PI / 180.0f, + 270.0f * G_PI / 180.0f); + cairo_close_path (cr); + + pattern = cairo_pattern_create_linear (x, y, x, y + 2.0f * r); + cairo_pattern_add_color_stop_rgba (pattern, + 0.0f, + rgba_start[0], + rgba_start[1], + rgba_start[2], + rgba_start[3]); + cairo_pattern_add_color_stop_rgba (pattern, + 1.0f, + rgba_end[0], + rgba_end[1], + rgba_end[2], + rgba_end[3]); + cairo_set_source (cr, pattern); + cairo_fill (cr); + cairo_pattern_destroy (pattern); +} + +static void +draw_circle (cairo_t* cr, + double x, + double y, + double r, + double* rgba_start, + double* rgba_end) +{ + cairo_pattern_t* pattern = NULL; + + cairo_move_to (cr, x, y); + cairo_arc (cr, + x + r, + y + r, + r, + 0.0f * G_PI / 180.0f, + 360.0f * G_PI / 180.0f); + + pattern = cairo_pattern_create_linear (x, y, x, y + 2.0f * r); + cairo_pattern_add_color_stop_rgba (pattern, + 0.0f, + rgba_start[0], + rgba_start[1], + rgba_start[2], + rgba_start[3]); + cairo_pattern_add_color_stop_rgba (pattern, + 1.0f, + rgba_end[0], + rgba_end[1], + rgba_end[2], + rgba_end[3]); + cairo_set_source (cr, pattern); + cairo_fill (cr); + cairo_pattern_destroy (pattern); +} + +static void +draw (GtkWidget* button, cairo_t *cr) +{ //PlayButtonPrivate* priv = PLAY_BUTTON_GET_PRIVATE(button); - double rect_width = 115; - double rect_height = 28; - double p_radius = 21; + double rect_width = 130; double y = 15; double x = 22; + double inner_height = 25.0f; + double inner_radius = 12.5f; + double inner_start[] = {229.0f / 255.0f, + 223.0f / 255.0f, + 215.0f / 255.0f, + 1.0f}; + double inner_end[] = {183.0f / 255.0f, + 178.0f / 255.0f, + 172.0f / 255.0f, + 1.0f}; + double middle_height = 27.0f; + double middle_radius = 13.5f; + double middle_start[] = {61.0f / 255.0f, + 60.0f / 255.0f, + 57.0f / 255.0f, + 1.0f}; + double middle_end[] = {94.0f / 255.0f, + 93.0f / 255.0f, + 90.0f / 255.0f, + 1.0f}; + double outter_height = 29.0f; + double outter_radius = 14.5f; + double outter_start[] = {36.0f / 255.0f, + 35.0f / 255.0f, + 33.0f / 255.0f, + 1.0f}; + double outter_end[] = {123.0f / 255.0f, + 123.0f / 255.0f, + 120.0f / 255.0f, + 1.0f}; + + double circle_radius = 19.0f; + //double radius=35; //double x= button->allocation.width/2 - rect_width/2; //double y= button->allocation.height/2 -rect_height/2; + // ffwd/back-background + draw_gradient (cr, + x, + y, + rect_width, + outter_radius, + outter_start, + outter_end); + draw_gradient (cr, + x, + y + 1, + rect_width - 2, + middle_radius, + middle_start, + middle_end); + draw_gradient (cr, + x, + y + 2, + rect_width - 4, + inner_radius, + inner_start, + inner_end); + + // play/pause-background + draw_circle (cr, + x + rect_width / 2.0f - 2.0f * outter_radius - 4.5f, + y - ((circle_radius - outter_radius)), + circle_radius, + outter_start, + outter_end); + draw_circle (cr, + x + rect_width / 2.0f - 2.0f * outter_radius - 4.5f + 1.0f, + y - ((circle_radius - outter_radius)) + 1.0f, + circle_radius - 1, + middle_start, + middle_end); + draw_circle (cr, + x + rect_width / 2.0f - 2.0f * outter_radius - 4.5f + 2.0f, + y - ((circle_radius - outter_radius)) + 2.0f, + circle_radius - 2.0f, + inner_start, + inner_end); + // Draw the outside drop shadow background - play_button_draw_background_shadow_1(button, cr, x, y, rect_width, rect_height, p_radius); + //play_button_draw_background_shadow_1(button, cr, x, y, rect_width, rect_height, p_radius); // Draw the inside drop shadow background - gint offset = 4; - play_button_draw_background_shadow_2(button, cr, x + offset-1, y + offset/2, rect_width-offset, rect_height-offset, p_radius-(offset/2)); + /*gint offset = 4; + play_button_draw_background_shadow_2(button, cr, x + offset-1, y + offset/2, rect_width-offset, rect_height-offset, p_radius-(offset/2));*/ - offset = 5; + //offset = 5; // Draw the inside actual background - play_button_draw_background(button, cr, x+offset-1, y + offset/2+1, rect_width-offset, rect_height-offset, p_radius-offset/2); + /*play_button_draw_background(button, cr, x+offset-1, y + offset/2+1, rect_width-offset, rect_height-offset, p_radius-offset/2); play_button_draw_pause_symbol(cr, rect_width/2 + rect_height/10 + x -1 + offset/2, rect_height/5 +y ); play_button_draw_pause_symbol(cr, rect_width/2 + rect_height/10 + x + offset/2 + 10, rect_height/5 +y ); - play_button_draw_previous_symbol(cr, x+rect_height/2 + offset, y + offset+2); + play_button_draw_previous_symbol(cr, x+rect_height/2 + offset, y + offset+2);*/ cairo_surface_write_to_png(cairo_get_target (cr), "/tmp/foobar.png"); } -- cgit v1.2.3 From 9ec9e3fa570d0208c6409b13103bcd558f2b61a8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mirco=20M=C3=BCller?= Date: Wed, 7 Jul 2010 03:46:29 +0200 Subject: finished the rendering of the custom widget --- src/play-button.c | 467 +++++++++++++++++++++++++++++++++--------------------- 1 file changed, 288 insertions(+), 179 deletions(-) (limited to 'src') diff --git a/src/play-button.c b/src/play-button.c index 347a0bc..3c5b120 100644 --- a/src/play-button.c +++ b/src/play-button.c @@ -3,6 +3,7 @@ Copyright 2010 Canonical Ltd. Authors: Conor Curran + Mirco Müller This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License version 3, as published @@ -430,6 +431,147 @@ draw_circle (cairo_t* cr, cairo_pattern_destroy (pattern); } +static void +_setup (cairo_t** cr, + cairo_surface_t** surf, + gint width, + gint height) +{ + if (!cr || !surf) + return; + + *surf = cairo_image_surface_create (CAIRO_FORMAT_ARGB32, width, height); + *cr = cairo_create (*surf); + cairo_scale (*cr, 1.0f, 1.0f); + cairo_set_operator (*cr, CAIRO_OPERATOR_CLEAR); + cairo_paint (*cr); + cairo_set_operator (*cr, CAIRO_OPERATOR_OVER); +} + +static void +_mask_prev (cairo_t* cr, + double x, + double y, + double tri_width, + double tri_height, + double tri_offset) +{ + if (!cr) + return; + + cairo_move_to (cr, x, y + tri_height / 2.0f); + cairo_line_to (cr, x + tri_width, y); + cairo_line_to (cr, x + tri_width, y + tri_height); + x += tri_offset; + cairo_move_to (cr, x, y + tri_height / 2.0f); + cairo_line_to (cr, x + tri_width, y); + cairo_line_to (cr, x + tri_width, y + tri_height); + x -= tri_offset; + cairo_rectangle (cr, x, y, 2.5f, tri_height); + cairo_close_path (cr); +} + +static void +_mask_next (cairo_t* cr, + double x, + double y, + double tri_width, + double tri_height, + double tri_offset) +{ + if (!cr) + return; + + cairo_move_to (cr, x, y); + cairo_line_to (cr, x + tri_width, y + tri_height / 2.0f); + cairo_line_to (cr, x, y + tri_height); + x += tri_offset; + cairo_move_to (cr, x, y); + cairo_line_to (cr, x + tri_width, y + tri_height / 2.0f); + cairo_line_to (cr, x, y + tri_height); + x -= tri_offset; + x += 2.0f * tri_width - tri_offset - 1.0f; + cairo_rectangle (cr, x, y, 2.5f, tri_height); + + cairo_close_path (cr); +} + +static void +_mask_pause (cairo_t* cr, + double x, + double y, + double bar_width, + double bar_height, + double bar_offset) +{ + if (!cr) + return; + + cairo_set_line_width (cr, bar_width); + cairo_set_line_cap (cr, CAIRO_LINE_CAP_ROUND); + + x += bar_width; + y += bar_width; + cairo_move_to (cr, x, y); + cairo_line_to (cr, x, y + bar_height); + cairo_move_to (cr, x + bar_offset, y); + cairo_line_to (cr, x + bar_offset, y + bar_height); + + //cairo_close_path (cr); +} + +static void +_fill (cairo_t* cr, + double x_start, + double y_start, + double x_end, + double y_end, + double* rgba_start, + double* rgba_end, + gboolean stroke) +{ + cairo_pattern_t* pattern = NULL; + + if (!cr || !rgba_start || !rgba_end) + return; + + pattern = cairo_pattern_create_linear (x_start, y_start, x_end, y_end); + cairo_pattern_add_color_stop_rgba (pattern, + 0.0f, + rgba_start[0], + rgba_start[1], + rgba_start[2], + rgba_start[3]); + cairo_pattern_add_color_stop_rgba (pattern, + 1.0f, + rgba_end[0], + rgba_end[1], + rgba_end[2], + rgba_end[3]); + cairo_set_source (cr, pattern); + if (stroke) + cairo_stroke (cr); + else + cairo_fill (cr); + cairo_pattern_destroy (pattern); +} + +static void +_finalize (cairo_t* cr, + cairo_t** cr_surf, + cairo_surface_t** surf, + double x, + double y) +{ + if (!cr || !cr_surf || !surf) + return; + + cairo_set_source_surface (cr, *surf, x, y); + cairo_paint (cr); + cairo_surface_destroy (*surf); + cairo_destroy (*cr_surf); +} + static void draw (GtkWidget* button, cairo_t *cr) { @@ -470,11 +612,40 @@ draw (GtkWidget* button, cairo_t *cr) double circle_radius = 19.0f; - //double radius=35; - //double x= button->allocation.width/2 - rect_width/2; - //double y= button->allocation.height/2 -rect_height/2; - - // ffwd/back-background + double button_start[] = {252.0f / 255.0f, + 251.0f / 255.0f, + 251.0f / 255.0f, + 1.0f}; + double button_end[] = {186.0f / 255.0f, + 180.0f / 255.0f, + 170.0f / 255.0f, + 1.0f}; + double button_shadow[] = {0.0f / 255.0f, + 0.0f / 255.0f, + 0.0f / 255.0f, + 0.75f}; + double prev_width = 25.0f; + double prev_height = 17.0f; + double next_width = prev_width; + double next_height = prev_height; + cairo_surface_t* surf = NULL; + cairo_t* cr_surf = NULL; + double tri_width = 11.0f; + double tri_height = 13.0f; + double tri_offset = 6.0f; + double prev_x = 20.0f; + double prev_y = 21.0f; + double next_x = 98.0f; + double next_y = prev_y; + double pause_width = 21.0f; + double pause_height = 27.0f; + double bar_width = 4.5f; + double bar_height = 24.0f; + double bar_offset = 10.0f; + double pause_x = 62.0f; + double pause_y = 15.0f; + + // prev/next-background draw_gradient (cr, x, y, @@ -517,182 +688,120 @@ draw (GtkWidget* button, cairo_t *cr) inner_start, inner_end); - // Draw the outside drop shadow background - //play_button_draw_background_shadow_1(button, cr, x, y, rect_width, rect_height, p_radius); - - // Draw the inside drop shadow background - /*gint offset = 4; - play_button_draw_background_shadow_2(button, cr, x + offset-1, y + offset/2, rect_width-offset, rect_height-offset, p_radius-(offset/2));*/ - - //offset = 5; - // Draw the inside actual background - /*play_button_draw_background(button, cr, x+offset-1, y + offset/2+1, rect_width-offset, rect_height-offset, p_radius-offset/2); - - play_button_draw_pause_symbol(cr, rect_width/2 + rect_height/10 + x -1 + offset/2, rect_height/5 +y ); - - play_button_draw_pause_symbol(cr, rect_width/2 + rect_height/10 + x + offset/2 + 10, rect_height/5 +y ); - play_button_draw_previous_symbol(cr, x+rect_height/2 + offset, y + offset+2);*/ - cairo_surface_write_to_png(cairo_get_target (cr), "/tmp/foobar.png"); -} - -static void -play_button_draw_previous_symbol(cairo_t* cr, double x, double y) -{ - gint line_width = 2; - cairo_set_line_width (cr, line_width); - gint shape_height = 15; - gint shape_width = 22; - gint single_arrow_width=16; - - cairo_pattern_t *pat; - pat = cairo_pattern_create_linear (x, y, x, y+shape_height); - - cairo_pattern_add_color_stop_rgb(pat, 0, 227/255.0, 222/255.0, 214/255.0); - cairo_pattern_add_color_stop_rgb(pat, .1, 207/255.0, 201/255.0, 190/255.0); - cairo_pattern_add_color_stop_rgb(pat, .4, 123/255.0, 123/255.0, 120/255.0); - cairo_set_source (cr, pat); - - cairo_move_to(cr, x, y); - cairo_rel_line_to (cr, 0, shape_height); - cairo_stroke(cr); - - cairo_move_to (cr, x+line_width, y+shape_height/2); - cairo_line_to (cr, x+single_arrow_width, y); - cairo_line_to (cr, x+single_arrow_width, y+shape_height); - cairo_line_to (cr, x+line_width, y+shape_height/2); - cairo_fill(cr); - - cairo_pattern_destroy (pat); - cairo_close_path(cr); -} - -static void -play_button_draw_pause_symbol(cairo_t* cr, double x, double y) -{ - cairo_set_line_width (cr, 7); - cairo_set_line_cap (cr, CAIRO_LINE_CAP_ROUND); - cairo_move_to (cr, x, y); - cairo_rel_line_to (cr, 0, 18); - //cairo_set_source_rgb(cr, 94/255.0, 93/255.0, 90/255.0); - - cairo_pattern_t *pat; - pat = cairo_pattern_create_linear (x, y, x, y+16); - cairo_pattern_add_color_stop_rgb(pat, 0, 227/255.0, 222/255.0, 214/255.0); - cairo_pattern_add_color_stop_rgb(pat, .1, 207/255.0, 201/255.0, 190/255.0); - cairo_pattern_add_color_stop_rgb(pat, .6, 123/255.0, 123/255.0, 120/255.0); - cairo_set_source (cr, pat); - cairo_stroke(cr); - cairo_close_path(cr); - - cairo_set_line_width (cr, 5.5); - cairo_set_line_cap (cr, CAIRO_LINE_CAP_ROUND); - cairo_move_to (cr, x, y+0.75); - cairo_rel_line_to (cr, 0, 16.5); - - pat = cairo_pattern_create_linear (x+1, y+1, x+1, y+16); - cairo_pattern_add_color_stop_rgb(pat, .3, 252/255.0, 252/255.0, 251/255.0); - cairo_pattern_add_color_stop_rgb(pat, .8, 227/255.0, 222/255.0, 214/255.0); - //cairo_pattern_add_color_stop_rgb(pat, .9, 207/255.0, 201/255.0, 190/255.0); - cairo_set_source (cr, pat); - cairo_stroke(cr); - cairo_close_path(cr); - - cairo_pattern_destroy (pat); -} - -static void -play_button_draw_background(GtkWidget* button, cairo_t* cr, double x, double y, double rect_width, double rect_height, double p_radius) -{ - double radius=rect_height/2; - cairo_set_line_width (cr, rect_height); - cairo_set_line_cap (cr, CAIRO_LINE_CAP_ROUND); - cairo_move_to(cr, x+radius, y+radius); - cairo_line_to(cr, x+rect_width, y+radius); - - cairo_pattern_t *pat; - pat = cairo_pattern_create_linear (x, y, x, y+rect_height); - cairo_pattern_add_color_stop_rgb(pat, .5, 225/255.0, 218/255.0, 211/255.0); - cairo_pattern_add_color_stop_rgb(pat, .7, 197/255.0, 192/255.0, 185/255.0); - cairo_pattern_add_color_stop_rgb(pat, .9, 185/255.0, 179/255.0, 173/255.0); - cairo_set_source (cr, pat); - cairo_stroke (cr); - - cairo_close_path(cr); - cairo_arc(cr, rect_width/2 + radius/2 + x + 2, rect_height/2 +y, p_radius, 0, 2*M_PI); - cairo_set_source (cr, pat); - cairo_fill(cr); - - cairo_close_path(cr); - cairo_arc(cr, rect_width/2 + radius/2 + x + 2, rect_height/2 +y, p_radius, 0, 2*M_PI); - cairo_set_source_rgb(cr, 94/255.0, 93/255.0, 90/255.0); - cairo_set_line_width (cr, 0.75); - cairo_stroke(cr); - cairo_close_path(cr); - cairo_pattern_destroy (pat); -} - -static void -play_button_draw_background_shadow_1(GtkWidget* button, cairo_t* cr, double x, double y, double rect_width, double rect_height, double p_radius) -{ - double radius=rect_height/2; - - cairo_set_line_width (cr, rect_height); - cairo_set_line_cap (cr, CAIRO_LINE_CAP_ROUND); - cairo_move_to(cr, x+radius, y+radius); - cairo_line_to(cr, x+rect_width, y+radius); - - cairo_pattern_t *pat; - pat = cairo_pattern_create_linear (x, y, x, y+rect_height); - cairo_pattern_add_color_stop_rgb(pat, .4, 36/255.0, 35/255.0, 33/255.0); - cairo_pattern_add_color_stop_rgb(pat, .7, 123/255.0, 123/255.0, 120/255.0); - cairo_set_source (cr, pat); - cairo_stroke (cr); - - cairo_close_path(cr); - cairo_arc(cr, rect_width/2 + radius/2 + x + 2, rect_height/2 +y, p_radius, 0, 2*M_PI); - pat = cairo_pattern_create_linear ((rect_width/2 + radius/2 + x), rect_height/2 + y-p_radius, (rect_width/2 + radius/2 + x), rect_height+(p_radius-rect_height/2)); - cairo_pattern_add_color_stop_rgb(pat, .4, 36/255.0, 35/255.0, 33/255.0); - cairo_pattern_add_color_stop_rgb(pat, .7, 123/255.0, 123/255.0, 120/255.0); - cairo_set_source (cr, pat); - cairo_fill(cr); - cairo_close_path(cr); - cairo_pattern_destroy (pat); - -} - -static void -play_button_draw_background_shadow_2(GtkWidget* button, cairo_t* cr, double x, double y, double rect_width, double rect_height, double p_radius) -{ - double radius=rect_height/2; - - cairo_set_line_width (cr, rect_height); - cairo_set_line_cap (cr, CAIRO_LINE_CAP_ROUND); - cairo_move_to(cr, x+radius, y+radius); - cairo_line_to(cr, x+rect_width, y+radius); - - cairo_pattern_t *pat; - pat = cairo_pattern_create_linear (x, y, x, y+rect_height); - cairo_pattern_add_color_stop_rgb(pat, .4, 61/255.0, 60/255.0, 57/255.0); - cairo_pattern_add_color_stop_rgb(pat, .7, 94/255.0, 93/255.0, 90/255.0); - cairo_set_source (cr, pat); - cairo_stroke (cr); - - cairo_close_path(cr); - cairo_arc(cr, rect_width/2 + radius/2 + x + 2, rect_height/2 +y, p_radius, 0, 2*M_PI); - pat = cairo_pattern_create_linear ((rect_width/2 + radius/2 + x), rect_height/2 + y-p_radius, (rect_width/2 + radius/2 + x), rect_height+(p_radius-rect_height/2)); - cairo_pattern_add_color_stop_rgb(pat, .4, 61/255.0, 60/255.0, 57/255.0); - cairo_pattern_add_color_stop_rgb(pat, .7, 94/255.0, 93/255.0, 90/255.0); - - cairo_set_source (cr, pat); - cairo_fill(cr); - cairo_close_path(cr); - cairo_pattern_destroy (pat); - + // draw previous-button drop-shadow + _setup (&cr_surf, &surf, prev_width, prev_height); + _mask_prev (cr_surf, + (prev_width - (2.0f * tri_width - tri_offset)) / 2.0f, + (prev_height - tri_height) / 2.0f, + tri_width, + tri_height, + tri_offset); + _fill (cr_surf, + (prev_width - (2.0f * tri_width - tri_offset)) / 2.0f, + (prev_height - tri_height) / 2.0f, + (prev_width - (2.0f * tri_width - tri_offset)) / 2.0f, + (double) tri_height, + button_shadow, + button_shadow, + FALSE); + _surface_blur (surf, 1); + _finalize (cr, &cr_surf, &surf, prev_x, prev_y + 1.0f); + + // draw previous-button + _setup (&cr_surf, &surf, prev_width, prev_height); + _mask_prev (cr_surf, + (prev_width - (2.0f * tri_width - tri_offset)) / 2.0f, + (prev_height - tri_height) / 2.0f, + tri_width, + tri_height, + tri_offset); + _fill (cr_surf, + (prev_width - (2.0f * tri_width - tri_offset)) / 2.0f, + (prev_height - tri_height) / 2.0f, + (prev_width - (2.0f * tri_width - tri_offset)) / 2.0f, + (double) tri_height, + button_start, + button_end, + FALSE); + _finalize (cr, &cr_surf, &surf, prev_x, prev_y); + + // draw next-button drop-shadow + _setup (&cr_surf, &surf, next_width, next_height); + _mask_next (cr_surf, + (next_width - (2.0f * tri_width - tri_offset)) / 2.0f, + (next_height - tri_height) / 2.0f, + tri_width, + tri_height, + tri_offset); + _fill (cr_surf, + (next_width - (2.0f * tri_width - tri_offset)) / 2.0f, + (next_height - tri_height) / 2.0f, + (next_width - (2.0f * tri_width - tri_offset)) / 2.0f, + (double) tri_height, + button_shadow, + button_shadow, + FALSE); + _surface_blur (surf, 1); + _finalize (cr, &cr_surf, &surf, next_x, next_y + 1.0f); + + // draw next-button + _setup (&cr_surf, &surf, next_width, next_height); + _mask_next (cr_surf, + (next_width - (2.0f * tri_width - tri_offset)) / 2.0f, + (next_height - tri_height) / 2.0f, + tri_width, + tri_height, + tri_offset); + _fill (cr_surf, + (next_width - (2.0f * tri_width - tri_offset)) / 2.0f, + (next_height - tri_height) / 2.0f, + (next_width - (2.0f * tri_width - tri_offset)) / 2.0f, + (double) tri_height, + button_start, + button_end, + FALSE); + _finalize (cr, &cr_surf, &surf, next_x, next_y); + + // draw pause-button drop-shadow + _setup (&cr_surf, &surf, pause_width, pause_height); + _mask_pause (cr_surf, + (pause_width - (2.0f * bar_width + bar_offset)) / 2.0f, + (pause_height - bar_height) / 2.0f, + bar_width, + bar_height - 2.0f * bar_width, + bar_offset); + _fill (cr_surf, + (pause_width - (2.0f * bar_width + bar_offset)) / 2.0f, + (pause_height - bar_height) / 2.0f, + (pause_width - (2.0f * bar_width + bar_offset)) / 2.0f, + (double) bar_height, + button_shadow, + button_shadow, + TRUE); + _surface_blur (surf, 1); + _finalize (cr, &cr_surf, &surf, pause_x, pause_y + 1.0f); + + // draw pause-button + _setup (&cr_surf, &surf, pause_width, pause_height); + _mask_pause (cr_surf, + (pause_width - (2.0f * bar_width + bar_offset)) / 2.0f, + (pause_height - bar_height) / 2.0f, + bar_width, + bar_height - 2.0f * bar_width, + bar_offset); + _fill (cr_surf, + (pause_width - (2.0f * bar_width + bar_offset)) / 2.0f, + (pause_height - bar_height) / 2.0f, + (pause_width - (2.0f * bar_width + bar_offset)) / 2.0f, + (double) bar_height, + button_start, + button_end, + TRUE); + _finalize (cr, &cr_surf, &surf, pause_x, pause_y); + + cairo_surface_write_to_png (cairo_get_target (cr), "/tmp/foobar.png"); } - - - /** * play_button_new: * @returns: a new #PlayButton. -- cgit v1.2.3