31 #include "khtmlview.moc" 36 #include <qx11info_x11.h> 39 #include "html/html_documentimpl.h" 40 #include "html/html_inlineimpl.h" 41 #include "html/html_formimpl.h" 42 #include "html/htmltokenizer.h" 44 #include "rendering/render_arena.h" 45 #include "rendering/render_canvas.h" 46 #include "rendering/render_frames.h" 47 #include "rendering/render_replaced.h" 48 #include "rendering/render_form.h" 49 #include "rendering/render_layer.h" 50 #include "rendering/render_line.h" 51 #include "rendering/render_table.h" 53 #define protected public 54 #include "rendering/render_text.h" 56 #include "xml/dom2_eventsimpl.h" 57 #include "css/cssstyleselector.h" 58 #include "misc/loader.h" 78 #include <QtGui/QBitmap> 79 #include <QtGui/QLabel> 80 #include <QtCore/QObject> 81 #include <QtGui/QPainter> 82 #include <QtCore/QHash> 83 #include <QtGui/QToolTip> 84 #include <QtCore/QString> 85 #include <QtGui/QTextDocument> 86 #include <QtCore/QTimer> 87 #include <QtCore/QAbstractEventDispatcher> 88 #include <QtCore/QVector> 89 #include <QtGui/QAbstractScrollArea> 90 #include <QtGui/QPrinter> 91 #include <QtGui/QPrintDialog> 99 #elif defined(Q_WS_WIN) 105 void dumpLineBoxes(RenderFlow *flow);
110 using namespace khtml;
131 class KHTMLViewPrivate {
135 enum PseudoFocusNodes {
141 enum StaticBackgroundState {
147 enum CompletedState {
154 : underMouse( 0 ), underMouseNonShared( 0 ), oldUnderMouse( 0 )
156 postponed_autorepeat = NULL;
157 scrollingFromWheelTimerId = 0;
161 vpolicy = Qt::ScrollBarAsNeeded;
162 hpolicy = Qt::ScrollBarAsNeeded;
164 prevScrollbarVisible =
true;
166 possibleTripleClick =
false;
167 emitCompletedAfterRepaint = CSNone;
168 cursorIconWidget = 0;
169 cursorIconType = KHTMLView::LINK_NORMAL;
170 m_mouseScrollTimer = 0;
171 m_mouseScrollIndicator = 0;
178 delete formCompletions;
179 delete postponed_autorepeat;
182 if (underMouseNonShared)
183 underMouseNonShared->deref();
185 oldUnderMouse->deref();
187 delete cursorIconWidget;
188 delete m_mouseScrollTimer;
189 delete m_mouseScrollIndicator;
196 if (underMouseNonShared)
197 underMouseNonShared->deref();
198 underMouseNonShared = 0;
200 oldUnderMouse->deref();
203 staticWidget = SBNone;
204 fixedObjectsCount = 0;
205 staticObjectsCount = 0;
206 tabMovePending =
false;
207 lastTabbingDirection =
true;
208 pseudoFocusNode = PFNone;
210 #ifndef KHTML_NO_SCROLLBARS 216 vpolicy = ScrollBarAlwaysOff;
217 hpolicy = ScrollBarAlwaysOff;
219 scrollBarMoved =
false;
220 contentsMoving =
false;
221 ignoreWheelEvents =
false;
222 scrollingFromWheel = QPoint(-1,-1);
231 isDoubleClick =
false;
232 scrollingSelf =
false;
233 delete postponed_autorepeat;
234 postponed_autorepeat = NULL;
238 scrollSuspended =
false;
239 scrollSuspendPreActivate =
false;
240 smoothScrolling =
false;
241 smoothScrollModeIsDefault =
true;
242 shouldSmoothScroll =
false;
243 smoothScrollMissedDeadlines = 0;
246 firstLayoutPending =
true;
248 firstRepaintPending =
true;
250 needsFullRepaint =
true;
252 layoutSchedulingEnabled =
true;
255 layoutAttemptCounter = 0;
256 scheduledLayoutCounter = 0;
257 updateRegion = QRegion();
258 m_dialogsAllowed =
true;
259 accessKeysActivated =
false;
260 accessKeysPreActivate =
false;
267 KHTMLGlobal::deref();
269 emitCompletedAfterRepaint = CSNone;
270 m_mouseEventsTarget = 0;
273 void newScrollTimer(
QWidget *view,
int tid)
276 view->killTimer(scrollTimerId);
278 scrollSuspended =
false;
280 enum ScrollDirection { ScrollLeft, ScrollRight, ScrollUp, ScrollDown };
282 void adjustScroller(
QWidget *view, ScrollDirection direction, ScrollDirection oppositedir)
284 static const struct {
int msec, pixels; } timings [] = {
285 {320,1}, {224,1}, {160,1}, {112,1}, {80,1}, {56,1}, {40,1},
286 {28,1}, {20,1}, {20,2}, {20,3}, {20,4}, {20,6}, {20,8}, {0,0}
288 if (!scrollTimerId ||
289 (static_cast<int>(scrollDirection) != direction &&
290 (static_cast<int>(scrollDirection) != oppositedir || scrollSuspended))) {
292 scrollBy = timings[scrollTiming].pixels;
293 scrollDirection = direction;
294 newScrollTimer(view, view->startTimer(timings[scrollTiming].msec));
295 }
else if (scrollDirection == direction &&
296 timings[scrollTiming+1].msec && !scrollSuspended) {
297 scrollBy = timings[++scrollTiming].pixels;
298 newScrollTimer(view, view->startTimer(timings[scrollTiming].msec));
299 }
else if (scrollDirection == oppositedir) {
301 scrollBy = timings[--scrollTiming].pixels;
302 newScrollTimer(view, view->startTimer(timings[scrollTiming].msec));
305 scrollSuspended =
false;
308 bool haveZoom()
const {
return zoomLevel != 100; }
310 void startScrolling()
312 smoothScrolling =
true;
314 shouldSmoothScroll =
false;
319 smoothScrollTimer.stop();
323 smoothScrolling =
false;
324 shouldSmoothScroll =
false;
327 void updateContentsXY()
329 contentsX = QApplication::isRightToLeft() ?
330 view->horizontalScrollBar()->maximum()-view->horizontalScrollBar()->value() : view->horizontalScrollBar()->value();
331 contentsY = view->verticalScrollBar()->value();
333 void scrollAccessKeys(
int dx,
int dy)
335 QList<QLabel*> wl = qFindChildren<QLabel*>(view->widget(),
"KHTMLAccessKey");
337 w->move( w->pos() + QPoint(dx, dy) );
340 void scrollExternalWidgets(
int dx,
int dy)
342 if (visibleWidgets.isEmpty())
345 QHashIterator<void*, QWidget*> it(visibleWidgets);
346 while (it.hasNext()) {
348 it.value()->move( it.value()->pos() + QPoint(dx, dy) );
352 NodeImpl *underMouse;
353 NodeImpl *underMouseNonShared;
354 NodeImpl *oldUnderMouse;
358 bool tabMovePending:1;
359 bool lastTabbingDirection:1;
360 PseudoFocusNodes pseudoFocusNode:3;
361 bool scrollBarMoved:1;
362 bool contentsMoving:1;
364 Qt::ScrollBarPolicy vpolicy;
365 Qt::ScrollBarPolicy hpolicy;
366 bool prevScrollbarVisible:1;
368 bool ignoreWheelEvents:1;
369 StaticBackgroundState staticWidget: 3;
370 int staticObjectsCount;
371 int fixedObjectsCount;
374 int borderX, borderY;
379 int clickX, clickY, clickCount;
385 int contentsX, contentsY;
387 QKeyEvent* postponed_autorepeat;
393 ScrollDirection scrollDirection :3;
394 bool scrollSuspended :1;
395 bool scrollSuspendPreActivate :1;
397 bool smoothScrolling :1;
398 bool smoothScrollModeIsDefault :1;
399 bool shouldSmoothScroll :1;
402 bool firstLayoutPending :1;
404 bool firstRepaintPending :1;
406 bool layoutSchedulingEnabled :1;
407 bool needsFullRepaint :1;
409 bool possibleTripleClick :1;
411 bool m_dialogsAllowed :1;
412 short smoothScrollMissedDeadlines;
414 int layoutAttemptCounter;
415 int scheduledLayoutCounter;
416 QRegion updateRegion;
417 QTimer smoothScrollTimer;
418 QTime smoothScrollStopwatch;
420 bool accessKeysEnabled;
421 bool accessKeysActivated;
422 bool accessKeysPreActivate;
423 CompletedState emitCompletedAfterRepaint;
426 KHTMLView::LinkCursor cursorIconType;
429 short m_mouseScroll_byX;
430 short m_mouseScroll_byY;
431 QPoint scrollingFromWheel;
432 int scrollingFromWheelTimerId;
433 QTimer *m_mouseScrollTimer;
434 QWidget *m_mouseScrollIndicator;
435 QPointer<QWidget> m_mouseEventsTarget;
440 #ifndef QT_NO_TOOLTIP 452 const QPoint &p, QRect &r, QString &s)
454 HTMLMapElementImpl* map;
455 if (img && img->document()->isHTMLDocument() &&
456 (map =
static_cast<HTMLDocumentImpl*
>(img->document())->getMap(img->imageMap()))) {
457 RenderObject::NodeInfo info(
true,
false);
458 RenderObject *rend = img->renderer();
460 if (!rend || !rend->absolutePosition(ax, ay))
463 bool inside = map->mapMouseEvent(p.x() - ax + scrollOfs.x(),
464 p.y() - ay + scrollOfs.y(), rend->contentWidth(),
465 rend->contentHeight(), info);
466 if (inside && info.URLElement()) {
467 HTMLAreaElementImpl *area =
static_cast<HTMLAreaElementImpl *
>(info.URLElement());
468 Q_ASSERT(area->id() == ID_AREA);
469 s = area->getAttribute(ATTR_TITLE).string();
470 QRegion reg = area->cachedRegion();
471 if (!s.isEmpty() && !reg.isEmpty()) {
472 r = reg.boundingRect();
483 switch ( e->type() ) {
484 case QEvent::ToolTip: {
485 QHelpEvent *he =
static_cast<QHelpEvent*
>(e);
486 QPoint p = he->pos();
488 DOM::NodeImpl *node =
d->underMouseNonShared;
491 if ( node->isElementNode() ) {
492 DOM::ElementImpl *e =
static_cast<DOM::ElementImpl*
>( node );
498 if (e->id() == ID_IMG && !e->getAttribute( ATTR_USEMAP ).isEmpty()) {
500 viewportToContents(QPoint(0, 0)), p, r, s);
503 s = e->getAttribute(ATTR_TITLE).string().trimmed();
506 region |= QRect( contentsToViewport( r.topLeft() ), r.size() );
507 if ( !s.isEmpty() ) {
508 QToolTip::showText( he->globalPos(),
509 Qt::convertFromPlainText( s, Qt::WhiteSpaceNormal ),
514 node = node->parentNode();
522 case QEvent::DragEnter:
523 case QEvent::DragMove:
524 case QEvent::DragLeave:
534 return QWidget::event(e);
535 case QEvent::StyleChange:
536 case QEvent::LayoutRequest: {
538 return QAbstractScrollArea::event(e);
540 case QEvent::PaletteChange:
541 slotPaletteChanged();
542 return QScrollArea::event(e);
544 return QScrollArea::event(e);
550 :
QScrollArea( parent ),
d( new KHTMLViewPrivate( this ) )
556 QScrollArea::setVerticalScrollBarPolicy(d->vpolicy);
557 QScrollArea::setHorizontalScrollBarPolicy(d->hpolicy);
560 widget()->setMouseTracking(
true);
568 DOM::DocumentImpl *doc = m_part->xmlDocImpl();
581 void KHTMLView::init()
585 setFrameStyle(QFrame::NoFrame);
586 setFocusPolicy(Qt::StrongFocus);
587 viewport()->setFocusProxy(
this);
596 setAcceptDrops(
true);
598 setWidget(
new QWidget(
this) );
599 widget()->setAttribute( Qt::WA_NoSystemBackground );
605 widget()->setAttribute( Qt::WA_OpaquePaintEvent );
607 verticalScrollBar()->setCursor( Qt::ArrowCursor );
608 horizontalScrollBar()->setCursor( Qt::ArrowCursor );
610 connect(&d->smoothScrollTimer, SIGNAL(
timeout()),
this, SLOT(scrollTick()));
613 void KHTMLView::resizeContentsToViewport()
615 QSize s = viewport()->size();
623 if (d->accessKeysEnabled && d->accessKeysActivated)
625 viewport()->unsetCursor();
626 if ( d->cursorIconWidget )
627 d->cursorIconWidget->hide();
628 if (d->smoothScrolling)
631 QAbstractEventDispatcher::instance()->unregisterTimers(
this);
634 QScrollArea::setHorizontalScrollBarPolicy(d->hpolicy);
635 QScrollArea::setVerticalScrollBarPolicy(d->vpolicy);
636 verticalScrollBar()->setEnabled(
false );
637 horizontalScrollBar()->setEnabled(
false );
643 QScrollArea::hideEvent(e);
648 QScrollArea::showEvent(e);
651 void KHTMLView::setMouseEventsTarget(
QWidget* w )
653 d->m_mouseEventsTarget = w;
656 QWidget* KHTMLView::mouseEventsTarget()
const 658 return d->m_mouseEventsTarget;
663 d->m_clipHolder = ch;
668 return d->m_clipHolder;
673 return widget() ? widget()->width() : 0;
678 return widget() ? widget()->height() : 0;
685 widget()->resize(w, h);
686 if (!widget()->isVisible())
702 if (
m_kwp->isRedirected()) {
704 if (RenderWidget* rw =
m_kwp->renderWidget()) {
705 int ret = rw->width()-rw->paddingLeft()-rw->paddingRight()-rw->borderLeft()-rw->borderRight();
706 if (verticalScrollBar()->isVisible()) {
707 ret -= verticalScrollBar()->sizeHint().width();
713 return viewport()->width();
718 if (
m_kwp->isRedirected()) {
720 if (RenderWidget* rw =
m_kwp->renderWidget()) {
721 int ret = rw->height()-rw->paddingBottom()-rw->paddingTop()-rw->borderTop()-rw->borderBottom();
722 if (horizontalScrollBar()->isVisible()) {
723 ret -= horizontalScrollBar()->sizeHint().height();
729 return viewport()->height();
734 horizontalScrollBar()->setValue( QApplication::isRightToLeft() ?
735 horizontalScrollBar()->maximum()-x : x );
736 verticalScrollBar()->setValue( y );
741 if (d->scrollTimerId)
742 d->newScrollTimer(
this, 0);
743 horizontalScrollBar()->setValue( horizontalScrollBar()->value()+x );
744 verticalScrollBar()->setValue( verticalScrollBar()->value()+y );
775 applyTransforms(x, y, w, h);
776 if (
m_kwp->isRedirected()) {
777 QPoint off =
m_kwp->absolutePos();
781 widget()->update(x, y, w, h);
791 applyTransforms(x, y, w, h);
792 if (
m_kwp->isRedirected()) {
793 QPoint off =
m_kwp->absolutePos();
797 widget()->repaint(x, y, w, h);
805 void KHTMLView::applyTransforms(
int& x,
int& y,
int& w,
int& h)
const 808 const int z = d->zoomLevel;
818 void KHTMLView::revertTransforms(
int& x,
int& y,
int& w,
int& h)
const 823 const int z = d->zoomLevel;
831 void KHTMLView::revertTransforms(
int& x,
int& y )
const 834 revertTransforms(x, y, dummy, dummy);
842 if (!m_part->xmlDocImpl())
843 resizeContentsToViewport();
846 if (m_part->xmlDocImpl() && m_part->xmlDocImpl()->styleSelector()->affectedByViewportChange()) {
847 m_part->xmlDocImpl()->updateStyleSelector();
850 if (d->layoutSchedulingEnabled)
853 QApplication::sendPostedEvents(viewport(), QEvent::Paint);
855 if ( m_part && m_part->xmlDocImpl() ) {
863 HTMLPartContainerElementImpl::sendPostedResizeEvents();
864 m_part->xmlDocImpl()->dispatchWindowEvent( EventImpl::RESIZE_EVENT,
false,
false );
876 if (!r.isValid() || r.isEmpty())
return;
878 QPainter p(widget());
882 p.scale( d->zoomLevel/100., d->zoomLevel/100.);
884 r.setX(r.x()*100/d->zoomLevel);
885 r.setY(r.y()*100/d->zoomLevel);
886 r.setWidth(r.width()*100/d->zoomLevel);
887 r.setHeight(r.height()*100/d->zoomLevel);
897 if(!m_part || !m_part->xmlDocImpl() || !m_part->xmlDocImpl()->renderer()) {
898 p.fillRect(ex, ey, ew, eh, palette().brush(QPalette::Active, QPalette::Base));
900 }
else if ( d->complete && static_cast<RenderCanvas*>(m_part->xmlDocImpl()->renderer())->needsLayout() ) {
902 unscheduleRelayout();
904 }
else if (m_part->xmlDocImpl()->tokenizer()) {
905 m_part->xmlDocImpl()->tokenizer()->setNormalYieldDelay();
909 kDebug( 6000 ) <<
"WARNING: paintEvent reentered! ";
910 kDebug( 6000 ) << kBacktrace();
915 m_part->xmlDocImpl()->renderer()->layer()->paint(&p, r);
917 if (d->hasFrameset) {
918 NodeImpl *body =
static_cast<HTMLDocumentImpl*
>(m_part->xmlDocImpl())->body();
919 if(body && body->renderer() && body->id() == ID_FRAMESET)
920 static_cast<RenderFrameSet*>(body->renderer())->paintFrameSetRules(&p, r);
922 d->hasFrameset =
false;
926 QApplication::sendEvent( m_part, &event );
928 if (d->contentsMoving && !d->smoothScrolling && widget()->underMouse()) {
929 QMouseEvent *tempEvent =
new QMouseEvent( QEvent::MouseMove, widget()->mapFromGlobal( QCursor::pos() ),
930 Qt::NoButton, Qt::NoButton, Qt::NoModifier );
931 QApplication::postEvent(widget(), tempEvent);
934 if (d->firstRepaintPending && !m_part->
parentPart()) {
937 d->firstRepaintPending =
false;
956 if( m_part && m_part->xmlDocImpl() ) {
957 DOM::DocumentImpl *document = m_part->xmlDocImpl();
959 khtml::RenderCanvas* canvas =
static_cast<khtml::RenderCanvas *
>(document->renderer());
960 if ( !canvas )
return;
962 d->layoutSchedulingEnabled=
false;
963 d->dirtyLayout =
true;
966 RenderObject *
ref = 0;
967 RenderObject* root = document->documentElement() ? document->documentElement()->renderer() : 0;
969 if (document->isHTMLDocument()) {
970 NodeImpl *body =
static_cast<HTMLDocumentImpl*
>(document)->body();
971 if(body && body->renderer() && body->id() == ID_FRAMESET) {
972 QScrollArea::setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
973 QScrollArea::setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
974 body->renderer()->setNeedsLayout(
true);
975 d->hasFrameset =
true;
978 ref = (!body || root->style()->hidesOverflow()) ? root : body->renderer();
983 if( ref->style()->overflowX() == OHIDDEN ) {
984 if (d->hpolicy == Qt::ScrollBarAsNeeded) QScrollArea::setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
985 }
else if (ref->style()->overflowX() == OSCROLL ) {
986 if (d->hpolicy == Qt::ScrollBarAsNeeded) QScrollArea::setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOn);
987 }
else if (horizontalScrollBarPolicy() != d->hpolicy) {
988 QScrollArea::setHorizontalScrollBarPolicy(d->hpolicy);
990 if ( ref->style()->overflowY() == OHIDDEN ) {
991 if (d->vpolicy == Qt::ScrollBarAsNeeded) QScrollArea::setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
992 }
else if (ref->style()->overflowY() == OSCROLL ) {
993 if (d->vpolicy == Qt::ScrollBarAsNeeded) QScrollArea::setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOn);
994 }
else if (verticalScrollBarPolicy() != d->vpolicy) {
995 QScrollArea::setVerticalScrollBarPolicy(d->vpolicy);
998 d->needsFullRepaint = d->firstLayoutPending;
1000 d->needsFullRepaint =
true;
1008 if (d->firstLayoutPending) {
1011 d->firstLayoutPending =
false;
1012 verticalScrollBar()->setEnabled(
true );
1013 horizontalScrollBar()->setEnabled(
true );
1017 if (d->accessKeysEnabled && d->accessKeysActivated) {
1025 if (d->layoutTimerId)
1026 killTimer(d->layoutTimerId);
1027 d->layoutTimerId = 0;
1028 d->layoutSchedulingEnabled=
true;
1031 void KHTMLView::closeChildDialogs()
1038 if ( dlgbase->testAttribute( Qt::WA_ShowModal ) ) {
1039 kDebug(6000) <<
"closeChildDialogs: closing dialog " << dlgbase;
1047 kWarning() <<
"closeChildDialogs: not a KDialog! Don't use QDialogs in KDE! " <<
static_cast<QWidget*
>(dlg);
1048 static_cast<QWidget*
>(dlg)->hide();
1051 d->m_dialogsAllowed =
false;
1054 bool KHTMLView::dialogsAllowed() {
1055 bool allowed = d->m_dialogsAllowed;
1058 allowed &= p->
view()->dialogsAllowed();
1064 closeChildDialogs();
1065 QScrollArea::closeEvent( ev );
1070 percent = percent < 20 ? 20 : (percent > 800 ? 800 : percent);
1071 int oldpercent = d->zoomLevel;
1072 d->zoomLevel = percent;
1073 if (percent != oldpercent) {
1074 if (d->layoutSchedulingEnabled)
1082 return d->zoomLevel;
1087 d->smoothScrollMode = m;
1088 d->smoothScrollModeIsDefault =
false;
1089 if (d->smoothScrolling && !m)
1096 if (!d->smoothScrollModeIsDefault)
1098 d->smoothScrollMode = m;
1099 if (d->smoothScrolling && !m)
1105 return d->smoothScrollMode;
1115 if (!m_part->xmlDocImpl())
return;
1116 if (d->possibleTripleClick && ( _mouse->button() & Qt::MouseButtonMask ) == Qt::LeftButton)
1122 int xm = _mouse->x();
1123 int ym = _mouse->y();
1124 revertTransforms(xm, ym);
1128 d->isDoubleClick =
false;
1130 DOM::NodeImpl::MouseEvent mev( _mouse->buttons(), DOM::NodeImpl::MousePress );
1131 m_part->xmlDocImpl()->prepareMouseEvent(
false, xm, ym, &mev );
1135 if ( (_mouse->button() == Qt::MidButton) &&
1137 mev.url.isNull() && (mev.innerNode.elementId() != ID_INPUT) ) {
1138 QPoint point = mapFromGlobal( _mouse->globalPos() );
1140 d->m_mouseScroll_byX = 0;
1141 d->m_mouseScroll_byY = 0;
1143 d->m_mouseScrollTimer =
new QTimer(
this );
1144 connect( d->m_mouseScrollTimer, SIGNAL(
timeout()),
this, SLOT(slotMouseScrollTimer()) );
1146 if ( !d->m_mouseScrollIndicator ) {
1147 QPixmap pixmap( 48, 48 ), icon;
1148 pixmap.fill(
QColor( qRgba( 127, 127, 127, 127 ) ) );
1150 QPainter p( &pixmap );
1151 QStyleOption option;
1153 option.rect.setRect( 16, 0, 16, 16 );
1154 QApplication::style()->drawPrimitive( QStyle::PE_IndicatorArrowUp, &option, &p );
1155 option.rect.setRect( 0, 16, 16, 16 );
1156 QApplication::style()->drawPrimitive( QStyle::PE_IndicatorArrowLeft, &option, &p );
1157 option.rect.setRect( 16, 32, 16, 16 );
1158 QApplication::style()->drawPrimitive( QStyle::PE_IndicatorArrowDown, &option, &p );
1159 option.rect.setRect( 32, 16, 16, 16 );
1160 QApplication::style()->drawPrimitive( QStyle::PE_IndicatorArrowRight, &option, &p );
1161 p.drawEllipse( 23, 23, 2, 2 );
1163 d->m_mouseScrollIndicator =
new QWidget(
this );
1164 d->m_mouseScrollIndicator->setFixedSize( 48, 48 );
1166 palette.setBrush( d->m_mouseScrollIndicator->backgroundRole(), QBrush( pixmap ) );
1167 d->m_mouseScrollIndicator->setPalette( palette );
1169 d->m_mouseScrollIndicator->move( point.x()-24, point.y()-24 );
1175 if ( cg.
readEntry(
"ShowMouseScrollIndicator",
true ) ) {
1176 d->m_mouseScrollIndicator->show();
1177 d->m_mouseScrollIndicator->unsetCursor();
1179 QBitmap
mask = d->m_mouseScrollIndicator->palette().brush(d->m_mouseScrollIndicator->backgroundRole()).texture().createHeuristicMask(
true );
1181 if ( hasHorBar && !hasVerBar ) {
1182 QBitmap bm( 16, 16 );
1184 QPainter painter( &mask );
1185 painter.drawPixmap( QRectF( 16, 0, bm.width(), bm.height() ), bm, bm.rect() );
1186 painter.drawPixmap( QRectF( 16, 32, bm.width(), bm.height() ), bm, bm.rect() );
1187 d->m_mouseScrollIndicator->setCursor( Qt::SizeHorCursor );
1189 else if ( !hasHorBar && hasVerBar ) {
1190 QBitmap bm( 16, 16 );
1192 QPainter painter( &mask );
1193 painter.drawPixmap( QRectF( 0, 16, bm.width(), bm.height() ), bm, bm.rect() );
1194 painter.drawPixmap( QRectF( 32, 16, bm.width(), bm.height() ), bm, bm.rect() );
1195 d->m_mouseScrollIndicator->setCursor( Qt::SizeVerCursor );
1198 d->m_mouseScrollIndicator->setCursor( Qt::SizeAllCursor );
1200 d->m_mouseScrollIndicator->setMask( mask );
1203 if ( hasHorBar && !hasVerBar )
1204 viewport()->setCursor( Qt::SizeHorCursor );
1205 else if ( !hasHorBar && hasVerBar )
1206 viewport()->setCursor( Qt::SizeVerCursor );
1208 viewport()->setCursor( Qt::SizeAllCursor );
1213 else if ( d->m_mouseScrollTimer ) {
1214 delete d->m_mouseScrollTimer;
1215 d->m_mouseScrollTimer = 0;
1217 if ( d->m_mouseScrollIndicator )
1218 d->m_mouseScrollIndicator->hide();
1221 if (d->clickCount > 0 &&
1222 QPoint(d->clickX-xm,d->clickY-ym).manhattanLength() <= QApplication::startDragDistance())
1230 bool swallowEvent = dispatchMouseEvent(EventImpl::MOUSEDOWN_EVENT,mev.innerNode.handle(),mev.innerNonSharedNode.handle(),
true,
1231 d->clickCount,_mouse,
true,DOM::NodeImpl::MousePress);
1233 if (!swallowEvent) {
1237 QApplication::sendEvent( m_part, &event );
1244 if(!m_part->xmlDocImpl())
return;
1246 int xm = _mouse->x();
1247 int ym = _mouse->y();
1248 revertTransforms(xm, ym);
1252 d->isDoubleClick =
true;
1254 DOM::NodeImpl::MouseEvent mev( _mouse->buttons(), DOM::NodeImpl::MouseDblClick );
1255 m_part->xmlDocImpl()->prepareMouseEvent(
false, xm, ym, &mev );
1259 if (d->clickCount > 0 &&
1260 QPoint(d->clickX-xm,d->clickY-ym).manhattanLength() <= QApplication::startDragDistance())
1267 bool swallowEvent = dispatchMouseEvent(EventImpl::MOUSEDOWN_EVENT,mev.innerNode.handle(),mev.innerNonSharedNode.handle(),
true,
1268 d->clickCount,_mouse,
true,DOM::NodeImpl::MouseDblClick);
1270 if (!swallowEvent) {
1272 QApplication::sendEvent( m_part, &
event );
1275 d->possibleTripleClick=
true;
1276 QTimer::singleShot(QApplication::doubleClickInterval(),
this,SLOT(tripleClickTimeout()));
1279 void KHTMLView::tripleClickTimeout()
1281 d->possibleTripleClick =
false;
1287 if (!target.isEmpty() && (target.toLower() !=
"_top") &&
1288 (target.toLower() !=
"_self") && (target.toLower() !=
"_parent")) {
1289 if (target.toLower() ==
"_blank")
1303 if ( d->m_mouseScrollTimer ) {
1304 QPoint point = mapFromGlobal( _mouse->globalPos() );
1306 int deltaX = point.x() - d->m_mouseScrollIndicator->x() - 24;
1307 int deltaY = point.y() - d->m_mouseScrollIndicator->y() - 24;
1309 (deltaX > 0) ? d->m_mouseScroll_byX = 1 : d->m_mouseScroll_byX = -1;
1310 (deltaY > 0) ? d->m_mouseScroll_byY = 1 : d->m_mouseScroll_byY = -1;
1312 double adX = qAbs(deltaX)/30.0;
1313 double adY = qAbs(deltaY)/30.0;
1315 d->m_mouseScroll_byX = qMax(qMin(d->m_mouseScroll_byX *
int(adX*adX), SHRT_MAX), SHRT_MIN);
1316 d->m_mouseScroll_byY = qMax(qMin(d->m_mouseScroll_byY *
int(adY*adY), SHRT_MAX), SHRT_MIN);
1318 if (d->m_mouseScroll_byX == 0 && d->m_mouseScroll_byY == 0) {
1319 d->m_mouseScrollTimer->stop();
1321 else if (!d->m_mouseScrollTimer->isActive()) {
1322 d->m_mouseScrollTimer->start( 20 );
1326 if(!m_part->xmlDocImpl())
return;
1328 int xm = _mouse->x();
1329 int ym = _mouse->y();
1330 revertTransforms(xm, ym);
1332 DOM::NodeImpl::MouseEvent mev( _mouse->buttons(), DOM::NodeImpl::MouseMove );
1334 m_part->xmlDocImpl()->prepareMouseEvent( _mouse->buttons() , xm, ym, &mev );
1340 DOM::NodeImpl* target = mev.innerNode.handle();
1341 DOM::NodeImpl* fn = m_part->xmlDocImpl()->focusNode();
1344 if (d->m_mouseEventsTarget && fn && fn->renderer() && fn->renderer()->isWidget())
1347 bool swallowEvent = dispatchMouseEvent(EventImpl::MOUSEMOVE_EVENT,target,mev.innerNonSharedNode.handle(),
false,
1348 0,_mouse,
true,DOM::NodeImpl::MouseMove);
1350 if (d->clickCount > 0 &&
1351 QPoint(d->clickX-xm,d->clickY-ym).manhattanLength() > QApplication::startDragDistance()) {
1355 khtml::RenderObject* r = target ? target->renderer() : 0;
1356 bool setCursor =
true;
1357 bool forceDefault =
false;
1358 if (r && r->isWidget()) {
1359 RenderWidget* rw =
static_cast<RenderWidget*
>(r);
1360 KHTMLWidget* kw = qobject_cast<
KHTMLView*>(rw->widget())? dynamic_cast<KHTMLWidget*>(rw->widget()) : 0;
1361 if (kw && kw->
m_kwp->isRedirected())
1363 else if (
QLineEdit* le = qobject_cast<QLineEdit*>(rw->widget())) {
1364 QList<QWidget*> wl = qFindChildren<QWidget *>( le,
"KLineEditButton" );
1367 if (w->underMouse()) {
1368 forceDefault =
true;
1373 else if (
QTextEdit* te = qobject_cast<QTextEdit*>(rw->widget())) {
1374 if (te->verticalScrollBar()->underMouse() || te->horizontalScrollBar()->underMouse())
1375 forceDefault =
true;
1378 khtml::RenderStyle* style = (r && r->style()) ? r->style() : 0;
1380 LinkCursor linkCursor = LINK_NORMAL;
1381 switch (!forceDefault ? (style ? style->cursor() : CURSOR_AUTO) : CURSOR_DEFAULT) {
1384 !r->isPointInsideSelection(xm, ym, m_part->caret())) )
1388 if (mev.url.string().startsWith(
"mailto:") && mev.url.string().indexOf(
'@')>0)
1389 linkCursor = LINK_MAILTO;
1392 linkCursor = LINK_NEWWINDOW;
1395 if (r && r->isFrameSet() && !
static_cast<RenderFrameSet*
>(r)->noResize())
1396 c =
QCursor(static_cast<RenderFrameSet*>(r)->cursorShape());
1402 case CURSOR_POINTER:
1404 if (mev.url.string().startsWith(
"mailto:") && mev.url.string().indexOf(
'@')>0)
1405 linkCursor = LINK_MAILTO;
1408 linkCursor = LINK_NEWWINDOW;
1410 case CURSOR_PROGRESS:
1414 case CURSOR_ALL_SCROLL:
1415 c =
QCursor(Qt::SizeAllCursor);
1417 case CURSOR_E_RESIZE:
1418 case CURSOR_W_RESIZE:
1419 case CURSOR_EW_RESIZE:
1420 c =
QCursor(Qt::SizeHorCursor);
1422 case CURSOR_N_RESIZE:
1423 case CURSOR_S_RESIZE:
1424 case CURSOR_NS_RESIZE:
1425 c =
QCursor(Qt::SizeVerCursor);
1427 case CURSOR_NE_RESIZE:
1428 case CURSOR_SW_RESIZE:
1429 case CURSOR_NESW_RESIZE:
1430 c =
QCursor(Qt::SizeBDiagCursor);
1432 case CURSOR_NW_RESIZE:
1433 case CURSOR_SE_RESIZE:
1434 case CURSOR_NWSE_RESIZE:
1435 c =
QCursor(Qt::SizeFDiagCursor);
1444 c =
QCursor(Qt::WhatsThisCursor);
1446 case CURSOR_DEFAULT:
1449 case CURSOR_NOT_ALLOWED:
1450 c =
QCursor(Qt::ForbiddenCursor);
1452 case CURSOR_ROW_RESIZE:
1453 c =
QCursor(Qt::SplitVCursor);
1455 case CURSOR_COL_RESIZE:
1456 c =
QCursor(Qt::SplitHCursor);
1458 case CURSOR_VERTICAL_TEXT:
1459 case CURSOR_CONTEXT_MENU:
1460 case CURSOR_NO_DROP:
1468 if (!setCursor && style && style->cursor() != CURSOR_AUTO)
1473 if (!p->parentPart())
1474 vp = p->view()->viewport();
1475 if ( setCursor && vp->cursor().handle() != c.handle() ) {
1476 if( c.shape() == Qt::ArrowCursor) {
1478 p->view()->viewport()->unsetCursor();
1485 if ( linkCursor!=LINK_NORMAL && isVisible() && hasFocus() ) {
1488 if( !d->cursorIconWidget ) {
1490 d->cursorIconWidget =
new QLabel( 0, Qt::X11BypassWindowManagerHint );
1491 XSetWindowAttributes attr;
1492 attr.save_under = True;
1493 XChangeWindowAttributes( QX11Info::display(), d->cursorIconWidget->winId(), CWSaveUnder, &attr );
1495 d->cursorIconWidget =
new QLabel( NULL, NULL );
1501 if (linkCursor != d->cursorIconType) {
1502 d->cursorIconType = linkCursor;
1506 case LINK_MAILTO: cursorIcon =
"mail-message-new";
break;
1507 case LINK_NEWWINDOW: cursorIcon =
"window-new";
break;
1508 default: cursorIcon =
"dialog-error";
break;
1513 d->cursorIconWidget->resize( icon_pixmap.width(), icon_pixmap.height());
1514 d->cursorIconWidget->setMask( icon_pixmap.createMaskFromColor(Qt::transparent));
1515 d->cursorIconWidget->setPixmap( icon_pixmap);
1516 d->cursorIconWidget->update();
1519 QPoint c_pos = QCursor::pos();
1520 d->cursorIconWidget->move( c_pos.x() + 15, c_pos.y() + 15 );
1522 XRaiseWindow( QX11Info::display(), d->cursorIconWidget->winId());
1523 QApplication::flush();
1524 #elif defined(Q_WS_WIN) 1525 SetWindowPos( d->cursorIconWidget->winId(), HWND_TOP, 0, 0, 0, 0, SWP_NOACTIVATE | SWP_NOMOVE | SWP_NOSIZE );
1529 d->cursorIconWidget->show();
1532 else if ( d->cursorIconWidget )
1533 d->cursorIconWidget->hide();
1535 if (r && r->isWidget()) {
1539 if (!swallowEvent) {
1541 QApplication::sendEvent( m_part, &event );
1547 bool swallowEvent =
false;
1549 int xm = _mouse->x();
1550 int ym = _mouse->y();
1551 revertTransforms(xm, ym);
1553 DOM::NodeImpl::MouseEvent mev( _mouse->buttons(), DOM::NodeImpl::MouseRelease );
1555 if ( m_part->xmlDocImpl() )
1557 m_part->xmlDocImpl()->prepareMouseEvent(
false, xm, ym, &mev );
1559 DOM::NodeImpl* target = mev.innerNode.handle();
1560 DOM::NodeImpl* fn = m_part->xmlDocImpl()->focusNode();
1563 if (d->m_mouseEventsTarget && fn && fn->renderer() && fn->renderer()->isWidget())
1566 swallowEvent = dispatchMouseEvent(EventImpl::MOUSEUP_EVENT,target,mev.innerNonSharedNode.handle(),
true,
1567 d->clickCount,_mouse,
false,DOM::NodeImpl::MouseRelease);
1570 if (d->m_mouseEventsTarget)
1571 d->m_mouseEventsTarget = 0;
1573 if (d->clickCount > 0 &&
1574 QPoint(d->clickX-xm,d->clickY-ym).manhattanLength() <= QApplication::startDragDistance()) {
1575 QMouseEvent me(d->isDoubleClick ? QEvent::MouseButtonDblClick : QEvent::MouseButtonRelease,
1576 _mouse->pos(), _mouse->button(), _mouse->buttons(), _mouse->modifiers());
1577 dispatchMouseEvent(EventImpl::CLICK_EVENT, mev.innerNode.handle(),mev.innerNonSharedNode.handle(),
true,
1578 d->clickCount, &me,
true, DOM::NodeImpl::MouseRelease);
1581 khtml::RenderObject* r = target ? target->renderer() : 0;
1582 if (r && r->isWidget())
1586 if (!swallowEvent) {
1588 QApplication::sendEvent( m_part, &event );
1593 bool KHTMLView::dispatchKeyEvent( QKeyEvent *_ke )
1595 if (!m_part->xmlDocImpl())
1617 if( _ke == d->postponed_autorepeat )
1622 if( _ke->type() == QEvent::KeyPress )
1624 if( !_ke->isAutoRepeat())
1626 bool ret = dispatchKeyEventHelper( _ke,
false );
1628 if( !ret && dispatchKeyEventHelper( _ke,
true ))
1634 bool ret = dispatchKeyEventHelper( _ke,
true );
1635 if( !ret && d->postponed_autorepeat )
1637 delete d->postponed_autorepeat;
1638 d->postponed_autorepeat = NULL;
1646 delete d->postponed_autorepeat;
1647 d->postponed_autorepeat = 0;
1649 if( !_ke->isAutoRepeat()) {
1650 return dispatchKeyEventHelper( _ke,
false );
1654 d->postponed_autorepeat =
new QKeyEvent( _ke->type(), _ke->key(), _ke->modifiers(),
1655 _ke->text(), _ke->isAutoRepeat(), _ke->count());
1656 if( _ke->isAccepted())
1657 d->postponed_autorepeat->accept();
1659 d->postponed_autorepeat->ignore();
1666 bool KHTMLView::dispatchKeyEventHelper( QKeyEvent *_ke,
bool keypress )
1668 DOM::NodeImpl* keyNode = m_part->xmlDocImpl()->focusNode();
1670 return keyNode->dispatchKeyEvent(_ke, keypress);
1672 return m_part->xmlDocImpl()->dispatchKeyEvent(_ke, keypress);
1679 if (d->accessKeysEnabled && _ke->key() == Qt::Key_Control && !(_ke->modifiers() & ~Qt::ControlModifier) && !d->accessKeysActivated)
1681 d->accessKeysPreActivate=
true;
1686 if (_ke->key() == Qt::Key_Shift && !(_ke->modifiers() & ~Qt::ShiftModifier))
1687 d->scrollSuspendPreActivate=
true;
1692 if (d->accessKeysEnabled && d->accessKeysActivated)
1694 int state = ( _ke->modifiers() & ( Qt::ShiftModifier | Qt::ControlModifier | Qt::AltModifier | Qt::MetaModifier ));
1695 if ( state==0 || state==Qt::ShiftModifier ) {
1696 if (_ke->key() != Qt::Key_Shift)
1697 accessKeysTimeout();
1698 handleAccessKey( _ke );
1702 accessKeysTimeout();
1707 if ( dispatchKeyEvent( _ke )) {
1713 int offs = (viewport()->height() < 30) ? viewport()->height() : 30;
1714 if (_ke->modifiers() & Qt::ShiftModifier)
1718 verticalScrollBar()->setValue( verticalScrollBar()->value() -viewport()->height() + offs );
1719 if(d->scrollSuspended)
1720 d->newScrollTimer(
this, 0);
1725 d->adjustScroller(
this, KHTMLViewPrivate::ScrollDown, KHTMLViewPrivate::ScrollUp);
1730 d->adjustScroller(
this, KHTMLViewPrivate::ScrollUp, KHTMLViewPrivate::ScrollDown);
1735 d->adjustScroller(
this, KHTMLViewPrivate::ScrollLeft, KHTMLViewPrivate::ScrollRight);
1740 d->adjustScroller(
this, KHTMLViewPrivate::ScrollRight, KHTMLViewPrivate::ScrollLeft);
1744 switch ( _ke->key() )
1748 if (!d->scrollTimerId || d->scrollSuspended)
1749 verticalScrollBar()->setValue( verticalScrollBar()->value()+10 );
1750 if (d->scrollTimerId)
1751 d->newScrollTimer(
this, 0);
1755 case Qt::Key_PageDown:
1756 d->shouldSmoothScroll =
true;
1757 verticalScrollBar()->setValue( verticalScrollBar()->value() +viewport()->height() - offs );
1758 if(d->scrollSuspended)
1759 d->newScrollTimer(
this, 0);
1764 if (!d->scrollTimerId || d->scrollSuspended)
1765 verticalScrollBar()->setValue( verticalScrollBar()->value()-10 );
1766 if (d->scrollTimerId)
1767 d->newScrollTimer(
this, 0);
1770 case Qt::Key_PageUp:
1771 d->shouldSmoothScroll =
true;
1772 verticalScrollBar()->setValue( verticalScrollBar()->value() -viewport()->height() + offs );
1773 if(d->scrollSuspended)
1774 d->newScrollTimer(
this, 0);
1778 if (!d->scrollTimerId || d->scrollSuspended)
1779 horizontalScrollBar()->setValue( horizontalScrollBar()->value()+10 );
1780 if (d->scrollTimerId)
1781 d->newScrollTimer(
this, 0);
1786 if (!d->scrollTimerId || d->scrollSuspended)
1787 horizontalScrollBar()->setValue( horizontalScrollBar()->value()-10 );
1788 if (d->scrollTimerId)
1789 d->newScrollTimer(
this, 0);
1792 case Qt::Key_Return:
1795 if (m_part->xmlDocImpl()) {
1796 NodeImpl *n = m_part->xmlDocImpl()->focusNode();
1802 verticalScrollBar()->setValue( 0 );
1803 horizontalScrollBar()->setValue( 0 );
1804 if(d->scrollSuspended)
1805 d->newScrollTimer(
this, 0);
1809 if(d->scrollSuspended)
1810 d->newScrollTimer(
this, 0);
1817 if (d->scrollTimerId)
1818 d->newScrollTimer(
this, 0);
1828 if( d->scrollSuspendPreActivate && _ke->key() != Qt::Key_Shift )
1829 d->scrollSuspendPreActivate =
false;
1830 if( _ke->key() == Qt::Key_Shift && d->scrollSuspendPreActivate && !(_ke->modifiers() & Qt::ShiftModifier))
1831 if (d->scrollTimerId) {
1832 d->scrollSuspended = !d->scrollSuspended;
1833 if (d->scrollSuspended)
1837 if (d->accessKeysEnabled)
1839 if (d->accessKeysPreActivate && _ke->key() != Qt::Key_Control)
1840 d->accessKeysPreActivate=
false;
1841 if (d->accessKeysPreActivate && !(_ke->modifiers() & Qt::ControlModifier))
1844 m_part->setStatusBarText(
i18n(
"Access Keys activated"),KHTMLPart::BarOverrideText);
1845 d->accessKeysActivated =
true;
1846 d->accessKeysPreActivate =
false;
1850 else if (d->accessKeysActivated)
1852 accessKeysTimeout();
1859 if ( dispatchKeyEvent( _ke ) )
1865 QScrollArea::keyReleaseEvent(_ke);
1871 if (m_part->xmlDocImpl() && focusNextPrevNode(next))
1873 if (m_part->xmlDocImpl()->focusNode())
1874 kDebug() <<
"focusNode.name: " 1875 << m_part->xmlDocImpl()->focusNode()->nodeName().string() << endl;
1880 d->pseudoFocusNode = KHTMLViewPrivate::PFNone;
1884 return QWidget::focusNextPrevChild(next);
1889 QPoint pos = QCursor::pos();
1892 pos = v->viewport()->mapFromGlobal( pos );
1897 pos = QPoint(pos.x() - viewport()->x(), pos.y() - viewport()->y());
1901 ensureVisible( xm, ym, 0, 5 );
1903 #ifndef KHTML_NO_SELECTION 1906 if (m_part->isExtendingSelection()) {
1907 RenderObject::NodeInfo renderInfo(
true,
false);
1908 m_part->xmlDocImpl()->renderer()->layer()
1909 ->nodeAtPoint(renderInfo, xm, ym);
1910 innerNode = renderInfo.innerNode();
1913 if (innerNode.
handle() && innerNode.
handle()->renderer()
1914 && innerNode.
handle()->renderer()->shouldSelect()) {
1915 m_part->extendSelectionTo(xm, ym, innerNode);
1917 #endif // KHTML_NO_SELECTION 1943 if (!qobject_cast<QFrame*>(w))
1944 w->setAttribute( Qt::WA_NoSystemBackground );
1946 w->setAttribute(Qt::WA_WState_InPaintEvent);
1948 if (!(w->objectName() ==
"KLineEditButton"))
1949 w->setAttribute(Qt::WA_OpaquePaintEvent);
1951 w->installEventFilter(view);
1955 if (qobject_cast<KHTMLView*>(w)) {
1956 handleWidget(static_cast<KHTMLView*>(w)->widget(), view,
false);
1957 handleWidget(static_cast<KHTMLView*>(w)->horizontalScrollBar(), view,
false);
1958 handleWidget(static_cast<KHTMLView*>(w)->verticalScrollBar(), view,
false);
1962 QObjectList children = w->children();
1963 foreach (
QObject*
object, children) {
1970 class KHTMLBackingStoreHackWidget :
public QWidget 1973 void publicEvent(
QEvent *e)
1981 switch (e->type()) {
1984 case QEvent::MouseButtonPress:
1985 case QEvent::MouseButtonRelease:
1986 case QEvent::MouseButtonDblClick:
1987 case QEvent::MouseMove:
1988 #ifndef QT_NO_WHEELEVENT 1991 case QEvent::ContextMenu:
1992 case QEvent::DragEnter:
1993 case QEvent::DragMove:
1994 case QEvent::DragLeave:
2000 return QScrollArea::viewportEvent(e);
2005 w->setAttribute(Qt::WA_WState_InPaintEvent, b);
2009 if (qobject_cast<KHTMLView*>(w)) {
2016 foreach(
QObject* cw, w->children()) {
2017 if (cw->isWidgetType() && !
static_cast<QWidget*
>(cw)->isWindow()
2018 && !(
static_cast<QWidget*
>(cw)->windowModality() & Qt::ApplicationModal)) {
2026 if ( e->type() == QEvent::ShortcutOverride ) {
2027 QKeyEvent* ke = (QKeyEvent*) e;
2028 if (m_part->isEditable() || m_part->isCaretMode()
2029 || (m_part->xmlDocImpl() && m_part->xmlDocImpl()->focusNode()
2030 && m_part->xmlDocImpl()->focusNode()->isContentEditable())) {
2031 if ( (ke->modifiers() & Qt::ControlModifier) || (ke->modifiers() & Qt::ShiftModifier) ) {
2032 switch ( ke->key() ) {
2048 if ( e->type() == QEvent::Leave ) {
2049 if (
d->cursorIconWidget )
2050 d->cursorIconWidget->hide();
2051 m_part->resetHoverText();
2058 else if (e->type() == QEvent::Resize) {
2062 }
else if (o->isWidgetType()) {
2065 while (v && v != view) {
2067 v = v->parentWidget();
2070 if (v && k && k->
m_kwp->isRedirected()) {
2072 bool isUpdate =
false;
2075 case QEvent::UpdateRequest: {
2077 static_cast<KHTMLBackingStoreHackWidget *
>(w)->publicEvent(e);
2081 case QEvent::UpdateLater:
2085 if (!allowWidgetPaintEvents) {
2091 while (v && v->parentWidget() != view) {
2094 v = v->parentWidget();
2097 QPoint ap = k->
m_kwp->absolutePos();
2101 QRect pr = isUpdate ?
static_cast<QUpdateLaterEvent*
>(e)->region().boundingRect() :
static_cast<QPaintEvent*
>(e)->rect();
2102 bool asap = !
d->contentsMoving && qobject_cast<QAbstractScrollArea*>(c);
2107 w->repaint(static_cast<QUpdateLaterEvent*>(e)->region());
2109 w->update(static_cast<QUpdateLaterEvent*>(e)->region());
2114 if ( asap && !isUpdate && !
d->painting && m_part->xmlDocImpl() && m_part->xmlDocImpl()->renderer() &&
2115 !
static_cast<khtml::RenderCanvas *
>(m_part->xmlDocImpl()->renderer())->needsLayout() ) {
2117 pr.width(), pr.height()+1);
2119 }
else if (!
d->painting) {
2120 scheduleRepaint(x + pr.x(), y + pr.y(),
2121 pr.width(), pr.height()+1, asap);
2125 case QEvent::MouseMove:
2126 case QEvent::MouseButtonPress:
2127 case QEvent::MouseButtonRelease:
2128 case QEvent::MouseButtonDblClick: {
2130 if (0 && w->parentWidget() == view && !qobject_cast<QScrollBar*>(w) && !::qobject_cast<QScrollBar *>(w)) {
2131 QMouseEvent *me =
static_cast<QMouseEvent *
>(e);
2132 QPoint pt = w->mapTo( view, me->pos());
2133 QMouseEvent me2(me->type(), pt, me->button(), me->buttons(), me->modifiers());
2135 if (e->type() == QEvent::MouseMove)
2137 else if(e->type() == QEvent::MouseButtonPress)
2139 else if(e->type() == QEvent::MouseButtonRelease)
2147 case QEvent::KeyPress:
2148 case QEvent::KeyRelease:
2149 if (w->parentWidget() == view && !qobject_cast<QScrollBar*>(w)) {
2150 QKeyEvent *ke =
static_cast<QKeyEvent *
>(e);
2151 if (e->type() == QEvent::KeyPress) {
2161 if (qobject_cast<KUrlRequester*>(w->parentWidget()) &&
2162 e->type() == QEvent::KeyPress) {
2172 case QEvent::FocusIn:
2173 case QEvent::FocusOut: {
2178 block =
static_cast<QFocusEvent*
>(e)->reason() != Qt::MouseFocusReason || root->underMouse();
2192 return QScrollArea::eventFilter(o, e);
2197 switch (e->type()) {
2198 case QEvent::MouseButtonPress:
2199 case QEvent::MouseButtonRelease:
2200 case QEvent::MouseButtonDblClick:
2201 case QEvent::MouseMove:
2203 #ifndef QT_NO_WHEELEVENT 2206 case QEvent::ContextMenu:
2207 case QEvent::DragEnter:
2208 case QEvent::DragMove:
2209 case QEvent::DragLeave:
2211 return QFrame::event(e);
2212 case QEvent::ChildPolished: {
2215 QObject *c =
static_cast<QChildEvent *
>(e)->child();
2216 if (c->isWidgetType()) {
2219 if (!(w->windowFlags() & Qt::Window) && !(w->windowModality() & Qt::ApplicationModal)) {
2221 if (k && k->
m_kwp->isRedirected()) {
2229 case QEvent::Move: {
2230 if (static_cast<QMoveEvent*>(e)->pos() != QPoint(0,0)) {
2231 widget()->move(0,0);
2243 bool KHTMLView::hasLayoutPending()
2245 return d->layoutTimerId && !
d->firstLayoutPending;
2248 DOM::NodeImpl *KHTMLView::nodeUnderMouse()
const 2250 return d->underMouse;
2253 DOM::NodeImpl *KHTMLView::nonSharedNodeUnderMouse()
const 2255 return d->underMouseNonShared;
2258 bool KHTMLView::scrollTo(
const QRect &bounds)
2260 d->scrollingSelf =
true;
2265 xe = bounds.right();
2266 ye = bounds.bottom();
2276 if (ye-y>curHeight-
d->borderY)
2277 ye = y + curHeight -
d->borderY;
2279 if (xe-x>curWidth-
d->borderX)
2280 xe = x + curWidth -
d->borderX;
2286 else if (xe +
d->borderX >
contentsX() + curWidth)
2287 deltax = xe +
d->borderX - (
contentsX() + curWidth );
2295 else if (ye +
d->borderY >
contentsY() + curHeight)
2296 deltay = ye +
d->borderY - (
contentsY() + curHeight );
2300 int maxx = curWidth-
d->borderX;
2301 int maxy = curHeight-
d->borderY;
2303 int scrollX, scrollY;
2305 scrollX = deltax > 0 ? (deltax > maxx ? maxx : deltax) : deltax == 0 ? 0 : (deltax>-maxx ? deltax : -maxx);
2306 scrollY = deltay > 0 ? (deltay > maxy ? maxy : deltay) : deltay == 0 ? 0 : (deltay>-maxy ? deltay : -maxy);
2318 horizontalScrollBar()->setValue( horizontalScrollBar()->value()+scrollX );
2319 verticalScrollBar()->setValue( verticalScrollBar()->value()+scrollY );
2321 d->scrollingSelf =
false;
2323 if ( (abs(deltax)<=maxx) && (abs(deltay)<=maxy) )
2329 bool KHTMLView::focusNextPrevNode(
bool next)
2338 DocumentImpl *doc = m_part->xmlDocImpl();
2339 NodeImpl *oldFocusNode = doc->focusNode();
2346 if ((oldFocusNode->renderer() && !oldFocusNode->renderer()->parent())
2347 || !oldFocusNode->isTabFocusable()) {
2348 doc->quietResetFocus();
2357 if (
d->scrollBarMoved)
2361 toFocus = doc->nextFocusNode(oldFocusNode);
2363 toFocus = doc->previousFocusNode(oldFocusNode);
2365 if (!toFocus && oldFocusNode) {
2367 toFocus = doc->nextFocusNode(NULL);
2369 toFocus = doc->previousFocusNode(NULL);
2372 while (toFocus && toFocus != oldFocusNode)
2375 QRect focusNodeRect = toFocus->getRect();
2379 QRect r = toFocus->getRect();
2380 ensureVisible( r.right(), r.bottom());
2381 ensureVisible( r.left(), r.top());
2382 d->scrollBarMoved =
false;
2383 d->tabMovePending =
false;
2384 d->lastTabbingDirection = next;
2385 d->pseudoFocusNode = KHTMLViewPrivate::PFNone;
2386 m_part->xmlDocImpl()->setFocusNode(toFocus);
2387 Node guard(toFocus);
2388 if (!toFocus->hasOneRef() )
2390 emit m_part->nodeActivated(
Node(toFocus));
2396 toFocus = doc->nextFocusNode(toFocus);
2398 toFocus = doc->previousFocusNode(toFocus);
2400 if (!toFocus && oldFocusNode)
2404 toFocus = doc->nextFocusNode(NULL);
2408 toFocus = doc->previousFocusNode(NULL);
2413 d->scrollBarMoved =
false;
2417 if (!oldFocusNode &&
d->pseudoFocusNode == KHTMLViewPrivate::PFNone)
2420 d->scrollBarMoved =
false;
2421 d->pseudoFocusNode = next?KHTMLViewPrivate::PFTop:KHTMLViewPrivate::PFBottom;
2425 NodeImpl *newFocusNode = NULL;
2427 if (
d->tabMovePending && next !=
d->lastTabbingDirection)
2430 newFocusNode = oldFocusNode;
2434 if (oldFocusNode ||
d->pseudoFocusNode == KHTMLViewPrivate::PFTop )
2435 newFocusNode = doc->nextFocusNode(oldFocusNode);
2439 if (oldFocusNode ||
d->pseudoFocusNode == KHTMLViewPrivate::PFBottom )
2440 newFocusNode = doc->previousFocusNode(oldFocusNode);
2443 bool targetVisible =
false;
2458 if (!m_part->isCaretMode() && newFocusNode->isContentEditable()) {
2459 kDebug(6200) <<
"show caret! fn: " << newFocusNode->nodeName().string() << endl;
2460 m_part->clearCaretRectIfNeeded();
2461 m_part->d->editor_context.m_selection.moveTo(Position(newFocusNode, 0L));
2462 m_part->setCaretVisible(
true);
2464 m_part->setCaretVisible(
false);
2465 kDebug(6200) <<
"hide caret! fn: " << newFocusNode->nodeName().string() << endl;
2467 m_part->notifySelectionChanged();
2469 targetVisible = scrollTo(newFocusNode->getRect());
2475 d->tabMovePending =
false;
2477 m_part->xmlDocImpl()->setFocusNode(newFocusNode);
2480 Node guard(newFocusNode);
2481 if (!newFocusNode->hasOneRef() )
2483 emit m_part->nodeActivated(
Node(newFocusNode));
2489 d->pseudoFocusNode = next?KHTMLViewPrivate::PFBottom:KHTMLViewPrivate::PFTop;
2495 if (!
d->tabMovePending)
2496 d->lastTabbingDirection = next;
2497 d->tabMovePending =
true;
2513 fallbacks = buildFallbackAccessKeys();
2514 for( NodeImpl* n = m_part->xmlDocImpl(); n != NULL; n = n->traverseNextNode()) {
2515 if( n->isElementNode()) {
2516 ElementImpl* en =
static_cast< ElementImpl*
>( n );
2517 DOMString s = en->getAttribute( ATTR_ACCESSKEY );
2520 QChar a = s.
string()[ 0 ].toUpper();
2521 if( qFind( taken.begin(), taken.end(), a ) == taken.end())
2524 if( accesskey.isNull() && fallbacks.contains( en )) {
2525 QChar a = fallbacks[ en ].toUpper();
2526 if( qFind( taken.begin(), taken.end(), a ) == taken.end())
2527 accesskey = QString(
"<qt><i>" ) + a +
"</i></qt>";
2529 if( !accesskey.isNull()) {
2530 QRect rec=en->getRect();
2532 lab->setAttribute(Qt::WA_DeleteOnClose);
2533 lab->setObjectName(
"KHTMLAccessKey");
2536 lab->setPalette(QToolTip::palette());
2537 lab->setLineWidth(2);
2538 lab->setFrameStyle(QFrame::Box | QFrame::Plain);
2541 lab->setParent( widget() );
2542 lab->setAutoFillBackground(
true);
2547 taken.append( accesskey[ 0 ] );
2556 if( !qobject_cast<KHTMLPart*>(cur) )
2559 if( part->
view() && part->
view() != caller )
2564 if (m_part->parentPart() && m_part->parentPart()->view()
2565 && m_part->parentPart()->view() != caller)
2566 m_part->parentPart()->view()->displayAccessKeys(
this, origview, taken, use_fallbacks );
2569 bool KHTMLView::isScrollingFromMouseWheel()
const 2571 return d->scrollingFromWheel != QPoint(-1,-1);
2574 void KHTMLView::accessKeysTimeout()
2576 d->accessKeysActivated=
false;
2577 d->accessKeysPreActivate =
false;
2578 m_part->setStatusBarText(QString(), KHTMLPart::BarOverrideText);
2583 bool KHTMLView::handleAccessKey(
const QKeyEvent* ev )
2588 if( ev->key() >= Qt::Key_A && ev->key() <= Qt::Key_Z )
2589 c =
'A' + ev->key() - Qt::Key_A;
2590 else if( ev->key() >= Qt::Key_0 && ev->key() <= Qt::Key_9 )
2591 c =
'0' + ev->key() - Qt::Key_0;
2595 if( ev->text().length() == 1 )
2596 c = ev->text()[ 0 ];
2600 return focusNodeWithAccessKey( c );
2603 bool KHTMLView::focusNodeWithAccessKey( QChar c,
KHTMLView* caller )
2605 DocumentImpl *doc = m_part->xmlDocImpl();
2608 ElementImpl* node = doc->findAccessKeyElement( c );
2612 if( !qobject_cast<KHTMLPart*>(cur) )
2615 if( part->
view() && part->
view() != caller
2616 && part->
view()->focusNodeWithAccessKey( c,
this ))
2620 if (m_part->parentPart() && m_part->parentPart()->view()
2621 && m_part->parentPart()->view() != caller
2622 && m_part->parentPart()->view()->focusNodeWithAccessKey( c,
this ))
2624 if( caller == NULL ) {
2627 it != fallbacks.end();
2640 QRect r = node->getRect();
2641 ensureVisible( r.right(), r.bottom());
2642 ensureVisible( r.left(), r.top());
2645 if( node->isFocusable()) {
2646 if (node->id()==ID_LABEL) {
2648 node=
static_cast<ElementImpl *
>(
static_cast< HTMLLabelElementImpl*
>( node )->getFormElement());
2649 if (!node)
return true;
2653 m_part->xmlDocImpl()->setFocusNode(node);
2655 if( node != NULL && node->hasOneRef())
2657 emit m_part->nodeActivated(
Node(node));
2658 if( node != NULL && node->hasOneRef())
2662 switch( node->id()) {
2664 static_cast< HTMLAnchorElementImpl*
>( node )->click();
2667 static_cast< HTMLInputElementImpl*
>( node )->click();
2670 static_cast< HTMLButtonElementImpl*
>( node )->click();
2673 static_cast< HTMLAreaElementImpl*
>( node )->click();
2687 for( NodeImpl* n = after ? start->nextSibling() : start->traversePreviousNode();
2689 n = after ? n->traverseNextNode() : n->traversePreviousNode()) {
2690 if( n->isTextNode()) {
2692 ret +=
static_cast< TextImpl*
>( n )->toString().string();
2694 ret.prepend( static_cast< TextImpl* >( n )->toString().
string());
2724 if( ret.trimmed().isEmpty())
2728 return ret.simplified();
2732 return ret.simplified();
2738 for( NodeImpl* n = start;
2740 n = n->traverseNextNode()) {
2741 if( n->id() == ID_LABEL ) {
2742 HTMLLabelElementImpl*
label =
static_cast< HTMLLabelElementImpl*
>( n );
2743 NodeImpl* labelfor = label->getFormElement();
2745 ret[ labelfor ] = label->innerText().string().simplified();
2752 struct AccessKeyData {
2753 ElementImpl* element;
2763 QLinkedList< AccessKeyData > data;
2768 for( NodeImpl* n = m_part->xmlDocImpl();
2770 n = n->traverseNextNode()) {
2771 if( n->isElementNode()) {
2772 ElementImpl* element =
static_cast< ElementImpl*
>( n );
2773 if( element->renderer() == NULL )
2778 bool ignore =
false;
2779 bool text_after =
false;
2780 bool text_before =
false;
2781 switch( element->id()) {
2783 url = element->getAttribute(ATTR_HREF).parsedUrl().string();
2786 text =
static_cast< HTMLElementImpl*
>( element )->innerText().string().simplified();
2790 HTMLInputElementImpl* in =
static_cast< HTMLInputElementImpl*
>( element );
2791 switch( in->inputType()) {
2792 case HTMLInputElementImpl::SUBMIT:
2793 text = in->value().string();
2795 text =
i18n(
"Submit" );
2798 case HTMLInputElementImpl::IMAGE:
2799 text = in->altText().string();
2802 case HTMLInputElementImpl::BUTTON:
2803 text = in->value().string();
2806 case HTMLInputElementImpl::RESET:
2807 text = in->value().string();
2809 text =
i18n(
"Reset" );
2812 case HTMLInputElementImpl::HIDDEN:
2815 case HTMLInputElementImpl::CHECKBOX:
2816 case HTMLInputElementImpl::RADIO:
2820 case HTMLInputElementImpl::TEXT:
2821 case HTMLInputElementImpl::PASSWORD:
2822 case HTMLInputElementImpl::FILE:
2833 text =
static_cast< HTMLElementImpl*
>( element )->innerText().string().simplified();
2834 switch( static_cast< HTMLButtonElementImpl* >( element )->buttonType()) {
2835 case HTMLButtonElementImpl::SUBMIT:
2837 text =
i18n(
"Submit" );
2840 case HTMLButtonElementImpl::RESET:
2842 text =
i18n(
"Reset" );
2859 ignore = !element->isFocusable();
2867 DOMString akey = element->getAttribute( ATTR_ACCESSKEY );
2868 if( akey.
length() == 1 ) {
2869 hrefs[url] = akey.
string()[ 0 ].toUpper();
2872 if( text.isNull() && labels.contains( element ))
2873 text = labels[ element ];
2874 if( text.isNull() && text_before )
2876 if( text.isNull() && text_after )
2878 text = text.trimmed();
2881 = m_part->settings()->fallbackAccessKeysAssignments();
2883 it != priorities.end();
2885 if( text == (*it).first )
2888 AccessKeyData tmp = { element, text, url, priority };
2894 for(
char c =
'A'; c <=
'Z'; ++c )
2896 for(
char c =
'0'; c <=
'9'; ++c )
2898 for( NodeImpl* n = m_part->xmlDocImpl();
2900 n = n->traverseNextNode()) {
2901 if( n->isElementNode()) {
2902 ElementImpl* en =
static_cast< ElementImpl*
>( n );
2903 DOMString s = en->getAttribute( ATTR_ACCESSKEY );
2905 QChar c = s.
string()[ 0 ].toUpper();
2906 keys.removeAll( c );
2912 for(
int priority = 10; priority >= 0; --priority ) {
2913 for( QLinkedList< AccessKeyData >::Iterator it = data.begin();
2916 if( (*it).priority != priority ) {
2922 QString text = (*it).text;
2924 const QString url = (*it).url;
2926 if( hrefs.contains( url ) ) {
2927 it = data.erase( it );
2930 if( !text.isEmpty()) {
2932 = m_part->settings()->fallbackAccessKeysAssignments();
2934 it != priorities.end();
2936 if( text == (*it).first && keys.contains( (*it).second )) {
2944 if( key.isNull() && !text.isEmpty()) {
2945 const QStringList words = text.split(
' ' );
2946 for( QStringList::ConstIterator it = words.begin();
2949 if( keys.contains( (*it)[ 0 ].toUpper())) {
2950 key = (*it)[ 0 ].toUpper();
2955 if( key.isNull() && !text.isEmpty()) {
2956 for(
int i = 0; i < text.length(); ++i ) {
2957 if( keys.contains( text[ i ].toUpper())) {
2958 key = text[ i ].toUpper();
2965 ret[ (*it).element ] = key;
2966 keys.removeAll( key );
2967 it = data.erase( it );
2969 if( !url.isEmpty() && !url.startsWith(
"javascript:", Qt::CaseInsensitive )) {
2970 for( QLinkedList< AccessKeyData >::Iterator it2 = data.begin();
2973 if( (*it2).url == url ) {
2974 ret[ (*it2).element ] = key;
2977 it2 = data.erase( it2 );
2987 void KHTMLView::setMediaType(
const QString &medium )
2992 QString KHTMLView::mediaType()
const 2997 bool KHTMLView::pagedMode()
const 3002 void KHTMLView::setWidgetVisible(RenderWidget* w,
bool vis)
3005 d->visibleWidgets.insert(w, w->widget());
3008 d->visibleWidgets.remove(w);
3011 bool KHTMLView::needsFullRepaint()
const 3013 return d->needsFullRepaint;
3017 class QPointerDeleter
3020 explicit QPointerDeleter(
QObject* o) : obj(o) {}
3021 ~QPointerDeleter() {
delete obj; }
3023 const QPointer<QObject> obj;
3029 if(!m_part->xmlDocImpl())
return;
3030 khtml::RenderCanvas *root =
static_cast<khtml::RenderCanvas *
>(m_part->xmlDocImpl()->renderer());
3034 const QPointerDeleter settingsDeleter(printSettings);
3038 const QPointerDeleter dialogDeleter(dialog);
3040 QString docname = m_part->xmlDocImpl()->URL().prettyUrl();
3041 if ( !docname.isEmpty() )
3044 if(quick || (dialog->exec() && dialog)) {
3045 viewport()->setCursor( Qt::WaitCursor );
3047 printer.setFullPage(
false);
3048 printer.setCreator(QString(
"KDE %1.%2.%3 HTML Library").arg(KDE_VERSION_MAJOR).arg(KDE_VERSION_MINOR).arg(KDE_VERSION_RELEASE));
3049 printer.setDocName(docname);
3051 QPainter *p =
new QPainter;
3052 p->begin( &printer );
3053 khtml::setPrintPainter( p );
3055 m_part->xmlDocImpl()->setPaintDevice( &printer );
3056 QString oldMediaType = mediaType();
3057 setMediaType(
"print" );
3061 m_part->xmlDocImpl()->setPrintStyleSheet( printSettings->printFriendly() ?
3062 "* { background-image: none !important;" 3063 " background-color: white !important;" 3064 " color: black !important; }" 3065 "body { margin: 0px !important; }" 3066 "html { margin: 0px !important; }" :
3067 "body { margin: 0px !important; }" 3068 "html { margin: 0px !important; }" 3071 kDebug(6000) <<
"printing: physical page width = " << printer.width()
3072 <<
" height = " << printer.height() << endl;
3073 root->setStaticMode(
true);
3074 root->setPagedMode(
true);
3075 root->setWidth(printer.width());
3077 root->setPageTop(0);
3078 root->setPageBottom(0);
3081 m_part->xmlDocImpl()->styleSelector()->computeFontSizes(printer.logicalDpiY(), 100);
3082 m_part->xmlDocImpl()->updateStyleSelector();
3083 root->setPrintImages(printSettings->printImages());
3084 root->makePageBreakAvoidBlocks();
3086 root->setNeedsLayoutAndMinMaxRecalc();
3091 bool printHeader = printSettings->printHeader();
3093 int headerHeight = 0;
3094 QFont headerFont(
"Sans Serif", 8);
3097 QString headerMid = docname;
3098 QString headerRight;
3102 p->setFont(headerFont);
3103 headerHeight = (p->fontMetrics().lineSpacing() * 3) / 2;
3107 kDebug(6000) <<
"printing: html page width = " << root->docWidth()
3108 <<
" height = " << root->docHeight() << endl;
3109 kDebug(6000) <<
"printing: margins left = " << printer.pageRect().left() - printer.paperRect().left()
3110 <<
" top = " << printer.pageRect().top() - printer.paperRect().top() << endl;
3111 kDebug(6000) <<
"printing: paper width = " << printer.width()
3112 <<
" height = " << printer.height() << endl;
3115 int pageWidth = printer.width();
3116 int pageHeight = printer.height();
3117 p->setClipRect(0,0, pageWidth, pageHeight);
3119 pageHeight -= headerHeight;
3121 #ifndef QT_NO_TRANSFORMATIONS 3122 bool scalePage =
false;
3124 if(root->docWidth() > printer.width()) {
3126 scale = ((double) printer.width())/((
double) root->docWidth());
3127 pageHeight = (int) (pageHeight/scale);
3128 pageWidth = (int) (pageWidth/scale);
3129 headerHeight = (int) (headerHeight/scale);
3132 kDebug(6000) <<
"printing: scaled html width = " << pageWidth
3133 <<
" height = " << pageHeight << endl;
3135 root->setHeight(pageHeight);
3136 root->setPageBottom(pageHeight);
3137 root->setNeedsLayout(
true);
3138 root->layoutIfNeeded();
3144 int available_width = printer.width() - 10 -
3145 2 * qMax(p->boundingRect(0, 0, printer.width(), p->fontMetrics().lineSpacing(),
Qt::AlignLeft, headerLeft).width(),
3146 p->boundingRect(0, 0, printer.width(), p->fontMetrics().lineSpacing(),
Qt::AlignLeft, headerRight).width());
3147 if (available_width < 150)
3148 available_width = 150;
3153 mid_width = p->boundingRect(0, 0, printer.width(), p->fontMetrics().lineSpacing(),
Qt::AlignLeft, headerMid).width();
3155 }
while (mid_width > available_width);
3161 while(top < root->docHeight()) {
3162 if(top > 0) printer.newPage();
3163 #ifndef QT_NO_TRANSFORMATIONS 3165 p->scale(scale, scale);
3168 p->setClipRect(0, 0, pageWidth, headerHeight);
3171 int dy = p->fontMetrics().lineSpacing();
3172 p->setPen(Qt::black);
3173 p->setFont(headerFont);
3175 headerRight = QString(
"#%1").arg(page);
3177 p->drawText(0, 0, printer.width(), dy,
Qt::AlignLeft, headerLeft);
3179 p->drawText(0, 0, printer.width(), dy,
Qt::AlignRight, headerRight);
3183 p->translate(0, headerHeight-top);
3185 bottom = top+pageHeight;
3187 root->setPageTop(top);
3188 root->setPageBottom(bottom);
3189 root->setPageNumber(page);
3191 root->layer()->paint(p, QRect(0, top, pageWidth, pageHeight));
3192 kDebug(6000) <<
"printed: page " << page <<
" bottom At = " << bottom;
3195 p->resetTransform();
3203 root->setPagedMode(
false);
3204 root->setStaticMode(
false);
3206 khtml::setPrintPainter( 0 );
3207 setMediaType( oldMediaType );
3208 m_part->xmlDocImpl()->setPaintDevice(
this );
3209 m_part->xmlDocImpl()->styleSelector()->computeFontSizes(m_part->xmlDocImpl()->logicalDpiY(), m_part->fontScaleFactor());
3210 m_part->xmlDocImpl()->updateStyleSelector();
3211 viewport()->unsetCursor();
3217 if(!m_part->xmlDocImpl())
return;
3218 DOM::DocumentImpl *document = m_part->xmlDocImpl();
3219 if (!document->isHTMLDocument())
return;
3220 khtml::RenderCanvas *root =
static_cast<khtml::RenderCanvas *
>(document->renderer());
3222 root->style()->resetPalette();
3223 NodeImpl *body =
static_cast<HTMLDocumentImpl*
>(document)->body();
3225 body->setChanged(
true);
3226 body->recalcStyle( NodeImpl::Force );
3229 void KHTMLView::paint(QPainter *p,
const QRect &rc,
int yOff,
bool *more)
3231 if(!m_part->xmlDocImpl())
return;
3232 khtml::RenderCanvas *root =
static_cast<khtml::RenderCanvas *
>(m_part->xmlDocImpl()->renderer());
3235 d->firstRepaintPending =
false;
3238 QPaintDevice* opd = m_part->xmlDocImpl()->paintDevice();
3239 m_part->xmlDocImpl()->setPaintDevice(p->device());
3240 root->setPagedMode(
true);
3241 root->setStaticMode(
true);
3242 root->setWidth(rc.width());
3245 QRegion creg = p->clipRegion();
3246 QTransform t = p->worldTransform();
3247 QRect w = p->window();
3248 QRect v = p->viewport();
3249 bool vte = p->viewTransformEnabled();
3250 bool wme = p->worldMatrixEnabled();
3253 p->translate(rc.left(), rc.top());
3254 double scale = ((double) rc.width()/(double) root->docWidth());
3255 int height = (int) ((
double) rc.height() / scale);
3256 #ifndef QT_NO_TRANSFORMATIONS 3257 p->scale(scale, scale);
3259 root->setPageTop(yOff);
3260 root->setPageBottom(yOff+height);
3262 root->layer()->paint(p, QRect(0, yOff, root->docWidth(), height));
3264 *more = yOff + height < root->docHeight();
3267 p->setWorldTransform(t);
3270 p->setViewTransformEnabled( vte );
3271 p->setWorldMatrixEnabled( wme );
3272 if (!creg.isEmpty())
3273 p->setClipRegion( creg );
3275 p->setClipRegion(QRegion(), Qt::NoClip);
3277 root->setPagedMode(
false);
3278 root->setStaticMode(
false);
3279 m_part->xmlDocImpl()->setPaintDevice( opd );
3282 void KHTMLView::render(QPainter* p,
const QRect& r,
const QPoint& off)
3285 d->firstRepaintPending =
false;
3287 QRect clip(off.x()+r.x(), off.y()+r.y(),r.width(),r.height());
3288 if(!m_part || !m_part->xmlDocImpl() || !m_part->xmlDocImpl()->renderer()) {
3289 p->fillRect(clip, palette().brush(QPalette::Active, QPalette::Base));
3292 QPaintDevice* opd = m_part->xmlDocImpl()->paintDevice();
3293 m_part->xmlDocImpl()->setPaintDevice(p->device());
3296 QRegion creg = p->clipRegion();
3297 QTransform t = p->worldTransform();
3298 QRect w = p->window();
3299 QRect v = p->viewport();
3300 bool vte = p->viewTransformEnabled();
3301 bool wme = p->worldMatrixEnabled();
3303 p->setClipRect(clip);
3307 m_part->xmlDocImpl()->renderer()->layer()->paint(p, rect);
3310 p->setWorldTransform(t);
3313 p->setViewTransformEnabled( vte );
3314 p->setWorldMatrixEnabled( wme );
3315 if (!creg.isEmpty())
3316 p->setClipRegion( creg );
3318 p->setClipRegion(QRegion(), Qt::NoClip);
3320 m_part->xmlDocImpl()->setPaintDevice( opd );
3323 void KHTMLView::setHasStaticBackground(
bool partial)
3326 if (
d->staticWidget == KHTMLViewPrivate::SBFull &&
m_kwp->isRedirected())
3329 d->staticWidget = partial ?
3330 KHTMLViewPrivate::SBPartial : KHTMLViewPrivate::SBFull;
3333 void KHTMLView::setHasNormalBackground()
3336 if (
d->staticWidget == KHTMLViewPrivate::SBFull &&
m_kwp->isRedirected())
3339 d->staticWidget = KHTMLViewPrivate::SBNone;
3342 void KHTMLView::addStaticObject(
bool fixed)
3345 d->fixedObjectsCount++;
3347 d->staticObjectsCount++;
3349 setHasStaticBackground(
true );
3352 void KHTMLView::removeStaticObject(
bool fixed)
3355 d->fixedObjectsCount--;
3357 d->staticObjectsCount--;
3359 assert(
d->fixedObjectsCount >= 0 &&
d->staticObjectsCount >= 0 );
3361 if (!
d->staticObjectsCount && !
d->fixedObjectsCount)
3362 setHasNormalBackground();
3364 setHasStaticBackground(
true );
3369 #ifndef KHTML_NO_SCROLLBARS 3370 d->vpolicy = policy;
3371 QScrollArea::setVerticalScrollBarPolicy(policy);
3379 #ifndef KHTML_NO_SCROLLBARS 3380 d->hpolicy = policy;
3381 QScrollArea::setHorizontalScrollBarPolicy(policy);
3387 void KHTMLView::restoreScrollBar()
3390 QScrollArea::setVerticalScrollBarPolicy(
d->vpolicy);
3393 d->prevScrollbarVisible = verticalScrollBar()->isVisible();
3396 QStringList KHTMLView::formCompletionItems(
const QString &
name)
const 3398 if (!m_part->settings()->isFormCompletionEnabled())
3399 return QStringList();
3400 if (!
d->formCompletions)
3402 return d->formCompletions->group(
"").readEntry(name, QStringList());
3405 void KHTMLView::clearCompletionHistory(
const QString& name)
3407 if (!
d->formCompletions)
3411 d->formCompletions->group(
"").writeEntry(name,
"");
3412 d->formCompletions->sync();
3415 void KHTMLView::addFormCompletionItem(
const QString &name,
const QString &value)
3417 if (!m_part->settings()->isFormCompletionEnabled())
3422 bool cc_number(
true);
3423 for (
int i = 0; i < value.length(); ++i)
3426 if (!c.isNumber() && c !=
'-' && !c.isSpace())
3434 QStringList items = formCompletionItems(name);
3435 if (!items.contains(value))
3436 items.prepend(value);
3437 while ((
int)items.count() > m_part->settings()->maxFormCompletionItems())
3438 items.erase(items.isEmpty() ? items.end() : --items.end());
3439 d->formCompletions->group(
"").writeEntry(name, items);
3442 void KHTMLView::addNonPasswordStorableSite(
const QString& host)
3444 if (!
d->formCompletions) {
3448 KConfigGroup cg(
d->formCompletions,
"NonPasswordStorableSites");
3449 QStringList sites = cg.
readEntry(
"Sites", QStringList());
3456 void KHTMLView::delNonPasswordStorableSite(
const QString& host)
3458 if (!
d->formCompletions) {
3462 KConfigGroup cg(
d->formCompletions,
"NonPasswordStorableSites");
3463 QStringList sites = cg.
readEntry(
"Sites", QStringList());
3464 sites.removeOne(host);
3469 bool KHTMLView::nonPasswordStorableSite(
const QString& host)
const 3471 if (!
d->formCompletions) {
3474 QStringList sites =
d->formCompletions->group(
"NonPasswordStorableSites" ).readEntry(
"Sites", QStringList());
3475 return (sites.indexOf(host) != -1);
3479 bool KHTMLView::dispatchMouseEvent(
int eventId, DOM::NodeImpl *targetNode,
3480 DOM::NodeImpl *targetNodeNonShared,
bool cancelable,
3481 int detail,QMouseEvent *_mouse,
bool setUnder,
3482 int mouseEventType,
int orient)
3485 if (targetNode && targetNode->isTextNode())
3486 targetNode = targetNode->parentNode();
3489 d->underMouse->deref();
3490 d->underMouse = targetNode;
3492 d->underMouse->ref();
3494 if (
d->underMouseNonShared)
3495 d->underMouseNonShared->deref();
3496 d->underMouseNonShared = targetNodeNonShared;
3497 if (
d->underMouseNonShared)
3498 d->underMouseNonShared->ref();
3500 bool isWheelEvent = (mouseEventType == DOM::NodeImpl::MouseWheel);
3502 int exceptioncode = 0;
3503 int pageX = _mouse->x();
3504 int pageY = _mouse->y();
3505 revertTransforms(pageX, pageY);
3508 int screenX = _mouse->globalX();
3509 int screenY = _mouse->globalY();
3511 switch (_mouse->button()) {
3512 case Qt::LeftButton:
3518 case Qt::RightButton:
3524 if (
d->accessKeysEnabled &&
d->accessKeysPreActivate && button!=-1)
3525 d->accessKeysPreActivate=
false;
3527 bool ctrlKey = (_mouse->modifiers() & Qt::ControlModifier);
3528 bool altKey = (_mouse->modifiers() & Qt::AltModifier);
3529 bool shiftKey = (_mouse->modifiers() & Qt::ShiftModifier);
3530 bool metaKey = (_mouse->modifiers() & Qt::MetaModifier);
3533 if (setUnder &&
d->oldUnderMouse != targetNode) {
3534 if (
d->oldUnderMouse &&
d->oldUnderMouse->document() != m_part->xmlDocImpl()) {
3535 d->oldUnderMouse->deref();
3536 d->oldUnderMouse = 0;
3539 if (
d->oldUnderMouse) {
3541 MouseEventImpl *me =
new MouseEventImpl(EventImpl::MOUSEOUT_EVENT,
3542 true,
true,m_part->xmlDocImpl()->defaultView(),
3543 0,screenX,screenY,clientX,clientY,pageX, pageY,
3544 ctrlKey,altKey,shiftKey,metaKey,
3547 d->oldUnderMouse->dispatchEvent(me,exceptioncode,
true);
3552 MouseEventImpl *me =
new MouseEventImpl(EventImpl::MOUSEOVER_EVENT,
3553 true,
true,m_part->xmlDocImpl()->defaultView(),
3554 0,screenX,screenY,clientX,clientY,pageX, pageY,
3555 ctrlKey,altKey,shiftKey,metaKey,
3556 button,
d->oldUnderMouse);
3559 targetNode->dispatchEvent(me,exceptioncode,
true);
3562 if (
d->oldUnderMouse)
3563 d->oldUnderMouse->deref();
3564 d->oldUnderMouse = targetNode;
3565 if (
d->oldUnderMouse)
3566 d->oldUnderMouse->ref();
3569 bool swallowEvent =
false;
3573 if (targetNode->isGenericFormElement()
3574 &&
static_cast<HTMLGenericFormElementImpl*
>(targetNode)->disabled())
3578 bool dblclick = ( eventId == EventImpl::CLICK_EVENT &&
3579 _mouse->type() == QEvent::MouseButtonDblClick );
3580 MouseEventImpl *me =
new MouseEventImpl(static_cast<EventImpl::EventId>(eventId),
3581 true,cancelable,m_part->xmlDocImpl()->defaultView(),
3582 detail,screenX,screenY,clientX,clientY,pageX, pageY,
3583 ctrlKey,altKey,shiftKey,metaKey,
3584 button,0, isWheelEvent ? 0 : _mouse, dblclick,
3585 isWheelEvent ?
static_cast<MouseEventImpl::Orientation
>(orient) : MouseEventImpl::ONone );
3587 if ( !
d->m_mouseEventsTarget && RenderLayer::gScrollBar && eventId == EventImpl::MOUSEDOWN_EVENT )
3589 d->m_mouseEventsTarget = RenderLayer::gScrollBar;
3590 if (
d->m_mouseEventsTarget && qobject_cast<QScrollBar*>(
d->m_mouseEventsTarget) &&
3591 dynamic_cast<KHTMLWidget*>(static_cast<QWidget*>(
d->m_mouseEventsTarget)) ) {
3595 QPoint p = w->
m_kwp->absolutePos();
3596 QMouseEvent fw(_mouse->type(), QPoint(pageX, pageY)-p, _mouse->button(), _mouse->buttons(), _mouse->modifiers());
3597 static_cast<RenderWidget::EventPropagator *
>(
static_cast<QWidget*
>(
d->m_mouseEventsTarget))->sendEvent(&fw);
3598 if (_mouse->type() == QMouseEvent::MouseButtonPress && _mouse->button() == Qt::RightButton) {
3599 QContextMenuEvent cme(QContextMenuEvent::Mouse, p);
3600 static_cast<RenderWidget::EventPropagator *
>(
static_cast<QWidget*
>(
d->m_mouseEventsTarget))->sendEvent(&cme);
3601 d->m_mouseEventsTarget = 0;
3603 swallowEvent =
true;
3605 targetNode->dispatchEvent(me,exceptioncode,
true);
3606 bool defaultHandled = me->defaultHandled();
3607 if (defaultHandled || me->defaultPrevented())
3608 swallowEvent =
true;
3610 if (eventId == EventImpl::MOUSEDOWN_EVENT && !me->defaultPrevented()) {
3615 DOM::NodeImpl* nodeImpl = targetNode;
3616 for ( ; nodeImpl && !nodeImpl->isFocusable(); nodeImpl = nodeImpl->parentNode())
3618 if (nodeImpl && nodeImpl->isMouseFocusable())
3619 m_part->xmlDocImpl()->setFocusNode(nodeImpl);
3620 else if (!nodeImpl || !nodeImpl->focused())
3621 m_part->xmlDocImpl()->setFocusNode(0);
3626 return swallowEvent;
3629 void KHTMLView::setIgnoreWheelEvents(
bool e )
3631 d->ignoreWheelEvents = e;
3634 #ifndef QT_NO_WHEELEVENT 3640 if (
d->scrollingFromWheel != QPoint(-1,-1) &&
d->scrollingFromWheel != QCursor::pos())
3641 d->scrollingFromWheel =
d->scrollingFromWheelTimerId ? QCursor::pos() : QPoint(-1,-1);
3643 if (
d->accessKeysEnabled &&
d->accessKeysPreActivate)
d->accessKeysPreActivate=
false;
3645 if ( ( e->modifiers() & Qt::ControlModifier) == Qt::ControlModifier )
3650 else if (
d->firstLayoutPending)
3654 else if( !
m_kwp->isRedirected() &&
3655 ( (e->orientation() == Qt::Vertical &&
3656 ((
d->ignoreWheelEvents && !verticalScrollBar()->isVisible())
3660 (e->orientation() == Qt::Horizontal &&
3661 ((
d->ignoreWheelEvents && !horizontalScrollBar()->isVisible())
3664 && m_part->parentPart())
3666 if ( m_part->parentPart()->view() )
3667 m_part->parentPart()->view()->wheelEvent( e );
3674 revertTransforms(xm, ym);
3676 DOM::NodeImpl::MouseEvent mev( e->buttons(), DOM::NodeImpl::MouseWheel );
3677 m_part->xmlDocImpl()->prepareMouseEvent(
false, xm, ym, &mev );
3679 MouseEventImpl::Orientation o = MouseEventImpl::OVertical;
3680 if (e->orientation() == Qt::Horizontal)
3681 o = MouseEventImpl::OHorizontal;
3683 QMouseEvent _mouse(QEvent::MouseMove, e->pos(), Qt::NoButton, e->buttons(), e->modifiers());
3684 bool swallow = dispatchMouseEvent(EventImpl::KHTML_MOUSEWHEEL_EVENT,mev.innerNode.handle(),mev.innerNonSharedNode.handle(),
3685 true,-e->delta()/40,&_mouse,
true,DOM::NodeImpl::MouseWheel,o);
3690 d->scrollBarMoved =
true;
3691 d->scrollingFromWheel = QCursor::pos();
3693 d->shouldSmoothScroll =
true;
3694 if (
d->scrollingFromWheelTimerId)
3695 killTimer(
d->scrollingFromWheelTimerId);
3696 d->scrollingFromWheelTimerId = startTimer(400);
3698 if (m_part->parentPart()) {
3700 bool h = (
static_cast<QWheelEvent*
>(e)->orientation() == Qt::Horizontal);
3701 bool d = (
static_cast<QWheelEvent*
>(e)->delta() < 0);
3702 QScrollBar* hsb = horizontalScrollBar();
3703 QScrollBar* vsb = verticalScrollBar();
3704 if ( (h && ((d && hsb->value() == hsb->maximum()) || (!d && hsb->value() == hsb->minimum()))) ||
3705 (!h && ((d && vsb->value() == vsb->maximum()) || (!d && vsb->value() == vsb->minimum()))) ) {
3710 QScrollArea::wheelEvent( e );
3719 QScrollArea::dragEnterEvent( ev );
3725 QScrollArea::dropEvent( ev );
3730 DOM::NodeImpl* fn = m_part->xmlDocImpl() ? m_part->xmlDocImpl()->focusNode() : 0;
3731 if (fn && fn->renderer() && fn->renderer()->isWidget() &&
3732 (e->reason() != Qt::MouseFocusReason) &&
3733 static_cast<khtml::RenderWidget*>(fn->renderer())->widget())
3734 static_cast<khtml::RenderWidget*>(fn->renderer())->widget()->setFocus();
3735 m_part->setSelectionVisible();
3736 QScrollArea::focusInEvent( e );
3742 m_part->stopAutoScroll();
3743 m_part->setSelectionVisible(
false);
3746 if (
d->cursorIconWidget )
3747 d->cursorIconWidget->hide();
3749 QScrollArea::focusOutEvent( e );
3754 if (!dx && !dy)
return;
3756 if ( !
d->firstLayoutPending && !
d->complete && m_part->xmlDocImpl() &&
3757 d->layoutSchedulingEnabled) {
3759 khtml::RenderCanvas* root =
static_cast<khtml::RenderCanvas *
>( m_part->xmlDocImpl()->renderer() );
3760 if (root && root->needsLayout()) {
3761 unscheduleRelayout();
3766 if (
d->shouldSmoothScroll &&
d->smoothScrollMode !=
SSMDisabled && m_part->xmlDocImpl() &&
3769 bool doSmoothScroll = (!
d->staticWidget ||
d->smoothScrollMode ==
SSMEnabled);
3771 int numStaticPixels = 0;
3772 QRegion r =
static_cast<RenderCanvas*
>(m_part->xmlDocImpl()->renderer())->staticRegion();
3775 if (!doSmoothScroll &&
d->staticWidget == KHTMLViewPrivate::SBPartial && r.rects().size() <= 10) {
3776 foreach(
const QRect &rr, r.rects())
3777 numStaticPixels += rr.width()*rr.height();
3779 doSmoothScroll =
true;
3781 if (doSmoothScroll) {
3782 setupSmoothScrolling(dx, dy);
3787 if ( underMouse() && QToolTip::isVisible() )
3788 QToolTip::hideText();
3790 if (!
d->scrollingSelf) {
3791 d->scrollBarMoved =
true;
3792 d->contentsMoving =
true;
3794 scheduleRepaint(0, 0, 0, 0);
3797 if (m_part->xmlDocImpl() && m_part->xmlDocImpl()->documentElement()) {
3798 m_part->xmlDocImpl()->documentElement()->dispatchHTMLEvent(EventImpl::SCROLL_EVENT,
true,
false);
3801 if (QApplication::isRightToLeft())
3804 if (!
d->smoothScrolling) {
3805 d->updateContentsXY();
3810 if (widget()->pos() != QPoint(0,0)) {
3811 kDebug(6000) <<
"Static widget wasn't positioned at (0,0). This should NOT happen. Please report this event to developers.";
3812 kDebug(6000) << kBacktrace();
3813 widget()->move(0,0);
3818 if (
m_kwp->isRedirected()) {
3823 off = viewport()->mapTo(
this, off);
3826 if (
d->staticWidget ) {
3830 if (!
d->visibleWidgets.isEmpty())
3831 checkExternalWidgetsPosition();
3833 if (
d->staticWidget == KHTMLViewPrivate::SBPartial
3834 && m_part->xmlDocImpl() && m_part->xmlDocImpl()->renderer() ) {
3836 QRegion r =
static_cast<RenderCanvas*
>(m_part->xmlDocImpl()->renderer())->staticRegion();
3840 for (
int i = 0; i < ar.size() ; ++i) {
3841 widget()->update( ar[i] );
3845 for (
int i = 0; i < ar.size() ; ++i) {
3846 w->scroll( dx, dy, ar[i].translated(off) );
3848 d->scrollExternalWidgets(dx, dy);
3853 if (
d->accessKeysActivated)
3854 d->scrollAccessKeys(dx, dy);
3859 if (
m_kwp->isRedirected()) {
3861 w->scroll(dx, dy, rect);
3862 if (
d->zoomLevel != 100) {
3866 widget()->scroll(dx, dy, widget()->rect() & viewport()->rect());
3869 d->scrollExternalWidgets(dx, dy);
3870 if (
d->accessKeysActivated)
3871 d->scrollAccessKeys(dx, dy);
3874 void KHTMLView::setupSmoothScrolling(
int dx,
int dy)
3877 int ddx = qMax(
d->steps ? abs(
d->dx)/
d->steps : 0,3);
3878 int ddy = qMax(
d->steps ? abs(
d->dy)/
d->steps : 0,3);
3884 if (
d->dx == 0 &&
d->dy == 0) {
3891 if (qMax(abs(
d->dx), abs(
d->dy)) /
d->steps < qMax(ddx,ddy)) {
3894 d->steps = qMax((abs(
d->dx)+ddx-1)/ddx, (abs(
d->dy)+ddy-1)/ddy);
3895 if (
d->steps < 1)
d->steps = 1;
3898 d->smoothScrollStopwatch.start();
3899 if (!
d->smoothScrolling) {
3900 d->startScrolling();
3905 void KHTMLView::scrollTick() {
3906 if (
d->dx == 0 &&
d->dy == 0) {
3911 if (
d->steps < 1)
d->steps = 1;
3915 if (takesteps < 1) takesteps = 1;
3916 if (takesteps >
d->steps) takesteps =
d->steps;
3917 for(
int i = 0; i < takesteps; i++) {
3918 int ddx = (
d->dx / (
d->steps+1)) * 2;
3919 int ddy = (
d->dy / (
d->steps+1)) * 2;
3922 if (abs(ddx) > abs(
d->dx)) ddx =
d->dx;
3923 if (abs(ddy) > abs(
d->dy)) ddy =
d->dy;
3933 d->shouldSmoothScroll =
false;
3936 if (takesteps < 2) {
3937 d->smoothScrollMissedDeadlines = 0;
3940 (!m_part->xmlDocImpl() || !m_part->xmlDocImpl()->parsing())) {
3941 d->smoothScrollMissedDeadlines++;
3957 if (child->parent() != widget())
3958 child->setParent( widget() );
3968 if ( e->timerId() ==
d->scrollTimerId ) {
3969 if(
d->scrollSuspended )
3971 switch (
d->scrollDirection) {
3972 case KHTMLViewPrivate::ScrollDown:
3974 d->newScrollTimer(
this, 0);
3976 verticalScrollBar()->setValue( verticalScrollBar()->value() +
d->scrollBy );
3978 case KHTMLViewPrivate::ScrollUp:
3980 d->newScrollTimer(
this, 0);
3982 verticalScrollBar()->setValue( verticalScrollBar()->value() -
d->scrollBy );
3984 case KHTMLViewPrivate::ScrollRight:
3986 d->newScrollTimer(
this, 0);
3988 horizontalScrollBar()->setValue( horizontalScrollBar()->value() +
d->scrollBy );
3990 case KHTMLViewPrivate::ScrollLeft:
3992 d->newScrollTimer(
this, 0);
3994 horizontalScrollBar()->setValue( horizontalScrollBar()->value() -
d->scrollBy );
3999 else if ( e->timerId() ==
d->scrollingFromWheelTimerId ) {
4000 killTimer(
d->scrollingFromWheelTimerId );
4001 d->scrollingFromWheelTimerId = 0;
4002 }
else if ( e->timerId() ==
d->layoutTimerId ) {
4003 if (
d->firstLayoutPending &&
d->layoutAttemptCounter < 4
4004 && (!m_part->xmlDocImpl() || !m_part->xmlDocImpl()->readyForLayout())) {
4005 d->layoutAttemptCounter++;
4006 killTimer(
d->layoutTimerId);
4007 d->layoutTimerId = 0;
4012 d->scheduledLayoutCounter++;
4013 if (
d->firstLayoutPending) {
4014 d->firstLayoutPending =
false;
4015 verticalScrollBar()->setEnabled(
true );
4016 horizontalScrollBar()->setEnabled(
true );
4020 d->contentsMoving =
false;
4021 if( m_part->xmlDocImpl() ) {
4022 DOM::DocumentImpl *document = m_part->xmlDocImpl();
4023 khtml::RenderCanvas* root =
static_cast<khtml::RenderCanvas *
>(document->renderer());
4025 if ( root && root->needsLayout() ) {
4026 if (
d->repaintTimerId)
4027 killTimer(
d->repaintTimerId);
4028 d->repaintTimerId = 0;
4034 if (
d->repaintTimerId)
4035 killTimer(
d->repaintTimerId);
4036 d->repaintTimerId = 0;
4041 d->updateRegion = QRegion();
4044 updateRegion = rects[0];
4046 for (
int i = 1; i < rects.size(); ++i ) {
4047 QRect newRegion = updateRegion.unite(rects[i]);
4048 if (2*newRegion.height() > 3*updateRegion.height() )
4051 updateRegion = rects[i];
4054 updateRegion = newRegion;
4057 if ( !updateRegion.isNull() )
4065 if (
d->dirtyLayout && !
d->visibleWidgets.isEmpty())
4066 checkExternalWidgetsPosition();
4068 d->dirtyLayout =
false;
4071 if (
d->emitCompletedAfterRepaint) {
4072 bool full =
d->emitCompletedAfterRepaint == KHTMLViewPrivate::CSFull;
4073 d->emitCompletedAfterRepaint = KHTMLViewPrivate::CSNone;
4075 emit m_part->completed();
4077 emit m_part->completed(
true);
4081 void KHTMLView::checkExternalWidgetsPosition()
4086 QHashIterator<void*, QWidget*> it(
d->visibleWidgets);
4087 while (it.hasNext()) {
4090 RenderWidget* rw =
static_cast<RenderWidget*
>( it.key() );
4091 if (!rw->absolutePosition(xp, yp) ||
4092 !visibleRect.intersects(QRect(xp, yp, it.value()->width(), it.value()->height())))
4093 toRemove.append(rw);
4095 foreach (RenderWidget* r, toRemove)
4096 if ( (w =
d->visibleWidgets.take(r) ) )
4097 w->move( 0, -500000);
4100 void KHTMLView::scheduleRelayout(khtml::RenderObject * )
4102 if (!
d->layoutSchedulingEnabled ||
d->layoutTimerId)
4106 if (
d->firstLayoutPending) {
4110 time =
d->layoutAttemptCounter ?
4112 }
else if (m_part->xmlDocImpl() && m_part->xmlDocImpl()->parsing()) {
4117 d->layoutTimerId = startTimer( time );
4120 void KHTMLView::unscheduleRelayout()
4122 if (!
d->layoutTimerId)
4125 killTimer(
d->layoutTimerId);
4126 d->layoutTimerId = 0;
4129 void KHTMLView::unscheduleRepaint()
4131 if (!
d->repaintTimerId)
4134 killTimer(
d->repaintTimerId);
4135 d->repaintTimerId = 0;
4138 void KHTMLView::scheduleRepaint(
int x,
int y,
int w,
int h,
bool asap)
4140 bool parsing = !m_part->xmlDocImpl() || m_part->xmlDocImpl()->parsing();
4145 int time = parsing && !
d->firstLayoutPending ? 150 : (!asap ? ( !
d->complete ? 80 : 20 ) : 0);
4147 #ifdef DEBUG_FLICKER 4149 p.begin( viewport() );
4153 p.fillRect( vx, vy, w, h, Qt::red );
4157 d->updateRegion =
d->updateRegion.unite(QRect(x,y,w,h));
4159 if (asap && !parsing)
4160 unscheduleRepaint();
4162 if ( !
d->repaintTimerId )
4163 d->repaintTimerId = startTimer( time );
4168 void KHTMLView::complete(
bool pendingAction )
4175 if (
d->layoutTimerId)
4179 killTimer(
d->layoutTimerId);
4180 d->layoutTimerId = startTimer( 0 );
4181 d->emitCompletedAfterRepaint = pendingAction ?
4182 KHTMLViewPrivate::CSActionPending : KHTMLViewPrivate::CSFull;
4186 if (
d->repaintTimerId)
4190 killTimer(
d->repaintTimerId);
4191 d->repaintTimerId = startTimer( 0 );
4192 d->emitCompletedAfterRepaint = pendingAction ?
4193 KHTMLViewPrivate::CSActionPending : KHTMLViewPrivate::CSFull;
4196 if (!
d->emitCompletedAfterRepaint)
4199 emit m_part->completed();
4201 emit m_part->completed(
true);
4206 void KHTMLView::updateScrollBars()
4208 const QWidget *view = widget();
4212 QSize p = viewport()->size();
4213 QSize m = maximumViewportSize();
4215 if (m.expandedTo(view->size()) == m)
4218 QSize v = view->size();
4219 horizontalScrollBar()->setRange(0, v.width() - p.width());
4220 horizontalScrollBar()->setPageStep(p.width());
4221 verticalScrollBar()->setRange(0, v.height() - p.height());
4222 verticalScrollBar()->setPageStep(p.height());
4223 if (!
d->smoothScrolling) {
4224 d->updateContentsXY();
4228 void KHTMLView::slotMouseScrollTimer()
4230 horizontalScrollBar()->setValue( horizontalScrollBar()->value() +
d->m_mouseScroll_byX );
4231 verticalScrollBar()->setValue( verticalScrollBar()->value() +
d->m_mouseScroll_byY);
4237 Selection sel = pos;
4238 sel.expandUsingGranularity(Selection::LINE);
4239 return toEnd ? sel.end() : sel.start();
4252 bool KHTMLView::caretKeyPressEvent(QKeyEvent *_ke)
4256 Position old_pos = caret.caretPos();
4257 Position pos = old_pos;
4258 bool recalcXPos =
true;
4259 bool handled =
true;
4261 bool ctrl = _ke->modifiers() & Qt::ControlModifier;
4262 bool shift = _ke->modifiers() & Qt::ShiftModifier;
4264 switch(_ke->key()) {
4268 pos = old_pos.nextLinePosition(caret.xPosForVerticalArrowNavigation(Selection::EXTENT));
4273 pos = old_pos.previousLinePosition(caret.xPosForVerticalArrowNavigation(Selection::EXTENT));
4278 pos = ctrl ? old_pos.previousWordPosition() : old_pos.previousCharacterPosition();
4282 pos = ctrl ? old_pos.nextWordPosition() : old_pos.nextCharacterPosition();
4285 case Qt::Key_PageDown:
4289 case Qt::Key_PageUp:
4312 if (pos != old_pos) {
4313 m_part->clearCaretRectIfNeeded();
4315 caret.moveTo(shift ? caret.nonCaretPos() : pos, pos);
4316 int old_x = caret.xPosForVerticalArrowNavigation(Selection::CARETPOS);
4318 m_part->selectionLayoutChanged();
4322 m_part->d->editor_context.m_xPosForVerticalArrowNavigation = old_x;
4324 m_part->emitCaretPositionChanged(pos);
4326 m_part->notifySelectionChanged();
4330 if (handled) _ke->accept();
4334 #undef DEBUG_CARETMODE
QString i18n(const char *text)
SmoothScrollingMode smoothScrollingMode() const
Retrieve the current smooth scrolling mode.
Contextual information about the caret and the built-in editor.
bool changeCursor() const
void updateContents(const QRect &r)
Requests an update of the content area.
SmoothScrollingMode
Smooth Scrolling Mode enumeration.
void setSmoothScrollingModeDefault(SmoothScrollingMode m)
static const int sSmoothScrollMinStaticPixels
virtual void mouseDoubleClickEvent(QMouseEvent *)
QCursor urlCursor() const
Returns the cursor which is used when the cursor is on a link.
DOM::Selection m_selection
static QMap< NodeImpl *, QString > buildLabels(NodeImpl *start)
The Node interface is the primary datatype for the entire Document Object Model.
void setSmoothScrollingMode(SmoothScrollingMode m)
Set the smooth scrolling mode.
static QString getElementText(NodeImpl *start, bool after)
khtml::EditorContext editor_context
static const int sLayoutAttemptDelay
static DOM::Position positionOfLineEnd(const DOM::Position &pos)
QString label(StandardShortcut id)
int contentsY() const
Returns the y coordinate of the contents area point that is currently located at the top left in the ...
virtual void focusOutEvent(QFocusEvent *)
QPoint contentsToViewport(const QPoint &p) const
Returns a point translated to viewport coordinates.
void addChild(QWidget *child, int dx, int dy)
bool frameExists(const QString &frameName)
Returns whether a frame with the specified name is exists or not.
This class is khtml's main class.
const char * name(StandardAction id)
static bool findImageMapRect(HTMLImageElementImpl *img, const QPoint &scrollOfs, const QPoint &p, QRect &r, QString &s)
calculates the client-side image map rectangle for the given image element
Renders and displays HTML in a QScrollArea.
void writeEntry(const QString &key, const QVariant &value, WriteConfigFlags pFlags=Normal)
virtual bool eventFilter(QObject *, QEvent *)
static KHTMLSettings * defaultHTMLSettings()
static const int sSmoothScrollTick
QPrintDialog * createPrintDialog(QPrinter *printer, PageSelectPolicy pageSelectPolicy, const QList< QWidget * > &customTabs, QWidget *parent=0)
void setContentsPos(int x, int y)
Place the contents area point x/y at the top left of the viewport.
static QDebug kDebug(bool cond, int area=KDE_DEFAULT_DEBUG_AREA)
bool m_beganSelectingText
static DOM::Position positionOfLineBegin(const DOM::Position &pos)
virtual bool focusNextPrevChild(bool next)
KSharedConfigPtr config()
virtual void closeEvent(QCloseEvent *)
KHTMLView * view() const
Returns a pointer to the HTML document's view.
virtual void mousePressEvent(QMouseEvent *)
KHTMLPart * part() const
Returns a pointer to the KHTMLPart that is rendering the page.
virtual void scrollContentsBy(int dx, int dy)
int visibleWidth() const
Returns the width of the viewport.
int visibleHeight() const
Returns the height of the viewport.
void layout()
ensure the display is up to date
QPixmap loadIcon(const QString &name, KIconLoader::Group group, int size=0, int state=KIconLoader::DefaultState, const QStringList &overlays=QStringList(), QString *path_store=0L, bool canReturnNull=false) const
virtual void focusInEvent(QFocusEvent *)
static const int sParsingLayoutsInterval
virtual void setVerticalScrollBarPolicy(Qt::ScrollBarPolicy policy)
Sets vertical scrollbar mode.
int contentsHeight() const
Returns the contents area's height.
virtual void dragEnterEvent(QDragEnterEvent *)
virtual void hideEvent(QHideEvent *)
This class implements the basic string we use in the DOM.
void keyPressEvent(QKeyEvent *_ke)
QString csqueeze(const QString &str, int maxlen=40)
static void handleWidget(QWidget *w, KHTMLView *view, bool recurse=true)
static const int sFirstLayoutDelay
static const int sLayoutAttemptIncrement
virtual void paintEvent(QPaintEvent *)
KAction * next(const QObject *recvr, const char *slot, QObject *parent)
static KIconLoader * iconLoader()
void setMarginWidth(int x)
Sets a margin in x direction.
static const int sMaxMissedDeadlines
void scrollBy(int x, int y)
Scrolls the content area by a given amount.
friend class KHTMLViewPrivate
static const int sParsingLayoutsIncrement
bool accessKeysEnabled() const
virtual void mouseMoveEvent(QMouseEvent *)
void timerEvent(QTimerEvent *)
QPoint viewportToContents(const QPoint &p) const
Returns a point translated to contents area coordinates.
virtual void resizeEvent(QResizeEvent *event)
void setZoomLevel(int percent)
Apply a zoom level to the content area.
This library provides a full-featured HTML parser and widget.
virtual void setHorizontalScrollBarPolicy(Qt::ScrollBarPolicy policy)
Sets horizontal scrollbar mode.
static const int sSmoothScrollTime
virtual bool event(QEvent *event)
static const int sWayTooMany
virtual bool widgetEvent(QEvent *)
static QString locateLocal(const char *type, const QString &filename, const KComponentData &cData=KGlobal::mainComponent())
void finishedLayout()
This signal is used for internal layouting.
virtual bool viewportEvent(QEvent *e)
int contentsX() const
Returns the x coordinate of the contents area point that is currently located at the top left in the ...
void installEventFilter(QWidget *filter)
void setMarginHeight(int y)
QWeakPointer< DOM::HTMLPartContainerElementImpl > m_partContainerElement
static QDebug kWarning(bool cond, int area=KDE_DEFAULT_DEBUG_AREA)
void print(bool quick=false)
Prints the HTML document.
QString formatDate(const QDate &date, DateFormat format=LongDate) const
virtual void wheelEvent(QWheelEvent *)
int contentsWidth() const
Returns the contents area's width.
void nodeActivated(const DOM::Node &)
This signal is emitted when an element retrieves the keyboard focus.
void repaintContents(const QRect &r)
Requests an immediate repaint of the content area.
virtual void dropEvent(QDropEvent *)
NodeImpl * handle() const
T readEntry(const QString &key, const T &aDefault) const
void keyReleaseEvent(QKeyEvent *_ke)
const KHTMLSettings * settings() const
virtual void showEvent(QShowEvent *)
static DOM::Position positionOfLineBoundary(const DOM::Position &pos, bool toEnd)
KHTMLView(KHTMLPart *part, QWidget *parent)
Constructs a KHTMLView.
static bool targetOpensNewWindow(KHTMLPart *part, QString target)
int zoomLevel() const
Retrieve the current zoom level.
KAction * close(const QObject *recvr, const char *slot, QObject *parent)
virtual void resizeContents(int w, int h)
Resize the contents area.
virtual void mouseReleaseEvent(QMouseEvent *)
void displayAccessKeys()
Display all accesskeys in small tooltips.
KHTMLPart * parentPart()
Returns a pointer to the parent KHTMLPart if the part is a frame in an HTML frameset.
static void setInPaintEventFlag(QWidget *w, bool b=true, bool recurse=true)
void slotPaletteChanged()