diff options
Diffstat (limited to 'WebKit/gtk')
22 files changed, 1149 insertions, 71 deletions
diff --git a/WebKit/gtk/ChangeLog b/WebKit/gtk/ChangeLog index 79e4a0b..4073840 100644 --- a/WebKit/gtk/ChangeLog +++ b/WebKit/gtk/ChangeLog @@ -1,3 +1,210 @@ +2010-08-25 Martin Robinson <mrobinson@igalia.com> + + Reviewed by Gustavo Noronha Silva. + + confirm dialog should show OK/Cancel instead of Yes/No for consistency + https://bugs.webkit.org/show_bug.cgi?id=32877 + + Change the button labels for the fallback confirmation dialog to be + OK and Cancel. + + * webkit/webkitwebview.cpp: + (webkit_web_view_script_dialog): + +2010-08-25 Martin Robinson <mrobinson@igalia.com> + + Reviewed by Gustavo Noronha Silva. + + Cairo and EFL port shouldn't depend on glib. + https://bugs.webkit.org/show_bug.cgi?id=44354 + + Replace occurrences of GRefPtr and adoptGRef with PlatformRefPtr and + adoptPlatformRef. + + * WebCoreSupport/ChromeClientGtk.cpp: + (WebKit::ChromeClient::requestGeolocationPermissionForFrame): + * WebCoreSupport/DragClientGtk.cpp: + (WebKit::DragClient::startDrag): + * WebCoreSupport/EditorClientGtk.h: + * WebCoreSupport/FrameLoaderClientGtk.cpp: + (WebKit::FrameLoaderClient::dispatchWillSendRequest): + (WebKit::FrameLoaderClient::dispatchDecidePolicyForMIMEType): + (WebKit::FrameLoaderClient::createPlugin): + * WebCoreSupport/FullscreenVideoController.h: + * WebCoreSupport/InspectorClientGtk.cpp: + (WebKit::InspectorClient::populateSetting): + (WebKit::InspectorClient::storeSetting): + * webkit/webkitdownload.cpp: + (webkit_download_error): + * webkit/webkitnetworkrequest.cpp: + (webkit_network_request_new_with_core_request): + * webkit/webkitnetworkresponse.cpp: + (webkit_network_response_new_with_core_response): + +2010-08-24 Xan Lopez <xlopez@igalia.com> + + Reviewed by Martin Robinson. + + Set a device to the event struct when building with GTK+ 3.x, it's + mandatory. + + * tests/testcopyandpaste.c: + (runPasteTestCallback): + +2010-08-24 Martin Robinson <mrobinson@igalia.com> + + Build fix for GTK+. + + * tests/testkeyevents.c: + (key_press_event_cb): + (key_release_event_cb): + +2010-08-24 Martin Robinson <mrobinson@igalia.com> + + Reviewed by Xan Lopez. + + [GTK] GTK3: EventSender and API tests should use gdk_event_new when synthesizing events + https://bugs.webkit.org/show_bug.cgi?id=44534 + + Fix an issue where a GdkEvent* is treated like a GdkEvent. + + * tests/testkeyevents.c: + (key_press_event_cb): + (key_release_event_cb): + +2010-08-24 Martin Robinson <mrobinson@igalia.com> + + Reviewed by Xan Lopez. + + [GTK] GTK3: EventSender and API tests should use gdk_event_new when synthesizing events + https://bugs.webkit.org/show_bug.cgi?id=44534 + + * tests/testcopyandpaste.c: + (runPasteTestCallback): Switch to using gdk_event_new and also reference the GdkWindow. + when setting it on the event. It is dereferenced by gdk_event_free(...). + * tests/testhittestresult.c: + (load_status_cb): Switch to using gdk_event_new. + +2010-08-24 Gustavo Noronha Silva <gustavo.noronha@collabora.co.uk> + + Rubber-stamped by Xan Lopez. + + Do not initialize the GSettings object in webkit_init - the other + call sites are always called in the main thread so this is + unnecessary. + + * webkit/webkitprivate.cpp: + (webkit_init): + +2010-08-20 Martin Robinson <mrobinson@igalia.com> + + Reviewed by Pavel Feldman. + + Web Inspector: Inspector tests were disabled for GTK. + https://bugs.webkit.org/show_bug.cgi?id=43977 + + Allow setting the inspector resources path via an environment variables + and add a method, inspectorFilesPath, to the WebKit InspectorClient that + encapsulates this logic. + + * WebCoreSupport/InspectorClientGtk.cpp: + (WebKit::InspectorClient::openInspectorFrontend): Use the new inspectorFilesPath method to + get the path to the resource. + (WebKit::InspectorClient::inspectorFilesPath): Added. + (WebKit::InspectorFrontendClient::localizedStringsURL): Use inspectorFilesPath method. + * WebCoreSupport/InspectorClientGtk.h: Add method and member variables for caching the result. + +2010-08-19 Gustavo Noronha Silva <gustavo.noronha@collabora.co.uk> + + Reviewed by Kenneth Rohde Christiansen. + + [Gtk] Enable view mode media feature layout test + https://bugs.webkit.org/show_bug.cgi?id=43278 + + Add the view-mode property, to control the WebCore page's viewMode. + + * docs/webkitgtk-sections.txt: + * webkit/webkitwebview.cpp: + (webkit_web_view_get_property): + (webkit_web_view_set_property): + (webkit_web_view_class_init): + (webkit_web_view_set_view_mode): + (webkit_web_view_get_view_mode): + * webkit/webkitwebview.h: + +2010-08-19 Philippe Normand <pnormand@igalia.com> + + Reviewed by Gustavo Noronha Silva. + + [GStreamer] GTK XOverlay support in GStreamerGWorld + https://bugs.webkit.org/show_bug.cgi?id=39474 + + New FullscreenVideoController object, private in the webview. It + is created when the user presses the fullscreen button of the + video controls. Video is displayed in fullscreen, controls are + displayed when the user moves the mouse and when the video is + paused. There's also basic keyboard shortcuts support: F/f to + leave fullscreen, space to toggle play/pause and up/down to + control volume. + + * WebCoreSupport/ChromeClientGtk.cpp: + (WebKit::ChromeClient::supportsFullscreenForNode): + (WebKit::ChromeClient::enterFullscreenForNode): + (WebKit::ChromeClient::exitFullscreenForNode): + * WebCoreSupport/ChromeClientGtk.h: + * WebCoreSupport/FullscreenVideoController.cpp: Added. + (hideHudCallback): + (onFullscreenGtkMotionNotifyEvent): + (onFullscreenGtkActiveNotification): + (onFullscreenGtkConfigureEvent): + (onFullscreenGtkDestroy): + (togglePlayPauseActivated): + (exitFullscreenActivated): + (progressBarUpdateCallback): + (timeScaleButtonPressed): + (timeScaleButtonReleased): + (timeScaleValueChanged): + (volumeValueChanged): + (playerVolumeChangedCallback): + (playerMuteChangedCallback): + (FullscreenVideoController::FullscreenVideoController): + (FullscreenVideoController::~FullscreenVideoController): + (FullscreenVideoController::setMediaElement): + (FullscreenVideoController::gtkConfigure): + (FullscreenVideoController::showHud): + (FullscreenVideoController::hideHud): + (onFullscreenGtkKeyPressEvent): + (FullscreenVideoController::enterFullscreen): + (FullscreenVideoController::updateHudPosition): + (FullscreenVideoController::exitOnUserRequest): + (FullscreenVideoController::exitFullscreen): + (FullscreenVideoController::canPlay): + (FullscreenVideoController::play): + (FullscreenVideoController::pause): + (FullscreenVideoController::playStateChanged): + (FullscreenVideoController::togglePlay): + (FullscreenVideoController::volume): + (FullscreenVideoController::muted): + (FullscreenVideoController::setVolume): + (FullscreenVideoController::volumeChanged): + (FullscreenVideoController::muteChanged): + (FullscreenVideoController::currentTime): + (FullscreenVideoController::setCurrentTime): + (FullscreenVideoController::duration): + (FullscreenVideoController::percentLoaded): + (FullscreenVideoController::beginSeek): + (FullscreenVideoController::doSeek): + (FullscreenVideoController::endSeek): + (timeToString): + (FullscreenVideoController::updateHudProgressBar): + (FullscreenVideoController::createHud): + * WebCoreSupport/FullscreenVideoController.h: Added. + (FullscreenVideoController::mediaElement): + * webkit/webkitprivate.cpp: + (webkit_web_view_enter_fullscreen): + (webkit_web_view_exit_fullscreen): + * webkit/webkitprivate.h: + 2010-08-18 Gustavo Noronha Silva <gustavo.noronha@collabora.co.uk> Reviewed by Martin Robinson. diff --git a/WebKit/gtk/WebCoreSupport/ChromeClientGtk.cpp b/WebKit/gtk/WebCoreSupport/ChromeClientGtk.cpp index 185ac16..7e4090b 100644 --- a/WebKit/gtk/WebCoreSupport/ChromeClientGtk.cpp +++ b/WebKit/gtk/WebCoreSupport/ChromeClientGtk.cpp @@ -30,6 +30,7 @@ #include "FloatRect.h" #include "FrameLoadRequest.h" #include "GtkVersioning.h" +#include "HTMLNames.h" #include "IntRect.h" #include "HitTestResult.h" #include "Icon.h" @@ -611,7 +612,7 @@ void ChromeClient::requestGeolocationPermissionForFrame(Frame* frame, Geolocatio WebKitWebFrame* webFrame = kit(frame); WebKitWebView* webView = getViewFromFrame(webFrame); - GRefPtr<WebKitGeolocationPolicyDecision> policyDecision(adoptGRef(webkit_geolocation_policy_decision_new(webFrame, geolocation))); + PlatformRefPtr<WebKitGeolocationPolicyDecision> policyDecision(adoptPlatformRef(webkit_geolocation_policy_decision_new(webFrame, geolocation))); gboolean isHandled = FALSE; g_signal_emit_by_name(webView, "geolocation-policy-decision-requested", webFrame, policyDecision.get(), &isHandled); @@ -641,4 +642,28 @@ PassRefPtr<WebCore::SearchPopupMenu> ChromeClient::createSearchPopupMenu(WebCore return adoptRef(new SearchPopupMenuGtk(client)); } +#if ENABLE(VIDEO) + +bool ChromeClient::supportsFullscreenForNode(const Node* node) +{ + return node->hasTagName(HTMLNames::videoTag); +} + +void ChromeClient::enterFullscreenForNode(Node* node) +{ + WebCore::Frame* frame = node->document()->frame(); + WebKitWebFrame* webFrame = kit(frame); + WebKitWebView* webView = getViewFromFrame(webFrame); + webkitWebViewEnterFullscreen(webView, node); +} + +void ChromeClient::exitFullscreenForNode(Node* node) +{ + WebCore::Frame* frame = node->document()->frame(); + WebKitWebFrame* webFrame = kit(frame); + WebKitWebView* webView = getViewFromFrame(webFrame); + webkitWebViewExitFullscreen(webView); +} +#endif + } diff --git a/WebKit/gtk/WebCoreSupport/ChromeClientGtk.h b/WebKit/gtk/WebCoreSupport/ChromeClientGtk.h index e3be1c2..21c4677 100644 --- a/WebKit/gtk/WebCoreSupport/ChromeClientGtk.h +++ b/WebKit/gtk/WebCoreSupport/ChromeClientGtk.h @@ -133,6 +133,11 @@ namespace WebKit { virtual bool selectItemWritingDirectionIsNatural(); virtual PassRefPtr<WebCore::PopupMenu> createPopupMenu(WebCore::PopupMenuClient*) const; virtual PassRefPtr<WebCore::SearchPopupMenu> createSearchPopupMenu(WebCore::PopupMenuClient*) const; +#if ENABLE(VIDEO) + virtual bool supportsFullscreenForNode(const WebCore::Node*); + virtual void enterFullscreenForNode(WebCore::Node*); + virtual void exitFullscreenForNode(WebCore::Node*); +#endif private: WebKitWebView* m_webView; diff --git a/WebKit/gtk/WebCoreSupport/DragClientGtk.cpp b/WebKit/gtk/WebCoreSupport/DragClientGtk.cpp index efce3dc..b6075b6 100644 --- a/WebKit/gtk/WebCoreSupport/DragClientGtk.cpp +++ b/WebKit/gtk/WebCoreSupport/DragClientGtk.cpp @@ -73,7 +73,7 @@ void DragClient::startDrag(DragImageRef image, const IntPoint& dragImageOrigin, WebKitWebView* webView = webkit_web_frame_get_web_view(kit(frame)); RefPtr<DataObjectGtk> dataObject = clipboardGtk->dataObject(); - GRefPtr<GtkTargetList> targetList(clipboardGtk->helper()->targetListForDataObject(dataObject.get())); + PlatformRefPtr<GtkTargetList> targetList(clipboardGtk->helper()->targetListForDataObject(dataObject.get())); GOwnPtr<GdkEvent> currentEvent(gtk_get_current_event()); GdkDragContext* context = gtk_drag_begin(GTK_WIDGET(m_webView), targetList.get(), dragOperationToGdkDragActions(clipboard->sourceOperation()), 1, currentEvent.get()); diff --git a/WebKit/gtk/WebCoreSupport/EditorClientGtk.h b/WebKit/gtk/WebCoreSupport/EditorClientGtk.h index 3e881fa..efb734f 100644 --- a/WebKit/gtk/WebCoreSupport/EditorClientGtk.h +++ b/WebKit/gtk/WebCoreSupport/EditorClientGtk.h @@ -141,7 +141,7 @@ namespace WebKit { bool m_treatContextCommitAsKeyEvent; GOwnPtr<gchar> m_pendingComposition; Vector<const char*> m_pendingEditorCommands; - GRefPtr<GtkWidget> m_nativeWidget; + PlatformRefPtr<GtkWidget> m_nativeWidget; }; } diff --git a/WebKit/gtk/WebCoreSupport/FrameLoaderClientGtk.cpp b/WebKit/gtk/WebCoreSupport/FrameLoaderClientGtk.cpp index 98ac4a1..2cf4f36 100644 --- a/WebKit/gtk/WebCoreSupport/FrameLoaderClientGtk.cpp +++ b/WebKit/gtk/WebCoreSupport/FrameLoaderClientGtk.cpp @@ -201,19 +201,19 @@ static char* toString(unsigned long identifier) void FrameLoaderClient::dispatchWillSendRequest(WebCore::DocumentLoader* loader, unsigned long identifier, ResourceRequest& request, const ResourceResponse& redirectResponse) { - GRefPtr<WebKitNetworkResponse> networkResponse(0); + PlatformRefPtr<WebKitNetworkResponse> networkResponse(0); // We are adding one more resource to the load, or maybe we are // just redirecting a load. if (redirectResponse.isNull()) static_cast<WebKit::DocumentLoader*>(loader)->increaseLoadCount(identifier); else - networkResponse = adoptGRef(webkit_network_response_new_with_core_response(redirectResponse)); + networkResponse = adoptPlatformRef(webkit_network_response_new_with_core_response(redirectResponse)); WebKitWebView* webView = getViewFromFrame(m_frame); GOwnPtr<gchar> identifierString(toString(identifier)); WebKitWebResource* webResource = webkit_web_view_get_resource(webView, identifierString.get()); - GRefPtr<WebKitNetworkRequest> networkRequest(adoptGRef(webkit_network_request_new_with_core_request(request))); + PlatformRefPtr<WebKitNetworkRequest> networkRequest(adoptPlatformRef(webkit_network_request_new_with_core_request(request))); if (!redirectResponse.isNull()) { // This is a redirect, so we need to update the WebResource's knowledge @@ -314,7 +314,7 @@ void FrameLoaderClient::dispatchDecidePolicyForMIMEType(FramePolicyFunction poli if (isHandled) return; - GRefPtr<WebKitNetworkResponse> networkResponse(adoptGRef(webkit_web_frame_get_network_response(m_frame))); + PlatformRefPtr<WebKitNetworkResponse> networkResponse(adoptPlatformRef(webkit_web_frame_get_network_response(m_frame))); if (networkResponse) { ResourceResponse response = core(networkResponse.get()); if (response.isAttachment()) { @@ -449,7 +449,7 @@ PassRefPtr<Widget> FrameLoaderClient::createPlugin(const IntSize& pluginSize, HT CString mimeTypeString = mimeType.utf8(); ASSERT(paramNames.size() == paramValues.size()); - GRefPtr<GHashTable> hash = adoptGRef(g_hash_table_new_full(g_str_hash, g_str_equal, g_free, g_free)); + PlatformRefPtr<GHashTable> hash = adoptPlatformRef(g_hash_table_new_full(g_str_hash, g_str_equal, g_free, g_free)); for (unsigned i = 0; i < paramNames.size(); ++i) { g_hash_table_insert(hash.get(), g_strdup(paramNames[i].utf8().data()), diff --git a/WebKit/gtk/WebCoreSupport/FullscreenVideoController.cpp b/WebKit/gtk/WebCoreSupport/FullscreenVideoController.cpp new file mode 100644 index 0000000..c95dcff --- /dev/null +++ b/WebKit/gtk/WebCoreSupport/FullscreenVideoController.cpp @@ -0,0 +1,575 @@ +/* + * Copyright (C) 2010 Igalia S.L + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public License + * along with this library; see the file COPYING.LIB. If not, write to + * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + * Boston, MA 02110-1301, USA. + */ + +#include "config.h" + +#if ENABLE(VIDEO) + +#include "FullscreenVideoController.h" + +#include "MediaPlayer.h" + +#include <gdk/gdk.h> +#include <gdk/gdkkeysyms.h> +#include <glib/gi18n-lib.h> +#include <gst/gst.h> +#include <gtk/gtk.h> + +using namespace std; +using namespace WebCore; + +#define HUD_AUTO_HIDE_INTERVAL 3000 // 3 seconds +#define PROGRESS_BAR_UPDATE_INTERVAL 150 // 150ms +#define VOLUME_UP_OFFSET 0.05 // 5% +#define VOLUME_DOWN_OFFSET 0.05 // 5% + +// Use symbolic icons only if we build with GTK+-3 support. They could +// be enabled for the GTK+2 build but we'd need to bump the required +// version to at least 2.22. +#if GTK_MAJOR_VERSION < 3 +#define PLAY_ICON_NAME "media-playback-start" +#define PAUSE_ICON_NAME "media-playback-pause" +#define EXIT_FULLSCREEN_ICON_NAME "view-restore" +#else +#define PLAY_ICON_NAME "media-playback-start-symbolic" +#define PAUSE_ICON_NAME "media-playback-pause-symbolic" +#define EXIT_FULLSCREEN_ICON_NAME "view-restore-symbolic" +#endif + +static gboolean hideHudCallback(FullscreenVideoController* controller) +{ + controller->hideHud(); + return FALSE; +} + +static gboolean onFullscreenGtkMotionNotifyEvent(GtkWidget* widget, GdkEventMotion* event, FullscreenVideoController* controller) +{ + controller->showHud(true); + return TRUE; +} + +static void onFullscreenGtkActiveNotification(GtkWidget* widget, GParamSpec* property, FullscreenVideoController* controller) +{ + if (!gtk_window_is_active(GTK_WINDOW(widget))) + controller->hideHud(); +} + +static gboolean onFullscreenGtkConfigureEvent(GtkWidget* widget, GdkEventConfigure* event, FullscreenVideoController* controller) +{ + controller->gtkConfigure(event); + return TRUE; +} + +static void onFullscreenGtkDestroy(GtkWidget* widget, FullscreenVideoController* controller) +{ + controller->exitFullscreen(); +} + +static void togglePlayPauseActivated(GtkAction* action, FullscreenVideoController* controller) +{ + controller->togglePlay(); +} + +static void exitFullscreenActivated(GtkAction* action, FullscreenVideoController* controller) +{ + controller->exitOnUserRequest(); +} + +static gboolean progressBarUpdateCallback(FullscreenVideoController* controller) +{ + return controller->updateHudProgressBar(); +} + +static gboolean timeScaleButtonPressed(GtkWidget* widget, GdkEventButton* event, FullscreenVideoController* controller) +{ + if (event->type != GDK_BUTTON_PRESS) + return FALSE; + + controller->beginSeek(); + return FALSE; +} + +static gboolean timeScaleButtonReleased(GtkWidget* widget, GdkEventButton* event, FullscreenVideoController* controller) +{ + controller->endSeek(); + return FALSE; +} + +static void timeScaleValueChanged(GtkWidget* widget, FullscreenVideoController* controller) +{ + controller->doSeek(); +} + +static void volumeValueChanged(GtkScaleButton *button, gdouble value, FullscreenVideoController* controller) +{ + controller->setVolume(static_cast<float>(value)); +} + +void playerVolumeChangedCallback(GObject *element, GParamSpec *pspec, FullscreenVideoController* controller) +{ + controller->volumeChanged(); +} + +void playerMuteChangedCallback(GObject *element, GParamSpec *pspec, FullscreenVideoController* controller) +{ + controller->muteChanged(); +} + +FullscreenVideoController::FullscreenVideoController() + : m_hudTimeoutId(0) + , m_progressBarUpdateId(0) + , m_seekLock(false) + , m_window(0) + , m_hudWindow(0) +{ +} + +FullscreenVideoController::~FullscreenVideoController() +{ + exitFullscreen(); +} + +void FullscreenVideoController::setMediaElement(HTMLMediaElement* mediaElement) +{ + if (mediaElement == m_mediaElement) + return; + + m_mediaElement = mediaElement; + if (!m_mediaElement) { + // Can't do full-screen, just get out + exitFullscreen(); + } +} + +void FullscreenVideoController::gtkConfigure(GdkEventConfigure* event) +{ + updateHudPosition(); +} + +void FullscreenVideoController::showHud(bool autoHide) +{ + if (!m_hudWindow) + return; + + if (m_hudTimeoutId) { + g_source_remove(m_hudTimeoutId); + m_hudTimeoutId = 0; + } + + // Show the cursor. + GdkWindow* window = gtk_widget_get_window(m_window); + gdk_window_set_cursor(window, m_cursor.get()); + + // Update the progress bar immediately before showing the window. + updateHudProgressBar(); + gtk_widget_show_all(m_hudWindow); + updateHudPosition(); + + // Start periodic updates of the progress bar. + if (!m_progressBarUpdateId) + m_progressBarUpdateId = g_timeout_add(PROGRESS_BAR_UPDATE_INTERVAL, reinterpret_cast<GSourceFunc>(progressBarUpdateCallback), this); + + // Hide the hud in few seconds, if requested. + if (autoHide) + m_hudTimeoutId = g_timeout_add(HUD_AUTO_HIDE_INTERVAL, reinterpret_cast<GSourceFunc>(hideHudCallback), this); +} + +void FullscreenVideoController::hideHud() +{ + if (m_hudTimeoutId) { + g_source_remove(m_hudTimeoutId); + m_hudTimeoutId = 0; + } + + if (!m_hudWindow) + return; + + // Keep the hud visible if a seek is in progress or if the volume + // popup is visible. + GtkWidget* volumePopup = gtk_scale_button_get_popup(GTK_SCALE_BUTTON(m_volumeButton)); + if (m_seekLock || gtk_widget_get_visible(volumePopup)) { + showHud(true); + return; + } + + GdkWindow* window = gtk_widget_get_window(m_window); + GdkCursor* cursor = gdk_cursor_new(GDK_BLANK_CURSOR); + gdk_window_set_cursor(window, cursor); + + gtk_widget_hide_all(m_hudWindow); + + if (m_progressBarUpdateId) { + g_source_remove(m_progressBarUpdateId); + m_progressBarUpdateId = 0; + } +} + +static gboolean onFullscreenGtkKeyPressEvent(GtkWidget* widget, GdkEventKey* event, FullscreenVideoController* controller) +{ + switch (event->keyval) { + case GDK_Escape: + case 'f': + case 'F': + controller->exitOnUserRequest(); + break; + case GDK_space: + case GDK_Return: + controller->togglePlay(); + break; + case GDK_Up: + // volume up + controller->setVolume(controller->volume() + VOLUME_UP_OFFSET); + break; + case GDK_Down: + // volume down + controller->setVolume(controller->volume() - VOLUME_DOWN_OFFSET); + break; + default: + break; + } + + return TRUE; +} + + +void FullscreenVideoController::enterFullscreen() +{ + if (!m_mediaElement) + return; + + if (m_mediaElement->platformMedia().type != WebCore::PlatformMedia::GStreamerGWorldType) + return; + + m_gstreamerGWorld = m_mediaElement->platformMedia().media.gstreamerGWorld; + if (!m_gstreamerGWorld->enterFullscreen()) + return; + + m_window = reinterpret_cast<GtkWidget*>(m_gstreamerGWorld->platformVideoWindow()->window()); + + GstElement* pipeline = m_gstreamerGWorld->pipeline(); + g_signal_connect(pipeline, "notify::volume", G_CALLBACK(playerVolumeChangedCallback), this); + g_signal_connect(pipeline, "notify::mute", G_CALLBACK(playerMuteChangedCallback), this); + + if (!m_hudWindow) + createHud(); + + // Ensure black background. + GdkColor color; + gdk_color_parse("black", &color); + gtk_widget_modify_bg(m_window, GTK_STATE_NORMAL, &color); + gtk_widget_set_double_buffered(m_window, FALSE); + + g_signal_connect(m_window, "key-press-event", G_CALLBACK(onFullscreenGtkKeyPressEvent), this); + g_signal_connect(m_window, "destroy", G_CALLBACK(onFullscreenGtkDestroy), this); + g_signal_connect(m_window, "notify::is-active", G_CALLBACK(onFullscreenGtkActiveNotification), this); + + gtk_widget_show_all(m_window); + + GdkWindow* window = gtk_widget_get_window(m_window); + GdkCursor* cursor = gdk_cursor_new(GDK_BLANK_CURSOR); + m_cursor = gdk_window_get_cursor(window); + gdk_window_set_cursor(window, cursor); + gdk_cursor_unref(cursor); + + g_signal_connect(m_window, "motion-notify-event", G_CALLBACK(onFullscreenGtkMotionNotifyEvent), this); + g_signal_connect(m_window, "configure-event", G_CALLBACK(onFullscreenGtkConfigureEvent), this); + + gtk_window_fullscreen(GTK_WINDOW(m_window)); + showHud(true); +} + +void FullscreenVideoController::updateHudPosition() +{ + if (!m_hudWindow) + return; + + // Get the screen rectangle. + GdkScreen* screen = gtk_window_get_screen(GTK_WINDOW(m_window)); + GdkWindow* window = gtk_widget_get_window(m_window); + GdkRectangle fullscreenRectangle; + gdk_screen_get_monitor_geometry(screen, gdk_screen_get_monitor_at_window(screen, window), + &fullscreenRectangle); + + // Get the popup window size. + int hudWidth, hudHeight; + gtk_window_get_size(GTK_WINDOW(m_hudWindow), &hudWidth, &hudHeight); + + // Resize the hud to the full width of the screen. + gtk_window_resize(GTK_WINDOW(m_hudWindow), fullscreenRectangle.width, hudHeight); + + // Move the hud to the bottom of the screen. + gtk_window_move(GTK_WINDOW(m_hudWindow), fullscreenRectangle.x, + fullscreenRectangle.height + fullscreenRectangle.y - hudHeight); +} + +void FullscreenVideoController::exitOnUserRequest() +{ + m_mediaElement->exitFullscreen(); +} + +void FullscreenVideoController::exitFullscreen() +{ + if (!m_hudWindow) + return; + + g_signal_handlers_disconnect_by_func(m_window, reinterpret_cast<void*>(onFullscreenGtkKeyPressEvent), this); + g_signal_handlers_disconnect_by_func(m_window, reinterpret_cast<void*>(onFullscreenGtkDestroy), this); + g_signal_handlers_disconnect_by_func(m_window, reinterpret_cast<void*>(onFullscreenGtkMotionNotifyEvent), this); + g_signal_handlers_disconnect_by_func(m_window, reinterpret_cast<void*>(onFullscreenGtkConfigureEvent), this); + + GstElement* pipeline = m_mediaElement->platformMedia().media.gstreamerGWorld->pipeline(); + g_signal_handlers_disconnect_by_func(pipeline, reinterpret_cast<void*>(playerVolumeChangedCallback), this); + g_signal_handlers_disconnect_by_func(pipeline, reinterpret_cast<void*>(playerMuteChangedCallback), this); + + if (m_hudTimeoutId) { + g_source_remove(m_hudTimeoutId); + m_hudTimeoutId = 0; + } + + if (m_progressBarUpdateId) { + g_source_remove(m_progressBarUpdateId); + m_progressBarUpdateId = 0; + } + + if (m_mediaElement->platformMedia().type == WebCore::PlatformMedia::GStreamerGWorldType) + m_mediaElement->platformMedia().media.gstreamerGWorld->exitFullscreen(); + + gtk_widget_hide_all(m_window); + + gtk_widget_destroy(m_hudWindow); + m_hudWindow = 0; +} + +bool FullscreenVideoController::canPlay() const +{ + return m_mediaElement && m_mediaElement->canPlay(); +} + +void FullscreenVideoController::play() +{ + if (m_mediaElement) + m_mediaElement->play(m_mediaElement->processingUserGesture()); + + playStateChanged(); + showHud(true); +} + +void FullscreenVideoController::pause() +{ + if (m_mediaElement) + m_mediaElement->pause(m_mediaElement->processingUserGesture()); + + playStateChanged(); + showHud(false); +} + +void FullscreenVideoController::playStateChanged() +{ + if (canPlay()) + g_object_set(m_playPauseAction, "tooltip", _("Play"), "icon-name", PLAY_ICON_NAME, NULL); + else + g_object_set(m_playPauseAction, "tooltip", _("Pause"), "icon-name", PAUSE_ICON_NAME, NULL); +} + +void FullscreenVideoController::togglePlay() +{ + if (canPlay()) + play(); + else + pause(); +} + +float FullscreenVideoController::volume() const +{ + return m_mediaElement ? m_mediaElement->volume() : 0; +} + +bool FullscreenVideoController::muted() const +{ + return m_mediaElement ? m_mediaElement->muted() : false; +} + +void FullscreenVideoController::setVolume(float volume) +{ + if (volume < 0.0 || volume > 1.0) + return; + + if (m_mediaElement) { + ExceptionCode ec; + m_mediaElement->setVolume(volume, ec); + } +} + +void FullscreenVideoController::volumeChanged() +{ + g_signal_handler_block(m_volumeButton, m_volumeUpdateId); + gtk_scale_button_set_value(GTK_SCALE_BUTTON(m_volumeButton), volume()); + g_signal_handler_unblock(m_volumeButton, m_volumeUpdateId); +} + +void FullscreenVideoController::muteChanged() +{ + g_signal_handler_block(m_volumeButton, m_volumeUpdateId); + gtk_scale_button_set_value(GTK_SCALE_BUTTON(m_volumeButton), muted() ? 0 : volume()); + g_signal_handler_unblock(m_volumeButton, m_volumeUpdateId); +} + +float FullscreenVideoController::currentTime() const +{ + return m_mediaElement ? m_mediaElement->currentTime() : 0; +} + +void FullscreenVideoController::setCurrentTime(float value) +{ + if (m_mediaElement) { + ExceptionCode ec; + m_mediaElement->setCurrentTime(value, ec); + } +} + +float FullscreenVideoController::duration() const +{ + return m_mediaElement ? m_mediaElement->duration() : 0; +} + +float FullscreenVideoController::percentLoaded() const +{ + return m_mediaElement ? m_mediaElement->percentLoaded() : 0; +} + +void FullscreenVideoController::beginSeek() +{ + m_seekLock = true; + + if (m_mediaElement) + m_mediaElement->beginScrubbing(); +} + +void FullscreenVideoController::doSeek() +{ + if (!m_seekLock) + return; + + setCurrentTime(gtk_range_get_value(GTK_RANGE(m_timeHScale))*duration() / 100); +} + +void FullscreenVideoController::endSeek() +{ + if (m_mediaElement) + m_mediaElement->endScrubbing(); + + m_seekLock = false; +} + +static String timeToString(float time) +{ + if (!isfinite(time)) + time = 0; + int seconds = fabsf(time); + int hours = seconds / (60 * 60); + int minutes = (seconds / 60) % 60; + seconds %= 60; + + if (hours) { + if (hours > 9) + return String::format("%s%02d:%02d:%02d", (time < 0 ? "-" : ""), hours, minutes, seconds); + return String::format("%s%01d:%02d:%02d", (time < 0 ? "-" : ""), hours, minutes, seconds); + } + + return String::format("%s%02d:%02d", (time < 0 ? "-" : ""), minutes, seconds); +} + +gboolean FullscreenVideoController::updateHudProgressBar() +{ + float mediaDuration(duration()); + float mediaPosition(currentTime()); + + if (!m_seekLock) { + gdouble value = 0.0; + + if (mediaPosition && mediaDuration) + value = (mediaPosition * 100.0) / mediaDuration; + + GtkAdjustment* adjustment = gtk_range_get_adjustment(GTK_RANGE(m_timeHScale)); + gtk_adjustment_set_value(adjustment, value); + } + + gtk_range_set_fill_level(GTK_RANGE(m_timeHScale), percentLoaded()* 100); + + gchar* label = g_strdup_printf("%s / %s", timeToString(mediaPosition).utf8().data(), + timeToString(mediaDuration).utf8().data()); + gtk_label_set_text(GTK_LABEL(m_timeLabel), label); + g_free(label); + return TRUE; +} + +void FullscreenVideoController::createHud() +{ + m_hudWindow = gtk_window_new(GTK_WINDOW_POPUP); + gtk_window_set_gravity(GTK_WINDOW(m_hudWindow), GDK_GRAVITY_SOUTH_WEST); + gtk_window_set_type_hint(GTK_WINDOW(m_hudWindow), GDK_WINDOW_TYPE_HINT_NORMAL); + + g_signal_connect(m_hudWindow, "motion-notify-event", G_CALLBACK(onFullscreenGtkMotionNotifyEvent), this); + + GtkWidget* hbox = gtk_hbox_new(FALSE, 4); + gtk_container_add(GTK_CONTAINER(m_hudWindow), hbox); + + m_playPauseAction = gtk_action_new("play", _("Play / Pause"), _("Play or pause the media"), PAUSE_ICON_NAME); + g_signal_connect(m_playPauseAction, "activate", G_CALLBACK(togglePlayPauseActivated), this); + + playStateChanged(); + + GtkWidget* item = gtk_action_create_tool_item(m_playPauseAction); + gtk_box_pack_start(GTK_BOX(hbox), item, FALSE, TRUE, 0); + + GtkWidget* label = gtk_label_new(_("Time:")); + gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, TRUE, 0); + + GtkObject* adjustment = gtk_adjustment_new(0.0, 0.0, 100.0, 0.1, 1.0, 1.0); + m_timeHScale = gtk_hscale_new(GTK_ADJUSTMENT(adjustment)); + gtk_scale_set_draw_value(GTK_SCALE(m_timeHScale), FALSE); + gtk_range_set_show_fill_level(GTK_RANGE(m_timeHScale), TRUE); + gtk_range_set_update_policy(GTK_RANGE(m_timeHScale), GTK_UPDATE_CONTINUOUS); + g_signal_connect(m_timeHScale, "button-press-event", G_CALLBACK(timeScaleButtonPressed), this); + g_signal_connect(m_timeHScale, "button-release-event", G_CALLBACK(timeScaleButtonReleased), this); + m_hscaleUpdateId = g_signal_connect(m_timeHScale, "value-changed", G_CALLBACK(timeScaleValueChanged), this); + + gtk_box_pack_start(GTK_BOX(hbox), m_timeHScale, TRUE, TRUE, 0); + + m_timeLabel = gtk_label_new(""); + gtk_box_pack_start(GTK_BOX(hbox), m_timeLabel, FALSE, TRUE, 0); + + // Volume button. + m_volumeButton = gtk_volume_button_new(); + gtk_box_pack_start(GTK_BOX(hbox), m_volumeButton, FALSE, TRUE, 0); + gtk_scale_button_set_value(GTK_SCALE_BUTTON(m_volumeButton), volume()); + m_volumeUpdateId = g_signal_connect(m_volumeButton, "value-changed", G_CALLBACK(volumeValueChanged), this); + + + m_exitFullscreenAction = gtk_action_new("exit", _("Exit Fullscreen"), _("Exit from fullscreen mode"), EXIT_FULLSCREEN_ICON_NAME); + g_signal_connect(m_exitFullscreenAction, "activate", G_CALLBACK(exitFullscreenActivated), this); + g_object_set(m_exitFullscreenAction, "icon-name", EXIT_FULLSCREEN_ICON_NAME, NULL); + item = gtk_action_create_tool_item(m_exitFullscreenAction); + gtk_box_pack_start(GTK_BOX(hbox), item, FALSE, TRUE, 0); + + + m_progressBarUpdateId = g_timeout_add(PROGRESS_BAR_UPDATE_INTERVAL, reinterpret_cast<GSourceFunc>(progressBarUpdateCallback), this); +} + +#endif diff --git a/WebKit/gtk/WebCoreSupport/FullscreenVideoController.h b/WebKit/gtk/WebCoreSupport/FullscreenVideoController.h new file mode 100644 index 0000000..1567d9b --- /dev/null +++ b/WebKit/gtk/WebCoreSupport/FullscreenVideoController.h @@ -0,0 +1,103 @@ +/* + * Copyright (C) 2010 Igalia S.L + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public License + * along with this library; see the file COPYING.LIB. If not, write to + * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + * Boston, MA 02110-1301, USA. + */ + +#ifndef FullscreenVideoController_h +#define FullscreenVideoController_h + +#if ENABLE(VIDEO) + +#include "GRefPtr.h" +#include "GStreamerGWorld.h" +#include "HTMLMediaElement.h" +#include <wtf/RefPtr.h> + +typedef struct _GtkObject GtkObject; +typedef struct _GtkWidget GtkWidget; +typedef struct _GtkAction GtkAction; +typedef struct _GdkCursor GdkCursor; +typedef struct _GdkEventConfigure GdkEventConfigure; + + +class FullscreenVideoController : public Noncopyable { +public: + FullscreenVideoController(); + virtual ~FullscreenVideoController(); + + void setMediaElement(WebCore::HTMLMediaElement*); + WebCore::HTMLMediaElement* mediaElement() const { return m_mediaElement.get(); } + + void gtkConfigure(GdkEventConfigure* event); + + void enterFullscreen(); + void exitFullscreen(); + + void exitOnUserRequest(); + void togglePlay(); + void beginSeek(); + void doSeek(); + void endSeek(); + + void hideHud(); + void showHud(bool); + gboolean updateHudProgressBar(); + + float volume() const; + void setVolume(float); + void volumeChanged(); + void muteChanged(); + +private: + bool canPlay() const; + void play(); + void pause(); + void playStateChanged(); + + bool muted() const; + + float currentTime() const; + void setCurrentTime(float); + + float duration() const; + float percentLoaded() const; + + void createHud(); + void updateHudPosition(); + + RefPtr<WebCore::HTMLMediaElement> m_mediaElement; + RefPtr<WebCore::GStreamerGWorld> m_gstreamerGWorld; + + guint m_hudTimeoutId; + guint m_progressBarUpdateId; + guint m_progressBarFillUpdateId; + guint m_hscaleUpdateId; + guint m_volumeUpdateId; + bool m_seekLock; + GtkWidget* m_window; + PlatformRefPtr<GdkCursor> m_cursor; + GtkWidget* m_hudWindow; + GtkAction* m_playPauseAction; + GtkAction* m_exitFullscreenAction; + GtkWidget* m_timeHScale; + GtkWidget* m_timeLabel; + GtkWidget* m_volumeButton; +}; + +#endif + +#endif // FullscreenVideoController_h diff --git a/WebKit/gtk/WebCoreSupport/InspectorClientGtk.cpp b/WebKit/gtk/WebCoreSupport/InspectorClientGtk.cpp index b0dd40e..aedf21f 100644 --- a/WebKit/gtk/WebCoreSupport/InspectorClientGtk.cpp +++ b/WebKit/gtk/WebCoreSupport/InspectorClientGtk.cpp @@ -79,18 +79,8 @@ void InspectorClient::openInspectorFrontend(InspectorController* controller) webkit_web_inspector_set_web_view(webInspector, inspectorWebView); - GOwnPtr<gchar> inspectorURI; - - // Make the Web Inspector work when running tests - // FixMe: it is not working. It should be not the subdirectory of the current directory, but a subdirectory of $(WEBKITOUTPUTDIR). - if (g_file_test("resources/inspector/inspector.html", G_FILE_TEST_EXISTS)) { - GOwnPtr<gchar> currentDirectory(g_get_current_dir()); - GOwnPtr<gchar> fullPath(g_strdup_printf("%s/resources/inspector/inspector.html", currentDirectory.get())); - inspectorURI.set(g_filename_to_uri(fullPath.get(), NULL, NULL)); - } else { - inspectorURI.set(g_filename_to_uri(DATA_DIR"/webkitgtk-"WEBKITGTK_API_VERSION_STRING"/webinspector/inspector.html", NULL, NULL)); - } - + GOwnPtr<gchar> inspectorPath(g_build_filename(inspectorFilesPath(), "inspector.html", NULL)); + GOwnPtr<gchar> inspectorURI(g_filename_to_uri(inspectorPath.get(), 0, 0)); webkit_web_view_load_uri(inspectorWebView, inspectorURI.get()); gtk_widget_show(GTK_WIDGET(inspectorWebView)); @@ -185,7 +175,7 @@ void InspectorClient::populateSetting(const String& key, String* value) if (!settings) return; - GRefPtr<GVariant> variant = adoptGRef(g_settings_get_value(settings, toGSettingName(key).utf8().data())); + PlatformRefPtr<GVariant> variant = adoptPlatformRef(g_settings_get_value(settings, toGSettingName(key).utf8().data())); if (key == "resourceTrackingEnabled" || key == "xhrMonitor" || key == "debuggerEnabled" || key == "profilerEnabled") @@ -203,15 +193,15 @@ void InspectorClient::storeSetting(const String& key, const String& value) if (!settings) return; - GRefPtr<GVariant> variant(0); + PlatformRefPtr<GVariant> variant(0); // Set the key with the appropriate type, and also avoid setting // unknown keys to avoid aborting the execution. if (key == "resourceTrackingEnabled" || key == "xhrMonitor" || key == "debuggerEnabled" || key == "profilerEnabled") - variant = adoptGRef(variantFromTruthString(value)); + variant = adoptPlatformRef(variantFromTruthString(value)); else if (key == "frontendSettings") - variant = adoptGRef(g_variant_new_string(value.utf8().data())); + variant = adoptPlatformRef(g_variant_new_string(value.utf8().data())); if (!variant) return; @@ -250,7 +240,19 @@ bool InspectorClient::sendMessageToFrontend(const String& message) return true; } -bool destroyed = TRUE; +const char* InspectorClient::inspectorFilesPath() +{ + if (m_inspectorFilesPath) + m_inspectorFilesPath.get(); + + const char* environmentPath = getenv("WEBKIT_INSPECTOR_PATH"); + if (environmentPath && g_file_test(environmentPath, G_FILE_TEST_IS_DIR)) + m_inspectorFilesPath.set(g_strdup(environmentPath)); + else + m_inspectorFilesPath.set(g_build_filename(DATA_DIR, "webkitgtk-"WEBKITGTK_API_VERSION_STRING, "webinspector", NULL)); + + return m_inspectorFilesPath.get(); +} InspectorFrontendClient::InspectorFrontendClient(WebKitWebView* inspectedWebView, WebKitWebView* inspectorWebView, WebKitWebInspector* webInspector, Page* inspectorPage, InspectorClient* inspectorClient) : InspectorFrontendClientLocal(core(inspectedWebView)->inspectorController(), inspectorPage) @@ -300,20 +302,11 @@ void InspectorFrontendClient::destroyInspectorWindow() String InspectorFrontendClient::localizedStringsURL() { - GOwnPtr<gchar> URL; - - // Make the Web Inspector work when running tests - if (g_file_test("WebCore/English.lproj/localizedStrings.js", G_FILE_TEST_EXISTS)) { - GOwnPtr<gchar> currentDirectory(g_get_current_dir()); - GOwnPtr<gchar> fullPath(g_strdup_printf("%s/WebCore/English.lproj/localizedStrings.js", currentDirectory.get())); - URL.set(g_filename_to_uri(fullPath.get(), NULL, NULL)); - } else { - GOwnPtr<gchar> localizedStringsPath(g_strdup_printf(DATA_DIR"/webkitgtk-%.1f/webinspector/localizedStrings.js", WEBKITGTK_API_VERSION)); - URL.set(g_filename_to_uri(localizedStringsPath.get(), NULL, NULL)); - } + GOwnPtr<gchar> stringsPath(g_build_filename(m_inspectorClient->inspectorFilesPath(), "localizedStrings.js", NULL)); + GOwnPtr<gchar> stringsURI(g_filename_to_uri(stringsPath.get(), 0, 0)); // FIXME: support l10n of localizedStrings.js - return String::fromUTF8(URL.get()); + return String::fromUTF8(stringsURI.get()); } String InspectorFrontendClient::hiddenPanels() diff --git a/WebKit/gtk/WebCoreSupport/InspectorClientGtk.h b/WebKit/gtk/WebCoreSupport/InspectorClientGtk.h index b72bc82..8b68405 100644 --- a/WebKit/gtk/WebCoreSupport/InspectorClientGtk.h +++ b/WebKit/gtk/WebCoreSupport/InspectorClientGtk.h @@ -29,6 +29,7 @@ #ifndef InspectorClientGtk_h #define InspectorClientGtk_h +#include "GOwnPtr.h" #include "InspectorClient.h" #include "InspectorFrontendClientLocal.h" #include "webkitwebview.h" @@ -64,11 +65,13 @@ namespace WebKit { virtual bool sendMessageToFrontend(const WTF::String&); void releaseFrontendPage(); + const char* inspectorFilesPath(); private: WebKitWebView* m_inspectedWebView; WebCore::Page* m_frontendPage; InspectorFrontendClient* m_frontendClient; + GOwnPtr<gchar> m_inspectorFilesPath; }; class InspectorFrontendClient : public WebCore::InspectorFrontendClientLocal { diff --git a/WebKit/gtk/docs/webkitgtk-sections.txt b/WebKit/gtk/docs/webkitgtk-sections.txt index 0083146..35f9b40 100644 --- a/WebKit/gtk/docs/webkitgtk-sections.txt +++ b/WebKit/gtk/docs/webkitgtk-sections.txt @@ -419,6 +419,7 @@ WebKitNetworkResponseClass <FILE>webkitwebview</FILE> WebKitNavigationResponse WebKitWebViewTargetInfo +WebKitWebViewViewMode <TITLE>WebKitWebView</TITLE> WebKitWebView webkit_web_view_can_copy_clipboard @@ -453,6 +454,7 @@ webkit_web_view_get_settings webkit_web_view_get_title webkit_web_view_get_transparent webkit_web_view_get_uri +webkit_web_view_get_view_mode webkit_web_view_get_view_source_mode webkit_web_view_get_zoom_level webkit_web_view_go_back @@ -481,6 +483,7 @@ webkit_web_view_set_highlight_text_matches webkit_web_view_set_maintains_back_forward_list webkit_web_view_set_settings webkit_web_view_set_transparent +webkit_web_view_set_view_mode webkit_web_view_set_view_source_mode webkit_web_view_set_zoom_level webkit_web_view_stop_loading diff --git a/WebKit/gtk/po/ChangeLog b/WebKit/gtk/po/ChangeLog index f088275..309ba09 100644 --- a/WebKit/gtk/po/ChangeLog +++ b/WebKit/gtk/po/ChangeLog @@ -1,3 +1,12 @@ +2010-08-19 Philippe Normand <pnormand@igalia.com> + + Reviewed by Gustavo Noronha Silva. + + [GStreamer] GTK XOverlay support in GStreamerGWorld + https://bugs.webkit.org/show_bug.cgi?id=39474 + + * POTFILES: Added new file that contains strings to extract. + 2010-08-03 Jorge González <aloriel@gmail.com> Reviewed by Gustavo Noronha. diff --git a/WebKit/gtk/po/POTFILES b/WebKit/gtk/po/POTFILES index 05ba138..ffd0015 100644 --- a/WebKit/gtk/po/POTFILES +++ b/WebKit/gtk/po/POTFILES @@ -1,6 +1,7 @@ # List of source files which contain translatable strings. WebKit/gtk/WebCoreSupport/ChromeClientGtk.cpp WebKit/gtk/WebCoreSupport/ContextMenuClientGtk.cpp +WebKit/gtk/WebCoreSupport/FullscreenVideoController.cpp WebKit/gtk/webkit/webkitdownload.cpp WebKit/gtk/webkit/webkitsoupauthdialog.c WebKit/gtk/webkit/webkitwebframe.cpp diff --git a/WebKit/gtk/tests/testcopyandpaste.c b/WebKit/gtk/tests/testcopyandpaste.c index 0ef91d1..58fb764 100644 --- a/WebKit/gtk/tests/testcopyandpaste.c +++ b/WebKit/gtk/tests/testcopyandpaste.c @@ -128,21 +128,25 @@ static CopyAndPasteFixture* currentFixture; static JSValueRef runPasteTestCallback(JSContextRef context, JSObjectRef function, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef* exception) { // Simulate a paste keyboard sequence. - GdkEvent event; - memset(&event, 0, sizeof(event)); - event.key.keyval = gdk_unicode_to_keyval('v'); - event.key.state = GDK_CONTROL_MASK; - event.key.window = gtk_widget_get_window(GTK_WIDGET(currentFixture->webView)); + GdkEvent* event = gdk_event_new(GDK_KEY_PRESS); + event->key.keyval = gdk_unicode_to_keyval('v'); + event->key.state = GDK_CONTROL_MASK; + event->key.window = gtk_widget_get_window(GTK_WIDGET(currentFixture->webView)); + g_object_ref(event->key.window); +#ifndef GTK_API_VERSION_2 + gdk_event_set_device(event, gdk_device_get_associated_device(gdk_display_get_core_pointer(gdk_drawable_get_display(event->key.window)))); +#endif GdkKeymapKey* keys; gint n_keys; - if (gdk_keymap_get_entries_for_keyval(gdk_keymap_get_default(), event.key.keyval, &keys, &n_keys)) { - event.key.hardware_keycode = keys[0].keycode; + if (gdk_keymap_get_entries_for_keyval(gdk_keymap_get_default(), event->key.keyval, &keys, &n_keys)) { + event->key.hardware_keycode = keys[0].keycode; g_free(keys); } - event.key.type = GDK_KEY_PRESS; - gtk_main_do_event(&event); - event.key.type = GDK_KEY_RELEASE; - gtk_main_do_event(&event); + + gtk_main_do_event(event); + event->key.type = GDK_KEY_RELEASE; + gtk_main_do_event(event); + gdk_event_free(event); JSStringRef scriptString = JSStringCreateWithUTF8CString("document.body.innerHTML;"); JSValueRef value = JSEvaluateScript(context, scriptString, 0, 0, 0, 0); diff --git a/WebKit/gtk/tests/testhittestresult.c b/WebKit/gtk/tests/testhittestresult.c index 89fe95c..0d7fb05 100644 --- a/WebKit/gtk/tests/testhittestresult.c +++ b/WebKit/gtk/tests/testhittestresult.c @@ -81,15 +81,15 @@ load_status_cb(WebKitWebView* webView, if (status == WEBKIT_LOAD_FINISHED) { WebKitHitTestResult* result; guint context; - GdkEventButton event; + GdkEvent* event = gdk_event_new(GDK_BUTTON_PRESS); WebKitDOMNode* node; - event.type = GDK_BUTTON_PRESS; /* Close enough to 0,0 */ - event.x = 5; - event.y = 5; + event->button.x = 5; + event->button.y = 5; - result = webkit_web_view_get_hit_test_result(webView, &event); + result = webkit_web_view_get_hit_test_result(webView, (GdkEventButton*) event); + gdk_event_free(event); g_assert(result); g_object_get(result, "context", &context, NULL); diff --git a/WebKit/gtk/webkit/webkitdownload.cpp b/WebKit/gtk/webkit/webkitdownload.cpp index 0717e7c..9bcb739 100644 --- a/WebKit/gtk/webkit/webkitdownload.cpp +++ b/WebKit/gtk/webkit/webkitdownload.cpp @@ -905,7 +905,7 @@ static void webkit_download_error(WebKitDownload* download, const ResourceError& webkit_download_close_stream(download); WebKitDownloadPrivate* priv = download->priv; - GRefPtr<WebKitDownload> protect(download); + PlatformRefPtr<WebKitDownload> protect(download); g_timer_stop(priv->timer); webkit_download_set_status(download, WEBKIT_DOWNLOAD_STATUS_ERROR); diff --git a/WebKit/gtk/webkit/webkitnetworkrequest.cpp b/WebKit/gtk/webkit/webkitnetworkrequest.cpp index c72abbd..8b50948 100644 --- a/WebKit/gtk/webkit/webkitnetworkrequest.cpp +++ b/WebKit/gtk/webkit/webkitnetworkrequest.cpp @@ -164,7 +164,7 @@ static void webkit_network_request_init(WebKitNetworkRequest* request) // for internal use only WebKitNetworkRequest* webkit_network_request_new_with_core_request(const WebCore::ResourceRequest& resourceRequest) { - GRefPtr<SoupMessage> soupMessage(adoptGRef(resourceRequest.toSoupMessage())); + PlatformRefPtr<SoupMessage> soupMessage(adoptPlatformRef(resourceRequest.toSoupMessage())); if (soupMessage) return WEBKIT_NETWORK_REQUEST(g_object_new(WEBKIT_TYPE_NETWORK_REQUEST, "message", soupMessage.get(), NULL)); diff --git a/WebKit/gtk/webkit/webkitnetworkresponse.cpp b/WebKit/gtk/webkit/webkitnetworkresponse.cpp index 6745b94..d4dd562 100644 --- a/WebKit/gtk/webkit/webkitnetworkresponse.cpp +++ b/WebKit/gtk/webkit/webkitnetworkresponse.cpp @@ -161,7 +161,7 @@ static void webkit_network_response_init(WebKitNetworkResponse* response) // for internal use only WebKitNetworkResponse* webkit_network_response_new_with_core_response(const WebCore::ResourceResponse& resourceResponse) { - GRefPtr<SoupMessage> soupMessage(adoptGRef(resourceResponse.toSoupMessage())); + PlatformRefPtr<SoupMessage> soupMessage(adoptPlatformRef(resourceResponse.toSoupMessage())); if (soupMessage) return WEBKIT_NETWORK_RESPONSE(g_object_new(WEBKIT_TYPE_NETWORK_RESPONSE, "message", soupMessage.get(), NULL)); diff --git a/WebKit/gtk/webkit/webkitprivate.cpp b/WebKit/gtk/webkit/webkitprivate.cpp index 91b2904..1b7f7a3 100644 --- a/WebKit/gtk/webkit/webkitprivate.cpp +++ b/WebKit/gtk/webkit/webkitprivate.cpp @@ -28,6 +28,8 @@ #include "FrameLoader.h" #include "FrameLoaderClientGtk.h" #include "GtkVersioning.h" +#include "HTMLMediaElement.h" +#include "HTMLNames.h" #include "HitTestResult.h" #include "IconDatabase.h" #include "Logging.h" @@ -50,6 +52,10 @@ #include <stdlib.h> #include <wtf/Threading.h> +#if ENABLE(VIDEO) +#include "FullscreenVideoController.h" +#endif + #if ENABLE(DATABASE) #include "DatabaseTracker.h" #endif @@ -278,12 +284,6 @@ void webkit_init() // FIXME: Expose this with an API and/or calculate based on available resources webkit_set_cache_model(WEBKIT_CACHE_MODEL_WEB_BROWSER); -#ifdef HAVE_GSETTINGS - // Initialize settings variables here to make sure this happens in - // the main thread. - inspectorGSettings(); -#endif - #if ENABLE(DATABASE) gchar* databaseDirectory = g_build_filename(g_get_user_data_dir(), "webkit", "databases", NULL); webkit_set_web_database_directory_path(databaseDirectory); @@ -327,3 +327,33 @@ void webkit_reset_origin_access_white_lists() { SecurityOrigin::resetOriginAccessWhitelists(); } + + +void webkitWebViewEnterFullscreen(WebKitWebView* webView, Node* node) +{ + if (!node->hasTagName(HTMLNames::videoTag)) + return; + +#if ENABLE(VIDEO) + HTMLMediaElement* videoElement = static_cast<HTMLMediaElement*>(node); + WebKitWebViewPrivate* priv = webView->priv; + + // First exit Fullscreen for the old mediaElement. + if (priv->fullscreenVideoController) + priv->fullscreenVideoController->exitFullscreen(); + + priv->fullscreenVideoController = new FullscreenVideoController; + priv->fullscreenVideoController->setMediaElement(videoElement); + priv->fullscreenVideoController->enterFullscreen(); +#endif +} + +void webkitWebViewExitFullscreen(WebKitWebView* webView) +{ +#if ENABLE(VIDEO) + WebKitWebViewPrivate* priv = webView->priv; + if (priv->fullscreenVideoController) + priv->fullscreenVideoController->exitFullscreen(); +#endif +} + diff --git a/WebKit/gtk/webkit/webkitprivate.h b/WebKit/gtk/webkit/webkitprivate.h index a5508a4..92bb27d 100644 --- a/WebKit/gtk/webkit/webkitprivate.h +++ b/WebKit/gtk/webkit/webkitprivate.h @@ -56,6 +56,8 @@ #include "InspectorClientGtk.h" #include "IntPoint.h" #include "FrameLoaderClient.h" +#include "FullscreenVideoController.h" +#include "Node.h" #include "Page.h" #include "ResourceHandle.h" #include "ResourceRequest.h" @@ -161,6 +163,8 @@ extern "C" { gboolean disposing; gboolean usePrimaryForPaste; + FullscreenVideoController* fullscreenVideoController; + // These are hosted here because the DataSource object is // created too late in the frame loading process. WebKitWebResource* mainResource; @@ -410,6 +414,9 @@ extern "C" { WEBKIT_API void webkit_web_frame_layout(WebKitWebFrame* frame); + + void webkitWebViewEnterFullscreen(WebKitWebView* webView, WebCore::Node* node); + void webkitWebViewExitFullscreen(WebKitWebView* webView); } #endif diff --git a/WebKit/gtk/webkit/webkitwebview.cpp b/WebKit/gtk/webkit/webkitwebview.cpp index 64b7dcc..76fe6cb 100644 --- a/WebKit/gtk/webkit/webkitwebview.cpp +++ b/WebKit/gtk/webkit/webkitwebview.cpp @@ -195,7 +195,8 @@ enum { PROP_ENCODING, PROP_CUSTOM_ENCODING, PROP_ICON_URI, - PROP_IM_CONTEXT + PROP_IM_CONTEXT, + PROP_VIEW_MODE }; static guint webkit_web_view_signals[LAST_SIGNAL] = { 0, }; @@ -449,6 +450,9 @@ static void webkit_web_view_get_property(GObject* object, guint prop_id, GValue* case PROP_IM_CONTEXT: g_value_set_object(value, webkit_web_view_get_im_context(webView)); break; + case PROP_VIEW_MODE: + g_value_set_enum(value, webkit_web_view_get_view_mode(webView)); + break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec); } @@ -480,6 +484,9 @@ static void webkit_web_view_set_property(GObject* object, guint prop_id, const G case PROP_CUSTOM_ENCODING: webkit_web_view_set_custom_encoding(webView, g_value_get_string(value)); break; + case PROP_VIEW_MODE: + webkit_web_view_set_view_mode(webView, static_cast<WebKitWebViewViewMode>(g_value_get_enum(value))); + break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec); } @@ -985,8 +992,8 @@ static gboolean webkit_web_view_script_dialog(WebKitWebView* webView, WebKitWebF break; case WEBKIT_SCRIPT_DIALOG_CONFIRM: messageType = GTK_MESSAGE_QUESTION; - buttons = GTK_BUTTONS_YES_NO; - defaultResponse = GTK_RESPONSE_YES; + buttons = GTK_BUTTONS_OK_CANCEL; + defaultResponse = GTK_RESPONSE_OK; break; case WEBKIT_SCRIPT_DIALOG_PROMPT: messageType = GTK_MESSAGE_QUESTION; @@ -1016,17 +1023,11 @@ static gboolean webkit_web_view_script_dialog(WebKitWebView* webView, WebKitWebF gint response = gtk_dialog_run(GTK_DIALOG(dialog)); switch (response) { - case GTK_RESPONSE_YES: - didConfirm = TRUE; - break; case GTK_RESPONSE_OK: didConfirm = TRUE; if (entry) *value = g_strdup(gtk_entry_get_text(GTK_ENTRY(entry))); - else - *value = 0; break; - case GTK_RESPONSE_NO: case GTK_RESPONSE_CANCEL: didConfirm = FALSE; break; @@ -2859,6 +2860,32 @@ static void webkit_web_view_class_init(WebKitWebViewClass* webViewClass) GTK_TYPE_IM_CONTEXT, WEBKIT_PARAM_READABLE)); + /** + * WebKitWebView:view-mode: + * + * The "view-mode" media feature for the #WebKitWebView. + * + * The "view-mode" media feature is additional information for web + * applications about how the application is running, when it comes + * to user experience. Whether the application is running inside a + * regular browser window, in a dedicated window, fullscreen, for + * instance. + * + * This property stores a %WebKitWebViewViewMode value that matches + * the "view-mode" media feature the web application will see. + * + * See http://www.w3.org/TR/view-mode/ for more information. + * + * Since: 1.3.4 + */ + g_object_class_install_property(objectClass, PROP_VIEW_MODE, + g_param_spec_enum("view-mode", + "View Mode", + "The view-mode media feature for the #WebKitWebView.", + WEBKIT_TYPE_WEB_VIEW_VIEW_MODE, + WEBKIT_WEB_VIEW_VIEW_MODE_WINDOWED, + WEBKIT_PARAM_READWRITE)); + g_type_class_add_private(webViewClass, sizeof(WebKitWebViewPrivate)); } @@ -4252,6 +4279,76 @@ const char* webkit_web_view_get_custom_encoding(WebKitWebView* webView) } /** + * webkit_web_view_set_view_mode: + * @web_view: the #WebKitWebView that will have its view mode set + * @mode: the %WebKitWebViewViewMode to be set + * + * Sets the view-mode property of the #WebKitWebView. Check the + * property's documentation for more information. + * + * Since: 1.3.4 + */ +void webkit_web_view_set_view_mode(WebKitWebView* webView, WebKitWebViewViewMode mode) +{ + g_return_if_fail(WEBKIT_IS_WEB_VIEW(webView)); + + Page* page = core(webView); + + switch (mode) { + case WEBKIT_WEB_VIEW_VIEW_MODE_FLOATING: + page->setViewMode(Page::ViewModeFloating); + break; + case WEBKIT_WEB_VIEW_VIEW_MODE_FULLSCREEN: + page->setViewMode(Page::ViewModeFullscreen); + break; + case WEBKIT_WEB_VIEW_VIEW_MODE_MAXIMIZED: + page->setViewMode(Page::ViewModeMaximized); + break; + case WEBKIT_WEB_VIEW_VIEW_MODE_MINIMIZED: + page->setViewMode(Page::ViewModeMinimized); + break; + default: + page->setViewMode(Page::ViewModeWindowed); + break; + } +} + +/** + * webkit_web_view_get_view_mode: + * @web_view: the #WebKitWebView to obtain the view mode from + * + * Gets the value of the view-mode property of the + * #WebKitWebView. Check the property's documentation for more + * information. + * + * Return value: the %WebKitWebViewViewMode currently set for the + * #WebKitWebView. + * + * Since: 1.3.4 + */ +WebKitWebViewViewMode webkit_web_view_get_view_mode(WebKitWebView* webView) +{ + g_return_val_if_fail(WEBKIT_IS_WEB_VIEW(webView), WEBKIT_WEB_VIEW_VIEW_MODE_WINDOWED); + + Page* page = core(webView); + Page::ViewMode mode = page->viewMode(); + + if (mode == Page::ViewModeFloating) + return WEBKIT_WEB_VIEW_VIEW_MODE_FLOATING; + + if (mode == Page::ViewModeFullscreen) + return WEBKIT_WEB_VIEW_VIEW_MODE_FULLSCREEN; + + if (mode == Page::ViewModeMaximized) + return WEBKIT_WEB_VIEW_VIEW_MODE_MAXIMIZED; + + if (mode == Page::ViewModeMinimized) + return WEBKIT_WEB_VIEW_VIEW_MODE_MINIMIZED; + + return WEBKIT_WEB_VIEW_VIEW_MODE_WINDOWED; +} + +/** * webkit_web_view_move_cursor: * @web_view: a #WebKitWebView * @step: a #GtkMovementStep diff --git a/WebKit/gtk/webkit/webkitwebview.h b/WebKit/gtk/webkit/webkitwebview.h index 865ae9d..a320131 100644 --- a/WebKit/gtk/webkit/webkitwebview.h +++ b/WebKit/gtk/webkit/webkitwebview.h @@ -64,6 +64,15 @@ typedef enum WEBKIT_WEB_VIEW_TARGET_INFO_NETSCAPE_URL } WebKitWebViewTargetInfo; +typedef enum +{ + WEBKIT_WEB_VIEW_VIEW_MODE_WINDOWED, + WEBKIT_WEB_VIEW_VIEW_MODE_FLOATING, + WEBKIT_WEB_VIEW_VIEW_MODE_FULLSCREEN, + WEBKIT_WEB_VIEW_VIEW_MODE_MAXIMIZED, + WEBKIT_WEB_VIEW_VIEW_MODE_MINIMIZED +} WebKitWebViewViewMode; + struct _WebKitWebView { GtkContainer parent_instance; @@ -340,6 +349,13 @@ WEBKIT_API const char* webkit_web_view_get_custom_encoding (WebKitWebView * webView); WEBKIT_API void +webkit_web_view_set_view_mode (WebKitWebView *web_view, + WebKitWebViewViewMode mode); + +WEBKIT_API WebKitWebViewViewMode +webkit_web_view_get_view_mode (WebKitWebView *web_view); + +WEBKIT_API void webkit_web_view_move_cursor (WebKitWebView * webView, GtkMovementStep step, gint count); |
