📄 khtmlview.cpp.orig
字号:
{ m_part->xmlDocImpl()->prepareMouseEvent( false, xm, ym, &mev ); swallowEvent = dispatchMouseEvent(EventImpl::MOUSEUP_EVENT,mev.innerNode.handle(),mev.innerNonSharedNode.handle(),true, d->clickCount,_mouse,false,DOM::NodeImpl::MouseRelease); if (d->clickCount > 0 && QPoint(d->clickX-xm,d->clickY-ym).manhattanLength() <= QApplication::startDragDistance()) { QMouseEvent me(d->isDoubleClick ? QEvent::MouseButtonDblClick : QEvent::MouseButtonRelease, _mouse->pos(), _mouse->button(), _mouse->state()); dispatchMouseEvent(EventImpl::CLICK_EVENT, mev.innerNode.handle(),mev.innerNonSharedNode.handle(),true, d->clickCount, &me, true, DOM::NodeImpl::MouseRelease); } DOM::NodeImpl* fn = m_part->xmlDocImpl()->focusNode(); if (fn && fn != mev.innerNode.handle() && fn->renderer() && fn->renderer()->isWidget() && _mouse->button() != MidButton) { forwardPeripheralEvent(static_cast<khtml::RenderWidget*>(fn->renderer()), _mouse, xm, ym); } khtml::RenderObject* r = mev.innerNode.handle() ? mev.innerNode.handle()->renderer() : 0; if (r && r->isWidget()) _mouse->ignore(); } if (!swallowEvent) { khtml::MouseReleaseEvent event( _mouse, xm, ym, mev.url, mev.target, mev.innerNode ); QApplication::sendEvent( m_part, &event ); }}// returns true if event should be swallowedbool KHTMLView::dispatchKeyEvent( QKeyEvent *_ke ){ if (!m_part->xmlDocImpl()) return false; // Pressing and releasing a key should generate keydown, keypress and keyup events // Holding it down should generated keydown, keypress (repeatedly) and keyup events // The problem here is that Qt generates two autorepeat events (keyrelease+keypress) // for autorepeating, while DOM wants only one autorepeat event (keypress), so one // of the Qt events shouldn't be passed to DOM, but it should be still filtered // out if DOM would filter the autorepeat event. Additional problem is that Qt keyrelease // events don't have text() set (Qt bug?), so DOM often would ignore the keypress event // if it was created using Qt keyrelease, but Qt autorepeat keyrelease comes // before Qt autorepeat keypress (i.e. problem whether to filter it out or not). // The solution is to filter out and postpone the Qt autorepeat keyrelease until // the following Qt keypress event comes. If DOM accepts the DOM keypress event, // the postponed event will be simply discarded. If not, it will be passed to keyPressEvent() // again, and here it will be ignored. // // Qt: Press | Release(autorepeat) Press(autorepeat) etc. | Release // DOM: Down + Press | (nothing) Press | Up // It's also possible to get only Releases. E.g. the release of alt-tab, // or when the keypresses get captured by an accel. if( _ke == d->postponed_autorepeat ) // replayed event { return false; } if( _ke->type() == QEvent::KeyPress ) { if( !_ke->isAutoRepeat()) { bool ret = dispatchKeyEventHelper( _ke, false ); // keydown // don't send keypress even if keydown was blocked, like IE (and unlike Mozilla) if( !ret && dispatchKeyEventHelper( _ke, true )) // keypress ret = true; return ret; } else // autorepeat { bool ret = dispatchKeyEventHelper( _ke, true ); // keypress if( !ret && d->postponed_autorepeat ) keyPressEvent( d->postponed_autorepeat ); delete d->postponed_autorepeat; d->postponed_autorepeat = NULL; return ret; } } else // QEvent::KeyRelease { // Discard postponed "autorepeat key-release" events that didn't see // a keypress after them (e.g. due to QAccel) if ( d->postponed_autorepeat ) { delete d->postponed_autorepeat; d->postponed_autorepeat = 0; } if( !_ke->isAutoRepeat()) { return dispatchKeyEventHelper( _ke, false ); // keyup } else { d->postponed_autorepeat = new QKeyEvent( _ke->type(), _ke->key(), _ke->ascii(), _ke->state(), _ke->text(), _ke->isAutoRepeat(), _ke->count()); if( _ke->isAccepted()) d->postponed_autorepeat->accept(); else d->postponed_autorepeat->ignore(); return true; } }}// returns true if event should be swallowedbool KHTMLView::dispatchKeyEventHelper( QKeyEvent *_ke, bool keypress ){ DOM::NodeImpl* keyNode = m_part->xmlDocImpl()->focusNode(); if (keyNode) { return keyNode->dispatchKeyEvent(_ke, keypress); } else { // no focused node, send to document return m_part->xmlDocImpl()->dispatchKeyEvent(_ke, keypress); }}void KHTMLView::keyPressEvent( QKeyEvent *_ke ){#ifndef KHTML_NO_TYPE_AHEAD_FIND if(d->typeAheadActivated) { // type-ahead find aka find-as-you-type if(_ke->key() == Key_BackSpace) { d->findString = d->findString.left(d->findString.length() - 1); if(!d->findString.isEmpty()) { findAhead(false); } else { findTimeout(); } d->timer.start(3000, true); _ke->accept(); return; } else if(_ke->key() == Key_Escape) { findTimeout(); _ke->accept(); return; } else if(_ke->key() == Key_Space || !_ke->text().stripWhiteSpace().isEmpty()) { d->findString += _ke->text(); findAhead(true); d->timer.start(3000, true); _ke->accept(); return; } }#endif // KHTML_NO_TYPE_AHEAD_FIND#ifndef KHTML_NO_CARET if (m_part->isEditable() || m_part->isCaretMode() || (m_part->xmlDocImpl() && m_part->xmlDocImpl()->focusNode() && m_part->xmlDocImpl()->focusNode()->contentEditable())) { d->caretViewContext()->keyReleasePending = true; caretKeyPressEvent(_ke); return; }#endif // KHTML_NO_CARET // If CTRL was hit, be prepared for access keys if (d->accessKeysEnabled && _ke->key() == Key_Control && _ke->state()==0 && !d->accessKeysActivated) { d->accessKeysPreActivate=true; _ke->accept(); return; } if (_ke->key() == Key_Shift && _ke->state()==0) d->scrollSuspendPreActivate=true; // accesskey handling needs to be done before dispatching, otherwise e.g. lineedits // may eat the event if (d->accessKeysEnabled && d->accessKeysActivated) { int state = ( _ke->state() & ( ShiftButton | ControlButton | AltButton | MetaButton )); if ( state==0 || state==ShiftButton) { if (_ke->key() != Key_Shift) accessKeysTimeout(); handleAccessKey( _ke ); _ke->accept(); return; } accessKeysTimeout(); } if ( dispatchKeyEvent( _ke )) { // If either keydown or keypress was accepted by a widget, or canceled by JS, stop here. _ke->accept(); return; } int offs = (clipper()->height() < 30) ? clipper()->height() : 30; if (_ke->state() & Qt::ShiftButton) switch(_ke->key()) { case Key_Space: if ( d->vmode == QScrollView::AlwaysOff ) _ke->accept(); else { scrollBy( 0, -clipper()->height() + offs ); if(d->scrollSuspended) d->newScrollTimer(this, 0); } break; case Key_Down: case Key_J: d->adjustScroller(this, KHTMLViewPrivate::ScrollDown, KHTMLViewPrivate::ScrollUp); break; case Key_Up: case Key_K: d->adjustScroller(this, KHTMLViewPrivate::ScrollUp, KHTMLViewPrivate::ScrollDown); break; case Key_Left: case Key_H: d->adjustScroller(this, KHTMLViewPrivate::ScrollLeft, KHTMLViewPrivate::ScrollRight); break; case Key_Right: case Key_L: d->adjustScroller(this, KHTMLViewPrivate::ScrollRight, KHTMLViewPrivate::ScrollLeft); break; } else switch ( _ke->key() ) { case Key_Down: case Key_J: if ( d->vmode == QScrollView::AlwaysOff ) _ke->accept(); else { if (!d->scrollTimerId || d->scrollSuspended) scrollBy( 0, 10 ); if (d->scrollTimerId) d->newScrollTimer(this, 0); } break; case Key_Space: case Key_Next: if ( d->vmode == QScrollView::AlwaysOff ) _ke->accept(); else { scrollBy( 0, clipper()->height() - offs ); if(d->scrollSuspended) d->newScrollTimer(this, 0); } break; case Key_Up: case Key_K: if ( d->vmode == QScrollView::AlwaysOff ) _ke->accept(); else { if (!d->scrollTimerId || d->scrollSuspended) scrollBy( 0, -10 ); if (d->scrollTimerId) d->newScrollTimer(this, 0); } break; case Key_Prior: if ( d->vmode == QScrollView::AlwaysOff ) _ke->accept(); else { scrollBy( 0, -clipper()->height() + offs ); if(d->scrollSuspended) d->newScrollTimer(this, 0); } break; case Key_Right: case Key_L: if ( d->hmode == QScrollView::AlwaysOff ) _ke->accept(); else { if (!d->scrollTimerId || d->scrollSuspended) scrollBy( 10, 0 ); if (d->scrollTimerId) d->newScrollTimer(this, 0); } break; case Key_Left: case Key_H: if ( d->hmode == QScrollView::AlwaysOff ) _ke->accept(); else { if (!d->scrollTimerId || d->scrollSuspended) scrollBy( -10, 0 ); if (d->scrollTimerId) d->newScrollTimer(this, 0); } break; case Key_Enter: case Key_Return: // ### FIXME: // or even better to HTMLAnchorElementImpl::event() if (m_part->xmlDocImpl()) { NodeImpl *n = m_part->xmlDocImpl()->focusNode(); if (n) n->setActive(); } break; case Key_Home: if ( d->vmode == QScrollView::AlwaysOff ) _ke->accept(); else { setContentsPos( 0, 0 ); if(d->scrollSuspended) d->newScrollTimer(this, 0); } break; case Key_End: if ( d->vmode == QScrollView::AlwaysOff ) _ke->accept(); else { setContentsPos( 0, contentsHeight() - visibleHeight() ); if(d->scrollSuspended) d->newScrollTimer(this, 0); } break; case Key_Shift: // what are you doing here? _ke->ignore(); return; default: if (d->scrollTimerId) d->newScrollTimer(this, 0); _ke->ignore(); return; } _ke->accept();}void KHTMLView::findTimeout(){#ifndef KHTML_NO_TYPE_AHEAD_FIND d->typeAheadActivated = false; d->findString = ""; m_part->setStatusBarText(i18n("Find stopped."), KHTMLPart::BarDefaultText); m_part->enableFindAheadActions( true );#endif // KHTML_NO_TYPE_AHEAD_FIND}#ifndef KHTML_NO_TYPE_AHEAD_FINDvoid KHTMLView::startFindAhead( bool linksOnly ){ if( linksOnly ) { d->findLinksOnly = true; m_part->setStatusBarText(i18n("Starting -- find links as you type"), KHTMLPart::BarDefaultText); } else { d->findLinksOnly = false; m_part->setStatusBarText(i18n("Starting -- find text as you type"), KHTMLPart::BarDefaultText); } m_part->findTextBegin(); d->typeAheadActivated = true; // disable, so that the shortcut ( / or ' by default ) doesn't interfere m_part->enableFindAheadActions( false ); d->timer.start(3000, true);}void KHTMLView::findAhead(bool increase){ QString status; if(d->findLinksOnly) { m_part->findText(d->findString, KHTMLPart::FindNoPopups | KHTMLPart::FindLinksOnly, this); if(m_part->findTextNext()) { status = i18n("Link found: \"%1\"."); } else { if(increase) KNotifyClient::beep(); status = i18n("Link not found: \"%1\"."); } } else { m_part->findText(d->findString, KHTMLPart::FindNoPopups, this); if(m_part->findTextNext()) { status = i18n("Text found: \"%1\"."); } else { if(increase) KNotifyClient::beep(); status = i18n("Text not found: \"%1\"."); }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -