Commit 017a5e3d authored by Matthias Clasen's avatar Matthias Clasen Committed by Matthias Clasen
Browse files

More work on GtkAssistant by Carlos Garnacho:

2006-01-28  Matthias Clasen  <mclasen@redhat.com>

	More work on GtkAssistant by Carlos Garnacho:

	* demos/gtk-demo/Makefile.am:
	* demos/gtk-demo/assistant.c: Add a  GtkAssistant demo.

	* gtk/gtkassistant.c: Handle focus, several small fixes to the
	flow computations.
parent bd51b09f
2006-01-28 Matthias Clasen <mclasen@redhat.com>
More work on GtkAssistant by Carlos Garnacho:
* demos/gtk-demo/Makefile.am:
* demos/gtk-demo/assistant.c: Add a GtkAssistant demo.
* gtk/gtkassistant.c: Handle focus, several small fixes to the
flow computations.
2006-01-27 Federico Mena Quintero <federico@ximian.com>
Fixes bug #328820:
......
2006-01-28 Matthias Clasen <mclasen@redhat.com>
More work on GtkAssistant by Carlos Garnacho:
* demos/gtk-demo/Makefile.am:
* demos/gtk-demo/assistant.c: Add a GtkAssistant demo.
* gtk/gtkassistant.c: Handle focus, several small fixes to the
flow computations.
2006-01-27 Federico Mena Quintero <federico@ximian.com>
Fixes bug #328820:
......
......@@ -6,6 +6,7 @@ democodedir=$(datadir)/gtk-2.0/demo
## demo app, which means alphabetized by demo title, not filename
demos = \
appwindow.c \
assistant.c \
button_box.c \
changedisplay.c \
clipboard.c \
......
/* Assistant
*
* Demonstrates a sample multistep assistant. Assistants are used to divide
* an operation into several simpler sequential steps, and to guide the user
* through these steps.
*/
#include <gtk/gtk.h>
#include "demo-common.h"
static GtkWidget *assistant = NULL;
static void
on_assistant_apply (GtkWidget *widget, gpointer data)
{
/* Apply here changes, this is a fictional
example, so we just do nothing here */
}
static void
on_assistant_close_cancel (GtkWidget *widget, gpointer data)
{
GtkWidget **assistant = (GtkWidget **) data;
gtk_widget_destroy (*assistant);
*assistant = NULL;
}
static void
on_assistant_prepare (GtkWidget *widget, GtkWidget *page, gpointer data)
{
gint current_page, n_pages;
gchar *title;
current_page = gtk_assistant_get_current_page (GTK_ASSISTANT (widget));
n_pages = gtk_assistant_get_n_pages (GTK_ASSISTANT (widget));
title = g_strdup_printf ("Sample assistant (%d of %d)", current_page + 1, n_pages);
gtk_window_set_title (GTK_WINDOW (widget), title);
g_free (title);
}
static void
on_entry_changed (GtkWidget *widget, gpointer data)
{
GtkAssistant *assistant = GTK_ASSISTANT (data);
GtkWidget *current_page;
gint page_number;
const gchar *text;
page_number = gtk_assistant_get_current_page (assistant);
current_page = gtk_assistant_get_nth_page (assistant, page_number);
text = gtk_entry_get_text (GTK_ENTRY (widget));
if (text && *text)
gtk_assistant_set_page_complete (assistant, current_page, TRUE);
else
gtk_assistant_set_page_complete (assistant, current_page, FALSE);
}
static void
create_page1 (GtkWidget *assistant)
{
GtkWidget *box, *label, *entry;
GdkPixbuf *pixbuf;
box = gtk_hbox_new (FALSE, 12);
gtk_container_set_border_width (GTK_CONTAINER (box), 12);
label = gtk_label_new ("You must fill out this entry to continue:");
gtk_box_pack_start (GTK_BOX (box), label, FALSE, FALSE, 0);
entry = gtk_entry_new ();
gtk_box_pack_start (GTK_BOX (box), entry, TRUE, TRUE, 0);
g_signal_connect (G_OBJECT (entry), "changed",
G_CALLBACK (on_entry_changed), assistant);
gtk_widget_show_all (box);
gtk_assistant_append_page (GTK_ASSISTANT (assistant), box);
gtk_assistant_set_page_title (GTK_ASSISTANT (assistant), box, "Page 1");
gtk_assistant_set_page_type (GTK_ASSISTANT (assistant), box, GTK_ASSISTANT_PAGE_INTRO);
pixbuf = gtk_widget_render_icon (assistant, GTK_STOCK_DIALOG_INFO, GTK_ICON_SIZE_DIALOG, NULL);
gtk_assistant_set_page_header_image (GTK_ASSISTANT (assistant), box, pixbuf);
g_object_unref (pixbuf);
}
static void
create_page2 (GtkWidget *assistant)
{
GtkWidget *box, *checkbutton;
GdkPixbuf *pixbuf;
box = gtk_vbox_new (12, FALSE);
gtk_container_set_border_width (GTK_CONTAINER (box), 12);
checkbutton = gtk_check_button_new_with_label ("This is optional data, you may continue "
"even if you do not check this");
gtk_box_pack_start (GTK_BOX (box), checkbutton, FALSE, FALSE, 0);
gtk_widget_show_all (box);
gtk_assistant_append_page (GTK_ASSISTANT (assistant), box);
gtk_assistant_set_page_complete (GTK_ASSISTANT (assistant), box, TRUE);
gtk_assistant_set_page_title (GTK_ASSISTANT (assistant), box, "Page 2");
pixbuf = gtk_widget_render_icon (assistant, GTK_STOCK_DIALOG_INFO, GTK_ICON_SIZE_DIALOG, NULL);
gtk_assistant_set_page_header_image (GTK_ASSISTANT (assistant), box, pixbuf);
g_object_unref (pixbuf);
}
static void
create_page3 (GtkWidget *assistant)
{
GtkWidget *label;
GdkPixbuf *pixbuf;
label = gtk_label_new ("This is a confirmation page, press 'Apply' to apply changes");
gtk_widget_show (label);
gtk_assistant_append_page (GTK_ASSISTANT (assistant), label);
gtk_assistant_set_page_type (GTK_ASSISTANT (assistant), label, GTK_ASSISTANT_PAGE_CONFIRM);
gtk_assistant_set_page_complete (GTK_ASSISTANT (assistant), label, TRUE);
gtk_assistant_set_page_title (GTK_ASSISTANT (assistant), label, "Confirmation");
pixbuf = gtk_widget_render_icon (assistant, GTK_STOCK_DIALOG_INFO, GTK_ICON_SIZE_DIALOG, NULL);
gtk_assistant_set_page_header_image (GTK_ASSISTANT (assistant), label, pixbuf);
g_object_unref (pixbuf);
}
GtkWidget*
do_assistant (GtkWidget *do_widget)
{
if (!assistant)
{
assistant = gtk_assistant_new ();
gtk_window_set_default_size (GTK_WINDOW (assistant), -1, 300);
gtk_window_set_screen (GTK_WINDOW (assistant),
gtk_widget_get_screen (do_widget));
create_page1 (assistant);
create_page2 (assistant);
create_page3 (assistant);
g_signal_connect (G_OBJECT (assistant), "cancel",
G_CALLBACK (on_assistant_close_cancel), &assistant);
g_signal_connect (G_OBJECT (assistant), "close",
G_CALLBACK (on_assistant_close_cancel), &assistant);
g_signal_connect (G_OBJECT (assistant), "apply",
G_CALLBACK (on_assistant_apply), NULL);
g_signal_connect (G_OBJECT (assistant), "prepare",
G_CALLBACK (on_assistant_prepare), NULL);
}
if (!GTK_WIDGET_VISIBLE (assistant))
gtk_widget_show (assistant);
else
{
gtk_widget_destroy (assistant);
assistant = NULL;
}
return assistant;
}
2006-01-28 Matthias Clasen <mclasen@redhat.com>
* gtk/gtk-docs.sgml:
* gtk/migrating-GtkAssistant.sgml: Add a migration guide
GnomeDruid --> GtkAssistant. (Carlos Garnacho)
2006-01-27 Federico Mena Quintero <federico@ximian.com>
* gtk/tmpl/gtkfilechooser.sgml: Mention that ~ is also a default
......
......@@ -199,6 +199,7 @@
<!ENTITY gtk-migrating-GtkIconView SYSTEM "xml/migrating-GtkIconView.sgml">
<!ENTITY gtk-migrating-GtkAboutDialog SYSTEM "xml/migrating-GtkAboutDialog.sgml">
<!ENTITY gtk-migrating-GtkColorButton SYSTEM "xml/migrating-GtkColorButton.sgml">
<!ENTITY gtk-migrating-GtkAssistant SYSTEM "xml/migrating-GtkAssistant.sgml">
<!ENTITY version SYSTEM "version.xml">
<!ENTITY gtk-query-immodules SYSTEM "gtk-query-immodules-2.0.xml">
<!ENTITY gtk-update-icon-cache SYSTEM "gtk-update-icon-cache.xml">
......@@ -589,6 +590,7 @@ that is, GUI components such as <link linkend="GtkButton">GtkButton</link> or
&gtk-migrating-GtkIconView;
&gtk-migrating-GtkAboutDialog;
&gtk-migrating-GtkColorButton;
&gtk-migrating-GtkAssistant;
</part>
<part>
......
<chapter id="gtk-migrating-GtkAssistant">
<chapterinfo>
<author>
<firstname>Carlos</firstname>
<surname>Garnacho</surname>
<affiliation>
<address>
<email>carlosg@gnome.org</email>
</address>
</affiliation>
</author>
</chapterinfo>
<title>Migrating from GnomeDruid to GtkAssistant</title>
<para>
Since version 2.10, GTK+ provides the GtkAssistant widget as a replacement
for the <structname>GnomeDruid</structname> widget in the libgnomeui library.
</para>
<para>
Conceptually, both <structname>GtkAssistant</structname> and <structname>GnomeDruid</structname>
do the same task, but there are several areas where the API has been completely
redesigned, so this chapter covers the main changes between both widgets.
</para>
<section id="inserting-pages">
<title>Inserting pages</title>
<para>
<structname>GnomeDruid</structname> was implemented as a container for
<structname>GnomeDruidPage</structname> abstract objects, which are implemented by the
<structname>GnomeDruidPageEdge</structname> and <structname>GnomeDruidPageStandard</structname>
widgets. Instead, <structname>GtkAssistant</structname> allows any widget to be a page, and implements
per-page settings (such as page type or title) as child properties. So instead of:
</para>
<programlisting>
/* Page 1 */
page = gnome_druid_page_edge_new (GNOME_EDGE_START);
gnome_druid_page_edge_set_test (GNOME_DRUID_PAGE_EDGE (page),
"Welcome to the assistant, it will make your life easier");
gtk_widget_show (page);
gnome_druid_append_page (GNOME_DRUID (druid), GNOME_DRUID_PAGE (page));
/* Page 2 */
page = gnome_druid_page_standard_new ();
gtk_container_add (GTK_CONTAINER (GNOME_DRUID_PAGE_STANDARD (page)->vbox,
create_page1 ());
gtk_widget_show_all (page);
gnome_druid_append_page (GNOME_DRUID (druid), GNOME_DRUID_PAGE (page));
/* Page 3 */
page = gnome_druid_page_edge_new (GNOME_EDGE_FINISH);
gnome_druid_page_edge_set_test (GNOME_DRUID_PAGE_EDGE (page),
"Now you are done, your life is easier");
gtk_widget_show (page);
gnome_druid_append_page (GNOME_DRUID (druid), GNOME_DRUID_PAGE (page));
</programlisting>
<para>
You have to write:
</para>
<programlisting>
gtk_assistant_append_page (GTK_ASSISTANT (assistant),
gtk_label_new ("Welcome to the assistant, it will make your life easier"));
gtk_assistant_append_page (GTK_ASSISTANT (assistant),
create_page1 ());
gtk_assistant_append_page (GTK_ASSISTANT (assistant),
gtk_label_new ("Now you are done, your life is easier");
</programlisting>
</section>
<section id="decorating-the-assistant-pages">
<title>Decorating the assistant pages</title>
<para>
To decorate your assistant pages, <structname>GtkAssistant</structname> provides similar functions
to <structname>GnomeDruid</structname>, so you have to transform code like this:
</para>
<programlisting>
gnome_druid_page_edge_set_title (GNOME_DRUID_PAGE_EDGE (page), "Welcome");
gnome_druid_page_edge_set_logo (GNOME_DRUID_PAGE_EDGE (page), logo_pixbuf);
gnome_druid_page_edge_set_watermark (GNOME_DRUID_PAGE_EDGE (page), watermark_pixbuf);
</programlisting>
<para>
Into this:
</para>
<programlisting>
gtk_assistant_set_page_title (GTK_ASSISTANT (assistant), page_widget, "Welcome");
gtk_assistant_set_page_header_image (GTK_ASSISTANT (assistant), page_widget, logo_pixbuf);
gtk_assistant_set_page_side_image (GTK_ASSISTANT (assistant), page_widget, watermark_pixbuf);
</programlisting>
<para>
Where page_widget is the widget used as a page.
</para>
</section>
<section id="setting-the-page-flow">
<title>Setting the page flow</title>
<para>
Here is the area where <structname>GtkAssistant</structname> and <structname>GnomeDruid</structname>
differ the most. While <structname>GnomeDruid</structname> used the "next" and "back" signals from the
<structname>GnomeDruidPage</structname>, <structname>GtkAssistant</structname> uses the following
techniques:
</para>
<itemizedlist>
<listitem>
<para>gtk_assistant_set_forward_page_func (): Allows to define a GtkAssistantPageFunc to let the
assistant know which will be the following page given the current page.</para>
</listitem>
<listitem>
<para>gtk_assistant_set_page_complete (): Lets the assistant know whether the specified page is complete
or not, updating buttons state accordingly.</para>
</listitem>
<listitem>
<para>gtk_assistant_set_page_type (): Lets the assistant know the page role and update the buttons
state accordingly. Pages can have the following roles:</para>
<simplelist>
<member>Intro</member>
<member>Content</member>
<member>Progress</member>
<member>Confirmation</member>
<member>Summary</member>
</simplelist>
</listitem>
</itemizedlist>
<para>
A sample GtkAssistantPageFunc could look like this:
</para>
<programlisting>
static gint
forward_page_function (gint current_page,
gpointer data)
{
switch (current_page)
{
case 0:
return 1;
case 1:
if (check_page1_data ())
return 2;
else
return 3;
case 2:
return 3;
default:
return -1;
}
}
</programlisting>
</section>
</chapter>
<!--
Local variables:
mode: sgml
sgml-parent-document: ("gtk-docs.sgml" "book" "part" "chapter")
End:
-->
<!-- ##### SECTION Title ##### -->
GtkAssistant
<!-- ##### SECTION Short_Description ##### -->
guiding users through multi-step operations
<!-- ##### SECTION Long_Description ##### -->
<para>
</para>
<!-- ##### SECTION See_Also ##### -->
<para>
</para>
<!-- ##### SECTION Stability_Level ##### -->
<!-- ##### STRUCT GtkAssistant ##### -->
<para>
</para>
<!-- ##### SIGNAL GtkAssistant::apply ##### -->
<para>
</para>
@assistant: the object which received the signal.
<!-- ##### SIGNAL GtkAssistant::cancel ##### -->
<para>
</para>
@assistant: the object which received the signal.
<!-- ##### SIGNAL GtkAssistant::close ##### -->
<para>
</para>
@assistant: the object which received the signal.
<!-- ##### SIGNAL GtkAssistant::prepare ##### -->
<para>
</para>
@assistant: the object which received the signal.
@widget:
<!-- ##### ARG GtkAssistant:complete ##### -->
<para>
</para>
<!-- ##### ARG GtkAssistant:header-image ##### -->
<para>
</para>
<!-- ##### ARG GtkAssistant:page-type ##### -->
<para>
</para>
<!-- ##### ARG GtkAssistant:sidebar-image ##### -->
<para>
</para>
<!-- ##### ARG GtkAssistant:title ##### -->
<para>
</para>
<!-- ##### ARG GtkAssistant:content-padding ##### -->
<para>
</para>
<!-- ##### ARG GtkAssistant:header-padding ##### -->
<para>
</para>
<!-- ##### FUNCTION gtk_assistant_new ##### -->
<para>
</para>
@Returns:
<!-- ##### FUNCTION gtk_assistant_get_current_page ##### -->
<para>
</para>
@assistant:
@Returns:
<!-- ##### FUNCTION gtk_assistant_set_current_page ##### -->
<para>
</para>
@assistant:
@page_num:
<!-- ##### FUNCTION gtk_assistant_get_n_pages ##### -->
<para>
</para>
@assistant:
@Returns:
<!-- ##### FUNCTION gtk_assistant_get_nth_page ##### -->
<para>
</para>
@assistant:
@page_num:
@Returns:
<!-- ##### FUNCTION gtk_assistant_prepend_page ##### -->
<para>
</para>
@assistant:
@page:
@Returns:
<!-- ##### FUNCTION gtk_assistant_append_page ##### -->
<para>
</para>
@assistant:
@page:
@Returns:
<!-- ##### FUNCTION gtk_assistant_insert_page ##### -->
<para>
</para>
@assistant:
@page:
@position:
@Returns:
<!-- ##### USER_FUNCTION GtkAssistantPageFunc ##### -->
<para>
</para>
@current_page:
@data:
@Returns:
<!-- ##### FUNCTION gtk_assistant_set_forward_page_func ##### -->
<para>
</para>
@assistant:
@page_func:
@data:
@destroy:
<!-- ##### ENUM GtkAssistantPageType ##### -->
<para>
</para>
@GTK_ASSISTANT_PAGE_CONTENT:
@GTK_ASSISTANT_PAGE_INTRO:
@GTK_ASSISTANT_PAGE_CONFIRM:
@GTK_ASSISTANT_PAGE_SUMMARY:
@GTK_ASSISTANT_PAGE_PROGRESS:
<!-- ##### FUNCTION gtk_assistant_set_page_type ##### -->
<para>
</para>
@assistant:
@page:
@type:
<!-- ##### FUNCTION gtk_assistant_get_page_type ##### -->
<para>
</para>
@assistant:
@page:
@Returns:
<!-- ##### FUNCTION gtk_assistant_set_page_title ##### -->
<para>
</para>
@assistant:
@page:
@title:
<!-- ##### FUNCTION gtk_assistant_get_page_title ##### -->
<para>
</para>