⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 bridgeimpl.cpp

📁 khtml在gtk上的移植版本
💻 CPP
📖 第 1 页 / 共 3 页
字号:
/* * Copyright (c) 2004 Nokia. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the * distribution. * * Neither the name of Nokia nor the names of its contributors may be * used to endorse or promote products derived from this software * without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED * OF THE POSSIBILITY OF SUCH DAMAGE. */#include <assert.h>#include <glib.h>#include <gdk/gdk.h>#include <gtk/gtk.h>#include "BridgeImpl.h"#include "NRCore/WebCoreViewFactory.h"#include "NRCore/WebCoreSettings.h"#include "NRCore/WebCoreResourceLoader.h"#include "NRCore/WebCoreCache.h"#include "NRCore/KWIQResponse.h"#include "Http.h"#include "XftTextRendererFactory.h"#include "ImageRendererFactory.h"#include "VisitedURLHistory.h"#include "GdkXftContext.h"#include "UnicodeImpl.h"#include "ResourceLoadListener.h"#include "PageLoadListener.h"#include "osbimpl.h"#include "GdkHelpers.h"#include "GLibHelpers.h"static void mapToParentWindow(GdkWindow* parent, GdkWindow* child, int&x, int&y);extern "C" {    static void size_allocate( GtkWidget *widget, GtkAllocation *allocation, gpointer data);    static int expose(GtkWidget *widget, GdkEventExpose *event, gpointer data);    static gint motion_notify(GtkWidget *widget, GdkEventMotion *event, gpointer data);    static gint button_press(GtkWidget *widget, GdkEventButton *event, gpointer data);    static gint button_release(GtkWidget *widget, GdkEventButton *event, gpointer data);    static gboolean focus(GtkWidget *widget, GtkDirectionType dir, gpointer data);    static  gboolean focus_inout_event(GtkWidget *widget, GdkEventFocus *event, gpointer data);    static gboolean key_press(GtkWidget *widget, GdkEventKey *event, gpointer data);}class FactoryInitializer{public:    FactoryInitializer()    {	WebCoreUnicodeDigitValueFunction = UnicodeImplDigitValueFunction;	WebCoreUnicodeDirectionFunction = UnicodeImplDirectionFunction;	WebCoreUnicodeMirroredFunction = UnicodeImplMirroredFunction;	WebCoreUnicodeMirroredCharFunction = UnicodeImplMirroredCharFunction;	WebCoreUnicodeLowerFunction = UnicodeImplLowerFunction;	WebCoreUnicodeUpperFunction = UnicodeImplUpperFunction;	XftTextRendererFactory::useAsSharedFactory();	ImageRendererFactory::useAsSharedFactory();	VisitedURLHistory::useAsSharedProvider();    }};static FactoryInitializer _fi;extern "C"{static gbooleanfocus_scrolledwindow(GtkWidget *widget, GtkDirectionType dir, gpointer data){#if DEBUG    g_printerr("%s: widget:%x dir:%x data:%x \n",	       __PRETTY_FUNCTION__,	       (int)widget,	       (int)dir,	       (int)data);#endif    BridgeImpl *bridge = static_cast<BridgeImpl*>(data);    GtkWidget *foundWidget = 0;    switch (dir){    case GTK_DIR_TAB_FORWARD:	foundWidget = bridge->nextKeyView();	break;    case GTK_DIR_TAB_BACKWARD:	foundWidget = bridge->previousKeyView();	break;    default:	break;    }    if (foundWidget && foundWidget != widget) 	bridge->makeFirstResponder(foundWidget);    return foundWidget ? TRUE : FALSE; // TRUE To stop propagating,  FALSE to continue}static gbooleanfocus_in_scrolledwindow(GtkWidget *widget, GdkEventFocus *event, gpointer data){#if DEBUG    g_printerr("%s: widget:%x data:%x in:%x\n",	   __PRETTY_FUNCTION__,	   (int)widget,	   (int)data, event->in);#endif        if (event->in == FALSE) {	// FIXME: How to unset document focus	// BridgeImpl *bridge = static_cast<BridgeImpl*>(data);    }    return FALSE;}}staticvoid freeGListOfStrings(GList* listOfStrings){    if (listOfStrings) {	GList* iter = listOfStrings;	while (iter) {	    if (iter->data) g_free(iter->data);	    iter = g_list_next(iter);	}	g_list_free(listOfStrings);    }}BridgeImpl::BridgeImpl(BridgeImpl *parent)    :_parent(parent)    , _childFrames(0)    , _documentState(0)    , _shouldReapplyStyles(false)    , _inexpose(false)    , _requestedURL(0)    , _currentURL(0)    , _generatedFrameName(0)    , _generatedFrameNameId(0)    , _frameName(0)    , _activeRequest(0)    , _isReloading(false){    if (parent) { 	_parent = parent;	setParent(parent);	didSetName("root frame");    } else {	_parent = 0;    }    WebCoreBridge::init();    WebCoreCache::setDisabled(false);    _oldCanvasSize.x = _oldCanvasSize.y =  _oldCanvasSize.width = _oldCanvasSize.height = 0;    frameWidget = GTK_SCROLLED_WINDOW (gtk_scrolled_window_new(NULL, NULL));    gtk_scrolled_window_set_shadow_type(frameWidget, GTK_SHADOW_NONE);    GtkAdjustment* ha = gtk_scrolled_window_get_hadjustment(frameWidget);    GtkAdjustment* va = gtk_scrolled_window_get_vadjustment(frameWidget);    ha->step_increment = 20;    va->step_increment = 10;        frameCanvas = gtk_layout_new(gtk_scrolled_window_get_hadjustment(frameWidget),				 gtk_scrolled_window_get_vadjustment(frameWidget));    gtk_widget_set_double_buffered(GTK_WIDGET (frameCanvas), FALSE);    gtk_widget_set_double_buffered(GTK_WIDGET (frameWidget), FALSE);    gtk_widget_add_events(GTK_WIDGET (frameCanvas),			  GDK_KEY_PRESS_MASK			  | GDK_KEY_RELEASE_MASK			  | GDK_BUTTON_PRESS_MASK			  | GDK_BUTTON_RELEASE_MASK			  | GDK_FOCUS_CHANGE_MASK			  | GDK_POINTER_MOTION_MASK 			  | GDK_POINTER_MOTION_HINT_MASK			  | GDK_EXPOSURE_MASK);    gtk_container_add(GTK_CONTAINER (frameWidget), frameCanvas);    frameWidget.connect("focus",			::focus_scrolledwindow,			this);    frameWidget.connect("focus-in-event",			::focus_in_scrolledwindow,			this);    frameWidget.connect("focus-out-event",		       ::focus_in_scrolledwindow,			this);    connectFrameContents();    createKHTMLViewWithGtkWidget(GTK_WIDGET(frameWidget), 0,0);}void BridgeImpl::sizeAllocate(GtkWidget *widget, GtkAllocation* allocation){    if (_oldCanvasSize.x == allocation->x && 	_oldCanvasSize.y == allocation->y && 	_oldCanvasSize.width == allocation->width &&	_oldCanvasSize.height == allocation->height)	return;        _oldCanvasSize = *allocation;    GtkAdjustment* ha = gtk_scrolled_window_get_hadjustment(GTK_SCROLLED_WINDOW(frameWidget));    GtkAdjustment* va = gtk_scrolled_window_get_vadjustment(GTK_SCROLLED_WINDOW(frameWidget));    va->page_increment = (gdouble) allocation->width;    ha->page_increment = (gdouble) allocation->height;    forceLayoutAdjustingViewSize(false);    sendResizeEvent();}/**  * * Bridge delete semantics: *  on deleting top level main frame, the KHTMLPart takes care of subframes. *  HTMLFrameElementImpl::detach calls KHTMLPart::frameDetached, which will inform *  Bridge that frame is ready to be deleted *  Bridge then deletes itself and derefs its part. *  After that KHTMLPart::frameDetached removes the part KHTMLPart's subframe list *  and derefs the part for the last time. part gets destroyed. */BridgeImpl::~BridgeImpl(){#ifdef DEBUG    g_printerr("%s this:%x, part:%x, frameName:%s",	       __PRETTY_FUNCTION__, 	       (int)this, 	       (int)part(),	       _frameName);#endif    if (_frameName) g_free(_frameName);    if (_requestedURL) g_free(_requestedURL);    if (_currentURL) g_free(_currentURL);    if (_generatedFrameName) g_free(_generatedFrameName);    GList* iter = g_list_first(_childFrames);    BridgeImpl* child;    while (iter) {	child = static_cast<BridgeImpl*>(iter->data);	assert(child);	child->_parent = 0;	iter = g_list_next(iter);    }    g_list_free(_childFrames);    freeGListOfStrings(_documentState);    disconnectFrameContents();    }BridgeImpl* BridgeImpl::mainFrame(){    if (_parent) 	return _parent->mainFrame();    return this;}/** Searches for a child frame from current frame and subframes  * internal function * Searches for a child frame from current frame and subframes recursively * @return 0 on failure */BridgeImpl* BridgeImpl::findChildFrameNamed(const gchar* frameName){    if (strcmp(this->_frameName, frameName)==0)	return this;    BridgeImpl* result;    GList* iter = g_list_first(_childFrames);    BridgeImpl* child;    while (iter) {	child = static_cast<BridgeImpl*>(iter->data);	assert(child);	result = child->findChildFrameNamed(frameName);	if (result) 	    return result;	iter = g_list_next(iter);    }    return 0;}/** Searches for child frames from current frame, subframes, and parent frames  * internal * First searches name from self, then childframes, except asendFrom -branch.  * If not found, ascens one level up in the hierarchy */BridgeImpl* BridgeImpl::ascendingFindFrameNamed(const gchar* frameName, BridgeImpl* ascendFrom){    // search self    if (strcmp(this->_frameName, frameName)==0)	return this;    BridgeImpl* result = 0;    // search subtrees != ascendFrom    GList* iter = g_list_first(_childFrames);    BridgeImpl* child;    while (iter) {	child = static_cast<BridgeImpl*>(iter->data);	assert(child);	if (child != ascendFrom) {	    result = child->findChildFrameNamed(frameName);	    if (result) return result;	}	iter = g_list_next(iter);    }    // search parent    if (_parent)	return _parent->ascendingFindFrameNamed(frameName, this);    return 0;}WebCoreBridge* BridgeImpl::findFrameNamed(const gchar *frameName){        // search common names    if (strcmp(frameName, "_top")==0)	return mainFrame();    if (strcmp(frameName,"_parent")==0) 	return _parent ? _parent : this;    if (strcmp(frameName,"_self")==0)	return this;    // search self    if (this->_frameName == frameName)	return this;    BridgeImpl* result = 0;    // search subframes    result = findChildFrameNamed(frameName);    if (result) 	return result;    // search upper branches    if (_parent) {	result = _parent->ascendingFindFrameNamed(frameName, this);	if (result)	    return result;    }    // search other peers    BridgeImpl *thisMain = mainFrame();    GList* myPeers = thisMain->peers();    GList* iter = g_list_first(myPeers);    BridgeImpl *child;    while (iter) {	child = static_cast<BridgeImpl*>(iter->data);	if (thisMain != child) {  // skip this windows' branch, already searched	    result = child->findChildFrameNamed(frameName);	    if (result) 		return result;	}	iter = g_list_next(iter);    }    return 0;}const gchar* BridgeImpl::generateFrameName(){    static gchar* templ = "<!-- frame: %d-->";    // doesn't this leak one duplicated string?    if (_generatedFrameName) g_free(_generatedFrameName);    _generatedFrameName = g_strdup_printf(templ, _generatedFrameNameId);    _generatedFrameNameId++;    return _generatedFrameName;}void BridgeImpl::frameDetached(){    if (_parent) {	_parent->_childFrames = g_list_remove(_parent->_childFrames, this);    }        delete this;}GtkWidget* BridgeImpl::documentView(){    return GTK_WIDGET (frameWidget);}void BridgeImpl::commitLoad(){    assignToString(&_currentURL, _requestedURL);    emitCommitLoad();    }// methods overrides default WebCore method. void BridgeImpl::openURL(const gchar *_URL, 			 bool reload, 			 const gchar *_contentType,			 const gchar *refresh, 			 GTime _lastModified, 			 KWIQPageCache* pageCache){    _generatedFrameNameId = 0;    clearFrameContents(true);    WebCoreBridge::openURL(_URL, reload, _contentType, refresh, _lastModified, pageCache);    VisitedURLHistory::sharedProvider()->insertVisitedURL(_URL);}/**  * call didNotOpenURL(URL) * if user doesn't accept the load  (popup-blocker, form submission dialog */void BridgeImpl::loadURL(const gchar* URL,			 const gchar* referrer,			 bool reload, 			 bool onLoadEvent,  			 const gchar* target,			 NSEvent *event, 			 NRCit::DOMElement* form, 			 GHashTable* formValues){    WebCoreBridge *targetBridge = this;    if (isEmptyString(_frameName))	assignToString(&_frameName, target);    if (!isEmptyString(target)) targetBridge = findFrameNamed(target);        if (targetBridge && targetBridge != this) {	targetBridge->loadURL(URL, referrer, reload, onLoadEvent, target, event, form, formValues);	return;    }     if (!URL) URL = "";    if (!targetBridge) {        // unknown windows should open in new window	// target will have _blank or some custom name	if (onLoadEvent) {	    // FIXME: implement: settings -> block popups	    didNotOpenURL(URL); 	} else { 	    mainFrame()->createWindowWithURL(URL, target);	    return;	}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -