1
/***************************************************************************
2
* Copyright 2012 Marco Martin <mart@kde.org> *
4
* This program is free software; you can redistribute it and/or modify *
5
* it under the terms of the GNU General Public License as published by *
6
* the Free Software Foundation; either version 2 of the License, or *
7
* (at your option) any later version. *
9
* This program is distributed in the hope that it will be useful, *
10
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
11
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
12
* GNU General Public License for more details. *
14
* You should have received a copy of the GNU General Public License *
15
* along with this program; if not, write to the *
16
* Free Software Foundation, Inc., *
17
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA . *
18
***************************************************************************/
20
#include "fullscreenwindow.h"
21
#include "../core/declarativeitemcontainer_p.h"
22
#include "plasmacomponentsplugin.h"
24
#include <QApplication>
25
#include <QDeclarativeItem>
26
#include <QDeclarativeContext>
27
#include <QGraphicsObject>
28
#include <QGraphicsScene>
29
#include <QGraphicsView>
30
#include <QGraphicsWidget>
33
#include <QDesktopWidget>
36
#include <KWindowSystem>
37
#include <KStandardDirs>
39
#include <Plasma/Corona>
40
#include <Plasma/WindowEffects>
43
uint FullScreenWindow::s_numItems = 0;
45
class Background : public QWidget
48
Background(FullScreenWindow *dialog)
52
setAttribute( Qt::WA_NoSystemBackground );
53
setAttribute( Qt::WA_TranslucentBackground );
55
setWindowFlags(Qt::FramelessWindowHint | Qt::CustomizeWindowHint);
56
KWindowSystem::setOnAllDesktops(winId(), true);
57
unsigned long state = NET::Sticky | NET::StaysOnTop | NET::KeepAbove | NET::SkipTaskbar | NET::SkipPager | NET::MaxVert | NET::MaxHoriz;
58
KWindowSystem::setState(effectiveWinId(), state);
64
void paintEvent( QPaintEvent *e )
66
QPainter painter( this );
67
painter.setCompositionMode(QPainter::CompositionMode_Source);
68
painter.fillRect(e->rect(), QColor(0, 0, 0, 80));
71
void mousePressEvent(QMouseEvent *event)
74
m_dialog->view()->winId();
75
KWindowSystem::forceActiveWindow(m_dialog->view()->winId());
78
void mouseReleaseEvent(QMouseEvent *event)
80
if (!m_dialog->view()->geometry().contains(event->globalPos())) {
86
FullScreenWindow *m_dialog;
89
FullScreenWindow::FullScreenWindow(QDeclarativeItem *parent)
90
: QDeclarativeItem(parent),
91
m_declarativeItemContainer(0)
93
m_view = new QGraphicsView();
94
m_view->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
95
m_view->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
96
m_view->installEventFilter(this);
97
m_view->setAutoFillBackground(false);
98
m_view->viewport()->setAutoFillBackground(false);
99
m_view->setAttribute(Qt::WA_TranslucentBackground);
100
m_view->setAttribute(Qt::WA_NoSystemBackground);
101
m_view->viewport()->setAttribute(Qt::WA_NoSystemBackground);
102
m_view->setCacheMode(QGraphicsView::CacheNone);
103
m_view->setWindowFlags(Qt::FramelessWindowHint | Qt::CustomizeWindowHint);
104
m_view->setFrameShape(QFrame::NoFrame);
105
KWindowSystem::setOnAllDesktops(m_view->winId(), true);
106
unsigned long state = NET::Sticky | NET::StaysOnTop | NET::KeepAbove | NET::SkipTaskbar | NET::SkipPager;
107
KWindowSystem::setState(m_view->effectiveWinId(), state);
109
m_background = new Background(this);
112
FullScreenWindow::~FullScreenWindow()
117
void FullScreenWindow::init(const QString &componentName)
123
//Try to figure out the path of the dialog component
124
QString componentsPlatform = getenv("KDE_PLASMA_COMPONENTS_PLATFORM");
125
if (componentsPlatform.isEmpty()) {
126
KConfigGroup cg(KSharedConfig::openConfig("kdeclarativerc"), "Components-platform");
127
componentsPlatform = cg.readEntry("name", "desktop");
131
if (componentsPlatform == "desktop") {
132
foreach(const QString &importPath, KGlobal::dirs()->findDirs("module", "imports/")) {
133
filePath = importPath % "org/kde/plasma/components/" % componentName % ".qml";
140
foreach(const QString &importPath, KGlobal::dirs()->findDirs("module", "platformimports/" % componentsPlatform)) {
141
filePath = importPath % "org/kde/plasma/components/" % componentName % ".qml";
150
QDeclarativeEngine *engine = EngineBookKeeping::self()->engine();
152
kWarning() << "Warning, no QDeclarativeEngines available anymore, should never happen";
155
QDeclarativeComponent *component = new QDeclarativeComponent(engine, filePath, this);
157
QDeclarativeContext *creationContext = component->creationContext();
158
m_rootObject = component->create(creationContext);
159
if (component->status() == QDeclarativeComponent::Error) {
160
kWarning()<<component->errors();
164
setMainItem(qobject_cast<QGraphicsObject *>(m_rootObject.data()));
165
connect(m_rootObject.data(), SIGNAL(statusChanged()), this, SLOT(statusHasChanged()));
166
connect(m_rootObject.data(), SIGNAL(accepted()), this, SIGNAL(accepted()));
167
connect(m_rootObject.data(), SIGNAL(rejected()), this, SIGNAL(rejected()));
168
connect(m_rootObject.data(), SIGNAL(clickedOutside()), this, SIGNAL(clickedOutside()));
172
QGraphicsObject *FullScreenWindow::mainItem() const
174
return m_mainItem.data();
177
void FullScreenWindow::setMainItem(QGraphicsObject *mainItem)
179
if (m_mainItem.data() != mainItem) {
181
m_mainItem.data()->setParent(mainItem->parent());
182
m_mainItem.data()->removeEventFilter(this);
183
m_mainItem.data()->setY(0);
186
m_mainItem = mainItem;
188
mainItem->setParentItem(0);
189
mainItem->setParent(this);
190
m_scene = mainItem->scene();
193
mainItem->installEventFilter(this);
195
//if this is called in Compenent.onCompleted we have to wait a loop the item is added to a scene
196
QTimer::singleShot(0, this, SLOT(syncViewToMainItem()));
200
void FullScreenWindow::syncViewToMainItem()
206
//not have a scene? go up in the hyerarchy until we find something with a scene
207
QGraphicsScene *scene = m_mainItem.data()->scene();
209
QObject *parent = m_mainItem.data();
210
while ((parent = parent->parent())) {
211
QGraphicsObject *qo = qobject_cast<QGraphicsObject *>(parent);
216
scene->addItem(m_mainItem.data());
218
Plasma::Corona *corona = qobject_cast<Plasma::Corona *>(scene);
219
QDeclarativeItem *di = qobject_cast<QDeclarativeItem *>(m_mainItem.data());
222
if (!m_declarativeItemContainer) {
223
m_declarativeItemContainer = new DeclarativeItemContainer();
224
scene->addItem(m_declarativeItemContainer);
225
corona->addOffscreenWidget(m_declarativeItemContainer);
227
m_declarativeItemContainer->setDeclarativeItem(di);
229
m_mainItem.data()->setY(-10000*s_numItems);
230
m_mainItem.data()->setY(10000*s_numItems);
242
m_view->setScene(scene);
245
if (m_declarativeItemContainer) {
246
m_view->resize(m_declarativeItemContainer->size().toSize());
247
m_view->setSceneRect(m_declarativeItemContainer->geometry());
249
QRectF itemGeometry(QPointF(m_mainItem.data()->x(), m_mainItem.data()->y()),
250
QSizeF(m_mainItem.data()->boundingRect().size()));
251
m_view->resize(itemGeometry.size().toSize());
252
m_view->setSceneRect(itemGeometry);
255
m_view->move(QApplication::desktop()->availableGeometry().center() - QPoint(m_view->width()/2, m_view->height()/2));
258
void FullScreenWindow::syncMainItemToView()
264
m_mainItem.data()->setProperty("width", m_view->width());
265
m_mainItem.data()->setProperty("height", m_view->height());
267
if (m_declarativeItemContainer) {
268
m_view->resize(m_declarativeItemContainer->size().toSize());
269
m_view->setSceneRect(m_declarativeItemContainer->geometry());
271
QRectF itemGeometry(QPointF(m_mainItem.data()->x(), m_mainItem.data()->y()),
272
QSizeF(m_mainItem.data()->boundingRect().size()));
273
m_view->setSceneRect(itemGeometry);
277
bool FullScreenWindow::isVisible() const
279
return m_view->isVisible();
282
void FullScreenWindow::setVisible(const bool visible)
284
if (m_view->isVisible() != visible) {
285
m_background->setVisible(visible);
286
Plasma::WindowEffects::slideWindow(m_view->winId(), Plasma::BottomEdge, 0);
287
m_view->setVisible(visible);
288
unsigned long state = NET::Sticky | NET::StaysOnTop | NET::KeepAbove | NET::SkipTaskbar | NET::SkipPager;
289
KWindowSystem::setState(m_view->effectiveWinId(), state);
290
KWindowSystem::setState(m_background->effectiveWinId(), state);
293
KWindowSystem::forceActiveWindow(m_view->effectiveWinId());
298
QGraphicsView *FullScreenWindow::view() const
304
QDeclarativeListProperty<QGraphicsObject> FullScreenWindow::title()
307
return m_rootObject.data()->property("title").value<QDeclarativeListProperty<QGraphicsObject> >();
309
return QDeclarativeListProperty<QGraphicsObject>(this, m_dummyTitleElements);
313
QDeclarativeListProperty<QGraphicsObject> FullScreenWindow::content()
316
return m_rootObject.data()->property("content").value<QDeclarativeListProperty<QGraphicsObject> >();
318
return QDeclarativeListProperty<QGraphicsObject>(this, m_dummyContentElements);
322
QDeclarativeListProperty<QGraphicsObject> FullScreenWindow::buttons()
325
return m_rootObject.data()->property("buttons").value<QDeclarativeListProperty<QGraphicsObject> >();
327
return QDeclarativeListProperty<QGraphicsObject>(this, m_dummyButtonsElements);
331
DialogStatus::Status FullScreenWindow::status() const
334
return (DialogStatus::Status)m_rootObject.data()->property("status").toInt();
336
return DialogStatus::Closed;
341
void FullScreenWindow::statusHasChanged()
343
if (status() == DialogStatus::Closed) {
348
emit statusChanged();
351
void FullScreenWindow::open()
354
QMetaObject::invokeMethod(m_rootObject.data(), "open");
358
void FullScreenWindow::accept()
361
QMetaObject::invokeMethod(m_rootObject.data(), "accept");
365
void FullScreenWindow::reject()
368
QMetaObject::invokeMethod(m_rootObject.data(), "reject");
372
void FullScreenWindow::close()
375
QMetaObject::invokeMethod(m_rootObject.data(), "close");
382
bool FullScreenWindow::eventFilter(QObject *watched, QEvent *event)
384
if (watched == m_mainItem.data() &&
385
(event->type() == QEvent::GraphicsSceneResize)) {
386
syncViewToMainItem();
387
} else if (watched == m_view &&
388
(event->type() == QEvent::Resize)) {
389
syncMainItemToView();
396
#include "fullscreenwindow.moc"