diff options
Diffstat (limited to 'xembed/tests')
-rw-r--r-- | xembed/tests/.cvsignore | 9 | ||||
-rw-r--r-- | xembed/tests/Makefile.am | 36 | ||||
-rw-r--r-- | xembed/tests/gtk-client.c | 153 | ||||
-rw-r--r-- | xembed/tests/gtk-embedder.c | 314 | ||||
-rw-r--r-- | xembed/tests/qt-client.cpp | 103 | ||||
-rw-r--r-- | xembed/tests/qt-client.h | 27 | ||||
-rw-r--r-- | xembed/tests/qt-embedder.cpp | 135 | ||||
-rw-r--r-- | xembed/tests/qt-embedder.h | 28 |
8 files changed, 805 insertions, 0 deletions
diff --git a/xembed/tests/.cvsignore b/xembed/tests/.cvsignore new file mode 100644 index 0000000..2bffb50 --- /dev/null +++ b/xembed/tests/.cvsignore @@ -0,0 +1,9 @@ +.deps +.libs +Makefile +Makefile.in +gtk-client +gtk-embedder +qt-client +qt-embedder +moc_* diff --git a/xembed/tests/Makefile.am b/xembed/tests/Makefile.am new file mode 100644 index 0000000..c33cdf2 --- /dev/null +++ b/xembed/tests/Makefile.am @@ -0,0 +1,36 @@ +noinst_PROGRAMS = qt-client qt-embedder gtk-client gtk-embedder + +INCLUDES = @all_includes@ @GTK_CFLAGS@ -DG_DISABLE_DEPRECATED -DGDK_DISABLE_DEPRECATED -DGTK_DISABLE_DEPRECATED + +# +# Qt Examples +# + +qt_libs = $(LIB_QT) $(LIB_KDECORE) $(LIB_KDEUI) $(LIB_KFILE) $(LIBSOCKET) + +BUILT_SOURCES=moc_qt-client.cc moc_qt-embedder.cc + +moc_qt-client.cc: qt-client.h + $(MOC) $< -o $@ + +moc_qt-embedder.cc: qt-embedder.h + $(MOC) $< -o $@ + +qt_client_SOURCES = qt-client.cpp qt-client.h +qt_client_LDADD = $(qt_libs) moc_qt-client.$(OBJEXT) + +qt_embedder_SOURCES = qt-embedder.cpp qt-embedder.h +qt_embedder_LDADD = $(qt_libs) moc_qt-embedder.$(OBJEXT) + +CLEANFILES = moc_qt-client.cc moc_qt-embedder.cc + +# +# GTK+ examples +# + +gtk_client_SOURCES = gtk-client.c +gtk_client_LDADD = $(GTK_LIBS) + +gtk_embedder_SOURCES = gtk-embedder.c +gtk_embedder_LDADD = $(GTK_LIBS) + diff --git a/xembed/tests/gtk-client.c b/xembed/tests/gtk-client.c new file mode 100644 index 0000000..70af4b8 --- /dev/null +++ b/xembed/tests/gtk-client.c @@ -0,0 +1,153 @@ +#include <stdio.h> +#include <stdlib.h> + +#include <gtk/gtk.h> + +static void +remove_buttons (GtkWidget *widget, GtkWidget *other_button) +{ + gtk_widget_destroy (other_button); + gtk_widget_destroy (widget); +} + +static gboolean +blink_cb (gpointer data) +{ + GtkWidget *widget = data; + + gtk_widget_show (widget); + g_object_set_data (G_OBJECT (widget), "blink", GPOINTER_TO_UINT (0)); + + return FALSE; +} + +static void +blink (GtkWidget *widget, + GtkWidget *window) +{ + guint blink_timeout = GPOINTER_TO_UINT (g_object_get_data (G_OBJECT (window), "blink")); + + if (!blink_timeout) + { + blink_timeout = g_timeout_add (1000, blink_cb, window); + gtk_widget_hide (window); + + g_object_set_data (G_OBJECT (window), "blink", GUINT_TO_POINTER (blink_timeout)); + } +} + +static void +remote_destroy (GtkWidget *window) +{ + guint blink_timeout = GPOINTER_TO_UINT (g_object_get_data (G_OBJECT (window), "blink")); + if (blink_timeout) + g_source_remove (blink_timeout); + + gtk_main_quit (); +} + +static void +add_buttons (GtkWidget *widget, GtkWidget *box) +{ + GtkWidget *add_button; + GtkWidget *remove_button; + + add_button = gtk_button_new_with_mnemonic ("_Add"); + gtk_box_pack_start (GTK_BOX (box), add_button, TRUE, TRUE, 0); + gtk_widget_show (add_button); + + g_signal_connect (add_button, "clicked", + G_CALLBACK (add_buttons), box); + + remove_button = gtk_button_new_with_mnemonic ("_Remove"); + gtk_box_pack_start (GTK_BOX (box), remove_button, TRUE, TRUE, 0); + gtk_widget_show (remove_button); + + g_signal_connect (remove_button, "clicked", + G_CALLBACK (remove_buttons), add_button); +} + +guint32 +create_child_plug (guint32 xid) +{ + GtkWidget *window; + GtkWidget *hbox; + GtkWidget *entry; + GtkWidget *button; + GtkWidget *label; + + window = gtk_plug_new (xid); + + g_signal_connect (window, "destroy", + G_CALLBACK (remote_destroy), NULL); + gtk_container_set_border_width (GTK_CONTAINER (window), 0); + + hbox = gtk_hbox_new (FALSE, 0); + gtk_container_add (GTK_CONTAINER (window), hbox); + + label = gtk_label_new ("GTK+"); + gtk_box_pack_start (GTK_BOX (hbox), label, TRUE, TRUE, 0); + + entry = gtk_entry_new (); + gtk_box_pack_start (GTK_BOX (hbox), entry, TRUE, TRUE, 0); + + button = gtk_button_new_with_mnemonic ("_Close"); + gtk_box_pack_start (GTK_BOX (hbox), button, TRUE, TRUE, 0); + + g_signal_connect_swapped (button, "clicked", + G_CALLBACK (gtk_widget_destroy), window); + + button = gtk_button_new_with_mnemonic ("_Blink"); + gtk_box_pack_start (GTK_BOX (hbox), button, TRUE, TRUE, 0); + + g_signal_connect (button, "clicked", + G_CALLBACK (blink), window); + + add_buttons (NULL, hbox); + + gtk_widget_show_all (window); + + if (GTK_WIDGET_REALIZED (window)) + return gtk_plug_get_id (GTK_PLUG (window)); + else + return 0; +} + +int +main (int argc, char *argv[]) +{ + guint32 xid; + guint32 plug_xid; + + gtk_init (&argc, &argv); + + if (argc != 1 && argc != 2) + { + fprintf (stderr, "Usage: testsocket_child [WINDOW_ID]\n"); + exit (1); + } + + if (argc == 2) + { + xid = strtol (argv[1], NULL, 0); + if (xid == 0) + { + fprintf (stderr, "Invalid window id '%s'\n", argv[1]); + exit (1); + } + + create_child_plug (xid); + } + else + { + plug_xid = create_child_plug (0); + printf ("%d\n", plug_xid); + fflush (stdout); + } + + gtk_main (); + + return 0; +} + + diff --git a/xembed/tests/gtk-embedder.c b/xembed/tests/gtk-embedder.c new file mode 100644 index 0000000..8d7c1a1 --- /dev/null +++ b/xembed/tests/gtk-embedder.c @@ -0,0 +1,314 @@ +#include <gtk/gtk.h> + +#include <string.h> +#include <stdlib.h> +#include <stdio.h> + +int n_children = 0; + +GSList *sockets = NULL; + +GtkWidget *window; +GtkWidget *vbox; + +typedef struct +{ + GtkWidget *box; + GtkWidget *frame; + GtkWidget *socket; +} Socket; + +static void +quit_cb (gpointer callback_data, + guint callback_action, + GtkWidget *widget) +{ + GtkWidget *message_dialog = gtk_message_dialog_new (GTK_WINDOW (window), 0, + GTK_MESSAGE_QUESTION, + GTK_BUTTONS_NONE, + "Really Quit?"); + gtk_dialog_add_buttons (GTK_DIALOG (message_dialog), + GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, + GTK_STOCK_QUIT, GTK_RESPONSE_YES, + NULL); + + gtk_dialog_set_default_response (GTK_DIALOG (message_dialog), GTK_RESPONSE_YES); + + if (gtk_dialog_run (GTK_DIALOG (message_dialog)) == GTK_RESPONSE_YES) + gtk_widget_destroy (window); + + gtk_widget_destroy (message_dialog); +} + +static GtkItemFactoryEntry menu_items[] = +{ + { "/_File", NULL, 0, 0, "<Branch>" }, + { "/File/_Quit", "<control>Q", quit_cb, 0 }, +}; + +static void +socket_destroyed (GtkWidget *widget, + Socket *socket) +{ + sockets = g_slist_remove (sockets, socket); + g_free (socket); +} + +static void +plug_added (GtkWidget *widget, + Socket *socket) +{ + g_print ("Plug added to socket\n"); + + gtk_widget_show (socket->socket); + gtk_widget_hide (socket->frame); +} + +static gboolean +plug_removed (GtkWidget *widget, + Socket *socket) +{ + g_print ("Plug removed from socket\n"); + + gtk_widget_hide (socket->socket); + gtk_widget_show (socket->frame); + + return TRUE; +} + +static Socket * +create_socket (void) +{ + GtkWidget *label; + + Socket *socket = g_new (Socket, 1); + + socket->box = gtk_vbox_new (FALSE, 0); + + socket->socket = gtk_socket_new (); + + gtk_box_pack_start (GTK_BOX (socket->box), socket->socket, TRUE, TRUE, 0); + + socket->frame = gtk_frame_new (NULL); + gtk_frame_set_shadow_type (GTK_FRAME (socket->frame), GTK_SHADOW_IN); + gtk_box_pack_start (GTK_BOX (socket->box), socket->frame, TRUE, TRUE, 0); + gtk_widget_show (socket->frame); + + label = gtk_label_new (NULL); + gtk_label_set_markup (GTK_LABEL (label), "<span color=\"red\">Empty</span>"); + gtk_container_add (GTK_CONTAINER (socket->frame), label); + gtk_widget_show (label); + + sockets = g_slist_prepend (sockets, socket); + + + g_signal_connect (G_OBJECT (socket->socket), "destroy", + G_CALLBACK (socket_destroyed), socket); + g_signal_connect (G_OBJECT (socket->socket), "plug_added", + G_CALLBACK (plug_added), socket); + g_signal_connect (G_OBJECT (socket->socket), "plug_removed", + G_CALLBACK (plug_removed), socket); + + return socket; +} + +void +remove_child (void) +{ + if (sockets) + { + Socket *socket = sockets->data; + gtk_widget_destroy (socket->box); + } +} + +static gboolean +child_read_watch (GIOChannel *channel, GIOCondition cond, gpointer data) +{ + GIOStatus status; + GError *error = NULL; + char *line; + gsize term; + int xid; + + status = g_io_channel_read_line (channel, &line, NULL, &term, &error); + switch (status) + { + case G_IO_STATUS_NORMAL: + line[term] = '\0'; + xid = strtol (line, NULL, 0); + if (xid == 0) + { + fprintf (stderr, "Invalid window id '%s'\n", line); + } + else + { + Socket *socket = create_socket (); + gtk_box_pack_start (GTK_BOX (vbox), socket->box, TRUE, TRUE, 0); + gtk_widget_show (socket->box); + + gtk_socket_add_id (GTK_SOCKET (socket->socket), xid); + } + g_free (line); + return TRUE; + case G_IO_STATUS_AGAIN: + return TRUE; + case G_IO_STATUS_EOF: + n_children--; + g_io_channel_shutdown (channel, FALSE, NULL); + return FALSE; + case G_IO_STATUS_ERROR: + fprintf (stderr, "Error reading fd from child: %s\n", error->message); + exit (1); + return FALSE; + default: + g_assert_not_reached (); + return FALSE; + } + +} + +void +add_child (gboolean active, + gboolean qt) +{ + Socket *socket; + char *argv[3] = { NULL, NULL, NULL }; + char buffer[20]; + int out_fd; + GIOChannel *channel; + GError *error = NULL; + + argv[0] = qt ? "./qt-client" : "./gtk-client"; + + if (active) + { + socket = create_socket (); + gtk_box_pack_start (GTK_BOX (vbox), socket->box, TRUE, TRUE, 0); + gtk_widget_show (socket->box); + sprintf(buffer, "%#lx", (gulong) gtk_socket_get_id (GTK_SOCKET (socket->socket))); + argv[1] = buffer; + } + + if (!g_spawn_async_with_pipes (NULL, argv, NULL, 0, NULL, NULL, NULL, NULL, &out_fd, NULL, &error)) + { + fprintf (stderr, "Can't exec %s: %s\n", argv[0], error->message); + exit (1); + } + + n_children++; + channel = g_io_channel_unix_new (out_fd); + g_io_channel_set_flags (channel, G_IO_FLAG_NONBLOCK, &error); + if (error) + { + fprintf (stderr, "Error making channel non-blocking: %s\n", error->message); + exit (1); + } + + g_io_add_watch (channel, G_IO_IN | G_IO_HUP, child_read_watch, NULL); +} + +void +add_active_gtk_child (void) +{ + add_child (TRUE, FALSE); +} + +void +add_passive_gtk_child (void) +{ + add_child (FALSE, FALSE); +} + +void +add_active_qt_child (void) +{ + add_child (TRUE, TRUE); +} + +void +add_passive_qt_child (void) +{ + add_child (FALSE, TRUE); +} + +int +main (int argc, char *argv[]) +{ + GtkWidget *button; + GtkWidget *hbox; + GtkAccelGroup *accel_group; + GtkItemFactory *item_factory; + + gtk_init (&argc, &argv); + + window = gtk_window_new (GTK_WINDOW_TOPLEVEL); + g_signal_connect (window, "destroy", + G_CALLBACK (gtk_main_quit), NULL); + + gtk_window_set_title (GTK_WINDOW (window), "Socket Test"); + gtk_container_set_border_width (GTK_CONTAINER (window), 0); + + vbox = gtk_vbox_new (FALSE, 0); + gtk_container_add (GTK_CONTAINER (window), vbox); + + accel_group = gtk_accel_group_new (); + gtk_window_add_accel_group (GTK_WINDOW (window), accel_group); + item_factory = gtk_item_factory_new (GTK_TYPE_MENU_BAR, "<main>", accel_group); + + + gtk_item_factory_create_items (item_factory, + G_N_ELEMENTS (menu_items), menu_items, + NULL); + + gtk_box_pack_start (GTK_BOX (vbox), + gtk_item_factory_get_widget (item_factory, "<main>"), + FALSE, FALSE, 0); + + button = gtk_button_new_with_label ("Add Active Qt Child"); + gtk_box_pack_start (GTK_BOX(vbox), button, FALSE, FALSE, 0); + + g_signal_connect (button, "clicked", + G_CALLBACK (add_active_qt_child), NULL); + + button = gtk_button_new_with_label ("Add Passive Qt Child"); + gtk_box_pack_start (GTK_BOX(vbox), button, FALSE, FALSE, 0); + + g_signal_connect (button, "clicked", + GTK_SIGNAL_FUNC (add_passive_qt_child), NULL); + + button = gtk_button_new_with_label ("Add Active GTK+ Child"); + gtk_box_pack_start (GTK_BOX(vbox), button, FALSE, FALSE, 0); + + g_signal_connect (button, "clicked", + G_CALLBACK (add_active_gtk_child), NULL); + + button = gtk_button_new_with_label ("Add Passive GTK+ Child"); + gtk_box_pack_start (GTK_BOX(vbox), button, FALSE, FALSE, 0); + + g_signal_connect (button, "clicked", + G_CALLBACK (add_passive_gtk_child), NULL); + + button = gtk_button_new_with_label ("Remove Last Child"); + gtk_box_pack_start (GTK_BOX(vbox), button, FALSE, FALSE, 0); + + g_signal_connect (GTK_OBJECT(button), "clicked", + G_CALLBACK (remove_child), NULL); + + hbox = gtk_hbox_new (FALSE, 0); + gtk_box_pack_start (GTK_BOX(vbox), hbox, FALSE, FALSE, 0); + + gtk_widget_show_all (window); + + gtk_main (); + + if (n_children) + { + g_print ("Waiting for children to exit\n"); + + while (n_children) + g_main_context_iteration (NULL, TRUE); + } + + return 0; +} diff --git a/xembed/tests/qt-client.cpp b/xembed/tests/qt-client.cpp new file mode 100644 index 0000000..04f2223 --- /dev/null +++ b/xembed/tests/qt-client.cpp @@ -0,0 +1,103 @@ +#include <kapp.h> +#include <qlabel.h> +#include <qlineedit.h> +#include <qlayout.h> +#include <qpushbutton.h> +#include <qtimer.h> + +#include <qxembed.h> + +#include "qt-client.h" + +XEmbedQtButtonBox::XEmbedQtButtonBox (XEmbedQtClient *client) + : QWidget (client) +{ + QHBoxLayout *layout = new QHBoxLayout (this); + layout->setAutoAdd (TRUE); + + QPushButton *button; + + button = new QPushButton( "&Add", this ); + QObject::connect (button, SIGNAL(clicked()), client, SLOT(addButtons())); + + button = new QPushButton( "&Remove", this ); + QObject::connect (button, SIGNAL(clicked()), this, SLOT(close())); +} + + +XEmbedQtClient::XEmbedQtClient () +{ + QHBoxLayout *layout = new QHBoxLayout (this); + + layout->setAutoAdd (TRUE); + + new QLabel ("Qt", this); + + new QLineEdit (this); + + QPushButton *button; + + button = new QPushButton( "&Close", this ); + QObject::connect (button, SIGNAL(clicked()), this, SLOT(close())); + + button = new QPushButton( "&Blink", this ); + QObject::connect (button, SIGNAL(clicked()), this, SLOT(blink())); + + addButtons(); +} + +void +XEmbedQtClient::blink() +{ + hide (); + + QTimer *timer = new QTimer ( this ); + QObject::connect (timer, SIGNAL(timeout()), this, SLOT(show())); + timer->start (1000, TRUE); +} + +void +XEmbedQtClient::addButtons () +{ + XEmbedQtButtonBox *box = new XEmbedQtButtonBox (this); + box->show(); +} + + +int main( int argc, char **argv ) +{ + KApplication a( argc, argv, "qt-client" ); + WId embedder_xid, client_xid; + XEmbedQtClient *client; + + if (argc != 1 && argc != 2) + { + fprintf (stderr, "Usage: qt-client [WINDOW_ID]\n"); + exit (1); + } + + QXEmbed::initialize (); + + if (argc == 2) + { + embedder_xid = strtol (argv[1], NULL, 0); + if (embedder_xid == 0) + { + fprintf (stderr, "Invalid window id '%s'\n", argv[1]); + exit (1); + } + + client = new XEmbedQtClient (); + QXEmbed::embedClientIntoWindow (client, embedder_xid); + } + else + { + client = new XEmbedQtClient (); + printf ("%d\n", client->winId()); + fflush (stdout); + } + + a.setMainWidget( client ); + + return a.exec(); +} diff --git a/xembed/tests/qt-client.h b/xembed/tests/qt-client.h new file mode 100644 index 0000000..6911b22 --- /dev/null +++ b/xembed/tests/qt-client.h @@ -0,0 +1,27 @@ +#include <qmainwindow.h> + +class XEmbedQtClient; + +class XEmbedQtButtonBox : public QWidget +{ + Q_OBJECT + + public: + + XEmbedQtButtonBox (XEmbedQtClient *client); +}; + +class XEmbedQtClient : public QWidget +{ + Q_OBJECT + + public: + + XEmbedQtClient (); + + public slots: + void addButtons (); + + private slots: + void blink(); +}; diff --git a/xembed/tests/qt-embedder.cpp b/xembed/tests/qt-embedder.cpp new file mode 100644 index 0000000..66cd84b --- /dev/null +++ b/xembed/tests/qt-embedder.cpp @@ -0,0 +1,135 @@ +#include <kapp.h> +#include <qmenubar.h> +#include <qmessagebox.h> +#include <qpopupmenu.h> +#include <qprocess.h> +#include <qpushbutton.h> +#include <qvbox.h> + +#include <qxembed.h> + +#include "qt-embedder.h" + +XEmbedQtEmbedder::XEmbedQtEmbedder () +{ + // Create menu + QPopupMenu *file_menu = new QPopupMenu (this); + + menuBar()->insertItem ("&File", file_menu); + + file_menu->insertItem( "&Quit", this, SLOT( maybeQuit() ), CTRL+Key_Q ); + + vbox_ = new QVBox (this); + + setCentralWidget (vbox_); + + QPushButton *button; + + button = new QPushButton ("Add Active GTK+ Child", vbox_); + QObject::connect (button, SIGNAL(clicked()), this, SLOT(addActiveGtkChild())); + + button = new QPushButton ("Add Passive GTK+ Child", vbox_); + QObject::connect (button, SIGNAL(clicked()), this, SLOT(addPassiveGtkChild())); + + button = new QPushButton ("Add Active Qt Child", vbox_); + QObject::connect (button, SIGNAL(clicked()), this, SLOT(addActiveQtChild())); + + button = new QPushButton ("Add Passive Qt Child", vbox_); + QObject::connect (button, SIGNAL(clicked()), this, SLOT(addPassiveQtChild())); + + button = new QPushButton ("Remove Last Child", vbox_); + QObject::connect (button, SIGNAL(clicked()), this, SLOT(removeChild())); +} + + +void +XEmbedQtEmbedder::addChild (bool active, bool isQt) +{ + QXEmbed *embedder = new QXEmbed (vbox_); + embedder->show (); + + embedders_.append (embedder); + + QProcess *proc = new QProcess (this); + + proc->setCommunication (QProcess::Stdout); + + if (isQt) + proc->addArgument ("./qt-client"); + else + proc->addArgument ("./gtk-client"); + + if (!active) + proc->addArgument (QString::number (embedder->winId ())); + + proc->start (); + + if (active) + { + QString pid_str = proc->readLineStdout (); + embedder->embed (pid_str.toLong ()); + } +} + +void +XEmbedQtEmbedder::addActiveGtkChild () +{ + addChild (TRUE, FALSE); +} + +void +XEmbedQtEmbedder::addPassiveGtkChild () +{ + addChild (TRUE, FALSE); +} + +void +XEmbedQtEmbedder::addActiveQtChild () +{ + addChild (TRUE, TRUE); +} + +void +XEmbedQtEmbedder::addPassiveQtChild () +{ + addChild (FALSE, TRUE); +} + +void +XEmbedQtEmbedder::removeChild () +{ + if (!embedders_.isEmpty ()) + { + embedders_.getLast()->close(); + embedders_.removeLast(); + } +} + +void +XEmbedQtEmbedder::maybeQuit () +{ + QMessageBox mb( "qt-embedder", "Really Quit?", + QMessageBox::Information, + QMessageBox::Yes | QMessageBox::Default, + QMessageBox::Cancel | QMessageBox::Escape, + 0, this ); + mb.setButtonText( QMessageBox::Yes, "&Quit" ); + mb.setButtonText( QMessageBox::No, "Cancel"); + + if (mb.exec() == QMessageBox::Yes) + { + qApp->closeAllWindows (); + } +} + +int main( int argc, char **argv ) +{ + KApplication a( argc, argv, "qt-embedder" ); + + XEmbedQtEmbedder *embedder = new XEmbedQtEmbedder (); + + a.setMainWidget( embedder ); + embedder->show(); + + return a.exec(); +} diff --git a/xembed/tests/qt-embedder.h b/xembed/tests/qt-embedder.h new file mode 100644 index 0000000..ab678f9 --- /dev/null +++ b/xembed/tests/qt-embedder.h @@ -0,0 +1,28 @@ +#include <qmainwindow.h> +#include <qptrlist.h> + +class QVBox; + +class XEmbedQtEmbedder : public QMainWindow +{ + Q_OBJECT + + public: + + XEmbedQtEmbedder (); + + private: + QVBox *vbox_; + QPtrList<QWidget> embedders_; + + void addChild (bool active, bool isQt); + + private slots: + + void addActiveGtkChild (); + void addPassiveGtkChild (); + void addActiveQtChild (); + void addPassiveQtChild (); + void removeChild (); + void maybeQuit (); +}; |