#define SPEED_DEBUG
#include "khtml_part.h"
#if APPLE_CHANGES
#define DIRECT_LINKAGE_TO_ECMA
#define QT_NO_CLIPBOARD
#define QT_NO_DRAGANDDROP
#endif
#include "khtml_pagecache.h"
#include "dom/dom_string.h"
#include "dom/dom_element.h"
#include "html/html_documentimpl.h"
#include "html/html_baseimpl.h"
#include "html/html_miscimpl.h"
#include "html/html_imageimpl.h"
#include "rendering/render_text.h"
#include "rendering/render_frames.h"
#include "misc/htmlhashes.h"
#include "misc/loader.h"
#include "xml/dom2_eventsimpl.h"
#include "xml/xml_tokenizer.h"
#include "css/cssstyleselector.h"
#include "css/csshelper.h"
using namespace DOM;
#include "khtmlview.h"
#include <kparts/partmanager.h>
#include "ecma/kjs_proxy.h"
#include "khtml_settings.h"
#include <sys/types.h>
#include <assert.h>
#include <unistd.h>
#include <kstandarddirs.h>
#include <kio/job.h>
#include <kio/global.h>
#include <kdebug.h>
#include <kiconloader.h>
#include <klocale.h>
#include <kcharsets.h>
#include <kmessagebox.h>
#include <kstdaction.h>
#include <kfiledialog.h>
#include <ktrader.h>
#include <kdatastream.h>
#include <ktempfile.h>
#include <kglobalsettings.h>
#include <kurldrag.h>
#include <kapplication.h>
#if !defined(QT_NO_DRAGANDDROP)
#include <kmultipledrag.h>
#endif
#include <ksslcertchain.h>
#include <ksslinfodlg.h>
#include <qclipboard.h>
#include <qfile.h>
#include <qmetaobject.h>
#include <private/qucomextra_p.h>
#include "khtmlpart_p.h"
#ifdef APPLE_CHANGES
#include <CoreServices/CoreServices.h>
#endif
using khtml::Decoder;
using khtml::RenderObject;
using khtml::RenderText;
using khtml::InlineTextBoxArray;
using KParts::BrowserInterface;
namespace khtml {
class PartStyleSheetLoader : public CachedObjectClient
{
public:
PartStyleSheetLoader(KHTMLPart *part, DOM::DOMString url, DocLoader* dl)
{
m_part = part;
m_cachedSheet = Cache::requestStyleSheet(dl, url );
if (m_cachedSheet)
m_cachedSheet->ref( this );
}
virtual ~PartStyleSheetLoader()
{
if ( m_cachedSheet ) m_cachedSheet->deref(this);
}
virtual void setStyleSheet(const DOM::DOMString&, const DOM::DOMString &sheet)
{
if ( m_part )
m_part->setUserStyleSheet( sheet.string() );
delete this;
}
QGuardedPtr<KHTMLPart> m_part;
khtml::CachedCSSStyleSheet *m_cachedSheet;
};
};
FrameList::Iterator FrameList::find( const QString &name )
{
Iterator it = begin();
Iterator e = end();
for (; it!=e; ++it )
if ( (*it).m_name==name )
break;
return it;
}
KHTMLPart::KHTMLPart( QWidget *parentWidget, const char *widgetname, QObject *parent, const char *name,
GUIProfile prof )
: KParts::ReadOnlyPart( parent, name )
{
d = 0;
KHTMLFactory::registerPart( this );
setInstance( KHTMLFactory::instance(), prof == BrowserViewGUI && !parentPart() );
#if !APPLE_CHANGES
init( new KHTMLView( this, parentWidget, widgetname ), prof );
#endif
}
#if !APPLE_CHANGES
KHTMLPart::KHTMLPart( KHTMLView *view, QObject *parent, const char *name, GUIProfile prof )
: KParts::ReadOnlyPart( parent, name )
{
d = 0;
KHTMLFactory::registerPart( this );
setInstance( KHTMLFactory::instance(), prof == BrowserViewGUI && !parentPart() );
assert( view );
init( view, prof );
}
#endif // APPLE_CHANGES
void KHTMLPart::init( KHTMLView *view, GUIProfile prof )
{
if ( prof == DefaultGUI )
setXMLFile( "khtml.rc" );
else if ( prof == BrowserViewGUI )
setXMLFile( "khtml_browser.rc" );
frameCount = 0;
d = new KHTMLPartPrivate(parent());
d->m_view = view;
setWidget( d->m_view );
#if !APPLE_CHANGES
d->m_guiProfile = prof;
#endif
d->m_extension = new KHTMLPartBrowserExtension( this );
d->m_hostExtension = new KHTMLPartBrowserHostExtension( this );
d->m_bSecurityInQuestion = false;
d->m_bMousePressed = false;
#if !APPLE_CHANGES
d->m_paLoadImages = 0;
d->m_paViewDocument = new KAction( i18n( "View Document Source" ), 0, this, SLOT( slotViewDocumentSource() ), actionCollection(), "viewDocumentSource" );
d->m_paViewFrame = new KAction( i18n( "View Frame Source" ), 0, this, SLOT( slotViewFrameSource() ), actionCollection(), "viewFrameSource" );
d->m_paSaveBackground = new KAction( i18n( "Save &Background Image As..." ), 0, this, SLOT( slotSaveBackground() ), actionCollection(), "saveBackground" );
d->m_paSaveDocument = new KAction( i18n( "&Save As..." ), CTRL+Key_S, this, SLOT( slotSaveDocument() ), actionCollection(), "saveDocument" );
if ( parentPart() )
d->m_paSaveDocument->setShortcut( KShortcut() ); d->m_paSaveFrame = new KAction( i18n( "Save &Frame As..." ), 0, this, SLOT( slotSaveFrame() ), actionCollection(), "saveFrame" );
d->m_paSecurity = new KAction( i18n( "Security..." ), "decrypted", 0, this, SLOT( slotSecurity() ), actionCollection(), "security" );
d->m_paDebugRenderTree = new KAction( "print rendering tree to stdout", 0, this, SLOT( slotDebugRenderTree() ), actionCollection(), "debugRenderTree" );
d->m_paDebugDOMTree = new KAction( "print DOM tree to stdout", 0, this, SLOT( slotDebugDOMTree() ), actionCollection(), "debugDOMTree" );
QString foo1 = i18n("Show Images");
QString foo2 = i18n("Show Animated Images");
QString foo3 = i18n("Stop Animated Images");
d->m_paSetEncoding = new KSelectAction( i18n( "Set &Encoding" ), 0, this, SLOT( slotSetEncoding() ), actionCollection(), "setEncoding" );
QStringList encodings = KGlobal::charsets()->descriptiveEncodingNames();
encodings.prepend( i18n( "Auto" ) );
d->m_paSetEncoding->setItems( encodings );
d->m_paSetEncoding->setCurrentItem(0);
d->m_paUseStylesheet = new KSelectAction( i18n( "&Use Stylesheet"), 0, this, SLOT( slotUseStylesheet() ), actionCollection(), "useStylesheet" );
d->m_paIncZoomFactor = new KHTMLZoomFactorAction( this, true, i18n( "Increase Font Sizes" ), "viewmag+", this, SLOT( slotIncZoom() ), actionCollection(), "incFontSizes" );
d->m_paDecZoomFactor = new KHTMLZoomFactorAction( this, false, i18n( "Decrease Font Sizes" ), "viewmag-", this, SLOT( slotDecZoom() ), actionCollection(), "decFontSizes" );
d->m_paFind = KStdAction::find( this, SLOT( slotFind() ), actionCollection(), "find" );
if ( parentPart() )
d->m_paFind->setShortcut( KShortcut() );
d->m_paPrintFrame = new KAction( i18n( "Print Frame" ), "frameprint", 0, this, SLOT( slotPrintFrame() ), actionCollection(), "printFrame" );
d->m_paSelectAll = KStdAction::selectAll( this, SLOT( slotSelectAll() ), actionCollection(), "selectAll" );
if ( parentPart() )
d->m_paSelectAll->setShortcut( KShortcut() ); #endif
#if !APPLE_CHANGES
d->m_bJScriptEnabled = KHTMLFactory::defaultHTMLSettings()->isJavaScriptEnabled();
d->m_bJScriptDebugEnabled = KHTMLFactory::defaultHTMLSettings()->isJavaScriptDebugEnabled();
d->m_bJavaEnabled = KHTMLFactory::defaultHTMLSettings()->isJavaEnabled();
d->m_bPluginsEnabled = KHTMLFactory::defaultHTMLSettings()->isPluginsEnabled();
#else
d->m_bJScriptEnabled = true;
d->m_bJScriptDebugEnabled = true;
d->m_bJavaEnabled = true;
d->m_bPluginsEnabled = true;
#endif
#if !APPLE_CHANGES
connect( this, SIGNAL( completed() ),
this, SLOT( updateActions() ) );
connect( this, SIGNAL( completed( bool ) ),
this, SLOT( updateActions() ) );
connect( this, SIGNAL( started( KIO::Job * ) ),
this, SLOT( updateActions() ) );
d->m_popupMenuXML = KXMLGUIFactory::readConfigFile( locate( "data", "khtml/khtml_popupmenu.rc", KHTMLFactory::instance() ) );
#endif
connect( khtml::Cache::loader(), SIGNAL( requestStarted( khtml::DocLoader*, khtml::CachedObject* ) ),
this, SLOT( slotLoaderRequestStarted( khtml::DocLoader*, khtml::CachedObject* ) ) );
connect( khtml::Cache::loader(), SIGNAL( requestDone( khtml::DocLoader*, khtml::CachedObject *) ),
this, SLOT( slotLoaderRequestDone( khtml::DocLoader*, khtml::CachedObject *) ) );
connect( khtml::Cache::loader(), SIGNAL( requestFailed( khtml::DocLoader*, khtml::CachedObject *) ),
this, SLOT( slotLoaderRequestDone( khtml::DocLoader*, khtml::CachedObject *) ) );
findTextBegin();
connect( &d->m_redirectionTimer, SIGNAL( timeout() ),
this, SLOT( slotRedirect() ) );
#if !APPLE_CHANGES
d->m_dcopobject = new KHTMLPartIface(this);
#endif
}
KHTMLPart::~KHTMLPart()
{
#if !APPLE_CHANGES
if ( d->m_findDialog )
disconnect( d->m_findDialog, SIGNAL( destroyed() ),
this, SLOT( slotFindDialogDestroyed() ) );
if ( d->m_manager )
{
d->m_manager->setActivePart( 0 );
}
#endif
stopAutoScroll();
cancelRedirection();
if (!d->m_bComplete)
closeURL();
disconnect( khtml::Cache::loader(), SIGNAL( requestStarted( khtml::DocLoader*, khtml::CachedObject* ) ),
this, SLOT( slotLoaderRequestStarted( khtml::DocLoader*, khtml::CachedObject* ) ) );
disconnect( khtml::Cache::loader(), SIGNAL( requestDone( khtml::DocLoader*, khtml::CachedObject *) ),
this, SLOT( slotLoaderRequestDone( khtml::DocLoader*, khtml::CachedObject *) ) );
disconnect( khtml::Cache::loader(), SIGNAL( requestFailed( khtml::DocLoader*, khtml::CachedObject *) ),
this, SLOT( slotLoaderRequestDone( khtml::DocLoader*, khtml::CachedObject *) ) );
clear();
if ( d->m_view )
{
d->m_view->hide();
d->m_view->viewport()->hide();
d->m_view->m_part = 0;
}
#if APPLE_CHANGES
delete d->m_hostExtension;
#endif
delete d; d = 0;
KHTMLFactory::deregisterPart( this );
}
bool KHTMLPart::restoreURL( const KURL &url )
{
kdDebug( 6050 ) << "KHTMLPart::restoreURL " << url.url() << endl;
cancelRedirection();
d->m_bComplete = false;
d->m_bLoadEventEmitted = false;
d->m_workingURL = url;
#if !APPLE_CHANGES
d->m_bJScriptEnabled = KHTMLFactory::defaultHTMLSettings()->isJavaScriptEnabled(url.host());
d->m_bJScriptDebugEnabled = KHTMLFactory::defaultHTMLSettings()->isJavaScriptDebugEnabled();
d->m_bJavaEnabled = KHTMLFactory::defaultHTMLSettings()->isJavaEnabled(url.host());
d->m_bPluginsEnabled = KHTMLFactory::defaultHTMLSettings()->isPluginsEnabled(url.host());
#else
d->m_bJScriptEnabled = d->m_settings->isJavaScriptEnabled(url.host());
d->m_bJScriptDebugEnabled = d->m_settings->isJavaScriptDebugEnabled();
d->m_bJavaEnabled = d->m_settings->isJavaEnabled(url.host());
d->m_bPluginsEnabled = d->m_settings->isPluginsEnabled(url.host());
#endif
m_url = url;
KHTMLPageCache::self()->fetchData( d->m_cacheId, this, SLOT(slotRestoreData(const QByteArray &)));
emit started( 0L );
return true;
}
#if APPLE_CHANGES
bool KHTMLPart::didOpenURL(const KURL &url)
#else
bool KHTMLPart::openURL( const KURL &url )
#endif
{
kdDebug( 6050 ) << "KHTMLPart(" << this << ")::openURL " << url.url() << endl;
if (d->m_scheduledRedirection == redirectionDuringLoad){
return false;
}
cancelRedirection();
#if !APPLE_CHANGES
if ( url.protocol() == "error" && url.hasSubURL() ) {
closeURL();
KURL::List urls = KURL::split( url );
if ( urls.count() > 1 ) {
KURL mainURL = urls.first();
int error = mainURL.queryItem( "error" ).toInt();
if ( error == 0 ) error = KIO::ERR_UNKNOWN;
QString errorText = mainURL.queryItem( "errText" );
urls.pop_front();
d->m_workingURL = KURL::join( urls );
emit d->m_extension->setLocationBarURL( d->m_workingURL.prettyURL() );
htmlError( error, errorText, d->m_workingURL );
return true;
}
}
#endif // APPLE_CHANGES
KParts::URLArgs args( d->m_extension->urlArgs() );
#if !APPLE_CHANGES
if (d->m_doc) {
bool isFrameSet = false;
if ( d->m_doc->isHTMLDocument() ) {
HTMLDocumentImpl* htmlDoc = static_cast<HTMLDocumentImpl*>(d->m_doc);
isFrameSet = htmlDoc->body() && (htmlDoc->body()->id() == ID_FRAMESET);
}
if ( !isFrameSet &&
urlcmp( url.url(), m_url.url(), true, true ) &&
url.hasRef() && !args.doPost() && !args.reload )
{
kdDebug( 6050 ) << "KHTMLPart::openURL, jumping to anchor. m_url = " << url.url() << endl;
m_url = url;
emit started( 0L );
if ( !gotoAnchor( url.encodedHtmlRef()) )
gotoAnchor( url.htmlRef() );
d->m_bComplete = true;
d->m_doc->setParsing(false);
kdDebug( 6050 ) << "completed..." << endl;
emit completed();
return true;
}
}
#endif // APPLE_CHANGES
if (!d->m_restored)
{
kdDebug( 6050 ) << "closing old URL" << endl;
closeURL();
}
#if !APPLE_CHANGES
args.metaData().insert("main_frame_request", parentPart() == 0 ? "TRUE" : "FALSE" );
args.metaData().insert("ssl_was_in_use", d->m_ssl_in_use ? "TRUE" : "FALSE" );
args.metaData().insert("ssl_activate_warnings", "TRUE" );
#endif
if (d->m_restored)
d->m_cachePolicy = KIO::CC_Cache;
else if (args.reload)
d->m_cachePolicy = KIO::CC_Refresh;
else
d->m_cachePolicy = KIO::CC_Verify;
if ( args.doPost() && (url.protocol().startsWith("http")) )
{
d->m_job = KIO::http_post( url, args.postData, false );
d->m_job->addMetaData("content-type", args.contentType() );
}
else
{
d->m_job = KIO::get( url, false, false );
d->m_job->addMetaData("cache", KIO::getCacheControlString(d->m_cachePolicy));
}
d->m_job->addMetaData(args.metaData());
connect( d->m_job, SIGNAL( result( KIO::Job * ) ),
SLOT( slotFinished( KIO::Job * ) ) );
#if !APPLE_CHANGES
connect( d->m_job, SIGNAL( data( KIO::Job*, const QByteArray &)),
SLOT( slotData( KIO::Job*, const QByteArray &)));
#endif
connect( d->m_job, SIGNAL(redirection(KIO::Job*, const KURL&) ),
SLOT( slotRedirection(KIO::Job*,const KURL&) ) );
d->m_bComplete = false;
d->m_bLoadEventEmitted = false;
if( d->m_bJScriptEnabled )
{
d->m_kjsStatusBarText = QString::null;
d->m_kjsDefaultStatusBarText = QString::null;
}
#if !APPLE_CHANGES
d->m_bJScriptDebugEnabled = KHTMLFactory::defaultHTMLSettings()->isJavaScriptDebugEnabled();
d->m_bJavaEnabled = KHTMLFactory::defaultHTMLSettings()->isJavaEnabled(url.host());
d->m_bPluginsEnabled = KHTMLFactory::defaultHTMLSettings()->isPluginsEnabled(url.host());
#else
d->m_bJScriptDebugEnabled = d->m_settings->isJavaScriptDebugEnabled();
d->m_bJavaEnabled = d->m_settings->isJavaEnabled(url.host());
d->m_bPluginsEnabled = d->m_settings->isPluginsEnabled(url.host());
#endif
m_url = url;
if(m_url.protocol().startsWith( "http" ) && !m_url.host().isEmpty() &&
m_url.path().isEmpty()) {
m_url.setPath("/");
emit d->m_extension->setLocationBarURL( m_url.prettyURL() );
}
d->m_workingURL = m_url;
kdDebug( 6050 ) << "KHTMLPart::openURL now (before started) m_url = " << m_url.url() << endl;
connect( d->m_job, SIGNAL( speed( KIO::Job*, unsigned long ) ),
this, SLOT( slotJobSpeed( KIO::Job*, unsigned long ) ) );
connect( d->m_job, SIGNAL( percent( KIO::Job*, unsigned long ) ),
this, SLOT( slotJobPercent( KIO::Job*, unsigned long ) ) );
emit started( 0L );
return true;
}
bool KHTMLPart::closeURL()
{
if ( d->m_job )
{
KHTMLPageCache::self()->cancelEntry(d->m_cacheId);
d->m_job->kill();
d->m_job = 0;
}
if ( d->m_doc && d->m_doc->isHTMLDocument() ) {
HTMLDocumentImpl* hdoc = static_cast<HTMLDocumentImpl*>( d->m_doc );
if ( hdoc->body() && d->m_bLoadEventEmitted && !d->m_bUnloadEventEmitted ) {
hdoc->body()->dispatchWindowEvent( EventImpl::UNLOAD_EVENT, false, false );
if ( d->m_doc )
d->m_doc->updateRendering();
d->m_bUnloadEventEmitted = true;
}
}
d->m_bComplete = true; d->m_bLoadEventEmitted = true; d->m_cachePolicy = KIO::CC_Verify;
KHTMLPageCache::self()->cancelFetch(this);
if ( d->m_doc && d->m_doc->parsing() )
{
kdDebug( 6050 ) << " was still parsing... calling end " << endl;
slotFinishedParsing();
d->m_doc->setParsing(false);
}
if ( !d->m_workingURL.isEmpty() )
{
kdDebug( 6050 ) << "Aborted before starting to render, reverting location bar to " << m_url.prettyURL() << endl;
emit d->m_extension->setLocationBarURL( m_url.prettyURL() );
}
d->m_workingURL = KURL();
if ( d->m_doc && d->m_doc->docLoader() )
khtml::Cache::loader()->cancelRequests( d->m_doc->docLoader() );
ConstFrameIt it = d->m_frames.begin();
ConstFrameIt end = d->m_frames.end();
for (; it != end; ++it )
if ( !( *it ).m_part.isNull() )
( *it ).m_part->closeURL();
d->m_bPendingChildRedirection = false;
cancelRedirection();
emit nodeActivated(Node());
return true;
}
DOM::HTMLDocument KHTMLPart::htmlDocument() const
{
if (d->m_doc && d->m_doc->isHTMLDocument())
return static_cast<HTMLDocumentImpl*>(d->m_doc);
else
return static_cast<HTMLDocumentImpl*>(0);
}
DOM::Document KHTMLPart::document() const
{
return d->m_doc;
}
KParts::BrowserExtension *KHTMLPart::browserExtension() const
{
return d->m_extension;
}
KHTMLView *KHTMLPart::view() const
{
return d->m_view;
}
void KHTMLPart::setJScriptEnabled( bool enable )
{
if ( !enable && jScriptEnabled() && d->m_jscript ) {
d->m_jscript->clear();
}
d->m_bJScriptForce = enable;
d->m_bJScriptOverride = true;
}
bool KHTMLPart::jScriptEnabled() const
{
if ( d->m_bJScriptOverride )
return d->m_bJScriptForce;
return d->m_bJScriptEnabled;
}
void KHTMLPart::setMetaRefreshEnabled( bool enable )
{
d->m_metaRefreshEnabled = enable;
}
bool KHTMLPart::metaRefreshEnabled() const
{
return d->m_metaRefreshEnabled;
}
#ifdef DIRECT_LINKAGE_TO_ECMA
extern "C" { KJSProxy *kjs_html_init(KHTMLPart *khtmlpart); }
#endif
KJSProxy *KHTMLPart::jScript()
{
if (!jScriptEnabled()){
return 0;
}
if ( !d->m_jscript )
{
#ifndef DIRECT_LINKAGE_TO_ECMA
KLibrary *lib = KLibLoader::self()->library("kjs_html");
if ( !lib ) {
setJScriptEnabled( false );
return 0;
}
void *sym = lib->symbol("kjs_html_init");
if ( !sym ) {
lib->unload();
setJScriptEnabled( false );
return 0;
}
typedef KJSProxy* (*initFunction)(KHTMLPart *);
initFunction initSym = (initFunction) sym;
d->m_jscript = (*initSym)(this);
d->m_kjs_lib = lib;
#else
d->m_jscript = kjs_html_init(this);
#endif
if (d->m_bJScriptDebugEnabled)
d->m_jscript->setDebugEnabled(true);
}
return d->m_jscript;
}
void KHTMLPart::replaceContentsWithScriptResult( const KURL &url )
{
QString script = KURL::decode_string(url.url().mid(strlen("javascript:")));
QVariant ret = executeScript(script);
if (ret.type() == QVariant::String) {
begin();
write(ret.asString());
end();
}
}
QVariant KHTMLPart::executeScript( const QString &script, bool forceUserGesture )
{
return executeScript( DOM::Node(), script, forceUserGesture );
}
QVariant KHTMLPart::executeScript( const DOM::Node &n, const QString &script, bool forceUserGesture )
{
#ifdef KJS_VERBOSE
kdDebug(6070) << "KHTMLPart::executeScript n=" << n.nodeName().string().latin1() << "(" << (n.isNull() ? 0 : n.nodeType()) << ") " << script << endl;
#endif
KJSProxy *proxy = jScript();
if (!proxy || proxy->paused())
return QVariant();
d->m_runningScripts++;
QVariant ret = proxy->evaluate( forceUserGesture ? QString::null : m_url.url(), 0, script, n );
d->m_runningScripts--;
if (!d->m_runningScripts && d->m_doc && !d->m_doc->parsing() && d->m_submitForm )
submitFormAgain();
DocumentImpl::updateDocumentsRendering();
#ifdef KJS_VERBOSE
kdDebug(6070) << "KHTMLPart::executeScript - done" << endl;
#endif
return ret;
}
bool KHTMLPart::scheduleScript(const DOM::Node &n, const QString& script)
{
d->scheduledScript = script;
d->scheduledScriptNode = n;
return true;
}
QVariant KHTMLPart::executeScheduledScript()
{
if( d->scheduledScript.isEmpty() )
return QVariant();
QVariant ret = executeScript( d->scheduledScriptNode, d->scheduledScript );
d->scheduledScript = QString();
d->scheduledScriptNode = DOM::Node();
return ret;
}
void KHTMLPart::setJavaEnabled( bool enable )
{
d->m_bJavaForce = enable;
d->m_bJavaOverride = true;
}
bool KHTMLPart::javaEnabled() const
{
#ifndef Q_WS_QWS
if( d->m_bJavaOverride )
return d->m_bJavaForce;
return d->m_bJavaEnabled;
#else
return false;
#endif
}
KJavaAppletContext *KHTMLPart::javaContext()
{
#ifndef Q_WS_QWS
return d->m_javaContext;
#else
return 0;
#endif
}
KJavaAppletContext *KHTMLPart::createJavaContext()
{
#ifndef Q_WS_QWS
if ( !d->m_javaContext ) {
#if APPLE_CHANGES
d->m_javaContext = new KJavaAppletContext(d->m_dcopobject, this);
#else
d->m_javaContext = new KJavaAppletContext(d->m_dcopobject);
connect( d->m_javaContext, SIGNAL(showStatus(const QString&)),
this, SIGNAL(setStatusBarText(const QString&)) );
connect( d->m_javaContext, SIGNAL(showDocument(const QString&, const QString&)),
this, SLOT(slotShowDocument(const QString&, const QString&)) );
#endif
}
return d->m_javaContext;
#else
return 0;
#endif
}
void KHTMLPart::setPluginsEnabled( bool enable )
{
d->m_bPluginsForce = enable;
d->m_bPluginsOverride = true;
}
bool KHTMLPart::pluginsEnabled() const
{
if ( d->m_bPluginsOverride )
return d->m_bPluginsForce;
return d->m_bPluginsEnabled;
}
#if !APPLE_CHANGES
void KHTMLPart::slotShowDocument( const QString &url, const QString &target )
{
khtml::ChildFrame *child = 0;
KParts::URLArgs args;
args.frameName = target;
QString frameName = args.frameName.lower();
if ( !frameName.isEmpty() )
{
if ( frameName == QString::fromLatin1( "_top" ) )
{
emit d->m_extension->openURLRequest( url, args );
return;
}
else if ( frameName == QString::fromLatin1( "_blank" ) )
{
emit d->m_extension->createNewWindow( url, args );
return;
}
else if ( frameName == QString::fromLatin1( "_parent" ) )
{
KParts::URLArgs newArgs( args );
newArgs.frameName = QString::null;
emit d->m_extension->openURLRequest( url, newArgs );
return;
}
else if ( frameName != QString::fromLatin1( "_self" ) )
{
khtml::ChildFrame *_frame = recursiveFrameRequest( url, args );
if ( !_frame )
{
emit d->m_extension->openURLRequest( url, args );
return;
}
child = _frame;
}
}
if ( url.find( QString::fromLatin1( "javascript:" ), 0, false ) == 0 ) {
executeScript( KURL::decode_string( url.right( url.length() - 11) ) );
return;
}
if ( child ) {
requestObject( child, KURL(url), args );
} else if ( frameName==QString::fromLatin1("_self") ) {
KParts::URLArgs newArgs( args );
newArgs.frameName = QString::null;
emit d->m_extension->openURLRequest( KURL(url), newArgs );
}
}
#endif // APPLE_CHANGES
void KHTMLPart::slotDebugDOMTree()
{
if ( d->m_doc && d->m_doc->firstChild() )
qDebug("%s", d->m_doc->firstChild()->toHTML().latin1());
}
void KHTMLPart::slotDebugRenderTree()
{
#ifndef NDEBUG
if ( d->m_doc )
d->m_doc->renderer()->printTree();
#endif
}
void KHTMLPart::setAutoloadImages( bool enable )
{
if ( d->m_doc && d->m_doc->docLoader()->autoloadImages() == enable )
return;
if ( d->m_doc )
d->m_doc->docLoader()->setAutoloadImages( enable );
#if !APPLE_CHANGES
unplugActionList( "loadImages" );
if ( enable ) {
delete d->m_paLoadImages;
d->m_paLoadImages = 0;
}
else if ( !d->m_paLoadImages )
d->m_paLoadImages = new KAction( i18n( "Display Images on Page" ), "images_display", 0, this, SLOT( slotLoadImages() ), actionCollection(), "loadImages" );
if ( d->m_paLoadImages ) {
QPtrList<KAction> lst;
lst.append( d->m_paLoadImages );
plugActionList( "loadImages", lst );
}
#endif
}
bool KHTMLPart::autoloadImages() const
{
if ( d->m_doc )
return d->m_doc->docLoader()->autoloadImages();
return true;
}
void KHTMLPart::clear()
{
if ( d->m_bCleared )
return;
d->m_bCleared = true;
d->m_bClearing = true;
#if !APPLE_CHANGES
{
ConstFrameIt it = d->m_frames.begin();
ConstFrameIt end = d->m_frames.end();
for(; it != end; ++it )
{
if ( (*it).m_run )
(*it).m_run->abort();
}
}
{
QValueList<khtml::ChildFrame>::ConstIterator it = d->m_objects.begin();
QValueList<khtml::ChildFrame>::ConstIterator end = d->m_objects.end();
for(; it != end; ++it )
{
if ( (*it).m_run )
(*it).m_run->abort();
}
}
#endif
findTextBegin();
d->m_mousePressNode = DOM::Node();
if ( d->m_doc )
d->m_doc->detach();
if ( d->m_jscript )
d->m_jscript->clear();
if ( d->m_view )
d->m_view->clear();
if ( d->m_doc )
d->m_doc->deref();
d->m_doc = 0;
if (d->m_decoder)
d->m_decoder->deref();
d->m_decoder = 0;
{
ConstFrameIt it = d->m_frames.begin();
ConstFrameIt end = d->m_frames.end();
for(; it != end; ++it )
{
if ( (*it).m_part )
{
#if !APPLE_CHANGES
partManager()->removePart( (*it).m_part );
#endif
(*it).m_part->deref();
}
}
}
d->m_frames.clear();
{
ConstFrameIt it = d->m_objects.begin();
ConstFrameIt end = d->m_objects.end();
for(; it != end; ++it )
{
if ( (*it).m_part )
{
#if !APPLE_CHANGES
partManager()->removePart( (*it).m_part );
#endif
(*it).m_part->deref();
}
}
}
d->m_objects.clear();
#ifndef Q_WS_QWS
delete d->m_javaContext;
d->m_javaContext = 0;
#endif
d->m_scheduledRedirection = noRedirectionScheduled;
d->m_delayRedirect = 0;
d->m_redirectURL = QString::null;
d->m_redirectLockHistory = true;
d->m_redirectUserGesture = false;
d->m_bHTTPRefresh = false;
d->m_bClearing = false;
d->m_frameNameId = 1;
d->m_bFirstData = true;
d->m_bMousePressed = false;
d->m_selectionStart = DOM::Node();
d->m_selectionEnd = DOM::Node();
d->m_startOffset = 0;
d->m_endOffset = 0;
#ifndef QT_NO_CLIPBOARD
connect( kapp->clipboard(), SIGNAL( selectionChanged()), SLOT( slotClearSelection()));
#endif
d->m_totalObjectCount = 0;
d->m_loadedObjects = 0;
d->m_jobPercent = 0;
if ( !d->m_haveEncoding )
d->m_encoding = QString::null;
#ifdef SPEED_DEBUG
d->m_parsetime.restart();
#endif
}
bool KHTMLPart::openFile()
{
return true;
}
DOM::HTMLDocumentImpl *KHTMLPart::docImpl() const
{
if ( d && d->m_doc && d->m_doc->isHTMLDocument() )
return static_cast<HTMLDocumentImpl*>(d->m_doc);
return 0;
}
DOM::DocumentImpl *KHTMLPart::xmlDocImpl() const
{
if ( d )
return d->m_doc;
return 0;
}
void KHTMLPart::receivedFirstData()
{
begin( d->m_workingURL, d->m_extension->urlArgs().xOffset, d->m_extension->urlArgs().yOffset );
d->m_doc->docLoader()->setCachePolicy(d->m_cachePolicy);
d->m_workingURL = KURL();
d->m_cacheId = KHTMLPageCache::self()->createCacheEntry();
#if APPLE_CHANGES
QString qData;
#else
d->m_bSecurityInQuestion = false;
d->m_ssl_in_use = (d->m_job->queryMetaData("ssl_in_use") == "TRUE");
kdDebug(6050) << "SSL in use? " << d->m_job->queryMetaData("ssl_in_use") << endl;
{
KHTMLPart *p = parentPart();
if (p && p->d->m_ssl_in_use != d->m_ssl_in_use) {
while (p->parentPart()) p = p->parentPart();
p->d->m_paSecurity->setIcon( "halfencrypted" );
p->d->m_bSecurityInQuestion = true;
kdDebug(6050) << "parent setIcon half done." << endl;
}
}
d->m_paSecurity->setIcon( d->m_ssl_in_use ? "encrypted" : "decrypted" );
kdDebug(6050) << "setIcon " << ( d->m_ssl_in_use ? "encrypted" : "decrypted" ) << " done." << endl;
d->m_ssl_peer_certificate = d->m_job->queryMetaData("ssl_peer_certificate");
d->m_ssl_peer_chain = d->m_job->queryMetaData("ssl_peer_chain");
d->m_ssl_peer_ip = d->m_job->queryMetaData("ssl_peer_ip");
d->m_ssl_cipher = d->m_job->queryMetaData("ssl_cipher");
d->m_ssl_cipher_desc = d->m_job->queryMetaData("ssl_cipher_desc");
d->m_ssl_cipher_version = d->m_job->queryMetaData("ssl_cipher_version");
d->m_ssl_cipher_used_bits = d->m_job->queryMetaData("ssl_cipher_used_bits");
d->m_ssl_cipher_bits = d->m_job->queryMetaData("ssl_cipher_bits");
d->m_ssl_cert_state = d->m_job->queryMetaData("ssl_cert_state");
QString qData = d->m_job->queryMetaData("charset");
if ( !qData.isEmpty() && !d->m_haveEncoding ) d->m_encoding = qData;
#endif // APPLE_CHANGES
qData = d->m_job->queryMetaData("http-refresh");
if( !qData.isEmpty() && d->m_metaRefreshEnabled )
{
kdDebug(6050) << "HTTP Refresh Request: " << qData << endl;
double delay;
int pos = qData.find( ';' );
if ( pos == -1 )
pos = qData.find( ',' );
if( pos == -1 )
{
delay = qData.stripWhiteSpace().toDouble();
#if APPLE_CHANGES
scheduleRedirection( delay, m_url.url(), delay <= 1);
#else
scheduleRedirection( delay, m_url.url());
#endif
}
else
{
int end_pos = qData.length();
delay = qData.left(pos).stripWhiteSpace().toDouble();
while ( qData[++pos] == ' ' );
if ( qData.find( "url", pos, false ) == pos )
{
pos += 3;
while (qData[pos] == ' ' || qData[pos] == '=' )
pos++;
if ( qData[pos] == '"' )
{
pos++;
int index = end_pos-1;
while( index > pos )
{
if ( qData[index] == '"' )
break;
index--;
}
if ( index > pos )
end_pos = index;
}
}
#if APPLE_CHANGES
scheduleRedirection( delay, d->m_doc->completeURL( qData.mid( pos, end_pos ) ), delay <= 1);
#else
scheduleRedirection( delay, d->m_doc->completeURL( qData.mid( pos, end_pos ) ));
#endif
}
d->m_bHTTPRefresh = true;
}
d->m_lastModified = d->m_job->queryMetaData("modified");
}
#if !APPLE_CHANGES
void KHTMLPart::slotData( KIO::Job* kio_job, const QByteArray &data )
{
assert ( d->m_job == kio_job );
if ( !d->m_workingURL.isEmpty() )
receivedFirstData( );
KHTMLPageCache::self()->addData(d->m_cacheId, data);
write( data.data(), data.size() );
}
void KHTMLPart::slotRestoreData(const QByteArray &data )
{
if ( !d->m_workingURL.isEmpty() )
{
long saveCacheId = d->m_cacheId;
begin( d->m_workingURL, d->m_extension->urlArgs().xOffset, d->m_extension->urlArgs().yOffset );
d->m_cacheId = saveCacheId;
d->m_workingURL = KURL();
}
write( data.data(), data.size() );
if (data.size() == 0)
{
if (d->m_doc && d->m_doc->parsing())
end(); }
}
void KHTMLPart::showError( KIO::Job* job )
{
kdDebug() << "KHTMLPart::showError d->m_bParsing=" << (d->m_doc && d->m_doc->parsing()) << " d->m_bComplete=" << d->m_bComplete
<< " d->m_bCleared=" << d->m_bCleared << endl;
if (job->error() == KIO::ERR_NO_CONTENT)
return;
if ( (d->m_doc && d->m_doc->parsing()) || d->m_workingURL.isEmpty() ) job->showErrorDialog( );
else
{
htmlError( job->error(), job->errorText(), d->m_workingURL );
}
}
void KHTMLPart::htmlError( int errorCode, const QString& text, const KURL& reqUrl )
{
kdDebug(6050) << "KHTMLPart::htmlError errorCode=" << errorCode << " text=" << text << endl;
bool bJSFO = d->m_bJScriptForce;
bool bJSOO = d->m_bJScriptOverride;
d->m_bJScriptForce = false;
d->m_bJScriptOverride = true;
begin();
QString errText = QString::fromLatin1( "<HTML><HEAD><TITLE>" );
errText += i18n( "Error while loading %1" ).arg( reqUrl.htmlURL() );
errText += QString::fromLatin1( "</TITLE></HEAD><BODY><P>" );
errText += i18n( "An error occured while loading <B>%1</B>:" ).arg( reqUrl.htmlURL() );
errText += QString::fromLatin1( "</P><P>" );
QString kioErrString = KIO::buildErrorString( errorCode, text );
kioErrString.replace(QRegExp("&"), QString("&"));
kioErrString.replace(QRegExp("<"), QString("<"));
kioErrString.replace(QRegExp(">"), QString(">"));
kioErrString.replace( QRegExp("\n"), "<BR/>" );
errText += kioErrString;
errText += QString::fromLatin1( "</P></BODY></HTML>" );
write(errText);
end();
d->m_bJScriptForce = bJSFO;
d->m_bJScriptOverride = bJSOO;
m_url = reqUrl; d->m_workingURL = KURL();
emit started( 0 );
emit completed();
return;
QString errorName, techName, description;
QStringList causes, solutions;
QByteArray raw = KIO::rawErrorDetail( errorCode, text, &reqUrl );
QDataStream stream(raw, IO_ReadOnly);
stream >> errorName >> techName >> description >> causes >> solutions;
QString url, protocol, datetime;
url = reqUrl.prettyURL();
protocol = reqUrl.protocol();
datetime = KGlobal::locale()->formatDateTime( QDateTime::currentDateTime(),
false );
QString doc = QString::fromLatin1( "<html><head><title>" );
doc += i18n( "Error: " );
doc += errorName;
doc += QString::fromLatin1( " - %1</title></head><body><h1>" ).arg( url );
doc += i18n( "The requested operation could not be completed" );
doc += QString::fromLatin1( "</h1><h2>" );
doc += errorName;
doc += QString::fromLatin1( "</h2>" );
if ( techName != QString::null ) {
doc += QString::fromLatin1( "<h2>" );
doc += i18n( "Technical Reason: " );
doc += techName;
doc += QString::fromLatin1( "</h2>" );
}
doc += QString::fromLatin1( "<h3>" );
doc += i18n( "Details of the Request:" );
doc += QString::fromLatin1( "</h3><ul><li>" );
doc += i18n( "URL: %1" ).arg( url );
doc += QString::fromLatin1( "</li><li>" );
if ( protocol != QString::null ) {
doc += QString::fromLatin1( "</li><li>" );
}
doc += i18n( "Date and Time: %1" ).arg( datetime );
doc += QString::fromLatin1( "</li><li>" );
doc += i18n( "Additional Information: %1" ).arg( text );
doc += QString::fromLatin1( "</li></ul><h3>" );
doc += i18n( "Description:" );
doc += QString::fromLatin1( "</h3><p>" );
doc += description;
doc += QString::fromLatin1( "</p>" );
if ( causes.count() ) {
doc += QString::fromLatin1( "<h3>" );
doc += i18n( "Possible Causes:" );
doc += QString::fromLatin1( "</h3><ul><li>" );
doc += causes.join( "</li><li>" );
doc += QString::fromLatin1( "</li></ul>" );
}
if ( solutions.count() ) {
doc += QString::fromLatin1( "<h3>" );
doc += i18n( "Possible Solutions:" );
doc += QString::fromLatin1( "</h3><ul><li>" );
doc += solutions.join( "</li><li>" );
doc += QString::fromLatin1( "</li></ul>" );
}
doc += QString::fromLatin1( "</body></html>" );
write( doc );
end();
}
#endif
void KHTMLPart::slotFinished( KIO::Job * job )
{
if (job->error())
{
KHTMLPageCache::self()->cancelEntry(d->m_cacheId);
d->m_job = 0L;
#if !APPLE_CHANGES
emit canceled( job->errorString() );
#endif
checkCompleted();
#if !APPLE_CHANGES
showError( job );
#endif
return;
}
KHTMLPageCache::self()->endData(d->m_cacheId);
if ( d->m_doc && d->m_doc->docLoader()->expireDate() && m_url.protocol().lower().startsWith("http"))
KIO::http_update_cache(m_url, false, d->m_doc->docLoader()->expireDate());
d->m_workingURL = KURL();
d->m_job = 0L;
if (d->m_doc->parsing())
end(); }
void KHTMLPart::begin( const KURL &url, int xOffset, int yOffset )
{
#if APPLE_CHANGES
if (d->m_workingURL.isEmpty()) {
KWQ(this)->createEmptyDocument();
}
#endif
clear();
#if !APPLE_CHANGES
d->m_bJScriptEnabled = KHTMLFactory::defaultHTMLSettings()->isJavaScriptEnabled(url.host());
#else
d->m_bJScriptEnabled = d->m_settings->isJavaScriptEnabled(url.host());
#endif
d->m_bCleared = false;
d->m_cacheId = 0;
d->m_bComplete = false;
d->m_bLoadEventEmitted = false;
if(url.isValid()) {
#if APPLE_CHANGES
KHTMLFactory::vLinks()->insert( KWQ(this)->requestedURLString() );
#else
QString urlString = url.url();
KHTMLFactory::vLinks()->insert( urlString );
QString urlString2 = url.prettyURL();
if ( urlString != urlString2 ) {
KHTMLFactory::vLinks()->insert( urlString2 );
}
#endif
}
KParts::URLArgs args( d->m_extension->urlArgs() );
args.xOffset = xOffset;
args.yOffset = yOffset;
d->m_extension->setURLArgs( args );
KURL ref(url);
ref.setUser(QSTRING_NULL);
ref.setPass(QSTRING_NULL);
ref.setRef(QSTRING_NULL);
d->m_referrer = ref.protocol().startsWith("http") ? ref.url() : "";
m_url = url;
KURL baseurl;
#if APPLE_CHANGES
if ( !m_url.isEmpty() )
{
baseurl = m_url;
}
#else
if ( !m_url.isEmpty() )
{
KURL::List lst = KURL::split( m_url );
if ( !lst.isEmpty() )
baseurl = *lst.begin();
KURL title( baseurl );
title.setRef( QString::null );
title.setQuery( QString::null );
emit setWindowCaption( title.url() );
}
else
emit setWindowCaption( i18n( "no title", "* Unknown *" ) );
#endif
if (args.serviceType == "text/xml" || args.serviceType == "application/xml" || args.serviceType == "application/xhtml+xml")
d->m_doc = DOMImplementationImpl::instance()->createDocument( d->m_view );
else
d->m_doc = DOMImplementationImpl::instance()->createHTMLDocument( d->m_view );
d->m_doc->ref();
if (!d->m_doc->attached())
d->m_doc->attach( );
d->m_doc->setURL( m_url.url() );
d->m_doc->setBaseURL( baseurl.url() );
#if APPLE_CHANGES
if (d->m_decoder)
d->m_doc->setDecoder(d->m_decoder);
#endif
#if !APPLE_CHANGES
d->m_doc->docLoader()->setShowAnimations( KHTMLFactory::defaultHTMLSettings()->showAnimations() );
#else
d->m_doc->docLoader()->setShowAnimations( d->m_settings->showAnimations() );
#endif
#if APPLE_CHANGES
KWQ(this)->updatePolicyBaseURL();
#endif
#if !APPLE_CHANGES
d->m_paUseStylesheet->setItems(QStringList());
d->m_paUseStylesheet->setEnabled( false );
#endif
#if !APPLE_CHANGES
setAutoloadImages( KHTMLFactory::defaultHTMLSettings()->autoLoadImages() );
QString userStyleSheet = KHTMLFactory::defaultHTMLSettings()->userStyleSheet();
#else
setAutoloadImages( d->m_settings->autoLoadImages() );
QString userStyleSheet = d->m_settings->userStyleSheet();
#endif
if ( !userStyleSheet.isEmpty() )
setUserStyleSheet( KURL( userStyleSheet ) );
#if APPLE_CHANGES
KWQ(this)->restoreDocumentState();
#else
d->m_doc->setRestoreState(args.docState);
#endif
d->m_doc->open();
d->m_view->resizeContents( 0, 0 );
connect(d->m_doc,SIGNAL(finishedParsing()),this,SLOT(slotFinishedParsing()));
#if !APPLE_CHANGES
emit d->m_extension->enableAction( "print", true );
#endif
d->m_doc->setParsing(true);
}
void KHTMLPart::write( const char *str, int len )
{
if ( !d->m_decoder ) {
d->m_decoder = new Decoder;
if (!d->m_encoding.isNull())
d->m_decoder->setEncoding(d->m_encoding.latin1(),
d->m_haveEncoding ? Decoder::UserChosenEncoding : Decoder::EncodingFromHTTPHeader);
else {
const char *defaultEncoding = (parentPart() && parentPart()->d->m_decoder)
? parentPart()->d->m_decoder->encoding() : settings()->encoding().latin1();
d->m_decoder->setEncoding(defaultEncoding, Decoder::DefaultEncoding);
}
#if APPLE_CHANGES
if (d->m_doc)
d->m_doc->setDecoder(d->m_decoder);
#endif
}
if ( len == 0 )
return;
if ( len == -1 )
len = strlen( str );
QString decoded = d->m_decoder->decode( str, len );
if(decoded.isEmpty()) return;
if(d->m_bFirstData) {
d->m_doc->determineParseMode( decoded );
d->m_bFirstData = false;
if(d->m_decoder->visuallyOrdered()) d->m_doc->setVisuallyOrdered();
d->m_doc->recalcStyle( NodeImpl::Force );
}
if (jScript())
jScript()->appendSourceFile(m_url.url(),decoded);
Tokenizer* t = d->m_doc->tokenizer();
ref();
if(t)
t->write( decoded, true );
deref();
}
void KHTMLPart::write( const QString &str )
{
if ( str.isNull() )
return;
if(d->m_bFirstData) {
d->m_doc->setParseMode( DocumentImpl::Strict );
d->m_bFirstData = false;
}
if (jScript())
jScript()->appendSourceFile(m_url.url(),str);
Tokenizer* t = d->m_doc->tokenizer();
if(t)
t->write( str, true );
}
void KHTMLPart::end()
{
if(d->m_decoder)
write(d->m_decoder->flush());
if (d->m_doc)
d->m_doc->finishParsing();
}
#if !APPLE_CHANGES
void KHTMLPart::paint(QPainter *p, const QRect &rc, int yOff, bool *more)
{
if (!d->m_view) return;
d->m_view->paint(p, rc, yOff, more);
}
#endif
void KHTMLPart::stopAnimations()
{
if ( d->m_doc )
d->m_doc->docLoader()->setShowAnimations( KHTMLSettings::KAnimationDisabled );
ConstFrameIt it = d->m_frames.begin();
ConstFrameIt end = d->m_frames.end();
for (; it != end; ++it )
if ( !( *it ).m_part.isNull() && ( *it ).m_part->inherits( "KHTMLPart" ) ) {
KParts::ReadOnlyPart* p = ( *it ).m_part;
static_cast<KHTMLPart*>( p )->stopAnimations();
}
}
void KHTMLPart::slotFinishedParsing()
{
d->m_doc->setParsing(false);
checkEmitLoadEvent();
disconnect(d->m_doc,SIGNAL(finishedParsing()),this,SLOT(slotFinishedParsing()));
if (!d->m_view)
return;
d->m_view->restoreScrollBar();
if ( !m_url.encodedHtmlRef().isEmpty() )
if ( !gotoAnchor( m_url.encodedHtmlRef()) )
gotoAnchor( m_url.htmlRef() );
checkCompleted();
}
void KHTMLPart::slotLoaderRequestStarted( khtml::DocLoader* dl, khtml::CachedObject *obj )
{
#if !APPLE_CHANGES
if ( obj && obj->type() == khtml::CachedObject::Image && d->m_doc && d->m_doc->docLoader() == dl ) {
KHTMLPart* p = this;
while ( p ) {
KHTMLPart* op = p;
p->d->m_totalObjectCount++;
p = p->parentPart();
if ( !p && d->m_loadedObjects <= d->m_totalObjectCount )
QTimer::singleShot( 200, op, SLOT( slotProgressUpdate() ) );
}
}
#endif
}
void KHTMLPart::slotLoaderRequestDone( khtml::DocLoader* dl, khtml::CachedObject *obj )
{
#if !APPLE_CHANGES
if ( obj && obj->type() == khtml::CachedObject::Image && d->m_doc && d->m_doc->docLoader() == dl ) {
KHTMLPart* p = this;
while ( p ) {
KHTMLPart* op = p;
p->d->m_loadedObjects++;
p = p->parentPart();
if ( !p && d->m_loadedObjects <= d->m_totalObjectCount && d->m_jobPercent >= 100 )
QTimer::singleShot( 200, op, SLOT( slotProgressUpdate() ) );
}
}
#endif
checkCompleted();
}
#if !APPLE_CHANGES
void KHTMLPart::slotProgressUpdate()
{
int percent;
if ( d->m_loadedObjects < d->m_totalObjectCount )
percent = d->m_jobPercent / 4 + ( d->m_loadedObjects*300 ) / ( 4*d->m_totalObjectCount );
else
percent = d->m_jobPercent;
if ( d->m_loadedObjects < d->m_totalObjectCount && percent >= 75 )
emit d->m_extension->infoMessage( i18n( "%1 of 1 Image loaded", "%1 of %n Images loaded", d->m_totalObjectCount ).arg( d->m_loadedObjects ) );
emit d->m_extension->loadingProgress( percent );
}
void KHTMLPart::slotJobSpeed( KIO::Job* , unsigned long speed )
{
emit d->m_extension->speedProgress( speed );
}
void KHTMLPart::slotJobPercent( KIO::Job* , unsigned long percent )
{
d->m_jobPercent = percent;
if ( !parentPart() )
QTimer::singleShot( 0, this, SLOT( slotProgressUpdate() ) );
}
#endif
void KHTMLPart::checkCompleted()
{
#if !APPLE_CHANGES
if (d->m_doc && !d->m_doc->parsing() && !d->m_focusNodeRestored)
{
if (d->m_focusNodeNumber >= 0)
d->m_doc->setFocusNode(d->m_doc->nodeWithAbsIndex(d->m_focusNodeNumber));
else
d->m_doc->setFocusNode(0);
d->m_focusNodeRestored = true;
}
#endif
ConstFrameIt it = d->m_frames.begin();
ConstFrameIt end = d->m_frames.end();
for (; it != end; ++it )
if ( !(*it).m_bCompleted )
return;
if ( d->m_bComplete || (d->m_doc && d->m_doc->parsing()) )
return;
int requests = 0;
if ( d->m_doc && d->m_doc->docLoader() )
requests = khtml::Cache::loader()->numRequests( d->m_doc->docLoader() );
if ( requests > 0 )
return;
d->m_bComplete = true;
checkEmitLoadEvent();
#if APPLE_CHANGES
if (d->m_view) {
#endif
#if !APPLE_CHANGES
if ( m_url.encodedHtmlRef().isEmpty() && d->m_view->contentsY() == 0 )
d->m_view->setContentsPos( d->m_extension->urlArgs().xOffset,
d->m_extension->urlArgs().yOffset );
#endif
d->m_view->complete();
#if APPLE_CHANGES
} #endif
if ( d->m_scheduledRedirection != noRedirectionScheduled )
{
if ( parentPart() == 0 )
d->m_redirectionTimer.start( (int)(1000 * d->m_delayRedirect), true );
emit completed( true );
}
else
{
if ( d->m_bPendingChildRedirection )
emit completed ( true );
else
emit completed();
}
#if !APPLE_CHANGES
QStringList sheets;
if (d->m_doc)
sheets = d->m_doc->availableStyleSheets();
d->m_paUseStylesheet->setItems( sheets );
d->m_paUseStylesheet->setEnabled( !sheets.isEmpty() );
if (!sheets.isEmpty())
{
d->m_paUseStylesheet->setCurrentItem(kMax(sheets.findIndex(d->m_sheetUsed), 0));
slotUseStylesheet();
}
if (!parentPart())
emit setStatusBarText(i18n("Done."));
#endif
#ifdef SPEED_DEBUG
kdDebug(6050) << "DONE: " <<d->m_parsetime.elapsed() << endl;
#endif
}
void KHTMLPart::checkEmitLoadEvent()
{
if ( d->m_bLoadEventEmitted || !d->m_doc || d->m_doc->parsing() ) return;
ConstFrameIt it = d->m_frames.begin();
ConstFrameIt end = d->m_frames.end();
for (; it != end; ++it )
if ( !(*it).m_bCompleted ) return;
if ( d->m_doc )
{
DOMString domain = d->m_doc->domain();
ConstFrameIt it = d->m_frames.begin();
ConstFrameIt end = d->m_frames.end();
for (; it != end; ++it )
{
KParts::ReadOnlyPart *p = (*it).m_part;
if ( p && p->inherits( "KHTMLPart" ))
{
KHTMLPart* htmlFrame = static_cast<KHTMLPart *>(p);
if (htmlFrame->d->m_doc)
{
kdDebug() << "KHTMLPart::checkCompleted setting frame domain to " << domain.string() << endl;
htmlFrame->d->m_doc->setDomain( domain );
}
}
}
}
d->m_bLoadEventEmitted = true;
d->m_bUnloadEventEmitted = false;
if (d->m_doc)
d->m_doc->close();
}
const KHTMLSettings *KHTMLPart::settings() const
{
return d->m_settings;
}
#ifndef KDE_NO_COMPAT
KURL KHTMLPart::baseURL() const
{
if ( !d->m_doc ) return KURL();
return d->m_doc->baseURL();
}
QString KHTMLPart::baseTarget() const
{
if ( !d->m_doc ) return QString::null;
return d->m_doc->baseTarget();
}
#endif
KURL KHTMLPart::completeURL( const QString &url )
{
if ( !d->m_doc ) return url;
#if !APPLE_CHANGES
if (d->m_decoder)
return KURL(d->m_doc->completeURL(url), d->m_decoder->codec()->mibEnum());
#endif
return KURL( d->m_doc->completeURL( url ) );
}
void KHTMLPart::scheduleRedirection( double delay, const QString &url, bool doLockHistory, bool userGesture )
{
kdDebug(6050) << "KHTMLPart::scheduleRedirection delay=" << delay << " url=" << url << endl;
if (delay < 0 || delay > INT_MAX / 1000)
return;
if ( d->m_scheduledRedirection == noRedirectionScheduled || delay < d->m_delayRedirect )
{
if (d->m_doc == 0){
d->m_scheduledRedirection = redirectionDuringLoad;
}
else
d->m_scheduledRedirection = redirectionScheduled;
d->m_delayRedirect = delay;
d->m_redirectURL = url;
d->m_redirectLockHistory = doLockHistory;
d->m_redirectUserGesture = userGesture;
if ( d->m_bComplete ) {
d->m_redirectionTimer.stop();
d->m_redirectionTimer.start( (int)(1000 * d->m_delayRedirect), true );
}
}
}
void KHTMLPart::scheduleHistoryNavigation( int steps )
{
d->m_scheduledRedirection = historyNavigationScheduled;
d->m_delayRedirect = 0;
d->m_redirectURL = QString::null;
d->m_scheduledHistoryNavigationSteps = steps;
if ( d->m_bComplete ) {
d->m_redirectionTimer.stop();
d->m_redirectionTimer.start( (int)(1000 * d->m_delayRedirect), true );
}
}
void KHTMLPart::cancelRedirection(bool cancelWithLoadInProgress)
{
if (d) {
d->m_cancelWithLoadInProgress = cancelWithLoadInProgress;
d->m_scheduledRedirection = noRedirectionScheduled;
d->m_redirectionTimer.stop();
}
}
void KHTMLPart::slotRedirect()
{
if (d->m_scheduledRedirection == historyNavigationScheduled) {
d->m_scheduledRedirection = noRedirectionScheduled;
if (d->m_scheduledHistoryNavigationSteps == 0) openURL( url() ); else {
if (d->m_extension) {
BrowserInterface *interface = d->m_extension->browserInterface();
if (interface)
interface->callMethod( "goHistory(int)", d->m_scheduledHistoryNavigationSteps );
}
}
return;
}
QString u = d->m_redirectURL;
d->m_scheduledRedirection = noRedirectionScheduled;
d->m_delayRedirect = 0;
d->m_redirectURL = QString::null;
if ( u.find( QString::fromLatin1( "javascript:" ), 0, false ) == 0 )
{
QString script = KURL::decode_string( u.right( u.length() - 11 ) );
QVariant res = executeScript( script, d->m_redirectUserGesture );
if ( res.type() == QVariant::String ) {
begin( url() );
write( res.asString() );
end();
}
return;
}
KParts::URLArgs args;
if ( urlcmp( u, m_url.url(), true, false ) )
args.reload = true;
args.setLockHistory( d->m_redirectLockHistory );
urlSelected( u, 0, 0, "_self", args );
}
void KHTMLPart::slotRedirection(KIO::Job*, const KURL& url)
{
emit d->m_extension->setLocationBarURL( url.prettyURL() );
d->m_workingURL = url;
}
#if !APPLE_CHANGES
bool KHTMLPart::setEncoding( const QString &name, bool override )
{
d->m_encoding = name;
d->m_haveEncoding = override;
if( !m_url.isEmpty() ) {
closeURL();
KURL url = m_url;
m_url = 0;
d->m_restored = true;
openURL(url);
d->m_restored = false;
}
return true;
}
#endif
QString KHTMLPart::encoding() const
{
if(d->m_haveEncoding && !d->m_encoding.isEmpty())
return d->m_encoding;
if(d->m_decoder && d->m_decoder->encoding())
return QString(d->m_decoder->encoding());
return(settings()->encoding());
}
void KHTMLPart::setUserStyleSheet(const KURL &url)
{
if ( d->m_doc && d->m_doc->docLoader() )
(void) new khtml::PartStyleSheetLoader(this, url.url(), d->m_doc->docLoader());
}
void KHTMLPart::setUserStyleSheet(const QString &styleSheet)
{
if ( d->m_doc )
d->m_doc->setUserStyleSheet( styleSheet );
}
bool KHTMLPart::gotoAnchor( const QString &name )
{
if (!d->m_doc)
return false;
NodeImpl *n = d->m_doc->getElementById(name);
if (!n) {
HTMLCollectionImpl *anchors =
new HTMLCollectionImpl( d->m_doc, HTMLCollectionImpl::DOC_ANCHORS);
anchors->ref();
n = anchors->namedItem(name, !d->m_doc->inCompatMode());
anchors->deref();
}
d->m_doc->setCSSTarget(n);
if(!n) {
kdDebug(6050) << "KHTMLPart::gotoAnchor node '" << name << "' not found" << endl;
return false;
}
if ( d->m_doc ) {
d->m_doc->updateRendering();
if ( d->m_view && d->m_doc->renderer() && d->m_doc->renderer()->needsLayout() ) {
d->m_view->layout();
}
}
int x = 0, y = 0;
HTMLElementImpl *a = static_cast<HTMLElementImpl *>(n);
a->getUpperLeftCorner(x, y);
#if APPLE_CHANGES
d->m_view->setContentsPosRecursive(x, y);
#else
d->m_view->setContentsPos(x-50, y-50);
#endif
return true;
}
void KHTMLPart::setStandardFont( const QString &name )
{
d->m_settings->setStdFontName(name);
}
void KHTMLPart::setFixedFont( const QString &name )
{
d->m_settings->setFixedFontName(name);
}
#if !APPLE_CHANGES
void KHTMLPart::setURLCursor( const QCursor &c )
{
d->m_linkCursor = c;
}
#endif
QCursor KHTMLPart::urlCursor() const
{
#if APPLE_CHANGES
return KCursor::handCursor();
#else
return d->m_linkCursor;
#endif
}
bool KHTMLPart::onlyLocalReferences() const
{
return d->m_onlyLocalReferences;
}
void KHTMLPart::setOnlyLocalReferences(bool enable)
{
d->m_onlyLocalReferences = enable;
}
void KHTMLPart::setEditMode(TristateFlag flag)
{
d->m_inEditMode = flag;
}
TristateFlag KHTMLPart::editMode() const
{
if (d->m_inEditMode != FlagNone)
return d->m_inEditMode == FlagEnabled ? FlagEnabled : FlagDisabled;
KHTMLPart *part = parentPart();
while (part) {
if (part->d->m_inEditMode != FlagNone)
return part->d->m_inEditMode == FlagEnabled ? FlagEnabled : FlagDisabled;
part = part->parentPart();
}
return FlagNone;
}
bool KHTMLPart::inEditMode() const
{
return editMode() == FlagEnabled;
}
void KHTMLPart::findTextBegin(NodeImpl *startNode, int startPos)
{
d->m_findPos = startPos;
d->m_findNode = startNode;
}
bool KHTMLPart::findTextNext( const QString &str, bool forward, bool caseSensitive, bool isRegExp )
{
if ( !d->m_doc )
return false;
if(!d->m_findNode) {
if (d->m_doc->isHTMLDocument())
d->m_findNode = static_cast<HTMLDocumentImpl*>(d->m_doc)->body();
else
d->m_findNode = d->m_doc;
}
if ( !d->m_findNode )
{
kdDebug() << "KHTMLPart::findTextNext no findNode -> return false" << endl;
return false;
}
if ( d->m_findNode->id() == ID_FRAMESET )
{
kdDebug() << "KHTMLPart::findTextNext FRAMESET -> return false" << endl;
return false;
}
while(1)
{
if( (d->m_findNode->nodeType() == Node::TEXT_NODE || d->m_findNode->nodeType() == Node::CDATA_SECTION_NODE) && d->m_findNode->renderer() )
{
DOMString nodeText = d->m_findNode->nodeValue();
DOMStringImpl *t = nodeText.implementation();
QConstString s(t->s, t->l);
int matchLen = 0;
#if !APPLE_CHANGES
if ( isRegExp ) {
QRegExp matcher( str );
matcher.setCaseSensitive( caseSensitive );
d->m_findPos = matcher.search(s.string(), d->m_findPos+1);
if ( d->m_findPos != -1 )
matchLen = matcher.matchedLength();
}
else {
d->m_findPos = s.string().find(str, d->m_findPos+1, caseSensitive);
matchLen = str.length();
}
#else
if (forward) {
d->m_findPos = s.string().find(str, d->m_findPos+1, caseSensitive);
} else {
if (d->m_findPos == -1) {
d->m_findPos = s.string().findRev(str, -1, caseSensitive);
} else if (d->m_findPos != 0) {
d->m_findPos = s.string().findRev(str, d->m_findPos-1, caseSensitive);
} else {
d->m_findPos = -1;
}
}
matchLen = str.length();
#endif
if(d->m_findPos != -1)
{
#if !APPLE_CHANGES
int x = 0, y = 0;
static_cast<khtml::RenderText *>(d->m_findNode->renderer())
->posOfChar(d->m_findPos, x, y);
d->m_view->setContentsPos(x-50, y-50);
#endif
d->m_selectionStart = d->m_findNode;
d->m_startOffset = d->m_findPos;
d->m_selectionEnd = d->m_findNode;
d->m_endOffset = d->m_findPos + matchLen;
d->m_startBeforeEnd = true;
d->m_doc->setSelection( d->m_selectionStart.handle(), d->m_startOffset,
d->m_selectionEnd.handle(), d->m_endOffset );
emitSelectionChanged();
return true;
}
}
d->m_findPos = -1;
NodeImpl *next;
if ( forward )
{
next = d->m_findNode->firstChild();
if(!next) next = d->m_findNode->nextSibling();
while(d->m_findNode && !next) {
d->m_findNode = d->m_findNode->parentNode();
if( d->m_findNode ) {
next = d->m_findNode->nextSibling();
}
}
}
else
{
next = d->m_findNode->lastChild();
if (!next ) next = d->m_findNode->previousSibling();
while ( d->m_findNode && !next )
{
d->m_findNode = d->m_findNode->parentNode();
if( d->m_findNode )
{
next = d->m_findNode->previousSibling();
}
}
}
d->m_findNode = next;
if(!d->m_findNode) return false;
}
}
QString KHTMLPart::text(const DOM::Range &r) const
{
if (r.isNull())
return QString();
bool hasNewLine = true;
bool addedSpace = true;
bool needSpace = false;
QString text;
DOM::Node startNode = r.startContainer();
DOM::Node endNode = r.endContainer();
int startOffset = r.startOffset();
int endOffset = r.endOffset();
if (!startNode.isNull() && startNode.nodeType() == Node::ELEMENT_NODE) {
if (startOffset >= 0 && startOffset < (int)startNode.childNodes().length()) {
startNode = startNode.childNodes().item(r.startOffset());
startOffset = -1;
}
}
if (!endNode.isNull() && endNode.nodeType() == Node::ELEMENT_NODE) {
if (endOffset > 0 && endOffset <= (int)endNode.childNodes().length()) {
endNode = endNode.childNodes().item(endOffset - 1);
endOffset = -1;
}
}
DOM::Node n = startNode;
while(!n.isNull()) {
if(n.nodeType() == DOM::Node::TEXT_NODE) {
if (hasNewLine) {
addedSpace = true;
hasNewLine = false;
}
QString str = n.nodeValue().string();
int start = (n == startNode) ? startOffset : -1;
int end = (n == endNode) ? endOffset : -1;
RenderObject* renderer = n.handle()->renderer();
if (renderer && renderer->isText()) {
if (renderer->style()->whiteSpace() == khtml::PRE) {
if (needSpace && !addedSpace)
text += ' ';
int runStart = (start == -1) ? 0 : start;
int runEnd = (end == -1) ? str.length() : end;
text += str.mid(runStart, runEnd-runStart);
needSpace = false;
addedSpace = str[runEnd-1].direction() == QChar::DirWS;
}
else {
RenderText* textObj = static_cast<RenderText*>(n.handle()->renderer());
InlineTextBoxArray runs = textObj->inlineTextBoxes();
if (runs.count() == 0 && str.length() > 0) {
needSpace = true;
}
else {
for (unsigned i = 0; i < runs.count(); i++) {
int runStart = (start == -1) ? runs[i]->m_start : start;
int runEnd = (end == -1) ? runs[i]->m_start + runs[i]->m_len : end;
runEnd = QMIN(runEnd, runs[i]->m_start + runs[i]->m_len);
if (runStart >= runs[i]->m_start &&
runStart < runs[i]->m_start + runs[i]->m_len) {
if (i == 0 && runs[0]->m_start == runStart && runStart > 0)
needSpace = true; if (needSpace && !addedSpace)
text += ' ';
QString runText = str.mid(runStart, runEnd - runStart);
runText.replace('\n', ' ');
text += runText;
int nextRunStart = (i+1 < runs.count()) ? runs[i+1]->m_start : str.length();
needSpace = nextRunStart > runEnd; addedSpace = str[runEnd-1].direction() == QChar::DirWS;
start = -1;
}
if (end != -1 && runEnd >= end)
break;
}
}
}
}
}
else {
unsigned short id = n.elementId();
switch(id) {
case ID_BR:
text += "\n";
hasNewLine = true;
break;
case ID_TD:
case ID_TH:
case ID_HR:
case ID_OL:
case ID_UL:
case ID_LI:
case ID_DD:
case ID_DL:
case ID_DT:
case ID_PRE:
case ID_BLOCKQUOTE:
case ID_DIV:
if (!hasNewLine)
text += "\n";
hasNewLine = true;
break;
case ID_P:
case ID_TR:
case ID_H1:
case ID_H2:
case ID_H3:
case ID_H4:
case ID_H5:
case ID_H6:
if (!hasNewLine)
text += "\n";
text += "\n";
hasNewLine = true;
break;
}
}
if(n == endNode) break;
DOM::Node next = n.firstChild();
if(next.isNull()) next = n.nextSibling();
while( next.isNull() && !n.parentNode().isNull() ) {
n = n.parentNode();
if(n == endNode) break;
next = n.nextSibling();
unsigned short id = n.elementId();
switch(id) {
case ID_TD:
case ID_TH:
case ID_HR:
case ID_OL:
case ID_UL:
case ID_LI:
case ID_DD:
case ID_DL:
case ID_DT:
case ID_PRE:
case ID_BLOCKQUOTE:
case ID_DIV:
if (!hasNewLine)
text += "\n";
hasNewLine = true;
break;
case ID_P:
case ID_TR:
case ID_H1:
case ID_H2:
case ID_H3:
case ID_H4:
case ID_H5:
case ID_H6:
if (!hasNewLine)
text += "\n";
hasNewLine = true;
break;
}
}
n = next;
}
int start = 0;
int end = text.length();
while ((start < end) && (text[start] == '\n'))
start++;
while ((start < (end-1)) && (text[end-1] == '\n') && (text[end-2] == '\n'))
end--;
return text.mid(start, end-start);
}
QString KHTMLPart::selectedText() const
{
return text(selection());
}
bool KHTMLPart::hasSelection() const
{
return ( !d->m_selectionStart.isNull() &&
!d->m_selectionEnd.isNull() );
}
DOM::Range KHTMLPart::selection() const
{
DOM::Range r = document().createRange();
if (hasSelection()) {
r.setStart( d->m_selectionStart, d->m_startOffset );
r.setEnd( d->m_selectionEnd, d->m_endOffset );
}
return r;
}
void KHTMLPart::setSelection( const DOM::Range &r )
{
d->m_selectionStart = r.startContainer();
d->m_startOffset = r.startOffset();
d->m_selectionEnd = r.endContainer();
d->m_endOffset = r.endOffset();
d->m_doc->setSelection(d->m_selectionStart.handle(),d->m_startOffset,
d->m_selectionEnd.handle(),d->m_endOffset);
}
void KHTMLPart::slotClearSelection()
{
d->m_selectionStart = 0;
d->m_startOffset = 0;
d->m_selectionEnd = 0;
d->m_endOffset = 0;
if ( d->m_doc ) d->m_doc->clearSelection();
emitSelectionChanged();
}
#if !APPLE_CHANGES
void KHTMLPart::overURL( const QString &url, const QString &target, bool shiftPressed )
{
if ( !d->m_kjsStatusBarText.isEmpty() && !shiftPressed ) {
emit onURL( url );
emit setStatusBarText( d->m_kjsStatusBarText );
d->m_kjsStatusBarText = QString::null;
return;
}
emit onURL( url );
if ( url.isEmpty() )
{
emit setStatusBarText(completeURL(url).htmlURL());
return;
}
if (url.find( QString::fromLatin1( "javascript:" ),0, false ) != -1 )
{
emit setStatusBarText( KURL::decode_string( url.mid( url.find( "javascript:", 0, false ) ) ) );
return;
}
KURL u = completeURL(url);
if ( url.isEmpty() )
u.setFileName( url );
QString com;
KMimeType::Ptr typ = KMimeType::findByURL( u );
if ( typ )
com = typ->comment( u, false );
if ( u.isMalformed() )
{
emit setStatusBarText(u.htmlURL());
return;
}
if ( u.isLocalFile() )
{
QCString path = QFile::encodeName( u.path() );
struct stat buff;
bool ok = !stat( path.data(), &buff );
struct stat lbuff;
if (ok) ok = !lstat( path.data(), &lbuff );
QString text = u.htmlURL();
QString text2 = text;
if (ok && S_ISLNK( lbuff.st_mode ) )
{
QString tmp;
if ( com.isNull() )
tmp = i18n( "Symbolic Link");
else
tmp = i18n("%1 (Link)").arg(com);
char buff_two[1024];
text += " -> ";
int n = readlink ( path.data(), buff_two, 1022);
if (n == -1)
{
text2 += " ";
text2 += tmp;
emit setStatusBarText(text2);
return;
}
buff_two[n] = 0;
text += buff_two;
text += " ";
text += tmp;
}
else if ( ok && S_ISREG( buff.st_mode ) )
{
if (buff.st_size < 1024)
text = i18n("%2 (%1 bytes)").arg((long) buff.st_size).arg(text2); else
{
float d = (float) buff.st_size/1024.0;
text = i18n("%1 (%2 K)").arg(text2).arg(KGlobal::locale()->formatNumber(d, 2)); }
text += " ";
text += com;
}
else if ( ok && S_ISDIR( buff.st_mode ) )
{
text += " ";
text += com;
}
else
{
text += " ";
text += com;
}
emit setStatusBarText(text);
}
else
{
QString extra;
if (target == QString::fromLatin1("_blank"))
{
extra = i18n(" (In new window)");
}
else if (!target.isEmpty() &&
(target != QString::fromLatin1("_top")) &&
(target != QString::fromLatin1("_self")) &&
(target != QString::fromLatin1("_parent")))
{
extra = i18n(" (In other frame)");
}
if (u.protocol() == QString::fromLatin1("mailto")) {
QString mailtoMsg;
mailtoMsg += i18n("Email to: ") + KURL::decode_string(u.path());
QStringList queries = QStringList::split('&', u.query().mid(1));
for (QStringList::Iterator it = queries.begin(); it != queries.end(); ++it)
if ((*it).startsWith(QString::fromLatin1("subject=")))
mailtoMsg += i18n(" - Subject: ") + KURL::decode_string((*it).mid(8));
else if ((*it).startsWith(QString::fromLatin1("cc=")))
mailtoMsg += i18n(" - CC: ") + KURL::decode_string((*it).mid(3));
else if ((*it).startsWith(QString::fromLatin1("bcc=")))
mailtoMsg += i18n(" - BCC: ") + KURL::decode_string((*it).mid(4));
mailtoMsg.replace(QRegExp("&"), QString("&"));
mailtoMsg.replace(QRegExp("<"), QString("<"));
mailtoMsg.replace(QRegExp(">"), QString(">"));
mailtoMsg.replace(QRegExp("([\n\r\t]|[ ]{10})"), "");
emit setStatusBarText(mailtoMsg);
return;
}
#if 0
else if (u.protocol() == QString::fromLatin1("http")) {
DOM::Node hrefNode = nodeUnderMouse().parentNode();
while (hrefNode.nodeName().string() != QString::fromLatin1("A") && !hrefNode.isNull())
hrefNode = hrefNode.parentNode();
if (!hrefNode.isNull()) {
DOM::Node hreflangNode = hrefNode.attributes().getNamedItem("HREFLANG");
if (!hreflangNode.isNull()) {
QString countryCode = hreflangNode.nodeValue().string().lower();
if (countryCode == QString::fromLatin1("en"))
countryCode = QString::fromLatin1("gb");
QString flagImg = QString::fromLatin1("<img src=%1>").arg(
locate("locale", QString::fromLatin1("l10n/")
+ countryCode
+ QString::fromLatin1("/flag.png")));
emit setStatusBarText(flagImg + u.prettyURL() + extra);
}
}
}
#endif
emit setStatusBarText(u.htmlURL() + extra);
}
}
#endif // APPLE_CHANGES
void KHTMLPart::urlSelected( const QString &url, int button, int state, const QString &_target,
KParts::URLArgs args )
{
bool hasTarget = false;
QString target = _target;
if ( target.isEmpty() && d->m_doc )
target = d->m_doc->baseTarget();
if ( !target.isEmpty() )
hasTarget = true;
if ( url.find( QString::fromLatin1( "javascript:" ), 0, false ) == 0 )
{
executeScript( KURL::decode_string( url.right( url.length() - 11) ), true );
return;
}
KURL cURL = completeURL(url);
#if !APPLE_CHANGES
if ( url.isEmpty() )
cURL.setFileName( url );
#endif
if ( !cURL.isValid() )
return;
#if !APPLE_CHANGES
if ( button == LeftButton && ( state & ShiftButton ) )
{
KIO::MetaData metaData;
metaData["referrer"] = d->m_referrer;
KHTMLPopupGUIClient::saveURL( d->m_view, i18n( "Save As..." ), cURL, metaData );
return;
}
if (!checkLinkSecurity(cURL,
i18n( "<qt>The link <B>%1</B><BR>leads from this untrusted page to your local filesystem.<BR>Do you want to follow the link?" ),
i18n( "Follow" )))
return;
#endif
args.frameName = target;
if ( d->m_bHTTPRefresh )
{
d->m_bHTTPRefresh = false;
args.metaData()["cache"] = "refresh";
}
#if !APPLE_CHANGES
args.metaData().insert("main_frame_request",
parentPart() == 0 ? "TRUE":"FALSE");
args.metaData().insert("ssl_was_in_use", d->m_ssl_in_use ? "TRUE":"FALSE");
args.metaData().insert("ssl_activate_warnings", "TRUE");
#endif
#if APPLE_CHANGES
args.metaData()["referrer"] = d->m_referrer;
KWQ(this)->urlSelected(cURL, button, state, args);
#else
if ( hasTarget )
{
khtml::ChildFrame *frame = recursiveFrameRequest( cURL, args, false );
if ( frame )
{
args.metaData()["referrer"] = d->m_referrer;
requestObject( frame, cURL, args );
return;
}
}
if ( !d->m_bComplete && !hasTarget )
closeURL();
if (!d->m_referrer.isEmpty())
args.metaData()["referrer"] = d->m_referrer;
if ( button == MidButton && (state & ShiftButton) )
{
KParts::WindowArgs winArgs;
winArgs.lowerWindow = true;
KParts::ReadOnlyPart *newPart = 0;
emit d->m_extension->createNewWindow( cURL, args, winArgs, newPart );
return;
}
emit d->m_extension->openURLRequest( cURL, args );
#endif // APPLE_CHANGES
}
#if !APPLE_CHANGES
void KHTMLPart::slotViewDocumentSource()
{
KURL url(m_url);
if (!(url.isLocalFile()) && KHTMLPageCache::self()->isValid(d->m_cacheId))
{
KTempFile sourceFile(QString::null, QString::fromLatin1(".html"));
if (sourceFile.status() == 0)
{
KHTMLPageCache::self()->saveData(d->m_cacheId, sourceFile.dataStream());
url = KURL();
url.setPath(sourceFile.name());
}
}
(void) KRun::runURL( url, QString::fromLatin1("text/plain") );
}
void KHTMLPart::slotViewFrameSource()
{
KParts::ReadOnlyPart *frame = currentFrame();
if ( !frame )
return;
KURL url = frame->url();
if (!(url.isLocalFile()) && frame->inherits("KHTMLPart"))
{
long cacheId = static_cast<KHTMLPart *>(frame)->d->m_cacheId;
if (KHTMLPageCache::self()->isValid(cacheId))
{
KTempFile sourceFile(QString::null, QString::fromLatin1(".html"));
if (sourceFile.status() == 0)
{
KHTMLPageCache::self()->saveData(cacheId, sourceFile.dataStream());
url = KURL();
url.setPath(sourceFile.name());
}
}
}
(void) KRun::runURL( url, QString::fromLatin1("text/plain") );
}
KURL KHTMLPart::backgroundURL() const
{
if (!d->m_doc || !d->m_doc->isHTMLDocument())
return KURL();
QString relURL = static_cast<HTMLDocumentImpl*>(d->m_doc)->body()->getAttribute( ATTR_BACKGROUND ).string();
return KURL( m_url, relURL );
}
void KHTMLPart::slotSaveBackground()
{
KIO::MetaData metaData;
metaData["referrer"] = d->m_referrer;
KHTMLPopupGUIClient::saveURL( d->m_view, i18n("Save background image as"), backgroundURL(), metaData );
}
void KHTMLPart::slotSaveDocument()
{
KURL srcURL( m_url );
if ( srcURL.fileName(false).isEmpty() )
srcURL.setFileName( "index.html" );
KIO::MetaData metaData;
KHTMLPopupGUIClient::saveURL( d->m_view, i18n( "Save As" ), srcURL, metaData, i18n("*.html *.htm|HTML files"), d->m_cacheId );
}
void KHTMLPart::slotSecurity()
{
KSSLInfoDlg *kid = new KSSLInfoDlg(d->m_ssl_in_use, widget(), "kssl_info_dlg", true );
if (d->m_bSecurityInQuestion)
kid->setSecurityInQuestion(true);
if (d->m_ssl_in_use) {
KSSLCertificate *x = KSSLCertificate::fromString(d->m_ssl_peer_certificate.local8Bit());
if (x) {
QStringList cl = QStringList::split(QString("\n"), d->m_ssl_peer_chain);
QPtrList<KSSLCertificate> ncl;
ncl.setAutoDelete(true);
for (QStringList::Iterator it = cl.begin(); it != cl.end(); ++it) {
KSSLCertificate *y = KSSLCertificate::fromString((*it).local8Bit());
if (y) ncl.append(y);
}
if (ncl.count() > 0)
x->chain().setChain(ncl);
kid->setup(x,
d->m_ssl_peer_ip,
m_url.url(),
d->m_ssl_cipher,
d->m_ssl_cipher_desc,
d->m_ssl_cipher_version,
d->m_ssl_cipher_used_bits.toInt(),
d->m_ssl_cipher_bits.toInt(),
(KSSLCertificate::KSSLValidation) d->m_ssl_cert_state.toInt()
);
kid->exec();
delete x;
} else kid->exec();
} else kid->exec();
}
void KHTMLPart::slotSaveFrame()
{
if ( !d->m_activeFrame )
return;
KURL srcURL( static_cast<KParts::ReadOnlyPart *>( d->m_activeFrame )->url() );
if ( srcURL.fileName(false).isEmpty() )
srcURL.setFileName( "index.html" );
KIO::MetaData metaData;
KHTMLPopupGUIClient::saveURL( d->m_view, i18n( "Save As" ), srcURL, metaData, i18n("*.html *.htm|HTML files") );
}
void KHTMLPart::slotSetEncoding()
{
if(d->m_paSetEncoding->currentItem() == 0)
setEncoding(QString::null, false);
else {
QString enc = KGlobal::charsets()->encodingForName(d->m_paSetEncoding->currentText());
setEncoding(enc, true);
}
}
void KHTMLPart::slotUseStylesheet()
{
if (d->m_doc && d->m_paUseStylesheet->currentText() != d->m_sheetUsed) {
d->m_sheetUsed = d->m_paUseStylesheet->currentText();
d->m_doc->updateStyleSelector();
}
}
void KHTMLPart::updateActions()
{
bool frames = false;
QValueList<khtml::ChildFrame>::ConstIterator it = d->m_frames.begin();
QValueList<khtml::ChildFrame>::ConstIterator end = d->m_frames.end();
for (; it != end; ++it )
if ( (*it).m_type == khtml::ChildFrame::Frame )
{
frames = true;
break;
}
d->m_paViewFrame->setEnabled( frames );
d->m_paSaveFrame->setEnabled( frames );
if ( frames )
d->m_paFind->setText( i18n( "&Find in Frame..." ) );
else
d->m_paFind->setText( i18n( "&Find..." ) );
KParts::Part *frame = 0;
if ( frames )
frame = currentFrame();
bool enableFindAndSelectAll = true;
if ( frame )
enableFindAndSelectAll = frame->inherits( "KHTMLPart" );
d->m_paFind->setEnabled( enableFindAndSelectAll );
d->m_paSelectAll->setEnabled( enableFindAndSelectAll );
bool enablePrintFrame = false;
if ( frame )
{
QObject *ext = KParts::BrowserExtension::childObject( frame );
if ( ext )
enablePrintFrame = ext->metaObject()->slotNames().contains( "print()" );
}
d->m_paPrintFrame->setEnabled( enablePrintFrame );
QString bgURL;
if ( d->m_doc && d->m_doc->isHTMLDocument() && static_cast<HTMLDocumentImpl*>(d->m_doc)->body() && !d->m_bClearing )
bgURL = static_cast<HTMLDocumentImpl*>(d->m_doc)->body()->getAttribute( ATTR_BACKGROUND ).string();
d->m_paSaveBackground->setEnabled( !bgURL.isEmpty() );
}
#endif
bool KHTMLPart::requestFrame( khtml::RenderPart *frame, const QString &url, const QString &frameName,
const QStringList ¶ms, bool isIFrame )
{
FrameIt it = d->m_frames.find( frameName );
if ( it == d->m_frames.end() )
{
khtml::ChildFrame child;
child.m_name = frameName;
it = d->m_frames.append( child );
}
(*it).m_type = isIFrame ? khtml::ChildFrame::IFrame : khtml::ChildFrame::Frame;
(*it).m_frame = frame;
(*it).m_params = params;
if ( url.find( QString::fromLatin1( "javascript:" ), 0, false ) == 0 )
{
if (!processObjectRequest(&(*it), "about:blank", "text/html" ))
return false;
KHTMLPart *newPart = static_cast<KHTMLPart *>(&*(*it).m_part);
newPart->replaceContentsWithScriptResult( url );
return true;
}
return requestObject( &(*it), completeURL( url ));
}
QString KHTMLPart::requestFrameName()
{
#if APPLE_CHANGES
return KWQ(this)->generateFrameName();
#else
return QString::fromLatin1("<!--frame %1-->").arg(d->m_frameNameId++);
#endif
}
bool KHTMLPart::requestObject( khtml::RenderPart *frame, const QString &url, const QString &serviceType,
const QStringList ¶ms )
{
khtml::ChildFrame child;
QValueList<khtml::ChildFrame>::Iterator it = d->m_objects.append( child );
(*it).m_frame = frame;
(*it).m_type = khtml::ChildFrame::Object;
(*it).m_params = params;
KURL completedURL;
if (!url.isEmpty())
completedURL = completeURL(url);
KParts::URLArgs args;
args.serviceType = serviceType;
return requestObject( &(*it), completedURL, args );
}
bool KHTMLPart::requestObject( khtml::ChildFrame *child, const KURL &url, const KParts::URLArgs &_args )
{
#if !APPLE_CHANGES
if (!checkLinkSecurity(url))
return false;
#endif
if ( child->m_bPreloaded )
{
if ( child->m_frame && child->m_part )
child->m_frame->setWidget( child->m_part->widget() );
child->m_bPreloaded = false;
return true;
}
KParts::URLArgs args( _args );
#if !APPLE_CHANGES
if ( child->m_run )
child->m_run->abort();
#endif
if ( child->m_part && !args.reload && urlcmp( child->m_part->url().url(), url.url(), true, true ) )
args.serviceType = child->m_serviceType;
child->m_args = args;
child->m_args.reload = (d->m_cachePolicy == KIO::CC_Reload) || (d->m_cachePolicy == KIO::CC_Refresh);
child->m_serviceName = QString::null;
if (!d->m_referrer.isEmpty() && !child->m_args.metaData().contains( "referrer" ))
child->m_args.metaData()["referrer"] = d->m_referrer;
#if !APPLE_CHANGES
child->m_args.metaData().insert("main_frame_request",
parentPart() == 0 ? "TRUE":"FALSE");
child->m_args.metaData().insert("ssl_was_in_use",
d->m_ssl_in_use ? "TRUE":"FALSE");
child->m_args.metaData().insert("ssl_activate_warnings", "TRUE");
#endif
if ((url.isEmpty() || url.url() == "about:blank") && args.serviceType.isEmpty())
args.serviceType = QString::fromLatin1( "text/html" );
#if APPLE_CHANGES
return processObjectRequest( child, url, args.serviceType );
#else
if ( args.serviceType.isEmpty() ) {
child->m_run = new KHTMLRun( this, child, url, child->m_args,
child->m_type != khtml::ChildFrame::Frame );
return false;
} else {
return processObjectRequest( child, url, args.serviceType );
}
#endif
}
bool KHTMLPart::processObjectRequest( khtml::ChildFrame *child, const KURL &_url, const QString &mimetype )
{
KURL url( _url );
if ( d->m_onlyLocalReferences || ( url.isEmpty() && mimetype.isEmpty() ) )
{
checkEmitLoadEvent();
child->m_bCompleted = true;
return true;
}
if (child->m_bNotify)
{
child->m_bNotify = false;
if ( !child->m_args.lockHistory() )
emit d->m_extension->openURLNotify();
}
#if APPLE_CHANGES
if ( child->m_part )
{
KHTMLPart *part = dynamic_cast<KHTMLPart *>(&*child->m_part);
if (part)
part->openURL(url);
}
else
{
KParts::ReadOnlyPart *part = KWQ(this)->createPart(*child, url, mimetype);
#else
if ( !child->m_services.contains( mimetype ) )
{
KParts::ReadOnlyPart *part = createPart( d->m_view->viewport(), child->m_name.ascii(), this, child->m_name.ascii(), mimetype, child->m_serviceName, child->m_services, child->m_params );
#endif
if ( !part )
{
if ( child->m_frame )
if (child->m_frame->partLoadingErrorNotify( child, url, mimetype ))
return true;
checkEmitLoadEvent();
return false;
}
if ( child->m_part )
{
#if !APPLE_CHANGES
partManager()->removePart( (KParts::ReadOnlyPart *)child->m_part );
#endif
child->m_part->deref();
}
child->m_serviceType = mimetype;
if ( child->m_frame )
child->m_frame->setWidget( part->widget() );
#if !APPLE_CHANGES
if ( child->m_type != khtml::ChildFrame::Object )
partManager()->addPart( part, false );
#endif
child->m_part = part;
assert( ((void*) child->m_part) != 0);
if ( child->m_type != khtml::ChildFrame::Object )
{
connect( part, SIGNAL( started( KIO::Job *) ),
this, SLOT( slotChildStarted( KIO::Job *) ) );
connect( part, SIGNAL( completed() ),
this, SLOT( slotChildCompleted() ) );
connect( part, SIGNAL( completed(bool) ),
this, SLOT( slotChildCompleted(bool) ) );
connect( part, SIGNAL( setStatusBarText( const QString & ) ),
this, SIGNAL( setStatusBarText( const QString & ) ) );
connect( this, SIGNAL( completed() ),
part, SLOT( slotParentCompleted() ) );
connect( this, SIGNAL( completed(bool) ),
part, SLOT( slotParentCompleted() ) );
}
#if APPLE_CHANGES
}
#else
child->m_extension = KParts::BrowserExtension::childObject( part );
if ( child->m_extension )
{
connect( child->m_extension, SIGNAL( openURLNotify() ),
d->m_extension, SIGNAL( openURLNotify() ) );
connect( child->m_extension, SIGNAL( openURLRequestDelayed( const KURL &, const KParts::URLArgs & ) ),
this, SLOT( slotChildURLRequest( const KURL &, const KParts::URLArgs & ) ) );
connect( child->m_extension, SIGNAL( createNewWindow( const KURL &, const KParts::URLArgs & ) ),
d->m_extension, SIGNAL( createNewWindow( const KURL &, const KParts::URLArgs & ) ) );
connect( child->m_extension, SIGNAL( createNewWindow( const KURL &, const KParts::URLArgs &, const KParts::WindowArgs &, KParts::ReadOnlyPart *& ) ),
d->m_extension, SIGNAL( createNewWindow( const KURL &, const KParts::URLArgs & , const KParts::WindowArgs &, KParts::ReadOnlyPart *&) ) );
connect( child->m_extension, SIGNAL( popupMenu( const QPoint &, const KFileItemList & ) ),
d->m_extension, SIGNAL( popupMenu( const QPoint &, const KFileItemList & ) ) );
connect( child->m_extension, SIGNAL( popupMenu( KXMLGUIClient *, const QPoint &, const KFileItemList & ) ),
d->m_extension, SIGNAL( popupMenu( KXMLGUIClient *, const QPoint &, const KFileItemList & ) ) );
connect( child->m_extension, SIGNAL( popupMenu( const QPoint &, const KURL &, const QString &, mode_t ) ),
d->m_extension, SIGNAL( popupMenu( const QPoint &, const KURL &, const QString &, mode_t ) ) );
connect( child->m_extension, SIGNAL( popupMenu( KXMLGUIClient *, const QPoint &, const KURL &, const QString &, mode_t ) ),
d->m_extension, SIGNAL( popupMenu( KXMLGUIClient *, const QPoint &, const KURL &, const QString &, mode_t ) ) );
connect( child->m_extension, SIGNAL( infoMessage( const QString & ) ),
d->m_extension, SIGNAL( infoMessage( const QString & ) ) );
child->m_extension->setBrowserInterface( d->m_extension->browserInterface() );
}
}
#endif
checkEmitLoadEvent();
if ( !child->m_part )
return false;
if ( child->m_bPreloaded )
{
if ( child->m_frame && child->m_part )
child->m_frame->setWidget( child->m_part->widget() );
child->m_bPreloaded = false;
return true;
}
child->m_args.reload = (d->m_cachePolicy == KIO::CC_Reload) || (d->m_cachePolicy == KIO::CC_Refresh);
child->m_args.serviceType = mimetype;
child->m_bCompleted = false;
if ( child->m_extension )
child->m_extension->setURLArgs( child->m_args );
#if APPLE_CHANGES
if (url.isEmpty() || url.url() == "about:blank") {
ReadOnlyPart *readOnlyPart = child->m_part;
KHTMLPart *part = dynamic_cast<KHTMLPart *>(readOnlyPart);
if (part) {
part->completed();
}
}
#else
if(url.protocol() == "javascript" || url.url() == "about:blank") {
if (!child->m_part->inherits("KHTMLPart"))
return false;
KHTMLPart* p = static_cast<KHTMLPart*>(static_cast<KParts::ReadOnlyPart *>(child->m_part));
p->begin();
if (d->m_doc && p->d->m_doc)
p->d->m_doc->setBaseURL(d->m_doc->baseURL());
if (!url.url().startsWith("about:")) {
p->write(url.path());
} else {
p->m_url = url;
}
p->end();
return true;
}
else if ( !url.isEmpty() )
{
return child->m_part->openURL( url );
}
else
#endif
return true;
}
#if !APPLE_CHANGES
KParts::ReadOnlyPart *KHTMLPart::createPart( QWidget *parentWidget, const char *widgetName,
QObject *parent, const char *name, const QString &mimetype,
QString &serviceName, QStringList &serviceTypes,
const QStringList ¶ms )
{
QString constr;
if ( !serviceName.isEmpty() )
constr.append( QString::fromLatin1( "Name == '%1'" ).arg( serviceName ) );
KTrader::OfferList offers = KTrader::self()->query( mimetype, "KParts/ReadOnlyPart", constr, QString::null );
if ( offers.isEmpty() )
return 0L;
KService::Ptr service = *offers.begin();
KLibFactory *factory = KLibLoader::self()->factory( QFile::encodeName(service->library()) );
if ( !factory )
return 0L;
KParts::ReadOnlyPart *res = 0L;
const char *className = "KParts::ReadOnlyPart";
if ( service->serviceTypes().contains( "Browser/View" ) )
className = "Browser/View";
if ( factory->inherits( "KParts::Factory" ) )
res = static_cast<KParts::ReadOnlyPart *>(static_cast<KParts::Factory *>( factory )->createPart( parentWidget, widgetName, parent, name, className, params ));
else
res = static_cast<KParts::ReadOnlyPart *>(factory->create( parentWidget, widgetName, className ));
if ( !res )
return res;
serviceTypes = service->serviceTypes();
serviceName = service->name();
return res;
}
KParts::PartManager *KHTMLPart::partManager()
{
if ( !d->m_manager )
{
d->m_manager = new KParts::PartManager( d->m_view->topLevelWidget(), this, "khtml part manager" );
d->m_manager->setAllowNestedParts( true );
connect( d->m_manager, SIGNAL( activePartChanged( KParts::Part * ) ),
this, SLOT( slotActiveFrameChanged( KParts::Part * ) ) );
connect( d->m_manager, SIGNAL( partRemoved( KParts::Part * ) ),
this, SLOT( slotPartRemoved( KParts::Part * ) ) );
}
return d->m_manager;
}
#endif
void KHTMLPart::submitFormAgain()
{
if( d->m_doc && !d->m_doc->parsing() && d->m_submitForm)
KHTMLPart::submitForm( d->m_submitForm->submitAction, d->m_submitForm->submitUrl, d->m_submitForm->submitFormData, d->m_submitForm->target, d->m_submitForm->submitContentType, d->m_submitForm->submitBoundary );
delete d->m_submitForm;
d->m_submitForm = 0;
disconnect(this, SIGNAL(completed()), this, SLOT(submitFormAgain()));
}
void KHTMLPart::submitForm( const char *action, const QString &url, const QByteArray &formData, const QString &_target, const QString& contentType, const QString& boundary )
{
kdDebug(6000) << this << ": KHTMLPart::submitForm target=" << _target << " url=" << url << endl;
KURL u = completeURL( url );
if ( !u.isValid() )
{
return;
}
#if !APPLE_CHANGES
if (!d->m_submitForm && u.protocol() != "https" && u.protocol() != "mailto") {
if (d->m_ssl_in_use) { int rc = KMessageBox::warningContinueCancel(NULL, i18n("Warning: This is a secure form but it is attempting to send your data back unencrypted."
"\nA third party may be able to intercept and view this information."
"\nAre you sure you wish to continue?"),
i18n("SSL"));
if (rc == KMessageBox::Cancel)
return;
} else { KSSLSettings kss(true);
if (kss.warnOnUnencrypted()) {
int rc = KMessageBox::warningContinueCancel(NULL,
i18n("Warning: Your data is about to be transmitted across the network unencrypted."
"\nAre you sure you wish to continue?"),
i18n("KDE"),
QString::null,
"WarnOnUnencryptedForm");
KConfig *config = kapp->config();
QString grpNotifMsgs = QString::fromLatin1("Notification Messages");
KConfigGroupSaver saver( config, grpNotifMsgs );
if (!config->readBoolEntry("WarnOnUnencryptedForm", true)) {
config->deleteEntry("WarnOnUnencryptedForm");
config->sync();
kss.setWarnOnUnencrypted(false);
kss.save();
}
if (rc == KMessageBox::Cancel)
return;
}
}
}
if (!d->m_submitForm && u.protocol() == "mailto") {
int rc = KMessageBox::warningContinueCancel(NULL,
i18n("This site is attempting to submit form data via email."),
i18n("KDE"),
QString::null,
"WarnTriedEmailSubmit");
if (rc == KMessageBox::Cancel) {
return;
}
}
#endif // APPLE_CHANGES
QString urlstring = u.url();
if ( urlstring.find( QString::fromLatin1( "javascript:" ), 0, false ) == 0 ) {
urlstring = KURL::decode_string(urlstring);
d->m_executingJavaScriptFormAction = true;
executeScript( urlstring.right( urlstring.length() - 11) );
d->m_executingJavaScriptFormAction = false;
return;
}
#if !APPLE_CHANGES
if (!checkLinkSecurity(u,
i18n( "<qt>The form will be submitted to <BR><B>%1</B><BR>on your local filesystem.<BR>Do you want to submit the form?" ),
i18n( "Submit" )))
return;
#endif
KParts::URLArgs args;
if (!d->m_referrer.isEmpty())
args.metaData()["referrer"] = d->m_referrer;
#if !APPLE_CHANGES
args.metaData().insert("main_frame_request",
parentPart() == 0 ? "TRUE":"FALSE");
args.metaData().insert("ssl_was_in_use", d->m_ssl_in_use ? "TRUE":"FALSE");
args.metaData().insert("ssl_activate_warnings", "TRUE");
#endif
args.frameName = _target.isEmpty() ? d->m_doc->baseTarget() : _target ;
if (u.protocol() == "mailto") {
QString q = u.query().mid(1);
QStringList nvps = QStringList::split("&", q);
bool triedToAttach = false;
for (QStringList::Iterator nvp = nvps.begin(); nvp != nvps.end(); ++nvp) {
QStringList pair = QStringList::split("=", *nvp);
if (pair.count() >= 2) {
if (pair.first().lower() == "attach") {
nvp = nvps.remove(nvp);
triedToAttach = true;
}
}
}
#if !APPLE_CHANGES
if (triedToAttach)
KMessageBox::information(NULL, i18n("This site attempted to attach a file from your computer in the form submission. The attachment was removed for your protection."), i18n("KDE"), "WarnTriedAttach");
#endif
QString bodyEnc;
if (contentType.lower() == "multipart/form-data") {
bodyEnc = KURL::encode_string(QString::fromLatin1(formData.data(),
formData.size()));
} else if (contentType.lower() == "text/plain") {
QString tmpbody = QString::fromLatin1(formData.data(),
formData.size());
tmpbody.replace(QRegExp("[&]"), "\n");
tmpbody.replace(QRegExp("[+]"), " ");
tmpbody = KURL::decode_string(tmpbody); bodyEnc = KURL::encode_string(tmpbody); } else {
bodyEnc = KURL::encode_string(QString::fromLatin1(formData.data(),
formData.size()));
}
nvps.append(QString("body=%1").arg(bodyEnc));
q = nvps.join("&");
u.setQuery(q);
}
if ( strcmp( action, "get" ) == 0 ) {
if (u.protocol() != "mailto")
u.setQuery( QString::fromLatin1( formData.data(), formData.size() ) );
args.setDoPost( false );
}
else {
args.postData = formData;
args.setDoPost( true );
if (contentType.isNull() || contentType == "application/x-www-form-urlencoded")
args.setContentType( "Content-Type: application/x-www-form-urlencoded" );
else args.setContentType( "Content-Type: " + contentType + "; boundary=" + boundary );
}
if ( d->m_doc->parsing() || d->m_runningScripts > 0 ) {
if( d->m_submitForm ) {
kdDebug(6000) << "KHTMLPart::submitForm ABORTING!" << endl;
return;
}
d->m_submitForm = new KHTMLPartPrivate::SubmitForm;
d->m_submitForm->submitAction = action;
d->m_submitForm->submitUrl = url;
d->m_submitForm->submitFormData = formData;
d->m_submitForm->target = _target;
d->m_submitForm->submitContentType = contentType;
d->m_submitForm->submitBoundary = boundary;
connect(this, SIGNAL(completed()), this, SLOT(submitFormAgain()));
}
else
{
#if APPLE_CHANGES
KWQ(this)->submitForm( u, args);
#else
emit d->m_extension->openURLRequest( u, args );
#endif
}
}
#if !APPLE_CHANGES
void KHTMLPart::popupMenu( const QString &linkUrl )
{
KURL popupURL;
KURL linkKURL;
if ( linkUrl.isEmpty() ) popupURL = this->url();
else { popupURL = completeURL( linkUrl );
linkKURL = popupURL;
}
KXMLGUIClient *client = new KHTMLPopupGUIClient( this, d->m_popupMenuXML, linkKURL );
emit d->m_extension->popupMenu( client, QCursor::pos(), popupURL,
QString::fromLatin1( "text/html" ), S_IFREG );
delete client;
emit popupMenu(linkUrl, QCursor::pos());
}
#endif
void KHTMLPart::slotParentCompleted()
{
if ( d->m_scheduledRedirection != noRedirectionScheduled && !d->m_redirectionTimer.isActive() )
{
d->m_redirectionTimer.start( (int)(1000 * d->m_delayRedirect), true );
}
}
void KHTMLPart::slotChildStarted( KIO::Job *job )
{
khtml::ChildFrame *child = childFrame( sender() );
assert( child );
child->m_bCompleted = false;
if ( d->m_bComplete )
{
#if 0
if ( !parentPart() ) {
emit d->m_extension->openURLNotify();
}
#endif
d->m_bComplete = false;
emit started( job );
}
}
void KHTMLPart::slotChildCompleted()
{
slotChildCompleted( false );
}
void KHTMLPart::slotChildCompleted( bool complete )
{
khtml::ChildFrame *child = childFrame( sender() );
assert( child );
child->m_bCompleted = true;
child->m_args = KParts::URLArgs();
if ( parentPart() == 0 )
d->m_bPendingChildRedirection = (d->m_bPendingChildRedirection || complete);
checkCompleted();
}
#if !APPLE_CHANGES
void KHTMLPart::slotChildURLRequest( const KURL &url, const KParts::URLArgs &args )
{
khtml::ChildFrame *child = childFrame( sender()->parent() );
QString frameName = args.frameName.lower();
if ( !frameName.isEmpty() )
{
if ( frameName == QString::fromLatin1( "_top" ) )
{
emit d->m_extension->openURLRequest( url, args );
return;
}
else if ( frameName == QString::fromLatin1( "_blank" ) )
{
emit d->m_extension->createNewWindow( url, args );
return;
}
else if ( frameName == QString::fromLatin1( "_parent" ) )
{
KParts::URLArgs newArgs( args );
newArgs.frameName = QString::null;
emit d->m_extension->openURLRequest( url, newArgs );
return;
}
else if ( frameName != QString::fromLatin1( "_self" ) )
{
khtml::ChildFrame *_frame = recursiveFrameRequest( url, args );
if ( !_frame )
{
emit d->m_extension->openURLRequest( url, args );
return;
}
child = _frame;
}
}
QString urlStr = url.url();
if ( urlStr.find( QString::fromLatin1( "javascript:" ), 0, false ) == 0 ) {
executeScript( KURL::decode_string( urlStr.right( urlStr.length() - 11) ) );
return;
}
if ( child ) {
child->m_bNotify = true;
requestObject( child, url, args );
} else if ( frameName==QString::fromLatin1("_self") ) {
KParts::URLArgs newArgs( args );
newArgs.frameName = QString::null;
emit d->m_extension->openURLRequest( url, newArgs );
}
}
#endif // APPLE_CHANGES
khtml::ChildFrame *KHTMLPart::childFrame( const QObject *obj )
{
assert( obj->inherits( "KParts::ReadOnlyPart" ) );
const ReadOnlyPart *part = static_cast<const ReadOnlyPart *>( obj );
FrameIt it = d->m_frames.begin();
FrameIt end = d->m_frames.end();
for (; it != end; ++it )
if ( static_cast<ReadOnlyPart *>((*it).m_part) == part )
return &(*it);
it = d->m_objects.begin();
end = d->m_objects.end();
for (; it != end; ++it )
if ( static_cast<ReadOnlyPart *>((*it).m_part) == part )
return &(*it);
return 0L;
}
KHTMLPart *KHTMLPart::findFrame( const QString &f )
{
#if 0
kdDebug() << "KHTMLPart::findFrame '" << f << "'" << endl;
FrameIt it2 = d->m_frames.begin();
FrameIt end = d->m_frames.end();
for (; it2 != end; ++it2 )
kdDebug() << " - having frame '" << (*it2).m_name << "'" << endl;
#endif
ConstFrameIt it = d->m_frames.find( f );
if ( it == d->m_frames.end() )
{
return 0L;
}
else {
KParts::ReadOnlyPart *p = (*it).m_part;
if ( p && p->inherits( "KHTMLPart" ))
{
return (KHTMLPart*)p;
}
else
{
#if 0
if (p)
kdWarning() << "KHTMLPart::findFrame frame " << f << " found but isn't a KHTMLPart ! " << p->className() << endl;
else
kdWarning() << "KHTMLPart::findFrame frame " << f << " found but m_part=0L" << endl;
#endif
return 0L;
}
}
}
#if !APPLE_CHANGES
KParts::ReadOnlyPart *KHTMLPart::currentFrame() const
{
KParts::ReadOnlyPart* part = (KParts::ReadOnlyPart*)(this);
while ( part && part->inherits("KHTMLPart") &&
static_cast<KHTMLPart *>(part)->d->m_frames.count() > 0 ) {
KHTMLPart* frameset = static_cast<KHTMLPart *>(part);
part = static_cast<KParts::ReadOnlyPart *>(frameset->partManager()->activePart());
if ( !part ) return frameset;
}
return part;
}
#endif // APPLE_CHANGES
bool KHTMLPart::frameExists( const QString &frameName )
{
ConstFrameIt it = d->m_frames.find( frameName );
if ( it == d->m_frames.end() )
return false;
return (!(*it).m_frame.isNull());
}
KHTMLPart *KHTMLPart::parentPart() const
{
if ( !parent() || !parent()->inherits( "KHTMLPart" ) )
return 0L;
return (KHTMLPart *)parent();
}
#if !APPLE_CHANGES
khtml::ChildFrame *KHTMLPart::recursiveFrameRequest( const KURL &url, const KParts::URLArgs &args,
bool callParent )
{
FrameIt it = d->m_frames.find( args.frameName );
if ( it != d->m_frames.end() )
return &(*it);
it = d->m_frames.begin();
FrameIt end = d->m_frames.end();
for (; it != end; ++it )
if ( (*it).m_part && (*it).m_part->inherits( "KHTMLPart" ) )
{
KHTMLPart *childPart = (KHTMLPart *)(KParts::ReadOnlyPart *)(*it).m_part;
khtml::ChildFrame *res = childPart->recursiveFrameRequest( url, args, false );
if ( !res )
continue;
childPart->requestObject( res, url, args );
return 0L;
}
if ( parentPart() && callParent )
{
khtml::ChildFrame *res = parentPart()->recursiveFrameRequest( url, args );
if ( res )
parentPart()->requestObject( res, url, args );
return 0L;
}
return 0L;
}
void KHTMLPart::saveState( QDataStream &stream )
{
kdDebug( 6050 ) << "KHTMLPart::saveState saving URL " << m_url.url() << endl;
stream << m_url << (Q_INT32)d->m_view->contentsX() << (Q_INT32)d->m_view->contentsY()
<< (Q_INT32) d->m_view->contentsWidth() << (Q_INT32) d->m_view->contentsHeight() << (Q_INT32) d->m_view->marginWidth() << (Q_INT32) d->m_view->marginHeight();
int focusNodeNumber;
if (!d->m_focusNodeRestored)
focusNodeNumber = d->m_focusNodeNumber;
else if (d->m_doc->focusNode())
focusNodeNumber = d->m_doc->nodeAbsIndex(d->m_doc->focusNode());
else
focusNodeNumber = -1;
stream << focusNodeNumber;
stream << d->m_cacheId;
QStringList docState;
if (d->m_doc)
{
docState = d->m_doc->docState();
}
stream << d->m_encoding << d->m_sheetUsed << docState;
stream << d->m_zoomFactor;
stream << d->m_ssl_in_use
<< d->m_ssl_peer_certificate
<< d->m_ssl_peer_chain
<< d->m_ssl_peer_ip
<< d->m_ssl_cipher
<< d->m_ssl_cipher_desc
<< d->m_ssl_cipher_version
<< d->m_ssl_cipher_used_bits
<< d->m_ssl_cipher_bits
<< d->m_ssl_cert_state;
QStringList frameNameLst, frameServiceTypeLst, frameServiceNameLst;
KURL::List frameURLLst;
QValueList<QByteArray> frameStateBufferLst;
ConstFrameIt it = d->m_frames.begin();
ConstFrameIt end = d->m_frames.end();
for (; it != end; ++it )
{
if ( !(*it).m_part )
continue;
frameNameLst << (*it).m_name;
frameServiceTypeLst << (*it).m_serviceType;
frameServiceNameLst << (*it).m_serviceName;
frameURLLst << (*it).m_part->url();
QByteArray state;
QDataStream frameStream( state, IO_WriteOnly );
if ( (*it).m_extension )
(*it).m_extension->saveState( frameStream );
frameStateBufferLst << state;
}
stream << (Q_UINT32) frameNameLst.count();
stream << frameNameLst << frameServiceTypeLst << frameServiceNameLst << frameURLLst << frameStateBufferLst;
}
void KHTMLPart::restoreState( QDataStream &stream )
{
KURL u;
Q_INT32 xOffset, yOffset, wContents, hContents, mWidth, mHeight;
Q_UINT32 frameCount;
QStringList frameNames, frameServiceTypes, docState, frameServiceNames;
KURL::List frameURLs;
QValueList<QByteArray> frameStateBuffers;
QValueList<int> fSizes;
QString encoding, sheetUsed;
long old_cacheId = d->m_cacheId;
stream >> u >> xOffset >> yOffset >> wContents >> hContents >> mWidth >> mHeight;
d->m_view->setMarginWidth( mWidth );
d->m_view->setMarginHeight( mHeight );
stream >> d->m_focusNodeNumber;
d->m_focusNodeRestored = false;
kdDebug(6050)<<"new focus Node number is:"<<d->m_focusNodeNumber<<endl;
stream >> d->m_cacheId;
stream >> encoding >> sheetUsed >> docState;
d->m_encoding = encoding;
d->m_sheetUsed = sheetUsed;
int zoomFactor;
stream >> zoomFactor;
setZoomFactor(zoomFactor);
stream >> d->m_ssl_in_use
>> d->m_ssl_peer_certificate
>> d->m_ssl_peer_chain
>> d->m_ssl_peer_ip
>> d->m_ssl_cipher
>> d->m_ssl_cipher_desc
>> d->m_ssl_cipher_version
>> d->m_ssl_cipher_used_bits
>> d->m_ssl_cipher_bits
>> d->m_ssl_cert_state;
d->m_paSecurity->setIcon( d->m_ssl_in_use ? "encrypted" : "decrypted" );
stream >> frameCount >> frameNames >> frameServiceTypes >> frameServiceNames
>> frameURLs >> frameStateBuffers;
d->m_bComplete = false;
d->m_bLoadEventEmitted = false;
if (d->m_cacheId == old_cacheId)
{
cancelRedirection();
FrameIt fIt = d->m_frames.begin();
FrameIt fEnd = d->m_frames.end();
for (; fIt != fEnd; ++fIt )
(*fIt).m_bCompleted = false;
fIt = d->m_frames.begin();
QStringList::ConstIterator fNameIt = frameNames.begin();
QStringList::ConstIterator fServiceTypeIt = frameServiceTypes.begin();
QStringList::ConstIterator fServiceNameIt = frameServiceNames.begin();
KURL::List::ConstIterator fURLIt = frameURLs.begin();
QValueList<QByteArray>::ConstIterator fBufferIt = frameStateBuffers.begin();
for (; fIt != fEnd; ++fIt, ++fNameIt, ++fServiceTypeIt, ++fServiceNameIt, ++fURLIt, ++fBufferIt )
{
khtml::ChildFrame *child = &(*fIt);
if ( child->m_name != *fNameIt || child->m_serviceType != *fServiceTypeIt )
{
child->m_bPreloaded = true;
child->m_name = *fNameIt;
child->m_serviceName = *fServiceNameIt;
processObjectRequest( child, *fURLIt, *fServiceTypeIt );
}
if ( child->m_part )
{
child->m_bCompleted = false;
if ( child->m_extension && !(*fBufferIt).isEmpty() )
{
QDataStream frameStream( *fBufferIt, IO_ReadOnly );
child->m_extension->restoreState( frameStream );
}
else
child->m_part->openURL( *fURLIt );
}
}
KParts::URLArgs args( d->m_extension->urlArgs() );
args.xOffset = xOffset;
args.yOffset = yOffset;
args.docState = docState; d->m_extension->setURLArgs( args );
d->m_view->resizeContents( wContents, hContents);
d->m_view->setContentsPos( xOffset, yOffset );
}
else
{
closeURL();
d->m_bCleared = false;
clear();
d->m_encoding = encoding;
d->m_sheetUsed = sheetUsed;
QStringList::ConstIterator fNameIt = frameNames.begin();
QStringList::ConstIterator fNameEnd = frameNames.end();
QStringList::ConstIterator fServiceTypeIt = frameServiceTypes.begin();
QStringList::ConstIterator fServiceNameIt = frameServiceNames.begin();
KURL::List::ConstIterator fURLIt = frameURLs.begin();
QValueList<QByteArray>::ConstIterator fBufferIt = frameStateBuffers.begin();
for (; fNameIt != fNameEnd; ++fNameIt, ++fServiceTypeIt, ++fServiceNameIt, ++fURLIt, ++fBufferIt )
{
khtml::ChildFrame newChild;
newChild.m_bPreloaded = true;
newChild.m_name = *fNameIt;
newChild.m_serviceName = *fServiceNameIt;
FrameIt childFrame = d->m_frames.append( newChild );
processObjectRequest( &(*childFrame), *fURLIt, *fServiceTypeIt );
(*childFrame).m_bPreloaded = true;
if ( (*childFrame).m_part )
{
if ( (*childFrame).m_extension )
if ( (*childFrame).m_extension && !(*fBufferIt).isEmpty() )
{
QDataStream frameStream( *fBufferIt, IO_ReadOnly );
(*childFrame).m_extension->restoreState( frameStream );
}
else
(*childFrame).m_part->openURL( *fURLIt );
}
}
KParts::URLArgs args( d->m_extension->urlArgs() );
args.xOffset = xOffset;
args.yOffset = yOffset;
args.docState = docState;
d->m_extension->setURLArgs( args );
if (!KHTMLPageCache::self()->isValid(d->m_cacheId))
{
d->m_restored = true;
openURL( u );
d->m_restored = false;
}
else
{
restoreURL( u );
}
}
}
void KHTMLPart::show()
{
if ( d->m_view )
d->m_view->show();
}
void KHTMLPart::hide()
{
if ( d->m_view )
d->m_view->hide();
}
#endif // APPLE_CHANGES
DOM::Node KHTMLPart::nodeUnderMouse() const
{
return d->m_view->nodeUnderMouse();
}
void KHTMLPart::emitSelectionChanged()
{
#if !APPLE_CHANGES
emit d->m_extension->enableAction( "copy", hasSelection() );
emit d->m_extension->selectionInfo( selectedText() );
emit selectionChanged();
#endif
}
int KHTMLPart::zoomFactor() const
{
return d->m_zoomFactor;
}
static const int zoomSizes[] = { 20, 40, 60, 80, 90, 95, 100, 105, 110, 120, 140, 160, 180, 200, 250, 300 };
static const int zoomSizeCount = (sizeof(zoomSizes) / sizeof(int));
static const int minZoom = 20;
static const int maxZoom = 300;
void KHTMLPart::slotIncZoom()
{
int zoomFactor = d->m_zoomFactor;
if (zoomFactor < maxZoom) {
for (int i = 0; i < zoomSizeCount; ++i)
if (zoomSizes[i] > zoomFactor) {
zoomFactor = zoomSizes[i];
break;
}
setZoomFactor(zoomFactor);
}
}
void KHTMLPart::slotDecZoom()
{
int zoomFactor = d->m_zoomFactor;
if (zoomFactor > minZoom) {
for (int i = zoomSizeCount-1; i >= 0; --i)
if (zoomSizes[i] < zoomFactor) {
zoomFactor = zoomSizes[i];
break;
}
setZoomFactor(zoomFactor);
}
}
void KHTMLPart::setZoomFactor (int percent)
{
#if !APPLE_CHANGES // limits are client's responsibility
if (percent < minZoom) percent = minZoom;
if (percent > maxZoom) percent = maxZoom;
#endif
if (d->m_zoomFactor == percent) return;
d->m_zoomFactor = percent;
if(d->m_doc) {
#if !APPLE_CHANGES
QApplication::setOverrideCursor( waitCursor );
#endif
d->m_doc->recalcStyle( NodeImpl::Force );
#if !APPLE_CHANGES
QApplication::restoreOverrideCursor();
#endif
}
ConstFrameIt it = d->m_frames.begin();
ConstFrameIt end = d->m_frames.end();
for (; it != end; ++it )
if ( !( *it ).m_part.isNull() && ( *it ).m_part->inherits( "KHTMLPart" ) ) {
KParts::ReadOnlyPart* p = ( *it ).m_part;
static_cast<KHTMLPart*>( p )->setZoomFactor(d->m_zoomFactor);
}
#if !APPLE_CHANGES
d->m_paDecZoomFactor->setEnabled( d->m_zoomFactor > minZoom );
d->m_paIncZoomFactor->setEnabled( d->m_zoomFactor < maxZoom );
#endif
if (d->m_doc && d->m_doc->renderer() && d->m_doc->renderer()->needsLayout())
view()->layout();
}
void KHTMLPart::setJSStatusBarText( const QString &text )
{
d->m_kjsStatusBarText = text;
emit setStatusBarText( d->m_kjsStatusBarText );
}
void KHTMLPart::setJSDefaultStatusBarText( const QString &text )
{
d->m_kjsDefaultStatusBarText = text;
emit setStatusBarText( d->m_kjsDefaultStatusBarText );
}
QString KHTMLPart::jsStatusBarText() const
{
return d->m_kjsStatusBarText;
}
QString KHTMLPart::jsDefaultStatusBarText() const
{
return d->m_kjsDefaultStatusBarText;
}
QString KHTMLPart::referrer() const
{
return d->m_referrer;
}
QString KHTMLPart::lastModified() const
{
return d->m_lastModified;
}
#if !APPLE_CHANGES
void KHTMLPart::slotLoadImages()
{
if (d->m_doc )
d->m_doc->docLoader()->setAutoloadImages( !d->m_doc->docLoader()->autoloadImages() );
ConstFrameIt it = d->m_frames.begin();
ConstFrameIt end = d->m_frames.end();
for (; it != end; ++it )
if ( !( *it ).m_part.isNull() && ( *it ).m_part->inherits( "KHTMLPart" ) ) {
KParts::ReadOnlyPart* p = ( *it ).m_part;
static_cast<KHTMLPart*>( p )->slotLoadImages();
}
}
#endif
void KHTMLPart::reparseConfiguration()
{
#if !APPLE_CHANGES
setAutoloadImages( settings->autoLoadImages() );
if (d->m_doc)
d->m_doc->docLoader()->setShowAnimations( settings->showAnimations() );
d->m_bJScriptEnabled = settings->isJavaScriptEnabled(m_url.host());
d->m_bJScriptDebugEnabled = settings->isJavaScriptDebugEnabled();
d->m_bJavaEnabled = settings->isJavaEnabled(m_url.host());
d->m_bPluginsEnabled = settings->isPluginsEnabled(m_url.host());
delete d->m_settings;
d->m_settings = new KHTMLSettings(*KHTMLFactory::defaultHTMLSettings());
QString userStyleSheet = KHTMLFactory::defaultHTMLSettings()->userStyleSheet();
#else
setAutoloadImages( d->m_settings->autoLoadImages() );
if (d->m_doc)
d->m_doc->docLoader()->setShowAnimations( d->m_settings->showAnimations() );
d->m_bJScriptEnabled = d->m_settings->isJavaScriptEnabled(m_url.host());
d->m_bJScriptDebugEnabled = d->m_settings->isJavaScriptDebugEnabled();
d->m_bJavaEnabled = d->m_settings->isJavaEnabled(m_url.host());
d->m_bPluginsEnabled = d->m_settings->isPluginsEnabled(m_url.host());
QString userStyleSheet = d->m_settings->userStyleSheet();
#endif
if ( !userStyleSheet.isEmpty() )
setUserStyleSheet( KURL( userStyleSheet ) );
else
setUserStyleSheet( QString() );
#if !APPLE_CHANGES
QApplication::setOverrideCursor( waitCursor );
#endif
if(d->m_doc) d->m_doc->updateStyleSelector();
#if !APPLE_CHANGES
QApplication::restoreOverrideCursor();
#endif
}
QStringList KHTMLPart::frameNames() const
{
QStringList res;
ConstFrameIt it = d->m_frames.begin();
ConstFrameIt end = d->m_frames.end();
for (; it != end; ++it )
if (!(*it).m_bPreloaded)
res += (*it).m_name;
return res;
}
QPtrList<KParts::ReadOnlyPart> KHTMLPart::frames() const
{
QPtrList<KParts::ReadOnlyPart> res;
ConstFrameIt it = d->m_frames.begin();
ConstFrameIt end = d->m_frames.end();
for (; it != end; ++it )
if (!(*it).m_bPreloaded)
res.append( (*it).m_part );
return res;
}
#if !APPLE_CHANGES
bool KHTMLPart::openURLInFrame( const KURL &url, const KParts::URLArgs &urlArgs )
{
FrameIt it = d->m_frames.find( urlArgs.frameName );
if ( it == d->m_frames.end() )
return false;
if ( !urlArgs.lockHistory() )
emit d->m_extension->openURLNotify();
requestObject( &(*it), url, urlArgs );
return true;
}
#endif
void KHTMLPart::setDNDEnabled( bool b )
{
d->m_bDnd = b;
}
bool KHTMLPart::dndEnabled() const
{
return d->m_bDnd;
}
void KHTMLPart::customEvent( QCustomEvent *event )
{
if ( khtml::MousePressEvent::test( event ) )
{
khtmlMousePressEvent( static_cast<khtml::MousePressEvent *>( event ) );
return;
}
if ( khtml::MouseDoubleClickEvent::test( event ) )
{
khtmlMouseDoubleClickEvent( static_cast<khtml::MouseDoubleClickEvent *>( event ) );
return;
}
if ( khtml::MouseMoveEvent::test( event ) )
{
khtmlMouseMoveEvent( static_cast<khtml::MouseMoveEvent *>( event ) );
return;
}
if ( khtml::MouseReleaseEvent::test( event ) )
{
khtmlMouseReleaseEvent( static_cast<khtml::MouseReleaseEvent *>( event ) );
return;
}
if ( khtml::DrawContentsEvent::test( event ) )
{
khtmlDrawContentsEvent( static_cast<khtml::DrawContentsEvent *>( event ) );
return;
}
KParts::ReadOnlyPart::customEvent( event );
}
#if APPLE_CHANGES
static bool firstRunAt(RenderObject *renderNode, int y, NodeImpl *&startNode, long &startOffset)
{
for (RenderObject *n = renderNode; n; n = n->nextSibling()) {
if (n->isText()) {
RenderText *textRenderer = static_cast<khtml::RenderText *>(n);
InlineTextBoxArray runs = textRenderer->inlineTextBoxes();
for (unsigned i = 0; i != runs.count(); i++) {
if (runs[i]->m_y == y) {
startNode = textRenderer->element();
startOffset = runs[i]->m_start;
return true;
}
}
}
if (firstRunAt(n->firstChild(), y, startNode, startOffset)) {
return true;
}
}
return false;
}
static bool lastRunAt(RenderObject *renderNode, int y, NodeImpl *&endNode, long &endOffset)
{
RenderObject *n = renderNode;
if (!n) {
return false;
}
RenderObject *next;
while ((next = n->nextSibling())) {
n = next;
}
while (1) {
if (lastRunAt(n->firstChild(), y, endNode, endOffset)) {
return true;
}
if (n->isText()) {
RenderText *textRenderer = static_cast<khtml::RenderText *>(n);
InlineTextBoxArray runs = textRenderer->inlineTextBoxes();
for (int i = (int)runs.count()-1; i >= 0; i--) {
if (runs[i]->m_y == y) {
endNode = textRenderer->element();
endOffset = runs[i]->m_start + runs[i]->m_len;
return true;
}
}
}
if (n == renderNode) {
return false;
}
n = n->previousSibling();
}
}
static bool startAndEndLineNodesIncludingNode (DOM::NodeImpl *node, int offset, DOM::Node &_startNode, long &startOffset, DOM::Node &_endNode, long &endOffset)
{
if (node && (node->nodeType() == Node::TEXT_NODE || node->nodeType() == Node::CDATA_SECTION_NODE)){
int pos;
int selectionPointY;
khtml::RenderText *renderer = static_cast<khtml::RenderText *>(node->renderer());
khtml::InlineTextBox * run = renderer->findNextInlineTextBox( offset, pos );
DOMString t = node->nodeValue();
DOM::NodeImpl* startNode;
DOM::NodeImpl* endNode;
if (!run)
return false;
selectionPointY = run->m_y;
khtml::RenderObject *renderNode = renderer;
while (renderNode && renderNode->isInline())
renderNode = renderNode->parent();
renderNode = renderNode->firstChild();
if (!firstRunAt (renderNode, selectionPointY, startNode, startOffset))
return false;
if (!lastRunAt (renderNode, selectionPointY, endNode, endOffset))
return false;
_startNode = startNode;
_endNode = endNode;
return true;
}
return false;
}
static void findWordBoundary(QChar *chars, int len, int position, int *start, int *end)
{
TextBreakLocatorRef breakLocator;
OSStatus status = UCCreateTextBreakLocator(NULL, 0, kUCTextBreakWordMask, &breakLocator);
if (status == noErr) {
UniCharArrayOffset startOffset, endOffset;
status = UCFindTextBreak(breakLocator, kUCTextBreakWordMask, 0, (const UniChar *)chars, len, position, &endOffset);
if (status == noErr) {
status = UCFindTextBreak(breakLocator, kUCTextBreakWordMask, kUCTextBreakGoBackwardsMask, (const UniChar *)chars, len, position, &startOffset);
}
UCDisposeTextBreakLocator(&breakLocator);
if (status == noErr) {
*start = startOffset;
*end = endOffset;
return;
}
}
if (chars[position].isSpace()) {
int pos = position;
while (chars[pos].isSpace() && pos >= 0)
pos--;
*start = pos+1;
pos = position;
while (chars[pos].isSpace() && pos < (int)len)
pos++;
*end = pos;
} else if (chars[position].isPunct()) {
int pos = position;
while (chars[pos].isPunct() && pos >= 0)
pos--;
*start = pos+1;
pos = position;
while (chars[pos].isPunct() && pos < (int)len)
pos++;
*end = pos;
} else {
int pos = position;
while (!chars[pos].isSpace() && !chars[pos].isPunct() && pos >= 0)
pos--;
*start = pos+1;
pos = position;
while (!chars[pos].isSpace() && !chars[pos].isPunct() && pos < (int)len)
pos++;
*end = pos;
}
}
#endif
bool KHTMLPart::isPointInsideSelection(int x, int y)
{
if (d->m_selectionStart == d->m_selectionEnd && d->m_startOffset == d->m_endOffset) {
return false;
}
if (!xmlDocImpl()->renderer()) {
return false;
}
RenderObject::NodeInfo nodeInfo(true, true);
xmlDocImpl()->renderer()->layer()->nodeAtPoint(nodeInfo, x, y);
DOM::NodeImpl* innerNode = nodeInfo.innerNode();
if (!innerNode->renderer()) {
return false;
}
int offset = 0, ax, ay;
DOM::NodeImpl* node = 0;
if (innerNode->nodeType() == Node::TEXT_NODE) {
innerNode = innerNode->parentNode();
}
innerNode->renderer()->absolutePosition (ax, ay);
innerNode->renderer()->checkSelectionPoint( x, y, ax-innerNode->renderer()->xPos(), ay-innerNode->renderer()->yPos(), node, offset);
if (!node) {
return false;
}
DOM::Node n = d->m_selectionStart;
while(!n.isNull()) {
if (n == node) {
if ((n == d->m_selectionStart && offset < d->m_startOffset) ||
(n == d->m_selectionEnd && offset > d->m_endOffset)) {
return false;
}
return true;
}
if (n == d->m_selectionEnd) {
break;
}
DOM::Node next = n.firstChild();
if (next.isNull()) {
next = n.nextSibling();
}
while (next.isNull() && !n.parentNode().isNull()) {
n = n.parentNode();
next = n.nextSibling();
}
n = next;
}
return false;
}
void KHTMLPart::khtmlMousePressEvent( khtml::MousePressEvent *event )
{
DOM::DOMString url = event->url();
QMouseEvent *_mouse = event->qmouseEvent();
DOM::Node innerNode = event->innerNode();
d->m_mousePressNode = innerNode;
d->m_dragStartPos = _mouse->pos();
if ( !event->url().isNull() ) {
d->m_strSelectedURL = event->url().string();
d->m_strSelectedURLTarget = event->target().string();
}
else
d->m_strSelectedURL = d->m_strSelectedURLTarget = QString::null;
if ( _mouse->button() == LeftButton ||
_mouse->button() == MidButton )
{
d->m_bMousePressed = true;
#ifndef KHTML_NO_SELECTION
#if APPLE_CHANGES
d->m_selectionInitiatedWithDoubleClick = false;
d->m_selectionInitiatedWithTripleClick = false;
d->m_mouseMovedSinceLastMousePress = false;
if (event->qmouseEvent()->clickCount() == 2){
QMouseEvent *_mouse = event->qmouseEvent();
DOM::Node innerNode = event->innerNode();
d->m_selectionStart = 0;
d->m_selectionEnd = 0;
d->m_startOffset = 0;
d->m_endOffset = 0;
if ( _mouse->button() == LeftButton ){
if ( !innerNode.isNull() && innerNode.handle()->renderer()) {
int startOffset = 0, endOffset = 0;
DOM::NodeImpl* node = 0;
if (innerNode.nodeType() == Node::TEXT_NODE)
innerNode = innerNode.parentNode();
innerNode.handle()->renderer()->checkSelectionPoint( event->x(), event->y(),
event->absX()-innerNode.handle()->renderer()->xPos(),
event->absY()-innerNode.handle()->renderer()->yPos(),
node, startOffset);
if (node && (node->nodeType() == Node::TEXT_NODE || node->nodeType() == Node::CDATA_SECTION_NODE)){
DOMString t = node->nodeValue();
QChar *chars = t.unicode();
uint len = t.length();
findWordBoundary (chars, len, startOffset, &startOffset, &endOffset);
d->m_startBeforeEnd = true;
d->m_selectionStart = node;
d->m_startOffset = startOffset;
d->m_selectionEnd = d->m_selectionStart;
d->m_endOffset = endOffset;
}
}
}
if (d->m_selectionStart == 0 || d->m_selectionEnd == 0)
d->m_doc->clearSelection();
else{
d->m_initialSelectionStart = d->m_selectionStart;
d->m_initialSelectionStartOffset = d->m_startOffset;
d->m_initialSelectionEnd = d->m_selectionEnd;
d->m_initialSelectionEndOffset = d->m_endOffset;
d->m_selectionInitiatedWithDoubleClick = true;
d->m_doc->setSelection(d->m_selectionStart.handle(), d->m_startOffset,
d->m_selectionEnd.handle(),d->m_endOffset);
}
emitSelectionChanged();
startAutoScroll();
}
else if (event->qmouseEvent()->clickCount() >= 3){
QMouseEvent *_mouse = event->qmouseEvent();
DOM::Node innerNode = event->innerNode();
d->m_selectionStart = 0;
d->m_selectionEnd = 0;
d->m_startOffset = 0;
d->m_endOffset = 0;
if ( _mouse->button() == LeftButton ){
if ( !innerNode.isNull() && innerNode.handle()->renderer()) {
int startOffset = 0;
DOM::NodeImpl* node = 0;
if (innerNode.nodeType() == Node::TEXT_NODE)
innerNode = innerNode.parentNode();
innerNode.handle()->renderer()->checkSelectionPoint( event->x(), event->y(),
event->absX()-innerNode.handle()->renderer()->xPos(),
event->absY()-innerNode.handle()->renderer()->yPos(),
node, startOffset);
startAndEndLineNodesIncludingNode (node, startOffset, d->m_selectionStart, d->m_startOffset, d->m_selectionEnd, d->m_endOffset);
}
}
if (d->m_selectionStart == 0 || d->m_selectionEnd == 0)
d->m_doc->clearSelection();
else {
d->m_initialSelectionStart = d->m_selectionStart;
d->m_initialSelectionStartOffset = d->m_startOffset;
d->m_initialSelectionEnd = d->m_selectionEnd;
d->m_initialSelectionEndOffset = d->m_endOffset;
d->m_selectionInitiatedWithTripleClick = true;
d->m_doc->setSelection(d->m_selectionStart.handle(), d->m_startOffset,
d->m_selectionEnd.handle(),d->m_endOffset);
}
emitSelectionChanged();
startAutoScroll();
}
else {
#endif
if ( _mouse->button() == LeftButton )
{
if ( !innerNode.isNull() && innerNode.handle()->renderer()) {
#if APPLE_CHANGES
if (isPointInsideSelection(event->x(), event->y())) {
return;
}
#endif
int offset = 0;
DOM::NodeImpl* node = 0;
if (innerNode.nodeType() == Node::TEXT_NODE)
innerNode = innerNode.parentNode();
innerNode.handle()->renderer()->checkSelectionPoint( event->x(), event->y(),
event->absX()-innerNode.handle()->renderer()->xPos(),
event->absY()-innerNode.handle()->renderer()->yPos(), node, offset);
d->m_selectionStart = node;
d->m_startOffset = offset;
d->m_selectionEnd = d->m_selectionStart;
d->m_endOffset = d->m_startOffset;
d->m_doc->clearSelection();
}
else
{
d->m_selectionStart = DOM::Node();
d->m_selectionEnd = DOM::Node();
}
emitSelectionChanged();
startAutoScroll();
}
#if APPLE_CHANGES
}
#endif
#else
d->m_dragLastPos = _mouse->globalPos();
#endif
}
#if !APPLE_CHANGES
if ( _mouse->button() == RightButton )
{
popupMenu( d->m_strSelectedURL );
d->m_strSelectedURL = d->m_strSelectedURLTarget = QString::null;
}
#endif
}
void KHTMLPart::khtmlMouseDoubleClickEvent( khtml::MouseDoubleClickEvent *event)
{
}
void KHTMLPart::khtmlMouseMoveEvent( khtml::MouseMoveEvent *event )
{
QMouseEvent *_mouse = event->qmouseEvent();
DOM::Node innerNode = event->innerNode();
#ifndef QT_NO_DRAGANDDROP
if( d->m_bMousePressed && (!d->m_strSelectedURL.isEmpty() || (!innerNode.isNull() && innerNode.elementId() == ID_IMG) ) &&
( d->m_dragStartPos - _mouse->pos() ).manhattanLength() > KGlobalSettings::dndEventDelay() &&
d->m_bDnd && d->m_mousePressNode == innerNode ) {
QPixmap p;
QDragObject *drag = 0;
if( !d->m_strSelectedURL.isEmpty() ) {
KURL u( completeURL( d->m_strSelectedURL) );
KURLDrag* urlDrag = KURLDrag::newDrag( u, d->m_view->viewport() );
if ( !d->m_referrer.isEmpty() )
urlDrag->metaData()["referrer"] = d->m_referrer;
drag = urlDrag;
p = KMimeType::pixmapForURL(u, 0, KIcon::Desktop, KIcon::SizeMedium);
} else {
HTMLImageElementImpl *i = static_cast<HTMLImageElementImpl *>(innerNode.handle());
if( i ) {
KMultipleDrag *mdrag = new KMultipleDrag( d->m_view->viewport() );
mdrag->addDragObject( new QImageDrag( i->currentImage(), 0L ) );
KURL u( completeURL( khtml::parseURL(i->getAttribute(ATTR_SRC)).string() ) );
KURLDrag* urlDrag = KURLDrag::newDrag( u, 0L );
if ( !d->m_referrer.isEmpty() )
urlDrag->metaData()["referrer"] = d->m_referrer;
mdrag->addDragObject( urlDrag );
drag = mdrag;
p = KMimeType::mimeType("image/png")->pixmap(KIcon::Desktop);
}
}
if ( !p.isNull() )
drag->setPixmap(p);
stopAutoScroll();
if(drag)
drag->drag();
d->m_bMousePressed = false;
d->m_strSelectedURL = d->m_strSelectedURLTarget = QString::null;
return;
}
#endif
DOM::DOMString url = event->url();
DOM::DOMString target = event->target();
if ( !d->m_bMousePressed )
{
#if !APPLE_CHANGES
if ( url.length() )
{
bool shiftPressed = ( _mouse->state() & ShiftButton );
if ( !innerNode.isNull() && innerNode.elementId() == ID_IMG )
{
HTMLImageElementImpl *i = static_cast<HTMLImageElementImpl *>(innerNode.handle());
if ( i && i->isServerMap() )
{
khtml::RenderObject *r = i->renderer();
if(r)
{
int absx, absy, vx, vy;
r->absolutePosition(absx, absy);
view()->contentsToViewport( absx, absy, vx, vy );
int x(_mouse->x() - vx), y(_mouse->y() - vy);
d->m_overURL = url.string() + QString("?%1,%2").arg(x).arg(y);
d->m_overURLTarget = target.string();
overURL( d->m_overURL, target.string(), shiftPressed );
return;
}
}
}
if ( d->m_overURL.isEmpty() || d->m_overURL != url || d->m_overURLTarget != target )
{
d->m_overURL = url.string();
d->m_overURLTarget = target.string();
overURL( d->m_overURL, target.string(), shiftPressed );
}
}
else {
if( !d->m_overURL.isEmpty() ) {
d->m_overURL = d->m_overURLTarget = QString::null;
emit onURL( QString::null );
emit setStatusBarText( d->m_kjsDefaultStatusBarText );
}
}
#endif // APPLE_CHANGES
}
else {
#ifndef KHTML_NO_SELECTION
if( d->m_bMousePressed && innerNode.handle() && innerNode.handle()->renderer() &&
( _mouse->state() == LeftButton )) {
int offset = -1;
DOM::NodeImpl* node=0;
if (innerNode.nodeType() == Node::TEXT_NODE)
innerNode = innerNode.parentNode();
innerNode.handle()->renderer()->checkSelectionPoint( event->x(), event->y(),
event->absX()-innerNode.handle()->renderer()->xPos(),
event->absY()-innerNode.handle()->renderer()->yPos(), node, offset);
#if APPLE_CHANGES
if (node == 0)
return;
if (!d->m_mouseMovedSinceLastMousePress) {
d->m_mouseMovedSinceLastMousePress = true;
d->m_selectionStart = node;
d->m_startOffset = offset;
d->m_selectionEnd = node;
d->m_endOffset = offset;
d->m_doc->clearSelection();
}
#endif
DOM::Node n = d->m_selectionStart;
d->m_startBeforeEnd = false;
while(!n.isNull()) {
if(n == node) {
d->m_startBeforeEnd = true;
break;
}
DOM::Node next = n.firstChild();
if(next.isNull()) next = n.nextSibling();
while( next.isNull() && !n.parentNode().isNull() ) {
n = n.parentNode();
next = n.nextSibling();
}
n = next;
}
#if APPLE_CHANGES
if ( d->m_selectionInitiatedWithDoubleClick){
int wordStartOffset = offset, wordEndOffset = offset;
if (node && (node->nodeType() == Node::TEXT_NODE || node->nodeType() == Node::CDATA_SECTION_NODE)){
DOMString t = node->nodeValue();
QChar *chars = t.unicode();
uint len = t.length();
findWordBoundary (chars, len, offset, &wordStartOffset, &wordEndOffset);
}
if (d->m_startBeforeEnd) {
if (node == d->m_initialSelectionStart.handle() && node == d->m_initialSelectionEnd.handle()){
d->m_selectionStart = d->m_initialSelectionStart;
d->m_startOffset = MIN(d->m_initialSelectionStartOffset, wordStartOffset);
wordEndOffset = MAX(d->m_initialSelectionEndOffset, wordEndOffset);
d->m_selectionEnd = node;
d->m_endOffset = wordEndOffset;
}
else {
d->m_selectionStart = d->m_initialSelectionStart;
d->m_startOffset = d->m_initialSelectionStartOffset;
d->m_selectionEnd = node;
d->m_endOffset = wordEndOffset;
}
}
else {
d->m_selectionStart = d->m_initialSelectionEnd;
d->m_startOffset = d->m_initialSelectionEndOffset;
d->m_selectionEnd = node;
d->m_endOffset = wordStartOffset;
}
}
else if (d->m_selectionInitiatedWithTripleClick ){
DOM::Node lineStart, lineEnd;
long lineStartOffset, lineEndOffset;
if (startAndEndLineNodesIncludingNode (node, offset, lineStart, lineStartOffset, lineEnd, lineEndOffset)){
if (d->m_startBeforeEnd) {
if (node == d->m_initialSelectionStart.handle() && node == lineEnd.handle()){
d->m_selectionStart = d->m_initialSelectionStart;
d->m_startOffset = MIN(lineStartOffset, d->m_initialSelectionStartOffset);
d->m_selectionEnd = lineEnd;
d->m_endOffset = MAX(lineEndOffset, d->m_initialSelectionEndOffset);
}
else {
d->m_selectionStart = d->m_initialSelectionStart;
d->m_startOffset = d->m_initialSelectionStartOffset;
d->m_selectionEnd = lineEnd;
d->m_endOffset = lineEndOffset;
}
}
else {
d->m_selectionStart = d->m_initialSelectionEnd;
d->m_startOffset = d->m_initialSelectionEndOffset;
d->m_selectionEnd = lineStart;
d->m_endOffset = lineStartOffset;
}
}
}
else {
d->m_selectionEnd = node;
d->m_endOffset = offset;
}
#else
d->m_selectionEnd = node;
d->m_endOffset = offset;
#endif
if ( !d->m_selectionStart.isNull() && !d->m_selectionEnd.isNull() )
{
if (d->m_selectionEnd == d->m_selectionStart && d->m_endOffset < d->m_startOffset)
d->m_doc->setSelection(d->m_selectionStart.handle(),d->m_endOffset,
d->m_selectionEnd.handle(),d->m_startOffset);
else if (d->m_startBeforeEnd)
d->m_doc->setSelection(d->m_selectionStart.handle(),d->m_startOffset,
d->m_selectionEnd.handle(),d->m_endOffset);
else
d->m_doc->setSelection(d->m_selectionEnd.handle(),d->m_endOffset,
d->m_selectionStart.handle(),d->m_startOffset);
}
#else
if ( d->m_doc && d->m_view ) {
QPoint diff( _mouse->globalPos() - d->m_dragLastPos );
if ( abs( diff.x() ) > 64 || abs( diff.y() ) > 64 ) {
d->m_view->scrollBy( -diff.x(), -diff.y() );
d->m_dragLastPos = _mouse->globalPos();
}
}
#endif
}
}
}
void KHTMLPart::khtmlMouseReleaseEvent( khtml::MouseReleaseEvent *event )
{
DOM::Node innerNode = event->innerNode();
d->m_mousePressNode = DOM::Node();
if ( d->m_bMousePressed )
stopAutoScroll();
d->m_bMousePressed = false;
#ifndef QT_NO_CLIPBOARD
QMouseEvent *_mouse = event->qmouseEvent();
if ((d->m_guiProfile == BrowserViewGUI) && (_mouse->button() == MidButton) && (event->url().isNull()))
{
QClipboard *cb = QApplication::clipboard();
cb->setSelectionMode( true );
QCString plain("plain");
QString url = cb->text(plain).stripWhiteSpace();
KURL u(url);
if ( u.isMalformed() ) {
if ( url.startsWith( "ftp." ) )
{
url.prepend( "ftp://" );
u = url;
}
else
{
url.prepend( "http://" );
u = url;
}
}
if (u.isValid())
{
QString savedReferrer = d->m_referrer;
d->m_referrer = QString::null; urlSelected(url, 0,0, "_top");
d->m_referrer = savedReferrer; }
}
#endif
#if APPLE_CHANGES
if (d->m_dragStartPos.x() == event->qmouseEvent()->x() &&
d->m_dragStartPos.y() == event->qmouseEvent()->y() &&
!d->m_selectionInitiatedWithDoubleClick &&
!d->m_selectionInitiatedWithTripleClick) {
d->m_selectionStart = 0;
d->m_selectionEnd = 0;
d->m_startOffset = 0;
d->m_endOffset = 0;
d->m_doc->clearSelection();
}
#endif
#ifndef KHTML_NO_SELECTION
if(d->m_selectionStart == d->m_selectionEnd && d->m_startOffset == d->m_endOffset) {
d->m_selectionStart = 0;
d->m_selectionEnd = 0;
d->m_startOffset = 0;
d->m_endOffset = 0;
emitSelectionChanged();
} else {
DOM::Node n = d->m_selectionStart;
d->m_startBeforeEnd = false;
if( d->m_selectionStart == d->m_selectionEnd ) {
if( d->m_startOffset < d->m_endOffset )
d->m_startBeforeEnd = true;
} else {
while(!n.isNull()) {
if(n == d->m_selectionEnd) {
d->m_startBeforeEnd = true;
break;
}
DOM::Node next = n.firstChild();
if(next.isNull()) next = n.nextSibling();
while( next.isNull() && !n.parentNode().isNull() ) {
n = n.parentNode();
next = n.nextSibling();
}
n = next;
}
}
if(!d->m_startBeforeEnd)
{
DOM::Node tmpNode = d->m_selectionStart;
int tmpOffset = d->m_startOffset;
d->m_selectionStart = d->m_selectionEnd;
d->m_startOffset = d->m_endOffset;
d->m_selectionEnd = tmpNode;
d->m_endOffset = tmpOffset;
d->m_startBeforeEnd = true;
}
#ifndef QT_NO_CLIPBOARD
QString text = selectedText();
text.replace(QRegExp(QChar(0xa0)), " ");
QClipboard *cb = QApplication::clipboard();
cb->setSelectionMode( true );
disconnect( kapp->clipboard(), SIGNAL( selectionChanged()), this, SLOT( slotClearSelection()));
cb->setText(text);
connect( kapp->clipboard(), SIGNAL( selectionChanged()), SLOT( slotClearSelection()));
cb->setSelectionMode( false );
#endif
emitSelectionChanged();
}
#endif
}
void KHTMLPart::khtmlDrawContentsEvent( khtml::DrawContentsEvent * )
{
}
#if !APPLE_CHANGES
void KHTMLPart::guiActivateEvent( KParts::GUIActivateEvent *event )
{
if ( event->activated() )
{
emitSelectionChanged();
emit d->m_extension->enableAction( "print", d->m_doc != 0 );
if ( !d->m_settings->autoLoadImages() && d->m_paLoadImages )
{
QPtrList<KAction> lst;
lst.append( d->m_paLoadImages );
plugActionList( "loadImages", lst );
}
}
}
void KHTMLPart::slotFind()
{
KHTMLPart *part = static_cast<KHTMLPart *>( currentFrame() );
if (!part)
return;
if (!part->inherits("KHTMLPart") )
{
kdError(6000) << "slotFind: part is a " << part->className() << ", can't do a search into it" << endl;
return;
}
if ( !d->m_findDialog ) {
d->m_findDialog = new KHTMLFind( part, part->widget(), "khtmlfind" );
connect( d->m_findDialog, SIGNAL( done() ),
this, SLOT( slotFindDone() ) );
connect( d->m_findDialog, SIGNAL( destroyed() ),
this, SLOT( slotFindDialogDestroyed() ) );
}
d->m_findDialog->setPart( part );
d->m_findDialog->setText( part->d->m_lastFindState.text );
d->m_findDialog->setCaseSensitive( part->d->m_lastFindState.caseSensitive );
d->m_findDialog->setDirection( part->d->m_lastFindState.direction );
d->m_findDialog->show();
d->m_paFind->setEnabled( false );
}
void KHTMLPart::slotFindDone()
{
assert( d->m_findDialog );
KHTMLPart *part = d->m_findDialog->part();
part->d->m_lastFindState.text = d->m_findDialog->getText();
part->d->m_lastFindState.caseSensitive = d->m_findDialog->case_sensitive();
part->d->m_lastFindState.direction = d->m_findDialog->get_direction();
d->m_paFind->setEnabled( true );
}
void KHTMLPart::slotFindDialogDestroyed()
{
assert( sender() == d->m_findDialog );
d->m_findDialog = 0;
d->m_paFind->setEnabled( true );
}
void KHTMLPart::slotPrintFrame()
{
if ( d->m_frames.count() == 0 )
return;
KParts::ReadOnlyPart *frame = currentFrame();
if (!frame)
return;
KParts::BrowserExtension *ext = KParts::BrowserExtension::childObject( frame );
if ( !ext )
return;
QMetaObject *mo = ext->metaObject();
int idx = mo->findSlot( "print()", TRUE );
if ( idx >= 0 ) {
QUObject o[ 1 ];
ext->qt_invoke( idx, o );
}
}
void KHTMLPart::slotSelectAll()
{
KParts::ReadOnlyPart *part = currentFrame();
if (part && part->inherits("KHTMLPart"))
static_cast<KHTMLPart *>(part)->selectAll();
}
#endif // APPLE_CHANGES
void KHTMLPart::startAutoScroll()
{
#if !APPLE_CHANGES
connect(&d->m_scrollTimer, SIGNAL( timeout() ), this, SLOT( slotAutoScroll() ));
d->m_scrollTimer.start(100, false);
#endif
}
void KHTMLPart::stopAutoScroll()
{
#if !APPLE_CHANGES
disconnect(&d->m_scrollTimer, SIGNAL( timeout() ), this, SLOT( slotAutoScroll() ));
if (d->m_scrollTimer.isActive())
d->m_scrollTimer.stop();
#endif
}
void KHTMLPart::slotAutoScroll()
{
if (d->m_view)
d->m_view->doAutoScroll();
else
stopAutoScroll(); }
void KHTMLPart::selectAll()
{
if(!d->m_doc) return;
NodeImpl *first;
if (d->m_doc->isHTMLDocument())
first = static_cast<HTMLDocumentImpl*>(d->m_doc)->body();
else
first = d->m_doc;
NodeImpl *next;
while ( first && !((first->nodeType() == Node::TEXT_NODE || first->nodeType() == Node::CDATA_SECTION_NODE) && first->renderer()) )
{
next = first->firstChild();
if ( !next ) next = first->nextSibling();
while( first && !next )
{
first = first->parentNode();
if ( first )
next = first->nextSibling();
}
first = next;
}
NodeImpl *last;
if (d->m_doc->isHTMLDocument())
last = static_cast<HTMLDocumentImpl*>(d->m_doc)->body();
else
last = d->m_doc;
while ( last && !((last->nodeType() == Node::TEXT_NODE || last->nodeType() == Node::CDATA_SECTION_NODE) && last->renderer()) )
{
next = last->lastChild();
if ( !next ) next = last->previousSibling();
while ( last && !next )
{
last = last->parentNode();
if ( last )
next = last->previousSibling();
}
last = next;
}
if ( !first || !last )
return;
Q_ASSERT(first->renderer());
Q_ASSERT(last->renderer());
d->m_selectionStart = first;
d->m_startOffset = 0;
d->m_selectionEnd = last;
d->m_endOffset = last->nodeValue().length();
d->m_startBeforeEnd = true;
d->m_doc->setSelection( d->m_selectionStart.handle(), d->m_startOffset,
d->m_selectionEnd.handle(), d->m_endOffset );
emitSelectionChanged();
}
#if !APPLE_CHANGES
bool KHTMLPart::checkLinkSecurity(const KURL &linkURL,const QString &message, const QString &button)
{
QString linkProto = linkURL.protocol().lower();
QString proto = m_url.protocol().lower();
if ( !linkProto.isEmpty() && !proto.isEmpty() &&
( linkProto == "cgi" || linkProto == "file" ) &&
proto != "file" && proto != "cgi" && proto != "man" && proto != "about")
{
Tokenizer *tokenizer = d->m_doc->tokenizer();
if (tokenizer)
tokenizer->setOnHold(true);
int response = KMessageBox::Cancel;
if (!message.isEmpty())
{
response = KMessageBox::warningContinueCancel( 0,
message.arg(linkURL.url()),
i18n( "Security Warning" ),
button);
}
else
{
KMessageBox::error( 0,
i18n( "<qt>This untrusted page contains a link<BR><B>%1</B><BR>to your local file system.").arg(linkURL.url()),
i18n( "Security Alert" ));
}
if (tokenizer)
tokenizer->setOnHold(false);
return (response==KMessageBox::Continue);
}
return true;
}
#endif
QVariant KHTMLPart::executeScript(QString filename, int baseLine, const DOM::Node &n, const QString &script)
{
#ifdef KJS_VERBOSE
kdDebug(6070) << "executeScript: filename=" << filename << " baseLine=" << baseLine << " script=" << script << endl;
#endif
KJSProxy *proxy = jScript();
if (!proxy || proxy->paused())
return QVariant();
QVariant ret = proxy->evaluate(filename,baseLine,script, n );
DocumentImpl::updateDocumentsRendering();
return ret;
}
void KHTMLPart::slotPartRemoved( KParts::Part *part )
{
if ( part == d->m_activeFrame )
d->m_activeFrame = 0L;
}
#if !APPLE_CHANGES
void KHTMLPart::slotActiveFrameChanged( KParts::Part *part )
{
if ( part == this )
{
kdError(6050) << "strange error! we activated ourselves" << endl;
assert( false );
return;
}
if ( d->m_activeFrame && d->m_activeFrame->widget() && d->m_activeFrame->widget()->inherits( "QFrame" ) )
{
QFrame *frame = static_cast<QFrame *>( d->m_activeFrame->widget() );
if (frame->frameStyle() != QFrame::NoFrame)
{
frame->setFrameStyle( QFrame::StyledPanel | QFrame::Sunken);
frame->repaint();
}
}
d->m_activeFrame = part;
if ( d->m_activeFrame && d->m_activeFrame->widget()->inherits( "QFrame" ) )
{
QFrame *frame = static_cast<QFrame *>( d->m_activeFrame->widget() );
if (frame->frameStyle() != QFrame::NoFrame)
{
frame->setFrameStyle( QFrame::StyledPanel | QFrame::Plain);
frame->repaint();
}
kdDebug(6050) << "new active frame " << d->m_activeFrame << endl;
}
updateActions();
d->m_extension->setExtensionProxy( KParts::BrowserExtension::childObject( d->m_activeFrame ) );
}
#endif
void KHTMLPart::setActiveNode(const DOM::Node &node)
{
if (!d->m_doc || !d->m_view)
return;
d->m_doc->setFocusNode(node.handle());
QRect rect = node.handle()->getRect();
d->m_view->ensureVisible(rect.right(), rect.bottom());
d->m_view->ensureVisible(rect.left(), rect.top());
}
DOM::Node KHTMLPart::activeNode() const
{
return DOM::Node(d->m_doc?d->m_doc->focusNode():0);
}
DOM::EventListener *KHTMLPart::createHTMLEventListener( QString code )
{
KJSProxy *proxy = jScript();
if (!proxy)
return 0;
return proxy->createHTMLEventHandler( m_url.url(), code );
}
KHTMLPart *KHTMLPart::opener()
{
return d->m_opener;
}
void KHTMLPart::setOpener(KHTMLPart *_opener)
{
d->m_opener = _opener;
}
bool KHTMLPart::openedByJS()
{
return d->m_openedByJS;
}
void KHTMLPart::setOpenedByJS(bool _openedByJS)
{
d->m_openedByJS = _openedByJS;
}
void KHTMLPart::preloadStyleSheet(const QString &url, const QString &stylesheet)
{
khtml::Cache::preloadStyleSheet(url, stylesheet);
}
void KHTMLPart::preloadScript(const QString &url, const QString &script)
{
khtml::Cache::preloadScript(url, script);
}
#if !APPLE_CHANGES
QCString KHTMLPart::dcopObjectId() const
{
QCString id;
id.sprintf("html-widget%d", d->m_dcop_counter);
return id;
}
#endif
long KHTMLPart::cacheId() const
{
return d->m_cacheId;
}
bool KHTMLPart::restored() const
{
return d->m_restored;
}
void KHTMLPart::incrementFrameCount()
{
frameCount++;
if (parentPart()) {
parentPart()->incrementFrameCount();
}
}
void KHTMLPart::decrementFrameCount()
{
frameCount--;
if (parentPart()) {
parentPart()->decrementFrameCount();
}
}
int KHTMLPart::topLevelFrameCount()
{
if (parentPart()) {
return parentPart()->topLevelFrameCount();
}
return frameCount;
}
bool KHTMLPart::tabsToLinks() const
{
return true;
}
bool KHTMLPart::tabsToAllControls() const
{
return true;
}
using namespace KParts;
#include "khtml_part.moc"