📄 khtmlview.cpp
字号:
if (scrollTo(nextRect)) { if (!nextTarget) { if (m_part->xmlDocImpl()->focusNode()) m_part->xmlDocImpl()->setFocusNode(0); d->borderTouched = false; return false; } else { HTMLAnchorElementImpl *anchor = 0; if ( ( nextTarget->id() == ID_A || nextTarget->id() == ID_AREA ) ) anchor = static_cast<HTMLAnchorElementImpl *>( nextTarget ); if (anchor && !anchor->areaHref().isNull()) m_part->overURL(anchor->areaHref().string(), 0); else m_part->overURL(QString(), 0); kdDebug(6000)<<"reached link:"<<nextTarget->nodeName().string()<<endl; m_part->xmlDocImpl()->setFocusNode(nextTarget); emit m_part->nodeActivated(Node(nextTarget)); } } return true;}bool KHTMLView::gotoNextLink(){ return gotoLink(true); }bool KHTMLView::gotoPrevLink(){ return gotoLink(false); }void KHTMLView::print(){ if(!m_part->xmlDocImpl()) return; khtml::RenderRoot *root = static_cast<khtml::RenderRoot *>(m_part->xmlDocImpl()->renderer()); if(!root) return; KPrinter *printer = new KPrinter; if(printer->setup(this)) { QApplication::setOverrideCursor( waitCursor ); // set up KPrinter printer->setFullPage(false); printer->setCreator("KDE 2.1 HTML Library"); QString docname = m_part->xmlDocImpl()->URL().string(); if ( !docname.isEmpty() ) printer->setDocName(docname); QPainter *p = new QPainter; p->begin( printer ); khtml::setPrintPainter( p ); m_part->xmlDocImpl()->setPaintDevice( printer ); QPaintDeviceMetrics metrics( printer ); // this is a simple approximation... we layout the document // according to the width of the page, then just cut // pages without caring about the content. We should do better // in the future, but for the moment this is better than no // printing support kdDebug(6000) << "printing: physical page width = " << metrics.width() << " height = " << metrics.height() << endl; root->setPrintingMode(true); root->setWidth(metrics.width()); QValueList<int> oldSizes = m_part->fontSizes(); const int printFontSizes[] = { 6, 7, 8, 10, 12, 14, 18, 24, 28, 34, 40, 48, 56, 68, 82, 100, 0 }; QValueList<int> fontSizes; for ( int i = 0; printFontSizes[i] != 0; i++ ) fontSizes << printFontSizes[ i ]; m_part->setFontSizes(fontSizes); m_part->xmlDocImpl()->applyChanges(); root->updateSize(); // ok. now print the pages. kdDebug(6000) << "printing: html page width = " << root->docWidth() << " height = " << root->docHeight() << endl; kdDebug(6000) << "printing: margins left = " << printer->margins().width() << " top = " << printer->margins().height() << endl; kdDebug(6000) << "printing: paper width = " << metrics.width() << " height = " << metrics.height() << endl; // if the width is too large to fit on the paper we just scale // the whole thing. int pageHeight = metrics.height(); int pageWidth = metrics.width(); // We print the bottom 'overlap' units again at the top of the next page. int overlap = 30; p->setClipRect(0,0, pageWidth, pageHeight); if(root->docWidth() > metrics.width()) { double scale = ((double) metrics.width())/((double) root->docWidth());#ifndef QT_NO_TRANSFORMATIONS p->scale(scale, scale);#endif pageHeight = (int) (pageHeight/scale); pageWidth = (int) (pageWidth/scale); overlap = (int) (overlap/scale); } kdDebug(6000) << "printing: scaled html width = " << pageWidth << " height = " << pageHeight << endl; int top = 0; while(top < root->docHeight()) { if(top > 0) printer->newPage(); root->print(p, 0, top, pageWidth, pageHeight, 0, 0); p->translate(0,-(pageHeight-overlap)); if (top + pageHeight >= root->docHeight()) break; // Stop if we have printed everything top += (pageHeight-overlap); } p->end(); delete p; // and now reset the layout to the usual one... root->setPrintingMode(false); khtml::setPrintPainter( 0 ); m_part->xmlDocImpl()->setPaintDevice( this ); m_part->setFontSizes(oldSizes); m_part->xmlDocImpl()->applyChanges(); QApplication::restoreOverrideCursor(); } delete printer;}void KHTMLView::slotPaletteChanged(){ if(!m_part->xmlDocImpl()) return; DOM::DocumentImpl *document = m_part->xmlDocImpl(); if (!document->isHTMLDocument()) return; khtml::RenderRoot *root = static_cast<khtml::RenderRoot *>(document->renderer()); if(!root) return; root->style()->resetPalette(); NodeImpl *body = static_cast<HTMLDocumentImpl*>(document)->body(); if(!body) return; body->setChanged(true); body->applyChanges();}void KHTMLView::paint(QPainter *p, const QRect &rc, int yOff, bool *more){ if(!m_part->xmlDocImpl()) return; khtml::RenderRoot *root = static_cast<khtml::RenderRoot *>(m_part->xmlDocImpl()->renderer()); if(!root) return; m_part->xmlDocImpl()->setPaintDevice(p->device()); root->setPrintingMode(true); root->setWidth(rc.width()); p->save(); p->setClipRect(rc); p->translate(rc.left(), rc.top()); double scale = ((double) rc.width()/(double) root->docWidth()); int height = (int) ((double) rc.height() / scale);#ifndef QT_NO_TRANSFORMATIONS p->scale(scale, scale);#endif root->print(p, 0, yOff, root->docWidth(), height, 0, 0); if (more) *more = yOff + height < root->docHeight(); p->restore(); root->setPrintingMode(false); m_part->xmlDocImpl()->setPaintDevice( this );}void KHTMLView::useSlowRepaints(){ kdDebug(0) << "slow repaints requested" << endl; d->useSlowRepaints = true; setStaticBackground(true);}void KHTMLView::setVScrollBarMode ( ScrollBarMode mode ){#ifndef KHTML_NO_SCROLLBARS d->vmode = mode; QScrollView::setVScrollBarMode(mode);#else Q_UNUSED( mode );#endif}void KHTMLView::setHScrollBarMode ( ScrollBarMode mode ){#ifndef KHTML_NO_SCROLLBARS d->hmode = mode; QScrollView::setHScrollBarMode(mode);#else Q_UNUSED( mode );#endif}void KHTMLView::restoreScrollBar ( ){ int ow = visibleWidth(); QScrollView::setVScrollBarMode(d->vmode); if (visibleWidth() != ow) { layout(); updateContents(contentsX(),contentsY(),visibleWidth(),visibleHeight()); } d->prevScrollbarVisible = verticalScrollBar()->isVisible();}void KHTMLView::toggleActLink(bool pressed){ ElementImpl *e = m_part->xmlDocImpl()->focusNode(); // ### FIXME: // move this code to HTMLAnchorElementImpl::setPressed(false), // or even better to HTMLAnchorElementImpl::event() if (!pressed && e && e==d->originalNode && (e->id()==ID_A || e->id()==ID_AREA)) { HTMLAnchorElementImpl *a = static_cast<HTMLAnchorElementImpl *>(e); emit m_part->urlSelected( a->areaHref().string(), LeftButton, 0, a->targetRef().string() ); } if (e) e->setActive(pressed);}QStringList KHTMLView::formCompletionItems(const QString &name) const{ if (!m_part->settings()->isFormCompletionEnabled()) return QStringList(); if (!d->formCompletions) d->formCompletions = new KSimpleConfig(locateLocal("data", "khtml/formcompletions")); return d->formCompletions->readListEntry(name);}void KHTMLView::addFormCompletionItem(const QString &name, const QString &value){ if (!m_part->settings()->isFormCompletionEnabled()) return; // don't store values that are all numbers or just numbers with // dashes or spaces as those are likely credit card numbers or // something similar bool cc_number(true); for (int i = 0; i < value.length(); ++i) { QChar c(value[i]); if (!c.isNumber() && c != '-' && !c.isSpace()) { cc_number = false; break; } } if (cc_number) return; QStringList items = formCompletionItems(name); if (!items.contains(value)) items.prepend(value); while ((int)items.count() > m_part->settings()->maxFormCompletionItems()) items.remove(items.fromLast()); d->formCompletions->writeEntry(name, items);}void KHTMLView::dispatchMouseEvent(int eventId, DOM::NodeImpl *targetNode, bool cancelable, int detail,QMouseEvent *_mouse, bool setUnder, int mouseEventType){ if (d->underMouse) d->underMouse->deref(); d->underMouse = targetNode; if (d->underMouse) d->underMouse->ref(); int exceptioncode; int clientX, clientY; viewportToContents(_mouse->x(), _mouse->y(), clientX, clientY); int screenX = _mouse->globalX(); int screenY = _mouse->globalY(); int button = -1; switch (_mouse->button()) { case LeftButton: button = 0; break; case MidButton: button = 1; break; case RightButton: button = 2; break; default: break; } bool ctrlKey = (_mouse->state() & ControlButton); bool altKey = (_mouse->state() & AltButton); bool shiftKey = (_mouse->state() & ShiftButton); bool metaKey = false; // ### qt support? // Also send the DOMFOCUSIN_EVENT when clicking on a node (Niko) // usually done in setFocusNode() // Allow LMB, MMB and RMB (correct?)// if(button != -1 && targetNode)// {// UIEventImpl *ue = new UIEventImpl(EventImpl::DOMFOCUSIN_EVENT,// true,false,m_part->xmlDocImpl()->defaultView(),// 0);// ue->ref();// targetNode->dispatchEvent(ue,exceptioncode);// ue->deref();// } // mouseout/mouseover if (setUnder && (d->prevMouseX != clientX || d->prevMouseY != clientY)) { NodeImpl *oldUnder = 0; if (d->prevMouseX >= 0 && d->prevMouseY >= 0) { NodeImpl::MouseEvent mev( _mouse->stateAfter(), static_cast<NodeImpl::MouseEventType>(mouseEventType)); m_part->xmlDocImpl()->prepareMouseEvent( d->prevMouseX, d->prevMouseY, 0, 0, &mev ); oldUnder = mev.innerNode.handle(); } if (oldUnder != targetNode) { // send mouseout event to the old node if (oldUnder){ oldUnder->ref(); MouseEventImpl *me = new MouseEventImpl(EventImpl::MOUSEOUT_EVENT, true,true,m_part->xmlDocImpl()->defaultView(), 0,screenX,screenY,clientX,clientY, ctrlKey,altKey,shiftKey,metaKey, button,targetNode); me->ref(); oldUnder->dispatchEvent(me,exceptioncode); me->deref(); } // send mouseover event to the new node if (targetNode) { MouseEventImpl *me = new MouseEventImpl(EventImpl::MOUSEOVER_EVENT, true,true,m_part->xmlDocImpl()->defaultView(), 0,screenX,screenY,clientX,clientY, ctrlKey,altKey,shiftKey,metaKey, button,oldUnder); me->ref(); targetNode->dispatchEvent(me,exceptioncode); me->deref(); } if (oldUnder) oldUnder->deref(); } } if (targetNode) { // send the actual event MouseEventImpl *me = new MouseEventImpl(static_cast<EventImpl::EventId>(eventId), true,cancelable,m_part->xmlDocImpl()->defaultView(), detail,screenX,screenY,clientX,clientY, ctrlKey,altKey,shiftKey,metaKey, button,0); me->ref(); targetNode->dispatchEvent(me,exceptioncode); bool defaultHandled = me->defaultHandled(); me->deref(); // special case for HTML click & ondblclick handler if (eventId == EventImpl::CLICK_EVENT) { me = new MouseEventImpl(d->isDoubleClick ? EventImpl::KHTML_DBLCLICK_EVENT : EventImpl::KHTML_CLICK_EVENT, true,cancelable,m_part->xmlDocImpl()->defaultView(), detail,screenX,screenY,clientX,clientY, ctrlKey,altKey,shiftKey,metaKey, button,0); me->ref(); if (defaultHandled) me->setDefaultHandled(); targetNode->dispatchEvent(me,exceptioncode); me->deref(); } }}void KHTMLView::viewportWheelEvent(QWheelEvent* e){ if ( d->vmode == QScrollView::AlwaysOff ) e->accept(); else if ( !verticalScrollBar()->isVisible() && m_part->parentPart() ) { if ( m_part->parentPart()->view() ) m_part->parentPart()->view()->wheelEvent( e ); e->ignore(); } else QScrollView::viewportWheelEvent( e );}void KHTMLView::focusOutEvent( QFocusEvent *e ){ m_part->stopAutoScroll(); QScrollView::focusOutEvent( e );}// vim:ts=4:sw=4
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -