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

📄 loader.cpp

📁 khtml在gtk上的移植版本
💻 CPP
📖 第 1 页 / 共 4 页
字号:
/*    This file is part of the KDE libraries    Copyright (C) 1998 Lars Knoll (knoll@mpi-hd.mpg.de)    Copyright (C) 2001 Dirk Mueller (mueller@kde.org)    Copyright (C) 2002 Waldo Bastian (bastian@kde.org)    Copyright (C) 2003 Apple Computer, Inc.    This library is free software; you can redistribute it and/or    modify it under the terms of the GNU Library General Public    License as published by the Free Software Foundation; either    version 2 of the License, or (at your option) any later version.    This library is distributed in the hope that it will be useful,    but WITHOUT ANY WARRANTY; without even the implied warranty of    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU    Library General Public License for more details.    You should have received a copy of the GNU Library General Public License    along with this library; see the file COPYING.LIB.  If not, write to    the Free Software Foundation, Inc., 59 Temple Place - Suite 330,    Boston, MA 02111-1307, USA.    This class provides all functionality needed for loading images, style sheets and html    pages from the web. It has a memory cache for these objects.*/#undef CACHE_DEBUG//#define CACHE_DEBUG#include <assert.h>#include "loader.h"// up to which size is a picture for sure cacheable#define MAXCACHEABLE 40*1024// default cache size#define DEFCACHESIZE 4096*1024#include <qasyncio.h>#include <qasyncimageio.h>#include <qpainter.h>#include <qbitmap.h>#include <qmovie.h>#include <kio/job.h>#include <kio/jobclasses.h>#include <kglobal.h>#include <kimageio.h>#include <kcharsets.h>#include <kiconloader.h>#include <scheduler.h>#include <kdebug.h>#include "khtml_factory.h"#include "khtml_part.h"#include "html/html_documentimpl.h"#include "css/css_stylesheetimpl.h"#ifndef KHTML_NO_XBL#include "xbl/xbl_docimpl.h"#endif#if APPLE_CHANGES#include "KWQAssertions.h"#include "KWQLoader.h"#endifusing namespace khtml;using namespace DOM;#if APPLE_CHANGESstatic bool cacheDisabled;#endif// Call this "walker" instead of iterator so people won't expect Qt or STL-style iterator interface.// Just keep calling next() on this. It's safe from deletions of the current itemclass CachedObjectClientWalker {public:    CachedObjectClientWalker(const QPtrDict<CachedObjectClient> &clients) : _current(0), _iterator(clients) { }    CachedObjectClient *next();private:    CachedObjectClient *_current;    QPtrDictIterator<CachedObjectClient> _iterator;};CachedObject::~CachedObject(){    if(m_deleted) abort();    Cache::removeFromLRUList(this);    m_deleted = true;#if APPLE_CHANGES    KWQReleaseResponse(m_response);#endif}void CachedObject::finish(){    if( m_size > MAXCACHEABLE )        m_status = Uncacheable;    else        m_status = Cached;    KURL url(m_url.string());    if (m_expireDateChanged && url.protocol().startsWith("http"))    {        m_expireDateChanged = false;        KIO::http_update_cache(url, false, m_expireDate);#ifdef CACHE_DEBUG        kdDebug(6060) << " Setting expire date for image "<<m_url.string()<<" to " << m_expireDate << endl;#endif    }#ifdef CACHE_DEBUG    else kdDebug(6060) << " No expire date for image "<<m_url.string()<<endl;#endif}void CachedObject::setExpireDate(time_t _expireDate, bool changeHttpCache){    if ( _expireDate == m_expireDate)        return;    if (m_status == Uncacheable || m_status == Cached)    {        finish();    }    m_expireDate = _expireDate;    if (changeHttpCache && m_expireDate)       m_expireDateChanged = true;}bool CachedObject::isExpired() const{    if (!m_expireDate) return false;    time_t now = time(0);    return (difftime(now, m_expireDate) >= 0);}#if APPLE_CHANGESvoid CachedObject::setResponse(KWIQResponse *response){    KWQRetainResponse(response);    KWQReleaseResponse(m_response);    m_response = response;}#endifvoid CachedObject::setRequest(Request *_request){    if ( _request && !m_request )        m_status = Pending;    m_request = _request;    if (canDelete() && m_free)        delete this;    else if (allowInLRUList())        Cache::insertInLRUList(this);}void CachedObject::ref(CachedObjectClient *c){    m_clients.insert(c, c);    Cache::removeFromLRUList(this);    increaseAccessCount();}void CachedObject::deref(CachedObjectClient *c){    m_clients.remove(c);    if (allowInLRUList())        Cache::insertInLRUList(this);}void CachedObject::setSize(int size){    bool sizeChanged = Cache::adjustSize(this, size - m_size);    // The object must now be moved to a different queue, since its size has been changed.    if (sizeChanged && allowInLRUList())        Cache::removeFromLRUList(this);    m_size = size;        if (sizeChanged && allowInLRUList())        Cache::insertInLRUList(this);}// -------------------------------------------------------------------------------------------CachedCSSStyleSheet::CachedCSSStyleSheet(DocLoader* dl, const DOMString &url, KIO::CacheControl _cachePolicy, time_t _expireDate, const QString& charset)    : CachedObject(url, CSSStyleSheet, _cachePolicy, _expireDate){    // It's css we want.    setAccept( QString::fromLatin1("text/css") );    // load the file    Cache::loader()->load(dl, this, false);    m_loading = true;    bool b;    if(!charset.isEmpty())	m_codec = KGlobal::charsets()->codecForName(charset, b);    else        m_codec = QTextCodec::codecForName("iso8859-1");}CachedCSSStyleSheet::CachedCSSStyleSheet(const DOMString &url, const QString &stylesheet_data)    : CachedObject(url, CSSStyleSheet, KIO::CC_Verify, 0, stylesheet_data.length()){    m_loading = false;    m_status = Persistent;    m_codec = 0;    m_sheet = DOMString(stylesheet_data);}CachedCSSStyleSheet::~CachedCSSStyleSheet(){}void CachedCSSStyleSheet::ref(CachedObjectClient *c){    CachedObject::ref(c);    if(!m_loading) c->setStyleSheet( m_url, m_sheet );}void CachedCSSStyleSheet::deref(CachedObjectClient *c){    Cache::flush();    CachedObject::deref(c);    if ( canDelete() && m_free )      delete this;}void CachedCSSStyleSheet::data( QBuffer &buffer, bool eof ){    if(!eof) return;    buffer.close();    setSize(buffer.buffer().size());    QString data = m_codec->toUnicode( buffer.buffer().data(), size() );    m_sheet = DOMString(data);    m_loading = false;    checkNotify();}void CachedCSSStyleSheet::checkNotify(){    if(m_loading) return;#ifdef CACHE_DEBUG    kdDebug( 6060 ) << "CachedCSSStyleSheet:: finishedLoading " << m_url.string() << endl;#endif    CachedObjectClientWalker w(m_clients);    while (CachedObjectClient *c = w.next())        c->setStyleSheet(m_url, m_sheet);}void CachedCSSStyleSheet::error( int /*err*/, const char */*text*/ ){    m_loading = false;    checkNotify();}// -------------------------------------------------------------------------------------------CachedScript::CachedScript(DocLoader* dl, const DOMString &url, KIO::CacheControl _cachePolicy, time_t _expireDate, const QString& charset)    : CachedObject(url, Script, _cachePolicy, _expireDate){    // It's javascript we want.    // But some websites think their scripts are <some wrong mimetype here>    // and refuse to serve them if we only accept application/x-javascript.    setAccept( QString::fromLatin1("*/*") );    // load the file    Cache::loader()->load(dl, this, false);    m_loading = true;    bool b;    if(!charset.isEmpty())        m_codec = KGlobal::charsets()->codecForName(charset, b);    else	m_codec = QTextCodec::codecForName("iso8859-1");}CachedScript::CachedScript(const DOMString &url, const QString &script_data)    : CachedObject(url, Script, KIO::CC_Verify, 0, script_data.length()){    m_loading = false;    m_status = Persistent;    m_codec = 0;    m_script = DOMString(script_data);}CachedScript::~CachedScript(){}void CachedScript::ref(CachedObjectClient *c){    CachedObject::ref(c);    if(!m_loading) c->notifyFinished(this);}void CachedScript::deref(CachedObjectClient *c){    Cache::flush();    CachedObject::deref(c);    if ( canDelete() && m_free )      delete this;}void CachedScript::data( QBuffer &buffer, bool eof ){    if(!eof) return;    buffer.close();    setSize(buffer.buffer().size());    QString data = m_codec->toUnicode( buffer.buffer().data(), size() );    m_script = DOMString(data);    m_loading = false;    checkNotify();}void CachedScript::checkNotify(){    if(m_loading) return;    CachedObjectClientWalker w(m_clients);    while (CachedObjectClient *c = w.next())        c->notifyFinished(this);}void CachedScript::error( int /*err*/, const char */*text*/ ){    m_loading = false;    checkNotify();}// ------------------------------------------------------------------------------------------#if !APPLE_CHANGES namespace khtml{    class ImageSource : public QDataSource    {    public:        ImageSource(QByteArray buf);        /**         * Overload QDataSource::readyToSend() and returns the number         * of bytes ready to send if not eof instead of returning -1.         */        int readyToSend();        /*!          Reads and sends a block of data.        */        void sendTo(QDataSink*, int count);        /**         * Sets the EOF state.         */        void setEOF( bool state );        /*!          KHTMLImageSource's is rewindable.        */        bool rewindable() const;        /*!          Enables rewinding.  No special action is taken.        */        void enableRewind(bool on);        /*          Calls reset() on the QIODevice.        */        void rewind();        /*          Indicates that the buffered data is no longer          needed.        */        void cleanBuffer();        QByteArray buffer;        unsigned int pos;    private:        bool eof     : 1;        bool rew     : 1;        bool rewable : 1;    };}ImageSource::ImageSource(QByteArray buf){  buffer = buf;  rew = false;  pos = 0;  eof = false;  rewable = true;}int ImageSource::readyToSend(){    if(eof && pos == buffer.size())        return -1;    return  buffer.size() - pos;}void ImageSource::sendTo(QDataSink* sink, int n){    sink->receive((const uchar*)&buffer.at(pos), n);    pos += n;    // buffer is no longer needed    if(eof && pos == buffer.size() && !rewable)    {        buffer.resize(0);        pos = 0;    }}void ImageSource::setEOF( bool state ){    eof = state;#if KWIQ    if (eof)	QDataSource::eof();#endif    }// ImageSource's is rewindable.bool ImageSource::rewindable() const{    return rewable;}// Enables rewinding.  No special action is taken.void ImageSource::enableRewind(bool on){    rew = on;}// Calls reset() on the QIODevice.void ImageSource::rewind(){    pos = 0;    if (!rew) {        QDataSource::rewind();    } else        ready();}void ImageSource::cleanBuffer(){    // if we need to be able to rewind, buffer is needed    if(rew)        return;    rewable = false;    // buffer is no longer needed    if(eof && pos == buffer.size())    {        buffer.resize(0);        pos = 0;    }}static QString buildAcceptHeader(){    QString result = KImageIO::mimeTypes( KImageIO::Reading ).join(", ");    if (result.right(2) == ", ")        result = result.left(result.length()-2);    return result;}#endif // APPLE_CHANGESstatic bool crossDomain(const QString &a, const QString &b){    if (a == b) return false;    QStringList l1 = QStringList::split('.', a);    QStringList l2 = QStringList::split('.', b);    while(l1.count() > l2.count())        l1.pop_front();    while(l2.count() > l1.count())        l2.pop_front();    while(l2.count() >= 2)    {        if (l1 == l2)           return false;        l1.pop_front();        l2.pop_front();    }    return true;}// -------------------------------------------------------------------------------------CachedImage::CachedImage(DocLoader* dl, const DOMString &url, KIO::CacheControl _cachePolicy, time_t _expireDate)    : QObject(), CachedObject(url, Image, _cachePolicy, _expireDate)#if APPLE_CHANGES    , m_dataSize(0)#endif{#if KWIQ    QOBJECT_TYPE(khtml::CachedImage);#endif#if !APPLE_CHANGES    static const QString &acceptHeader = KGlobal::staticQString( buildAcceptHeader() );#endif    m = 0;    p = 0;    pixPart = 0;    bg = 0;#if !APPLE_CHANGES || KWIQ    bgColor = qRgba( 0, 0, 0, 0xFF );    typeChecked = false;#endif    isFullyTransparent = false;    errorOccured = false;    monochrome = false;    formatType = 0;    m_status = Unknown;    imgSource = 0;    m_loading = true;#if !APPLE_CHANGES    setAccept( acceptHeader );#endif    m_showAnimations = dl->showAnimations();}CachedImage::~CachedImage(){    clear();}void CachedImage::ref( CachedObjectClient *c ){#ifdef CACHE_DEBUG    kdDebug( 6060 ) << this << " CachedImage::ref(" << c << ") " << endl;#endif    CachedObject::ref(c);    if( m ) {        m->unpause();        if( m->finished() || m_clients.count() == 1 )            m->restart();    }    // for mouseovers, dynamic changes    if (!valid_rect().isNull())

⌨️ 快捷键说明

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