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);
110using namespace khtml;
131class 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;
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()) {
503 s = e->getAttribute(ATTR_TITLE).string().trimmed();
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:
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();
581void 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()));
613void 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);
651void KHTMLView::setMouseEventsTarget(
QWidget* w )
653 d->m_mouseEventsTarget = w;
656QWidget* 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);
805void KHTMLView::applyTransforms(
int& x,
int& y,
int& w,
int& h)
const
808 const int z =
d->zoomLevel;
818void KHTMLView::revertTransforms(
int& x,
int& y,
int& w,
int& h)
const
823 const int z =
d->zoomLevel;
831void 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;
1031void 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;
1054bool 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()));
1279void 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);
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)
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 );
1593bool 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();
1666bool 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);
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)) {
1962 QObjectList children = w->children();
1963 foreach (
QObject*
object, children) {
1964 QWidget *widget = qobject_cast<QWidget*>(
object);
1970class 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;
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);
2243bool KHTMLView::hasLayoutPending()
2245 return d->layoutTimerId && !
d->firstLayoutPending;
2248DOM::NodeImpl *KHTMLView::nodeUnderMouse()
const
2250 return d->underMouse;
2253DOM::NodeImpl *KHTMLView::nonSharedNodeUnderMouse()
const
2255 return d->underMouseNonShared;
2258bool 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) )
2329bool 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() )
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();
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() )
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 )
2569bool KHTMLView::isScrollingFromMouseWheel()
const
2571 return d->scrollingFromWheel != QPoint(-1,-1);
2574void KHTMLView::accessKeysTimeout()
2576 d->accessKeysActivated=
false;
2577 d->accessKeysPreActivate =
false;
2578 m_part->setStatusBarText(QString(), KHTMLPart::BarOverrideText);
2583bool 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 );
2603bool 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 ))
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())
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();
2752struct 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();
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()) {
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 );
2987void KHTMLView::setMediaType(
const QString &medium )
2992QString KHTMLView::mediaType()
const
2997bool KHTMLView::pagedMode()
const
3002void KHTMLView::setWidgetVisible(RenderWidget* w,
bool vis)
3005 d->visibleWidgets.insert(w, w->widget());
3008 d->visibleWidgets.remove(w);
3011bool 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);
3178 p->drawText(0, 0, printer.width(), dy, Qt::AlignHCenter, headerMid);
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 );
3229void 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 );
3282void 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 );
3323void KHTMLView::setHasStaticBackground(
bool partial)
3326 if (
d->staticWidget == KHTMLViewPrivate::SBFull &&
m_kwp->isRedirected())
3329 d->staticWidget = partial ?
3330 KHTMLViewPrivate::SBPartial : KHTMLViewPrivate::SBFull;
3333void KHTMLView::setHasNormalBackground()
3336 if (
d->staticWidget == KHTMLViewPrivate::SBFull &&
m_kwp->isRedirected())
3339 d->staticWidget = KHTMLViewPrivate::SBNone;
3342void KHTMLView::addStaticObject(
bool fixed)
3345 d->fixedObjectsCount++;
3347 d->staticObjectsCount++;
3349 setHasStaticBackground(
true );
3352void 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);
3387void KHTMLView::restoreScrollBar()
3389 int ow = visibleWidth();
3390 QScrollArea::setVerticalScrollBarPolicy(
d->vpolicy);
3391 if (visibleWidth() != ow)
3393 d->prevScrollbarVisible = verticalScrollBar()->isVisible();
3396QStringList KHTMLView::formCompletionItems(
const QString &name)
const
3399 return QStringList();
3400 if (!
d->formCompletions)
3402 return d->formCompletions->group(
"").readEntry(name, QStringList());
3405void KHTMLView::clearCompletionHistory(
const QString& name)
3407 if (!
d->formCompletions)
3411 d->formCompletions->group(
"").writeEntry(name,
"");
3412 d->formCompletions->sync();
3415void KHTMLView::addFormCompletionItem(
const QString &name,
const QString &value)
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);
3438 items.erase(items.isEmpty() ? items.end() : --items.end());
3439 d->formCompletions->group(
"").writeEntry(name, items);
3442void KHTMLView::addNonPasswordStorableSite(
const QString& host)
3444 if (!
d->formCompletions) {
3448 KConfigGroup cg(
d->formCompletions,
"NonPasswordStorableSites");
3449 QStringList sites = cg.readEntry(
"Sites", QStringList());
3451 cg.writeEntry(
"Sites", sites);
3456void 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);
3465 cg.writeEntry(
"Sites", sites);
3469bool 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);
3479bool 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) &&
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;
3629void 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())
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);
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);
3874void 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();
3905void 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;
4081void KHTMLView::checkExternalWidgetsPosition()
4084 QRect visibleRect(contentsX(), contentsY(), visibleWidth(), visibleHeight());
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);
4100void 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 );
4120void KHTMLView::unscheduleRelayout()
4122 if (!
d->layoutTimerId)
4125 killTimer(
d->layoutTimerId);
4126 d->layoutTimerId = 0;
4129void KHTMLView::unscheduleRepaint()
4131 if (!
d->repaintTimerId)
4134 killTimer(
d->repaintTimerId);
4135 d->repaintTimerId = 0;
4138void 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);
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 );
4168void 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)
4206void 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();
4228void 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();
4252bool 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();
4324 m_part->emitCaretPositionChanged(pos);
4326 m_part->notifySelectionChanged();
4330 if (handled) _ke->accept();
4334#undef DEBUG_CARETMODE
This class implements the basic string we use in the DOM.
The Node interface is the primary datatype for the entire Document Object Model.
NodeImpl * handle() const
QString readEntry(const char *key, const char *aDefault=0) const
static KIconLoader * iconLoader()
static KHTMLSettings * defaultHTMLSettings()
khtml::EditorContext editor_context
This class is khtml's main class.
KHTMLView * view() const
Returns a pointer to the HTML document's view.
bool isEditable() const
Returns true if the document is editable, false otherwise.
KHTMLPart * parentPart()
Returns a pointer to the parent KHTMLPart if the part is a frame in an HTML frameset.
void nodeActivated(const DOM::Node &)
This signal is emitted when an element retrieves the keyboard focus.
void setCaretVisible(bool show)
Sets the visibility of the caret.
virtual void begin(const KUrl &url=KUrl(), int xOffset=0, int yOffset=0)
Clears the widget and prepares it for new content.
const KHTMLSettings * settings() const
QList< KParts::ReadOnlyPart * > frames() const
int fontScaleFactor() const
Returns the current font scale factor.
bool isCaretMode() const
Returns whether caret mode is on/off.
QCursor urlCursor() const
Returns the cursor which is used when the cursor is on a link.
bool frameExists(const QString &frameName)
Returns whether a frame with the specified name is exists or not.
int maxFormCompletionItems() const
QList< QPair< QString, QChar > > fallbackAccessKeysAssignments() const
bool isFormCompletionEnabled() const
bool accessKeysEnabled() const
bool changeCursor() const
Renders and displays HTML in a QScrollArea.
void slotPaletteChanged()
virtual void closeEvent(QCloseEvent *)
void addChild(QWidget *child, int dx, int dy)
void repaintContents(const QRect &r)
Requests an immediate repaint of the content area.
KHTMLPart * part() const
Returns a pointer to the KHTMLPart that is rendering the page.
int contentsWidth() const
Returns the contents area's width.
void finishedLayout()
This signal is used for internal layouting.
virtual void resizeEvent(QResizeEvent *event)
void displayAccessKeys()
Display all accesskeys in small tooltips.
virtual void mousePressEvent(QMouseEvent *)
virtual void focusOutEvent(QFocusEvent *)
void setContentsPos(int x, int y)
Place the contents area point x/y at the top left of the viewport.
void setMarginHeight(int y)
virtual void dropEvent(QDropEvent *)
virtual void focusInEvent(QFocusEvent *)
virtual bool widgetEvent(QEvent *)
void keyPressEvent(QKeyEvent *_ke)
virtual void scrollContentsBy(int dx, int dy)
void setZoomLevel(int percent)
Apply a zoom level to the content area.
virtual void dragEnterEvent(QDragEnterEvent *)
virtual bool focusNextPrevChild(bool next)
void setSmoothScrollingModeDefault(SmoothScrollingMode m)
virtual bool event(QEvent *event)
void timerEvent(QTimerEvent *)
KHTMLView(KHTMLPart *part, QWidget *parent)
Constructs a KHTMLView.
void setMarginWidth(int x)
Sets a margin in x direction.
void layout()
ensure the display is up to date
virtual void mouseDoubleClickEvent(QMouseEvent *)
virtual void resizeContents(int w, int h)
Resize the contents area.
void setSmoothScrollingMode(SmoothScrollingMode m)
Set the smooth scrolling mode.
virtual void setHorizontalScrollBarPolicy(Qt::ScrollBarPolicy policy)
Sets horizontal scrollbar mode.
int contentsX() const
Returns the x coordinate of the contents area point that is currently located at the top left in the ...
virtual bool viewportEvent(QEvent *e)
virtual void paintEvent(QPaintEvent *)
int contentsY() const
Returns the y coordinate of the contents area point that is currently located at the top left in the ...
virtual void wheelEvent(QWheelEvent *)
int zoomLevel() const
Retrieve the current zoom level.
virtual void showEvent(QShowEvent *)
virtual void hideEvent(QHideEvent *)
virtual void mouseReleaseEvent(QMouseEvent *)
virtual void setVerticalScrollBarPolicy(Qt::ScrollBarPolicy policy)
Sets vertical scrollbar mode.
virtual void mouseMoveEvent(QMouseEvent *)
int visibleWidth() const
Returns the width of the viewport.
SmoothScrollingMode
Smooth Scrolling Mode enumeration.
void print(bool quick=false)
Prints the HTML document.
void keyReleaseEvent(QKeyEvent *_ke)
QPoint viewportToContents(const QPoint &p) const
Returns a point translated to contents area coordinates.
virtual bool eventFilter(QObject *, QEvent *)
SmoothScrollingMode smoothScrollingMode() const
Retrieve the current smooth scrolling mode.
int contentsHeight() const
Returns the contents area's height.
void scrollBy(int x, int y)
Scrolls the content area by a given amount.
void updateContents(const QRect &r)
Requests an update of the content area.
int visibleHeight() const
Returns the height of the viewport.
QPoint contentsToViewport(const QPoint &p) const
Returns a point translated to viewport coordinates.
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
QString formatDate(const QDate &date, DateFormat format=LongDate) const
static QString locateLocal(const char *type, const QString &filename, bool createDir, const KComponentData &cData=KGlobal::mainComponent())
QWeakPointer< DOM::HTMLPartContainerElementImpl > m_partContainerElement
static const int sParsingLayoutsInterval
static QString getElementText(NodeImpl *start, bool after)
static const int sSmoothScrollTick
static bool targetOpensNewWindow(KHTMLPart *part, QString target)
static const int sWayTooMany
static DOM::Position positionOfLineBegin(const DOM::Position &pos)
static const int sMaxMissedDeadlines
static DOM::Position positionOfLineBoundary(const DOM::Position &pos, bool toEnd)
static void handleWidget(QWidget *w, KHTMLView *view, bool recurse=true)
static DOM::Position positionOfLineEnd(const DOM::Position &pos)
static const int sSmoothScrollMinStaticPixels
static QMap< NodeImpl *, QString > buildLabels(NodeImpl *start)
static const int sLayoutAttemptIncrement
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
static const int sSmoothScrollTime
static const int sParsingLayoutsIncrement
static void setInPaintEventFlag(QWidget *w, bool b=true, bool recurse=true)
static const int sFirstLayoutDelay
static const int sLayoutAttemptDelay
QString i18n(const char *text)
This library provides a full-featured HTML parser and widget.
KSharedConfigPtr config()
KAction * next(const QObject *recvr, const char *slot, QObject *parent)
KAction * close(const QObject *recvr, const char *slot, QObject *parent)
QString label(StandardShortcut id)
QString csqueeze(const QString &str, int maxlen=40)
void installEventFilter(QWidget *filter)
QPrintDialog * createPrintDialog(QPrinter *printer, const QList< QWidget * > &customTabs, QWidget *parent=0)
Contextual information about the caret and the built-in editor.
bool m_beganSelectingText
DOM::Selection m_selection
int m_xPosForVerticalArrowNavigation