Commit 0297f9a0 authored by Jonathan Blandford's avatar Jonathan Blandford Committed by Jonathan Blandford
Browse files

add the doc shooter to the docs dir as an uninstalled helper tool.

Mon Aug 23 17:19:19 2004  Jonathan Blandford  <jrb@redhat.com>

        * configure.in:
        * docs/tools/Makefile.am (clean-local): add the doc shooter to the
        docs dir as an uninstalled helper tool.
parent 945bcade
Mon Aug 23 17:19:19 2004 Jonathan Blandford <jrb@redhat.com>
* configure.in:
* docs/tools/Makefile.am (clean-local): add the doc shooter to the
docs dir as an uninstalled helper tool.
2004-08-23 Matthias Clasen <mclasen@redhat.com>
* gdk/x11/gdkwindow-x11.c (show_window_internal): Make it compile.
......
Mon Aug 23 17:19:19 2004 Jonathan Blandford <jrb@redhat.com>
* configure.in:
* docs/tools/Makefile.am (clean-local): add the doc shooter to the
docs dir as an uninstalled helper tool.
2004-08-23 Matthias Clasen <mclasen@redhat.com>
* gdk/x11/gdkwindow-x11.c (show_window_internal): Make it compile.
......
Mon Aug 23 17:19:19 2004 Jonathan Blandford <jrb@redhat.com>
* configure.in:
* docs/tools/Makefile.am (clean-local): add the doc shooter to the
docs dir as an uninstalled helper tool.
2004-08-23 Matthias Clasen <mclasen@redhat.com>
* gdk/x11/gdkwindow-x11.c (show_window_internal): Make it compile.
......
Mon Aug 23 17:19:19 2004 Jonathan Blandford <jrb@redhat.com>
* configure.in:
* docs/tools/Makefile.am (clean-local): add the doc shooter to the
docs dir as an uninstalled helper tool.
2004-08-23 Matthias Clasen <mclasen@redhat.com>
* gdk/x11/gdkwindow-x11.c (show_window_internal): Make it compile.
......
......@@ -1601,6 +1601,7 @@ docs/reference/gdk/version.xml
docs/reference/gtk/Makefile
docs/reference/gtk/version.xml
docs/faq/Makefile
docs/tools/Makefile
docs/tutorial/Makefile
gdk-pixbuf/Makefile
gdk-pixbuf/gdk_pixbuf.rc
......
## Process this file with automake to produce Makefile.in
SUBDIRS = tutorial faq reference
SUBDIRS = tutorial faq reference tools
EXTRA_DIST = \
defsformat.txt \
......
Makefile
Makefile.in
doc-shooter
INCLUDES = \
-I$(top_srcdir) \
-I$(top_builddir)/gdk \
-I$(top_srcdir)/gdk \
-I$(top_srcdir)/gdk/x11 \
$(GTK_DEBUG_FLAGS) \
$(GTK_DEP_CFLAGS)
DEPS = \
$(top_builddir)/gdk-pixbuf/libgdk_pixbuf-$(GTK_API_VERSION).la \
$(top_builddir)/gdk/$(gdktargetlib) \
$(top_builddir)/gtk/$(gtktargetlib)
LDADDS = \
$(top_builddir)/gdk-pixbuf/libgdk_pixbuf-$(GTK_API_VERSION).la \
$(top_builddir)/gdk/$(gdktargetlib) \
$(top_builddir)/gtk/$(gtktargetlib)
noinst_PROGRAMS = \
doc-shooter
doc_shooter_DEPENDENCIES = $(DEPS)
doc_shooter_LDADD = $(LDADDS)
doc_shooter_SOURCES= \
shadow.c \
shadow.h \
shooter.c \
widgets.c \
widgets.h
clean-local:
rm -f *.png
#include "shadow.h"
#include <math.h>
#define BLUR_RADIUS 5
#define SHADOW_OFFSET (BLUR_RADIUS * 4 / 5)
#define SHADOW_OPACITY 0.75
typedef struct {
int size;
double *data;
} ConvFilter;
static double
gaussian (double x, double y, double r)
{
return ((1 / (2 * M_PI * r)) *
exp ((- (x * x + y * y)) / (2 * r * r)));
}
static ConvFilter *
create_blur_filter (int radius)
{
ConvFilter *filter;
int x, y;
double sum;
filter = g_new0 (ConvFilter, 1);
filter->size = radius * 2 + 1;
filter->data = g_new (double, filter->size * filter->size);
sum = 0.0;
for (y = 0 ; y < filter->size; y++)
{
for (x = 0 ; x < filter->size; x++)
{
sum += filter->data[y * filter->size + x] = gaussian (x - (filter->size >> 1),
y - (filter->size >> 1),
radius);
}
}
for (y = 0; y < filter->size; y++)
{
for (x = 0; x < filter->size; x++)
{
filter->data[y * filter->size + x] /= sum;
}
}
return filter;
}
static GdkPixbuf *
create_shadow (GdkPixbuf *src)
{
int x, y, i, j;
int width, height;
GdkPixbuf *dest;
static ConvFilter *filter = NULL;
int src_rowstride, dest_rowstride;
int src_bpp, dest_bpp;
guchar *src_pixels, *dest_pixels;
if (!filter)
filter = create_blur_filter (BLUR_RADIUS);
width = gdk_pixbuf_get_width (src) + BLUR_RADIUS * 2 + SHADOW_OFFSET;
height = gdk_pixbuf_get_height (src) + BLUR_RADIUS * 2 + SHADOW_OFFSET;
dest = gdk_pixbuf_new (gdk_pixbuf_get_colorspace (src),
gdk_pixbuf_get_has_alpha (src),
gdk_pixbuf_get_bits_per_sample (src),
width, height);
gdk_pixbuf_fill (dest, 0);
src_pixels = gdk_pixbuf_get_pixels (src);
src_rowstride = gdk_pixbuf_get_rowstride (src);
src_bpp = gdk_pixbuf_get_has_alpha (src) ? 4 : 3;
dest_pixels = gdk_pixbuf_get_pixels (dest);
dest_rowstride = gdk_pixbuf_get_rowstride (dest);
dest_bpp = gdk_pixbuf_get_has_alpha (dest) ? 4 : 3;
for (y = 0; y < height; y++)
{
for (x = 0; x < width; x++)
{
int sumr = 0, sumg = 0, sumb = 0, suma = 0;
for (i = 0; i < filter->size; i++)
{
for (j = 0; j < filter->size; j++)
{
int src_x, src_y;
src_y = -(BLUR_RADIUS + SHADOW_OFFSET) + y - (filter->size >> 1) + i;
src_x = -(BLUR_RADIUS + SHADOW_OFFSET) + x - (filter->size >> 1) + j;
if (src_y < 0 || src_y > gdk_pixbuf_get_height (src) ||
src_x < 0 || src_x > gdk_pixbuf_get_width (src))
continue;
sumr += src_pixels [src_y * src_rowstride +
src_x * src_bpp + 0] *
filter->data [i * filter->size + j];
sumg += src_pixels [src_y * src_rowstride +
src_x * src_bpp + 1] *
filter->data [i * filter->size + j];
sumb += src_pixels [src_y * src_rowstride +
src_x * src_bpp + 2] *
filter->data [i * filter->size + j];
if (src_bpp == 4)
suma += src_pixels [src_y * src_rowstride +
src_x * src_bpp + 3] *
filter->data [i * filter->size + j];
}
}
if (dest_bpp == 4)
dest_pixels [y * dest_rowstride +
x * dest_bpp + 3] = suma * SHADOW_OPACITY;
}
}
return dest;
}
GdkPixbuf *
create_shadowed_pixbuf (GdkPixbuf *src)
{
GdkPixbuf *dest;
dest = create_shadow (src);
gdk_pixbuf_composite (src, dest,
BLUR_RADIUS, BLUR_RADIUS,
gdk_pixbuf_get_width (src),
gdk_pixbuf_get_height (src),
BLUR_RADIUS, BLUR_RADIUS, 1.0, 1.0,
GDK_INTERP_NEAREST, 255);
return dest;
}
#ifndef __SHADOW_H__
#define __SHADOW_H__
#include <gdk-pixbuf/gdk-pixbuf.h>
GdkPixbuf *create_shadowed_pixbuf (GdkPixbuf *src);
#endif /* __SHADOW_H__ */
#include <gdk/gdk.h>
#include <gtk/gtk.h>
#include <gdkx.h>
#include <stdio.h>
#include <errno.h>
#include <sys/wait.h>
#include <unistd.h>
#include <X11/extensions/shape.h>
#include <gdk-pixbuf/gdk-pixbuf.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/wait.h>
#include <signal.h>
#include <unistd.h>
#include <stdlib.h>
#include <fcntl.h>
#include <errno.h>
#include <locale.h>
#include "widgets.h"
#include "shadow.h"
#define MAXIMUM_WM_REPARENTING_DEPTH 4
#ifndef _
#define _(x) (x)
#endif
static Window
find_toplevel_window (Window xid)
{
Window root, parent, *children;
int nchildren;
do
{
if (XQueryTree (GDK_DISPLAY (), xid, &root,
&parent, &children, &nchildren) == 0)
{
g_warning ("Couldn't find window manager window");
return 0;
}
if (root == parent)
return xid;
xid = parent;
}
while (TRUE);
}
static GdkPixbuf *
add_border_to_shot (GdkPixbuf *pixbuf)
{
GdkPixbuf *retval;
retval = gdk_pixbuf_new (GDK_COLORSPACE_RGB, TRUE, 8,
gdk_pixbuf_get_width (pixbuf) + 2,
gdk_pixbuf_get_height (pixbuf) + 2);
/* Fill with solid black */
gdk_pixbuf_fill (retval, 0xFF);
gdk_pixbuf_copy_area (pixbuf,
0, 0,
gdk_pixbuf_get_width (pixbuf),
gdk_pixbuf_get_height (pixbuf),
retval, 1, 1);
return retval;
}
static GdkPixbuf *
remove_shaped_area (GdkPixbuf *pixbuf,
Window window)
{
GdkPixbuf *retval;
XRectangle *rectangles;
int rectangle_count, rectangle_order;
int i;
retval = gdk_pixbuf_new (GDK_COLORSPACE_RGB, TRUE, 8,
gdk_pixbuf_get_width (pixbuf),
gdk_pixbuf_get_height (pixbuf));
gdk_pixbuf_fill (retval, 0);
rectangles = XShapeGetRectangles (GDK_DISPLAY (), window,
ShapeBounding, &rectangle_count, &rectangle_order);
for (i = 0; i < rectangle_count; i++)
{
int y, x;
for (y = rectangles[i].y; y < rectangles[i].y + rectangles[i].height; y++)
{
guchar *src_pixels, *dest_pixels;
src_pixels = gdk_pixbuf_get_pixels (pixbuf) +
y * gdk_pixbuf_get_rowstride (pixbuf) +
rectangles[i].x * (gdk_pixbuf_get_has_alpha (pixbuf) ? 4 : 3);
dest_pixels = gdk_pixbuf_get_pixels (retval) +
y * gdk_pixbuf_get_rowstride (retval) +
rectangles[i].x * 4;
for (x = rectangles[i].x; x < rectangles[i].x + rectangles[i].width; x++)
{
*dest_pixels++ = *src_pixels ++;
*dest_pixels++ = *src_pixels ++;
*dest_pixels++ = *src_pixels ++;
*dest_pixels++ = 255;
if (gdk_pixbuf_get_has_alpha (pixbuf))
src_pixels++;
}
}
}
return retval;
}
static GdkPixbuf *
take_window_shot (Window child,
gboolean include_decoration)
{
GdkWindow *window;
Display *disp;
Window w, xid;
gint x_orig, y_orig;
gint x = 0, y = 0;
gint width, height;
GdkPixbuf *tmp, *tmp2;
GdkPixbuf *retval;
disp = GDK_DISPLAY ();
w = GDK_ROOT_WINDOW ();
if (include_decoration)
xid = find_toplevel_window (child);
else
xid = child;
window = gdk_window_foreign_new (xid);
gdk_drawable_get_size (window, &width, &height);
gdk_window_get_origin (window, &x_orig, &y_orig);
if (x_orig < 0)
{
x = - x_orig;
width = width + x_orig;
x_orig = 0;
}
if (y_orig < 0)
{
y = - y_orig;
height = height + y_orig;
y_orig = 0;
}
if (x_orig + width > gdk_screen_width ())
width = gdk_screen_width () - x_orig;
if (y_orig + height > gdk_screen_height ())
height = gdk_screen_height () - y_orig;
tmp = gdk_pixbuf_get_from_drawable (NULL, window, NULL,
x, y, 0, 0, width, height);
if (include_decoration)
tmp2 = remove_shaped_area (tmp, xid);
else
tmp2 = add_border_to_shot (tmp);
retval = create_shadowed_pixbuf (tmp2);
g_object_unref (tmp);
g_object_unref (tmp2);
return retval;
}
int main (int argc, char **argv)
{
GList *toplevels;
GdkPixbuf *screenshot = NULL;
GList *node;
/* If there's no DISPLAY, we silently error out. We don't want to break
* headless builds. */
if (! gtk_init_check (&argc, &argv))
return 0;
toplevels = get_all_widgets ();
for (node = toplevels; node; node = g_list_next (node))
{
GdkWindow *window;
WidgetInfo *info;
XID id;
char *filename;
info = node->data;
gtk_widget_show (info->window);
window = info->window->window;
gtk_widget_show_now (info->window);
gtk_widget_draw (info->window, &(info->window->allocation));
while (gtk_events_pending ())
{
gtk_main_iteration ();
}
sleep (1);
while (gtk_events_pending ())
{
gtk_main_iteration ();
}
id = gdk_x11_drawable_get_xid (GDK_DRAWABLE (window));
screenshot = take_window_shot (id, info->include_decorations);
filename = g_strdup_printf ("./%s.png", info->name);
gdk_pixbuf_save (screenshot, filename, "png", NULL, NULL);
g_free(filename);
gtk_widget_hide (info->window);
}
return 0;
}
#include "widgets.h"
static WidgetInfo *
new_widget_info (const char *name,
GtkWidget *widget)
{
WidgetInfo *info;
info = g_new0 (WidgetInfo, 1);
info->name = g_strdup (name);
info->window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
info->no_focus = TRUE;
info->include_decorations = FALSE;
gtk_widget_set_app_paintable (info->window, TRUE);
g_signal_connect (info->window, "focus", G_CALLBACK (gtk_true), NULL);
gtk_container_set_border_width (GTK_CONTAINER (info->window), 12);
gtk_widget_show_all (widget);
gtk_container_add (GTK_CONTAINER (info->window), widget);
return info;
}
static WidgetInfo *
create_button (void)
{
GtkWidget *widget;
widget = gtk_button_new_with_mnemonic ("_Button");
return new_widget_info ("button", widget);
}
static WidgetInfo *
create_toggle_button (void)
{
GtkWidget *widget;
widget = gtk_toggle_button_new_with_mnemonic ("_Toggle Button");
gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (widget), FALSE);
return new_widget_info ("toggle-button", widget);
}
static WidgetInfo *
create_check_button (void)
{
GtkWidget *widget;
widget = gtk_check_button_new_with_mnemonic ("_Check Button");
gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (widget), TRUE);
return new_widget_info ("check-button", widget);
}
static WidgetInfo *
create_entry (void)
{
GtkWidget *widget;
widget = gtk_entry_new ();
gtk_entry_set_text (GTK_ENTRY (widget), "Entry");
gtk_editable_set_position (GTK_EDITABLE (widget), -1);
return new_widget_info ("entry", widget);
}
static WidgetInfo *
create_radio (void)
{
GtkWidget *widget;
GtkWidget *radio;
widget = gtk_vbox_new (FALSE, 3);
radio = gtk_radio_button_new_with_mnemonic (NULL, "Radio Button Item _One");
gtk_box_pack_start (GTK_BOX (widget), radio, FALSE, FALSE, 0);
radio = gtk_radio_button_new_with_mnemonic_from_widget (GTK_RADIO_BUTTON (radio), "Radio Button Item _Two");
gtk_box_pack_start (GTK_BOX (widget), radio, FALSE, FALSE, 0);
radio = gtk_radio_button_new_with_mnemonic_from_widget (GTK_RADIO_BUTTON (radio), "Radio Button Item T_hree");
gtk_box_pack_start (GTK_BOX (widget), radio, FALSE, FALSE, 0);
return new_widget_info ("radio-group", widget);
}
static WidgetInfo *
create_label (void)
{
GtkWidget *widget;
widget = gtk_label_new ("Label");
return new_widget_info ("label", widget);
}
static WidgetInfo *
create_combo_box_entry (void)
{
GtkWidget *widget;
widget = gtk_combo_box_entry_new_text ();
gtk_entry_set_text (GTK_ENTRY (GTK_BIN (widget)->child), "Combo Box Entry");
return new_widget_info ("combo-box-entry", widget);
}
static WidgetInfo *
create_text_view (void)
{
GtkWidget *widget;
GtkWidget *text_view;
widget = gtk_frame_new (NULL);
gtk_frame_set_shadow_type (GTK_FRAME (widget), GTK_SHADOW_IN);
text_view = gtk_text_view_new ();
gtk_container_add (GTK_CONTAINER (widget), text_view);
/* Bad hack to add some size to the widget */
gtk_text_buffer_set_text (gtk_text_view_get_buffer (GTK_TEXT_VIEW (text_view)),
"Multiline \nText\n\n", -1);
gtk_text_view_set_cursor_visible (GTK_TEXT_VIEW (text_view), FALSE);
return new_widget_info ("multiline-text", widget);
}