2 * Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies)
3 * Copyright (C) 2009 Girish Ramakrishnan <girish@forwardbias.in>
4 * Copyright (C) 2006 George Staikos <staikos@kde.org>
5 * Copyright (C) 2006 Dirk Mueller <mueller@kde.org>
6 * Copyright (C) 2006 Zack Rusin <zack@kde.org>
7 * Copyright (C) 2006 Simon Hausmann <hausmann@kde.org>
11 * Redistribution and use in source and binary forms, with or without
12 * modification, are permitted provided that the following conditions
14 * 1. Redistributions of source code must retain the above copyright
15 * notice, this list of conditions and the following disclaimer.
16 * 2. Redistributions in binary form must reproduce the above copyright
17 * notice, this list of conditions and the following disclaimer in the
18 * documentation and/or other materials provided with the distribution.
20 * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
21 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
23 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
24 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
25 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
26 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
27 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
28 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
29 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
30 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
33 #include "launcherwindow.h"
35 const int gExitClickArea = 80;
36 QVector<int> LauncherWindow::m_zoomLevels;
38 LauncherWindow::LauncherWindow(WindowOptions* data, QGraphicsScene* sharedScene)
43 , m_formatMenuAction(0)
47 m_windowOptions = *data;
50 if (sharedScene && data->useGraphicsView)
51 static_cast<QGraphicsView*>(m_view)->setScene(sharedScene);
56 LauncherWindow::~LauncherWindow()
61 page()->setQnamThreaded(false);
64 void LauncherWindow::init()
66 QSplitter* splitter = new QSplitter(Qt::Vertical, this);
67 setCentralWidget(splitter);
69 #if defined(Q_OS_SYMBIAN)
70 setWindowState(Qt::WindowMaximized);
72 setWindowState(Qt::WindowNoState);
76 m_inspector = new WebInspector;
77 #ifndef QT_NO_PROPERTIES
78 if (!m_windowOptions.inspectorUrl.isEmpty())
79 m_inspector->setProperty("_q_inspectorUrl", m_windowOptions.inspectorUrl);
81 connect(this, SIGNAL(destroyed()), m_inspector, SLOT(deleteLater()));
83 // the zoom values are chosen to be like in Mozilla Firefox 3
84 if (!m_zoomLevels.count()) {
85 m_zoomLevels << 30 << 50 << 67 << 80 << 90;
87 m_zoomLevels << 110 << 120 << 133 << 150 << 170 << 200 << 240 << 300;
95 void LauncherWindow::initializeView()
99 m_inputUrl = addressUrl();
100 QUrl url = page()->mainFrame()->url();
101 setPage(new WebPage(this));
102 page()->setQnamThreaded(m_windowOptions.useThreadedQnam);
104 QSplitter* splitter = static_cast<QSplitter*>(centralWidget());
106 if (!m_windowOptions.useGraphicsView) {
107 WebViewTraditional* view = new WebViewTraditional(splitter);
108 view->setPage(page());
110 view->installEventFilter(this);
114 WebViewGraphicsBased* view = new WebViewGraphicsBased(splitter);
115 view->setPage(page());
117 connect(view, SIGNAL(currentFPSUpdated(int)), this, SLOT(updateFPS(int)));
119 view->installEventFilter(this);
120 // The implementation of QAbstractScrollArea::eventFilter makes us need
121 // to install the event filter also on the viewport of a QGraphicsView.
122 view->viewport()->installEventFilter(this);
127 m_touchMocking = false;
129 connect(page(), SIGNAL(loadStarted()), this, SLOT(loadStarted()));
130 connect(page(), SIGNAL(loadFinished(bool)), this, SLOT(loadFinished()));
131 connect(page(), SIGNAL(linkHovered(const QString&, const QString&, const QString&)),
132 this, SLOT(showLinkHover(const QString&, const QString&)));
133 connect(this, SIGNAL(enteredFullScreenMode(bool)), this, SLOT(toggleFullScreenMode(bool)));
137 splitter->addWidget(m_inspector);
138 m_inspector->setPage(page());
141 if (m_windowOptions.remoteInspectorPort)
142 page()->setProperty("_q_webInspectorServerPort", m_windowOptions.remoteInspectorPort);
145 page()->mainFrame()->load(url);
147 setAddressUrl(m_inputUrl);
148 m_inputUrl = QString();
152 void LauncherWindow::applyPrefs()
154 QWebSettings* settings = page()->settings();
155 settings->setAttribute(QWebSettings::AcceleratedCompositingEnabled, m_windowOptions.useCompositing);
156 settings->setAttribute(QWebSettings::TiledBackingStoreEnabled, m_windowOptions.useTiledBackingStore);
157 settings->setAttribute(QWebSettings::FrameFlatteningEnabled, m_windowOptions.useFrameFlattening);
158 settings->setAttribute(QWebSettings::WebGLEnabled, m_windowOptions.useWebGL);
160 if (!isGraphicsBased())
163 WebViewGraphicsBased* view = static_cast<WebViewGraphicsBased*>(m_view);
164 view->setViewportUpdateMode(m_windowOptions.viewportUpdateMode);
165 view->setFrameRateMeasurementEnabled(m_windowOptions.showFrameRate);
166 view->setItemCacheMode(m_windowOptions.cacheWebView ? QGraphicsItem::DeviceCoordinateCache : QGraphicsItem::NoCache);
168 if (m_windowOptions.resizesToContents)
169 toggleResizesToContents(m_windowOptions.resizesToContents);
172 void LauncherWindow::createChrome()
174 #ifndef QT_NO_SHORTCUT
175 QMenu* fileMenu = menuBar()->addMenu("&File");
176 fileMenu->addAction("New Window", this, SLOT(newWindow()), QKeySequence::New);
177 fileMenu->addAction(tr("Open File..."), this, SLOT(openFile()), QKeySequence::Open);
178 fileMenu->addAction(tr("Open Location..."), this, SLOT(openLocation()), QKeySequence(Qt::CTRL | Qt::Key_L));
179 fileMenu->addAction("Close Window", this, SLOT(close()), QKeySequence::Close);
180 fileMenu->addSeparator();
181 fileMenu->addAction("Take Screen Shot...", this, SLOT(screenshot()));
182 #ifndef QT_NO_PRINTER
183 fileMenu->addAction(tr("Print..."), this, SLOT(print()), QKeySequence::Print);
185 fileMenu->addSeparator();
186 fileMenu->addAction("Quit", QApplication::instance(), SLOT(closeAllWindows()), QKeySequence(Qt::CTRL | Qt::Key_Q));
188 QMenu* editMenu = menuBar()->addMenu("&Edit");
189 editMenu->addAction(page()->action(QWebPage::Undo));
190 editMenu->addAction(page()->action(QWebPage::Redo));
191 editMenu->addSeparator();
192 editMenu->addAction(page()->action(QWebPage::Cut));
193 editMenu->addAction(page()->action(QWebPage::Copy));
194 editMenu->addAction(page()->action(QWebPage::Paste));
195 editMenu->addSeparator();
196 QAction* setEditable = editMenu->addAction("Set Editable", this, SLOT(setEditable(bool)));
197 setEditable->setCheckable(true);
199 QMenu* viewMenu = menuBar()->addMenu("&View");
200 viewMenu->addAction(page()->action(QWebPage::Stop));
201 viewMenu->addAction(page()->action(QWebPage::Reload));
202 viewMenu->addSeparator();
203 QAction* zoomIn = viewMenu->addAction("Zoom &In", this, SLOT(zoomIn()));
204 QAction* zoomOut = viewMenu->addAction("Zoom &Out", this, SLOT(zoomOut()));
205 QAction* resetZoom = viewMenu->addAction("Reset Zoom", this, SLOT(resetZoom()));
206 QAction* zoomTextOnly = viewMenu->addAction("Zoom Text Only", this, SLOT(toggleZoomTextOnly(bool)));
207 zoomTextOnly->setCheckable(true);
208 zoomTextOnly->setChecked(false);
209 viewMenu->addSeparator();
210 viewMenu->addAction("Dump HTML", this, SLOT(dumpHtml()));
211 // viewMenu->addAction("Dump plugins", this, SLOT(dumpPlugins()));
213 zoomIn->setShortcut(QKeySequence(Qt::CTRL | Qt::Key_Plus));
214 zoomOut->setShortcut(QKeySequence(Qt::CTRL | Qt::Key_Minus));
215 resetZoom->setShortcut(QKeySequence(Qt::CTRL | Qt::Key_0));
217 QMenu* formatMenu = new QMenu("F&ormat", this);
218 m_formatMenuAction = menuBar()->addMenu(formatMenu);
219 m_formatMenuAction->setVisible(false);
220 formatMenu->addAction(page()->action(QWebPage::ToggleBold));
221 formatMenu->addAction(page()->action(QWebPage::ToggleItalic));
222 formatMenu->addAction(page()->action(QWebPage::ToggleUnderline));
223 QMenu* writingMenu = formatMenu->addMenu(tr("Writing Direction"));
224 writingMenu->addAction(page()->action(QWebPage::SetTextDirectionDefault));
225 writingMenu->addAction(page()->action(QWebPage::SetTextDirectionLeftToRight));
226 writingMenu->addAction(page()->action(QWebPage::SetTextDirectionRightToLeft));
228 QMenu* windowMenu = menuBar()->addMenu("&Window");
229 QAction* toggleFullScreen = windowMenu->addAction("Toggle FullScreen", this, SIGNAL(enteredFullScreenMode(bool)));
230 toggleFullScreen->setShortcut(Qt::Key_F11);
231 toggleFullScreen->setCheckable(true);
232 toggleFullScreen->setChecked(false);
233 // When exit fullscreen mode by clicking on the exit area (bottom right corner) we must
234 // uncheck the Toggle FullScreen action.
235 toggleFullScreen->connect(this, SIGNAL(enteredFullScreenMode(bool)), SLOT(setChecked(bool)));
237 QWebSettings* settings = page()->settings();
239 QMenu* toolsMenu = menuBar()->addMenu("&Develop");
240 QMenu* graphicsViewMenu = toolsMenu->addMenu("QGraphicsView");
241 QAction* toggleGraphicsView = graphicsViewMenu->addAction("Toggle use of QGraphicsView", this, SLOT(toggleWebView(bool)));
242 toggleGraphicsView->setCheckable(true);
243 toggleGraphicsView->setChecked(isGraphicsBased());
245 QAction* toggleWebGL = toolsMenu->addAction("Toggle WebGL", this, SLOT(toggleWebGL(bool)));
246 toggleWebGL->setCheckable(true);
247 toggleWebGL->setChecked(settings->testAttribute(QWebSettings::WebGLEnabled));
249 QAction* toggleThreadedQnam = toolsMenu->addAction("Toggle threaded network", this, SLOT(toggleThreadedQnam(bool)));
250 toggleThreadedQnam->setCheckable(true);
251 toggleThreadedQnam->setChecked(m_windowOptions.useThreadedQnam);
253 QAction* spatialNavigationAction = toolsMenu->addAction("Toggle Spatial Navigation", this, SLOT(toggleSpatialNavigation(bool)));
254 spatialNavigationAction->setCheckable(true);
255 spatialNavigationAction->setShortcut(QKeySequence(Qt::CTRL | Qt::SHIFT | Qt::Key_S));
257 QAction* toggleFrameFlattening = toolsMenu->addAction("Toggle Frame Flattening", this, SLOT(toggleFrameFlattening(bool)));
258 toggleFrameFlattening->setCheckable(true);
259 toggleFrameFlattening->setChecked(settings->testAttribute(QWebSettings::FrameFlatteningEnabled));
261 QAction* touchMockAction = toolsMenu->addAction("Toggle touch mocking", this, SLOT(setTouchMocking(bool)));
262 touchMockAction->setCheckable(true);
263 touchMockAction->setShortcut(QKeySequence(Qt::CTRL | Qt::ALT | Qt::Key_T));
265 toolsMenu->addSeparator();
267 QAction* toggleLocalStorage = toolsMenu->addAction("Enable Local Storage", this, SLOT(toggleLocalStorage(bool)));
268 toggleLocalStorage->setCheckable(true);
269 toggleLocalStorage->setChecked(m_windowOptions.useLocalStorage);
271 QAction* toggleOfflineStorageDatabase = toolsMenu->addAction("Enable Offline Storage Database", this, SLOT(toggleOfflineStorageDatabase(bool)));
272 toggleOfflineStorageDatabase->setCheckable(true);
273 toggleOfflineStorageDatabase->setChecked(m_windowOptions.useOfflineStorageDatabase);
275 QAction* toggleOfflineWebApplicationCache = toolsMenu->addAction("Enable Offline Web Application Cache", this, SLOT(toggleOfflineWebApplicationCache(bool)));
276 toggleOfflineWebApplicationCache->setCheckable(true);
277 toggleOfflineWebApplicationCache->setChecked(m_windowOptions.useOfflineWebApplicationCache);
279 QAction* offlineStorageDefaultQuotaAction = toolsMenu->addAction("Set Offline Storage Default Quota Size", this, SLOT(setOfflineStorageDefaultQuota()));
280 offlineStorageDefaultQuotaAction->setCheckable(true);
281 offlineStorageDefaultQuotaAction->setChecked(m_windowOptions.offlineStorageDefaultQuotaSize);
283 toolsMenu->addSeparator();
285 QAction* userAgentAction = toolsMenu->addAction("Change User Agent", this, SLOT(showUserAgentDialog()));
286 userAgentAction->setShortcut(QKeySequence(Qt::CTRL | Qt::SHIFT | Qt::Key_U));
288 toolsMenu->addAction("Select Elements...", this, SLOT(selectElements()));
290 QAction* showInspectorAction = toolsMenu->addAction("Show Web Inspector", m_inspector, SLOT(setVisible(bool)), QKeySequence(Qt::CTRL | Qt::ALT | Qt::Key_I));
291 showInspectorAction->setCheckable(true);
292 showInspectorAction->connect(m_inspector, SIGNAL(visibleChanged(bool)), SLOT(setChecked(bool)));
294 // GraphicsView sub menu.
295 QAction* toggleAcceleratedCompositing = graphicsViewMenu->addAction("Toggle Accelerated Compositing", this, SLOT(toggleAcceleratedCompositing(bool)));
296 toggleAcceleratedCompositing->setCheckable(true);
297 toggleAcceleratedCompositing->setChecked(settings->testAttribute(QWebSettings::AcceleratedCompositingEnabled));
298 toggleAcceleratedCompositing->setEnabled(isGraphicsBased());
299 toggleAcceleratedCompositing->connect(toggleGraphicsView, SIGNAL(toggled(bool)), SLOT(setEnabled(bool)));
301 QAction* toggleResizesToContents = graphicsViewMenu->addAction("Toggle Resizes To Contents Mode", this, SLOT(toggleResizesToContents(bool)));
302 toggleResizesToContents->setCheckable(true);
303 toggleResizesToContents->setChecked(m_windowOptions.resizesToContents);
304 toggleResizesToContents->setEnabled(isGraphicsBased());
305 toggleResizesToContents->connect(toggleGraphicsView, SIGNAL(toggled(bool)), SLOT(setEnabled(bool)));
307 QAction* toggleTiledBackingStore = graphicsViewMenu->addAction("Toggle Tiled Backing Store", this, SLOT(toggleTiledBackingStore(bool)));
308 toggleTiledBackingStore->setCheckable(true);
309 toggleTiledBackingStore->setChecked(m_windowOptions.useTiledBackingStore);
310 toggleTiledBackingStore->setEnabled(isGraphicsBased());
311 toggleTiledBackingStore->connect(toggleGraphicsView, SIGNAL(toggled(bool)), SLOT(setEnabled(bool)));
313 #if defined(QT_CONFIGURED_WITH_OPENGL)
314 QAction* toggleQGLWidgetViewport = graphicsViewMenu->addAction("Toggle use of QGLWidget Viewport", this, SLOT(toggleQGLWidgetViewport(bool)));
315 toggleQGLWidgetViewport->setCheckable(true);
316 toggleQGLWidgetViewport->setChecked(m_windowOptions.useQGLWidgetViewport);
317 toggleQGLWidgetViewport->setEnabled(isGraphicsBased());
318 toggleQGLWidgetViewport->connect(toggleGraphicsView, SIGNAL(toggled(bool)), SLOT(setEnabled(bool)));
321 QMenu* viewportUpdateMenu = graphicsViewMenu->addMenu("Change Viewport Update Mode");
322 viewportUpdateMenu->setEnabled(isGraphicsBased());
323 viewportUpdateMenu->connect(toggleGraphicsView, SIGNAL(toggled(bool)), SLOT(setEnabled(bool)));
325 QAction* fullUpdate = viewportUpdateMenu->addAction("FullViewportUpdate");
326 fullUpdate->setCheckable(true);
327 fullUpdate->setChecked((m_windowOptions.viewportUpdateMode == QGraphicsView::FullViewportUpdate) ? true : false);
329 QAction* minimalUpdate = viewportUpdateMenu->addAction("MinimalViewportUpdate");
330 minimalUpdate->setCheckable(true);
331 minimalUpdate->setChecked((m_windowOptions.viewportUpdateMode == QGraphicsView::MinimalViewportUpdate) ? true : false);
333 QAction* smartUpdate = viewportUpdateMenu->addAction("SmartViewportUpdate");
334 smartUpdate->setCheckable(true);
335 smartUpdate->setChecked((m_windowOptions.viewportUpdateMode == QGraphicsView::SmartViewportUpdate) ? true : false);
337 QAction* boundingRectUpdate = viewportUpdateMenu->addAction("BoundingRectViewportUpdate");
338 boundingRectUpdate->setCheckable(true);
339 boundingRectUpdate->setChecked((m_windowOptions.viewportUpdateMode == QGraphicsView::BoundingRectViewportUpdate) ? true : false);
341 QAction* noUpdate = viewportUpdateMenu->addAction("NoViewportUpdate");
342 noUpdate->setCheckable(true);
343 noUpdate->setChecked((m_windowOptions.viewportUpdateMode == QGraphicsView::NoViewportUpdate) ? true : false);
345 QSignalMapper* signalMapper = new QSignalMapper(viewportUpdateMenu);
346 signalMapper->setMapping(fullUpdate, QGraphicsView::FullViewportUpdate);
347 signalMapper->setMapping(minimalUpdate, QGraphicsView::MinimalViewportUpdate);
348 signalMapper->setMapping(smartUpdate, QGraphicsView::SmartViewportUpdate);
349 signalMapper->setMapping(boundingRectUpdate, QGraphicsView::BoundingRectViewportUpdate);
350 signalMapper->setMapping(noUpdate, QGraphicsView::NoViewportUpdate);
352 connect(fullUpdate, SIGNAL(triggered()), signalMapper, SLOT(map()));
353 connect(minimalUpdate, SIGNAL(triggered()), signalMapper, SLOT(map()));
354 connect(smartUpdate, SIGNAL(triggered()), signalMapper, SLOT(map()));
355 connect(boundingRectUpdate, SIGNAL(triggered()), signalMapper, SLOT(map()));
356 connect(noUpdate, SIGNAL(triggered()), signalMapper, SLOT(map()));
358 connect(signalMapper, SIGNAL(mapped(int)), this, SLOT(changeViewportUpdateMode(int)));
360 QActionGroup* viewportUpdateModeActions = new QActionGroup(viewportUpdateMenu);
361 viewportUpdateModeActions->addAction(fullUpdate);
362 viewportUpdateModeActions->addAction(minimalUpdate);
363 viewportUpdateModeActions->addAction(smartUpdate);
364 viewportUpdateModeActions->addAction(boundingRectUpdate);
365 viewportUpdateModeActions->addAction(noUpdate);
367 graphicsViewMenu->addSeparator();
369 QAction* flipAnimated = graphicsViewMenu->addAction("Animated Flip");
370 flipAnimated->connect(toggleGraphicsView, SIGNAL(toggled(bool)), SLOT(setEnabled(bool)));
371 flipAnimated->setEnabled(isGraphicsBased());
372 connect(flipAnimated, SIGNAL(triggered()), SLOT(animatedFlip()));
374 QAction* flipYAnimated = graphicsViewMenu->addAction("Animated Y-Flip");
375 flipYAnimated->connect(toggleGraphicsView, SIGNAL(toggled(bool)), SLOT(setEnabled(bool)));
376 flipYAnimated->setEnabled(isGraphicsBased());
377 connect(flipYAnimated, SIGNAL(triggered()), SLOT(animatedYFlip()));
379 QAction* cloneWindow = graphicsViewMenu->addAction("Clone Window", this, SLOT(cloneWindow()));
380 cloneWindow->connect(toggleGraphicsView, SIGNAL(toggled(bool)), SLOT(setEnabled(bool)));
381 cloneWindow->setEnabled(isGraphicsBased());
383 graphicsViewMenu->addSeparator();
385 QAction* showFPS = graphicsViewMenu->addAction("Show FPS", this, SLOT(showFPS(bool)));
386 showFPS->setCheckable(true);
387 showFPS->setEnabled(isGraphicsBased());
388 showFPS->connect(toggleGraphicsView, SIGNAL(toggled(bool)), SLOT(setEnabled(bool)));
389 showFPS->setChecked(m_windowOptions.showFrameRate);
391 QMenu* settingsMenu = menuBar()->addMenu("&Settings");
393 QAction* toggleAutoLoadImages = settingsMenu->addAction("Disable Auto Load Images", this, SLOT(toggleAutoLoadImages(bool)));
394 toggleAutoLoadImages->setCheckable(true);
395 toggleAutoLoadImages->setChecked(false);
397 QAction* togglePlugins = settingsMenu->addAction("Disable Plugins", this, SLOT(togglePlugins(bool)));
398 togglePlugins->setCheckable(true);
399 togglePlugins->setChecked(false);
401 QAction* toggleInterruptingJavaScripteEnabled = settingsMenu->addAction("Enable interrupting js scripts", this, SLOT(toggleInterruptingJavaScriptEnabled(bool)));
402 toggleInterruptingJavaScripteEnabled->setCheckable(true);
403 toggleInterruptingJavaScripteEnabled->setChecked(false);
405 QAction* toggleJavascriptCanOpenWindows = settingsMenu->addAction("Enable js popup windows", this, SLOT(toggleJavascriptCanOpenWindows(bool)));
406 toggleJavascriptCanOpenWindows->setCheckable(true);
407 toggleJavascriptCanOpenWindows->setChecked(false);
412 bool LauncherWindow::isGraphicsBased() const
414 return bool(qobject_cast<QGraphicsView*>(m_view));
417 void LauncherWindow::keyPressEvent(QKeyEvent* event)
420 switch (event->key()) {
431 MainWindow::keyPressEvent(event);
434 void LauncherWindow::grabZoomKeys(bool grab)
438 qWarning("Can't grab keys unless we have a window id");
442 Atom atom = XInternAtom(QX11Info::display(), "_HILDON_ZOOM_KEY_ATOM", False);
444 qWarning("Unable to obtain _HILDON_ZOOM_KEY_ATOM");
448 unsigned long val = (grab) ? 1 : 0;
449 XChangeProperty(QX11Info::display(), winId(), atom, XA_INTEGER, 32, PropModeReplace, reinterpret_cast<unsigned char*>(&val), 1);
453 void LauncherWindow::sendTouchEvent()
455 if (m_touchPoints.isEmpty())
458 QEvent::Type type = QEvent::TouchUpdate;
459 if (m_touchPoints.size() == 1) {
460 if (m_touchPoints[0].state() == Qt::TouchPointReleased)
461 type = QEvent::TouchEnd;
462 else if (m_touchPoints[0].state() == Qt::TouchPointPressed)
463 type = QEvent::TouchBegin;
466 QTouchEvent touchEv(type);
467 touchEv.setTouchPoints(m_touchPoints);
468 QCoreApplication::sendEvent(page(), &touchEv);
470 // After sending the event, remove all touchpoints that were released
471 if (m_touchPoints[0].state() == Qt::TouchPointReleased)
472 m_touchPoints.removeAt(0);
473 if (m_touchPoints.size() > 1 && m_touchPoints[1].state() == Qt::TouchPointReleased)
474 m_touchPoints.removeAt(1);
477 bool LauncherWindow::eventFilter(QObject* obj, QEvent* event)
479 // If click pos is the bottom right corner (square with size defined by gExitClickArea)
480 // and the window is on FullScreen, the window must return to its original state.
481 if (event->type() == QEvent::MouseButtonRelease) {
482 QMouseEvent* ev = static_cast<QMouseEvent*>(event);
483 if (windowState() == Qt::WindowFullScreen
484 && ev->pos().x() > (width() - gExitClickArea)
485 && ev->pos().y() > (height() - gExitClickArea)) {
487 emit enteredFullScreenMode(false);
492 return QObject::eventFilter(obj, event);
494 if (event->type() == QEvent::MouseButtonPress
495 || event->type() == QEvent::MouseButtonRelease
496 || event->type() == QEvent::MouseButtonDblClick
497 || event->type() == QEvent::MouseMove) {
499 QMouseEvent* ev = static_cast<QMouseEvent*>(event);
500 if (ev->type() == QEvent::MouseMove
501 && !(ev->buttons() & Qt::LeftButton))
504 QTouchEvent::TouchPoint touchPoint;
505 touchPoint.setState(Qt::TouchPointMoved);
506 if ((ev->type() == QEvent::MouseButtonPress
507 || ev->type() == QEvent::MouseButtonDblClick))
508 touchPoint.setState(Qt::TouchPointPressed);
509 else if (ev->type() == QEvent::MouseButtonRelease)
510 touchPoint.setState(Qt::TouchPointReleased);
513 touchPoint.setScreenPos(ev->globalPos());
514 touchPoint.setPos(ev->pos());
515 touchPoint.setPressure(1);
517 // If the point already exists, update it. Otherwise create it.
518 if (m_touchPoints.size() > 0 && !m_touchPoints[0].id())
519 m_touchPoints[0] = touchPoint;
520 else if (m_touchPoints.size() > 1 && !m_touchPoints[1].id())
521 m_touchPoints[1] = touchPoint;
523 m_touchPoints.append(touchPoint);
526 } else if (event->type() == QEvent::KeyPress
527 && static_cast<QKeyEvent*>(event)->key() == Qt::Key_F
528 && static_cast<QKeyEvent*>(event)->modifiers() == Qt::ControlModifier) {
530 // If the keyboard point is already pressed, release it.
531 // Otherwise create it and append to m_touchPoints.
532 if (m_touchPoints.size() > 0 && m_touchPoints[0].id() == 1) {
533 m_touchPoints[0].setState(Qt::TouchPointReleased);
535 } else if (m_touchPoints.size() > 1 && m_touchPoints[1].id() == 1) {
536 m_touchPoints[1].setState(Qt::TouchPointReleased);
539 QTouchEvent::TouchPoint touchPoint;
540 touchPoint.setState(Qt::TouchPointPressed);
542 touchPoint.setScreenPos(QCursor::pos());
543 touchPoint.setPos(m_view->mapFromGlobal(QCursor::pos()));
544 touchPoint.setPressure(1);
545 m_touchPoints.append(touchPoint);
548 // After sending the event, change the touchpoint state to stationary
549 m_touchPoints.last().setState(Qt::TouchPointStationary);
556 void LauncherWindow::loadStarted()
558 m_view->setFocus(Qt::OtherFocusReason);
561 void LauncherWindow::loadFinished()
563 QUrl url = page()->mainFrame()->url();
564 addCompleterEntry(url);
565 if (m_inputUrl.isEmpty())
566 setAddressUrl(url.toString(QUrl::RemoveUserInfo));
568 setAddressUrl(m_inputUrl);
569 m_inputUrl = QString();
573 void LauncherWindow::showLinkHover(const QString &link, const QString &toolTip)
576 statusBar()->showMessage(link);
578 #ifndef QT_NO_TOOLTIP
579 if (!toolTip.isEmpty())
580 QToolTip::showText(QCursor::pos(), toolTip);
584 void LauncherWindow::zoomAnimationFinished()
586 if (!isGraphicsBased())
588 QGraphicsWebView* view = static_cast<WebViewGraphicsBased*>(m_view)->graphicsWebView();
589 view->setTiledBackingStoreFrozen(false);
592 void LauncherWindow::applyZoom()
594 #ifndef QT_NO_ANIMATION
595 if (isGraphicsBased() && page()->settings()->testAttribute(QWebSettings::TiledBackingStoreEnabled)) {
596 QGraphicsWebView* view = static_cast<WebViewGraphicsBased*>(m_view)->graphicsWebView();
597 view->setTiledBackingStoreFrozen(true);
598 if (!m_zoomAnimation) {
599 m_zoomAnimation = new QPropertyAnimation(view, "scale");
600 m_zoomAnimation->setStartValue(view->scale());
601 connect(m_zoomAnimation, SIGNAL(finished()), this, SLOT(zoomAnimationFinished()));
603 m_zoomAnimation->stop();
604 m_zoomAnimation->setStartValue(m_zoomAnimation->currentValue());
607 m_zoomAnimation->setDuration(300);
608 m_zoomAnimation->setEndValue(qreal(m_currentZoom) / 100.);
609 m_zoomAnimation->start();
613 page()->mainFrame()->setZoomFactor(qreal(m_currentZoom) / 100.0);
616 void LauncherWindow::zoomIn()
618 int i = m_zoomLevels.indexOf(m_currentZoom);
620 if (i < m_zoomLevels.count() - 1)
621 m_currentZoom = m_zoomLevels[i + 1];
626 void LauncherWindow::zoomOut()
628 int i = m_zoomLevels.indexOf(m_currentZoom);
631 m_currentZoom = m_zoomLevels[i - 1];
636 void LauncherWindow::resetZoom()
642 void LauncherWindow::toggleZoomTextOnly(bool b)
644 page()->settings()->setAttribute(QWebSettings::ZoomTextOnly, b);
647 void LauncherWindow::print()
649 #if !defined(QT_NO_PRINTER)
650 QPrintPreviewDialog dlg(this);
651 connect(&dlg, SIGNAL(paintRequested(QPrinter*)),
652 page()->mainFrame(), SLOT(print(QPrinter*)));
657 void LauncherWindow::screenshot()
659 QPixmap pixmap = QPixmap::grabWidget(m_view);
661 #if !defined(Q_OS_SYMBIAN)
663 label->setAttribute(Qt::WA_DeleteOnClose);
664 label->setWindowTitle("Screenshot - Preview");
665 label->setPixmap(pixmap);
669 #ifndef QT_NO_FILEDIALOG
670 QString fileName = QFileDialog::getSaveFileName(label, "Screenshot");
671 if (!fileName.isEmpty()) {
672 pixmap.save(fileName, "png");
674 label->setWindowTitle(QString("Screenshot - Saved at %1").arg(fileName));
678 #if defined(QT_CONFIGURED_WITH_OPENGL)
679 toggleQGLWidgetViewport(m_windowOptions.useQGLWidgetViewport);
683 void LauncherWindow::setEditable(bool on)
685 page()->setContentEditable(on);
686 m_formatMenuAction->setVisible(on);
690 void LauncherWindow::dumpPlugins() {
691 QList<QWebPluginInfo> plugins = QWebSettings::pluginDatabase()->plugins();
692 foreach (const QWebPluginInfo plugin, plugins) {
693 qDebug() << "Plugin:" << plugin.name();
694 foreach (const QWebPluginInfo::MimeType mime, plugin.mimeTypes()) {
695 qDebug() << " " << mime.name;
701 void LauncherWindow::dumpHtml()
703 qDebug() << "HTML: " << page()->mainFrame()->toHtml();
706 void LauncherWindow::selectElements()
708 #ifndef QT_NO_INPUTDIALOG
710 QString str = QInputDialog::getText(this, "Select elements", "Choose elements",
711 QLineEdit::Normal, "a", &ok);
713 if (ok && !str.isEmpty()) {
714 QWebElementCollection result = page()->mainFrame()->findAllElements(str);
715 foreach (QWebElement e, result)
716 e.setStyleProperty("background-color", "yellow");
718 statusBar()->showMessage(QString("%1 element(s) selected").arg(result.count()), 5000);
724 void LauncherWindow::setTouchMocking(bool on)
729 void LauncherWindow::toggleWebView(bool graphicsBased)
731 m_windowOptions.useGraphicsView = graphicsBased;
737 void LauncherWindow::toggleAcceleratedCompositing(bool toggle)
739 m_windowOptions.useCompositing = toggle;
740 page()->settings()->setAttribute(QWebSettings::AcceleratedCompositingEnabled, toggle);
743 void LauncherWindow::toggleTiledBackingStore(bool toggle)
745 page()->settings()->setAttribute(QWebSettings::TiledBackingStoreEnabled, toggle);
748 void LauncherWindow::toggleResizesToContents(bool toggle)
750 m_windowOptions.resizesToContents = toggle;
751 static_cast<WebViewGraphicsBased*>(m_view)->setResizesToContents(toggle);
754 void LauncherWindow::toggleWebGL(bool toggle)
756 m_windowOptions.useWebGL = toggle;
757 page()->settings()->setAttribute(QWebSettings::WebGLEnabled, toggle);
760 void LauncherWindow::toggleThreadedQnam(bool toggle)
762 m_windowOptions.useThreadedQnam = toggle;
763 page()->setQnamThreaded(toggle);
766 void LauncherWindow::animatedFlip()
768 qobject_cast<WebViewGraphicsBased*>(m_view)->animatedFlip();
771 void LauncherWindow::animatedYFlip()
773 qobject_cast<WebViewGraphicsBased*>(m_view)->animatedYFlip();
775 void LauncherWindow::toggleSpatialNavigation(bool b)
777 page()->settings()->setAttribute(QWebSettings::SpatialNavigationEnabled, b);
780 void LauncherWindow::toggleFullScreenMode(bool enable)
783 setWindowState(Qt::WindowFullScreen);
785 #if defined(Q_OS_SYMBIAN)
786 setWindowState(Qt::WindowMaximized);
788 setWindowState(Qt::WindowNoState);
793 void LauncherWindow::toggleFrameFlattening(bool toggle)
795 m_windowOptions.useFrameFlattening = toggle;
796 page()->settings()->setAttribute(QWebSettings::FrameFlatteningEnabled, toggle);
799 void LauncherWindow::toggleInterruptingJavaScriptEnabled(bool enable)
801 page()->setInterruptingJavaScriptEnabled(enable);
804 void LauncherWindow::toggleJavascriptCanOpenWindows(bool enable)
806 page()->settings()->setAttribute(QWebSettings::JavascriptCanOpenWindows, enable);
809 void LauncherWindow::toggleAutoLoadImages(bool enable)
811 page()->settings()->setAttribute(QWebSettings::AutoLoadImages, !enable);
814 void LauncherWindow::togglePlugins(bool enable)
816 page()->settings()->setAttribute(QWebSettings::PluginsEnabled, !enable);
819 #if defined(QT_CONFIGURED_WITH_OPENGL)
820 void LauncherWindow::toggleQGLWidgetViewport(bool enable)
822 if (!isGraphicsBased())
825 m_windowOptions.useQGLWidgetViewport = enable;
826 WebViewGraphicsBased* view = static_cast<WebViewGraphicsBased*>(m_view);
828 view->setViewport(enable ? new QGLWidget() : 0);
832 void LauncherWindow::changeViewportUpdateMode(int mode)
834 m_windowOptions.viewportUpdateMode = QGraphicsView::ViewportUpdateMode(mode);
836 if (!isGraphicsBased())
839 WebViewGraphicsBased* view = static_cast<WebViewGraphicsBased*>(m_view);
840 view->setViewportUpdateMode(m_windowOptions.viewportUpdateMode);
843 void LauncherWindow::showFPS(bool enable)
845 if (!isGraphicsBased())
848 m_windowOptions.showFrameRate = enable;
849 WebViewGraphicsBased* view = static_cast<WebViewGraphicsBased*>(m_view);
850 view->setFrameRateMeasurementEnabled(enable);
853 #if defined(Q_WS_MAEMO_5) && defined(Q_OS_SYMBIAN)
856 statusBar()->clearMessage();
861 void LauncherWindow::showUserAgentDialog()
864 QFile file(":/useragentlist.txt");
865 if (file.open(QIODevice::ReadOnly)) {
866 while (!file.atEnd())
867 items << file.readLine().trimmed();
872 QString customUserAgent = settings.value("CustomUserAgent").toString();
873 if (!items.contains(customUserAgent) && !customUserAgent.isEmpty())
874 items << customUserAgent;
876 QDialog* dialog = new QDialog(this);
877 dialog->resize(size().width() * 0.7, dialog->size().height());
878 dialog->setMaximumHeight(dialog->size().height());
879 dialog->setWindowTitle("Change User Agent");
881 QVBoxLayout* layout = new QVBoxLayout(dialog);
882 dialog->setLayout(layout);
884 #ifndef QT_NO_COMBOBOX
885 QComboBox* combo = new QComboBox(dialog);
886 combo->setSizeAdjustPolicy(QComboBox::AdjustToMinimumContentsLength);
887 combo->setEditable(true);
888 combo->insertItems(0, items);
889 layout->addWidget(combo);
891 int index = combo->findText(page()->userAgentForUrl(QUrl()));
892 combo->setCurrentIndex(index);
895 QDialogButtonBox* buttonBox = new QDialogButtonBox(QDialogButtonBox::Ok
896 | QDialogButtonBox::Cancel, Qt::Horizontal, dialog);
897 connect(buttonBox, SIGNAL(accepted()), dialog, SLOT(accept()));
898 connect(buttonBox, SIGNAL(rejected()), dialog, SLOT(reject()));
899 layout->addWidget(buttonBox);
901 #ifndef QT_NO_COMBOBOX
902 if (dialog->exec() && !combo->currentText().isEmpty()) {
903 page()->setUserAgent(combo->currentText());
904 if (!items.contains(combo->currentText()))
905 settings.setValue("CustomUserAgent", combo->currentText());
912 void LauncherWindow::updateFPS(int fps)
914 QString fpsStatusText = QString("Current FPS: %1").arg(fps);
916 #if defined(Q_WS_MAEMO_5) && defined(Q_OS_SYMBIAN)
917 setWindowTitle(fpsStatusText);
919 statusBar()->showMessage(fpsStatusText);
923 void LauncherWindow::toggleLocalStorage(bool toggle)
925 m_windowOptions.useLocalStorage = toggle;
926 page()->settings()->setAttribute(QWebSettings::LocalStorageEnabled, toggle);
929 void LauncherWindow::toggleOfflineStorageDatabase(bool toggle)
931 m_windowOptions.useOfflineStorageDatabase = toggle;
932 page()->settings()->setAttribute(QWebSettings::OfflineStorageDatabaseEnabled, toggle);
935 void LauncherWindow::toggleOfflineWebApplicationCache(bool toggle)
937 m_windowOptions.useOfflineWebApplicationCache = toggle;
938 page()->settings()->setAttribute(QWebSettings::OfflineWebApplicationCacheEnabled, toggle);
941 void LauncherWindow::setOfflineStorageDefaultQuota()
943 // For command line execution, quota size is taken from command line.
944 if (m_windowOptions.offlineStorageDefaultQuotaSize)
945 page()->settings()->setOfflineStorageDefaultQuota(m_windowOptions.offlineStorageDefaultQuotaSize);
948 // Maximum size is set to 25 * 1024 * 1024.
949 int quotaSize = QInputDialog::getInt(this, "Offline Storage Default Quota Size" , "Quota Size", 0, 0, 26214400, 1, &ok);
951 page()->settings()->setOfflineStorageDefaultQuota(quotaSize);
955 LauncherWindow* LauncherWindow::newWindow()
957 LauncherWindow* mw = new LauncherWindow(&m_windowOptions);
962 LauncherWindow* LauncherWindow::cloneWindow()
964 LauncherWindow* mw = new LauncherWindow(&m_windowOptions, qobject_cast<QGraphicsView*>(m_view)->scene());