2 * Copyright (C) 2013 Canonical, Ltd.
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; version 3.
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
13 * You should have received a copy of the GNU General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
18import AccountsService 0.1
20import Unity.Application 0.1
21import Ubuntu.Components 0.1
22import Ubuntu.Components.Popups 0.1
23import Ubuntu.Gestures 0.1
24import Unity.Launcher 0.1
25import LightDM 0.1 as LightDM
27import SessionBroadcast 0.1
34import Unity.Notifications 1.0 as NotificationBackend
35import Unity.Session 0.1
40 // this is only here to select the width / height of the window if not running fullscreen
41 property bool tablet: false
42 width: tablet ? units.gu(160) : applicationArguments.hasGeometry() ? applicationArguments.width() : units.gu(40)
43 height: tablet ? units.gu(100) : applicationArguments.hasGeometry() ? applicationArguments.height() : units.gu(71)
45 property real edgeSize: units.gu(2)
46 property url defaultBackground: Qt.resolvedUrl(shell.width >= units.gu(60) ? "graphics/tablet_background.jpg" : "graphics/phone_background.jpg")
47 property url background
48 readonly property real panelHeight: panel.panelHeight
50 property bool dashShown: dash.shown
52 property bool sideStageEnabled: shell.width >= units.gu(100)
53 readonly property string focusedApplicationId: ApplicationManager.focusedApplicationId
55 function activateApplication(appId) {
56 if (ApplicationManager.findApplication(appId)) {
57 ApplicationManager.requestFocusApplication(appId);
59 if (stages.locked && ApplicationManager.focusedApplicationId == appId) {
60 applicationsDisplayLoader.item.select(appId);
63 var execFlags = shell.sideStageEnabled ? ApplicationManager.NoFlag : ApplicationManager.ForceMainStage;
64 ApplicationManager.startApplication(appId, execFlags);
71 property: "applicationManager"
72 value: ApplicationManager
75 Component.onCompleted: {
76 Theme.name = "Ubuntu.Components.Themes.SuruGradient"
80 id: backgroundSettings
81 schema.id: "org.gnome.desktop.background"
83 property url gSettingsPicture: backgroundSettings.pictureUri != undefined && backgroundSettings.pictureUri.length > 0 ? backgroundSettings.pictureUri : shell.defaultBackground
84 onGSettingsPictureChanged: {
85 shell.background = gSettingsPicture
92 Keys.onVolumeUpPressed: volumeControl.volumeUp()
93 Keys.onVolumeDownPressed: volumeControl.volumeDown()
98 anchors.rightMargin: stages.overlayWidth
99 clip: stages.overlayMode && !stages.painting
103 blockInput: parent.clip
108 objectName: "underlay"
110 anchors.rightMargin: -parent.anchors.rightMargin
112 // Whether the underlay is fully covered by opaque UI elements.
113 property bool fullyCovered: panel.indicators.fullyOpened && shell.width <= panel.indicators.width
115 // Whether the user should see the topmost application surface (if there's one at all).
116 readonly property bool applicationSurfaceShouldBeSeen: stages.shown && !stages.painting && !stages.overlayMode
118 // NB! Application surfaces are stacked behind the shell one. So they can only be seen by the user
119 // through the translucent parts of the shell surface.
120 visible: !fullyCovered && !applicationSurfaceShouldBeSeen
125 opacity: dash.disappearingAnimationProgress
130 source: shell.width > shell.height ? "Dash/graphics/paper_landscape.png" : "Dash/graphics/paper_portrait.png"
131 fillMode: Image.PreserveAspectCrop
132 horizontalAlignment: Image.AlignRight
133 verticalAlignment: Image.AlignTop
140 available: !greeter.shown && !lockscreen.shown
141 hides: [stages, launcher, panel.indicators]
142 shown: disappearingAnimationProgress !== 1.0 && greeterWrapper.showProgress !== 1.0
143 enabled: disappearingAnimationProgress === 0.0 && greeterWrapper.showProgress === 0.0 && edgeDemo.dashEnabled
147 topMargin: panel.panelHeight
150 contentScale: 1.0 - 0.2 * disappearingAnimationProgress
151 opacity: 1.0 - disappearingAnimationProgress
152 property real disappearingAnimationProgress: {
153 if (stages.overlayMode) {
156 return stages.showProgress
160 // FIXME: only necessary because stages.showProgress is not animated
161 Behavior on disappearingAnimationProgress { SmoothedAnimation { velocity: 5 }}
168 direction: Direction.Leftwards
170 anchors { top: parent.top; right: parent.right; bottom: parent.bottom }
171 width: shell.edgeSize
173 property real progress: stages.width
176 if (status == DirectionalDragArea.Recognized) {
177 if (ApplicationManager.count == 0) {
178 progress = Math.max(stages.width - stagesDragHandle.width + touchX, stages.width * .3)
180 progress = stages.width - stagesDragHandle.width + touchX
187 if (ApplicationManager.count > 0 && progress < stages.width - units.gu(10)) {
190 stagesDragHandle.progress = stages.width;
199 height: parent.height
203 if (overlayMode || locked) {
206 return launcher.progress
208 return stagesDragHandle.progress
212 Behavior on x { SmoothedAnimation { velocity: 600; duration: UbuntuAnimation.FastDuration } }
214 property bool shown: false
216 property real showProgress: overlayMode ? 0 : MathUtils.clamp(1 - x / shell.width, 0, 1)
218 property bool fullyShown: x == 0
219 property bool fullyHidden: x == width
221 property bool painting: applicationsDisplayLoader.item ? applicationsDisplayLoader.item.painting : false
222 property bool fullscreen: applicationsDisplayLoader.item ? applicationsDisplayLoader.item.fullscreen : false
223 property bool overlayMode: applicationsDisplayLoader.item ? applicationsDisplayLoader.item.overlayMode : false
224 property int overlayWidth: applicationsDisplayLoader.item ? applicationsDisplayLoader.item.overlayWidth : false
225 property bool locked: applicationsDisplayLoader.item ? applicationsDisplayLoader.item.locked : false
227 function show(focusApp) {
229 panel.indicators.hide();
232 if (!ApplicationManager.focusedApplicationId && ApplicationManager.count > 0 && focusApp) {
233 ApplicationManager.focusApplication(ApplicationManager.get(0).appId);
239 if (ApplicationManager.focusedApplicationId) {
240 ApplicationManager.unfocusCurrentApplication();
245 target: ApplicationManager
251 onFocusedApplicationIdChanged: {
252 if (ApplicationManager.focusedApplicationId.length > 0) {
255 if (!stages.overlayMode) {
261 onApplicationAdded: {
265 onApplicationRemoved: {
266 if (ApplicationManager.focusedApplicationId.length == 0) {
272 property bool dialogShown: false
279 text: "Are you sure that you want to logout?"
283 PopupUtils.close(dialogueLogout);
284 stages.dialogShown = false;
290 DBusUnitySessionService.Logout();
291 PopupUtils.close(dialogueLogout);
292 stages.dialogShown = false;
303 text: "Are you sure that you want to shutdown?"
307 PopupUtils.close(dialogueShutdown);
308 stages.dialogShown = false;
314 dBusUnitySessionServiceConnection.closeAllApps();
315 DBusUnitySessionService.Shutdown();
316 PopupUtils.close(dialogueShutdown);
317 stages.dialogShown = false;
328 text: "Are you sure that you want to reboot?"
332 PopupUtils.close(dialogueReboot)
333 stages.dialogShown = false;
339 dBusUnitySessionServiceConnection.closeAllApps();
340 DBusUnitySessionService.Reboot();
341 PopupUtils.close(dialogueReboot);
342 stages.dialogShown = false;
353 text: i18n.tr("Are you sure you would like to turn power off?")
355 text: i18n.tr("Power off")
357 dBusUnitySessionServiceConnection.closeAllApps();
358 PopupUtils.close(dialoguePower);
359 stages.dialogShown = false;
360 shutdownFadeOutRectangle.enabled = true;
361 shutdownFadeOutRectangle.visible = true;
362 shutdownFadeOut.start();
366 text: i18n.tr("Restart")
368 dBusUnitySessionServiceConnection.closeAllApps();
369 DBusUnitySessionService.Reboot();
370 PopupUtils.close(dialoguePower);
371 stages.dialogShown = false;
375 text: i18n.tr("Cancel")
377 PopupUtils.close(dialoguePower);
378 stages.dialogShown = false;
384 function showPowerDialog() {
385 if (!stages.dialogShown) {
386 stages.dialogShown = true;
387 PopupUtils.open(powerDialog);
392 id: dBusUnitySessionServiceConnection
393 objectName: "dBusUnitySessionServiceConnection"
394 target: DBusUnitySessionService
396 function closeAllApps() {
398 var app = ApplicationManager.get(0);
402 ApplicationManager.stopApplication(app.appId);
407 // Display a dialog to ask the user to confirm.
408 if (!stages.dialogShown) {
409 stages.dialogShown = true;
410 PopupUtils.open(logoutDialog);
414 onShutdownRequested: {
415 // Display a dialog to ask the user to confirm.
416 if (!stages.dialogShown) {
417 stages.dialogShown = true;
418 PopupUtils.open(shutdownDialog);
423 // Display a dialog to ask the user to confirm.
424 if (!stages.dialogShown) {
425 stages.dialogShown = true;
426 PopupUtils.open(rebootDialog);
437 id: applicationsDisplayLoader
440 source: shell.sideStageEnabled ? "Stages/StageWithSideStage.qml" : "Stages/PhoneStage.qml"
443 target: applicationsDisplayLoader.item
445 value: !stages.fullyShown
448 target: applicationsDisplayLoader.item
453 target: applicationsDisplayLoader.item
454 property: "dragAreaWidth"
455 value: shell.edgeSize
462 objectName: "lockscreen"
464 readonly property int backgroundTopMargin: -panel.panelHeight
466 hides: [launcher, panel.indicators]
469 showAnimation: StandardAnimation { property: "opacity"; to: 1 }
470 hideAnimation: StandardAnimation { property: "opacity"; to: 0 }
472 x: required ? 0 : - width
474 height: parent.height - panel.panelHeight
475 background: shell.background
479 onEntered: LightDM.Greeter.respond(passphrase);
480 onCancel: greeter.show()
482 Component.onCompleted: {
483 if (LightDM.Users.count == 1) {
484 LightDM.Greeter.authenticate(LightDM.Users.data(0, LightDM.UserRoles.NameRole))
490 target: LightDM.Greeter
492 onShowGreeter: greeter.show()
495 if (LightDM.Users.count == 1) {
496 // TODO: There's no better way for now to determine if its a PIN or a passphrase.
498 lockscreen.alphaNumeric = false
500 lockscreen.alphaNumeric = true
502 lockscreen.placeholderText = i18n.tr("Please enter %1").arg(text);
507 onAuthenticationComplete: {
508 if (LightDM.Greeter.promptless) {
511 if (LightDM.Greeter.authenticated) {
514 lockscreen.clear(true);
520 target: LightDM.Greeter
522 value: greeter.shown || lockscreen.shown
528 opacity: greeterWrapper.showProgress * 0.8
532 // Just a tiny wrapper to adjust greeter's x without messing with its own dragging
537 height: parent.height - panel.panelHeight
540 enabled: !launcher.dashSwipe
544 readonly property real showProgress: MathUtils.clamp((1 - x/width) + greeter.showProgress - 1, 0, 1)
548 objectName: "greeter"
551 hides: [launcher, panel.indicators]
554 defaultBackground: shell.background
557 height: parent.height
559 dragHandleWidth: shell.edgeSize
564 if (!LightDM.Greeter.promptless) {
567 // If there is only one user, we start authenticating with that one here.
568 // If there are more users, the Greeter will handle that
569 if (LightDM.Users.count == 1) {
570 LightDM.Greeter.authenticate(LightDM.Users.data(0, LightDM.UserRoles.NameRole));
572 greeter.forceActiveFocus();
576 onUnlocked: greeter.hide()
578 // Update launcher items for new user
579 var user = LightDM.Users.data(uid, LightDM.UserRoles.NameRole);
580 AccountsService.user = user;
581 LauncherModel.setUser(user);
584 onTease: launcher.tease()
587 target: ApplicationManager
588 property: "suspended"
589 value: greeter.shown && greeterWrapper.showProgress == 1
596 blockInput: ApplicationManager.focusedApplicationId.length === 0 || greeter.shown || lockscreen.shown || launcher.shown
597 || panel.indicators.shown
604 onDisplayPowerStateChange: {
605 // We ignore any display-off signals when the proximity sensor
606 // is active. This usually indicates something like a phone call.
607 if (status == Powerd.Off && reason != Powerd.Proximity) {
611 // No reason to chew demo CPU when user isn't watching
612 if (status == Powerd.Off) {
613 edgeDemo.paused = true;
614 } else if (status == Powerd.On) {
615 edgeDemo.paused = false;
620 function showHome() {
621 var animate = !greeter.shown && !stages.shown
623 dash.setCurrentScope("clickscope", animate, false)
634 anchors.fill: parent //because this draws indicator menus
637 available: edgeDemo.panelEnabled
638 contentEnabled: edgeDemo.panelContentEnabled
639 width: parent.width > units.gu(60) ? units.gu(40) : parent.width
640 panelHeight: units.gu(3)
642 property string focusedAppId: ApplicationManager.focusedApplicationId
643 property var focusedApplication: ApplicationManager.findApplication(focusedAppId)
644 fullscreenMode: focusedApplication && stages.fullscreen && !greeter.shown && !lockscreen.shown
652 height: (panel.fullscreenMode) ? shell.edgeSize : panel.panelHeight
658 blockInput: launcher.shown
661 bottom: parent.bottom
664 width: launcher.width
670 readonly property bool dashSwipe: progress > 0
672 anchors.top: parent.top
673 anchors.bottom: parent.bottom
675 dragAreaWidth: shell.edgeSize
676 available: edgeDemo.launcherEnabled
679 if (edgeDemo.running)
685 if (stages.shown && !stages.overlayMode && !stages.locked) {
689 launcher.switchToNextState("visible");
697 onDashSwipeChanged: if (dashSwipe && stages.shown) dash.setCurrentScope("clickscope", false, true)
698 onLauncherApplicationSelected: {
699 if (!edgeDemo.running)
700 shell.activateApplication(appId)
704 panel.indicators.hide()
710 id: modalNotificationBackground
712 visible: notifications.useModal && !greeter.shown && (notifications.state == "narrow")
723 blockInput: modalNotificationBackground.visible
730 model: NotificationBackend.Model
735 height: parent.height - panel.panelHeight
740 when: overlay.width <= units.gu(60)
741 AnchorChanges { target: notifications; anchors.left: parent.left }
745 when: overlay.width > units.gu(60)
746 AnchorChanges { target: notifications; anchors.left: undefined }
747 PropertyChanges { target: notifications; width: units.gu(38) }
752 anchors { left: parent.left; right: parent.right }
753 height: parent.contentHeight
754 blockInput: height > 0
760 onFocusChanged: if (!focus) forceActiveFocus();
765 bottom: parent.bottom
768 width: shell.edgeSize
775 bottom: parent.bottom
778 width: shell.edgeSize
789 anchors.topMargin: panel.panelHeight
790 anchors.fill: parent // as needs to know the geometry of the shell
793 //FIXME: This should be handled in the input stack, keyboard shouldnt propagate
795 anchors.bottom: parent.bottom
796 anchors.left: parent.left
797 anchors.right: parent.right
798 height: ApplicationManager.keyboardVisible ? ApplicationManager.keyboardHeight : 0
800 enabled: ApplicationManager.keyboardVisible
804 anchors.centerIn: parent
805 visible: ApplicationManager.fake ? ApplicationManager.fake : false
806 text: "EARLY ALPHA\nNOT READY FOR USE"
809 font.weight: Font.Black
810 horizontalAlignment: Text.AlignHCenter
811 verticalAlignment: Text.AlignVCenter
812 fontSizeMode: Text.Fit
814 scale: Math.min(parent.width, parent.height) / width
822 indicators: panel.indicators
827 target: SessionBroadcast
828 onShowHome: showHome()
832 if (event.key == Qt.Key_PowerOff || event.key == Qt.Key_PowerDown) {
833 if (!powerKeyTimer.running) {
834 powerKeyTimer.start();
836 event.accepted = true;
841 if (event.key == Qt.Key_PowerOff || event.key == Qt.Key_PowerDown) {
842 powerKeyTimer.stop();
843 event.accepted = true;
851 triggeredOnStart: false
854 stages.showPowerDialog();
859 id: shutdownFadeOutRectangle
865 NumberAnimation on opacity {
870 if (shutdownFadeOutRectangle.enabled && shutdownFadeOutRectangle.visible) {
871 DBusUnitySessionService.Shutdown();
keysesc to close
- j k
- move down, up
- enter
- open
- esc
- back, or up a level
- 1 2 3 4
- readme, files, commits, refs
- /
- filter
- y
- copy the clone command
- c
- compare the chosen commit with another (or shift-click both)
- ?
- show or hide this list