Back to index

lightning-sunbird  0.9+nobinonly
gtkmozembed2.cpp
Go to the documentation of this file.
00001 /* ***** BEGIN LICENSE BLOCK *****
00002  * Version: MPL 1.1/GPL 2.0/LGPL 2.1
00003  *
00004  * The contents of this file are subject to the Mozilla Public License Version
00005  * 1.1 (the "License"); you may not use this file except in compliance with
00006  * the License. You may obtain a copy of the License at
00007  * http://www.mozilla.org/MPL/
00008  *
00009  * Software distributed under the License is distributed on an "AS IS" basis,
00010  * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
00011  * for the specific language governing rights and limitations under the
00012  * License.
00013  *
00014  * The Original Code is mozilla.org code.
00015  *
00016  * The Initial Developer of the Original Code is
00017  * Christopher Blizzard. Portions created by Christopher Blizzard are Copyright (C) Christopher Blizzard.  All Rights Reserved.
00018  * Portions created by the Initial Developer are Copyright (C) 2001
00019  * the Initial Developer. All Rights Reserved.
00020  *
00021  * Contributor(s):
00022  *   Christopher Blizzard <blizzard@mozilla.org>
00023  *   Ramiro Estrugo <ramiro@eazel.com>
00024  *
00025  * Alternatively, the contents of this file may be used under the terms of
00026  * either the GNU General Public License Version 2 or later (the "GPL"), or
00027  * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
00028  * in which case the provisions of the GPL or the LGPL are applicable instead
00029  * of those above. If you wish to allow use of your version of this file only
00030  * under the terms of either the GPL or the LGPL, and not to allow others to
00031  * use your version of this file under the terms of the MPL, indicate your
00032  * decision by deleting the provisions above and replace them with the notice
00033  * and other provisions required by the GPL or the LGPL. If you do not delete
00034  * the provisions above, a recipient may use your version of this file under
00035  * the terms of any one of the MPL, the GPL or the LGPL.
00036  *
00037  * ***** END LICENSE BLOCK ***** */
00038 
00039 #include <stdio.h>
00040 
00041 #include "gtkmozembed.h"
00042 #include "gtkmozembedprivate.h"
00043 #include "gtkmozembed_internal.h"
00044 
00045 #include "EmbedPrivate.h"
00046 #include "EmbedWindow.h"
00047 
00048 // so we can do our get_nsIWebBrowser later...
00049 #include <nsIWebBrowser.h>
00050 
00051 // for strings
00052 #include <nsXPIDLString.h>
00053 #include <nsReadableUtils.h>
00054 
00055 #ifdef MOZ_WIDGET_GTK2
00056 
00057 #include "gtkmozembedmarshal.h"
00058 
00059 #define NEW_TOOLKIT_STRING(x) g_strdup(NS_ConvertUTF16toUTF8(x).get())
00060 #define GET_OBJECT_CLASS_TYPE(x) G_OBJECT_CLASS_TYPE(x)
00061 
00062 #endif /* MOZ_WIDGET_GTK2 */
00063 
00064 #ifdef MOZ_WIDGET_GTK
00065 
00066 // so we can get callbacks from the mozarea
00067 #include <gtkmozarea.h>
00068 
00069 // so we get the right marshaler for gtk 1.2
00070 #define gtkmozembed_VOID__INT_UINT \
00071   gtk_marshal_NONE__INT_INT
00072 #define gtkmozembed_VOID__STRING_INT_INT \
00073   gtk_marshal_NONE__POINTER_INT_INT
00074 #define gtkmozembed_VOID__STRING_INT_UINT \
00075   gtk_marshal_NONE__POINTER_INT_INT
00076 #define gtkmozembed_VOID__POINTER_INT_POINTER \
00077   gtk_marshal_NONE__POINTER_INT_POINTER
00078 #define gtkmozembed_BOOL__STRING \
00079   gtk_marshal_BOOL__POINTER
00080 
00081 #define G_SIGNAL_TYPE_STATIC_SCOPE 0
00082 
00083 #define NEW_TOOLKIT_STRING(x) g_strdup(NS_LossyConvertUTF16toASCII(x).get())
00084 #define GET_OBJECT_CLASS_TYPE(x) (GTK_OBJECT_CLASS(x)->type)
00085 
00086 // Some "massaged" enum information for the GTK Type System
00087 static GtkFlagValue gtk_moz_embed_progress_flags_values[] = {
00088   { GTK_MOZ_EMBED_FLAG_START,
00089     "GTK_MOZ_EMBED_FLAG_START", "start" },
00090   { GTK_MOZ_EMBED_FLAG_REDIRECTING,
00091     "GTK_MOZ_EMBED_FLAG_REDIRECTING", "redirecting" },
00092   { GTK_MOZ_EMBED_FLAG_TRANSFERRING,
00093     "GTK_MOZ_EMBED_FLAG_TRANSFERRING", "transferring" },
00094   { GTK_MOZ_EMBED_FLAG_NEGOTIATING,
00095     "GTK_MOZ_EMBED_FLAG_NEGOTIATING", "negotiating" },
00096   { GTK_MOZ_EMBED_FLAG_STOP,
00097     "GTK_MOZ_EMBED_FLAG_STOP", "stop" },
00098   { GTK_MOZ_EMBED_FLAG_IS_REQUEST,
00099     "GTK_MOZ_EMBED_FLAG_IS_REQUEST", "is-request" },
00100   { GTK_MOZ_EMBED_FLAG_IS_DOCUMENT,
00101     "GTK_MOZ_EMBED_FLAG_IS_DOCUMENT", "is-document" },
00102   { GTK_MOZ_EMBED_FLAG_IS_NETWORK,
00103     "GTK_MOZ_EMBED_FLAG_IS_NETWORK", "is-network" },
00104   { GTK_MOZ_EMBED_FLAG_IS_WINDOW,
00105     "GTK_MOZ_EMBED_FLAG_IS_WINDOW", "is-window" },
00106   { GTK_MOZ_EMBED_FLAG_RESTORING,
00107     "GTK_MOZ_EMBED_FLAG_RESTORING", "restoring" },
00108   { 0,
00109     NULL, NULL }
00110 };
00111 
00112 static GtkEnumValue gtk_moz_embed_status_enums_values[] = {
00113   { GTK_MOZ_EMBED_STATUS_FAILED_DNS,
00114     "GTK_MOZ_EMBED_STATUS_FAILED_DNS", "failed-dns" },
00115   { GTK_MOZ_EMBED_STATUS_FAILED_CONNECT,
00116     "GTK_MOZ_EMBED_STATUS_FAILED_CONNECT", "failed-connect" },
00117   { GTK_MOZ_EMBED_STATUS_FAILED_TIMEOUT,
00118     "GTK_MOZ_EMBED_STATUS_FAILED_TIMEOUT", "failed-timeout" },
00119   { GTK_MOZ_EMBED_STATUS_FAILED_USERCANCELED,
00120     "GTK_MOZ_EMBED_STATUS_FAILED_USERCANCELED", "failed-usercanceled" },
00121   { 0,
00122     NULL, NULL }
00123 };
00124 
00125 static GtkFlagValue gtk_moz_embed_reload_flags_values[] = {
00126   { GTK_MOZ_EMBED_FLAG_RELOADNORMAL,
00127     "GTK_MOZ_EMBED_FLAG_RELOADNORMAL", "reloadnormal" },
00128   { GTK_MOZ_EMBED_FLAG_RELOADBYPASSCACHE,
00129     "GTK_MOZ_EMBED_FLAG_RELOADBYPASSCACHE", "reloadbypasscache" },
00130   { GTK_MOZ_EMBED_FLAG_RELOADBYPASSPROXY,
00131     "GTK_MOZ_EMBED_FLAG_RELOADBYPASSPROXY", "reloadbypassproxy" },
00132   { GTK_MOZ_EMBED_FLAG_RELOADBYPASSPROXYANDCACHE,
00133     "GTK_MOZ_EMBED_FLAG_RELOADBYPASSPROXYANDCACHE",
00134     "reloadbypassproxyandcache" },
00135   { GTK_MOZ_EMBED_FLAG_RELOADCHARSETCHANGE,
00136     "GTK_MOZ_EMBED_FLAG_RELOADCHARSETCHANGE", "reloadcharset" },
00137   { 0,
00138     NULL, NULL }
00139 };
00140 
00141 static GtkFlagValue gtk_moz_embed_chrome_flags_values[] = {
00142   { GTK_MOZ_EMBED_FLAG_DEFAULTCHROME, 
00143     "GTK_MOZ_EMBED_FLAG_DEFAULTCHROME", "defaultchrome" },
00144   { GTK_MOZ_EMBED_FLAG_WINDOWBORDERSON, 
00145     "GTK_MOZ_EMBED_FLAG_WINDOWBORDERSON", "windowborderson" },
00146   { GTK_MOZ_EMBED_FLAG_WINDOWCLOSEON,
00147     "GTK_MOZ_EMBED_FLAG_WINDOWCLOSEON", "windowcloseon" },
00148   { GTK_MOZ_EMBED_FLAG_WINDOWRESIZEON,
00149     "GTK_MOZ_EMBED_FLAG_WINDOWRESIZEON", "windowresizeon" },
00150   { GTK_MOZ_EMBED_FLAG_MENUBARON, 
00151     "GTK_MOZ_EMBED_FLAG_MENUBARON", "menubaron" },
00152   { GTK_MOZ_EMBED_FLAG_TOOLBARON,
00153     "GTK_MOZ_EMBED_FLAG_TOOLBARON", "toolbaron" },
00154   { GTK_MOZ_EMBED_FLAG_LOCATIONBARON,
00155     "GTK_MOZ_EMBED_FLAG_LOCATIONBARON", "locationbaron" },
00156   { GTK_MOZ_EMBED_FLAG_STATUSBARON,
00157     "GTK_MOZ_EMBED_FLAG_STATUSBARON", "statusbaron" },
00158   { GTK_MOZ_EMBED_FLAG_PERSONALTOOLBARON,
00159     "GTK_MOZ_EMBED_FLAG_PERSONALTOOLBARON", "personaltoolbaron" },
00160   { GTK_MOZ_EMBED_FLAG_SCROLLBARSON,
00161     "GTK_MOZ_EMBED_FLAG_SCROLLBARSON", "scrollbarson" },
00162   { GTK_MOZ_EMBED_FLAG_TITLEBARON, 
00163     "GTK_MOZ_EMBED_FLAG_TITLEBARON", "titlebaron" },
00164   { GTK_MOZ_EMBED_FLAG_EXTRACHROMEON,
00165     "GTK_MOZ_EMBED_FLAG_EXTRACHROMEON", "extrachromeon" },
00166   { GTK_MOZ_EMBED_FLAG_ALLCHROME, 
00167     "GTK_MOZ_EMBED_FLAG_ALLCHROME", "allchrome" },
00168   { GTK_MOZ_EMBED_FLAG_WINDOWRAISED, 
00169     "GTK_MOZ_EMBED_FLAG_WINDOWRAISED", "windowraised" },
00170   { GTK_MOZ_EMBED_FLAG_WINDOWLOWERED,
00171     "GTK_MOZ_EMBED_FLAG_WINDOWLOWERED", "windowlowered" },
00172   { GTK_MOZ_EMBED_FLAG_CENTERSCREEN,
00173     "GTK_MOZ_EMBED_FLAG_CENTERSCREEN", "centerscreen" },
00174   { GTK_MOZ_EMBED_FLAG_DEPENDENT,
00175     "GTK_MOZ_EMBED_FLAG_DEPENDENT", "dependent" },
00176   { GTK_MOZ_EMBED_FLAG_MODAL,
00177     "GTK_MOZ_EMBED_FLAG_MODAL", "modal" },
00178   { GTK_MOZ_EMBED_FLAG_OPENASDIALOG,
00179     "GTK_MOZ_EMBED_FLAG_OPENASDIALOG", "openasdialog" },
00180   { GTK_MOZ_EMBED_FLAG_OPENASCHROME, 
00181     "GTK_MOZ_EMBED_FLAG_OPENASCHROME", "openaschrome" },
00182   { 0,
00183     NULL, NULL }
00184 };
00185 #endif /* MOZ_WIDGET_GTK */
00186 
00187 class nsIDirectoryServiceProvider;
00188 
00189 // class and instance initialization
00190 
00191 static void
00192 gtk_moz_embed_class_init(GtkMozEmbedClass *klass);
00193 
00194 static void
00195 gtk_moz_embed_init(GtkMozEmbed *embed);
00196 
00197 // GtkObject methods
00198 
00199 static void
00200 gtk_moz_embed_destroy(GtkObject *object);
00201 
00202 // GtkWidget methods
00203 
00204 static void
00205 gtk_moz_embed_realize(GtkWidget *widget);
00206 
00207 static void
00208 gtk_moz_embed_unrealize(GtkWidget *widget);
00209 
00210 static void
00211 gtk_moz_embed_size_allocate(GtkWidget *widget, GtkAllocation *allocation);
00212 
00213 static void
00214 gtk_moz_embed_map(GtkWidget *widget);
00215 
00216 static void
00217 gtk_moz_embed_unmap(GtkWidget *widget);
00218 
00219 #ifdef MOZ_ACCESSIBILITY_ATK
00220 static AtkObject* gtk_moz_embed_get_accessible (GtkWidget *widget);
00221 #endif
00222 
00223 static gint
00224 handle_child_focus_in(GtkWidget     *aWidget,
00225                     GdkEventFocus *aGdkFocusEvent,
00226                     GtkMozEmbed   *aEmbed);
00227 
00228 static gint
00229 handle_child_focus_out(GtkWidget     *aWidget,
00230                      GdkEventFocus *aGdkFocusEvent,
00231                      GtkMozEmbed   *aEmbed);
00232 
00233 #ifdef MOZ_WIDGET_GTK
00234 // signal handlers for tracking the focus in and and focus out events
00235 // on the toplevel window.
00236 
00237 static void
00238 handle_toplevel_focus_in (GtkMozArea    *aArea,
00239                        GtkMozEmbed   *aEmbed);
00240 static void
00241 handle_toplevel_focus_out(GtkMozArea    *aArea,
00242                        GtkMozEmbed   *aEmbed);
00243 #endif /* MOZ_WIDGET_GTK */
00244 
00245 // globals for this type of widget
00246 
00247 static GtkBinClass *embed_parent_class;
00248 
00249 guint moz_embed_signals[EMBED_LAST_SIGNAL] = { 0 };
00250 
00251 // GtkObject + class-related functions
00252 
00253 GtkType
00254 gtk_moz_embed_get_type(void)
00255 {
00256   static GtkType moz_embed_type = 0;
00257   if (!moz_embed_type)
00258   {
00259     static const GtkTypeInfo moz_embed_info =
00260     {
00261       "GtkMozEmbed",
00262       sizeof(GtkMozEmbed),
00263       sizeof(GtkMozEmbedClass),
00264       (GtkClassInitFunc)gtk_moz_embed_class_init,
00265       (GtkObjectInitFunc)gtk_moz_embed_init,
00266       0,
00267       0,
00268       0
00269     };
00270     moz_embed_type = gtk_type_unique(GTK_TYPE_BIN, &moz_embed_info);
00271   }
00272 
00273   return moz_embed_type;
00274 }
00275 
00276 static void
00277 gtk_moz_embed_class_init(GtkMozEmbedClass *klass)
00278 {
00279   GtkContainerClass  *container_class;
00280   GtkWidgetClass     *widget_class;
00281   GtkObjectClass     *object_class;
00282   
00283   container_class = GTK_CONTAINER_CLASS(klass);
00284   widget_class    = GTK_WIDGET_CLASS(klass);
00285   object_class    = GTK_OBJECT_CLASS(klass);
00286 
00287   embed_parent_class = (GtkBinClass *)gtk_type_class(gtk_bin_get_type());
00288 
00289   widget_class->realize = gtk_moz_embed_realize;
00290   widget_class->unrealize = gtk_moz_embed_unrealize;
00291   widget_class->size_allocate = gtk_moz_embed_size_allocate;
00292   widget_class->map = gtk_moz_embed_map;
00293   widget_class->unmap = gtk_moz_embed_unmap;
00294 
00295 #ifdef MOZ_ACCESSIBILITY_ATK
00296   widget_class->get_accessible = gtk_moz_embed_get_accessible;
00297 #endif
00298 
00299   object_class->destroy = gtk_moz_embed_destroy;
00300   
00301   // set up our signals
00302 
00303   moz_embed_signals[LINK_MESSAGE] = 
00304     gtk_signal_new ("link_message",
00305                   GTK_RUN_FIRST,
00306                   GET_OBJECT_CLASS_TYPE(klass),
00307                   GTK_SIGNAL_OFFSET(GtkMozEmbedClass, link_message),
00308                   gtk_marshal_NONE__NONE,
00309                   GTK_TYPE_NONE, 0);
00310   moz_embed_signals[JS_STATUS] =
00311     gtk_signal_new ("js_status",
00312                   GTK_RUN_FIRST,
00313                   GET_OBJECT_CLASS_TYPE(klass),
00314                   GTK_SIGNAL_OFFSET(GtkMozEmbedClass, js_status),
00315                   gtk_marshal_NONE__NONE,
00316                   GTK_TYPE_NONE, 0);
00317   moz_embed_signals[LOCATION] =
00318     gtk_signal_new ("location",
00319                   GTK_RUN_FIRST,
00320                   GET_OBJECT_CLASS_TYPE(klass),
00321                   GTK_SIGNAL_OFFSET(GtkMozEmbedClass, location),
00322                   gtk_marshal_NONE__NONE,
00323                   GTK_TYPE_NONE, 0);
00324   moz_embed_signals[TITLE] = 
00325     gtk_signal_new("title",
00326                  GTK_RUN_FIRST,
00327                  GET_OBJECT_CLASS_TYPE(klass),
00328                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, title),
00329                  gtk_marshal_NONE__NONE,
00330                  GTK_TYPE_NONE, 0);
00331   moz_embed_signals[PROGRESS] =
00332     gtk_signal_new("progress",
00333                  GTK_RUN_FIRST,
00334                  GET_OBJECT_CLASS_TYPE(klass),
00335                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, progress),
00336                  gtk_marshal_NONE__INT_INT,
00337                  GTK_TYPE_NONE, 2, GTK_TYPE_INT, GTK_TYPE_INT);
00338   moz_embed_signals[PROGRESS_ALL] = 
00339     gtk_signal_new("progress_all",
00340                  GTK_RUN_FIRST,
00341                  GET_OBJECT_CLASS_TYPE(klass),
00342                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, progress_all),
00343                  gtkmozembed_VOID__STRING_INT_INT,
00344                  GTK_TYPE_NONE, 3,
00345                  GTK_TYPE_STRING | G_SIGNAL_TYPE_STATIC_SCOPE,
00346                  GTK_TYPE_INT, GTK_TYPE_INT);
00347   moz_embed_signals[NET_STATE] =
00348     gtk_signal_new("net_state",
00349                  GTK_RUN_FIRST,
00350                  GET_OBJECT_CLASS_TYPE(klass),
00351                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, net_state),
00352                  gtkmozembed_VOID__INT_UINT,
00353                  GTK_TYPE_NONE, 2, GTK_TYPE_INT, GTK_TYPE_UINT);
00354   moz_embed_signals[NET_STATE_ALL] =
00355     gtk_signal_new("net_state_all",
00356                  GTK_RUN_FIRST,
00357                  GET_OBJECT_CLASS_TYPE(klass),
00358                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, net_state_all),
00359                  gtkmozembed_VOID__STRING_INT_UINT,
00360                  GTK_TYPE_NONE, 3,
00361                  GTK_TYPE_STRING | G_SIGNAL_TYPE_STATIC_SCOPE,
00362                  GTK_TYPE_INT, GTK_TYPE_UINT);
00363   moz_embed_signals[NET_START] =
00364     gtk_signal_new("net_start",
00365                  GTK_RUN_FIRST,
00366                  GET_OBJECT_CLASS_TYPE(klass),
00367                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, net_start),
00368                  gtk_marshal_NONE__NONE,
00369                  GTK_TYPE_NONE, 0);
00370   moz_embed_signals[NET_STOP] =
00371     gtk_signal_new("net_stop",
00372                  GTK_RUN_FIRST,
00373                  GET_OBJECT_CLASS_TYPE(klass),
00374                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, net_stop),
00375                  gtk_marshal_NONE__NONE,
00376                  GTK_TYPE_NONE, 0);
00377   moz_embed_signals[NEW_WINDOW] =
00378     gtk_signal_new("new_window",
00379                  GTK_RUN_FIRST,
00380                  GET_OBJECT_CLASS_TYPE(klass),
00381                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, new_window),
00382                  gtk_marshal_NONE__POINTER_UINT,
00383                  GTK_TYPE_NONE, 2, GTK_TYPE_POINTER, GTK_TYPE_UINT);
00384   moz_embed_signals[VISIBILITY] =
00385     gtk_signal_new("visibility",
00386                  GTK_RUN_FIRST,
00387                  GET_OBJECT_CLASS_TYPE(klass),
00388                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, visibility),
00389                  gtk_marshal_NONE__BOOL,
00390                  GTK_TYPE_NONE, 1, GTK_TYPE_BOOL);
00391   moz_embed_signals[DESTROY_BROWSER] =
00392     gtk_signal_new("destroy_browser",
00393                  GTK_RUN_FIRST,
00394                  GET_OBJECT_CLASS_TYPE(klass),
00395                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, destroy_brsr),
00396                  gtk_marshal_NONE__NONE,
00397                  GTK_TYPE_NONE, 0);
00398   moz_embed_signals[OPEN_URI] = 
00399     gtk_signal_new("open_uri",
00400                  GTK_RUN_LAST,
00401                  GET_OBJECT_CLASS_TYPE(klass),
00402                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, open_uri),
00403                  gtkmozembed_BOOL__STRING,
00404                  GTK_TYPE_BOOL, 1, GTK_TYPE_STRING |
00405                                    G_SIGNAL_TYPE_STATIC_SCOPE);
00406   moz_embed_signals[SIZE_TO] =
00407     gtk_signal_new("size_to",
00408                  GTK_RUN_LAST,
00409                  GET_OBJECT_CLASS_TYPE(klass),
00410                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, size_to),
00411                  gtk_marshal_NONE__INT_INT,
00412                  GTK_TYPE_NONE, 2, GTK_TYPE_INT, GTK_TYPE_INT);
00413   moz_embed_signals[DOM_KEY_DOWN] =
00414     gtk_signal_new("dom_key_down",
00415                  GTK_RUN_LAST,
00416                  GET_OBJECT_CLASS_TYPE(klass),
00417                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, dom_key_down),
00418                  gtk_marshal_BOOL__POINTER,
00419                  GTK_TYPE_BOOL, 1, GTK_TYPE_POINTER);
00420   moz_embed_signals[DOM_KEY_PRESS] =
00421     gtk_signal_new("dom_key_press",
00422                  GTK_RUN_LAST,
00423                  GET_OBJECT_CLASS_TYPE(klass),
00424                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, dom_key_press),
00425                  gtk_marshal_BOOL__POINTER,
00426                  GTK_TYPE_BOOL, 1, GTK_TYPE_POINTER);
00427   moz_embed_signals[DOM_KEY_UP] =
00428     gtk_signal_new("dom_key_up",
00429                  GTK_RUN_LAST,
00430                  GET_OBJECT_CLASS_TYPE(klass),
00431                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, dom_key_up),
00432                  gtk_marshal_BOOL__POINTER,
00433                  GTK_TYPE_BOOL, 1, GTK_TYPE_POINTER);
00434   moz_embed_signals[DOM_MOUSE_DOWN] =
00435     gtk_signal_new("dom_mouse_down",
00436                  GTK_RUN_LAST,
00437                  GET_OBJECT_CLASS_TYPE(klass),
00438                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, dom_mouse_down),
00439                  gtk_marshal_BOOL__POINTER,
00440                  GTK_TYPE_BOOL, 1, GTK_TYPE_POINTER);
00441   moz_embed_signals[DOM_MOUSE_UP] =
00442     gtk_signal_new("dom_mouse_up",
00443                  GTK_RUN_LAST,
00444                  GET_OBJECT_CLASS_TYPE(klass),
00445                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, dom_mouse_up),
00446                  gtk_marshal_BOOL__POINTER,
00447                  GTK_TYPE_BOOL, 1, GTK_TYPE_POINTER);
00448   moz_embed_signals[DOM_MOUSE_CLICK] =
00449     gtk_signal_new("dom_mouse_click",
00450                  GTK_RUN_LAST,
00451                  GET_OBJECT_CLASS_TYPE(klass),
00452                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, dom_mouse_click),
00453                  gtk_marshal_BOOL__POINTER,
00454                  GTK_TYPE_BOOL, 1, GTK_TYPE_POINTER);
00455   moz_embed_signals[DOM_MOUSE_DBL_CLICK] =
00456     gtk_signal_new("dom_mouse_dbl_click",
00457                  GTK_RUN_LAST,
00458                  GET_OBJECT_CLASS_TYPE(klass),
00459                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, dom_mouse_dbl_click),
00460                  gtk_marshal_BOOL__POINTER,
00461                  GTK_TYPE_BOOL, 1, GTK_TYPE_POINTER);
00462   moz_embed_signals[DOM_MOUSE_OVER] =
00463     gtk_signal_new("dom_mouse_over",
00464                  GTK_RUN_LAST,
00465                  GET_OBJECT_CLASS_TYPE(klass),
00466                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, dom_mouse_over),
00467                  gtk_marshal_BOOL__POINTER,
00468                  GTK_TYPE_BOOL, 1, GTK_TYPE_POINTER);
00469   moz_embed_signals[DOM_MOUSE_OUT] =
00470     gtk_signal_new("dom_mouse_out",
00471                  GTK_RUN_LAST,
00472                  GET_OBJECT_CLASS_TYPE(klass),
00473                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, dom_mouse_out),
00474                  gtk_marshal_BOOL__POINTER,
00475                  GTK_TYPE_BOOL, 1, GTK_TYPE_POINTER);
00476   moz_embed_signals[SECURITY_CHANGE] =
00477     gtk_signal_new("security_change",
00478                  GTK_RUN_LAST,
00479                  GET_OBJECT_CLASS_TYPE(klass),
00480                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, security_change),
00481                  gtk_marshal_NONE__POINTER_UINT,
00482                  GTK_TYPE_NONE, 2, GTK_TYPE_POINTER, GTK_TYPE_UINT);
00483   moz_embed_signals[STATUS_CHANGE] =
00484     gtk_signal_new("status_change",
00485                  GTK_RUN_LAST,
00486                  GET_OBJECT_CLASS_TYPE(klass),
00487                  GTK_SIGNAL_OFFSET(GtkMozEmbedClass, status_change),
00488                  gtkmozembed_VOID__POINTER_INT_POINTER,
00489                  GTK_TYPE_NONE, 3,
00490                  GTK_TYPE_POINTER, GTK_TYPE_INT, GTK_TYPE_POINTER);
00491   moz_embed_signals[DOM_ACTIVATE] =
00492     gtk_signal_new("dom_activate",
00493                    GTK_RUN_LAST,
00494                    GET_OBJECT_CLASS_TYPE(klass),
00495                    GTK_SIGNAL_OFFSET(GtkMozEmbedClass, dom_activate),
00496                    gtk_marshal_BOOL__POINTER,
00497                    GTK_TYPE_BOOL, 1, GTK_TYPE_POINTER);
00498   moz_embed_signals[DOM_FOCUS_IN] =
00499     gtk_signal_new("dom_focus_in",
00500                    GTK_RUN_LAST,
00501                    GET_OBJECT_CLASS_TYPE(klass),
00502                    GTK_SIGNAL_OFFSET(GtkMozEmbedClass, dom_focus_in),
00503                    gtk_marshal_BOOL__POINTER,
00504                    GTK_TYPE_BOOL, 1, GTK_TYPE_POINTER);
00505   moz_embed_signals[DOM_FOCUS_OUT] =
00506     gtk_signal_new("dom_focus_out",
00507                    GTK_RUN_LAST,
00508                    GET_OBJECT_CLASS_TYPE(klass),
00509                    GTK_SIGNAL_OFFSET(GtkMozEmbedClass, dom_focus_out),
00510                    gtk_marshal_BOOL__POINTER,
00511                    GTK_TYPE_BOOL, 1, GTK_TYPE_POINTER);
00512 #ifdef MOZ_WIDGET_GTK
00513   gtk_object_class_add_signals(object_class, moz_embed_signals,
00514                             EMBED_LAST_SIGNAL);
00515 #endif /* MOZ_WIDGET_GTK */
00516 
00517 }
00518 
00519 static void
00520 gtk_moz_embed_init(GtkMozEmbed *embed)
00521 {
00522   EmbedPrivate *priv = new EmbedPrivate();
00523   embed->data = priv;
00524   gtk_widget_set_name(GTK_WIDGET(embed), "gtkmozembed");
00525 
00526 #ifdef MOZ_WIDGET_GTK2
00527   GTK_WIDGET_UNSET_FLAGS(GTK_WIDGET(embed), GTK_NO_WINDOW);
00528 #endif
00529 }
00530 
00531 GtkWidget *
00532 gtk_moz_embed_new(void)
00533 {
00534   return GTK_WIDGET(gtk_type_new(gtk_moz_embed_get_type()));
00535 }
00536 
00537 // GtkObject methods
00538 
00539 static void
00540 gtk_moz_embed_destroy(GtkObject *object)
00541 {
00542   GtkMozEmbed  *embed;
00543   EmbedPrivate *embedPrivate;
00544   
00545   g_return_if_fail(object != NULL);
00546   g_return_if_fail(GTK_IS_MOZ_EMBED(object));
00547 
00548   embed = GTK_MOZ_EMBED(object);
00549   embedPrivate = (EmbedPrivate *)embed->data;
00550 
00551   if (embedPrivate) {
00552 
00553     // Destroy the widget only if it's been Init()ed.
00554     if(embedPrivate->mMozWindowWidget != 0) {
00555       embedPrivate->Destroy();
00556     }
00557 
00558     delete embedPrivate;
00559     embed->data = NULL;
00560   }
00561 }
00562 
00563 // GtkWidget methods
00564 
00565 static void
00566 gtk_moz_embed_realize(GtkWidget *widget)
00567 {
00568   GtkMozEmbed    *embed;
00569   EmbedPrivate   *embedPrivate;
00570   GdkWindowAttr   attributes;
00571   gint            attributes_mask;
00572   
00573   g_return_if_fail(widget != NULL);
00574   g_return_if_fail(GTK_IS_MOZ_EMBED(widget));
00575 
00576   embed = GTK_MOZ_EMBED(widget);
00577   embedPrivate = (EmbedPrivate *)embed->data;
00578 
00579   GTK_WIDGET_SET_FLAGS(widget, GTK_REALIZED);
00580 
00581   attributes.window_type = GDK_WINDOW_CHILD;
00582   attributes.x = widget->allocation.x;
00583   attributes.y = widget->allocation.y;
00584   attributes.width = widget->allocation.width;
00585   attributes.height = widget->allocation.height;
00586   attributes.wclass = GDK_INPUT_OUTPUT;
00587   attributes.visual = gtk_widget_get_visual (widget);
00588   attributes.colormap = gtk_widget_get_colormap (widget);
00589   attributes.event_mask = gtk_widget_get_events (widget) | GDK_EXPOSURE_MASK;
00590 
00591   attributes_mask = GDK_WA_X | GDK_WA_Y | GDK_WA_VISUAL | GDK_WA_COLORMAP;
00592 
00593   widget->window = gdk_window_new (gtk_widget_get_parent_window (widget),
00594                                &attributes, attributes_mask);
00595   gdk_window_set_user_data (widget->window, embed);
00596 
00597   widget->style = gtk_style_attach (widget->style, widget->window);
00598   gtk_style_set_background (widget->style, widget->window, GTK_STATE_NORMAL);
00599 
00600   // initialize the window
00601   nsresult rv;
00602   rv = embedPrivate->Init(embed);
00603   g_return_if_fail(NS_SUCCEEDED(rv));
00604   
00605   PRBool alreadyRealized = PR_FALSE;
00606   rv = embedPrivate->Realize(&alreadyRealized);
00607   g_return_if_fail(NS_SUCCEEDED(rv));
00608 
00609   // if we're already realized we don't need to hook up to anything below
00610   if (alreadyRealized)
00611     return;
00612 
00613   if (embedPrivate->mURI.Length())
00614     embedPrivate->LoadCurrentURI();
00615 
00616   // connect to the focus out event for the child
00617   GtkWidget *child_widget = GTK_BIN(widget)->child;
00618   gtk_signal_connect_while_alive(GTK_OBJECT(child_widget),
00619                              "focus_out_event",
00620                              GTK_SIGNAL_FUNC(handle_child_focus_out),
00621                              embed,
00622                              GTK_OBJECT(child_widget));
00623   gtk_signal_connect_while_alive(GTK_OBJECT(child_widget),
00624                              "focus_in_event",
00625                              GTK_SIGNAL_FUNC(handle_child_focus_in),
00626                              embed,
00627                              GTK_OBJECT(child_widget));
00628 
00629 #ifdef MOZ_WIDGET_GTK
00630   // connect to the toplevel focus out events for the child
00631   GtkMozArea *mozarea = GTK_MOZAREA(child_widget);
00632   gtk_signal_connect_while_alive(GTK_OBJECT(mozarea),
00633                              "toplevel_focus_in",
00634                              GTK_SIGNAL_FUNC(handle_toplevel_focus_in),
00635                              embed,
00636                              GTK_OBJECT(mozarea));
00637 
00638   gtk_signal_connect_while_alive(GTK_OBJECT(mozarea),
00639                              "toplevel_focus_out",
00640                              GTK_SIGNAL_FUNC(handle_toplevel_focus_out),
00641                              embed,
00642                              GTK_OBJECT(mozarea));
00643 #endif /* MOZ_WIDGET_GTK */
00644 }
00645 
00646 static void
00647 gtk_moz_embed_unrealize(GtkWidget *widget)
00648 {
00649   GtkMozEmbed  *embed;
00650   EmbedPrivate *embedPrivate;
00651   
00652   g_return_if_fail(widget != NULL);
00653   g_return_if_fail(GTK_IS_MOZ_EMBED(widget));
00654 
00655   embed = GTK_MOZ_EMBED(widget);
00656   embedPrivate = (EmbedPrivate *)embed->data;
00657 
00658   if (embedPrivate) {
00659     embedPrivate->Unrealize();
00660   }
00661 
00662   if (GTK_WIDGET_CLASS(embed_parent_class)->unrealize)
00663     (* GTK_WIDGET_CLASS(embed_parent_class)->unrealize)(widget);
00664 }
00665 
00666 static void
00667 gtk_moz_embed_size_allocate(GtkWidget *widget, GtkAllocation *allocation)
00668 {
00669   GtkMozEmbed  *embed;
00670   EmbedPrivate *embedPrivate;
00671   
00672   g_return_if_fail(widget != NULL);
00673   g_return_if_fail(GTK_IS_MOZ_EMBED(widget));
00674 
00675   embed = GTK_MOZ_EMBED(widget);
00676   embedPrivate = (EmbedPrivate *)embed->data;
00677   
00678   widget->allocation = *allocation;
00679 
00680   if (GTK_WIDGET_REALIZED(widget))
00681   {
00682     gdk_window_move_resize(widget->window,
00683                         allocation->x, allocation->y,
00684                         allocation->width, allocation->height);
00685     embedPrivate->Resize(allocation->width, allocation->height);
00686   }
00687 }
00688 
00689 static void
00690 gtk_moz_embed_map(GtkWidget *widget)
00691 {
00692   GtkMozEmbed  *embed;
00693   EmbedPrivate *embedPrivate;
00694   
00695   g_return_if_fail(widget != NULL);
00696   g_return_if_fail(GTK_IS_MOZ_EMBED(widget));
00697 
00698   embed = GTK_MOZ_EMBED(widget);
00699   embedPrivate = (EmbedPrivate *)embed->data;
00700 
00701   GTK_WIDGET_SET_FLAGS(widget, GTK_MAPPED);
00702 
00703   embedPrivate->Show();
00704 
00705   gdk_window_show(widget->window);
00706   
00707 }
00708 
00709 static void
00710 gtk_moz_embed_unmap(GtkWidget *widget)
00711 {
00712   GtkMozEmbed  *embed;
00713   EmbedPrivate *embedPrivate;
00714   
00715   g_return_if_fail(widget != NULL);
00716   g_return_if_fail(GTK_IS_MOZ_EMBED(widget));
00717 
00718   embed = GTK_MOZ_EMBED(widget);
00719   embedPrivate = (EmbedPrivate *)embed->data;
00720 
00721   GTK_WIDGET_UNSET_FLAGS(widget, GTK_MAPPED);
00722 
00723   gdk_window_hide(widget->window);
00724 
00725   embedPrivate->Hide();
00726 }
00727 
00728 #ifdef MOZ_ACCESSIBILITY_ATK
00729 static AtkObject*
00730 gtk_moz_embed_get_accessible (GtkWidget *widget)
00731 {
00732   g_return_val_if_fail(widget != NULL, NULL);
00733   g_return_val_if_fail(GTK_IS_MOZ_EMBED(widget), NULL);
00734 
00735   GtkMozEmbed  *embed = GTK_MOZ_EMBED(widget);;
00736   EmbedPrivate *embedPrivate = (EmbedPrivate *)embed->data;
00737   return NS_STATIC_CAST(AtkObject *,
00738                         embedPrivate->GetAtkObjectForCurrentDocument());
00739 }
00740 #endif /* MOZ_ACCESSIBILITY_ATK */
00741 
00742 static gint
00743 handle_child_focus_in(GtkWidget     *aWidget,
00744                     GdkEventFocus *aGdkFocusEvent,
00745                     GtkMozEmbed   *aEmbed)
00746 {
00747   EmbedPrivate *embedPrivate;
00748 
00749   embedPrivate = (EmbedPrivate *)aEmbed->data;
00750 
00751   embedPrivate->ChildFocusIn();
00752 
00753   return FALSE;
00754 }
00755 
00756 static gint
00757 handle_child_focus_out(GtkWidget     *aWidget,
00758                      GdkEventFocus *aGdkFocusEvent,
00759                      GtkMozEmbed   *aEmbed)
00760 {
00761   EmbedPrivate *embedPrivate;
00762 
00763   embedPrivate = (EmbedPrivate *)aEmbed->data;
00764 
00765   embedPrivate->ChildFocusOut();
00766  
00767   return FALSE;
00768 }
00769 
00770 #ifdef MOZ_WIDGET_GTK
00771 void
00772 handle_toplevel_focus_in (GtkMozArea    *aArea,
00773                        GtkMozEmbed   *aEmbed)
00774 {
00775   EmbedPrivate   *embedPrivate;
00776   embedPrivate = (EmbedPrivate *)aEmbed->data;
00777 
00778   embedPrivate->TopLevelFocusIn();
00779 }
00780 
00781 void
00782 handle_toplevel_focus_out(GtkMozArea    *aArea,
00783                        GtkMozEmbed   *aEmbed)
00784 {
00785   EmbedPrivate   *embedPrivate;
00786   embedPrivate = (EmbedPrivate *)aEmbed->data;
00787 
00788   embedPrivate->TopLevelFocusOut();
00789 }
00790 #endif /* MOZ_WIDGET_GTK */
00791 
00792 // Widget methods
00793 
00794 void
00795 gtk_moz_embed_push_startup(void)
00796 {
00797   EmbedPrivate::PushStartup();
00798 }
00799 
00800 void
00801 gtk_moz_embed_pop_startup(void)
00802 {
00803   EmbedPrivate::PopStartup();
00804 }
00805 
00806 void
00807 gtk_moz_embed_set_comp_path(const char *aPath)
00808 {
00809   EmbedPrivate::SetCompPath(aPath);
00810 }
00811 
00812 void
00813 gtk_moz_embed_set_app_components(const nsModuleComponentInfo* aComps,
00814                                  int aNumComponents)
00815 {
00816   EmbedPrivate::SetAppComponents(aComps, aNumComponents);
00817 }
00818 
00819 void
00820 gtk_moz_embed_set_profile_path(const char *aDir, const char *aName)
00821 {
00822   EmbedPrivate::SetProfilePath(aDir, aName);
00823 }
00824 
00825 void
00826 gtk_moz_embed_set_directory_service_provider(nsIDirectoryServiceProvider *appFileLocProvider) {
00827   EmbedPrivate::SetDirectoryServiceProvider(appFileLocProvider);
00828 }
00829 
00830 void
00831 gtk_moz_embed_load_url(GtkMozEmbed *embed, const char *url)
00832 {
00833   EmbedPrivate *embedPrivate;
00834   
00835   g_return_if_fail(embed != NULL);
00836   g_return_if_fail(GTK_IS_MOZ_EMBED(embed));
00837 
00838   embedPrivate = (EmbedPrivate *)embed->data;
00839 
00840   embedPrivate->SetURI(url);
00841 
00842   // If the widget is realized, load the URI.  If it isn't then we
00843   // will load it later.
00844   if (GTK_WIDGET_REALIZED(embed))
00845     embedPrivate->LoadCurrentURI();
00846 }
00847 
00848 void
00849 gtk_moz_embed_stop_load(GtkMozEmbed *embed)
00850 {
00851   EmbedPrivate *embedPrivate;
00852   
00853   g_return_if_fail(embed != NULL);
00854   g_return_if_fail(GTK_IS_MOZ_EMBED(embed));
00855 
00856   embedPrivate = (EmbedPrivate *)embed->data;
00857 
00858   if (embedPrivate->mNavigation)
00859     embedPrivate->mNavigation->Stop(nsIWebNavigation::STOP_ALL);
00860 }
00861 
00862 gboolean
00863 gtk_moz_embed_can_go_back(GtkMozEmbed *embed)
00864 {
00865   PRBool retval = PR_FALSE;
00866   EmbedPrivate *embedPrivate;
00867 
00868   g_return_val_if_fail ((embed != NULL), FALSE);
00869   g_return_val_if_fail (GTK_IS_MOZ_EMBED(embed), FALSE);
00870 
00871   embedPrivate = (EmbedPrivate *)embed->data;
00872 
00873   if (embedPrivate->mNavigation)
00874     embedPrivate->mNavigation->GetCanGoBack(&retval);
00875   return retval;
00876 }
00877 
00878 gboolean
00879 gtk_moz_embed_can_go_forward(GtkMozEmbed *embed)
00880 {
00881   PRBool retval = PR_FALSE;
00882   EmbedPrivate *embedPrivate;
00883 
00884   g_return_val_if_fail ((embed != NULL), FALSE);
00885   g_return_val_if_fail (GTK_IS_MOZ_EMBED(embed), FALSE);
00886 
00887   embedPrivate = (EmbedPrivate *)embed->data;
00888 
00889   if (embedPrivate->mNavigation)
00890     embedPrivate->mNavigation->GetCanGoForward(&retval);
00891   return retval;
00892 }
00893 
00894 void
00895 gtk_moz_embed_go_back(GtkMozEmbed *embed)
00896 {
00897   EmbedPrivate *embedPrivate;
00898 
00899   g_return_if_fail (embed != NULL);
00900   g_return_if_fail (GTK_IS_MOZ_EMBED(embed));
00901 
00902   embedPrivate = (EmbedPrivate *)embed->data;
00903 
00904   if (embedPrivate->mNavigation)
00905     embedPrivate->mNavigation->GoBack();
00906 }
00907 
00908 void
00909 gtk_moz_embed_go_forward(GtkMozEmbed *embed)
00910 {
00911   EmbedPrivate *embedPrivate;
00912 
00913   g_return_if_fail (embed != NULL);
00914   g_return_if_fail (GTK_IS_MOZ_EMBED(embed));
00915 
00916   embedPrivate = (EmbedPrivate *)embed->data;
00917 
00918   if (embedPrivate->mNavigation)
00919     embedPrivate->mNavigation->GoForward();
00920 }
00921 
00922 void
00923 gtk_moz_embed_render_data(GtkMozEmbed *embed, const char *data,
00924                        guint32 len, const char *base_uri,
00925                        const char *mime_type)
00926 {
00927   EmbedPrivate *embedPrivate;
00928 
00929   g_return_if_fail (embed != NULL);
00930   g_return_if_fail (GTK_IS_MOZ_EMBED(embed));
00931 
00932   embedPrivate = (EmbedPrivate *)embed->data;
00933 
00934   embedPrivate->OpenStream(base_uri, mime_type);
00935   embedPrivate->AppendToStream((const PRUint8*)data, len);
00936   embedPrivate->CloseStream();
00937 }
00938 
00939 void
00940 gtk_moz_embed_open_stream(GtkMozEmbed *embed, const char *base_uri,
00941                        const char *mime_type)
00942 {
00943   EmbedPrivate *embedPrivate;
00944 
00945   g_return_if_fail (embed != NULL);
00946   g_return_if_fail (GTK_IS_MOZ_EMBED(embed));
00947   g_return_if_fail (GTK_WIDGET_REALIZED(GTK_WIDGET(embed)));
00948 
00949   embedPrivate = (EmbedPrivate *)embed->data;
00950 
00951   embedPrivate->OpenStream(base_uri, mime_type);
00952 }
00953 
00954 void gtk_moz_embed_append_data(GtkMozEmbed *embed, const char *data,
00955                             guint32 len)
00956 {
00957   EmbedPrivate *embedPrivate;
00958 
00959   g_return_if_fail (embed != NULL);
00960   g_return_if_fail (GTK_IS_MOZ_EMBED(embed));
00961   g_return_if_fail (GTK_WIDGET_REALIZED(GTK_WIDGET(embed)));
00962 
00963   embedPrivate = (EmbedPrivate *)embed->data;
00964   embedPrivate->AppendToStream((const PRUint8*)data, len);
00965 }
00966 
00967 void
00968 gtk_moz_embed_close_stream(GtkMozEmbed *embed)
00969 {
00970   EmbedPrivate *embedPrivate;
00971 
00972   g_return_if_fail (embed != NULL);
00973   g_return_if_fail (GTK_IS_MOZ_EMBED(embed));
00974   g_return_if_fail (GTK_WIDGET_REALIZED(GTK_WIDGET(embed)));
00975 
00976   embedPrivate = (EmbedPrivate *)embed->data;
00977   embedPrivate->CloseStream();
00978 }
00979 
00980 char *
00981 gtk_moz_embed_get_link_message(GtkMozEmbed *embed)
00982 {
00983   char *retval = nsnull;
00984   EmbedPrivate *embedPrivate;
00985 
00986   g_return_val_if_fail ((embed != NULL), (char *)NULL);
00987   g_return_val_if_fail (GTK_IS_MOZ_EMBED(embed), (char *)NULL);
00988 
00989   embedPrivate = (EmbedPrivate *)embed->data;
00990 
00991   if (embedPrivate->mWindow)
00992     retval = NEW_TOOLKIT_STRING(embedPrivate->mWindow->mLinkMessage);
00993 
00994   return retval;
00995 }
00996 
00997 char *
00998 gtk_moz_embed_get_js_status(GtkMozEmbed *embed)
00999 {
01000   char *retval = nsnull;
01001   EmbedPrivate *embedPrivate;
01002 
01003   g_return_val_if_fail ((embed != NULL), (char *)NULL);
01004   g_return_val_if_fail (GTK_IS_MOZ_EMBED(embed), (char *)NULL);
01005 
01006   embedPrivate = (EmbedPrivate *)embed->data;
01007 
01008   if (embedPrivate->mWindow)
01009     retval = NEW_TOOLKIT_STRING(embedPrivate->mWindow->mJSStatus);
01010 
01011   return retval;
01012 }
01013 
01014 char *
01015 gtk_moz_embed_get_title(GtkMozEmbed *embed)
01016 {
01017   char *retval = nsnull;
01018   EmbedPrivate *embedPrivate;
01019 
01020   g_return_val_if_fail ((embed != NULL), (char *)NULL);
01021   g_return_val_if_fail (GTK_IS_MOZ_EMBED(embed), (char *)NULL);
01022 
01023   embedPrivate = (EmbedPrivate *)embed->data;
01024 
01025   if (embedPrivate->mWindow)
01026     retval = NEW_TOOLKIT_STRING(embedPrivate->mWindow->mTitle);
01027 
01028   return retval;
01029 }
01030 
01031 char *
01032 gtk_moz_embed_get_location(GtkMozEmbed *embed)
01033 {
01034   char *retval = nsnull;
01035   EmbedPrivate *embedPrivate;
01036 
01037   g_return_val_if_fail ((embed != NULL), (char *)NULL);
01038   g_return_val_if_fail (GTK_IS_MOZ_EMBED(embed), (char *)NULL);
01039 
01040   embedPrivate = (EmbedPrivate *)embed->data;
01041   
01042   if (!embedPrivate->mURI.IsEmpty())
01043     retval = NEW_TOOLKIT_STRING(embedPrivate->mURI);
01044 
01045   return retval;
01046 }
01047 
01048 void
01049 gtk_moz_embed_reload(GtkMozEmbed *embed, gint32 flags)
01050 {
01051   EmbedPrivate *embedPrivate;
01052 
01053   g_return_if_fail (embed != NULL);
01054   g_return_if_fail (GTK_IS_MOZ_EMBED(embed));
01055 
01056   embedPrivate = (EmbedPrivate *)embed->data;
01057 
01058   PRUint32 reloadFlags = 0;
01059   
01060   // map the external API to the internal web navigation API.
01061   switch (flags) {
01062   case GTK_MOZ_EMBED_FLAG_RELOADNORMAL:
01063     reloadFlags = 0;
01064     break;
01065   case GTK_MOZ_EMBED_FLAG_RELOADBYPASSCACHE:
01066     reloadFlags = nsIWebNavigation::LOAD_FLAGS_BYPASS_CACHE;
01067     break;
01068   case GTK_MOZ_EMBED_FLAG_RELOADBYPASSPROXY:
01069     reloadFlags = nsIWebNavigation::LOAD_FLAGS_BYPASS_PROXY;
01070     break;
01071   case GTK_MOZ_EMBED_FLAG_RELOADBYPASSPROXYANDCACHE:
01072     reloadFlags = (nsIWebNavigation::LOAD_FLAGS_BYPASS_PROXY |
01073                  nsIWebNavigation::LOAD_FLAGS_BYPASS_CACHE);
01074     break;
01075   case GTK_MOZ_EMBED_FLAG_RELOADCHARSETCHANGE:
01076     reloadFlags = nsIWebNavigation::LOAD_FLAGS_CHARSET_CHANGE;
01077     break;
01078   default:
01079     reloadFlags = 0;
01080     break;
01081   }
01082 
01083   embedPrivate->Reload(reloadFlags);
01084 }
01085 
01086 void
01087 gtk_moz_embed_set_chrome_mask(GtkMozEmbed *embed, guint32 flags)
01088 {
01089   EmbedPrivate *embedPrivate;
01090 
01091   g_return_if_fail (embed != NULL);
01092   g_return_if_fail (GTK_IS_MOZ_EMBED(embed));
01093 
01094   embedPrivate = (EmbedPrivate *)embed->data;
01095 
01096   embedPrivate->SetChromeMask(flags);
01097 }
01098 
01099 guint32
01100 gtk_moz_embed_get_chrome_mask(GtkMozEmbed *embed)
01101 {
01102   EmbedPrivate *embedPrivate;
01103 
01104   g_return_val_if_fail ((embed != NULL), 0);
01105   g_return_val_if_fail (GTK_IS_MOZ_EMBED(embed), 0);
01106 
01107   embedPrivate = (EmbedPrivate *)embed->data;
01108 
01109   return embedPrivate->mChromeMask;
01110 }
01111 
01112 #ifdef MOZ_WIDGET_GTK
01113 
01114 GtkType
01115 gtk_moz_embed_progress_flags_get_type(void)
01116 {
01117   static GtkType progress_flags_type = 0;
01118     
01119   if (!progress_flags_type)
01120     progress_flags_type =
01121       gtk_type_register_flags("GtkMozEmbedReloadFlags",
01122                            gtk_moz_embed_progress_flags_values);
01123   return progress_flags_type;
01124 }
01125 
01126 GtkType
01127 gtk_moz_embed_status_enums_get_type(void)
01128 {
01129   static GtkType status_enum_type = 0;
01130 
01131   if (!status_enum_type)
01132     status_enum_type =
01133       gtk_type_register_enum("GtkMozEmbedStatusFlags",
01134                           gtk_moz_embed_status_enums_values);
01135   return status_enum_type;
01136 }
01137 
01138 GtkType
01139 gtk_moz_embed_reload_flags_get_type(void)
01140 {
01141   static GtkType reload_flags_type = 0;
01142 
01143   if (!reload_flags_type)
01144     reload_flags_type =
01145       gtk_type_register_flags("GtkMozEmbedReloadFlags",
01146                            gtk_moz_embed_reload_flags_values);
01147   return reload_flags_type;
01148 }
01149 
01150 GtkType
01151 gtk_moz_embed_chrome_flags_get_type(void)
01152 {
01153   static GtkType chrome_flags_type = 0;
01154 
01155   if (!chrome_flags_type)
01156     chrome_flags_type = 
01157       gtk_type_register_flags("GtkMozEmbedChromeFlags",
01158                            gtk_moz_embed_chrome_flags_values);
01159   return chrome_flags_type;
01160 }
01161 
01162 #endif /* MOZ_WIDGET_GTK */
01163 
01164 void
01165 gtk_moz_embed_get_nsIWebBrowser  (GtkMozEmbed *embed, nsIWebBrowser **retval)
01166 {
01167   EmbedPrivate *embedPrivate;
01168 
01169   g_return_if_fail (embed != NULL);
01170   g_return_if_fail (GTK_IS_MOZ_EMBED(embed));
01171 
01172   embedPrivate = (EmbedPrivate *)embed->data;
01173   
01174   if (embedPrivate->mWindow)
01175     embedPrivate->mWindow->GetWebBrowser(retval);
01176 }
01177 
01178 PRUnichar *
01179 gtk_moz_embed_get_title_unichar (GtkMozEmbed *embed)
01180 {
01181   PRUnichar *retval = nsnull;
01182   EmbedPrivate *embedPrivate;
01183                    
01184   g_return_val_if_fail ((embed != NULL), (PRUnichar *)NULL);
01185   g_return_val_if_fail (GTK_IS_MOZ_EMBED(embed), (PRUnichar *)NULL);
01186   
01187   embedPrivate = (EmbedPrivate *)embed->data;
01188                    
01189   if (embedPrivate->mWindow)
01190     retval = ToNewUnicode(embedPrivate->mWindow->mTitle);
01191                    
01192   return retval;
01193 }
01194 
01195 PRUnichar *
01196 gtk_moz_embed_get_js_status_unichar (GtkMozEmbed *embed)
01197 {
01198   PRUnichar *retval = nsnull;
01199   EmbedPrivate *embedPrivate;
01200                    
01201   g_return_val_if_fail ((embed != NULL), (PRUnichar *)NULL);
01202   g_return_val_if_fail (GTK_IS_MOZ_EMBED(embed), (PRUnichar *)NULL);
01203   
01204   embedPrivate = (EmbedPrivate *)embed->data;
01205                    
01206   if (embedPrivate->mWindow)
01207     retval = ToNewUnicode(embedPrivate->mWindow->mJSStatus);
01208                    
01209   return retval;
01210 }
01211 
01212 PRUnichar *
01213 gtk_moz_embed_get_link_message_unichar (GtkMozEmbed *embed)
01214 {
01215   PRUnichar *retval = nsnull;
01216   EmbedPrivate *embedPrivate;
01217                    
01218   g_return_val_if_fail ((embed != NULL), (PRUnichar *)NULL);
01219   g_return_val_if_fail (GTK_IS_MOZ_EMBED(embed), (PRUnichar *)NULL);
01220   
01221   embedPrivate = (EmbedPrivate *)embed->data;
01222                    
01223   if (embedPrivate->mWindow)
01224     retval = ToNewUnicode(embedPrivate->mWindow->mLinkMessage);
01225                    
01226   return retval;
01227 }
01228 
01229 // class and instance initialization
01230 
01231 static void
01232 gtk_moz_embed_single_class_init(GtkMozEmbedSingleClass *klass);
01233 
01234 static void
01235 gtk_moz_embed_single_init(GtkMozEmbedSingle *embed);
01236 
01237 GtkMozEmbedSingle *
01238 gtk_moz_embed_single_new(void);
01239 
01240 enum {
01241   NEW_WINDOW_ORPHAN,
01242   SINGLE_LAST_SIGNAL
01243 };
01244 
01245 guint moz_embed_single_signals[SINGLE_LAST_SIGNAL] = { 0 };
01246 
01247 // GtkObject + class-related functions
01248 
01249 GtkType
01250 gtk_moz_embed_single_get_type(void)
01251 {
01252   static GtkType moz_embed_single_type = 0;
01253   if (!moz_embed_single_type)
01254   {
01255     static const GtkTypeInfo moz_embed_single_info =
01256     {
01257       "GtkMozEmbedSingle",
01258       sizeof(GtkMozEmbedSingle),
01259       sizeof(GtkMozEmbedSingleClass),
01260       (GtkClassInitFunc)gtk_moz_embed_single_class_init,
01261       (GtkObjectInitFunc)gtk_moz_embed_single_init,
01262       0,
01263       0,
01264       0
01265     };
01266     moz_embed_single_type = gtk_type_unique(GTK_TYPE_OBJECT,
01267                                        &moz_embed_single_info);
01268   }
01269 
01270   return moz_embed_single_type;
01271 }
01272 
01273 static void
01274 gtk_moz_embed_single_class_init(GtkMozEmbedSingleClass *klass)
01275 {
01276   GtkObjectClass     *object_class;
01277 
01278   object_class    = GTK_OBJECT_CLASS(klass);
01279 
01280   // set up our signals
01281 
01282   moz_embed_single_signals[NEW_WINDOW_ORPHAN] =
01283     gtk_signal_new("new_window_orphan",
01284                  GTK_RUN_FIRST,
01285                  GET_OBJECT_CLASS_TYPE(klass),
01286                  GTK_SIGNAL_OFFSET(GtkMozEmbedSingleClass,
01287                                  new_window_orphan),
01288                  gtk_marshal_NONE__POINTER_UINT,
01289                  GTK_TYPE_NONE, 2, GTK_TYPE_POINTER, GTK_TYPE_UINT);
01290   
01291 #ifdef MOZ_WIDGET_GTK
01292   gtk_object_class_add_signals(object_class, moz_embed_single_signals,
01293                             SINGLE_LAST_SIGNAL);
01294 #endif /* MOZ_WIDGET_GTK */
01295 }
01296 
01297 static void
01298 gtk_moz_embed_single_init(GtkMozEmbedSingle *embed)
01299 {
01300   // this is a placeholder for later in case we need to stash data at
01301   // a later data and maintain backwards compatibility.
01302   embed->data = nsnull;
01303 }
01304 
01305 GtkMozEmbedSingle *
01306 gtk_moz_embed_single_new(void)
01307 {
01308   return (GtkMozEmbedSingle *)gtk_type_new(gtk_moz_embed_single_get_type());
01309 }
01310 
01311 GtkMozEmbedSingle *
01312 gtk_moz_embed_single_get(void)
01313 {
01314   static GtkMozEmbedSingle *singleton_object = nsnull;
01315   if (!singleton_object)
01316   {
01317     singleton_object = gtk_moz_embed_single_new();
01318   }
01319 
01320   return singleton_object;
01321 }
01322 
01323 // our callback from the window creator service
01324 void
01325 gtk_moz_embed_single_create_window(GtkMozEmbed **aNewEmbed,
01326                                guint         aChromeFlags)
01327 {
01328   GtkMozEmbedSingle *single = gtk_moz_embed_single_get();
01329 
01330   *aNewEmbed = nsnull;
01331 
01332   if (!single)
01333     return;
01334 
01335   gtk_signal_emit(GTK_OBJECT(single),
01336                 moz_embed_single_signals[NEW_WINDOW_ORPHAN],
01337                 aNewEmbed, aChromeFlags);
01338 
01339 }