Compare commits
314 Commits
wip/gcampa
...
3.9.1
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
18107d567d | ||
|
|
608818fa9f | ||
|
|
9ae2440ec1 | ||
|
|
ef9c50e63a | ||
|
|
5d50b08351 | ||
|
|
123fc19c4e | ||
|
|
a9058e471c | ||
|
|
bd1f48d9fe | ||
|
|
66ab4d217d | ||
|
|
7a8b392607 | ||
|
|
bfdf069d2d | ||
|
|
b4b00a48d9 | ||
|
|
e5f226612e | ||
|
|
20619ad3c1 | ||
|
|
37dce7d4c3 | ||
|
|
a67b82e730 | ||
|
|
e0b8ad7911 | ||
|
|
dbb39d366e | ||
|
|
e1de36398d | ||
|
|
871c28aeeb | ||
|
|
c84dc6254d | ||
|
|
60cb1ad7c5 | ||
|
|
4a5ff5dcfb | ||
|
|
5c40307745 | ||
|
|
39426f03e6 | ||
|
|
92e5d2b8f5 | ||
|
|
09aa59f98b | ||
|
|
c9c1c89a27 | ||
|
|
96b76709e9 | ||
|
|
ca3107e21b | ||
|
|
2e4f223207 | ||
|
|
17df668186 | ||
|
|
aef70152de | ||
|
|
e0252f35be | ||
|
|
0f47534766 | ||
|
|
54feaa67e8 | ||
|
|
64ecfa49eb | ||
|
|
fdae613b14 | ||
|
|
c57c08b2c6 | ||
|
|
d2103995cb | ||
|
|
196fb0f16e | ||
|
|
c0afe7260a | ||
|
|
099c8703ae | ||
|
|
b03e480dbf | ||
|
|
8430353389 | ||
|
|
a123ec94ef | ||
|
|
4a2f54f6ff | ||
|
|
b5c85eaeca | ||
|
|
8b3b91d78d | ||
|
|
e1de3973fe | ||
|
|
c1993a6ffc | ||
|
|
ab26fc438a | ||
|
|
c37259b01d | ||
|
|
bde8cc3285 | ||
|
|
59ba5504d0 | ||
|
|
65eb5a3d05 | ||
|
|
b925322e9e | ||
|
|
f0c2ad00f8 | ||
|
|
fc53a25a4c | ||
|
|
58872d162b | ||
|
|
30f1b8f02a | ||
|
|
ee4f199a9f | ||
|
|
e3957f3bac | ||
|
|
2506673514 | ||
|
|
7cb12015fd | ||
|
|
caaac9b9ec | ||
|
|
1dac4d00c4 | ||
|
|
b41902f4df | ||
|
|
ada70dd683 | ||
|
|
7e5d8a8d54 | ||
|
|
e981cae27c | ||
|
|
d7c377c229 | ||
|
|
8772edcd33 | ||
|
|
254740cf68 | ||
|
|
c3775c0f56 | ||
|
|
5ecf40e967 | ||
|
|
45026df4bd | ||
|
|
b8830f4a09 | ||
|
|
811ee1d989 | ||
|
|
8c32102e99 | ||
|
|
1b135095c7 | ||
|
|
becf4396c9 | ||
|
|
929e066506 | ||
|
|
355ad9ac2c | ||
|
|
2cda0472bd | ||
|
|
4710753700 | ||
|
|
2b439ef209 | ||
|
|
2fc76e6d9e | ||
|
|
ff544450a5 | ||
|
|
b4590da686 | ||
|
|
6c4be0311a | ||
|
|
4a2cdc20f0 | ||
|
|
6ce79c62eb | ||
|
|
96994721ef | ||
|
|
f358bb1a96 | ||
|
|
1bce210c51 | ||
|
|
8a3c8d1b1c | ||
|
|
08b224de1f | ||
|
|
86c92c37d2 | ||
|
|
07053c3df7 | ||
|
|
4fb33c9b09 | ||
|
|
5e6a25c3c2 | ||
|
|
e14ef4a294 | ||
|
|
8b659f0f4c | ||
|
|
a6395c95d4 | ||
|
|
98e74dfd38 | ||
|
|
1d728186db | ||
|
|
2499f2ed80 | ||
|
|
963905adcd | ||
|
|
7c21ab0985 | ||
|
|
77d3712261 | ||
|
|
0376f22d41 | ||
|
|
007820b7c1 | ||
|
|
dc98711477 | ||
|
|
e98c6ff31b | ||
|
|
9eae74357a | ||
|
|
1ee88a2878 | ||
|
|
14189e6827 | ||
|
|
3dd6113a0a | ||
|
|
ae5cdea5af | ||
|
|
3c1f389e25 | ||
|
|
284d821233 | ||
|
|
78272e5592 | ||
|
|
098bc41083 | ||
|
|
c837090282 | ||
|
|
cdc1678e6f | ||
|
|
2a3d76b0cc | ||
|
|
29e89491de | ||
|
|
d63947aec4 | ||
|
|
512f0a67fb | ||
|
|
a7cd4657f5 | ||
|
|
bf02cde598 | ||
|
|
b7dbb35546 | ||
|
|
6fd5f0e3de | ||
|
|
e6469df065 | ||
|
|
d61fe357f6 | ||
|
|
965dd2ab67 | ||
|
|
78e011d558 | ||
|
|
76590d6c69 | ||
|
|
16dc6ce41a | ||
|
|
1dadcee5c9 | ||
|
|
bed3bb45f7 | ||
|
|
18d850d7d6 | ||
|
|
f920fd8b6f | ||
|
|
b9da6d9ef6 | ||
|
|
3be489c69e | ||
|
|
cab092aad7 | ||
|
|
0451cba343 | ||
|
|
12334cd9ad | ||
|
|
9d18a2dff4 | ||
|
|
869e1dc241 | ||
|
|
b878f3fc4a | ||
|
|
2aeabcc38b | ||
|
|
94778c0dac | ||
|
|
390491b37a | ||
|
|
f8ea825577 | ||
|
|
f77ad7d184 | ||
|
|
e467a53def | ||
|
|
9cd2e12915 | ||
|
|
627a6587b4 | ||
|
|
9b3b419f7a | ||
|
|
f37ed44837 | ||
|
|
dddc333407 | ||
|
|
75714fb784 | ||
|
|
5a6342a5fe | ||
|
|
e07379b406 | ||
|
|
54bfe34273 | ||
|
|
bef876e4b4 | ||
|
|
6ef9ab6a0b | ||
|
|
53ffdd8d68 | ||
|
|
ba198034cb | ||
|
|
58e66b9e1b | ||
|
|
ac7efcb43a | ||
|
|
b514b9ec7c | ||
|
|
f69942eb35 | ||
|
|
f28827f625 | ||
|
|
f20a6b3635 | ||
|
|
7f7ff3ce3e | ||
|
|
0abb0756ba | ||
|
|
070ed9396c | ||
|
|
307004a455 | ||
|
|
d097327bd8 | ||
|
|
f72f501931 | ||
|
|
e9584cfcab | ||
|
|
aec0e75d73 | ||
|
|
a6b4d49454 | ||
|
|
1cc726593e | ||
|
|
5001bd8810 | ||
|
|
46aa70aa09 | ||
|
|
41cf447c45 | ||
|
|
b328fd7aed | ||
|
|
917a24580b | ||
|
|
af36182879 | ||
|
|
160c721afc | ||
|
|
ee0040ef1c | ||
|
|
9e60a55dd7 | ||
|
|
57f27572ae | ||
|
|
ceae032112 | ||
|
|
d3ab367fcd | ||
|
|
0ceefb48c8 | ||
|
|
a9815ae1e9 | ||
|
|
79140fd132 | ||
|
|
6c0f48ce25 | ||
|
|
da7ab7057d | ||
|
|
499ae609dd | ||
|
|
e78b3644e4 | ||
|
|
ce6b39bd1c | ||
|
|
603f528b47 | ||
|
|
5fecd07045 | ||
|
|
8edd7ad32e | ||
|
|
3a27d0b849 | ||
|
|
b351536dee | ||
|
|
eeea8559b6 | ||
|
|
17591117c1 | ||
|
|
c4470fd1e6 | ||
|
|
45fc7ec01f | ||
|
|
dc54472ca5 | ||
|
|
4b3bf05aaf | ||
|
|
ec014a7ecf | ||
|
|
a8c87f3bab | ||
|
|
b39e76200a | ||
|
|
01deb9ef7d | ||
|
|
5c89568cca | ||
|
|
6119b44746 | ||
|
|
7af4a7bf88 | ||
|
|
04e4d69662 | ||
|
|
a87e0f028a | ||
|
|
31774a7711 | ||
|
|
a32f27a2aa | ||
|
|
805a409318 | ||
|
|
42d45bd14a | ||
|
|
5870709fbc | ||
|
|
0fdb7430ff | ||
|
|
4771f80d6f | ||
|
|
91405583fd | ||
|
|
f864303aac | ||
|
|
e5ebf4a2b2 | ||
|
|
725a36e37a | ||
|
|
78dacfa865 | ||
|
|
16547fb3c2 | ||
|
|
9eeabf79f9 | ||
|
|
81b71cc143 | ||
|
|
8301acd4d6 | ||
|
|
f80afb1755 | ||
|
|
71c6b60054 | ||
|
|
95a1b874d8 | ||
|
|
07de96ede9 | ||
|
|
209014b083 | ||
|
|
127f10e7a8 | ||
|
|
67615a0cbc | ||
|
|
dde20f0c76 | ||
|
|
ddced79475 | ||
|
|
e80795b7f0 | ||
|
|
080337a4e8 | ||
|
|
884af3c986 | ||
|
|
edc95b2cb7 | ||
|
|
96239e95ec | ||
|
|
331ad76675 | ||
|
|
29152d3022 | ||
|
|
73fa4b1cbd | ||
|
|
7766a91e8c | ||
|
|
b7bad765aa | ||
|
|
5af09a60e9 | ||
|
|
ef623cfbbd | ||
|
|
ce5faba185 | ||
|
|
40d9ed535b | ||
|
|
d5675765f3 | ||
|
|
65067c24cc | ||
|
|
e2463cb501 | ||
|
|
de2f2d7ef1 | ||
|
|
7cdb75e7ce | ||
|
|
1502e308b8 | ||
|
|
dd1fe68e5c | ||
|
|
85c1dc5a0c | ||
|
|
7b3a689aad | ||
|
|
2c28a12cca | ||
|
|
324021fd64 | ||
|
|
1dceae97c6 | ||
|
|
0bef925b51 | ||
|
|
0ba1f29e40 | ||
|
|
3b1e536822 | ||
|
|
9a83662a18 | ||
|
|
5bcead5b5c | ||
|
|
d8f9502ea2 | ||
|
|
020128b9ca | ||
|
|
1566a4e607 | ||
|
|
fbd59631ee | ||
|
|
6c36856499 | ||
|
|
f4cda49988 | ||
|
|
a6b49fe7d6 | ||
|
|
26966b2bf3 | ||
|
|
36a7429aa0 | ||
|
|
7be1fe09f1 | ||
|
|
62bf08d323 | ||
|
|
260c082c4e | ||
|
|
5e0ff7fd56 | ||
|
|
aac312ca34 | ||
|
|
a90401454a | ||
|
|
5679e6b3a9 | ||
|
|
194574bb0e | ||
|
|
337d2da38a | ||
|
|
df848aa084 | ||
|
|
0cc1615252 | ||
|
|
d4259fa8aa | ||
|
|
157d7e2b59 | ||
|
|
ee50904147 | ||
|
|
ec39aa3890 | ||
|
|
beb0fdf4b8 | ||
|
|
443fe813c3 | ||
|
|
69cdc5a9b9 | ||
|
|
dac54a6019 | ||
|
|
e5ca53e56c | ||
|
|
7a79236bab | ||
|
|
cd37e2908f |
157
NEWS
157
NEWS
@@ -1,3 +1,160 @@
|
||||
3.9.1
|
||||
=====
|
||||
* Add additional toggle-overview keybinding [Matthias; #698251]
|
||||
* Disable <super> shortcut when sticky keys are enabled [Matthias; #685974]
|
||||
* Disable tray context menu while a notification displays [Jasper; #695800]
|
||||
* Watch GApplication busy state [Cosimo; #697207]
|
||||
* Disable style transitions if animations are disabled [Jasper; #698391]
|
||||
* Filter out hidden applications from "Frequent" view [Giovanni; #696949]
|
||||
* Fix window previews swapping place randomly [Jasper; #694469, #698776]
|
||||
* Add support for serialized GIcons in remote search providers [Cosimo; #698761]
|
||||
* Fix hotcorner regression in RTL locales [Jasper; #698884]
|
||||
* Allow some keybindings to work while a top bar menu is open [Florian; #698938]
|
||||
* Make open-app-menu keybinding a toggle action [Florian; #686756]
|
||||
* Only recognize common URL schemes in notification messages [Monica; #661225]
|
||||
* Misc fixes and cleanups [Tim, Jasper, Florian, Giovanni, Owen; #698531,
|
||||
#698622, #698427, #698483, #698513, #697203, #698959, #698918, #699029,
|
||||
#699075, #696720, #649748]
|
||||
|
||||
Contributors:
|
||||
Giovanni Campagna, Cosimo Cecchi, Monica Chelliah, Matthias Clasen, Tim Lunn,
|
||||
Florian Müllner, Jasper St. Pierre, Michael Wood, Owen W. Taylor
|
||||
|
||||
Translations:
|
||||
Fran Diéguez [gl], Muhammet Kara [tr], Daniel Mustieles [es],
|
||||
Gil Forcada [ia], Anish A [ml], Dimitris Spingos [el], Marek Černocký [cs],
|
||||
Žygimantas Beručka [lt]
|
||||
|
||||
3.8.1
|
||||
=====
|
||||
* Clip window group during startup animation [Jasper; #696323]
|
||||
* Check for logind rather than systemd [Martin; #696252]
|
||||
* Don't special-case last remote search provider position [Giovanni; #694974]
|
||||
* Fix memory leaks [Ray, Jasper; ##697119, #697295, #697300, #697395]
|
||||
* AppSwitcherPopup: Activate only the selected window if any [Rui; #697480]
|
||||
* Enable screen recorder keybinding in all modes [Florian; #696200]
|
||||
* Remove box-shadow from screen shield for performance reasons [Adel; #697274]
|
||||
* Add support for -st-natural-width/height CSS properties [Giovanni; #664411]
|
||||
* Remove excessive padding from notification buttons [Allan; #664411]
|
||||
* Fix thumbnail dragging in overview [Jasper; #697504]
|
||||
* theme-node: Add get_url()/lookup_url() methods [Florian; #693688]
|
||||
* Misc bug fixes and cleanups [Jasper, Rui, Colin, David, Ray, Matthias:
|
||||
#695859, #696259, #696585, #696436, #697432, #697435, #697560, #697722,
|
||||
#697709]
|
||||
|
||||
Contributors:
|
||||
Giovanni Campagna, Matthias Clasen, Allan Day, Adel Gadllah, David Gumberg,
|
||||
Rui Matos, Florian Müllner, Martin Pitt, Jasper St. Pierre, Ray Strode,
|
||||
Colin Walters
|
||||
|
||||
Translations:
|
||||
Daniel Martinez [an], Bruce Cowan [en_GB], Khaled Hosny [ar],
|
||||
Ihar Hrachyshka [be], Aron Xu [zh_CN], Wojciech Szczęsny [pl],
|
||||
Inaki Larranaga Murgoitio [eu], Kjartan Maraas [nb],
|
||||
Милош Поповић [sr, sr@latin], Trần Ngọc Quân [vi]
|
||||
|
||||
3.8.0.1
|
||||
=======
|
||||
* Background bug fixes [Ray; #696712]
|
||||
|
||||
3.8.0
|
||||
=====
|
||||
* Remove blur and desaturation from lock screen [Jasper; #696322]
|
||||
* Remove scroll view fade near edges [Adel; #696404]
|
||||
* dateMenu: Open calendar component when using Evolution [Florian; #696432]
|
||||
* Fix unlocking on fast user switch [Cosimo; #696287]
|
||||
* Tweak screen shield animation [Rui; #696380]
|
||||
* Fix major memory leak when changing backgrounds [Ray; #696157]
|
||||
* Miscellaneous bug fixes [Jasper, Adel, Florian; #696199, #696212, #696422,
|
||||
#696447, #696235]
|
||||
|
||||
Contributors:
|
||||
Giovanni Campagna, Cosimo Cecchi, Adel Gadllah, Rui Matos, Florian Müllner,
|
||||
Jasper St. Pierre, Ray Strode
|
||||
|
||||
Translations:
|
||||
Alexandre Franke [fr], Victor Ibragimov [tg], Arash Mousavi [fa],
|
||||
Gabor Kelemen [hu], Sandeep Sheshrao Shedmake [mr], ManojKumar Giri [or],
|
||||
Shantha kumar [ta], Rajesh Ranjan [hi], Stas Solovey [ru],
|
||||
Shankar Prasad [kn], Dušan Kazik [sk], Ihar Hrachyshka [be],
|
||||
Wouter Bolsterlee [nl], Kris Thomsen [da], Jiro Matsuzawa [ja],
|
||||
Daniel Korostil [uk], Ani Peter [ml], Krishnababu Krothapalli [te],
|
||||
Mantas Kriaučiūnas [lt], Praveen Illa [te]
|
||||
|
||||
3.7.92
|
||||
======
|
||||
* Drop fallback lock implementation [Florian; #693403]
|
||||
* Don't let the user trigger message-tray when in fullscreen [Jasper; #694997]
|
||||
* Scroll search results when using keynav [Jasper; #689681]
|
||||
* Allow raising the shield by starting to type the password [Jasper; #686740]
|
||||
* Improve tracking of fullscreen windows [Owen; #649748]
|
||||
* Improve animation of new windows in overview [Giovanni; #695582]
|
||||
* workspace switcher: Animate new workspaces created by DND [Giovanni; #685285]
|
||||
* Give user time to read messages on login screen [Ray; #694688]
|
||||
* Misc bug fixes and cleanups [Jasper, Ray, Florian, Cosimo, Giovanni, Adel,
|
||||
Stef, Takao, Rui, Neil; #695154, #694993, #695272, #691578, #694321, #695338,
|
||||
#695409, #695458, #695526, #695601, #695471, #695324, #695650, #695656,
|
||||
#695659, #695485, #695395, #694951, #695824, #695841, #695801, #694321,
|
||||
#693708, #695800, #695607, #695882, #691578, #685851, #694371, #690857,
|
||||
#694092, #695747, #696007, #693438, #696064, #696102
|
||||
|
||||
Contributors:
|
||||
Giovanni Campagna, Cosimo Cecchi, Allan Day, Takao Fujiwara, Adel Gadllah,
|
||||
Tim Lunn, Rui Matos, Florian Müllner, Neil Roberts, Jasper St. Pierre,
|
||||
Ray Strode, Stef Walter, Colin Walters, Owen W. Taylor
|
||||
|
||||
Translations:
|
||||
Nilamdyuti Goswami [as], Chao-Hsiung Liao [zh_HK, zh_TW],
|
||||
Yuri Myasoedov [ru], Gheyret Kenji [ug], Baurzhan Muftakhidinov [kk],
|
||||
Ville-Pekka Vainio [fi], Matej Urbančič [sl],
|
||||
Мирослав Николић [sr, sr@latin], Rūdolfs Mazurs [lv], Christian Kirbach [de],
|
||||
Andika Triwidada [id], Gil Forcada [ca], Mattias Põldaru [et],
|
||||
Duarte Loreto [pt], Adam Matoušek [cs], Changwoo Ryu [ko],
|
||||
Ihar Hrachyshka [be], Carles Ferrando [ca@valencia], Sweta Kothari [gu]
|
||||
|
||||
3.7.91
|
||||
======
|
||||
* overview: Fade out controls during DND that are not targets [Cosimo; #686984]
|
||||
* overview: Keep open when a Control key is held [Florian; #686984]
|
||||
* Improve login screen => session transition [Ray; #694321]
|
||||
* Center application grid horizontally [Florian; #694261]
|
||||
* Fix hiding panel when fullscreen windows span multiple monitors [Adel; 646861]
|
||||
* Tweak thresholds of pressure barrier [Jasper; #694467]
|
||||
* Tweak window picker layout [Jasper; #694902]
|
||||
* Expose key grab DBus API to gnome-settings-daemon [Florian; #643111]
|
||||
* Don't always show message tray in overview, add message indicator
|
||||
[Cosimo; #687787]
|
||||
* Tweak startup animation [Ray; #694326]
|
||||
* Add OSD popups and expose them to gnome-settings-daemon [Florian; #613543]
|
||||
* Move loupe icon to the start of the search entry [Jasper; #695069]
|
||||
* Don't show the input switcher with less than 2 items [Rui; 695000]
|
||||
* Fix auto-completion of system modals immediately upon display [Stef; #692937]
|
||||
* Ignore workspaces in alt-tab [Florian; #661156]
|
||||
* Disable copying text from password entries [Florian; #695104]
|
||||
* Use standard styling for ibus candidate popups [Allan; #694796]
|
||||
* Fix calendar changing height on month changes [Giovanni; #641383]
|
||||
* Port the hot corner to use pressure barriers [Jasper; #663661]
|
||||
* Misc bug fixes and cleanups: [Hashem, Giovanni, Alban, Jasper, Cosimo,
|
||||
Florian, Adel, Daniel, Matthias, Ray, Rui, Guillaume, Stef; #685849, #690643,
|
||||
#694292, #693814, #694234, #694365, #694287, #694336, #694256, #694261,
|
||||
#663601, #694441, #694284, #694463, #694475, #687248, #694394, #694320,
|
||||
#694701, #694784, #694858, #694906, #694327, #694876, #694905, #694969,
|
||||
#694970, #694988, #695006, #695001, #694998, #695023, #695002, #695073,
|
||||
#695126, #687748, #694837, #693907, #679851, #694988]
|
||||
|
||||
Contributors:
|
||||
Giovanni Campagna, Cosimo Cecchi, Matthias Clasen, Alban Crequy, Allan Day,
|
||||
Guillaume Desmottes, Adel Gadllah, Rui Matos, Daniel Mustieles,
|
||||
Hashem Nasarat, Jasper St. Pierre, Ray Strode, Stef Walter
|
||||
|
||||
Translations:
|
||||
Yuri Myasoedov [ru], Adam Matoušek [cs], Piotr Drąg [pl], Matej Urbančič [sl],
|
||||
Sweta Kothari [gu], Kjartan Maraas [nb], Nguyễn Thái Ngọc Duy [vi],
|
||||
Chao-Hsiung Liao [zh_HK, zh_TW], Dimitris Spingos [el],
|
||||
Inaki Larranaga Murgoitio [eu], Luca Ferretti [it], A S Alam [pa],
|
||||
Gheyret Kenji [ug], Stas Solovey [ru], Enrico Nicoletto [pt_BR],
|
||||
Fran Diéguez [gl], Daniel Mustieles [es], Aurimas Černius [lt]
|
||||
|
||||
3.7.90
|
||||
======
|
||||
* Let GNOME Shell work on EGL and GLES2 [Neil; #693225, #693438, #693339]
|
||||
|
||||
10
configure.ac
10
configure.ac
@@ -1,5 +1,5 @@
|
||||
AC_PREREQ(2.63)
|
||||
AC_INIT([gnome-shell],[3.7.90],[https://bugzilla.gnome.org/enter_bug.cgi?product=gnome-shell],[gnome-shell])
|
||||
AC_INIT([gnome-shell],[3.9.1],[https://bugzilla.gnome.org/enter_bug.cgi?product=gnome-shell],[gnome-shell])
|
||||
|
||||
AC_CONFIG_HEADERS([config.h])
|
||||
AC_CONFIG_SRCDIR([src/shell-global.c])
|
||||
@@ -63,9 +63,9 @@ AM_CONDITIONAL(BUILD_RECORDER, $build_recorder)
|
||||
CLUTTER_MIN_VERSION=1.13.4
|
||||
GOBJECT_INTROSPECTION_MIN_VERSION=0.10.1
|
||||
GJS_MIN_VERSION=1.35.4
|
||||
MUTTER_MIN_VERSION=3.7.90
|
||||
MUTTER_MIN_VERSION=3.9.1
|
||||
GTK_MIN_VERSION=3.7.9
|
||||
GIO_MIN_VERSION=2.35.0
|
||||
GIO_MIN_VERSION=2.37.0
|
||||
LIBECAL_MIN_VERSION=3.5.3
|
||||
LIBEDATASERVER_MIN_VERSION=3.5.3
|
||||
TELEPATHY_GLIB_MIN_VERSION=0.17.5
|
||||
@@ -74,7 +74,7 @@ STARTUP_NOTIFICATION_MIN_VERSION=0.11
|
||||
GCR_MIN_VERSION=3.3.90
|
||||
GNOME_DESKTOP_REQUIRED_VERSION=3.7.90
|
||||
GNOME_MENUS_REQUIRED_VERSION=3.5.3
|
||||
NETWORKMANAGER_MIN_VERSION=0.9.6
|
||||
NETWORKMANAGER_MIN_VERSION=0.9.8
|
||||
PULSE_MIN_VERS=2.0
|
||||
|
||||
# Collect more than 20 libraries for a prize!
|
||||
@@ -96,7 +96,7 @@ PKG_CHECK_MODULES(GNOME_SHELL, gio-unix-2.0 >= $GIO_MIN_VERSION
|
||||
polkit-agent-1 >= $POLKIT_MIN_VERSION xfixes
|
||||
libnm-glib libnm-util >= $NETWORKMANAGER_MIN_VERSION
|
||||
libnm-gtk >= $NETWORKMANAGER_MIN_VERSION
|
||||
gnome-keyring-1 gcr-3 >= $GCR_MIN_VERSION)
|
||||
libsecret-unstable gcr-3 >= $GCR_MIN_VERSION)
|
||||
|
||||
PKG_CHECK_MODULES(GNOME_SHELL_JS, gio-2.0 gjs-internals-1.0 >= $GJS_MIN_VERSION)
|
||||
PKG_CHECK_MODULES(ST, clutter-1.0 gtk+-3.0 libcroco-0.6 >= 0.6.8 x11)
|
||||
|
||||
@@ -11,6 +11,9 @@
|
||||
<KeyListEntry name="focus-active-notification"
|
||||
_description="Focus the active notification"/>
|
||||
|
||||
<KeyListEntry name="toggle-overview"
|
||||
_description="Show the overview"/>
|
||||
|
||||
<KeyListEntry name="toggle-application-view"
|
||||
_description="Show all applications"/>
|
||||
|
||||
|
||||
@@ -1,3 +1,6 @@
|
||||
wandadir = $(pkgdatadir)
|
||||
dist_wanda_DATA = wanda.png
|
||||
|
||||
desktopdir=$(datadir)/applications
|
||||
desktop_DATA = gnome-shell.desktop gnome-shell-extension-prefs.desktop
|
||||
|
||||
|
||||
@@ -46,7 +46,7 @@
|
||||
<!--
|
||||
GetResultMetas:
|
||||
@identifiers: An array of result identifiers as returned by GetInitialResultSet() or GetSubsearchResultSet()
|
||||
@metas: A dictionary describing the given search result, containing a human-readable 'name' (string), along with the result identifier this meta is for, 'id' (string). Optionally, either 'gicon' (a serialized GIcon) or 'icon-data' (raw image data as (iiibiiay) - width, height, rowstride, has-alpha, bits per sample, channels, data) can be specified if the result can be better served with a thumbnail of the content (such as with images). A 'description' field (string) may also be specified if more context would help the user find the desired result.
|
||||
@metas: A dictionary describing the given search result, containing a human-readable 'name' (string), along with the result identifier this meta is for, 'id' (string). Optionally, 'icon' (a serialized GIcon as obtained by g_icon_serialize) can be specified if the result can be better served with a thumbnail of the content (such as with images). 'gicon' (a serialized GIcon as obtained by g_icon_to_string) or 'icon-data' (raw image data as (iiibiiay) - width, height, rowstride, has-alpha, bits per sample, channels, data) are deprecated values that can also be used for that purpose. A 'description' field (string) may also be specified if more context would help the user find the desired result.
|
||||
|
||||
Return an array of meta data used to display each given result
|
||||
-->
|
||||
|
||||
@@ -117,6 +117,13 @@ value here is from the GsmPresenceStatus enumeration.</_summary>
|
||||
Overview.
|
||||
</_description>
|
||||
</key>
|
||||
<key name="toggle-overview" type="as">
|
||||
<default>["<Super>s"]</default>
|
||||
<_summary>Keybinding to open the overview</_summary>
|
||||
<_description>
|
||||
Keybinding to open the Activities Overview.
|
||||
</_description>
|
||||
</key>
|
||||
<key name="toggle-message-tray" type="as">
|
||||
<default>["<Super>m"]</default>
|
||||
<_summary>Keybinding to toggle the visibility of the message tray</_summary>
|
||||
|
||||
@@ -125,7 +125,12 @@ StScrollBar StButton#vhandle:active {
|
||||
|
||||
/* PopupMenu */
|
||||
|
||||
.popup-menu-boxpointer {
|
||||
.popup-menu-ornament {
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.popup-menu-boxpointer,
|
||||
.candidate-popup-boxpointer {
|
||||
-arrow-border-radius: 8px;
|
||||
-arrow-background-color: rgba(0,0,0,0.9);
|
||||
-arrow-border-width: 2px;
|
||||
@@ -315,10 +320,20 @@ StScrollBar StButton#vhandle:active {
|
||||
.notification-button:focus,
|
||||
.notification-icon-button:focus,
|
||||
.hotplug-notification-item:focus,
|
||||
.modal-dialog-button:focus {
|
||||
.modal-dialog-button:focus,
|
||||
.app-view-control:focus {
|
||||
border-width: 2px;
|
||||
}
|
||||
|
||||
.app-view-control:focus {
|
||||
padding: 3px;
|
||||
}
|
||||
|
||||
.app-view-control:first-child:ltr:focus,
|
||||
.app-view-control:last-child:rtl:focus {
|
||||
border-right-width: 1px;
|
||||
}
|
||||
|
||||
.candidate-page-button:active,
|
||||
.candidate-page-button:pressed,
|
||||
.notification-button:active,
|
||||
@@ -501,6 +516,7 @@ StScrollBar StButton#vhandle:active {
|
||||
}
|
||||
|
||||
#appMenu {
|
||||
spinner-image: url("process-working.svg");
|
||||
spacing: 4px;
|
||||
}
|
||||
|
||||
@@ -886,8 +902,8 @@ StScrollBar StButton#vhandle:active {
|
||||
.search-display > StBoxLayout,
|
||||
.all-apps > StBoxLayout,
|
||||
.frequent-apps > StBoxLayout {
|
||||
/* horizontal padding to make sure the scrollbar doesn't overlap content */
|
||||
padding: 0px 18px;
|
||||
/* horizontal padding to make sure scrollbars or dash don't overlap content */
|
||||
padding: 0px 88px;
|
||||
}
|
||||
|
||||
.app-folder-icon {
|
||||
@@ -963,6 +979,10 @@ StScrollBar StButton#vhandle:active {
|
||||
color:white;
|
||||
}
|
||||
|
||||
.app-display .app-well-app > .overview-icon {
|
||||
border-radius: 10px;
|
||||
}
|
||||
|
||||
.list-search-result:hover .list-search-result-description {
|
||||
text-shadow: rgba(0,0,0,0.8) 0px 1px 2px;
|
||||
}
|
||||
@@ -1257,15 +1277,15 @@ StScrollBar StButton#vhandle:active {
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
.calendar-other-month-day {
|
||||
color: #333333;
|
||||
}
|
||||
|
||||
.calendar-day-with-events {
|
||||
font-weight: bold;
|
||||
color: white;
|
||||
}
|
||||
|
||||
.calendar-other-month-day {
|
||||
color: #333333;
|
||||
}
|
||||
|
||||
.events-header-vbox {
|
||||
spacing: 6pt;
|
||||
padding-right: .5em;
|
||||
@@ -1438,11 +1458,13 @@ StScrollBar StButton#vhandle:active {
|
||||
}
|
||||
|
||||
.notification-button {
|
||||
padding: 4px 42px 5px;
|
||||
-st-natural-width: 140px;
|
||||
padding: 4px 4px 5px;
|
||||
}
|
||||
|
||||
.notification-button:focus {
|
||||
padding: 3px 41px 4px;
|
||||
-st-natural-width: 138px;
|
||||
padding: 3px 4px 4px;
|
||||
}
|
||||
|
||||
.notification-icon-button {
|
||||
@@ -2129,23 +2151,12 @@ StScrollBar StButton#vhandle:active {
|
||||
}
|
||||
|
||||
/* IBus Candidate Popup */
|
||||
.candidate-popup-boxpointer {
|
||||
-arrow-border-radius: 8px;
|
||||
-arrow-background-color: #707070;
|
||||
-arrow-border-width: 0px;
|
||||
-arrow-base: 24px;
|
||||
-arrow-rise: 11px;
|
||||
}
|
||||
|
||||
.candidate-popup-content {
|
||||
padding: 0.5em;
|
||||
spacing: 0.3em;
|
||||
}
|
||||
|
||||
.candidate-popup-text {
|
||||
font-size: 9pt;
|
||||
}
|
||||
|
||||
.candidate-index {
|
||||
padding: 0 0.5em 0 0;
|
||||
color: #cccccc;
|
||||
@@ -2211,6 +2222,9 @@ StScrollBar StButton#vhandle:active {
|
||||
border: none;
|
||||
background-color: transparent;
|
||||
|
||||
padding-bottom: 80px;
|
||||
padding-top: 80px;
|
||||
|
||||
border-radius: 16px;
|
||||
min-height: 150px;
|
||||
max-height: 700px;
|
||||
@@ -2438,7 +2452,6 @@ StScrollBar StButton#vhandle:active {
|
||||
|
||||
.screen-shield-background {
|
||||
background: black;
|
||||
box-shadow: 0px 4px 8px rgba(0,0,0,0.9);
|
||||
}
|
||||
|
||||
#lockDialogGroup {
|
||||
|
||||
BIN
data/wanda.png
Normal file
BIN
data/wanda.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 13 KiB |
@@ -66,11 +66,4 @@ its dependencies to build from tarballs.</description>
|
||||
<gnome:userid>fmuellner</gnome:userid>
|
||||
</foaf:Person>
|
||||
</maintainer>
|
||||
<maintainer>
|
||||
<foaf:Person>
|
||||
<foaf:name>Ray Strode</foaf:name>
|
||||
<foaf:mbox rdf:resource="mailto:halfline@gmail.com" />
|
||||
<gnome:userid>halfline</gnome:userid>
|
||||
</foaf:Person>
|
||||
</maintainer>
|
||||
</Project>
|
||||
|
||||
@@ -594,6 +594,7 @@ const LoginDialog = new Lang.Class({
|
||||
this._promptEntry = new St.Entry({ style_class: 'login-dialog-prompt-entry',
|
||||
can_focus: true });
|
||||
this._promptEntryTextChangedId = 0;
|
||||
this._promptEntryActivateId = 0;
|
||||
this._promptBox.add(this._promptEntry,
|
||||
{ expand: true,
|
||||
x_fill: true,
|
||||
@@ -690,6 +691,8 @@ const LoginDialog = new Lang.Class({
|
||||
},
|
||||
|
||||
_reset: function() {
|
||||
this._userVerifier.clear();
|
||||
|
||||
this._updateSensitivity(true);
|
||||
this._promptMessage.hide();
|
||||
this._user = null;
|
||||
@@ -771,7 +774,8 @@ const LoginDialog = new Lang.Class({
|
||||
},
|
||||
|
||||
_prepareDialog: function(forSecret, hold) {
|
||||
this._workSpinner = new Panel.AnimatedIcon('process-working.svg', WORK_SPINNER_ICON_SIZE);
|
||||
let spinnerIcon = global.datadir + '/theme/process-working.svg';
|
||||
this._workSpinner = new Panel.AnimatedIcon(spinnerIcon, WORK_SPINNER_ICON_SIZE);
|
||||
this._workSpinner.actor.opacity = 0;
|
||||
this._workSpinner.actor.show();
|
||||
|
||||
@@ -811,6 +815,11 @@ const LoginDialog = new Lang.Class({
|
||||
Lang.bind(this, function() {
|
||||
this._updateSignInButtonSensitivity(this._promptEntry.text.length > 0);
|
||||
}));
|
||||
|
||||
this._promptEntryActivateId =
|
||||
this._promptEntry.clutter_text.connect('activate', function() {
|
||||
hold.release();
|
||||
});
|
||||
},
|
||||
|
||||
_updateSensitivity: function(sensitive) {
|
||||
@@ -835,6 +844,11 @@ const LoginDialog = new Lang.Class({
|
||||
this._promptEntryTextChangedId = 0;
|
||||
}
|
||||
|
||||
if (this._promptEntryActivateId > 0) {
|
||||
this._promptEntry.clutter_text.disconnect(this._promptEntryActivateId);
|
||||
this._promptEntryActivateId = 0;
|
||||
}
|
||||
|
||||
this._setWorking(false);
|
||||
this._promptBox.hide();
|
||||
this._promptLoginHint.hide();
|
||||
@@ -917,7 +931,7 @@ const LoginDialog = new Lang.Class({
|
||||
return batch.run();
|
||||
},
|
||||
|
||||
_onSessionOpened: function(client, serviceName) {
|
||||
_startSession: function(serviceName) {
|
||||
Tweener.addTween(this.dialogLayout,
|
||||
{ opacity: 0,
|
||||
time: _FADE_ANIMATION_TIME,
|
||||
@@ -940,6 +954,18 @@ const LoginDialog = new Lang.Class({
|
||||
onCompleteScope: this });
|
||||
},
|
||||
|
||||
_onSessionOpened: function(client, serviceName) {
|
||||
if (!this._userVerifier.hasPendingMessages) {
|
||||
this._startSession(serviceName);
|
||||
} else {
|
||||
let signalId = this._userVerifier.connect('no-more-messages',
|
||||
Lang.bind(this, function() {
|
||||
this._userVerifier.disconnect(signalId);
|
||||
this._startSession(serviceName);
|
||||
}));
|
||||
}
|
||||
},
|
||||
|
||||
_waitForItemForUser: function(userName) {
|
||||
let item = this._userList.getItemFromUserName(userName);
|
||||
|
||||
@@ -1003,7 +1029,7 @@ const LoginDialog = new Lang.Class({
|
||||
function() {
|
||||
// If we're just starting out, start on the right
|
||||
// item.
|
||||
if (!this.is_loaded) {
|
||||
if (!this._userManager.is_loaded) {
|
||||
this._userList.jumpToItem(this._timedLoginItem);
|
||||
}
|
||||
},
|
||||
@@ -1141,15 +1167,6 @@ const LoginDialog = new Lang.Class({
|
||||
Lang.bind(this, function(userManager, user) {
|
||||
this._userList.removeUser(user);
|
||||
}));
|
||||
|
||||
// emitted in idle so caller doesn't have to explicitly check if
|
||||
// it's loaded immediately after construction
|
||||
// (since there's no way the caller could be listening for
|
||||
// 'loaded' yet)
|
||||
Mainloop.idle_add(Lang.bind(this, function() {
|
||||
this.emit('loaded');
|
||||
this.is_loaded = true;
|
||||
}));
|
||||
},
|
||||
|
||||
_onOpened: function() {
|
||||
@@ -1164,5 +1181,9 @@ const LoginDialog = new Lang.Class({
|
||||
this.parent();
|
||||
|
||||
Main.ctrlAltTabManager.removeGroup(this.dialogLayout);
|
||||
}
|
||||
},
|
||||
|
||||
addCharacter: function(unichar) {
|
||||
this._promptEntry.clutter_text.insert_unichar(unichar);
|
||||
},
|
||||
});
|
||||
|
||||
116
js/gdm/util.js
116
js/gdm/util.js
@@ -2,6 +2,7 @@
|
||||
|
||||
const Clutter = imports.gi.Clutter;
|
||||
const Gio = imports.gi.Gio;
|
||||
const GLib = imports.gi.GLib;
|
||||
const Lang = imports.lang;
|
||||
const Mainloop = imports.mainloop;
|
||||
const Signals = imports.signals;
|
||||
@@ -27,6 +28,9 @@ const ALLOWED_FAILURES_KEY = 'allowed-failures';
|
||||
const LOGO_KEY = 'logo';
|
||||
const DISABLE_USER_LIST_KEY = 'disable-user-list';
|
||||
|
||||
// Give user 16ms to read each character of a PAM message
|
||||
const USER_READ_TIME = 16
|
||||
|
||||
function fadeInActor(actor) {
|
||||
if (actor.opacity == 255 && actor.visible)
|
||||
return null;
|
||||
@@ -114,6 +118,9 @@ const ShellUserVerifier = new Lang.Class({
|
||||
|
||||
this._fprintManager = new Fprint.FprintManager();
|
||||
this._realmManager = new Realmd.Manager();
|
||||
this._messageQueue = [];
|
||||
this._messageQueueTimeoutId = 0;
|
||||
this.hasPendingMessages = false;
|
||||
|
||||
this._failCounter = 0;
|
||||
},
|
||||
@@ -153,13 +160,73 @@ const ShellUserVerifier = new Lang.Class({
|
||||
this._userVerifier.run_dispose();
|
||||
this._userVerifier = null;
|
||||
}
|
||||
|
||||
this._clearMessageQueue();
|
||||
},
|
||||
|
||||
answerQuery: function(serviceName, answer) {
|
||||
// Clear any previous message
|
||||
this.emit('show-message', null, null);
|
||||
if (!this._userVerifier.hasPendingMessages) {
|
||||
this._userVerifier.call_answer_query(serviceName, answer, this._cancellable, null);
|
||||
} else {
|
||||
let signalId = this._userVerifier.connect('no-more-messages',
|
||||
Lang.bind(this, function() {
|
||||
this._userVerifier.disconnect(signalId);
|
||||
this._userVerifier.call_answer_query(serviceName, answer, this._cancellable, null);
|
||||
}));
|
||||
}
|
||||
},
|
||||
|
||||
this._userVerifier.call_answer_query(serviceName, answer, this._cancellable, null);
|
||||
_getIntervalForMessage: function(message) {
|
||||
// We probably could be smarter here
|
||||
return message.length * USER_READ_TIME;
|
||||
},
|
||||
|
||||
finishMessageQueue: function() {
|
||||
if (!this.hasPendingMessages)
|
||||
return;
|
||||
|
||||
this._messageQueue = [];
|
||||
|
||||
this.hasPendingMessages = false;
|
||||
this.emit('no-more-messages');
|
||||
},
|
||||
|
||||
_queueMessageTimeout: function() {
|
||||
if (this._messageQueue.length == 0) {
|
||||
this.finishMessageQueue();
|
||||
return;
|
||||
}
|
||||
|
||||
if (this._messageQueueTimeoutId != 0)
|
||||
return;
|
||||
|
||||
let message = this._messageQueue.shift();
|
||||
this.emit('show-message', message.text, message.iconName);
|
||||
|
||||
this._messageQueueTimeoutId = GLib.timeout_add(GLib.PRIORITY_DEFAULT,
|
||||
message.interval,
|
||||
Lang.bind(this, function() {
|
||||
this._messageQueueTimeoutId = 0;
|
||||
this._queueMessageTimeout();
|
||||
}));
|
||||
},
|
||||
|
||||
_queueMessage: function(message, iconName) {
|
||||
let interval = this._getIntervalForMessage(message);
|
||||
|
||||
this.hasPendingMessages = true;
|
||||
this._messageQueue.push({ text: message, interval: interval, iconName: iconName });
|
||||
this._queueMessageTimeout();
|
||||
},
|
||||
|
||||
_clearMessageQueue: function() {
|
||||
this.finishMessageQueue();
|
||||
|
||||
if (this._messageQueueTimeoutId != 0) {
|
||||
GLib.source_remove(this._messageQueueTimeoutId);
|
||||
this._messageQueueTimeoutId = 0;
|
||||
}
|
||||
this.emit('show-message', null, null);
|
||||
},
|
||||
|
||||
_checkForFingerprintReader: function() {
|
||||
@@ -179,7 +246,7 @@ const ShellUserVerifier = new Lang.Class({
|
||||
logError(error, where);
|
||||
this._hold.release();
|
||||
|
||||
this.emit('show-message', _("Authentication error"), 'login-dialog-message-warning');
|
||||
this._queueMessage(_("Authentication error"), 'login-dialog-message-warning');
|
||||
this._verificationFailed(false);
|
||||
},
|
||||
|
||||
@@ -298,7 +365,7 @@ const ShellUserVerifier = new Lang.Class({
|
||||
// to indicate the user can swipe their finger instead
|
||||
this.emit('show-login-hint', _("(or swipe finger)"));
|
||||
} else if (serviceName == PASSWORD_SERVICE_NAME) {
|
||||
this.emit('show-message', info, 'login-dialog-message-info');
|
||||
this._queueMessage(info, 'login-dialog-message-info');
|
||||
}
|
||||
},
|
||||
|
||||
@@ -307,7 +374,7 @@ const ShellUserVerifier = new Lang.Class({
|
||||
// users who haven't enrolled their fingerprint.
|
||||
if (serviceName != PASSWORD_SERVICE_NAME)
|
||||
return;
|
||||
this.emit('show-message', problem, 'login-dialog-message-warning');
|
||||
this._queueMessage(problem, 'login-dialog-message-warning');
|
||||
},
|
||||
|
||||
_showRealmLoginHint: function() {
|
||||
@@ -346,8 +413,6 @@ const ShellUserVerifier = new Lang.Class({
|
||||
},
|
||||
|
||||
_onReset: function() {
|
||||
this.clear();
|
||||
|
||||
// Clear previous attempts to authenticate
|
||||
this._failCounter = 0;
|
||||
|
||||
@@ -358,6 +423,15 @@ const ShellUserVerifier = new Lang.Class({
|
||||
this.emit('verification-complete');
|
||||
},
|
||||
|
||||
_cancelAndReset: function() {
|
||||
this.cancel();
|
||||
this._onReset();
|
||||
},
|
||||
|
||||
_retry: function() {
|
||||
this.begin(this._userName, new Batch.Hold());
|
||||
},
|
||||
|
||||
_verificationFailed: function(retry) {
|
||||
// For Not Listed / enterprise logins, immediately reset
|
||||
// the dialog
|
||||
@@ -369,15 +443,25 @@ const ShellUserVerifier = new Lang.Class({
|
||||
this._failCounter < this._settings.get_int(ALLOWED_FAILURES_KEY);
|
||||
|
||||
if (canRetry) {
|
||||
this.clear();
|
||||
this.begin(this._userName, new Batch.Hold());
|
||||
if (!this._userVerifier.hasPendingMessages) {
|
||||
this._retry();
|
||||
} else {
|
||||
let signalId = this._userVerifier.connect('no-more-messages',
|
||||
Lang.bind(this, function() {
|
||||
this._userVerifier.disconnect(signalId);
|
||||
this._retry();
|
||||
}));
|
||||
}
|
||||
} else {
|
||||
// Allow some time to see the message, then reset everything
|
||||
Mainloop.timeout_add(3000, Lang.bind(this, function() {
|
||||
this.cancel();
|
||||
|
||||
this._onReset();
|
||||
}));
|
||||
if (!this._userVerifier.hasPendingMessages) {
|
||||
this._cancelAndReset();
|
||||
} else {
|
||||
let signalId = this._userVerifier.connect('no-more-messages',
|
||||
Lang.bind(this, function() {
|
||||
this._userVerifier.disconnect(signalId);
|
||||
this._cancelAndReset();
|
||||
}));
|
||||
}
|
||||
}
|
||||
|
||||
this.emit('verification-failed');
|
||||
|
||||
@@ -33,6 +33,10 @@ const SystemdLoginManagerIface = <interface name='org.freedesktop.login1.Manager
|
||||
<arg type='s' direction='in'/>
|
||||
<arg type='h' direction='out'/>
|
||||
</method>
|
||||
<method name='GetSession'>
|
||||
<arg type='s' direction='in'/>
|
||||
<arg type='o' direction='out'/>
|
||||
</method>
|
||||
<method name='ListSessions'>
|
||||
<arg name='sessions' type='a(susso)' direction='out'/>
|
||||
</method>
|
||||
@@ -72,7 +76,36 @@ const ConsoleKitSession = Gio.DBusProxy.makeProxyWrapper(ConsoleKitSessionIface)
|
||||
const ConsoleKitManager = Gio.DBusProxy.makeProxyWrapper(ConsoleKitManagerIface);
|
||||
|
||||
function haveSystemd() {
|
||||
return GLib.access("/sys/fs/cgroup/systemd", 0) >= 0;
|
||||
return GLib.access("/run/systemd/seats", 0) >= 0;
|
||||
}
|
||||
|
||||
function versionCompare(required, reference) {
|
||||
required = required.split('.');
|
||||
reference = reference.split('.');
|
||||
|
||||
for (let i = 0; i < required.length; i++) {
|
||||
if (required[i] != reference[i])
|
||||
return required[i] < reference[i];
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
function canLock() {
|
||||
try {
|
||||
let params = GLib.Variant.new('(ss)', ['org.gnome.DisplayManager.Manager', 'Version']);
|
||||
let result = Gio.DBus.system.call_sync('org.gnome.DisplayManager',
|
||||
'/org/gnome/DisplayManager/Manager',
|
||||
'org.freedesktop.DBus.Properties',
|
||||
'Get', params, null,
|
||||
Gio.DBusCallFlags.NONE,
|
||||
-1, null);
|
||||
|
||||
let version = result.deep_unpack()[0].deep_unpack();
|
||||
return versionCompare('3.5.91', version);
|
||||
} catch(e) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
let _loginManager = null;
|
||||
@@ -107,15 +140,23 @@ const LoginManagerSystemd = new Lang.Class({
|
||||
// Having this function is a bit of a hack since the Systemd and ConsoleKit
|
||||
// session objects have different interfaces - but in both cases there are
|
||||
// Lock/Unlock signals, and that's all we count upon at the moment.
|
||||
getCurrentSessionProxy: function() {
|
||||
if (!this._currentSession) {
|
||||
this._currentSession = new SystemdLoginSession(Gio.DBus.system,
|
||||
'org.freedesktop.login1',
|
||||
'/org/freedesktop/login1/session/' +
|
||||
GLib.getenv('XDG_SESSION_ID'));
|
||||
getCurrentSessionProxy: function(callback) {
|
||||
if (this._currentSession) {
|
||||
callback (this._currentSession);
|
||||
return;
|
||||
}
|
||||
|
||||
return this._currentSession;
|
||||
this._proxy.GetSessionRemote(GLib.getenv('XDG_SESSION_ID'), Lang.bind(this,
|
||||
function(result, error) {
|
||||
if (error) {
|
||||
logError(error, 'Could not get a proxy for the current session');
|
||||
} else {
|
||||
this._currentSession = new SystemdLoginSession(Gio.DBus.system,
|
||||
'org.freedesktop.login1',
|
||||
result[0]);
|
||||
callback(this._currentSession);
|
||||
}
|
||||
}));
|
||||
},
|
||||
|
||||
canPowerOff: function(asyncCallback) {
|
||||
@@ -204,15 +245,23 @@ const LoginManagerConsoleKit = new Lang.Class({
|
||||
// Having this function is a bit of a hack since the Systemd and ConsoleKit
|
||||
// session objects have different interfaces - but in both cases there are
|
||||
// Lock/Unlock signals, and that's all we count upon at the moment.
|
||||
getCurrentSessionProxy: function() {
|
||||
if (!this._currentSession) {
|
||||
let [currentSessionId] = this._proxy.GetCurrentSessionSync();
|
||||
this._currentSession = new ConsoleKitSession(Gio.DBus.system,
|
||||
'org.freedesktop.ConsoleKit',
|
||||
currentSessionId);
|
||||
getCurrentSessionProxy: function(callback) {
|
||||
if (this._currentSession) {
|
||||
callback (this._currentSession);
|
||||
return;
|
||||
}
|
||||
|
||||
return this._currentSession;
|
||||
this._proxy.GetCurrentSessionRemote(Lang.bind(this,
|
||||
function(result, error) {
|
||||
if (error) {
|
||||
logError(error, 'Could not get a proxy for the current session');
|
||||
} else {
|
||||
this._currentSession = new ConsoleKitSession(Gio.DBus.system,
|
||||
'org.freedesktop.ConsoleKit',
|
||||
result[0]);
|
||||
callback(this._currentSession);
|
||||
}
|
||||
}));
|
||||
},
|
||||
|
||||
canPowerOff: function(asyncCallback) {
|
||||
|
||||
@@ -5,6 +5,9 @@ const GLib = imports.gi.GLib;
|
||||
const St = imports.gi.St;
|
||||
|
||||
const Main = imports.ui.main;
|
||||
const Tweener = imports.ui.tweener;
|
||||
|
||||
const SCROLL_TIME = 0.1;
|
||||
|
||||
// http://daringfireball.net/2010/07/improved_regex_for_matching_urls
|
||||
const _balancedParens = '\\((?:[^\\s()<>]+|(?:\\(?:[^\\s()<>]+\\)))*\\)';
|
||||
@@ -15,7 +18,7 @@ const _urlRegexp = new RegExp(
|
||||
'(^|' + _leadingJunk + ')' +
|
||||
'(' +
|
||||
'(?:' +
|
||||
'[a-z][\\w-]+://' + // scheme://
|
||||
'(?:http|https|ftp)://' + // scheme://
|
||||
'|' +
|
||||
'www\\d{0,3}[.]' + // www.
|
||||
'|' +
|
||||
@@ -234,3 +237,39 @@ function makeCloseButton() {
|
||||
|
||||
return closeButton;
|
||||
}
|
||||
|
||||
function ensureActorVisibleInScrollView(scrollView, actor) {
|
||||
let adjustment = scrollView.vscroll.adjustment;
|
||||
let [value, lower, upper, stepIncrement, pageIncrement, pageSize] = adjustment.get_values();
|
||||
|
||||
let offset = 0;
|
||||
let vfade = scrollView.get_effect("fade");
|
||||
if (vfade)
|
||||
offset = vfade.vfade_offset;
|
||||
|
||||
let box = actor.get_allocation_box();
|
||||
let y1 = box.y1, y2 = box.y2;
|
||||
|
||||
let parent = actor.get_parent();
|
||||
while (parent != scrollView) {
|
||||
if (!parent)
|
||||
throw new Error("actor not in scroll view");
|
||||
|
||||
let box = parent.get_allocation_box();
|
||||
y1 += box.y1;
|
||||
y2 += box.y1;
|
||||
parent = parent.get_parent();
|
||||
}
|
||||
|
||||
if (y1 < value + offset)
|
||||
value = Math.max(0, y1 - offset);
|
||||
else if (y2 > value + pageSize - offset)
|
||||
value = Math.min(upper, y2 + offset - pageSize);
|
||||
else
|
||||
return;
|
||||
|
||||
Tweener.addTween(adjustment,
|
||||
{ value: value,
|
||||
time: SCROLL_TIME,
|
||||
transition: 'easeOutQuad' });
|
||||
}
|
||||
|
||||
@@ -232,11 +232,13 @@ const AppSwitcherPopup = new Lang.Class({
|
||||
},
|
||||
|
||||
_finish : function(timestamp) {
|
||||
this.parent();
|
||||
|
||||
let appIcon = this._items[this._selectedIndex];
|
||||
let window = this._currentWindow > 0 ? this._currentWindow : 0;
|
||||
appIcon.app.activate_window(appIcon.cachedWindows[window], timestamp);
|
||||
if (this._currentWindow < 0)
|
||||
appIcon.app.activate_full(-1, timestamp);
|
||||
else
|
||||
Main.activateWindow(appIcon.cachedWindows[this._currentWindow], timestamp);
|
||||
|
||||
this.parent();
|
||||
},
|
||||
|
||||
_onDestroy : function() {
|
||||
@@ -395,9 +397,9 @@ const WindowSwitcherPopup = new Lang.Class({
|
||||
},
|
||||
|
||||
_finish: function() {
|
||||
this.parent();
|
||||
|
||||
Main.activateWindow(this._items[this._selectedIndex].window);
|
||||
|
||||
this.parent();
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
@@ -29,7 +29,6 @@ const Util = imports.misc.util;
|
||||
|
||||
const MAX_APPLICATION_WORK_MILLIS = 75;
|
||||
const MENU_POPUP_TIMEOUT = 600;
|
||||
const SCROLL_TIME = 0.1;
|
||||
const MAX_COLUMNS = 6;
|
||||
|
||||
const INACTIVE_GRID_OPACITY = 77;
|
||||
@@ -157,6 +156,30 @@ const FolderView = new Lang.Class({
|
||||
}
|
||||
});
|
||||
|
||||
const AllViewLayout = new Lang.Class({
|
||||
Name: 'AllViewLayout',
|
||||
Extends: Clutter.BinLayout,
|
||||
|
||||
vfunc_get_preferred_height: function(container, forWidth) {
|
||||
let minBottom = 0;
|
||||
let naturalBottom = 0;
|
||||
|
||||
for (let child = container.get_first_child();
|
||||
child;
|
||||
child = child.get_next_sibling()) {
|
||||
let childY = child.y;
|
||||
let [childMin, childNatural] = child.get_preferred_height(forWidth);
|
||||
|
||||
if (childMin + childY > minBottom)
|
||||
minBottom = childMin + childY;
|
||||
|
||||
if (childNatural + childY > naturalBottom)
|
||||
naturalBottom = childNatural + childY;
|
||||
}
|
||||
return [minBottom, naturalBottom];
|
||||
}
|
||||
});
|
||||
|
||||
const AllView = new Lang.Class({
|
||||
Name: 'AllView',
|
||||
Extends: AlphabeticalView,
|
||||
@@ -165,7 +188,7 @@ const AllView = new Lang.Class({
|
||||
this.parent();
|
||||
|
||||
let box = new St.BoxLayout({ vertical: true });
|
||||
this._stack = new St.Widget({ layout_manager: new Clutter.BinLayout() });
|
||||
this._stack = new St.Widget({ layout_manager: new AllViewLayout() });
|
||||
this._stack.add_actor(this._grid.actor);
|
||||
this._eventBlocker = new St.Widget({ x_expand: true, y_expand: true });
|
||||
this._stack.add_actor(this._eventBlocker);
|
||||
@@ -259,29 +282,7 @@ const AllView = new Lang.Class({
|
||||
},
|
||||
|
||||
_ensureIconVisible: function(icon) {
|
||||
let adjustment = this.actor.vscroll.adjustment;
|
||||
let [value, lower, upper, stepIncrement, pageIncrement, pageSize] = adjustment.get_values();
|
||||
|
||||
let offset = 0;
|
||||
let vfade = this.actor.get_effect("fade");
|
||||
if (vfade)
|
||||
offset = vfade.vfade_offset;
|
||||
|
||||
// If this gets called as part of a right-click, the actor
|
||||
// will be needs_allocation, and so "icon.y" would return 0
|
||||
let box = icon.get_allocation_box();
|
||||
|
||||
if (box.y1 < value + offset)
|
||||
value = Math.max(0, box.y1 - offset);
|
||||
else if (box.y2 > value + pageSize - offset)
|
||||
value = Math.min(upper, box.y2 + offset - pageSize);
|
||||
else
|
||||
return;
|
||||
|
||||
Tweener.addTween(adjustment,
|
||||
{ value: value,
|
||||
time: SCROLL_TIME,
|
||||
transition: 'easeOutQuad' });
|
||||
Util.ensureActorVisibleInScrollView(this.actor, icon);
|
||||
},
|
||||
|
||||
_updateIconOpacities: function(folderOpen) {
|
||||
@@ -315,6 +316,8 @@ const FrequentView = new Lang.Class({
|
||||
loadApps: function() {
|
||||
let mostUsed = this._usage.get_most_used ("");
|
||||
for (let i = 0; i < mostUsed.length; i++) {
|
||||
if (!mostUsed[i].get_app_info().should_show())
|
||||
continue;
|
||||
let appIcon = new AppIcon(mostUsed[i]);
|
||||
this._grid.addItem(appIcon.actor, -1);
|
||||
}
|
||||
|
||||
@@ -38,6 +38,7 @@ const BackgroundCache = new Lang.Class({
|
||||
_init: function() {
|
||||
this._patterns = [];
|
||||
this._images = [];
|
||||
this._pendingFileLoads = [];
|
||||
this._fileMonitors = {};
|
||||
},
|
||||
|
||||
@@ -84,10 +85,10 @@ const BackgroundCache = new Lang.Class({
|
||||
} else {
|
||||
content.load_gradient(params.shadingType, params.color, params.secondColor);
|
||||
}
|
||||
|
||||
this._patterns.push(content);
|
||||
}
|
||||
|
||||
this._patterns.push(content);
|
||||
|
||||
return content;
|
||||
},
|
||||
|
||||
@@ -125,9 +126,81 @@ const BackgroundCache = new Lang.Class({
|
||||
},
|
||||
|
||||
removeImageContent: function(content) {
|
||||
let filename = content.get_filename();
|
||||
|
||||
if (filename && this._fileMonitors[filename])
|
||||
delete this._fileMonitors[filename];
|
||||
|
||||
this._removeContent(this._images, content);
|
||||
},
|
||||
|
||||
_loadImageContent: function(params) {
|
||||
params = Params.parse(params, { monitorIndex: 0,
|
||||
style: null,
|
||||
filename: null,
|
||||
effects: Meta.BackgroundEffects.NONE,
|
||||
cancellable: null,
|
||||
onFinished: null });
|
||||
|
||||
for (let i = 0; i < this._pendingFileLoads.length; i++) {
|
||||
if (this._pendingFileLoads[i].filename == params.filename &&
|
||||
this._pendingFileLoads[i].style == params.style) {
|
||||
this._pendingFileLoads[i].callers.push({ shouldCopy: true,
|
||||
monitorIndex: params.monitorIndex,
|
||||
effects: params.effects,
|
||||
onFinished: params.onFinished });
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
this._pendingFileLoads.push({ filename: params.filename,
|
||||
style: params.style,
|
||||
callers: [{ shouldCopy: false,
|
||||
monitorIndex: params.monitorIndex,
|
||||
effects: params.effects,
|
||||
onFinished: params.onFinished }] });
|
||||
|
||||
let content = new Meta.Background({ meta_screen: global.screen,
|
||||
monitor: params.monitorIndex,
|
||||
effects: params.effects });
|
||||
|
||||
content.load_file_async(params.filename,
|
||||
params.style,
|
||||
params.cancellable,
|
||||
Lang.bind(this,
|
||||
function(object, result) {
|
||||
try {
|
||||
content.load_file_finish(result);
|
||||
|
||||
this._monitorFile(params.filename);
|
||||
this._images.push(content);
|
||||
} catch(e) {
|
||||
content = null;
|
||||
}
|
||||
|
||||
for (let i = 0; i < this._pendingFileLoads.length; i++) {
|
||||
let pendingLoad = this._pendingFileLoads[i];
|
||||
if (pendingLoad.filename != params.filename ||
|
||||
pendingLoad.style != params.style)
|
||||
continue;
|
||||
|
||||
for (let j = 0; j < pendingLoad.callers.length; j++) {
|
||||
if (pendingLoad.callers[j].onFinished) {
|
||||
if (content && pendingLoad.callers[j].shouldCopy) {
|
||||
content = object.copy(pendingLoad.callers[j].monitorIndex,
|
||||
pendingLoad.callers[j].effects);
|
||||
|
||||
}
|
||||
|
||||
pendingLoad.callers[j].onFinished(content);
|
||||
}
|
||||
}
|
||||
|
||||
this._pendingFileLoads.splice(i, 1);
|
||||
}
|
||||
}));
|
||||
},
|
||||
|
||||
getImageContent: function(params) {
|
||||
params = Params.parse(params, { monitorIndex: 0,
|
||||
style: null,
|
||||
@@ -165,31 +238,19 @@ const BackgroundCache = new Lang.Class({
|
||||
|
||||
if (params.cancellable && params.cancellable.is_cancelled())
|
||||
content = null;
|
||||
else
|
||||
this._images.push(content);
|
||||
|
||||
if (params.onFinished)
|
||||
params.onFinished(content);
|
||||
} else {
|
||||
content = new Meta.Background({ meta_screen: global.screen,
|
||||
monitor: params.monitorIndex,
|
||||
effects: params.effects });
|
||||
this._loadImageContent({ filename: params.filename,
|
||||
style: params.style,
|
||||
effects: params.effects,
|
||||
monitorIndex: params.monitorIndex,
|
||||
cancellable: params.cancellable,
|
||||
onFinished: params.onFinished });
|
||||
|
||||
content.load_file_async(params.filename,
|
||||
params.style,
|
||||
params.cancellable,
|
||||
Lang.bind(this,
|
||||
function(object, result) {
|
||||
try {
|
||||
content.load_file_finish(result);
|
||||
|
||||
this._monitorFile(params.filename);
|
||||
this._images.push(content);
|
||||
} catch(e) {
|
||||
content = null;
|
||||
}
|
||||
|
||||
if (params.onFinished)
|
||||
params.onFinished(content);
|
||||
}));
|
||||
}
|
||||
},
|
||||
|
||||
@@ -267,9 +328,9 @@ const Background = new Lang.Class({
|
||||
_destroy: function() {
|
||||
this._cancellable.cancel();
|
||||
|
||||
if (this._animationUpdateTimeoutId) {
|
||||
GLib.source_remove (this._animationUpdateTimeoutId);
|
||||
this._animationUpdateTimeoutId = 0
|
||||
if (this._updateAnimationTimeoutId) {
|
||||
GLib.source_remove (this._updateAnimationTimeoutId);
|
||||
this._updateAnimationTimeoutId = 0;
|
||||
}
|
||||
|
||||
let i;
|
||||
@@ -356,7 +417,10 @@ const Background = new Lang.Class({
|
||||
|
||||
let actor = new Meta.BackgroundActor();
|
||||
actor.content = content;
|
||||
this.actor.add_child(actor);
|
||||
|
||||
// The background pattern is the first actor in
|
||||
// the group, and all images should be above that.
|
||||
this.actor.insert_child_at_index(actor, index + 1);
|
||||
|
||||
this._images[index] = actor;
|
||||
this._watchCacheFile(filename);
|
||||
@@ -367,27 +431,27 @@ const Background = new Lang.Class({
|
||||
content.brightness = this._brightness;
|
||||
content.vignette_sharpness = this._vignetteSharpness;
|
||||
|
||||
this._cache.removeImageContent(this._images[index].content);
|
||||
this._images[index].content = content;
|
||||
this._watchCacheFile(filename);
|
||||
},
|
||||
|
||||
_updateAnimationProgress: function() {
|
||||
if (this._images[1]) {
|
||||
this._images[1].raise_top();
|
||||
if (this._images[1])
|
||||
this._images[1].opacity = this._animation.transitionProgress * 255;
|
||||
}
|
||||
|
||||
this._queueAnimationUpdate();
|
||||
this._queueUpdateAnimation();
|
||||
},
|
||||
|
||||
_updateAnimation: function() {
|
||||
this._animationUpdateTimeoutId = 0;
|
||||
this._updateAnimationTimeoutId = 0;
|
||||
|
||||
let files = this._animation.getKeyFrameFiles(this._layoutManager.monitors[this._monitorIndex]);
|
||||
this._animation.update(this._layoutManager.monitors[this._monitorIndex]);
|
||||
let files = this._animation.keyFrameFiles;
|
||||
|
||||
if (!files) {
|
||||
if (files.length == 0) {
|
||||
this._setLoaded();
|
||||
this._queueAnimationUpdate();
|
||||
this._queueUpdateAnimation();
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -406,7 +470,7 @@ const Background = new Lang.Class({
|
||||
style: this._style,
|
||||
filename: files[i],
|
||||
cancellable: this._cancellable,
|
||||
onFinished: Lang.bind(this, function(content) {
|
||||
onFinished: Lang.bind(this, function(content, i) {
|
||||
numPendingImages--;
|
||||
|
||||
if (!content) {
|
||||
@@ -426,27 +490,34 @@ const Background = new Lang.Class({
|
||||
this._setLoaded();
|
||||
this._updateAnimationProgress();
|
||||
}
|
||||
})
|
||||
}, i)
|
||||
});
|
||||
}
|
||||
},
|
||||
|
||||
_queueAnimationUpdate: function() {
|
||||
if (this._animationUpdateTimeoutId != 0)
|
||||
_queueUpdateAnimation: function() {
|
||||
if (this._updateAnimationTimeoutId != 0)
|
||||
return;
|
||||
|
||||
if (!this._cancellable || this._cancellable.is_cancelled())
|
||||
return;
|
||||
|
||||
if (!this._animation.duration)
|
||||
if (!this._animation.transitionDuration)
|
||||
return;
|
||||
|
||||
let nSteps = 255 / ANIMATION_OPACITY_STEP_INCREMENT;
|
||||
let timePerStep = (this._animation.transitionDuration * 1000) / nSteps;
|
||||
|
||||
let interval = Math.max(ANIMATION_MIN_WAKEUP_INTERVAL * 1000,
|
||||
ANIMATION_OPACITY_STEP_INCREMENT / this._animation.duration);
|
||||
this._animationUpdateTimeoutId = GLib.timeout_add(GLib.PRIORITY_DEFAULT,
|
||||
timePerStep);
|
||||
|
||||
if (interval > GLib.MAXUINT32)
|
||||
return;
|
||||
|
||||
this._updateAnimationTimeoutId = GLib.timeout_add(GLib.PRIORITY_DEFAULT,
|
||||
interval,
|
||||
Lang.bind(this, function() {
|
||||
this._animationUpdateTimeoutId = 0;
|
||||
this._updateAnimationTimeoutId = 0;
|
||||
this._updateAnimation();
|
||||
return false;
|
||||
}));
|
||||
@@ -585,9 +656,9 @@ const Animation = new Lang.Class({
|
||||
params = Params.parse(params, { filename: null });
|
||||
|
||||
this.filename = params.filename;
|
||||
this._keyFrames = [];
|
||||
this.duration = 0.0;
|
||||
this.keyFrameFiles = [];
|
||||
this.transitionProgress = 0.0;
|
||||
this.transitionDuration = 0.0;
|
||||
this.loaded = false;
|
||||
},
|
||||
|
||||
@@ -599,33 +670,31 @@ const Animation = new Lang.Class({
|
||||
this._show.load_async(null,
|
||||
Lang.bind(this,
|
||||
function(object, result) {
|
||||
this.duration = this._show.get_total_duration();
|
||||
this.loaded = true;
|
||||
if (callback)
|
||||
callback();
|
||||
}));
|
||||
},
|
||||
|
||||
getKeyFrameFiles: function(monitor) {
|
||||
update: function(monitor) {
|
||||
this.keyFrameFiles = [];
|
||||
|
||||
if (!this._show)
|
||||
return null;
|
||||
return;
|
||||
|
||||
if (this._show.get_num_slides() < 1)
|
||||
return null;
|
||||
return;
|
||||
|
||||
let [progress, duration, isFixed, file1, file2] = this._show.get_current_slide(monitor.width, monitor.height);
|
||||
|
||||
this.transitionDuration = duration;
|
||||
this.transitionProgress = progress;
|
||||
|
||||
let files = [];
|
||||
|
||||
if (file1)
|
||||
files.push(file1);
|
||||
this.keyFrameFiles.push(file1);
|
||||
|
||||
if (file2)
|
||||
files.push(file2);
|
||||
|
||||
return files;
|
||||
this.keyFrameFiles.push(file2);
|
||||
},
|
||||
});
|
||||
Signals.addSignalMethods(Animation.prototype);
|
||||
@@ -648,17 +717,9 @@ const BackgroundManager = new Lang.Class({
|
||||
|
||||
this.background = this._createBackground();
|
||||
this._newBackground = null;
|
||||
this._loadedSignalId = 0;
|
||||
this._changedSignalId = 0;
|
||||
},
|
||||
|
||||
destroy: function() {
|
||||
if (this._loadedSignalId)
|
||||
this._newBackground.disconnect(this._loadedSignalId);
|
||||
|
||||
if (this._changedSignalId)
|
||||
this.background.disconnect(this._changedSignalId);
|
||||
|
||||
if (this._newBackground) {
|
||||
this._newBackground.actor.destroy();
|
||||
this._newBackground = null;
|
||||
@@ -677,22 +738,28 @@ const BackgroundManager = new Lang.Class({
|
||||
newBackground.saturation = background.saturation;
|
||||
newBackground.visible = background.visible;
|
||||
|
||||
let signalId = newBackground.connect('loaded',
|
||||
newBackground.loadedSignalId = newBackground.connect('loaded',
|
||||
Lang.bind(this, function() {
|
||||
newBackground.disconnect(signalId);
|
||||
newBackground.disconnect(newBackground.loadedSignalId);
|
||||
newBackground.loadedSignalId = 0;
|
||||
Tweener.addTween(background.actor,
|
||||
{ opacity: 0,
|
||||
time: FADE_ANIMATION_TIME,
|
||||
transition: 'easeOutQuad',
|
||||
onComplete: Lang.bind(this, function() {
|
||||
this.background = newBackground;
|
||||
this._newBackground = null;
|
||||
if (this._newBackground == newBackground) {
|
||||
this.background = newBackground;
|
||||
this._newBackground = null;
|
||||
} else {
|
||||
newBackground.actor.destroy();
|
||||
}
|
||||
|
||||
background.actor.destroy();
|
||||
|
||||
this.emit('changed');
|
||||
})
|
||||
});
|
||||
}));
|
||||
this._loadedSignalId = signalId;
|
||||
|
||||
this._newBackground = newBackground;
|
||||
},
|
||||
@@ -711,12 +778,19 @@ const BackgroundManager = new Lang.Class({
|
||||
background.actor.lower_bottom();
|
||||
}
|
||||
|
||||
let signalId = background.connect('changed', Lang.bind(this, function() {
|
||||
background.disconnect(signalId);
|
||||
background.changeSignalId = background.connect('changed', Lang.bind(this, function() {
|
||||
background.disconnect(background.changeSignalId);
|
||||
background.changeSignalId = 0;
|
||||
this._updateBackground(background, this._monitorIndex);
|
||||
}));
|
||||
|
||||
this._changedSignalId = signalId;
|
||||
background.actor.connect('destroy', Lang.bind(this, function() {
|
||||
if (background.changeSignalId)
|
||||
background.disconnect(background.changeSignalId);
|
||||
|
||||
if (background.loadedSignalId)
|
||||
background.disconnect(background.loadedSignalId);
|
||||
}));
|
||||
|
||||
return background;
|
||||
},
|
||||
|
||||
@@ -46,8 +46,10 @@ function addBackgroundMenu(actor) {
|
||||
clickAction.connect('long-press', function(action, actor, state) {
|
||||
if (state == Clutter.LongPressState.QUERY)
|
||||
return action.get_button() == 1 && !actor._backgroundMenu.isOpen;
|
||||
if (state == Clutter.LongPressState.ACTIVATE)
|
||||
if (state == Clutter.LongPressState.ACTIVATE) {
|
||||
openMenu();
|
||||
actor._backgroundManager.ignoreRelease();
|
||||
}
|
||||
return true;
|
||||
});
|
||||
clickAction.connect('clicked', function(action) {
|
||||
@@ -55,4 +57,12 @@ function addBackgroundMenu(actor) {
|
||||
openMenu();
|
||||
});
|
||||
actor.add_action(clickAction);
|
||||
|
||||
actor.connect('destroy', function() {
|
||||
actor._backgroundMenu.destroy();
|
||||
actor._backgroundMenu = null;
|
||||
actor._backgroundManager = null;
|
||||
|
||||
cursor.destroy();
|
||||
});
|
||||
}
|
||||
|
||||
@@ -71,7 +71,7 @@ function _formatEventTime(event, clockFormat) {
|
||||
default:
|
||||
/* explicit fall-through */
|
||||
case '12h':
|
||||
/* Transators: Shown in calendar event list, if 12h format,
|
||||
/* Translators: Shown in calendar event list, if 12h format,
|
||||
\u2236 is a ratio character, similar to : and \u2009 is
|
||||
a thin space */
|
||||
ret = event.date.toLocaleFormat(C_("event list time", "%l\u2236%M\u2009%p"));
|
||||
@@ -168,6 +168,12 @@ const EmptyEventSource = new Lang.Class({
|
||||
Name: 'EmptyEventSource',
|
||||
|
||||
_init: function() {
|
||||
this.isLoading = false;
|
||||
this.isDummy = true;
|
||||
this.hasCalendars = false;
|
||||
},
|
||||
|
||||
destroy: function() {
|
||||
},
|
||||
|
||||
requestRange: function(begin, end) {
|
||||
@@ -191,6 +197,7 @@ const CalendarServerIface = <interface name="org.gnome.Shell.CalendarServer">
|
||||
<arg type="b" direction="in" />
|
||||
<arg type="a(sssbxxa{sv})" direction="out" />
|
||||
</method>
|
||||
<property name="HasCalendars" type="b" access="read" />
|
||||
<signal name="Changed" />
|
||||
</interface>;
|
||||
|
||||
@@ -201,8 +208,7 @@ function CalendarServer() {
|
||||
g_interface_name: CalendarServerInfo.name,
|
||||
g_interface_info: CalendarServerInfo,
|
||||
g_name: 'org.gnome.Shell.CalendarServer',
|
||||
g_object_path: '/org/gnome/Shell/CalendarServer',
|
||||
g_flags: Gio.DBusProxyFlags.DO_NOT_LOAD_PROPERTIES });
|
||||
g_object_path: '/org/gnome/Shell/CalendarServer' });
|
||||
}
|
||||
|
||||
function _datesEqual(a, b) {
|
||||
@@ -229,6 +235,8 @@ const DBusEventSource = new Lang.Class({
|
||||
|
||||
_init: function() {
|
||||
this._resetCache();
|
||||
this.isLoading = false;
|
||||
this.isDummy = false;
|
||||
|
||||
this._initialized = false;
|
||||
this._dbusProxy = new CalendarServer();
|
||||
@@ -249,11 +257,27 @@ const DBusEventSource = new Lang.Class({
|
||||
this._onNameVanished();
|
||||
}));
|
||||
|
||||
this._dbusProxy.connect('g-properties-changed', Lang.bind(this, function() {
|
||||
this.emit('notify::has-calendars');
|
||||
}));
|
||||
|
||||
this._initialized = true;
|
||||
this.emit('notify::has-calendars');
|
||||
this._onNameAppeared();
|
||||
}));
|
||||
},
|
||||
|
||||
destroy: function() {
|
||||
this._dbusProxy.run_dispose();
|
||||
},
|
||||
|
||||
get hasCalendars() {
|
||||
if (this._initialized)
|
||||
return this._dbusProxy.HasCalendars;
|
||||
else
|
||||
return false;
|
||||
},
|
||||
|
||||
_resetCache: function() {
|
||||
this._events = [];
|
||||
this._lastRequestBegin = null;
|
||||
@@ -293,6 +317,7 @@ const DBusEventSource = new Lang.Class({
|
||||
}
|
||||
|
||||
this._events = newEvents;
|
||||
this.isLoading = false;
|
||||
this.emit('changed');
|
||||
},
|
||||
|
||||
@@ -315,6 +340,7 @@ const DBusEventSource = new Lang.Class({
|
||||
|
||||
requestRange: function(begin, end, forceReload) {
|
||||
if (forceReload || !(_datesEqual(begin, this._lastRequestBegin) && _datesEqual(end, this._lastRequestEnd))) {
|
||||
this.isLoading = true;
|
||||
this._lastRequestBegin = begin;
|
||||
this._lastRequestEnd = end;
|
||||
this._curRequestBegin = begin;
|
||||
@@ -389,19 +415,11 @@ const Calendar = new Lang.Class({
|
||||
// @eventSource: is an object implementing the EventSource API, e.g. the
|
||||
// requestRange(), getEvents(), hasEvents() methods and the ::changed signal.
|
||||
setEventSource: function(eventSource) {
|
||||
if (this._eventSource) {
|
||||
this._eventSource.disconnect(this._eventSourceChangedId);
|
||||
this._eventSource = null;
|
||||
}
|
||||
|
||||
this._eventSource = eventSource;
|
||||
|
||||
if (this._eventSource) {
|
||||
this._eventSourceChangedId = this._eventSource.connect('changed', Lang.bind(this, function() {
|
||||
this._update(false);
|
||||
}));
|
||||
this._update(true);
|
||||
}
|
||||
this._eventSource.connect('changed', Lang.bind(this, function() {
|
||||
this._update(false);
|
||||
}));
|
||||
this._update(true);
|
||||
},
|
||||
|
||||
// Sets the calendar to show a specific date
|
||||
@@ -538,20 +556,44 @@ const Calendar = new Lang.Class({
|
||||
children[i].destroy();
|
||||
|
||||
// Start at the beginning of the week before the start of the month
|
||||
//
|
||||
// We want to show always 6 weeks (to keep the calendar menu at the same
|
||||
// height if there are no events), so we pad it according to the following
|
||||
// policy:
|
||||
//
|
||||
// 1 - If a month has 6 weeks, we place no padding (example: Dec 2012)
|
||||
// 2 - If a month has 5 weeks and it starts on week start, we pad one week
|
||||
// before it (example: Apr 2012)
|
||||
// 3 - If a month has 5 weeks and it starts on any other day, we pad one week
|
||||
// after it (example: Nov 2012)
|
||||
// 4 - If a month has 4 weeks, we pad one week before and one after it
|
||||
// (example: Feb 2010)
|
||||
//
|
||||
// Actually computing the number of weeks is complex, but we know that the
|
||||
// problematic categories (2 and 4) always start on week start, and that
|
||||
// all months at the end have 6 weeks.
|
||||
|
||||
let beginDate = new Date(this._selectedDate);
|
||||
beginDate.setDate(1);
|
||||
beginDate.setSeconds(0);
|
||||
beginDate.setHours(12);
|
||||
let year = beginDate.getYear();
|
||||
|
||||
let daysToWeekStart = (7 + beginDate.getDay() - this._weekStart) % 7;
|
||||
beginDate.setTime(beginDate.getTime() - daysToWeekStart * MSECS_IN_DAY);
|
||||
let startsOnWeekStart = daysToWeekStart == 0;
|
||||
let weekPadding = startsOnWeekStart ? 7 : 0;
|
||||
|
||||
beginDate.setTime(beginDate.getTime() - (weekPadding + daysToWeekStart) * MSECS_IN_DAY);
|
||||
|
||||
let iter = new Date(beginDate);
|
||||
let row = 2;
|
||||
while (true) {
|
||||
// nRows here means 6 weeks + one header + one navbar
|
||||
let nRows = 8;
|
||||
while (row < 8) {
|
||||
let button = new St.Button({ label: iter.getDate().toString() });
|
||||
let rtl = button.get_text_direction() == Clutter.TextDirection.RTL;
|
||||
|
||||
if (!this._eventSource)
|
||||
if (this._eventSource.isDummy)
|
||||
button.reactive = false;
|
||||
|
||||
let iterStr = iter.toUTCString();
|
||||
@@ -560,8 +602,9 @@ const Calendar = new Lang.Class({
|
||||
this.setDate(newlySelectedDate, false);
|
||||
}));
|
||||
|
||||
let hasEvents = this._eventSource && this._eventSource.hasEvents(iter);
|
||||
let hasEvents = this._eventSource.hasEvents(iter);
|
||||
let styleClass = 'calendar-day-base calendar-day';
|
||||
|
||||
if (_isWorkDay(iter))
|
||||
styleClass += ' calendar-work-day'
|
||||
else
|
||||
@@ -601,17 +644,13 @@ const Calendar = new Lang.Class({
|
||||
}
|
||||
|
||||
iter.setTime(iter.getTime() + MSECS_IN_DAY);
|
||||
if (iter.getDay() == this._weekStart) {
|
||||
// We stop on the first "first day of the week" after the month we are displaying
|
||||
if (iter.getMonth() > this._selectedDate.getMonth() || iter.getYear() > this._selectedDate.getYear())
|
||||
break;
|
||||
|
||||
if (iter.getDay() == this._weekStart)
|
||||
row++;
|
||||
}
|
||||
}
|
||||
// Signal to the event source that we are interested in events
|
||||
// only from this date range
|
||||
if (this._eventSource)
|
||||
this._eventSource.requestRange(beginDate, iter, forceReload);
|
||||
this._eventSource.requestRange(beginDate, iter, forceReload);
|
||||
}
|
||||
});
|
||||
|
||||
@@ -629,16 +668,8 @@ const EventsList = new Lang.Class({
|
||||
},
|
||||
|
||||
setEventSource: function(eventSource) {
|
||||
if (this._eventSource) {
|
||||
this._eventSource.disconnect(this._eventSourceChangedId);
|
||||
this._eventSource = null;
|
||||
}
|
||||
|
||||
this._eventSource = eventSource;
|
||||
|
||||
if (this._eventSource) {
|
||||
this._eventSourceChangedId = this._eventSource.connect('changed', Lang.bind(this, this._update));
|
||||
}
|
||||
this._eventSource.connect('changed', Lang.bind(this, this._update));
|
||||
},
|
||||
|
||||
_addEvent: function(dayNameBox, timeBox, eventTitleBox, includeDayName, day, time, desc) {
|
||||
@@ -655,9 +686,6 @@ const EventsList = new Lang.Class({
|
||||
},
|
||||
|
||||
_addPeriod: function(header, begin, end, includeDayName, showNothingScheduled) {
|
||||
if (!this._eventSource)
|
||||
return;
|
||||
|
||||
let events = this._eventSource.getEvents(begin, end);
|
||||
|
||||
let clockFormat = this._desktopSettings.get_string(CLOCK_FORMAT_KEY);;
|
||||
@@ -754,6 +782,9 @@ const EventsList = new Lang.Class({
|
||||
},
|
||||
|
||||
_update: function() {
|
||||
if (this._eventSource.isLoading)
|
||||
return;
|
||||
|
||||
let today = new Date();
|
||||
if (_sameDay (this._date, today)) {
|
||||
this._showToday();
|
||||
|
||||
@@ -292,6 +292,7 @@ const AutorunResidentSource = new Lang.Class({
|
||||
|
||||
_init: function(manager) {
|
||||
this.parent(_("Removable Devices"), 'media-removable');
|
||||
this.resident = true;
|
||||
|
||||
this._mounts = [];
|
||||
|
||||
|
||||
@@ -222,7 +222,7 @@ const KeyringPrompter = new Lang.Class({
|
||||
enable: function() {
|
||||
this._prompter.register(Gio.DBus.session);
|
||||
this._dbusId = Gio.DBus.session.own_name('org.gnome.keyring.SystemPrompter',
|
||||
Gio.BusNameOwnerFlags.REPLACE, null, null);
|
||||
Gio.BusNameOwnerFlags.ALLOW_REPLACEMENT, null, null);
|
||||
},
|
||||
|
||||
disable: function() {
|
||||
|
||||
@@ -20,8 +20,7 @@ const Recorder = new Lang.Class({
|
||||
Main.wm.addKeybinding('toggle-recording',
|
||||
this._bindingSettings,
|
||||
Meta.KeyBindingFlags.NONE,
|
||||
Shell.KeyBindingMode.NORMAL |
|
||||
Shell.KeyBindingMode.OVERVIEW,
|
||||
Shell.KeyBindingMode.ALL,
|
||||
Lang.bind(this, this._toggleRecorder));
|
||||
},
|
||||
|
||||
|
||||
@@ -103,6 +103,11 @@ const CtrlAltTabManager = new Lang.Class({
|
||||
else
|
||||
icon = textureCache.bind_pixbuf_property(windows[i], 'icon');
|
||||
items.push({ name: windows[i].title,
|
||||
proxy: windows[i].get_compositor_private(),
|
||||
focusCallback: Lang.bind(windows[i],
|
||||
function(timestamp) {
|
||||
Main.activateWindow(this, timestamp);
|
||||
}),
|
||||
iconActor: icon,
|
||||
sortGroup: SortGroup.MIDDLE });
|
||||
}
|
||||
|
||||
@@ -161,8 +161,10 @@ const DateMenuButton = new Lang.Class({
|
||||
this._openClocksItem.actor.visible = app !== null;
|
||||
},
|
||||
|
||||
_setEventsVisibility: function(visible) {
|
||||
_updateEventsVisibility: function() {
|
||||
let visible = this._eventSource.hasCalendars;
|
||||
this._openCalendarItem.actor.visible = visible;
|
||||
this._openClocksItem.actor.visible = visible;
|
||||
this._separator.visible = visible;
|
||||
if (visible) {
|
||||
let alignment = 0.25;
|
||||
@@ -177,8 +179,16 @@ const DateMenuButton = new Lang.Class({
|
||||
},
|
||||
|
||||
_setEventSource: function(eventSource) {
|
||||
if (this._eventSource)
|
||||
this._eventSource.destroy();
|
||||
|
||||
this._calendar.setEventSource(eventSource);
|
||||
this._eventList.setEventSource(eventSource);
|
||||
|
||||
this._eventSource = eventSource;
|
||||
this._eventSource.connect('notify::has-calendars', Lang.bind(this, function() {
|
||||
this._updateEventsVisibility();
|
||||
}));
|
||||
},
|
||||
|
||||
_sessionUpdated: function() {
|
||||
@@ -187,10 +197,10 @@ const DateMenuButton = new Lang.Class({
|
||||
if (showEvents) {
|
||||
eventSource = new Calendar.DBusEventSource();
|
||||
} else {
|
||||
eventSource = null;
|
||||
eventSource = new Calendar.EmptyEventSource();
|
||||
}
|
||||
this._setEventSource(eventSource);
|
||||
this._setEventsVisibility(showEvents);
|
||||
this._updateEventsVisibility();
|
||||
|
||||
// This needs to be handled manually, as the code to
|
||||
// autohide separators doesn't work across the vbox
|
||||
@@ -211,6 +221,8 @@ const DateMenuButton = new Lang.Class({
|
||||
this.menu.close();
|
||||
|
||||
let app = Gio.AppInfo.get_default_for_type('text/calendar', false);
|
||||
if (app.get_id() == 'evolution.desktop')
|
||||
app = Gio.DesktopAppInfo.new('evolution-calendar.desktop');
|
||||
app.launch([], global.create_app_launch_context());
|
||||
},
|
||||
|
||||
|
||||
28
js/ui/dnd.js
28
js/ui/dnd.js
@@ -85,11 +85,13 @@ const _Draggable = new Lang.Class({
|
||||
|
||||
this.actor.connect('destroy', Lang.bind(this, function() {
|
||||
this._actorDestroyed = true;
|
||||
|
||||
// If the drag actor is destroyed and we were going to fix
|
||||
// up its hover state, fix up the parent hover state instead
|
||||
if (this.actor == this._firstLeaveActor)
|
||||
this._firstLeaveActor = this._dragOrigParent;
|
||||
if (this._dragInProgress)
|
||||
|
||||
if (this._dragInProgress && this._dragCancellable)
|
||||
this._cancelDrag(global.get_current_time());
|
||||
this.disconnectAll();
|
||||
}));
|
||||
@@ -102,6 +104,7 @@ const _Draggable = new Lang.Class({
|
||||
this._buttonDown = false; // The mouse button has been pressed and has not yet been released.
|
||||
this._dragInProgress = false; // The drag has been started, and has not been dropped or cancelled yet.
|
||||
this._animationInProgress = false; // The drag is over and the item is in the process of animating to its original position (snapping back or reverting).
|
||||
this._dragCancellable = true;
|
||||
|
||||
// During the drag, we eat enter/leave events so that actors don't prelight.
|
||||
// But we remember the actors that we first left/last entered so we can
|
||||
@@ -288,19 +291,19 @@ const _Draggable = new Lang.Class({
|
||||
this._dragOrigY = this._dragActor.y;
|
||||
this._dragOrigScale = this._dragActor.scale_x;
|
||||
|
||||
this._dragActor.reparent(Main.uiGroup);
|
||||
this._dragActor.raise_top();
|
||||
Shell.util_set_hidden_from_pick(this._dragActor, true);
|
||||
// Set the actor's scale such that it will keep the same
|
||||
// transformed size when it's reparented to the uiGroup
|
||||
let [scaledWidth, scaledHeight] = this.actor.get_transformed_size();
|
||||
this._dragActor.set_scale(scaledWidth / this.actor.width,
|
||||
scaledHeight / this.actor.height);
|
||||
|
||||
let [actorStageX, actorStageY] = this.actor.get_transformed_position();
|
||||
this._dragOffsetX = actorStageX - this._dragStartX;
|
||||
this._dragOffsetY = actorStageY - this._dragStartY;
|
||||
|
||||
// Set the actor's scale such that it will keep the same
|
||||
// transformed size when it's reparented to the uiGroup
|
||||
let [scaledWidth, scaledHeight] = this.actor.get_transformed_size();
|
||||
this.actor.set_scale(scaledWidth / this.actor.width,
|
||||
scaledHeight / this.actor.height);
|
||||
this._dragActor.reparent(Main.uiGroup);
|
||||
this._dragActor.raise_top();
|
||||
Shell.util_set_hidden_from_pick(this._dragActor, true);
|
||||
}
|
||||
|
||||
this._dragOrigOpacity = this._dragActor.opacity;
|
||||
@@ -439,6 +442,11 @@ const _Draggable = new Lang.Class({
|
||||
}
|
||||
}
|
||||
|
||||
// At this point it is too late to cancel a drag by destroying
|
||||
// the actor, the fate of which is decided by acceptDrop and its
|
||||
// side-effects
|
||||
this._dragCancellable = false;
|
||||
|
||||
while (target) {
|
||||
if (target._delegate && target._delegate.acceptDrop) {
|
||||
let [r, targX, targY] = target.transform_stage_point(dropX, dropY);
|
||||
@@ -447,8 +455,6 @@ const _Draggable = new Lang.Class({
|
||||
targX,
|
||||
targY,
|
||||
event.get_time())) {
|
||||
if (this._actorDestroyed)
|
||||
return true;
|
||||
// If it accepted the drop without taking the actor,
|
||||
// handle it ourselves.
|
||||
if (this._dragActor.get_parent() == Main.uiGroup) {
|
||||
|
||||
@@ -225,7 +225,8 @@ const EndSessionDialog = new Lang.Class({
|
||||
Extends: ModalDialog.ModalDialog,
|
||||
|
||||
_init: function() {
|
||||
this.parent({ styleClass: 'end-session-dialog' });
|
||||
this.parent({ styleClass: 'end-session-dialog',
|
||||
destroyOnClose: false });
|
||||
|
||||
this._user = AccountsService.UserManager.get_default().get_user(GLib.get_user_name());
|
||||
|
||||
|
||||
@@ -248,7 +248,7 @@ const GrabHelper = new Lang.Class({
|
||||
global.set_stage_input_mode(Shell.StageInputMode.FOCUSED);
|
||||
}
|
||||
|
||||
global.screen.focus_default_window(global.get_current_time());
|
||||
global.screen.focus_default_window(global.display.get_current_time_roundtrip());
|
||||
},
|
||||
|
||||
// ignoreRelease:
|
||||
@@ -308,6 +308,8 @@ const GrabHelper = new Lang.Class({
|
||||
if (!this.grabbed && this._capturedEventId > 0) {
|
||||
global.stage.disconnect(this._capturedEventId);
|
||||
this._capturedEventId = 0;
|
||||
|
||||
this._ignoreRelease = false;
|
||||
}
|
||||
|
||||
if (hadFocus) {
|
||||
@@ -353,6 +355,7 @@ const GrabHelper = new Lang.Class({
|
||||
this._ignoreRelease = true;
|
||||
let i = this._actorInGrabStack(event.get_source()) + 1;
|
||||
this.ungrab({ actor: this._grabStack[i].actor, isUser: true });
|
||||
return true;
|
||||
}
|
||||
|
||||
return this._modalCount > 0;
|
||||
|
||||
549
js/ui/layout.js
549
js/ui/layout.js
@@ -18,7 +18,6 @@ const Main = imports.ui.main;
|
||||
const Params = imports.misc.params;
|
||||
const Tweener = imports.ui.tweener;
|
||||
|
||||
const HOT_CORNER_ACTIVATION_TIMEOUT = 0.5;
|
||||
const STARTUP_ANIMATION_TIME = 0.5;
|
||||
const KEYBOARD_ANIMATION_TIME = 0.15;
|
||||
const BACKGROUND_FADE_ANIMATION_TIME = 1.0;
|
||||
@@ -29,6 +28,9 @@ const DEFAULT_BACKGROUND_COLOR = Clutter.Color.from_pixel(0x2e3436ff);
|
||||
const MESSAGE_TRAY_PRESSURE_THRESHOLD = 250; // pixels
|
||||
const MESSAGE_TRAY_PRESSURE_TIMEOUT = 1000; // ms
|
||||
|
||||
const HOT_CORNER_PRESSURE_THRESHOLD = 100; // pixels
|
||||
const HOT_CORNER_PRESSURE_TIMEOUT = 1000; // ms
|
||||
|
||||
function isPopupMetaWindow(actor) {
|
||||
switch(actor.meta_window.get_window_type()) {
|
||||
case Meta.WindowType.DROPDOWN_MENU:
|
||||
@@ -116,6 +118,22 @@ const MonitorConstraint = new Lang.Class({
|
||||
}
|
||||
});
|
||||
|
||||
const Monitor = new Lang.Class({
|
||||
Name: 'Monitor',
|
||||
|
||||
_init: function(index, geometry) {
|
||||
this.index = index;
|
||||
this.x = geometry.x;
|
||||
this.y = geometry.y;
|
||||
this.width = geometry.width;
|
||||
this.height = geometry.height;
|
||||
},
|
||||
|
||||
get inFullscreen() {
|
||||
return global.screen.get_monitor_in_fullscreen(this.index);
|
||||
}
|
||||
})
|
||||
|
||||
const defaultParams = {
|
||||
trackFullscreen: false,
|
||||
affectsStruts: false,
|
||||
@@ -130,9 +148,9 @@ const LayoutManager = new Lang.Class({
|
||||
this.monitors = [];
|
||||
this.primaryMonitor = null;
|
||||
this.primaryIndex = -1;
|
||||
this.hotCorners = [];
|
||||
|
||||
this._keyboardIndex = -1;
|
||||
this._hotCorners = [];
|
||||
this._leftPanelBarrier = null;
|
||||
this._rightPanelBarrier = null;
|
||||
this._trayBarrier = null;
|
||||
|
||||
@@ -140,6 +158,7 @@ const LayoutManager = new Lang.Class({
|
||||
this._updateRegionIdle = 0;
|
||||
|
||||
this._trackedActors = [];
|
||||
this._topActors = [];
|
||||
this._isPopupWindowVisible = false;
|
||||
this._startingUp = true;
|
||||
|
||||
@@ -191,6 +210,7 @@ const LayoutManager = new Lang.Class({
|
||||
this.trayBox = new St.Widget({ name: 'trayBox',
|
||||
layout_manager: new Clutter.BinLayout() });
|
||||
this.addChrome(this.trayBox);
|
||||
this._setupTrayPressure();
|
||||
|
||||
this.keyboardBox = new St.BoxLayout({ name: 'keyboardBox',
|
||||
reactive: true,
|
||||
@@ -218,6 +238,8 @@ const LayoutManager = new Lang.Class({
|
||||
Lang.bind(this, this._windowsRestacked));
|
||||
global.screen.connect('monitors-changed',
|
||||
Lang.bind(this, this._monitorsChanged));
|
||||
global.screen.connect('in-fullscreen-changed',
|
||||
Lang.bind(this, this._updateFullscreen));
|
||||
this._monitorsChanged();
|
||||
},
|
||||
|
||||
@@ -228,6 +250,8 @@ const LayoutManager = new Lang.Class({
|
||||
Main.overview.connect('showing', Lang.bind(this, this._overviewShowing));
|
||||
Main.overview.connect('hidden', Lang.bind(this, this._overviewHidden));
|
||||
Main.sessionMode.connect('updated', Lang.bind(this, this._sessionUpdated));
|
||||
|
||||
this._prepareStartupAnimation();
|
||||
},
|
||||
|
||||
_overviewShowing: function() {
|
||||
@@ -253,7 +277,7 @@ const LayoutManager = new Lang.Class({
|
||||
this.monitors = [];
|
||||
let nMonitors = screen.get_n_monitors();
|
||||
for (let i = 0; i < nMonitors; i++)
|
||||
this.monitors.push(screen.get_monitor_geometry(i));
|
||||
this.monitors.push(new Monitor(i, screen.get_monitor_geometry(i)));
|
||||
|
||||
if (nMonitors == 1) {
|
||||
this.primaryIndex = this.bottomIndex = 0;
|
||||
@@ -275,56 +299,61 @@ const LayoutManager = new Lang.Class({
|
||||
|
||||
_updateHotCorners: function() {
|
||||
// destroy old hot corners
|
||||
for (let i = 0; i < this._hotCorners.length; i++)
|
||||
this._hotCorners[i].destroy();
|
||||
this._hotCorners = [];
|
||||
this.hotCorners.forEach(function(corner) {
|
||||
if (corner)
|
||||
corner.destroy();
|
||||
});
|
||||
this.hotCorners = [];
|
||||
|
||||
let size = this.panelBox.height;
|
||||
|
||||
// build new hot corners
|
||||
for (let i = 0; i < this.monitors.length; i++) {
|
||||
if (i == this.primaryIndex)
|
||||
continue;
|
||||
|
||||
let monitor = this.monitors[i];
|
||||
let cornerX = this._rtl ? monitor.x + monitor.width : monitor.x;
|
||||
let cornerY = monitor.y;
|
||||
|
||||
let haveTopLeftCorner = true;
|
||||
|
||||
// Check if we have a top left (right for RTL) corner.
|
||||
// I.e. if there is no monitor directly above or to the left(right)
|
||||
let besideX = this._rtl ? monitor.x + 1 : cornerX - 1;
|
||||
let besideY = cornerY;
|
||||
let aboveX = cornerX;
|
||||
let aboveY = cornerY - 1;
|
||||
if (i != this.primaryIndex) {
|
||||
// Check if we have a top left (right for RTL) corner.
|
||||
// I.e. if there is no monitor directly above or to the left(right)
|
||||
let besideX = this._rtl ? monitor.x + 1 : cornerX - 1;
|
||||
let besideY = cornerY;
|
||||
let aboveX = cornerX;
|
||||
let aboveY = cornerY - 1;
|
||||
|
||||
for (let j = 0; j < this.monitors.length; j++) {
|
||||
if (i == j)
|
||||
continue;
|
||||
let otherMonitor = this.monitors[j];
|
||||
if (besideX >= otherMonitor.x &&
|
||||
besideX < otherMonitor.x + otherMonitor.width &&
|
||||
besideY >= otherMonitor.y &&
|
||||
besideY < otherMonitor.y + otherMonitor.height) {
|
||||
haveTopLeftCorner = false;
|
||||
break;
|
||||
}
|
||||
if (aboveX >= otherMonitor.x &&
|
||||
aboveX < otherMonitor.x + otherMonitor.width &&
|
||||
aboveY >= otherMonitor.y &&
|
||||
aboveY < otherMonitor.y + otherMonitor.height) {
|
||||
haveTopLeftCorner = false;
|
||||
break;
|
||||
for (let j = 0; j < this.monitors.length; j++) {
|
||||
if (i == j)
|
||||
continue;
|
||||
let otherMonitor = this.monitors[j];
|
||||
if (besideX >= otherMonitor.x &&
|
||||
besideX < otherMonitor.x + otherMonitor.width &&
|
||||
besideY >= otherMonitor.y &&
|
||||
besideY < otherMonitor.y + otherMonitor.height) {
|
||||
haveTopLeftCorner = false;
|
||||
break;
|
||||
}
|
||||
if (aboveX >= otherMonitor.x &&
|
||||
aboveX < otherMonitor.x + otherMonitor.width &&
|
||||
aboveY >= otherMonitor.y &&
|
||||
aboveY < otherMonitor.y + otherMonitor.height) {
|
||||
haveTopLeftCorner = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!haveTopLeftCorner)
|
||||
continue;
|
||||
|
||||
let corner = new HotCorner(this);
|
||||
this._hotCorners.push(corner);
|
||||
corner.actor.set_position(cornerX, cornerY);
|
||||
this.addChrome(corner.actor);
|
||||
if (haveTopLeftCorner) {
|
||||
let corner = new HotCorner(this, monitor, cornerX, cornerY);
|
||||
corner.setBarrierSize(size);
|
||||
this.hotCorners.push(corner);
|
||||
} else {
|
||||
this.hotCorners.push(null);
|
||||
}
|
||||
}
|
||||
|
||||
this.emit('hot-corners-changed');
|
||||
},
|
||||
|
||||
_createBackground: function(monitorIndex) {
|
||||
@@ -394,16 +423,16 @@ const LayoutManager = new Lang.Class({
|
||||
},
|
||||
|
||||
_panelBoxChanged: function() {
|
||||
this.emit('panel-box-changed');
|
||||
this._updatePanelBarriers();
|
||||
this._updatePanelBarrier();
|
||||
|
||||
let size = this.panelBox.height;
|
||||
this.hotCorners.forEach(function(corner) {
|
||||
if (corner)
|
||||
corner.setBarrierSize(size);
|
||||
});
|
||||
},
|
||||
|
||||
_updatePanelBarriers: function() {
|
||||
if (this._leftPanelBarrier) {
|
||||
this._leftPanelBarrier.destroy();
|
||||
this._leftPanelBarrier = null;
|
||||
}
|
||||
|
||||
_updatePanelBarrier: function() {
|
||||
if (this._rightPanelBarrier) {
|
||||
this._rightPanelBarrier.destroy();
|
||||
this._rightPanelBarrier = null;
|
||||
@@ -412,10 +441,6 @@ const LayoutManager = new Lang.Class({
|
||||
if (this.panelBox.height) {
|
||||
let primary = this.primaryMonitor;
|
||||
|
||||
this._leftPanelBarrier = new Meta.Barrier({ display: global.display,
|
||||
x1: primary.x, y1: primary.y,
|
||||
x2: primary.x, y2: primary.y + this.panelBox.height,
|
||||
directions: Meta.BarrierDirection.POSITIVE_X });
|
||||
this._rightPanelBarrier = new Meta.Barrier({ display: global.display,
|
||||
x1: primary.x + primary.width, y1: primary.y,
|
||||
x2: primary.x + primary.width, y2: primary.y + this.panelBox.height,
|
||||
@@ -423,28 +448,44 @@ const LayoutManager = new Lang.Class({
|
||||
}
|
||||
},
|
||||
|
||||
_setupTrayPressure: function() {
|
||||
this._trayPressure = new PressureBarrier(MESSAGE_TRAY_PRESSURE_THRESHOLD,
|
||||
MESSAGE_TRAY_PRESSURE_TIMEOUT,
|
||||
Shell.KeyBindingMode.NORMAL |
|
||||
Shell.KeyBindingMode.OVERVIEW);
|
||||
this._trayPressure.setEventFilter(this._trayBarrierEventFilter);
|
||||
this._trayPressure.connect('trigger', function(barrier) {
|
||||
if (Main.layoutManager.bottomMonitor.inFullscreen)
|
||||
return;
|
||||
|
||||
Main.messageTray.openTray();
|
||||
});
|
||||
},
|
||||
|
||||
_updateTrayBarrier: function() {
|
||||
let monitor = this.bottomMonitor;
|
||||
|
||||
if (this._trayBarrier) {
|
||||
this._trayPressure.removeBarrier(this._trayBarrier);
|
||||
this._trayBarrier.destroy();
|
||||
this._trayBarrier = null;
|
||||
}
|
||||
|
||||
if (this._trayPressure) {
|
||||
this._trayPressure.destroy();
|
||||
this._trayPressure = null;
|
||||
}
|
||||
|
||||
this._trayBarrier = new Meta.Barrier({ display: global.display,
|
||||
x1: monitor.x, x2: monitor.x + monitor.width,
|
||||
y1: monitor.y + monitor.height, y2: monitor.y + monitor.height,
|
||||
directions: Meta.BarrierDirection.NEGATIVE_Y });
|
||||
this._trayPressure.addBarrier(this._trayBarrier);
|
||||
},
|
||||
|
||||
this._trayPressure = new PressureBarrier(this._trayBarrier, MESSAGE_TRAY_PRESSURE_THRESHOLD, MESSAGE_TRAY_PRESSURE_TIMEOUT);
|
||||
this._trayPressure.connect('trigger', function(barrier) {
|
||||
Main.messageTray.openTray();
|
||||
});
|
||||
_trayBarrierEventFilter: function(event) {
|
||||
// Throw out all events where the pointer was grabbed by another
|
||||
// client, as the client that grabbed the pointer expects to have
|
||||
// complete control over it
|
||||
if (event.grabbed && Main.modalCount == 0)
|
||||
return true;
|
||||
|
||||
return false;
|
||||
},
|
||||
|
||||
_monitorsChanged: function() {
|
||||
@@ -534,7 +575,7 @@ const LayoutManager = new Lang.Class({
|
||||
// MetaBackgroundActor inside global.window_group covers the entirety of the
|
||||
// screen. So, we set no_clear_hint at the end of the animation.
|
||||
|
||||
prepareStartupAnimation: function() {
|
||||
_prepareStartupAnimation: function() {
|
||||
// Set ourselves to FULLSCREEN input mode while the animation is running
|
||||
// so events don't get delivered to X11 windows (which are distorted by the animation)
|
||||
global.stage_input_mode = Shell.StageInputMode.FULLSCREEN;
|
||||
@@ -557,6 +598,7 @@ const LayoutManager = new Lang.Class({
|
||||
y / global.screen_height);
|
||||
this.uiGroup.scale_x = this.uiGroup.scale_y = 0.5;
|
||||
this.uiGroup.opacity = 0;
|
||||
global.window_group.set_clip(monitor.x, monitor.y, monitor.width, monitor.height);
|
||||
}
|
||||
|
||||
this._systemBackground = new Background.SystemBackground();
|
||||
@@ -572,25 +614,25 @@ const LayoutManager = new Lang.Class({
|
||||
Lang.bind(this, function() {
|
||||
this._systemBackground.disconnect(signalId);
|
||||
this._systemBackground.actor.show();
|
||||
global.stage.show();
|
||||
|
||||
this.emit('startup-prepared');
|
||||
|
||||
// We're mostly prepared for the startup animation
|
||||
// now, but since a lot is going on asynchronously
|
||||
// during startup, let's defer emission of the
|
||||
// startup-prepared signal until the event loop is
|
||||
// uncontended and idle. This helps to prevent us
|
||||
// from running the animation when the system is
|
||||
// bogged down
|
||||
// during startup, let's defer the startup animation
|
||||
// until the event loop is uncontended and idle.
|
||||
// This helps to prevent us from running the animation
|
||||
// when the system is bogged down
|
||||
GLib.idle_add(GLib.PRIORITY_LOW,
|
||||
Lang.bind(this, function() {
|
||||
this.emit('startup-prepared');
|
||||
return false;
|
||||
}));
|
||||
|
||||
this._startupAnimation();
|
||||
return false;
|
||||
}));
|
||||
}));
|
||||
},
|
||||
|
||||
startupAnimation: function() {
|
||||
global.stage.show();
|
||||
_startupAnimation: function() {
|
||||
if (Main.sessionMode.isGreeter)
|
||||
this._startupAnimationGreeter();
|
||||
else
|
||||
@@ -633,12 +675,14 @@ const LayoutManager = new Lang.Class({
|
||||
this.trayBox.show();
|
||||
this.keyboardBox.show();
|
||||
|
||||
if (!Main.sessionMode.isGreeter)
|
||||
if (!Main.sessionMode.isGreeter) {
|
||||
this._createSecondaryBackgrounds();
|
||||
|
||||
this.emit('panel-box-changed');
|
||||
global.window_group.remove_clip();
|
||||
}
|
||||
|
||||
this._queueUpdateRegions();
|
||||
|
||||
this.emit('startup-complete');
|
||||
},
|
||||
|
||||
showKeyboard: function () {
|
||||
@@ -814,6 +858,11 @@ const LayoutManager = new Lang.Class({
|
||||
},
|
||||
|
||||
_updateVisibility: function() {
|
||||
let windowsVisible = Main.sessionMode.hasWindows && !this._inOverview;
|
||||
|
||||
global.window_group.visible = windowsVisible;
|
||||
global.top_window_group.visible = windowsVisible;
|
||||
|
||||
for (let i = 0; i < this._trackedActors.length; i++) {
|
||||
let actorData = this._trackedActors[i], visible;
|
||||
if (!actorData.trackFullscreen)
|
||||
@@ -821,7 +870,7 @@ const LayoutManager = new Lang.Class({
|
||||
if (!actorData.isToplevel)
|
||||
continue;
|
||||
|
||||
if (this._inOverview || !Main.sessionMode.hasWindows)
|
||||
if (!windowsVisible)
|
||||
visible = true;
|
||||
else if (this.findMonitorForActor(actorData.actor).inFullscreen)
|
||||
visible = false;
|
||||
@@ -871,95 +920,20 @@ const LayoutManager = new Lang.Class({
|
||||
},
|
||||
|
||||
_updateFullscreen: function() {
|
||||
let windows = this._getWindowActorsForWorkspace(global.screen.get_active_workspace());
|
||||
|
||||
// Reset all monitors to not fullscreen
|
||||
for (let i = 0; i < this.monitors.length; i++)
|
||||
this.monitors[i].inFullscreen = false;
|
||||
|
||||
// Ordinary chrome should be visible unless there is a window
|
||||
// with layer FULLSCREEN, or a window with layer
|
||||
// OVERRIDE_REDIRECT that covers the whole screen.
|
||||
// ('override_redirect' is not actually a layer above all
|
||||
// other windows, but this seems to be how mutter treats it
|
||||
// currently...) If we wanted to be extra clever, we could
|
||||
// figure out when an OVERRIDE_REDIRECT window was trying to
|
||||
// partially overlap us, and then adjust the input region and
|
||||
// our clip region accordingly...
|
||||
|
||||
// @windows is sorted bottom to top.
|
||||
|
||||
for (let i = windows.length - 1; i > -1; i--) {
|
||||
let window = windows[i];
|
||||
let metaWindow = window.meta_window;
|
||||
let layer = metaWindow.get_layer();
|
||||
|
||||
// Skip minimized windows
|
||||
if (!metaWindow.showing_on_its_workspace())
|
||||
continue;
|
||||
|
||||
if (layer == Meta.StackLayer.FULLSCREEN ||
|
||||
(layer == Meta.StackLayer.OVERRIDE_REDIRECT && metaWindow.is_monitor_sized())) {
|
||||
if (metaWindow.is_screen_sized()) {
|
||||
for (let i = 0; i < this.monitors.length; i++)
|
||||
this.monitors[i].inFullscreen = true;
|
||||
} else {
|
||||
let monitors = metaWindow.get_all_monitors();
|
||||
for (let i = 0; i < monitors.length; i++) {
|
||||
let index = monitors[i];
|
||||
this.monitors[index].inFullscreen = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
this._updateVisibility();
|
||||
this._queueUpdateRegions();
|
||||
},
|
||||
|
||||
_windowsRestacked: function() {
|
||||
let wasInFullscreen = [];
|
||||
for (let i = 0; i < this.monitors.length; i++)
|
||||
wasInFullscreen[i] = this.monitors[i].inFullscreen;
|
||||
|
||||
let primaryWasInFullscreen = this.primaryMonitor.inFullscreen;
|
||||
|
||||
this._updateFullscreen();
|
||||
|
||||
let changed = false;
|
||||
for (let i = 0; i < wasInFullscreen.length; i++) {
|
||||
if (wasInFullscreen[i] != this.monitors[i].inFullscreen) {
|
||||
changed = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!changed && (this._isPopupWindowVisible != global.top_window_group.get_children().some(isPopupMetaWindow)))
|
||||
if (this._isPopupWindowVisible != global.top_window_group.get_children().some(isPopupMetaWindow))
|
||||
changed = true;
|
||||
|
||||
if (changed) {
|
||||
this._updateVisibility();
|
||||
this._queueUpdateRegions();
|
||||
}
|
||||
|
||||
if (primaryWasInFullscreen != this.primaryMonitor.inFullscreen) {
|
||||
let windows = this._getWindowActorsForWorkspace(global.screen.get_active_workspace());
|
||||
for (let i = 0; i < windows.length; i++) {
|
||||
let window = windows[i];
|
||||
let metaWindow = window.meta_window;
|
||||
|
||||
// Skip minimized windows
|
||||
if (!metaWindow.showing_on_its_workspace())
|
||||
continue;
|
||||
|
||||
// Skip windows that aren't on the primary monitor
|
||||
if (!metaWindow.is_on_primary_monitor())
|
||||
continue;
|
||||
|
||||
// Minimize monitor sized windows that are not focused
|
||||
if (metaWindow.is_monitor_sized() &&
|
||||
!metaWindow.appears_focused)
|
||||
metaWindow.minimize();
|
||||
}
|
||||
this.emit('primary-fullscreen-changed', this.primaryMonitor.inFullscreen);
|
||||
}
|
||||
},
|
||||
|
||||
_updateRegions: function() {
|
||||
@@ -1089,54 +1063,25 @@ Signals.addSignalMethods(LayoutManager.prototype);
|
||||
const HotCorner = new Lang.Class({
|
||||
Name: 'HotCorner',
|
||||
|
||||
_init : function(layoutManager) {
|
||||
_init : function(layoutManager, monitor, x, y) {
|
||||
// We use this flag to mark the case where the user has entered the
|
||||
// hot corner and has not left both the hot corner and a surrounding
|
||||
// guard area (the "environs"). This avoids triggering the hot corner
|
||||
// multiple times due to an accidental jitter.
|
||||
this._entered = false;
|
||||
|
||||
this.actor = new Clutter.Actor({ name: 'hot-corner-environs',
|
||||
width: 3,
|
||||
height: 3,
|
||||
reactive: true });
|
||||
this._monitor = monitor;
|
||||
|
||||
this._corner = new Clutter.Rectangle({ name: 'hot-corner',
|
||||
width: 1,
|
||||
height: 1,
|
||||
opacity: 0,
|
||||
reactive: true });
|
||||
this._corner._delegate = this;
|
||||
this._x = x;
|
||||
this._y = y;
|
||||
|
||||
this.actor.add_child(this._corner);
|
||||
this._setupFallbackCornerIfNeeded(layoutManager);
|
||||
|
||||
if (Clutter.get_default_text_direction() == Clutter.TextDirection.RTL) {
|
||||
this._corner.set_position(this.actor.width - this._corner.width, 0);
|
||||
this.actor.set_anchor_point_from_gravity(Clutter.Gravity.NORTH_EAST);
|
||||
} else {
|
||||
this._corner.set_position(0, 0);
|
||||
}
|
||||
|
||||
this._activationTime = 0;
|
||||
|
||||
this.actor.connect('leave-event',
|
||||
Lang.bind(this, this._onEnvironsLeft));
|
||||
|
||||
// Clicking on the hot corner environs should result in the
|
||||
// same behavior as clicking on the hot corner.
|
||||
this.actor.connect('button-release-event',
|
||||
Lang.bind(this, this._onCornerClicked));
|
||||
|
||||
// In addition to being triggered by the mouse enter event,
|
||||
// the hot corner can be triggered by clicking on it. This is
|
||||
// useful if the user wants to undo the effect of triggering
|
||||
// the hot corner once in the hot corner.
|
||||
this._corner.connect('enter-event',
|
||||
Lang.bind(this, this._onCornerEntered));
|
||||
this._corner.connect('button-release-event',
|
||||
Lang.bind(this, this._onCornerClicked));
|
||||
this._corner.connect('leave-event',
|
||||
Lang.bind(this, this._onCornerLeft));
|
||||
this._pressureBarrier = new PressureBarrier(HOT_CORNER_PRESSURE_THRESHOLD,
|
||||
HOT_CORNER_PRESSURE_TIMEOUT,
|
||||
Shell.KeyBindingMode.NORMAL |
|
||||
Shell.KeyBindingMode.OVERVIEW);
|
||||
this._pressureBarrier.connect('trigger', Lang.bind(this, this._toggleOverview));
|
||||
|
||||
// Cache the three ripples instead of dynamically creating and destroying them.
|
||||
this._ripple1 = new St.BoxLayout({ style_class: 'ripple-box', opacity: 0, visible: false });
|
||||
@@ -1148,8 +1093,83 @@ const HotCorner = new Lang.Class({
|
||||
layoutManager.uiGroup.add_actor(this._ripple3);
|
||||
},
|
||||
|
||||
setBarrierSize: function(size) {
|
||||
if (this._verticalBarrier) {
|
||||
this._pressureBarrier.removeBarrier(this._verticalBarrier);
|
||||
this._verticalBarrier.destroy();
|
||||
this._verticalBarrier = null;
|
||||
}
|
||||
|
||||
if (this._horizontalBarrier) {
|
||||
this._pressureBarrier.removeBarrier(this._horizontalBarrier);
|
||||
this._horizontalBarrier.destroy();
|
||||
this._horizontalBarrier = null;
|
||||
}
|
||||
|
||||
if (size > 0) {
|
||||
if (Clutter.get_default_text_direction() == Clutter.TextDirection.RTL) {
|
||||
this._verticalBarrier = new Meta.Barrier({ display: global.display,
|
||||
x1: this._x, x2: this._x, y1: this._y, y2: this._y + size,
|
||||
directions: Meta.BarrierDirection.NEGATIVE_X });
|
||||
this._horizontalBarrier = new Meta.Barrier({ display: global.display,
|
||||
x1: this._x - size, x2: this._x, y1: this._y, y2: this._y,
|
||||
directions: Meta.BarrierDirection.POSITIVE_Y });
|
||||
} else {
|
||||
this._verticalBarrier = new Meta.Barrier({ display: global.display,
|
||||
x1: this._x, x2: this._x, y1: this._y, y2: this._y + size,
|
||||
directions: Meta.BarrierDirection.POSITIVE_X });
|
||||
this._horizontalBarrier = new Meta.Barrier({ display: global.display,
|
||||
x1: this._x, x2: this._x + size, y1: this._y, y2: this._y,
|
||||
directions: Meta.BarrierDirection.POSITIVE_Y });
|
||||
}
|
||||
|
||||
this._pressureBarrier.addBarrier(this._verticalBarrier);
|
||||
this._pressureBarrier.addBarrier(this._horizontalBarrier);
|
||||
}
|
||||
},
|
||||
|
||||
_setupFallbackCornerIfNeeded: function(layoutManager) {
|
||||
if (!global.display.supports_extended_barriers()) {
|
||||
this.actor = new Clutter.Actor({ name: 'hot-corner-environs',
|
||||
x: this._x, y: this._y,
|
||||
width: 3,
|
||||
height: 3,
|
||||
reactive: true });
|
||||
|
||||
this._corner = new Clutter.Rectangle({ name: 'hot-corner',
|
||||
width: 1,
|
||||
height: 1,
|
||||
opacity: 0,
|
||||
reactive: true });
|
||||
this._corner._delegate = this;
|
||||
|
||||
this.actor.add_child(this._corner);
|
||||
layoutManager.addChrome(this.actor);
|
||||
|
||||
if (Clutter.get_default_text_direction() == Clutter.TextDirection.RTL) {
|
||||
this._corner.set_position(this.actor.width - this._corner.width, 0);
|
||||
this.actor.set_anchor_point_from_gravity(Clutter.Gravity.NORTH_EAST);
|
||||
} else {
|
||||
this._corner.set_position(0, 0);
|
||||
}
|
||||
|
||||
this.actor.connect('leave-event',
|
||||
Lang.bind(this, this._onEnvironsLeft));
|
||||
|
||||
this._corner.connect('enter-event',
|
||||
Lang.bind(this, this._onCornerEntered));
|
||||
this._corner.connect('leave-event',
|
||||
Lang.bind(this, this._onCornerLeft));
|
||||
}
|
||||
},
|
||||
|
||||
destroy: function() {
|
||||
this.actor.destroy();
|
||||
this.setBarrierSize(0);
|
||||
this._pressureBarrier.destroy();
|
||||
this._pressureBarrier = null;
|
||||
|
||||
if (this.actor)
|
||||
this.actor.destroy();
|
||||
},
|
||||
|
||||
_animRipple : function(ripple, delay, time, startScale, startOpacity, finalScale) {
|
||||
@@ -1169,9 +1189,8 @@ const HotCorner = new Lang.Class({
|
||||
ripple.opacity = 255 * Math.sqrt(startOpacity);
|
||||
ripple.scale_x = ripple.scale_y = startScale;
|
||||
|
||||
let [x, y] = this._corner.get_transformed_position();
|
||||
ripple.x = x;
|
||||
ripple.y = y;
|
||||
ripple.x = this._x;
|
||||
ripple.y = this._y;
|
||||
|
||||
Tweener.addTween(ripple, { _opacity: 0,
|
||||
scale_x: finalScale,
|
||||
@@ -1183,7 +1202,7 @@ const HotCorner = new Lang.Class({
|
||||
onComplete: function() { ripple.visible = false; } });
|
||||
},
|
||||
|
||||
rippleAnimation: function() {
|
||||
_rippleAnimation: function() {
|
||||
// Show three concentric ripples expanding outwards; the exact
|
||||
// parameters were found by trial and error, so don't look
|
||||
// for them to make perfect sense mathematically
|
||||
@@ -1194,14 +1213,21 @@ const HotCorner = new Lang.Class({
|
||||
this._animRipple(this._ripple3, 0.35, 1.0, 0.0, 0.3, 1);
|
||||
},
|
||||
|
||||
_toggleOverview: function() {
|
||||
if (this._monitor.inFullscreen)
|
||||
return;
|
||||
|
||||
if (Main.overview.shouldToggleByCornerOrButton()) {
|
||||
this._rippleAnimation();
|
||||
Main.overview.toggle();
|
||||
}
|
||||
},
|
||||
|
||||
handleDragOver: function(source, actor, x, y, time) {
|
||||
if (source != Main.xdndHandler)
|
||||
return DND.DragMotionResult.CONTINUE;
|
||||
|
||||
if (!Main.overview.visible && !Main.overview.animationInProgress) {
|
||||
this.rippleAnimation();
|
||||
Main.overview.showTemporarily();
|
||||
}
|
||||
this._toggleOverview();
|
||||
|
||||
return DND.DragMotionResult.CONTINUE;
|
||||
},
|
||||
@@ -1209,22 +1235,11 @@ const HotCorner = new Lang.Class({
|
||||
_onCornerEntered : function() {
|
||||
if (!this._entered) {
|
||||
this._entered = true;
|
||||
if (!Main.overview.animationInProgress) {
|
||||
this._activationTime = Date.now() / 1000;
|
||||
|
||||
this.rippleAnimation();
|
||||
Main.overview.toggle();
|
||||
}
|
||||
this._toggleOverview();
|
||||
}
|
||||
return false;
|
||||
},
|
||||
|
||||
_onCornerClicked : function() {
|
||||
if (this.shouldToggleOverviewOnClick())
|
||||
Main.overview.toggle();
|
||||
return true;
|
||||
},
|
||||
|
||||
_onCornerLeft : function(actor, event) {
|
||||
if (event.get_related() != this.actor)
|
||||
this._entered = false;
|
||||
@@ -1236,42 +1251,47 @@ const HotCorner = new Lang.Class({
|
||||
if (event.get_related() != this._corner)
|
||||
this._entered = false;
|
||||
return false;
|
||||
},
|
||||
|
||||
// Checks if the Activities button is currently sensitive to
|
||||
// clicks. The first call to this function within the
|
||||
// HOT_CORNER_ACTIVATION_TIMEOUT time of the hot corner being
|
||||
// triggered will return false. This avoids opening and closing
|
||||
// the overview if the user both triggered the hot corner and
|
||||
// clicked the Activities button.
|
||||
shouldToggleOverviewOnClick: function() {
|
||||
if (Main.overview.animationInProgress)
|
||||
return false;
|
||||
if (this._activationTime == 0 || Date.now() / 1000 - this._activationTime > HOT_CORNER_ACTIVATION_TIMEOUT)
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
});
|
||||
|
||||
const PressureBarrier = new Lang.Class({
|
||||
Name: 'PressureBarrier',
|
||||
|
||||
_init: function(barrier, threshold, timeout) {
|
||||
this._barrier = barrier;
|
||||
_init: function(threshold, timeout, keybindingMode) {
|
||||
this._threshold = threshold;
|
||||
this._timeout = timeout;
|
||||
this._orientation = (barrier.y1 == barrier.y2) ? Clutter.Orientation.HORIZONTAL : Clutter.Orientation.VERTICAL;
|
||||
this._keybindingMode = keybindingMode;
|
||||
this._barriers = [];
|
||||
this._eventFilter = null;
|
||||
|
||||
this._isTriggered = false;
|
||||
this._reset();
|
||||
},
|
||||
|
||||
this._barrierHitId = this._barrier.connect('hit', Lang.bind(this, this._onBarrierHit));
|
||||
this._barrierLeftId = this._barrier.connect('left', Lang.bind(this, this._onBarrierLeft));
|
||||
addBarrier: function(barrier) {
|
||||
barrier._pressureHitId = barrier.connect('hit', Lang.bind(this, this._onBarrierHit));
|
||||
barrier._pressureLeftId = barrier.connect('left', Lang.bind(this, this._onBarrierLeft));
|
||||
|
||||
this._barriers.push(barrier);
|
||||
},
|
||||
|
||||
_disconnectBarrier: function(barrier) {
|
||||
barrier.disconnect(barrier._pressureHitId);
|
||||
barrier.disconnect(barrier._pressureLeftId);
|
||||
},
|
||||
|
||||
removeBarrier: function(barrier) {
|
||||
this._disconnectBarrier(barrier);
|
||||
this._barriers.splice(this._barriers.indexOf(barrier), 1);
|
||||
},
|
||||
|
||||
destroy: function() {
|
||||
this._barrier.disconnect(this._barrierHitId);
|
||||
this._barrier.disconnect(this._barrierLeftId);
|
||||
this._barrier = null;
|
||||
this._barriers.forEach(Lang.bind(this, this._disconnectBarrier));
|
||||
this._barriers = [];
|
||||
},
|
||||
|
||||
setEventFilter: function(filter) {
|
||||
this._eventFilter = filter;
|
||||
},
|
||||
|
||||
_reset: function() {
|
||||
@@ -1280,33 +1300,34 @@ const PressureBarrier = new Lang.Class({
|
||||
this._lastTime = 0;
|
||||
},
|
||||
|
||||
_getDistanceAcrossBarrier: function(event) {
|
||||
if (this._orientation == Clutter.Orientation.HORIZONTAL)
|
||||
_isHorizontal: function(barrier) {
|
||||
return barrier.y1 == barrier.y2;
|
||||
},
|
||||
|
||||
_getDistanceAcrossBarrier: function(barrier, event) {
|
||||
if (this._isHorizontal(barrier))
|
||||
return Math.abs(event.dy);
|
||||
else
|
||||
return Math.abs(event.dx);
|
||||
},
|
||||
|
||||
_getDistanceAlongBarrier: function(event) {
|
||||
if (this._orientation == Clutter.Orientation.HORIZONTAL)
|
||||
_getDistanceAlongBarrier: function(barrier, event) {
|
||||
if (this._isHorizontal(barrier))
|
||||
return Math.abs(event.dx);
|
||||
else
|
||||
return Math.abs(event.dy);
|
||||
},
|
||||
|
||||
_isBarrierEventTooOld: function(event) {
|
||||
// Ignore all events older than this time
|
||||
let threshold = this._lastTime - this._timeout;
|
||||
return event.time < threshold;
|
||||
},
|
||||
|
||||
_trimBarrierEvents: function() {
|
||||
// Events are guaranteed to be sorted in time order from
|
||||
// oldest to newest, so just look for the first old event,
|
||||
// and then chop events after that off.
|
||||
let i = 0;
|
||||
let threshold = this._lastTime - this._timeout;
|
||||
|
||||
while (i < this._barrierEvents.length) {
|
||||
if (!this._isBarrierEventTooOld(this._barrierEvents[i]))
|
||||
let [time, distance] = this._barrierEvents[i];
|
||||
if (time >= threshold)
|
||||
break;
|
||||
i++;
|
||||
}
|
||||
@@ -1314,7 +1335,8 @@ const PressureBarrier = new Lang.Class({
|
||||
let firstNewEvent = i;
|
||||
|
||||
for (i = 0; i < firstNewEvent; i++) {
|
||||
this._currentPressure -= this._getDistanceAcrossBarrier(this._barrierEvents[i]);
|
||||
let [time, distance] = this._barrierEvents[i];
|
||||
this._currentPressure -= distance;
|
||||
}
|
||||
|
||||
this._barrierEvents = this._barrierEvents.slice(firstNewEvent);
|
||||
@@ -1322,29 +1344,30 @@ const PressureBarrier = new Lang.Class({
|
||||
|
||||
_onBarrierLeft: function(barrier, event) {
|
||||
this._reset();
|
||||
this._isTriggered = false;
|
||||
},
|
||||
|
||||
_trigger: function() {
|
||||
this._isTriggered = true;
|
||||
this.emit('trigger');
|
||||
this._reset();
|
||||
},
|
||||
|
||||
_onBarrierHit: function(barrier, event) {
|
||||
// Throw out all events where the pointer was grabbed by another
|
||||
// client, as the client that grabbed the pointer expects to have
|
||||
// complete control over it
|
||||
if (event.grabbed && Main.modalCount == 0)
|
||||
// If we've triggered the barrier, wait until the pointer has the
|
||||
// left the barrier hitbox until we trigger it again.
|
||||
if (this._isTriggered)
|
||||
return;
|
||||
|
||||
let isOverview = ((Main.keybindingMode & (Shell.KeyBindingMode.OVERVIEW)) != 0);
|
||||
|
||||
// Throw out events where the grab is taken by something that's
|
||||
// not the overview (modal dialogs, etc.)
|
||||
if (event.grabbed && !isOverview)
|
||||
if (this._eventFilter && this._eventFilter(event))
|
||||
return;
|
||||
|
||||
let slide = this._getDistanceAlongBarrier(event);
|
||||
let distance = this._getDistanceAcrossBarrier(event);
|
||||
// Throw out all events not in the proper keybinding mode
|
||||
if (!(this._keybindingMode & Main.keybindingMode))
|
||||
return;
|
||||
|
||||
let slide = this._getDistanceAlongBarrier(barrier, event);
|
||||
let distance = this._getDistanceAcrossBarrier(barrier, event);
|
||||
|
||||
if (distance >= this._threshold) {
|
||||
this._trigger();
|
||||
@@ -1360,8 +1383,10 @@ const PressureBarrier = new Lang.Class({
|
||||
this._lastTime = event.time;
|
||||
|
||||
this._trimBarrierEvents();
|
||||
this._barrierEvents.push(event);
|
||||
this._currentPressure += Math.min(15, distance);
|
||||
distance = Math.min(15, distance);
|
||||
|
||||
this._barrierEvents.push([event.time, distance]);
|
||||
this._currentPressure += distance;
|
||||
|
||||
if (this._currentPressure >= this._threshold)
|
||||
this._trigger();
|
||||
|
||||
@@ -24,6 +24,7 @@ const Panel = imports.ui.panel;
|
||||
const Params = imports.misc.params;
|
||||
const RunDialog = imports.ui.runDialog;
|
||||
const Layout = imports.ui.layout;
|
||||
const LoginManager = imports.misc.loginManager;
|
||||
const LookingGlass = imports.ui.lookingGlass;
|
||||
const NotificationDaemon = imports.ui.notificationDaemon;
|
||||
const WindowAttentionHandler = imports.ui.windowAttentionHandler;
|
||||
@@ -32,7 +33,6 @@ const Scripting = imports.ui.scripting;
|
||||
const SessionMode = imports.ui.sessionMode;
|
||||
const ShellDBus = imports.ui.shellDBus;
|
||||
const ShellMountOperation = imports.ui.shellMountOperation;
|
||||
const UnlockDialog = imports.ui.unlockDialog;
|
||||
const WindowManager = imports.ui.windowManager;
|
||||
const Magnifier = imports.ui.magnifier;
|
||||
const XdndHandler = imports.ui.xdndHandler;
|
||||
@@ -41,6 +41,9 @@ const Util = imports.misc.util;
|
||||
const OVERRIDES_SCHEMA = 'org.gnome.shell.overrides';
|
||||
const DEFAULT_BACKGROUND_COLOR = Clutter.Color.from_pixel(0x2e3436ff);
|
||||
|
||||
const A11Y_SCHEMA = 'org.gnome.desktop.a11y.keyboard';
|
||||
const STICKY_KEYS_ENABLE = 'stickykeys-enable';
|
||||
|
||||
let componentManager = null;
|
||||
let panel = null;
|
||||
let overview = null;
|
||||
@@ -58,7 +61,7 @@ let shellDBusService = null;
|
||||
let shellMountOpDBusService = null;
|
||||
let screenSaverDBus = null;
|
||||
let modalCount = 0;
|
||||
let keybindingMode = Shell.KeyBindingMode.NORMAL;
|
||||
let keybindingMode = Shell.KeyBindingMode.NONE;
|
||||
let modalActorFocusStack = [];
|
||||
let uiGroup = null;
|
||||
let magnifier = null;
|
||||
@@ -69,8 +72,11 @@ let _startDate;
|
||||
let _defaultCssStylesheet = null;
|
||||
let _cssStylesheet = null;
|
||||
let _overridesSettings = null;
|
||||
let _a11ySettings = null;
|
||||
|
||||
function _sessionUpdated() {
|
||||
_loadDefaultStylesheet();
|
||||
|
||||
wm.setCustomKeybindingHandler('panel-main-menu',
|
||||
Shell.KeyBindingMode.NORMAL |
|
||||
Shell.KeyBindingMode.OVERVIEW,
|
||||
@@ -82,8 +88,9 @@ function _sessionUpdated() {
|
||||
Shell.KeyBindingMode.NORMAL |
|
||||
Shell.KeyBindingMode.OVERVIEW,
|
||||
sessionMode.hasRunDialog ? openRunDialog : null);
|
||||
if (sessionMode.isGreeter)
|
||||
screenShield.showDialog();
|
||||
|
||||
if (!sessionMode.hasRunDialog && lookingGlass)
|
||||
lookingGlass.close();
|
||||
}
|
||||
|
||||
function start() {
|
||||
@@ -91,29 +98,27 @@ function start() {
|
||||
global.logError = window.log;
|
||||
global.log = window.log;
|
||||
|
||||
// Hide the stage until we're ready for it
|
||||
global.stage.hide();
|
||||
|
||||
// Chain up async errors reported from C
|
||||
global.connect('notify-error', function (global, msg, detail) { notifyError(msg, detail); });
|
||||
|
||||
Gio.DesktopAppInfo.set_desktop_env('GNOME');
|
||||
|
||||
sessionMode = new SessionMode.SessionMode();
|
||||
|
||||
// start session after we know what mode we're running in
|
||||
let signalId = sessionMode.connect('updated', function() {
|
||||
sessionMode.disconnect(signalId);
|
||||
startSession();
|
||||
});
|
||||
sessionMode.connect('sessions-loaded', _sessionsLoaded);
|
||||
sessionMode.init();
|
||||
}
|
||||
|
||||
function startSession() {
|
||||
sessionMode.connect('updated', _loadDefaultStylesheet);
|
||||
function _sessionsLoaded() {
|
||||
sessionMode.connect('updated', _sessionUpdated);
|
||||
_initializeUI();
|
||||
|
||||
shellDBusService = new ShellDBus.GnomeShell();
|
||||
shellMountOpDBusService = new ShellMountOperation.GnomeShellMountOpHandler();
|
||||
|
||||
_sessionUpdated();
|
||||
}
|
||||
|
||||
function _initializeUI() {
|
||||
// Ensure ShellWindowTracker and ShellAppUsage are initialized; this will
|
||||
// also initialize ShellAppSystem first. ShellAppSystem
|
||||
// needs to load all the .desktop files, and ShellWindowTracker
|
||||
@@ -143,13 +148,9 @@ function startSession() {
|
||||
overview = new Overview.Overview();
|
||||
wm = new WindowManager.WindowManager();
|
||||
magnifier = new Magnifier.Magnifier();
|
||||
if (UnlockDialog.isSupported())
|
||||
if (LoginManager.canLock())
|
||||
screenShield = new ScreenShield.ScreenShield();
|
||||
else
|
||||
screenShield = new ScreenShield.ScreenShieldFallback();
|
||||
|
||||
// The message tray relies on being constructed
|
||||
// after the panel.
|
||||
panel = new Panel.Panel();
|
||||
messageTray = new MessageTray.MessageTray();
|
||||
keyboard = new Keyboard.Keyboard();
|
||||
@@ -158,14 +159,16 @@ function startSession() {
|
||||
componentManager = new Components.ComponentManager();
|
||||
|
||||
layoutManager.init();
|
||||
layoutManager.prepareStartupAnimation();
|
||||
overview.init();
|
||||
|
||||
_a11ySettings = new Gio.Settings({ schema: A11Y_SCHEMA });
|
||||
|
||||
global.screen.override_workspace_layout(Meta.ScreenCorner.TOPLEFT,
|
||||
false, -1, 1);
|
||||
global.display.connect('overlay-key', Lang.bind(overview, overview.toggle));
|
||||
sessionMode.connect('updated', _sessionUpdated);
|
||||
_sessionUpdated();
|
||||
global.display.connect('overlay-key', Lang.bind(overview, function () {
|
||||
if (!_a11ySettings.get_boolean (STICKY_KEYS_ENABLE))
|
||||
overview.toggle();
|
||||
}));
|
||||
|
||||
// Provide the bus object for gnome-session to
|
||||
// initiate logouts.
|
||||
@@ -199,8 +202,16 @@ function startSession() {
|
||||
ExtensionDownloader.init();
|
||||
ExtensionSystem.init();
|
||||
|
||||
layoutManager.connect('startup-prepared', function() {
|
||||
layoutManager.startupAnimation();
|
||||
if (sessionMode.isGreeter && screenShield) {
|
||||
layoutManager.connect('startup-prepared', function() {
|
||||
screenShield.showDialog();
|
||||
});
|
||||
}
|
||||
|
||||
layoutManager.connect('startup-complete', function() {
|
||||
if (keybindingMode == Shell.KeyBindingMode.NONE) {
|
||||
keybindingMode = Shell.KeyBindingMode.NORMAL;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
@@ -1557,23 +1557,22 @@ const MessageTray = new Lang.Class({
|
||||
|
||||
this.actor = new St.Widget({ name: 'message-tray',
|
||||
reactive: true,
|
||||
track_hover: true,
|
||||
layout_manager: new Clutter.BinLayout(),
|
||||
x_expand: true,
|
||||
y_expand: true,
|
||||
y_align: Clutter.ActorAlign.START,
|
||||
});
|
||||
this.actor.connect('notify::hover', Lang.bind(this, this._onTrayHoverChanged));
|
||||
|
||||
this._notificationWidget = new St.Widget({ name: 'notification-container',
|
||||
reactive: true,
|
||||
track_hover: true,
|
||||
y_align: Clutter.ActorAlign.START,
|
||||
x_align: Clutter.ActorAlign.CENTER,
|
||||
y_expand: true,
|
||||
x_expand: true,
|
||||
layout_manager: new Clutter.BinLayout() });
|
||||
this._notificationWidget.connect('key-release-event', Lang.bind(this, this._onNotificationKeyRelease));
|
||||
|
||||
this.actor.add_actor(this._notificationWidget);
|
||||
this._notificationWidget.connect('notify::hover', Lang.bind(this, this._onNotificationHoverChanged));
|
||||
|
||||
this._notificationBin = new St.Bin({ y_expand: true });
|
||||
this._notificationBin.set_y_align(Clutter.ActorAlign.START);
|
||||
@@ -1591,17 +1590,13 @@ const MessageTray = new Lang.Class({
|
||||
global.focus_manager.add_group(this.actor);
|
||||
this._summary = new St.BoxLayout({ style_class: 'message-tray-summary',
|
||||
reactive: true,
|
||||
track_hover: true,
|
||||
x_align: Clutter.ActorAlign.END,
|
||||
x_expand: true,
|
||||
y_align: Clutter.ActorAlign.CENTER,
|
||||
y_expand: true });
|
||||
this._summary.connect('notify::hover', Lang.bind(this, this._onSummaryHoverChanged));
|
||||
this.actor.add_actor(this._summary);
|
||||
this._summary.opacity = 0;
|
||||
|
||||
this._summaryMotionId = 0;
|
||||
this._trayMotionId = 0;
|
||||
|
||||
this._summaryBoxPointer = new BoxPointer.BoxPointer(St.Side.BOTTOM,
|
||||
{ reactive: true,
|
||||
@@ -1632,19 +1627,27 @@ const MessageTray = new Lang.Class({
|
||||
{ keybindingMode: Shell.KeyBindingMode.MESSAGE_TRAY });
|
||||
this._grabHelper.addActor(this._summaryBoxPointer.actor);
|
||||
this._grabHelper.addActor(this.actor);
|
||||
this._grabHelper.addActor(this._notificationWidget);
|
||||
|
||||
Main.layoutManager.connect('keyboard-visible-changed', Lang.bind(this, this._onKeyboardVisibleChanged));
|
||||
|
||||
this._trayState = State.HIDDEN;
|
||||
this._locked = false;
|
||||
this._traySummoned = false;
|
||||
this._useLongerTrayLeftTimeout = false;
|
||||
this._useLongerNotificationLeftTimeout = false;
|
||||
this._trayLeftTimeoutId = 0;
|
||||
this._pointerInTray = false;
|
||||
this._pointerInKeyboard = false;
|
||||
|
||||
// pointerInNotification is sort of a misnomer -- it tracks whether
|
||||
// a message tray notification should expand. The value is
|
||||
// partially driven by the hover state of the notification, but has
|
||||
// a lot of complex state related to timeouts and the current
|
||||
// state of the pointer when a notification pops up.
|
||||
this._pointerInNotification = false;
|
||||
|
||||
// This tracks this._notificationWidget.hover and is used to fizzle
|
||||
// out non-changing hover notifications in onNotificationHoverChanged.
|
||||
this._notificationHovered = false;
|
||||
|
||||
this._keyboardVisible = false;
|
||||
this._summaryState = State.HIDDEN;
|
||||
this._pointerInSummary = false;
|
||||
this._notificationClosed = false;
|
||||
this._notificationState = State.HIDDEN;
|
||||
this._notificationTimeoutId = 0;
|
||||
@@ -1654,7 +1657,6 @@ const MessageTray = new Lang.Class({
|
||||
this._desktopCloneState = State.HIDDEN;
|
||||
this._notificationRemoved = false;
|
||||
this._reNotifyAfterHideNotification = null;
|
||||
this._inFullscreen = false;
|
||||
this._desktopClone = null;
|
||||
this._inCtrlAltTab = false;
|
||||
|
||||
@@ -1666,20 +1668,19 @@ const MessageTray = new Lang.Class({
|
||||
});
|
||||
|
||||
Main.layoutManager.trayBox.add_actor(this.actor);
|
||||
this.actor.y = 0;
|
||||
Main.layoutManager.trayBox.add_actor(this._notificationWidget);
|
||||
Main.layoutManager.trackChrome(this.actor);
|
||||
Main.layoutManager.trackChrome(this._notificationWidget);
|
||||
Main.layoutManager.trackChrome(this._closeButton);
|
||||
|
||||
Main.layoutManager.connect('primary-fullscreen-changed', Lang.bind(this, this._onFullscreenChanged));
|
||||
global.screen.connect('in-fullscreen-changed', Lang.bind(this, this._updateState));
|
||||
Main.layoutManager.connect('hot-corners-changed', Lang.bind(this, this._hotCornersChanged));
|
||||
|
||||
// If the overview shows or hides while we're in
|
||||
// the message tray, revert back to normal mode.
|
||||
Main.overview.connect('showing', Lang.bind(this, this._escapeTray));
|
||||
Main.overview.connect('hiding', Lang.bind(this, this._escapeTray));
|
||||
|
||||
// Track if we've added the activities button
|
||||
this._activitiesButtonAdded = false;
|
||||
Main.sessionMode.connect('updated', Lang.bind(this, this._sessionUpdated));
|
||||
|
||||
Main.wm.addKeybinding('toggle-message-tray',
|
||||
@@ -1703,6 +1704,7 @@ const MessageTray = new Lang.Class({
|
||||
this._trayDwellTimeoutId = 0;
|
||||
this._setupTrayDwellIfNeeded();
|
||||
this._sessionUpdated();
|
||||
this._hotCornersChanged();
|
||||
|
||||
this._noMessages = new St.Label({ text: _("No Messages"),
|
||||
style_class: 'no-messages-label',
|
||||
@@ -1743,13 +1745,11 @@ const MessageTray = new Lang.Class({
|
||||
|
||||
_openContextMenu: function () {
|
||||
let [x, y, mask] = global.get_pointer();
|
||||
this._lock();
|
||||
this._contextMenu.setPosition(Math.round(x), Math.round(y));
|
||||
this._grabHelper.grab({ actor: this._contextMenu.actor,
|
||||
grabFocus: true,
|
||||
modal: true,
|
||||
onUngrab: Lang.bind(this, function () {
|
||||
this._contextMenu.close(BoxPointer.PopupAnimation.FULL);
|
||||
this._unlock();
|
||||
})
|
||||
});
|
||||
this._contextMenu.open(BoxPointer.PopupAnimation.FULL);
|
||||
@@ -1775,11 +1775,6 @@ const MessageTray = new Lang.Class({
|
||||
},
|
||||
|
||||
_sessionUpdated: function() {
|
||||
if (!this._activitiesButtonAdded && Main.panel.statusArea.activities) {
|
||||
this._activitiesButtonAdded = true;
|
||||
this._grabHelper.addActor(Main.panel.statusArea.activities.hotCorner.actor);
|
||||
}
|
||||
|
||||
if ((Main.sessionMode.isLocked || Main.sessionMode.isGreeter) && this._inCtrlAltTab) {
|
||||
Main.ctrlAltTabManager.removeGroup(this._summary);
|
||||
this._inCtrlAltTab = false;
|
||||
@@ -1798,12 +1793,12 @@ const MessageTray = new Lang.Class({
|
||||
y == monitor.y + monitor.height - 1);
|
||||
if (shouldDwell) {
|
||||
// We only set up dwell timeout when the user is not hovering over the tray
|
||||
// (!this.actor.hover). This avoids bringing up the message tray after the
|
||||
// (!this._notificationHovered). This avoids bringing up the message tray after the
|
||||
// user clicks on a notification with the pointer on the bottom pixel
|
||||
// of the monitor. The _trayDwelling variable is used so that we only try to
|
||||
// fire off one tray dwell - if it fails (because, say, the user has the mouse down),
|
||||
// we don't try again until the user moves the mouse up and down again.
|
||||
if (!this._trayDwelling && !this.actor.hover && this._trayDwellTimeoutId == 0) {
|
||||
if (!this._trayDwelling && !this._notificationHovered && this._trayDwellTimeoutId == 0) {
|
||||
// Save the interaction timestamp so we can detect user input
|
||||
let focusWindow = global.display.focus_window;
|
||||
this._trayDwellUserTime = focusWindow ? focusWindow.user_time : 0;
|
||||
@@ -1828,6 +1823,9 @@ const MessageTray = new Lang.Class({
|
||||
_trayDwellTimeout: function() {
|
||||
this._trayDwellTimeoutId = 0;
|
||||
|
||||
if (Main.layoutManager.bottomMonitor.inFullscreen)
|
||||
return false;
|
||||
|
||||
// We don't want to open the tray when a modal dialog
|
||||
// is up, so we check the modal count for that. When we are in the
|
||||
// overview we have to take the overview's modal push into account
|
||||
@@ -1999,18 +1997,6 @@ const MessageTray = new Lang.Class({
|
||||
this._notificationQueue.splice(index, 1);
|
||||
},
|
||||
|
||||
_lock: function() {
|
||||
this._locked = true;
|
||||
},
|
||||
|
||||
_unlock: function() {
|
||||
if (!this._locked)
|
||||
return;
|
||||
this._locked = false;
|
||||
this._pointerInTray = this.actor.hover;
|
||||
this._updateState();
|
||||
},
|
||||
|
||||
openTray: function() {
|
||||
if (Main.overview.animationInProgress)
|
||||
return;
|
||||
@@ -2035,8 +2021,6 @@ const MessageTray = new Lang.Class({
|
||||
|
||||
hide: function() {
|
||||
this._traySummoned = false;
|
||||
this.actor.set_hover(false);
|
||||
this._summary.set_hover(false);
|
||||
this._updateState();
|
||||
},
|
||||
|
||||
@@ -2096,33 +2080,28 @@ const MessageTray = new Lang.Class({
|
||||
this._updateState();
|
||||
},
|
||||
|
||||
_onSummaryHoverChanged: function() {
|
||||
this._pointerInSummary = this._summary.hover;
|
||||
this._updateState();
|
||||
_hotCornersChanged: function() {
|
||||
let primary = Main.layoutManager.primaryIndex;
|
||||
let corner = Main.layoutManager.hotCorners[primary];
|
||||
if (corner && corner.actor)
|
||||
this._grabHelper.addActor(corner.actor);
|
||||
},
|
||||
|
||||
_onTrayHoverChanged: function() {
|
||||
if (this.actor.hover) {
|
||||
_onNotificationHoverChanged: function() {
|
||||
if (this._notificationWidget.hover == this._notificationHovered)
|
||||
return;
|
||||
|
||||
this._notificationHovered = this._notificationWidget.hover;
|
||||
if (this._notificationHovered) {
|
||||
// No dwell inside notifications at the bottom of the screen
|
||||
this._cancelTrayDwell();
|
||||
|
||||
// Don't do anything if the one pixel area at the bottom is hovered over while the tray is hidden.
|
||||
if (this._trayState == State.HIDDEN && this._notificationState == State.HIDDEN)
|
||||
return;
|
||||
|
||||
// Don't do anything if this._useLongerTrayLeftTimeout is true, meaning the notification originally
|
||||
// popped up under the pointer, but this._trayLeftTimeoutId is 0, meaning the pointer didn't leave
|
||||
// the tray yet. We need to check for this case because sometimes _onTrayHoverChanged() gets called
|
||||
// multiple times while this.actor.hover is true.
|
||||
if (this._useLongerTrayLeftTimeout && !this._trayLeftTimeoutId)
|
||||
return;
|
||||
|
||||
this._useLongerTrayLeftTimeout = false;
|
||||
if (this._trayLeftTimeoutId) {
|
||||
Mainloop.source_remove(this._trayLeftTimeoutId);
|
||||
this._trayLeftTimeoutId = 0;
|
||||
this._trayLeftMouseX = -1;
|
||||
this._trayLeftMouseY = -1;
|
||||
this._useLongerNotificationLeftTimeout = false;
|
||||
if (this._notificationLeftTimeoutId) {
|
||||
Mainloop.source_remove(this._notificationLeftTimeoutId);
|
||||
this._notificationLeftTimeoutId = 0;
|
||||
this._notificationLeftMouseX = -1;
|
||||
this._notificationLeftMouseY = -1;
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -2131,32 +2110,32 @@ const MessageTray = new Lang.Class({
|
||||
global.stage.get_actor_at_pos(Clutter.PickMode.ALL, this._showNotificationMouseX, this._showNotificationMouseY);
|
||||
this._showNotificationMouseX = -1;
|
||||
this._showNotificationMouseY = -1;
|
||||
// Don't set this._pointerInTray to true if the pointer was initially in the area where the notification
|
||||
// Don't set this._pointerInNotification to true if the pointer was initially in the area where the notification
|
||||
// popped up. That way we will not be expanding notifications that happen to pop up over the pointer
|
||||
// automatically. Instead, the user is able to expand the notification by mousing away from it and then
|
||||
// mousing back in. Because this is an expected action, we set the boolean flag that indicates that a longer
|
||||
// timeout should be used before popping down the notification.
|
||||
if (this.actor.contains(actorAtShowNotificationPosition)) {
|
||||
this._useLongerTrayLeftTimeout = true;
|
||||
this._useLongerNotificationLeftTimeout = true;
|
||||
return;
|
||||
}
|
||||
}
|
||||
this._pointerInTray = true;
|
||||
this._pointerInNotification = true;
|
||||
this._updateState();
|
||||
} else {
|
||||
// We record the position of the mouse the moment it leaves the tray. These coordinates are used in
|
||||
// this._onTrayLeftTimeout() to determine if the mouse has moved far enough during the initial timeout for us
|
||||
// this._onNotificationLeftTimeout() to determine if the mouse has moved far enough during the initial timeout for us
|
||||
// to consider that the user intended to leave the tray and therefore hide the tray. If the mouse is still
|
||||
// close to its previous position, we extend the timeout once.
|
||||
let [x, y, mods] = global.get_pointer();
|
||||
this._trayLeftMouseX = x;
|
||||
this._trayLeftMouseY = y;
|
||||
this._notificationLeftMouseX = x;
|
||||
this._notificationLeftMouseY = y;
|
||||
|
||||
// We wait just a little before hiding the message tray in case the user quickly moves the mouse back into it.
|
||||
// We wait for a longer period if the notification popped up where the mouse pointer was already positioned.
|
||||
// That gives the user more time to mouse away from the notification and mouse back in in order to expand it.
|
||||
let timeout = this._useLongerTrayLeftTimeout ? LONGER_HIDE_TIMEOUT * 1000 : HIDE_TIMEOUT * 1000;
|
||||
this._trayLeftTimeoutId = Mainloop.timeout_add(timeout, Lang.bind(this, this._onTrayLeftTimeout));
|
||||
let timeout = this._useLongerNotificationLeftTimeout ? LONGER_HIDE_TIMEOUT * 1000 : HIDE_TIMEOUT * 1000;
|
||||
this._notificationLeftTimeoutId = Mainloop.timeout_add(timeout, Lang.bind(this, this._onNotificationLeftTimeout));
|
||||
}
|
||||
},
|
||||
|
||||
@@ -2165,11 +2144,6 @@ const MessageTray = new Lang.Class({
|
||||
this._updateState();
|
||||
},
|
||||
|
||||
_onFullscreenChanged: function(obj, state) {
|
||||
this._inFullscreen = state;
|
||||
this._updateState();
|
||||
},
|
||||
|
||||
_onStatusChanged: function(status) {
|
||||
if (status == GnomeSession.PresenceStatus.BUSY) {
|
||||
// remove notification and allow the summary to be closed now
|
||||
@@ -2185,23 +2159,22 @@ const MessageTray = new Lang.Class({
|
||||
this._updateState();
|
||||
},
|
||||
|
||||
_onTrayLeftTimeout: function() {
|
||||
_onNotificationLeftTimeout: function() {
|
||||
let [x, y, mods] = global.get_pointer();
|
||||
// We extend the timeout once if the mouse moved no further than MOUSE_LEFT_ACTOR_THRESHOLD to either side or up.
|
||||
// We don't check how far down the mouse moved because any point above the tray, but below the exit coordinate,
|
||||
// is close to the tray.
|
||||
if (this._trayLeftMouseX > -1 &&
|
||||
y > this._trayLeftMouseY - MOUSE_LEFT_ACTOR_THRESHOLD &&
|
||||
x < this._trayLeftMouseX + MOUSE_LEFT_ACTOR_THRESHOLD &&
|
||||
x > this._trayLeftMouseX - MOUSE_LEFT_ACTOR_THRESHOLD) {
|
||||
this._trayLeftMouseX = -1;
|
||||
this._trayLeftTimeoutId = Mainloop.timeout_add(LONGER_HIDE_TIMEOUT * 1000,
|
||||
Lang.bind(this, this._onTrayLeftTimeout));
|
||||
if (this._notificationLeftMouseX > -1 &&
|
||||
y > this._notificationLeftMouseY - MOUSE_LEFT_ACTOR_THRESHOLD &&
|
||||
x < this._notificationLeftMouseX + MOUSE_LEFT_ACTOR_THRESHOLD &&
|
||||
x > this._notificationLeftMouseX - MOUSE_LEFT_ACTOR_THRESHOLD) {
|
||||
this._notificationLeftMouseX = -1;
|
||||
this._notificationLeftTimeoutId = Mainloop.timeout_add(LONGER_HIDE_TIMEOUT * 1000,
|
||||
Lang.bind(this, this._onNotificationLeftTimeout));
|
||||
} else {
|
||||
this._trayLeftTimeoutId = 0;
|
||||
this._useLongerTrayLeftTimeout = false;
|
||||
this._pointerInTray = false;
|
||||
this._pointerInSummary = false;
|
||||
this._notificationLeftTimeoutId = 0;
|
||||
this._useLongerNotificationLeftTimeout = false;
|
||||
this._pointerInNotification = false;
|
||||
this._updateNotificationTimeout(0);
|
||||
this._updateState();
|
||||
}
|
||||
@@ -2209,9 +2182,7 @@ const MessageTray = new Lang.Class({
|
||||
},
|
||||
|
||||
_escapeTray: function() {
|
||||
this._unlock();
|
||||
this._pointerInTray = false;
|
||||
this._pointerInSummary = false;
|
||||
this._pointerInNotification = false;
|
||||
this._traySummoned = false;
|
||||
this._setClickedSummaryItem(null);
|
||||
this._updateNotificationTimeout(0);
|
||||
@@ -2220,7 +2191,7 @@ const MessageTray = new Lang.Class({
|
||||
|
||||
// All of the logic for what happens when occurs here; the various
|
||||
// event handlers merely update variables such as
|
||||
// 'this._pointerInTray', 'this._summaryState', etc, and
|
||||
// 'this._pointerInNotification', 'this._traySummoned', etc, and
|
||||
// _updateState() figures out what (if anything) needs to be done
|
||||
// at the present time.
|
||||
_updateState: function() {
|
||||
@@ -2228,25 +2199,22 @@ const MessageTray = new Lang.Class({
|
||||
let notificationQueue = this._notificationQueue;
|
||||
let notificationUrgent = notificationQueue.length > 0 && notificationQueue[0].urgency == Urgency.CRITICAL;
|
||||
let notificationForFeedback = notificationQueue.length > 0 && notificationQueue[0].forFeedback;
|
||||
let notificationsLimited = this._busy || this._inFullscreen;
|
||||
let notificationsLimited = this._busy || Main.layoutManager.bottomMonitor.inFullscreen;
|
||||
let notificationsPending = notificationQueue.length > 0 && (!notificationsLimited || notificationUrgent || notificationForFeedback) && Main.sessionMode.hasNotifications;
|
||||
let nextNotification = notificationQueue.length > 0 ? notificationQueue[0] : null;
|
||||
let notificationPinned = this._pointerInTray && !this._pointerInSummary && !this._notificationRemoved;
|
||||
let notificationPinned = this._pointerInNotification && !this._notificationRemoved;
|
||||
let notificationExpanded = this._notification && this._notification.expanded;
|
||||
let notificationExpired = this._notificationTimeoutId == 0 &&
|
||||
!(this._notification && this._notification.urgency == Urgency.CRITICAL) &&
|
||||
!(this._notification && this._notification.focused) &&
|
||||
!this._pointerInTray &&
|
||||
!this._locked &&
|
||||
!(this._pointerInKeyboard && notificationExpanded);
|
||||
!this._pointerInNotification;
|
||||
let notificationLockedOut = !Main.sessionMode.hasNotifications && this._notification;
|
||||
let notificationMustClose = this._notificationRemoved || notificationLockedOut || (notificationExpired && this._userActiveWhileNotificationShown) || this._notificationClosed;
|
||||
let canShowNotification = notificationsPending && this._summaryState == State.HIDDEN;
|
||||
let canShowNotification = notificationsPending && this._trayState == State.HIDDEN;
|
||||
|
||||
if (this._notificationState == State.HIDDEN) {
|
||||
if (canShowNotification) {
|
||||
if (canShowNotification)
|
||||
this._showNotification();
|
||||
}
|
||||
} else if (this._notificationState == State.SHOWN) {
|
||||
if (notificationMustClose)
|
||||
this._hideNotification();
|
||||
@@ -2256,27 +2224,17 @@ const MessageTray = new Lang.Class({
|
||||
this._ensureNotificationFocused();
|
||||
}
|
||||
|
||||
// Summary
|
||||
let summarySummoned = this._pointerInSummary || this._traySummoned;
|
||||
let summaryPinned = this._pointerInTray || summarySummoned || this._locked;
|
||||
let summaryHovered = this._pointerInTray || this._pointerInSummary;
|
||||
|
||||
let notificationsVisible = this._notificationState != State.HIDDEN;
|
||||
let notificationsDone = !notificationsVisible && !notificationsPending;
|
||||
|
||||
let mustHideSummary = ((notificationsPending && notificationUrgent)
|
||||
|| notificationsVisible || !Main.sessionMode.hasNotifications);
|
||||
|
||||
if (this._summaryState == State.HIDDEN && !mustHideSummary && summarySummoned)
|
||||
this._showSummary();
|
||||
else if (this._summaryState == State.SHOWN && (!summaryPinned || mustHideSummary))
|
||||
this._hideSummary();
|
||||
let mustHideTray = ((notificationsPending && notificationUrgent)
|
||||
|| notificationsVisible || !Main.sessionMode.hasNotifications);
|
||||
|
||||
// Summary notification
|
||||
let haveClickedSummaryItem = this._clickedSummaryItem != null;
|
||||
let summarySourceIsMainNotificationSource = (haveClickedSummaryItem && this._notification &&
|
||||
this._clickedSummaryItem.source == this._notification.source);
|
||||
let canShowSummaryBoxPointer = this._summaryState == State.SHOWN;
|
||||
let canShowSummaryBoxPointer = this._trayState == State.SHOWN;
|
||||
// We only have sources with empty notification stacks for legacy tray icons. Currently, we never attempt
|
||||
// to show notifications for legacy tray icons, but this would be necessary if we did.
|
||||
let requestedNotificationStackIsEmpty = (this._clickedSummaryItemMouseButton == 1 && this._clickedSummaryItem.source.notifications.length == 0);
|
||||
@@ -2291,7 +2249,7 @@ const MessageTray = new Lang.Class({
|
||||
if (haveClickedSummaryItem && !summarySourceIsMainNotificationSource && canShowSummaryBoxPointer && !requestedNotificationStackIsEmpty)
|
||||
this._showSummaryBoxPointer();
|
||||
} else if (this._summaryBoxPointerState == State.SHOWN) {
|
||||
if (!haveClickedSummaryItem || !canShowSummaryBoxPointer || wrongSummaryBoxPointer || mustHideSummary) {
|
||||
if (!haveClickedSummaryItem || !canShowSummaryBoxPointer || wrongSummaryBoxPointer || mustHideTray) {
|
||||
this._hideSummaryBoxPointer();
|
||||
if (wrongSummaryBoxPointer)
|
||||
this._showSummaryBoxPointer();
|
||||
@@ -2301,9 +2259,7 @@ const MessageTray = new Lang.Class({
|
||||
// Tray itself
|
||||
let trayIsVisible = (this._trayState == State.SHOWING ||
|
||||
this._trayState == State.SHOWN);
|
||||
let trayShouldBeVisible = (this._summaryState == State.SHOWING ||
|
||||
this._summaryState == State.SHOWN) &&
|
||||
!this._keyboardVisible;
|
||||
let trayShouldBeVisible = this._traySummoned && !this._keyboardVisible && !mustHideTray;
|
||||
if (!trayIsVisible && trayShouldBeVisible)
|
||||
trayShouldBeVisible = this._showTray();
|
||||
else if (trayIsVisible && !trayShouldBeVisible)
|
||||
@@ -2441,7 +2397,7 @@ const MessageTray = new Lang.Class({
|
||||
_showNotification: function() {
|
||||
this._notification = this._notificationQueue.shift();
|
||||
|
||||
this._userActiveWhileNotificationShown = this.idleMonitor.get_idletime() > IDLE_TIME;
|
||||
this._userActiveWhileNotificationShown = this.idleMonitor.get_idletime() <= IDLE_TIME;
|
||||
if (!this._userActiveWhileNotificationShown) {
|
||||
// If the user isn't active, set up a watch to let us know
|
||||
// when the user becomes active.
|
||||
@@ -2464,7 +2420,7 @@ const MessageTray = new Lang.Class({
|
||||
let [x, y, mods] = global.get_pointer();
|
||||
// We save the position of the mouse at the time when we started showing the notification
|
||||
// in order to determine if the notification popped up under it. We make that check if
|
||||
// the user starts moving the mouse and _onTrayHoverChanged() gets called. We don't
|
||||
// the user starts moving the mouse and _onNotificationHoverChanged() gets called. We don't
|
||||
// expand the notification if it just happened to pop up under the mouse unless the user
|
||||
// explicitly mouses away from it and then mouses back in.
|
||||
this._showNotificationMouseX = x;
|
||||
@@ -2526,13 +2482,13 @@ const MessageTray = new Lang.Class({
|
||||
|
||||
_notificationTimeout: function() {
|
||||
let [x, y, mods] = global.get_pointer();
|
||||
if (y > this._lastSeenMouseY + 10 && !this.actor.hover) {
|
||||
if (y > this._lastSeenMouseY + 10 && !this._notificationHovered) {
|
||||
// The mouse is moving towards the notification, so don't
|
||||
// hide it yet. (We just create a new timeout (and destroy
|
||||
// the old one) each time because the bookkeeping is
|
||||
// simpler.)
|
||||
this._updateNotificationTimeout(1000);
|
||||
} else if (this._useLongerTrayLeftTimeout && !this._trayLeftTimeoutId &&
|
||||
} else if (this._useLongerNotificationLeftTimeout && !this._notificationLeftTimeoutId &&
|
||||
(x != this._lastSeenMouseX || y != this._lastSeenMouseY)) {
|
||||
// Refresh the timeout if the notification originally
|
||||
// popped up under the pointer, and the pointer is hovering
|
||||
@@ -2576,6 +2532,14 @@ const MessageTray = new Lang.Class({
|
||||
this._notificationUnfocusedId = 0;
|
||||
}
|
||||
|
||||
this._useLongerNotificationLeftTimeout = false;
|
||||
if (this._notificationLeftTimeoutId) {
|
||||
Mainloop.source_remove(this._notificationLeftTimeoutId);
|
||||
this._notificationLeftTimeoutId = 0;
|
||||
this._notificationLeftMouseX = -1;
|
||||
this._notificationLeftMouseY = -1;
|
||||
}
|
||||
|
||||
if (this._notificationRemoved) {
|
||||
Tweener.removeTweens(this._notificationWidget);
|
||||
this._notificationWidget.y = this.actor.height;
|
||||
@@ -2603,10 +2567,9 @@ const MessageTray = new Lang.Class({
|
||||
if (notification.isTransient)
|
||||
notification.destroy(NotificationDestroyedReason.EXPIRED);
|
||||
|
||||
this._notificationRemoved = false;
|
||||
this._closeButton.hide();
|
||||
this._pointerInTray = false;
|
||||
this.actor.hover = false; // Clutter doesn't emit notify::hover when actors move
|
||||
this._pointerInNotification = false;
|
||||
this._notificationRemoved = false;
|
||||
this._notificationBin.child = null;
|
||||
this._notificationWidget.hide();
|
||||
},
|
||||
@@ -2619,10 +2582,9 @@ const MessageTray = new Lang.Class({
|
||||
},
|
||||
|
||||
_expandNotification: function(autoExpanding) {
|
||||
// Don't grab focus in notifications that are auto-expanded.
|
||||
// Don't focus notifications that are auto-expanding.
|
||||
if (!autoExpanding)
|
||||
this._grabHelper.grab({ actor: this._notification.actor,
|
||||
grabFocus: true });
|
||||
this._ensureNotificationFocused();
|
||||
|
||||
if (!this._notificationExpandedId)
|
||||
this._notificationExpandedId =
|
||||
@@ -2652,30 +2614,11 @@ const MessageTray = new Lang.Class({
|
||||
}
|
||||
},
|
||||
|
||||
// We use this function to grab focus when the user moves the pointer
|
||||
// to a notification with CRITICAL urgency that was already auto-expanded.
|
||||
_ensureNotificationFocused: function() {
|
||||
this._grabHelper.grab({ actor: this._notification.actor,
|
||||
grabFocus: true });
|
||||
},
|
||||
|
||||
_showSummary: function() {
|
||||
this._summary.opacity = 0;
|
||||
this._tween(this._summary, '_summaryState', State.SHOWN,
|
||||
{ opacity: 255,
|
||||
time: ANIMATION_TIME,
|
||||
transition: 'easeOutQuad',
|
||||
});
|
||||
},
|
||||
|
||||
_hideSummary: function() {
|
||||
this._tween(this._summary, '_summaryState', State.HIDDEN,
|
||||
{ opacity: 0,
|
||||
time: ANIMATION_TIME,
|
||||
transition: 'easeOutQuad',
|
||||
});
|
||||
},
|
||||
|
||||
_onSourceDoneDisplayingContent: function(source, closeTray) {
|
||||
if (closeTray) {
|
||||
this._escapeTray();
|
||||
@@ -2717,9 +2660,8 @@ const MessageTray = new Lang.Class({
|
||||
}
|
||||
|
||||
this._grabHelper.grab({ actor: this._summaryBoxPointer.bin.child,
|
||||
grabFocus: true,
|
||||
modal: true,
|
||||
onUngrab: Lang.bind(this, this._onSummaryBoxPointerUngrabbed) });
|
||||
this._lock();
|
||||
|
||||
this._summaryBoxPointer.actor.opacity = 0;
|
||||
this._summaryBoxPointer.actor.show();
|
||||
@@ -2754,10 +2696,8 @@ const MessageTray = new Lang.Class({
|
||||
this._clickedSummaryItem.actor.remove_style_pseudo_class('selected');
|
||||
this._clickedSummaryItem.actor.disconnect(this._clickedSummaryItemAllocationChangedId);
|
||||
this._summary.disconnect(this._summaryMotionId);
|
||||
Main.layoutManager.trayBox.disconnect(this._trayMotionId);
|
||||
this._clickedSummaryItemAllocationChangedId = 0;
|
||||
this._summaryMotionId = 0;
|
||||
this._trayMotionId = 0;
|
||||
}
|
||||
|
||||
this._clickedSummaryItem = item;
|
||||
@@ -2772,8 +2712,6 @@ const MessageTray = new Lang.Class({
|
||||
// _clickedSummaryItem.actor can change absolute position without changing allocation
|
||||
this._summaryMotionId = this._summary.connect('allocation-changed',
|
||||
Lang.bind(this, this._adjustSummaryBoxPointerPosition));
|
||||
this._trayMotionId = Main.layoutManager.trayBox.connect('notify::anchor-y',
|
||||
Lang.bind(this, this._adjustSummaryBoxPointerPosition));
|
||||
}
|
||||
|
||||
return true;
|
||||
@@ -2810,8 +2748,6 @@ const MessageTray = new Lang.Class({
|
||||
this._sourceDoneDisplayingId = 0;
|
||||
}
|
||||
|
||||
this._unlock();
|
||||
|
||||
if (this._summaryBoxPointerItem.source.notifications.length == 0) {
|
||||
this._summaryBoxPointer.actor.hide();
|
||||
this._hideSummaryBoxPointerCompleted();
|
||||
|
||||
@@ -38,13 +38,15 @@ const ModalDialog = new Lang.Class({
|
||||
styleClass: null,
|
||||
parentActor: Main.uiGroup,
|
||||
keybindingMode: Shell.KeyBindingMode.SYSTEM_MODAL,
|
||||
shouldFadeIn: true });
|
||||
shouldFadeIn: true,
|
||||
destroyOnClose: true });
|
||||
|
||||
this.state = State.CLOSED;
|
||||
this._hasModal = false;
|
||||
this._keybindingMode = params.keybindingMode;
|
||||
this._shellReactive = params.shellReactive;
|
||||
this._shouldFadeIn = params.shouldFadeIn;
|
||||
this._destroyOnClose = params.destroyOnClose;
|
||||
|
||||
this._group = new St.Widget({ visible: false,
|
||||
x: 0,
|
||||
@@ -277,6 +279,9 @@ const ModalDialog = new Lang.Class({
|
||||
this.state = State.CLOSED;
|
||||
this._group.hide();
|
||||
this.emit('closed');
|
||||
|
||||
if (this._destroyOnClose)
|
||||
this.destroy();
|
||||
})
|
||||
});
|
||||
},
|
||||
|
||||
@@ -244,7 +244,7 @@ const NotificationDaemon = new Lang.Class({
|
||||
Main.overview.connect('hidden',
|
||||
Lang.bind(this, this._onFocusAppChanged));
|
||||
|
||||
this._trayManager.manage_stage(global.stage, Main.messageTray.actor);
|
||||
this._trayManager.manage_screen(global.screen, Main.messageTray.actor);
|
||||
},
|
||||
|
||||
_imageForNotificationData: function(hints) {
|
||||
|
||||
@@ -164,12 +164,12 @@ const OsdWindow = new Lang.Class({
|
||||
},
|
||||
|
||||
_monitorsChanged: function() {
|
||||
/* assume 130x130 on a 640x480 display and scale from there */
|
||||
/* assume 110x110 on a 640x480 display and scale from there */
|
||||
let monitor = Main.layoutManager.primaryMonitor;
|
||||
let scalew = monitor.width / 640.0;
|
||||
let scaleh = monitor.height / 480.0;
|
||||
let scale = Math.min(scalew, scaleh);
|
||||
let size = 130 * Math.max(1, scale);
|
||||
let size = 110 * Math.max(1, scale);
|
||||
|
||||
this._box.set_size(size, size);
|
||||
this._box.translation_y = monitor.height / 4;
|
||||
|
||||
@@ -11,7 +11,6 @@ const Shell = imports.gi.Shell;
|
||||
const Gdk = imports.gi.Gdk;
|
||||
|
||||
const Background = imports.ui.background;
|
||||
const Dash = imports.ui.dash;
|
||||
const DND = imports.ui.dnd;
|
||||
const LayoutManager = imports.ui.layout;
|
||||
const Main = imports.ui.main;
|
||||
@@ -20,7 +19,6 @@ const OverviewControls = imports.ui.overviewControls;
|
||||
const Panel = imports.ui.panel;
|
||||
const Params = imports.misc.params;
|
||||
const Tweener = imports.ui.tweener;
|
||||
const ViewSelector = imports.ui.viewSelector;
|
||||
const WorkspaceThumbnail = imports.ui.workspaceThumbnail;
|
||||
|
||||
// Time for initial animation going into Overview mode
|
||||
@@ -33,6 +31,8 @@ const SHADE_ANIMATION_TIME = .20;
|
||||
|
||||
const DND_WINDOW_SWITCH_TIMEOUT = 1250;
|
||||
|
||||
const OVERVIEW_ACTIVATION_TIMEOUT = 0.5;
|
||||
|
||||
const ShellInfo = new Lang.Class({
|
||||
Name: 'ShellInfo',
|
||||
|
||||
@@ -93,9 +93,7 @@ const Overview = new Lang.Class({
|
||||
_init: function() {
|
||||
this._overviewCreated = false;
|
||||
this._initCalled = false;
|
||||
this._controlPressed = false;
|
||||
|
||||
global.stage.connect('captured-event', Lang.bind(this, this._capturedEvent));
|
||||
Main.sessionMode.connect('updated', Lang.bind(this, this._sessionUpdated));
|
||||
this._sessionUpdated();
|
||||
},
|
||||
@@ -133,22 +131,15 @@ const Overview = new Lang.Class({
|
||||
y_expand: true });
|
||||
this._overview._delegate = this;
|
||||
|
||||
this._groupStack = new St.Widget({ layout_manager: new Clutter.BinLayout(),
|
||||
x_expand: true, y_expand: true,
|
||||
clip_to_allocation: true });
|
||||
this._group = new St.BoxLayout({ name: 'overview-group',
|
||||
reactive: true,
|
||||
x_expand: true, y_expand: true });
|
||||
this._groupStack.add_actor(this._group);
|
||||
|
||||
this._backgroundGroup = new Meta.BackgroundGroup();
|
||||
global.overlay_group.add_child(this._backgroundGroup);
|
||||
this._backgroundGroup.hide();
|
||||
this._bgManagers = [];
|
||||
|
||||
this._activationTime = 0;
|
||||
|
||||
this.visible = false; // animating to overview, in overview, animating out
|
||||
this._shown = false; // show() and not hide()
|
||||
this._shownTemporarily = false; // showTemporarily() and not hideTemporarily()
|
||||
this._modal = false; // have a modal grab
|
||||
this.animationInProgress = false;
|
||||
this.visibleTarget = false;
|
||||
@@ -176,7 +167,6 @@ const Overview = new Lang.Class({
|
||||
Main.xdndHandler.connect('drag-end', Lang.bind(this, this._onDragEnd));
|
||||
|
||||
global.screen.connect('restacked', Lang.bind(this, this._onRestacked));
|
||||
this._group.connect('scroll-event', Lang.bind(this, this._onScrollEvent));
|
||||
|
||||
this._windowSwitchTimeoutId = 0;
|
||||
this._windowSwitchTimestamp = 0;
|
||||
@@ -238,20 +228,6 @@ const Overview = new Lang.Class({
|
||||
}
|
||||
},
|
||||
|
||||
_capturedEvent: function(actor, event) {
|
||||
let type = event.type();
|
||||
if (type != Clutter.EventType.KEY_PRESS &&
|
||||
type != Clutter.EventType.KEY_RELEASE)
|
||||
return false;
|
||||
|
||||
let symbol = event.get_key_symbol();
|
||||
if (symbol == Clutter.KEY_Control_L ||
|
||||
symbol == Clutter.KEY_Control_R)
|
||||
this._controlPressed = type == Clutter.EventType.KEY_PRESS;
|
||||
|
||||
return false;
|
||||
},
|
||||
|
||||
_sessionUpdated: function() {
|
||||
this.isDummy = !Main.sessionMode.hasOverview;
|
||||
this._createOverview();
|
||||
@@ -289,28 +265,13 @@ const Overview = new Lang.Class({
|
||||
this._overview.add_actor(this._searchEntryBin);
|
||||
|
||||
// Create controls
|
||||
this._dash = new Dash.Dash();
|
||||
this._viewSelector = new ViewSelector.ViewSelector(this._searchEntry,
|
||||
this._dash.showAppsButton);
|
||||
this._thumbnailsBox = new WorkspaceThumbnail.ThumbnailsBox();
|
||||
this._controls = new OverviewControls.ControlsManager(this._dash,
|
||||
this._thumbnailsBox,
|
||||
this._viewSelector);
|
||||
|
||||
this._controls.dashActor.x_align = Clutter.ActorAlign.START;
|
||||
this._controls.dashActor.y_expand = true;
|
||||
|
||||
// Put the dash in a separate layer to allow content to be centered
|
||||
this._groupStack.add_actor(this._controls.dashActor);
|
||||
|
||||
// Pack all the actors into the group
|
||||
this._group.add_actor(this._controls.dashSpacer);
|
||||
this._group.add(this._viewSelector.actor, { x_fill: true,
|
||||
expand: true });
|
||||
this._group.add_actor(this._controls.thumbnailsActor);
|
||||
this._controls = new OverviewControls.ControlsManager(this._searchEntry);
|
||||
this._dash = this._controls.dash;
|
||||
this._viewSelector = this._controls.viewSelector;
|
||||
|
||||
// Add our same-line elements after the search entry
|
||||
this._overview.add(this._groupStack, { y_fill: true, expand: true });
|
||||
this._overview.add(this._controls.actor, { y_fill: true, expand: true });
|
||||
this._controls.actor.connect('scroll-event', Lang.bind(this, this._onScrollEvent));
|
||||
|
||||
this._stack.add_actor(this._controls.indicatorActor);
|
||||
|
||||
@@ -346,18 +307,22 @@ const Overview = new Lang.Class({
|
||||
},
|
||||
|
||||
_onDragBegin: function() {
|
||||
this._inXdndDrag = true;
|
||||
|
||||
DND.addDragMonitor(this._dragMonitor);
|
||||
// Remember the workspace we started from
|
||||
this._lastActiveWorkspaceIndex = global.screen.get_active_workspace_index();
|
||||
},
|
||||
|
||||
_onDragEnd: function(time) {
|
||||
this._inXdndDrag = false;
|
||||
|
||||
// In case the drag was canceled while in the overview
|
||||
// we have to go back to where we started and hide
|
||||
// the overview
|
||||
if (this._shownTemporarily) {
|
||||
if (this._shown) {
|
||||
global.screen.get_workspace_by_index(this._lastActiveWorkspaceIndex).activate(time);
|
||||
this.hideTemporarily();
|
||||
this.hide();
|
||||
}
|
||||
this._resetWindowSwitchTimeout();
|
||||
this._lastHoveredWindow = null;
|
||||
@@ -405,7 +370,7 @@ const Overview = new Lang.Class({
|
||||
this._needsFakePointerEvent = true;
|
||||
Main.activateWindow(dragEvent.targetActor._delegate.metaWindow,
|
||||
this._windowSwitchTimestamp);
|
||||
this.hideTemporarily();
|
||||
this.hide();
|
||||
this._lastHoveredWindow = null;
|
||||
}));
|
||||
}
|
||||
@@ -501,9 +466,10 @@ const Overview = new Lang.Class({
|
||||
if (this._shown)
|
||||
return;
|
||||
this._shown = true;
|
||||
this._syncInputMode();
|
||||
if (!this._modal)
|
||||
|
||||
if (!this._syncInputMode())
|
||||
return;
|
||||
|
||||
this._animateVisible();
|
||||
},
|
||||
|
||||
@@ -536,6 +502,7 @@ const Overview = new Lang.Class({
|
||||
this.visible = true;
|
||||
this.animationInProgress = true;
|
||||
this.visibleTarget = true;
|
||||
this._activationTime = Date.now() / 1000;
|
||||
|
||||
// All the the actors in the window group are completely obscured,
|
||||
// hiding the group holding them while the Overview is displayed greatly
|
||||
@@ -547,8 +514,6 @@ const Overview = new Lang.Class({
|
||||
//
|
||||
// Disable unredirection while in the overview
|
||||
Meta.disable_unredirect_for_screen(global.screen);
|
||||
global.window_group.hide();
|
||||
global.top_window_group.hide();
|
||||
this._stack.show();
|
||||
this._backgroundGroup.show();
|
||||
this._viewSelector.show();
|
||||
@@ -568,24 +533,6 @@ const Overview = new Lang.Class({
|
||||
this.emit('showing');
|
||||
},
|
||||
|
||||
// showTemporarily:
|
||||
//
|
||||
// Animates the overview visible without grabbing mouse and keyboard input;
|
||||
// if show() has already been called, this has no immediate effect, but
|
||||
// will result in the overview not being hidden until hideTemporarily() is
|
||||
// called.
|
||||
showTemporarily: function() {
|
||||
if (this.isDummy)
|
||||
return;
|
||||
|
||||
if (this._shownTemporarily)
|
||||
return;
|
||||
|
||||
this._syncInputMode();
|
||||
this._animateVisible();
|
||||
this._shownTemporarily = true;
|
||||
},
|
||||
|
||||
// hide:
|
||||
//
|
||||
// Reverses the effect of show()
|
||||
@@ -596,33 +543,22 @@ const Overview = new Lang.Class({
|
||||
if (!this._shown)
|
||||
return;
|
||||
|
||||
if (this._controlPressed)
|
||||
return;
|
||||
let event = Clutter.get_current_event();
|
||||
if (event) {
|
||||
let type = event.type();
|
||||
let button = (type == Clutter.EventType.BUTTON_PRESS ||
|
||||
type == Clutter.EventType.BUTTON_RELEASE);
|
||||
let ctrl = (event.get_state() & Clutter.ModifierType.CONTROL_MASK) != 0;
|
||||
if (button && ctrl)
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this._shownTemporarily)
|
||||
this._animateNotVisible();
|
||||
this._animateNotVisible();
|
||||
|
||||
this._shown = false;
|
||||
this._syncInputMode();
|
||||
},
|
||||
|
||||
// hideTemporarily:
|
||||
//
|
||||
// Reverses the effect of showTemporarily()
|
||||
hideTemporarily: function() {
|
||||
if (this.isDummy)
|
||||
return;
|
||||
|
||||
if (!this._shownTemporarily)
|
||||
return;
|
||||
|
||||
if (!this._shown)
|
||||
this._animateNotVisible();
|
||||
|
||||
this._shownTemporarily = false;
|
||||
this._syncInputMode();
|
||||
},
|
||||
|
||||
toggle: function() {
|
||||
if (this.isDummy)
|
||||
return;
|
||||
@@ -633,6 +569,20 @@ const Overview = new Lang.Class({
|
||||
this.show();
|
||||
},
|
||||
|
||||
// Checks if the Activities button is currently sensitive to
|
||||
// clicks. The first call to this function within the
|
||||
// OVERVIEW_ACTIVATION_TIMEOUT time of the hot corner being
|
||||
// triggered will return false. This avoids opening and closing
|
||||
// the overview if the user both triggered the hot corner and
|
||||
// clicked the Activities button.
|
||||
shouldToggleByCornerOrButton: function() {
|
||||
if (this.animationInProgress)
|
||||
return false;
|
||||
if (this._activationTime == 0 || Date.now() / 1000 - this._activationTime > OVERVIEW_ACTIVATION_TIMEOUT)
|
||||
return true;
|
||||
return false;
|
||||
},
|
||||
|
||||
//// Private methods ////
|
||||
|
||||
_syncInputMode: function() {
|
||||
@@ -640,22 +590,23 @@ const Overview = new Lang.Class({
|
||||
// overview we don't have a problem with the release of a press/release
|
||||
// going to an application.
|
||||
if (this.animationInProgress)
|
||||
return;
|
||||
return true;
|
||||
|
||||
if (this._shown) {
|
||||
if (!this._modal) {
|
||||
if (Main.pushModal(this._overview,
|
||||
{ keybindingMode: Shell.KeyBindingMode.OVERVIEW }))
|
||||
this._modal = true;
|
||||
else
|
||||
this.hide();
|
||||
let shouldBeModal = !this._inXdndDrag;
|
||||
if (shouldBeModal) {
|
||||
if (!this._modal) {
|
||||
if (Main.pushModal(this._overview,
|
||||
{ keybindingMode: Shell.KeyBindingMode.OVERVIEW })) {
|
||||
this._modal = true;
|
||||
} else {
|
||||
this.hide();
|
||||
return false;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
global.stage_input_mode = Shell.StageInputMode.FULLSCREEN;
|
||||
}
|
||||
} else if (this._shownTemporarily) {
|
||||
if (this._modal) {
|
||||
Main.popModal(this._overview);
|
||||
this._modal = false;
|
||||
}
|
||||
global.stage_input_mode = Shell.StageInputMode.FULLSCREEN;
|
||||
} else {
|
||||
if (this._modal) {
|
||||
Main.popModal(this._overview);
|
||||
@@ -664,6 +615,7 @@ const Overview = new Lang.Class({
|
||||
else if (global.stage_input_mode == Shell.StageInputMode.FULLSCREEN)
|
||||
global.stage_input_mode = Shell.StageInputMode.NORMAL;
|
||||
}
|
||||
return true;
|
||||
},
|
||||
|
||||
_animateNotVisible: function() {
|
||||
@@ -697,7 +649,7 @@ const Overview = new Lang.Class({
|
||||
|
||||
this.emit('shown');
|
||||
// Handle any calls to hide* while we were showing
|
||||
if (!this._shown && !this._shownTemporarily)
|
||||
if (!this._shown)
|
||||
this._animateNotVisible();
|
||||
|
||||
this._syncInputMode();
|
||||
@@ -708,9 +660,6 @@ const Overview = new Lang.Class({
|
||||
// Re-enable unredirection
|
||||
Meta.enable_unredirect_for_screen(global.screen);
|
||||
|
||||
global.window_group.show();
|
||||
global.top_window_group.show();
|
||||
|
||||
this._viewSelector.hide();
|
||||
this._desktopFade.hide();
|
||||
this._backgroundGroup.hide();
|
||||
@@ -723,7 +672,7 @@ const Overview = new Lang.Class({
|
||||
|
||||
this.emit('hidden');
|
||||
// Handle any calls to show* while we were hiding
|
||||
if (this._shown || this._shownTemporarily)
|
||||
if (this._shown)
|
||||
this._animateVisible();
|
||||
|
||||
this._syncInputMode();
|
||||
|
||||
@@ -6,10 +6,12 @@ const Meta = imports.gi.Meta;
|
||||
const St = imports.gi.St;
|
||||
const Shell = imports.gi.Shell;
|
||||
|
||||
const Dash = imports.ui.dash;
|
||||
const Main = imports.ui.main;
|
||||
const Params = imports.misc.params;
|
||||
const Tweener = imports.ui.tweener;
|
||||
const ViewSelector = imports.ui.viewSelector;
|
||||
const WorkspaceThumbnail = imports.ui.workspaceThumbnail;
|
||||
|
||||
const SIDE_CONTROLS_ANIMATION_TIME = 0.16;
|
||||
|
||||
@@ -269,6 +271,11 @@ const ThumbnailsSlider = new Lang.Class({
|
||||
return alwaysZoomOut;
|
||||
},
|
||||
|
||||
getNonExpandedWidth: function() {
|
||||
let child = this.actor.get_first_child();
|
||||
return child.get_theme_node().get_length('visible-width');
|
||||
},
|
||||
|
||||
getSlide: function() {
|
||||
if (!this.visible)
|
||||
return 0;
|
||||
@@ -280,18 +287,16 @@ const ThumbnailsSlider = new Lang.Class({
|
||||
let child = this.actor.get_first_child();
|
||||
let preferredHeight = child.get_preferred_height(-1)[1];
|
||||
let expandedWidth = child.get_preferred_width(preferredHeight)[1];
|
||||
let visibleWidth = child.get_theme_node().get_length('visible-width');
|
||||
|
||||
return visibleWidth / expandedWidth;
|
||||
return this.getNonExpandedWidth() / expandedWidth;
|
||||
},
|
||||
|
||||
getVisibleWidth: function() {
|
||||
let alwaysZoomOut = this._getAlwaysZoomOut();
|
||||
if (alwaysZoomOut)
|
||||
return this.parent();
|
||||
|
||||
let child = this.actor.get_first_child();
|
||||
return child.get_theme_node().get_length('visible-width');
|
||||
else
|
||||
return this.getNonExpandedWidth();
|
||||
}
|
||||
});
|
||||
|
||||
@@ -309,6 +314,10 @@ const DashSlider = new Lang.Class({
|
||||
// available allocation
|
||||
this._dash.actor.x_expand = true;
|
||||
this._dash.actor.y_expand = true;
|
||||
|
||||
this.actor.x_align = Clutter.ActorAlign.START;
|
||||
this.actor.y_expand = true;
|
||||
|
||||
this.actor.add_actor(this._dash.actor);
|
||||
|
||||
this._dash.connect('icon-size-changed', Lang.bind(this, this.updateSlide));
|
||||
@@ -452,9 +461,11 @@ const MessagesIndicator = new Lang.Class({
|
||||
|
||||
_updateCount: function() {
|
||||
let count = 0;
|
||||
let hasChats = false;
|
||||
this._sources.forEach(Lang.bind(this,
|
||||
function(source) {
|
||||
count += source.indicatorCount;
|
||||
hasChats |= source.isChat;
|
||||
}));
|
||||
|
||||
this._count = count;
|
||||
@@ -462,6 +473,7 @@ const MessagesIndicator = new Lang.Class({
|
||||
"%d new messages",
|
||||
count).format(count);
|
||||
|
||||
this._icon.visible = hasChats;
|
||||
this._updateVisibility();
|
||||
},
|
||||
|
||||
@@ -476,39 +488,77 @@ const MessagesIndicator = new Lang.Class({
|
||||
const ControlsManager = new Lang.Class({
|
||||
Name: 'ControlsManager',
|
||||
|
||||
_init: function(dash, thumbnails, viewSelector) {
|
||||
this._dashSlider = new DashSlider(dash);
|
||||
this.dashActor = this._dashSlider.actor;
|
||||
this.dashSpacer = new DashSpacer();
|
||||
this.dashSpacer.setDashActor(this.dashActor);
|
||||
_init: function(searchEntry) {
|
||||
this.dash = new Dash.Dash();
|
||||
this._dashSlider = new DashSlider(this.dash);
|
||||
this._dashSpacer = new DashSpacer();
|
||||
this._dashSpacer.setDashActor(this._dashSlider.actor);
|
||||
|
||||
this._thumbnailsSlider = new ThumbnailsSlider(thumbnails);
|
||||
this.thumbnailsActor = this._thumbnailsSlider.actor;
|
||||
this._thumbnailsBox = new WorkspaceThumbnail.ThumbnailsBox();
|
||||
this._thumbnailsSlider = new ThumbnailsSlider(this._thumbnailsBox);
|
||||
|
||||
this._indicator = new MessagesIndicator(viewSelector);
|
||||
this.viewSelector = new ViewSelector.ViewSelector(searchEntry,
|
||||
this.dash.showAppsButton);
|
||||
this.viewSelector.connect('page-changed', Lang.bind(this, this._setVisibility));
|
||||
this.viewSelector.connect('page-empty', Lang.bind(this, this._onPageEmpty));
|
||||
|
||||
this._indicator = new MessagesIndicator(this.viewSelector);
|
||||
this.indicatorActor = this._indicator.actor;
|
||||
|
||||
this._viewSelector = viewSelector;
|
||||
this._viewSelector.connect('page-changed', Lang.bind(this, this._setVisibility));
|
||||
this._viewSelector.connect('page-empty', Lang.bind(this, this._onPageEmpty));
|
||||
this.actor = new St.Widget({ layout_manager: new Clutter.BinLayout(),
|
||||
x_expand: true, y_expand: true,
|
||||
clip_to_allocation: true });
|
||||
this._group = new St.BoxLayout({ name: 'overview-group',
|
||||
reactive: true,
|
||||
x_expand: true, y_expand: true });
|
||||
this.actor.add_actor(this._group);
|
||||
|
||||
this.actor.add_actor(this._dashSlider.actor);
|
||||
|
||||
this._group.add_actor(this._dashSpacer);
|
||||
this._group.add(this.viewSelector.actor, { x_fill: true,
|
||||
expand: true });
|
||||
this._group.add_actor(this._thumbnailsSlider.actor);
|
||||
|
||||
this._group.connect('notify::allocation', Lang.bind(this, this._updateWorkspacesGeometry));
|
||||
|
||||
Main.overview.connect('showing', Lang.bind(this, this._updateSpacerVisibility));
|
||||
Main.overview.connect('item-drag-begin', Lang.bind(this,
|
||||
function() {
|
||||
let activePage = this._viewSelector.getActivePage();
|
||||
let activePage = this.viewSelector.getActivePage();
|
||||
if (activePage != ViewSelector.ViewPage.WINDOWS)
|
||||
this._viewSelector.fadeHalf();
|
||||
this.viewSelector.fadeHalf();
|
||||
}));
|
||||
Main.overview.connect('item-drag-end', Lang.bind(this,
|
||||
function() {
|
||||
this._viewSelector.fadeIn();
|
||||
this.viewSelector.fadeIn();
|
||||
}));
|
||||
Main.overview.connect('item-drag-cancelled', Lang.bind(this,
|
||||
function() {
|
||||
this._viewSelector.fadeIn();
|
||||
this.viewSelector.fadeIn();
|
||||
}));
|
||||
},
|
||||
|
||||
_updateWorkspacesGeometry: function() {
|
||||
let [x, y] = this.actor.get_transformed_position();
|
||||
let [width, height] = this.actor.get_transformed_size();
|
||||
let geometry = { x: x, y: y, width: width, height: height };
|
||||
|
||||
let spacing = this.actor.get_theme_node().get_length('spacing');
|
||||
let dashWidth = this._dashSlider.getVisibleWidth() + spacing;
|
||||
let thumbnailsWidth = this._thumbnailsSlider.getNonExpandedWidth() + spacing;
|
||||
|
||||
geometry.width -= dashWidth;
|
||||
geometry.width -= thumbnailsWidth;
|
||||
|
||||
if (this.actor.get_text_direction() == Clutter.TextDirection.LTR)
|
||||
geometry.x += dashWidth;
|
||||
else
|
||||
geometry.x += thumbnailsWidth;
|
||||
|
||||
this.viewSelector.setWorkspacesFullGeometry(geometry);
|
||||
},
|
||||
|
||||
_setVisibility: function() {
|
||||
// Ignore the case when we're leaving the overview, since
|
||||
// actors will be made visible again when entering the overview
|
||||
@@ -518,7 +568,7 @@ const ControlsManager = new Lang.Class({
|
||||
(Main.overview.animationInProgress && !Main.overview.visibleTarget))
|
||||
return;
|
||||
|
||||
let activePage = this._viewSelector.getActivePage();
|
||||
let activePage = this.viewSelector.getActivePage();
|
||||
let dashVisible = (activePage == ViewSelector.ViewPage.WINDOWS ||
|
||||
activePage == ViewSelector.ViewPage.APPS);
|
||||
let thumbnailsVisible = (activePage == ViewSelector.ViewPage.WINDOWS);
|
||||
@@ -538,8 +588,8 @@ const ControlsManager = new Lang.Class({
|
||||
if (Main.overview.animationInProgress && !Main.overview.visibleTarget)
|
||||
return;
|
||||
|
||||
let activePage = this._viewSelector.getActivePage();
|
||||
this.dashSpacer.visible = (activePage == ViewSelector.ViewPage.WINDOWS);
|
||||
let activePage = this.viewSelector.getActivePage();
|
||||
this._dashSpacer.visible = (activePage == ViewSelector.ViewPage.WINDOWS);
|
||||
},
|
||||
|
||||
_onPageEmpty: function() {
|
||||
|
||||
161
js/ui/panel.js
161
js/ui/panel.js
@@ -18,7 +18,6 @@ const Atk = imports.gi.Atk;
|
||||
const Config = imports.misc.config;
|
||||
const CtrlAltTab = imports.ui.ctrlAltTab;
|
||||
const DND = imports.ui.dnd;
|
||||
const Layout = imports.ui.layout;
|
||||
const Overview = imports.ui.overview;
|
||||
const PopupMenu = imports.ui.popupMenu;
|
||||
const PanelMenu = imports.ui.panelMenu;
|
||||
@@ -145,8 +144,8 @@ const AnimatedIcon = new Lang.Class({
|
||||
Name: 'AnimatedIcon',
|
||||
Extends: Animation,
|
||||
|
||||
_init: function(name, size) {
|
||||
this.parent(global.datadir + '/theme/' + name, size, size, ANIMATED_ICON_UPDATE_TIMEOUT);
|
||||
_init: function(filename, size) {
|
||||
this.parent(filename, size, size, ANIMATED_ICON_UPDATE_TIMEOUT);
|
||||
}
|
||||
});
|
||||
|
||||
@@ -259,6 +258,7 @@ const AppMenuButton = new Lang.Class({
|
||||
this._actionGroupNotifyId = 0;
|
||||
|
||||
let bin = new St.Bin({ name: 'appMenu' });
|
||||
bin.connect('style-changed', Lang.bind(this, this._onStyleChanged));
|
||||
this.actor.add_actor(bin);
|
||||
|
||||
this.actor.bind_property("reactive", this.actor, "can-focus", 0);
|
||||
@@ -289,27 +289,25 @@ const AppMenuButton = new Lang.Class({
|
||||
this._visible = !Main.overview.visible;
|
||||
if (!this._visible)
|
||||
this.actor.hide();
|
||||
Main.overview.connect('hiding', Lang.bind(this, function () {
|
||||
this._overviewHidingId = Main.overview.connect('hiding', Lang.bind(this, function () {
|
||||
this.show();
|
||||
}));
|
||||
Main.overview.connect('showing', Lang.bind(this, function () {
|
||||
this._overviewShowingId = Main.overview.connect('showing', Lang.bind(this, function () {
|
||||
this.hide();
|
||||
}));
|
||||
|
||||
this._stop = true;
|
||||
|
||||
this._spinner = new AnimatedIcon('process-working.svg',
|
||||
PANEL_ICON_SIZE);
|
||||
this._container.add_actor(this._spinner.actor);
|
||||
this._spinner.actor.hide();
|
||||
this._spinner.actor.lower_bottom();
|
||||
this._spinner = null;
|
||||
|
||||
let tracker = Shell.WindowTracker.get_default();
|
||||
let appSys = Shell.AppSystem.get_default();
|
||||
tracker.connect('notify::focus-app', Lang.bind(this, this._focusAppChanged));
|
||||
appSys.connect('app-state-changed', Lang.bind(this, this._onAppStateChanged));
|
||||
|
||||
global.window_manager.connect('switch-workspace', Lang.bind(this, this._sync));
|
||||
this._focusAppNotifyId =
|
||||
tracker.connect('notify::focus-app', Lang.bind(this, this._focusAppChanged));
|
||||
this._appStateChangedSignalId =
|
||||
appSys.connect('app-state-changed', Lang.bind(this, this._onAppStateChanged));
|
||||
this._switchWorkspaceNotifyId =
|
||||
global.window_manager.connect('switch-workspace', Lang.bind(this, this._sync));
|
||||
|
||||
this._sync();
|
||||
},
|
||||
@@ -355,6 +353,18 @@ const AppMenuButton = new Lang.Class({
|
||||
onCompleteScope: this });
|
||||
},
|
||||
|
||||
_onStyleChanged: function(actor) {
|
||||
let node = actor.get_theme_node();
|
||||
let [success, icon] = node.lookup_url('spinner-image', false);
|
||||
if (!success || this._spinnerIcon == icon)
|
||||
return;
|
||||
this._spinnerIcon = icon;
|
||||
this._spinner = new AnimatedIcon(this._spinnerIcon, PANEL_ICON_SIZE);
|
||||
this._container.add_actor(this._spinner.actor);
|
||||
this._spinner.actor.hide();
|
||||
this._spinner.actor.lower_bottom();
|
||||
},
|
||||
|
||||
_onIconBoxStyleChanged: function() {
|
||||
let node = this._iconBox.get_theme_node();
|
||||
this._iconBottomClip = node.get_length('app-icon-bottom-clip');
|
||||
@@ -386,6 +396,10 @@ const AppMenuButton = new Lang.Class({
|
||||
|
||||
this._stop = true;
|
||||
this.actor.reactive = true;
|
||||
|
||||
if (this._spinner == null)
|
||||
return;
|
||||
|
||||
Tweener.addTween(this._spinner.actor,
|
||||
{ opacity: 0,
|
||||
time: SPINNER_ANIMATION_TIME,
|
||||
@@ -402,6 +416,10 @@ const AppMenuButton = new Lang.Class({
|
||||
startAnimation: function() {
|
||||
this._stop = false;
|
||||
this.actor.reactive = false;
|
||||
|
||||
if (this._spinner == null)
|
||||
return;
|
||||
|
||||
this._spinner.play();
|
||||
this._spinner.actor.show();
|
||||
},
|
||||
@@ -464,6 +482,9 @@ const AppMenuButton = new Lang.Class({
|
||||
}
|
||||
this._label.actor.allocate(childBox, flags);
|
||||
|
||||
if (this._spinner == null)
|
||||
return;
|
||||
|
||||
if (direction == Clutter.TextDirection.LTR) {
|
||||
childBox.x1 = Math.floor(iconWidth / 2) + this._label.actor.width;
|
||||
childBox.x2 = childBox.x1 + this._spinner.actor.width;
|
||||
@@ -547,14 +568,20 @@ const AppMenuButton = new Lang.Class({
|
||||
}
|
||||
|
||||
if (targetApp == this._targetApp) {
|
||||
if (targetApp && targetApp.get_state() != Shell.AppState.STARTING) {
|
||||
if (targetApp &&
|
||||
targetApp.get_state() != Shell.AppState.STARTING &&
|
||||
targetApp.get_state() != Shell.AppState.BUSY) {
|
||||
this.stopAnimation();
|
||||
this._maybeSetMenu();
|
||||
} else if (targetApp &&
|
||||
targetApp.get_state() == Shell.AppState.BUSY) {
|
||||
this.startAnimation();
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
this._spinner.actor.hide();
|
||||
if (this._spinner)
|
||||
this._spinner.actor.hide();
|
||||
if (this._iconBox.child != null)
|
||||
this._iconBox.child.destroy();
|
||||
this._iconBox.hide();
|
||||
@@ -581,7 +608,8 @@ const AppMenuButton = new Lang.Class({
|
||||
this._iconBox.set_child(icon);
|
||||
this._iconBox.show();
|
||||
|
||||
if (targetApp.get_state() == Shell.AppState.STARTING)
|
||||
if (targetApp.get_state() == Shell.AppState.STARTING ||
|
||||
targetApp.get_state() == Shell.AppState.BUSY)
|
||||
this.startAnimation();
|
||||
else
|
||||
this._maybeSetMenu();
|
||||
@@ -617,6 +645,33 @@ const AppMenuButton = new Lang.Class({
|
||||
|
||||
this.setMenu(menu);
|
||||
this._menuManager.addMenu(menu);
|
||||
},
|
||||
|
||||
destroy: function() {
|
||||
if (this._appStateChangedSignalId > 0) {
|
||||
let appSys = Shell.AppSystem.get_default();
|
||||
appSys.disconnect(this._appStateChangedSignalId);
|
||||
this._appStateChangedSignalId = 0;
|
||||
}
|
||||
if (this._focusAppNotifyId > 0) {
|
||||
let tracker = Shell.WindowTracker.get_default();
|
||||
tracker.disconnect(this._focusAppNotifyId);
|
||||
this._focusAppNotifyId = 0;
|
||||
}
|
||||
if (this._overviewHidingId > 0) {
|
||||
Main.overview.disconnect(this._overviewHidingId);
|
||||
this._overviewHidingId = 0;
|
||||
}
|
||||
if (this._overviewShowingId > 0) {
|
||||
Main.overview.disconnect(this._overviewShowingId);
|
||||
this._overviewShowingId = 0;
|
||||
}
|
||||
if (this._switchWorkspaceNotifyId > 0) {
|
||||
global.window_manager.disconnect(this._switchWorkspaceNotifyId);
|
||||
this._switchWorkspaceNotifyId = 0;
|
||||
}
|
||||
|
||||
this.parent();
|
||||
}
|
||||
});
|
||||
|
||||
@@ -630,23 +685,15 @@ const ActivitiesButton = new Lang.Class({
|
||||
this.parent(0.0, null, true);
|
||||
this.actor.accessible_role = Atk.Role.TOGGLE_BUTTON;
|
||||
|
||||
let container = new Shell.GenericContainer();
|
||||
container.connect('get-preferred-width', Lang.bind(this, this._containerGetPreferredWidth));
|
||||
container.connect('get-preferred-height', Lang.bind(this, this._containerGetPreferredHeight));
|
||||
container.connect('allocate', Lang.bind(this, this._containerAllocate));
|
||||
this.actor.add_actor(container);
|
||||
this.actor.name = 'panelActivities';
|
||||
|
||||
/* Translators: If there is no suitable word for "Activities"
|
||||
in your language, you can use the word for "Overview". */
|
||||
this._label = new St.Label({ text: _("Activities") });
|
||||
container.add_actor(this._label);
|
||||
this.actor.add_actor(this._label);
|
||||
|
||||
this.actor.label_actor = this._label;
|
||||
|
||||
this.hotCorner = new Layout.HotCorner(Main.layoutManager);
|
||||
container.add_actor(this.hotCorner.actor);
|
||||
|
||||
this.actor.connect('captured-event', Lang.bind(this, this._onCapturedEvent));
|
||||
this.actor.connect_after('button-release-event', Lang.bind(this, this._onButtonRelease));
|
||||
this.actor.connect_after('key-release-event', Lang.bind(this, this._onKeyRelease));
|
||||
@@ -661,44 +708,6 @@ const ActivitiesButton = new Lang.Class({
|
||||
}));
|
||||
|
||||
this._xdndTimeOut = 0;
|
||||
|
||||
// Since the hot corner uses stage coordinates, Clutter won't
|
||||
// queue relayouts for us when the panel moves. Queue a relayout
|
||||
// when that happens.
|
||||
Main.layoutManager.connect('panel-box-changed', Lang.bind(this, function() {
|
||||
container.queue_relayout();
|
||||
}));
|
||||
},
|
||||
|
||||
_containerGetPreferredWidth: function(actor, forHeight, alloc) {
|
||||
[alloc.min_size, alloc.natural_size] = this._label.get_preferred_width(forHeight);
|
||||
},
|
||||
|
||||
_containerGetPreferredHeight: function(actor, forWidth, alloc) {
|
||||
[alloc.min_size, alloc.natural_size] = this._label.get_preferred_height(forWidth);
|
||||
},
|
||||
|
||||
_containerAllocate: function(actor, box, flags) {
|
||||
this._label.allocate(box, flags);
|
||||
|
||||
// The hot corner needs to be outside any padding/alignment
|
||||
// that has been imposed on us
|
||||
let primary = Main.layoutManager.primaryMonitor;
|
||||
let hotBox = new Clutter.ActorBox();
|
||||
let ok, x, y;
|
||||
if (actor.get_text_direction() == Clutter.TextDirection.LTR) {
|
||||
[ok, x, y] = actor.transform_stage_point(primary.x, primary.y)
|
||||
} else {
|
||||
[ok, x, y] = actor.transform_stage_point(primary.x + primary.width, primary.y);
|
||||
// hotCorner.actor has northeast gravity, so we don't need
|
||||
// to adjust x for its width
|
||||
}
|
||||
|
||||
hotBox.x1 = Math.round(x);
|
||||
hotBox.x2 = hotBox.x1 + this.hotCorner.actor.width;
|
||||
hotBox.y1 = Math.round(y);
|
||||
hotBox.y2 = hotBox.y1 + this.hotCorner.actor.height;
|
||||
this.hotCorner.actor.allocate(hotBox, flags);
|
||||
},
|
||||
|
||||
handleDragOver: function(source, actor, x, y, time) {
|
||||
@@ -708,14 +717,14 @@ const ActivitiesButton = new Lang.Class({
|
||||
if (this._xdndTimeOut != 0)
|
||||
Mainloop.source_remove(this._xdndTimeOut);
|
||||
this._xdndTimeOut = Mainloop.timeout_add(BUTTON_DND_ACTIVATION_TIMEOUT,
|
||||
Lang.bind(this, this._xdndShowOverview, actor));
|
||||
Lang.bind(this, this._xdndToggleOverview, actor));
|
||||
|
||||
return DND.DragMotionResult.CONTINUE;
|
||||
},
|
||||
|
||||
_onCapturedEvent: function(actor, event) {
|
||||
if (event.type() == Clutter.EventType.BUTTON_PRESS) {
|
||||
if (!this.hotCorner.shouldToggleOverviewOnClick())
|
||||
if (!Main.overview.shouldToggleByCornerOrButton())
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
@@ -732,15 +741,12 @@ const ActivitiesButton = new Lang.Class({
|
||||
}
|
||||
},
|
||||
|
||||
_xdndShowOverview: function(actor) {
|
||||
_xdndToggleOverview: function(actor) {
|
||||
let [x, y, mask] = global.get_pointer();
|
||||
let pickedActor = global.stage.get_actor_at_pos(Clutter.PickMode.REACTIVE, x, y);
|
||||
|
||||
if (pickedActor == this.actor) {
|
||||
if (!Main.overview.visible && !Main.overview.animationInProgress) {
|
||||
Main.overview.showTemporarily();
|
||||
}
|
||||
}
|
||||
if (pickedActor == this.actor && Main.overview.shouldToggleByCornerOrButton())
|
||||
Main.overview.toggle();
|
||||
|
||||
Mainloop.source_remove(this._xdndTimeOut);
|
||||
this._xdndTimeOut = 0;
|
||||
@@ -952,7 +958,7 @@ const Panel = new Lang.Class({
|
||||
|
||||
this.statusArea = {};
|
||||
|
||||
this.menuManager = new PopupMenu.PopupMenuManager(this);
|
||||
this.menuManager = new PopupMenu.PopupMenuManager(this, { keybindingMode: Shell.KeyBindingMode.TOPBAR_POPUP });
|
||||
|
||||
this._leftBox = new St.BoxLayout({ name: 'panelLeft' });
|
||||
this.actor.add_actor(this._leftBox);
|
||||
@@ -1106,17 +1112,18 @@ const Panel = new Lang.Class({
|
||||
return true;
|
||||
},
|
||||
|
||||
openAppMenu: function() {
|
||||
toggleAppMenu: function() {
|
||||
let indicator = this.statusArea.appMenu;
|
||||
if (!indicator) // appMenu not supported by current session mode
|
||||
return;
|
||||
|
||||
let menu = indicator.menu;
|
||||
if (!indicator.actor.reactive || menu.isOpen)
|
||||
if (!indicator.actor.reactive)
|
||||
return;
|
||||
|
||||
menu.open();
|
||||
menu.actor.navigate_focus(null, Gtk.DirectionType.TAB_FORWARD, false);
|
||||
menu.toggle();
|
||||
if (menu.isOpen)
|
||||
menu.actor.navigate_focus(null, Gtk.DirectionType.TAB_FORWARD, false);
|
||||
},
|
||||
|
||||
set boxOpacity(value) {
|
||||
|
||||
@@ -19,6 +19,12 @@ const Tweener = imports.ui.tweener;
|
||||
|
||||
const SLIDER_SCROLL_STEP = 0.05; /* Slider scrolling step in % */
|
||||
|
||||
const Ornament = {
|
||||
NONE: 0,
|
||||
DOT: 1,
|
||||
CHECK: 2,
|
||||
};
|
||||
|
||||
function _ensureStyle(actor) {
|
||||
if (actor.get_children) {
|
||||
let children = actor.get_children();
|
||||
@@ -53,7 +59,9 @@ const PopupBaseMenuItem = new Lang.Class({
|
||||
this.actor._delegate = this;
|
||||
|
||||
this._children = [];
|
||||
this._dot = null;
|
||||
this._ornament = Ornament.NONE;
|
||||
this._ornamentLabel = new St.Label({ style_class: 'popup-menu-ornament' });
|
||||
this.actor.add_actor(this._ornamentLabel);
|
||||
this._columnWidths = null;
|
||||
this._spacing = 0;
|
||||
this.active = false;
|
||||
@@ -176,40 +184,24 @@ const PopupBaseMenuItem = new Lang.Class({
|
||||
this._removeChild(child);
|
||||
},
|
||||
|
||||
setShowDot: function(show) {
|
||||
if (show) {
|
||||
if (this._dot)
|
||||
return;
|
||||
setOrnament: function(ornament) {
|
||||
if (ornament == this._ornament)
|
||||
return;
|
||||
|
||||
this._dot = new St.DrawingArea({ style_class: 'popup-menu-item-dot' });
|
||||
this._dot.connect('repaint', Lang.bind(this, this._onRepaintDot));
|
||||
this.actor.add_actor(this._dot);
|
||||
this.actor.add_accessible_state (Atk.StateType.CHECKED);
|
||||
} else {
|
||||
if (!this._dot)
|
||||
return;
|
||||
this._ornament = ornament;
|
||||
|
||||
this._dot.destroy();
|
||||
this._dot = null;
|
||||
this.actor.remove_accessible_state (Atk.StateType.CHECKED);
|
||||
if (ornament == Ornament.DOT) {
|
||||
this._ornamentLabel.text = '\u2022';
|
||||
this.actor.add_accessible_state(Atk.StateType.CHECKED);
|
||||
} else if (ornament == Ornament.CHECK) {
|
||||
this._ornamentLabel.text = '\u2713';
|
||||
this.actor.add_accessible_state(Atk.StateType.CHECKED);
|
||||
} else if (ornament == Ornament.NONE) {
|
||||
this._ornamentLabel.text = '';
|
||||
this.actor.remove_accessible_state(Atk.StateType.CHECKED);
|
||||
}
|
||||
},
|
||||
|
||||
_onRepaintDot: function(area) {
|
||||
let cr = area.get_context();
|
||||
let [width, height] = area.get_surface_size();
|
||||
let color = area.get_theme_node().get_foreground_color();
|
||||
|
||||
cr.setSourceRGBA (
|
||||
color.red / 255,
|
||||
color.green / 255,
|
||||
color.blue / 255,
|
||||
color.alpha / 255);
|
||||
cr.arc(width / 2, height / 2, width / 3, 0, 2 * Math.PI);
|
||||
cr.fill();
|
||||
cr.$dispose();
|
||||
},
|
||||
|
||||
// This returns column widths in logical order (i.e. from the dot
|
||||
// to the image), not in visual order (left to right)
|
||||
getColumnWidths: function() {
|
||||
@@ -280,26 +272,25 @@ const PopupBaseMenuItem = new Lang.Class({
|
||||
let height = box.y2 - box.y1;
|
||||
let direction = this.actor.get_text_direction();
|
||||
|
||||
if (this._dot) {
|
||||
// The dot is placed outside box
|
||||
// one quarter of padding from the border of the container
|
||||
// (so 3/4 from the inner border)
|
||||
// (padding is box.x1)
|
||||
let dotBox = new Clutter.ActorBox();
|
||||
let dotWidth = Math.round(box.x1 / 2);
|
||||
// The ornament is placed outside box
|
||||
// one quarter of padding from the border of the container
|
||||
// (so 3/4 from the inner border)
|
||||
// (padding is box.x1)
|
||||
let ornamentBox = new Clutter.ActorBox();
|
||||
let ornamentWidth = box.x1;
|
||||
|
||||
if (direction == Clutter.TextDirection.LTR) {
|
||||
dotBox.x1 = Math.round(box.x1 / 4);
|
||||
dotBox.x2 = dotBox.x1 + dotWidth;
|
||||
} else {
|
||||
dotBox.x2 = box.x2 + 3 * Math.round(box.x1 / 4);
|
||||
dotBox.x1 = dotBox.x2 - dotWidth;
|
||||
}
|
||||
dotBox.y1 = Math.round(box.y1 + (height - dotWidth) / 2);
|
||||
dotBox.y2 = dotBox.y1 + dotWidth;
|
||||
this._dot.allocate(dotBox, flags);
|
||||
ornamentBox.x1 = 0;
|
||||
ornamentBox.x2 = ornamentWidth;
|
||||
ornamentBox.y1 = box.y1;
|
||||
ornamentBox.y2 = box.y2;
|
||||
|
||||
if (direction == Clutter.TextDirection.RTL) {
|
||||
ornamentBox.x1 += box.x2;
|
||||
ornamentBox.x2 += box.x2;
|
||||
}
|
||||
|
||||
this._ornamentLabel.allocate(ornamentBox, flags);
|
||||
|
||||
let x;
|
||||
if (direction == Clutter.TextDirection.LTR)
|
||||
x = box.x1;
|
||||
@@ -1157,6 +1148,7 @@ const PopupMenuBase = new Lang.Class({
|
||||
},
|
||||
|
||||
destroy: function() {
|
||||
this.close();
|
||||
this.removeAll();
|
||||
this.actor.destroy();
|
||||
|
||||
@@ -1474,23 +1466,12 @@ const PopupMenuSection = new Lang.Class({
|
||||
this.actor = this.box;
|
||||
this.actor._delegate = this;
|
||||
this.isOpen = true;
|
||||
|
||||
// an array of externally managed separators
|
||||
this.separators = [];
|
||||
},
|
||||
|
||||
// deliberately ignore any attempt to open() or close(), but emit the
|
||||
// corresponding signal so children can still pick it up
|
||||
open: function() { this.emit('open-state-changed', true); },
|
||||
close: function() { this.emit('open-state-changed', false); },
|
||||
|
||||
destroy: function() {
|
||||
for (let i = 0; i < this.separators.length; i++)
|
||||
this.separators[i].destroy();
|
||||
this.separators = [];
|
||||
|
||||
this.parent();
|
||||
}
|
||||
});
|
||||
|
||||
const PopupSubMenuMenuItem = new Lang.Class({
|
||||
@@ -1807,8 +1788,8 @@ const RemoteMenu = new Lang.Class({
|
||||
this.model = model;
|
||||
this.actionGroup = actionGroup;
|
||||
|
||||
this._actions = { };
|
||||
this._modelChanged(this.model, 0, 0, this.model.get_n_items(), this);
|
||||
this._actions = {};
|
||||
this._trackMenu(model, this);
|
||||
|
||||
this._actionStateChangeId = this.actionGroup.connect('action-state-changed', Lang.bind(this, this._actionStateChanged));
|
||||
this._actionEnableChangeId = this.actionGroup.connect('action-enabled-changed', Lang.bind(this, this._actionEnabledChanged));
|
||||
@@ -1828,39 +1809,8 @@ const RemoteMenu = new Lang.Class({
|
||||
this.parent();
|
||||
},
|
||||
|
||||
_createMenuItem: function(model, index) {
|
||||
let labelValue = model.get_item_attribute_value(index, Gio.MENU_ATTRIBUTE_LABEL, null);
|
||||
let label = labelValue ? labelValue.deep_unpack() : '';
|
||||
// remove all underscores that are not followed by another underscore
|
||||
label = label.replace(/_([^_])/, '$1');
|
||||
|
||||
let section_link = model.get_item_link(index, Gio.MENU_LINK_SECTION);
|
||||
if (section_link) {
|
||||
let item = new PopupMenuSection();
|
||||
if (label) {
|
||||
let title = new PopupMenuItem(label, { reactive: false,
|
||||
style_class: 'popup-subtitle-menu-item' });
|
||||
item._titleMenuItem = title;
|
||||
title._ignored = true;
|
||||
item.addMenuItem(title);
|
||||
}
|
||||
this._modelChanged(section_link, 0, 0, section_link.get_n_items(), item);
|
||||
return [item, true, ''];
|
||||
}
|
||||
|
||||
let submenu_link = model.get_item_link(index, Gio.MENU_LINK_SUBMENU);
|
||||
|
||||
if (submenu_link) {
|
||||
let item = new PopupSubMenuMenuItem(label);
|
||||
this._modelChanged(submenu_link, 0, 0, submenu_link.get_n_items(), item.menu);
|
||||
return [item, false, ''];
|
||||
}
|
||||
|
||||
let action_id = model.get_item_attribute_value(index, Gio.MENU_ATTRIBUTE_ACTION, null).deep_unpack();
|
||||
if (!this.actionGroup.has_action(action_id)) {
|
||||
// the action may not be there yet, wait for action-added
|
||||
return [null, false, 'action-added'];
|
||||
}
|
||||
_actionAdded: function(model, item, index) {
|
||||
let action_id = item.action_id;
|
||||
|
||||
if (!this._actions[action_id])
|
||||
this._actions[action_id] = { enabled: this.actionGroup.get_action_enabled(action_id),
|
||||
@@ -1868,7 +1818,7 @@ const RemoteMenu = new Lang.Class({
|
||||
items: [ ],
|
||||
};
|
||||
let action = this._actions[action_id];
|
||||
let item, target, destroyId, specificSignalId;
|
||||
let target, destroyId, specificSignalId;
|
||||
|
||||
if (action.state) {
|
||||
// Docs have get_state_hint(), except that the DBus protocol
|
||||
@@ -1879,28 +1829,28 @@ const RemoteMenu = new Lang.Class({
|
||||
|
||||
switch (String.fromCharCode(action.state.classify())) {
|
||||
case 'b':
|
||||
item = new PopupSwitchMenuItem(label, action.state.get_boolean());
|
||||
action.items.push(item);
|
||||
specificSignalId = item.connect('toggled', Lang.bind(this, function(item) {
|
||||
item.setOrnament(action.state.get_boolean() ?
|
||||
Ornament.CHECK : Ornament.NONE);
|
||||
specificSignalId = item.connect('activate', Lang.bind(this, function(item) {
|
||||
this.actionGroup.activate_action(action_id, null);
|
||||
}));
|
||||
break;
|
||||
case 's':
|
||||
item = new PopupMenuItem(label);
|
||||
item._remoteTarget = model.get_item_attribute_value(index, Gio.MENU_ATTRIBUTE_TARGET, null).deep_unpack();
|
||||
action.items.push(item);
|
||||
item.setShowDot(action.state.deep_unpack() == item._remoteTarget);
|
||||
item._remoteTarget = model.get_item_attribute_value(index, Gio.MENU_ATTRIBUTE_TARGET, null).deep_unpack();
|
||||
item.setOrnament(action.state.deep_unpack() == item._remoteTarget ?
|
||||
Ornament.DOT : Ornament.NONE);
|
||||
specificSignalId = item.connect('activate', Lang.bind(this, function(item) {
|
||||
this.actionGroup.activate_action(action_id, GLib.Variant.new_string(item._remoteTarget));
|
||||
}));
|
||||
break;
|
||||
default:
|
||||
log('Action "%s" has state of type %s, which is not supported'.format(action_id, action.state.get_type_string()));
|
||||
return [null, false, 'action-state-changed'];
|
||||
return;
|
||||
}
|
||||
} else {
|
||||
target = model.get_item_attribute_value(index, Gio.MENU_ATTRIBUTE_TARGET, null);
|
||||
item = new PopupMenuItem(label);
|
||||
action.items.push(item);
|
||||
specificSignalId = item.connect('activate', Lang.bind(this, function() {
|
||||
this.actionGroup.activate_action(action_id, target);
|
||||
@@ -1917,94 +1867,52 @@ const RemoteMenu = new Lang.Class({
|
||||
if (pos != -1)
|
||||
action.items.splice(pos, 1);
|
||||
}));
|
||||
},
|
||||
|
||||
return [item, false, ''];
|
||||
},
|
||||
_trackMenu: function(model, item) {
|
||||
item._tracker = Shell.MenuTracker.new(model,
|
||||
null, /* action namespace */
|
||||
Lang.bind(this, this._insertItem, item),
|
||||
Lang.bind(this, this._removeItem, item));
|
||||
|
||||
_modelChanged: function(model, position, removed, added, target) {
|
||||
let j, k;
|
||||
let j0, k0;
|
||||
item.connect('destroy', function() {
|
||||
item._tracker.destroy();
|
||||
item._tracker = null;
|
||||
});
|
||||
},
|
||||
|
||||
let currentItems = target._getMenuItems();
|
||||
_createMenuItem: function(model, index) {
|
||||
let labelValue = model.get_item_attribute_value(index, Gio.MENU_ATTRIBUTE_LABEL, null);
|
||||
let label = labelValue ? labelValue.deep_unpack() : '';
|
||||
// remove all underscores that are not followed by another underscore
|
||||
label = label.replace(/_([^_])/, '$1');
|
||||
|
||||
k0 = 0;
|
||||
// skip ignored items at the beginning
|
||||
while (k0 < currentItems.length && currentItems[k0]._ignored)
|
||||
k0++;
|
||||
// find the right menu item matching the model item
|
||||
for (j0 = 0; k0 < currentItems.length && j0 < position; j0++, k0++) {
|
||||
if (currentItems[k0]._ignored)
|
||||
k0++;
|
||||
let submenuModel = model.get_item_link(index, Gio.MENU_LINK_SUBMENU);
|
||||
if (submenuModel) {
|
||||
let item = new PopupSubMenuMenuItem(label);
|
||||
this._trackMenu(submenuModel, item.menu);
|
||||
return item;
|
||||
}
|
||||
|
||||
if (removed == -1) {
|
||||
// special flag to indicate we should destroy everything
|
||||
for (k = k0; k < currentItems.length; k++)
|
||||
currentItems[k].destroy();
|
||||
} else {
|
||||
for (j = j0, k = k0; k < currentItems.length && j < j0 + removed; j++, k++) {
|
||||
currentItems[k].destroy();
|
||||
let item = new PopupMenuItem(label);
|
||||
let action_id = model.get_item_attribute_value(index, Gio.MENU_ATTRIBUTE_ACTION, null).deep_unpack();
|
||||
item.actor.can_focus = item.actor.reactive = false;
|
||||
|
||||
if (currentItems[k]._ignored)
|
||||
j--;
|
||||
}
|
||||
item.action_id = action_id;
|
||||
|
||||
if (this.actionGroup.has_action(action_id)) {
|
||||
this._actionAdded(model, item, index);
|
||||
return item;
|
||||
}
|
||||
|
||||
for (j = j0, k = k0; j < j0 + added; j++, k++) {
|
||||
let [item, addSeparator, changeSignal] = this._createMenuItem(model, j);
|
||||
let signalId = this.actionGroup.connect('action-added', Lang.bind(this, function(actionGroup, actionName) {
|
||||
actionGroup.disconnect(signalId);
|
||||
if (this._actions[actionName]) return;
|
||||
|
||||
if (item) {
|
||||
// separators must be added in the parent to make autohiding work
|
||||
if (addSeparator) {
|
||||
let separator = new PopupSeparatorMenuItem();
|
||||
item.separators.push(separator);
|
||||
separator._ignored = true;
|
||||
target.addMenuItem(separator, k+1);
|
||||
k++;
|
||||
}
|
||||
this._actionAdded(model, item, index);
|
||||
}));
|
||||
|
||||
target.addMenuItem(item, k);
|
||||
|
||||
if (addSeparator) {
|
||||
let separator = new PopupSeparatorMenuItem();
|
||||
item.separators.push(separator);
|
||||
separator._ignored = true;
|
||||
target.addMenuItem(separator, k+1);
|
||||
k++;
|
||||
}
|
||||
} else if (changeSignal) {
|
||||
let signalId = this.actionGroup.connect(changeSignal, Lang.bind(this, function(actionGroup, actionName) {
|
||||
actionGroup.disconnect(signalId);
|
||||
if (this._actions[actionName]) return;
|
||||
|
||||
// force a full update
|
||||
this._modelChanged(model, 0, -1, model.get_n_items(), target);
|
||||
}));
|
||||
}
|
||||
}
|
||||
|
||||
if (!model._changedId) {
|
||||
model._changedId = model.connect('items-changed', Lang.bind(this, this._modelChanged, target));
|
||||
model._destroyId = target.connect('destroy', function() {
|
||||
if (model._changedId)
|
||||
model.disconnect(model._changedId);
|
||||
if (model._destroyId)
|
||||
target.disconnect(model._destroyId);
|
||||
model._changedId = 0;
|
||||
model._destroyId = 0;
|
||||
});
|
||||
}
|
||||
|
||||
if (target instanceof PopupMenuSection) {
|
||||
if (target._titleMenuItem)
|
||||
target.actor.visible = target.numMenuItems != 1;
|
||||
else
|
||||
target.actor.visible = target.numMenuItems != 0;
|
||||
} else {
|
||||
let sourceItem = target.sourceActor._delegate;
|
||||
if (sourceItem instanceof PopupSubMenuMenuItem)
|
||||
sourceItem.actor.visible = target.numMenuItems != 0;
|
||||
}
|
||||
return item;
|
||||
},
|
||||
|
||||
_actionStateChanged: function(actionGroup, action_id) {
|
||||
@@ -2017,7 +1925,8 @@ const RemoteMenu = new Lang.Class({
|
||||
switch (String.fromCharCode(action.state.classify())) {
|
||||
case 'b':
|
||||
for (let i = 0; i < action.items.length; i++)
|
||||
action.items[i].setToggleState(action.state.get_boolean());
|
||||
action.items[i].setOrnament(action.state.get_boolean() ?
|
||||
Ornament.CHECK : Ornament.NONE);
|
||||
break;
|
||||
case 'd':
|
||||
for (let i = 0; i < action.items.length; i++)
|
||||
@@ -2025,7 +1934,8 @@ const RemoteMenu = new Lang.Class({
|
||||
break;
|
||||
case 's':
|
||||
for (let i = 0; i < action.items.length; i++)
|
||||
action.items[i].setShowDot(action.items[i]._remoteTarget == action.state.deep_unpack());
|
||||
action.items[i].setOrnament(action.items[i]._remoteTarget == action.state.deep_unpack() ?
|
||||
Ornament.DOT : Ornament.NONE);
|
||||
}
|
||||
}
|
||||
},
|
||||
@@ -2042,7 +1952,23 @@ const RemoteMenu = new Lang.Class({
|
||||
item.actor.reactive = item.actor.can_focus = action.enabled;
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
_insertItem: function(position, model, item_index, action_namespace, is_separator, target) {
|
||||
let item;
|
||||
|
||||
if (is_separator)
|
||||
item = new PopupSeparatorMenuItem();
|
||||
else
|
||||
item = this._createMenuItem(model, item_index);
|
||||
|
||||
target.addMenuItem(item, position);
|
||||
},
|
||||
|
||||
_removeItem: function(position, target) {
|
||||
let items = target._getMenuItems();
|
||||
items[position].destroy();
|
||||
},
|
||||
});
|
||||
|
||||
/* Basic implementation of a menu manager.
|
||||
@@ -2051,9 +1977,9 @@ const RemoteMenu = new Lang.Class({
|
||||
const PopupMenuManager = new Lang.Class({
|
||||
Name: 'PopupMenuManager',
|
||||
|
||||
_init: function(owner) {
|
||||
_init: function(owner, grabParams) {
|
||||
this._owner = owner;
|
||||
this._grabHelper = new GrabHelper.GrabHelper(owner.actor);
|
||||
this._grabHelper = new GrabHelper.GrabHelper(owner.actor, grabParams);
|
||||
this._menus = [];
|
||||
},
|
||||
|
||||
@@ -2086,7 +2012,7 @@ const PopupMenuManager = new Lang.Class({
|
||||
},
|
||||
|
||||
removeMenu: function(menu) {
|
||||
if (menu == this._activeMenu)
|
||||
if (menu == this.activeMenu)
|
||||
this._closeMenu(menu);
|
||||
|
||||
let position = this._findMenu(menu);
|
||||
@@ -2110,9 +2036,9 @@ const PopupMenuManager = new Lang.Class({
|
||||
},
|
||||
|
||||
get activeMenu() {
|
||||
let actor = this._grabHelper.currentGrab.actor;
|
||||
if (actor)
|
||||
return actor._delegate;
|
||||
let firstGrab = this._grabHelper.grabStack[0];
|
||||
if (firstGrab)
|
||||
return firstGrab.actor._delegate;
|
||||
else
|
||||
return null;
|
||||
},
|
||||
@@ -2123,6 +2049,8 @@ const PopupMenuManager = new Lang.Class({
|
||||
|
||||
_onMenuOpenState: function(menu, open) {
|
||||
if (open) {
|
||||
if (this.activeMenu)
|
||||
this.activeMenu.close(BoxPointer.PopupAnimation.FADE);
|
||||
this._grabHelper.grab({ actor: menu.actor, modal: true, focus: menu.sourceActor,
|
||||
onUngrab: Lang.bind(this, this._closeMenu, menu) });
|
||||
} else {
|
||||
@@ -2139,13 +2067,8 @@ const PopupMenuManager = new Lang.Class({
|
||||
},
|
||||
|
||||
_changeMenu: function(newMenu) {
|
||||
let oldMenu = this.activeMenu;
|
||||
if (oldMenu) {
|
||||
oldMenu.close(BoxPointer.PopupAnimation.FADE);
|
||||
newMenu.open(BoxPointer.PopupAnimation.FADE);
|
||||
} else {
|
||||
newMenu.open(BoxPointer.PopupAnimation.FULL);
|
||||
}
|
||||
newMenu.open(this.activeMenu ? BoxPointer.PopupAnimation.FADE
|
||||
: BoxPointer.PopupAnimation.FULL);
|
||||
},
|
||||
|
||||
_onMenuSourceEnter: function(menu) {
|
||||
|
||||
@@ -127,8 +127,6 @@ function remoteProvidersLoaded(loadState) {
|
||||
// Special case gnome-control-center to be always active and always first
|
||||
sortOrder.unshift('gnome-control-center.desktop');
|
||||
|
||||
let numSorted = sortOrder.length;
|
||||
|
||||
loadState.loadedProviders.sort(
|
||||
function(providerA, providerB) {
|
||||
let idxA, idxB;
|
||||
@@ -148,15 +146,6 @@ function remoteProvidersLoaded(loadState) {
|
||||
return GLib.utf8_collate(nameA, nameB);
|
||||
}
|
||||
|
||||
if (numSorted > 1) {
|
||||
// if providerA is the last, it goes after everything
|
||||
if ((idxA + 1) == numSorted)
|
||||
return 1;
|
||||
// if providerB is the last, it goes after everything
|
||||
else if ((idxB + 1) == numSorted)
|
||||
return -1;
|
||||
}
|
||||
|
||||
// if providerA isn't found, it's sorted after providerB
|
||||
if (idxA == -1)
|
||||
return 1;
|
||||
@@ -198,7 +187,9 @@ const RemoteSearchProvider = new Lang.Class({
|
||||
|
||||
createIcon: function(size, meta) {
|
||||
let gicon;
|
||||
if (meta['gicon']) {
|
||||
if (meta['icon']) {
|
||||
gicon = Gio.icon_deserialize(meta['icon']);
|
||||
} else if (meta['gicon']) {
|
||||
gicon = Gio.icon_new_for_string(meta['gicon']);
|
||||
} else if (meta['icon-data']) {
|
||||
let [width, height, rowStride, hasAlpha,
|
||||
@@ -251,8 +242,12 @@ const RemoteSearchProvider = new Lang.Class({
|
||||
let metas = results[0];
|
||||
let resultMetas = [];
|
||||
for (let i = 0; i < metas.length; i++) {
|
||||
for (let prop in metas[i])
|
||||
metas[i][prop] = metas[i][prop].deep_unpack();
|
||||
for (let prop in metas[i]) {
|
||||
// we can use the serialized icon variant directly
|
||||
if (prop != 'icon')
|
||||
metas[i][prop] = metas[i][prop].deep_unpack();
|
||||
}
|
||||
|
||||
resultMetas.push({ id: metas[i]['id'],
|
||||
name: metas[i]['name'],
|
||||
description: metas[i]['description'],
|
||||
|
||||
@@ -30,144 +30,13 @@ const EXEC_ARG_KEY = 'exec-arg';
|
||||
|
||||
const DIALOG_GROW_TIME = 0.1;
|
||||
|
||||
const CommandCompleter = new Lang.Class({
|
||||
Name: 'CommandCompleter',
|
||||
|
||||
_init : function() {
|
||||
this._changedCount = 0;
|
||||
this._paths = GLib.getenv('PATH').split(':');
|
||||
this._paths.push(GLib.get_home_dir());
|
||||
this._valid = false;
|
||||
this._updateInProgress = false;
|
||||
this._childs = new Array(this._paths.length);
|
||||
this._monitors = new Array(this._paths.length);
|
||||
for (let i = 0; i < this._paths.length; i++) {
|
||||
this._childs[i] = [];
|
||||
let file = Gio.file_new_for_path(this._paths[i]);
|
||||
let info;
|
||||
try {
|
||||
info = file.query_info(Gio.FILE_ATTRIBUTE_STANDARD_TYPE, Gio.FileQueryInfoFlags.NONE, null);
|
||||
} catch (e) {
|
||||
// FIXME catchall
|
||||
this._paths[i] = null;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (info.get_attribute_uint32(Gio.FILE_ATTRIBUTE_STANDARD_TYPE) != Gio.FileType.DIRECTORY)
|
||||
continue;
|
||||
|
||||
this._paths[i] = file.get_path();
|
||||
this._monitors[i] = file.monitor_directory(Gio.FileMonitorFlags.NONE, null);
|
||||
if (this._monitors[i] != null) {
|
||||
this._monitors[i].connect('changed', Lang.bind(this, this._onChanged));
|
||||
}
|
||||
}
|
||||
this._paths = this._paths.filter(function(a) {
|
||||
return a != null;
|
||||
});
|
||||
this._update(0);
|
||||
},
|
||||
|
||||
update : function() {
|
||||
if (this._valid)
|
||||
return;
|
||||
this._update(0);
|
||||
},
|
||||
|
||||
_update : function(i) {
|
||||
if (i == 0 && this._updateInProgress)
|
||||
return;
|
||||
this._updateInProgress = true;
|
||||
this._changedCount = 0;
|
||||
this._i = i;
|
||||
if (i >= this._paths.length) {
|
||||
this._valid = true;
|
||||
this._updateInProgress = false;
|
||||
return;
|
||||
}
|
||||
let file = Gio.file_new_for_path(this._paths[i]);
|
||||
this._childs[this._i] = [];
|
||||
FileUtils.listDirAsync(file, Lang.bind(this, function (files) {
|
||||
for (let i = 0; i < files.length; i++) {
|
||||
this._childs[this._i].push(files[i].get_name());
|
||||
}
|
||||
this._update(this._i + 1);
|
||||
}));
|
||||
},
|
||||
|
||||
_onChanged : function(m, f, of, type) {
|
||||
if (!this._valid)
|
||||
return;
|
||||
let path = f.get_parent().get_path();
|
||||
let k = undefined;
|
||||
for (let i = 0; i < this._paths.length; i++) {
|
||||
if (this._paths[i] == path)
|
||||
k = i;
|
||||
}
|
||||
if (k === undefined) {
|
||||
return;
|
||||
}
|
||||
if (type == Gio.FileMonitorEvent.CREATED) {
|
||||
this._childs[k].push(f.get_basename());
|
||||
}
|
||||
if (type == Gio.FileMonitorEvent.DELETED) {
|
||||
this._changedCount++;
|
||||
if (this._changedCount > MAX_FILE_DELETED_BEFORE_INVALID) {
|
||||
this._valid = false;
|
||||
}
|
||||
let name = f.get_basename();
|
||||
this._childs[k] = this._childs[k].filter(function(e) {
|
||||
return e != name;
|
||||
});
|
||||
}
|
||||
if (type == Gio.FileMonitorEvent.UNMOUNTED) {
|
||||
this._childs[k] = [];
|
||||
}
|
||||
},
|
||||
|
||||
getCompletion: function(text) {
|
||||
let common = '';
|
||||
let notInit = true;
|
||||
if (!this._valid) {
|
||||
this._update(0);
|
||||
return common;
|
||||
}
|
||||
function _getCommon(s1, s2) {
|
||||
let k = 0;
|
||||
for (; k < s1.length && k < s2.length; k++) {
|
||||
if (s1[k] != s2[k])
|
||||
break;
|
||||
}
|
||||
if (k == 0)
|
||||
return '';
|
||||
return s1.substr(0, k);
|
||||
}
|
||||
function _hasPrefix(s1, prefix) {
|
||||
return s1.indexOf(prefix) == 0;
|
||||
}
|
||||
for (let i = 0; i < this._childs.length; i++) {
|
||||
for (let k = 0; k < this._childs[i].length; k++) {
|
||||
if (!_hasPrefix(this._childs[i][k], text))
|
||||
continue;
|
||||
if (notInit) {
|
||||
common = this._childs[i][k];
|
||||
notInit = false;
|
||||
}
|
||||
common = _getCommon(common, this._childs[i][k]);
|
||||
}
|
||||
}
|
||||
if (common.length)
|
||||
return common.substr(text.length);
|
||||
return common;
|
||||
}
|
||||
});
|
||||
|
||||
const RunDialog = new Lang.Class({
|
||||
Name: 'RunDialog',
|
||||
Extends: ModalDialog.ModalDialog,
|
||||
|
||||
_init : function() {
|
||||
this.parent({ styleClass: 'run-dialog' });
|
||||
this.parent({ styleClass: 'run-dialog',
|
||||
destroyOnClose: false });
|
||||
|
||||
this._lockdownSettings = new Gio.Settings({ schema: LOCKDOWN_SCHEMA });
|
||||
this._terminalSettings = new Gio.Settings({ schema: TERMINAL_SCHEMA });
|
||||
@@ -242,8 +111,6 @@ const RunDialog = new Lang.Class({
|
||||
key: Clutter.Escape }]);
|
||||
|
||||
this._pathCompleter = new Gio.FilenameCompleter();
|
||||
this._commandCompleter = new CommandCompleter();
|
||||
this._group.connect('notify::visible', Lang.bind(this._commandCompleter, this._commandCompleter.update));
|
||||
|
||||
this._history = new History.HistoryManager({ gsettingsKey: HISTORY_KEY,
|
||||
entry: this._entryText });
|
||||
@@ -259,18 +126,6 @@ const RunDialog = new Lang.Class({
|
||||
|
||||
return true;
|
||||
}
|
||||
if (symbol == Clutter.slash) {
|
||||
// Need preload data before get completion. GFilenameCompleter load content of parent directory.
|
||||
// Parent directory for /usr/include/ is /usr/. So need to add fake name('a').
|
||||
let text = o.get_text().concat('/a');
|
||||
let prefix;
|
||||
if (text.lastIndexOf(' ') == -1)
|
||||
prefix = text;
|
||||
else
|
||||
prefix = text.substr(text.lastIndexOf(' ') + 1);
|
||||
this._getCompletion(prefix);
|
||||
return false;
|
||||
}
|
||||
if (symbol == Clutter.Tab) {
|
||||
let text = o.get_text();
|
||||
let prefix;
|
||||
@@ -282,8 +137,6 @@ const RunDialog = new Lang.Class({
|
||||
if (postfix != null && postfix.length > 0) {
|
||||
o.insert_text(postfix, -1);
|
||||
o.set_cursor_position(text.length + postfix.length);
|
||||
if (postfix[postfix.length - 1] == '/')
|
||||
this._getCompletion(text + postfix + 'a');
|
||||
}
|
||||
return true;
|
||||
}
|
||||
@@ -291,11 +144,53 @@ const RunDialog = new Lang.Class({
|
||||
}));
|
||||
},
|
||||
|
||||
_getCommandCompletion: function(text) {
|
||||
function _getCommon(s1, s2) {
|
||||
if (s1 == null)
|
||||
return s2;
|
||||
|
||||
let k = 0;
|
||||
for (; k < s1.length && k < s2.length; k++) {
|
||||
if (s1[k] != s2[k])
|
||||
break;
|
||||
}
|
||||
if (k == 0)
|
||||
return '';
|
||||
return s1.substr(0, k);
|
||||
}
|
||||
|
||||
let paths = GLib.getenv('PATH').split(':');
|
||||
paths.push(GLib.get_home_dir());
|
||||
let someResults = paths.map(function(path) {
|
||||
let results = [];
|
||||
try {
|
||||
let file = Gio.File.new_for_path(path);
|
||||
let fileEnum = file.enumerate_children('standard::name', Gio.FileQueryInfoFlags.NONE, null);
|
||||
let info;
|
||||
while ((info = fileEnum.next_file(null))) {
|
||||
let name = info.get_name();
|
||||
if (name.slice(0, text.length) == text)
|
||||
results.push(name);
|
||||
}
|
||||
} catch (e if (!e.matches(Gio.IOErrorEnum, Gio.IOErrorEnum.NOT_FOUND) &&
|
||||
!e.matches(Gio.IOErrorEnum, Gio.IOErrorEnum.NOT_DIRECTORY))) {
|
||||
log(e);
|
||||
} finally {
|
||||
return results;
|
||||
}
|
||||
});
|
||||
let results = someResults.reduce(function(a, b) {
|
||||
return a.concat(b);
|
||||
}, []);
|
||||
let common = results.reduce(_getCommon, null);
|
||||
return common.substr(text.length);
|
||||
},
|
||||
|
||||
_getCompletion : function(text) {
|
||||
if (text.indexOf('/') != -1) {
|
||||
return this._pathCompleter.get_completion_suffix(text);
|
||||
} else {
|
||||
return this._commandCompleter.getCompletion(text);
|
||||
return this._getCommandCompletion(text);
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
@@ -38,11 +38,7 @@ const ARROW_DRAG_THRESHOLD = 0.1;
|
||||
const N_ARROWS = 3;
|
||||
const ARROW_ANIMATION_TIME = 0.6;
|
||||
const ARROW_ANIMATION_PEAK_OPACITY = 0.4;
|
||||
|
||||
// The distance in px that the lock screen will move to when pressing
|
||||
// a key that has no effect in the lock screen (bumping it)
|
||||
const BUMP_SIZE = 25;
|
||||
const BUMP_TIME = 0.3;
|
||||
const ARROW_IDLE_TIME = 30000; // ms
|
||||
|
||||
const SUMMARY_ICON_SIZE = 48;
|
||||
|
||||
@@ -54,7 +50,7 @@ const SUMMARY_ICON_SIZE = 48;
|
||||
// - CURTAIN_SLIDE_TIME is used when raising the shield before unlocking
|
||||
// - INITIAL_FADE_IN_TIME is used for the initial fade in at startup
|
||||
const STANDARD_FADE_TIME = 10;
|
||||
const MANUAL_FADE_TIME = 0.8;
|
||||
const MANUAL_FADE_TIME = 0.3;
|
||||
const BACKGROUND_FADE_TIME = 1.0;
|
||||
const CURTAIN_SLIDE_TIME = 0.3;
|
||||
const INITIAL_FADE_IN_TIME = 0.25;
|
||||
@@ -435,8 +431,8 @@ const ScreenShield = new Lang.Class({
|
||||
name: 'lockScreenGroup',
|
||||
visible: false,
|
||||
});
|
||||
this._lockScreenGroup.connect('key-release-event',
|
||||
Lang.bind(this, this._onLockScreenKeyRelease));
|
||||
this._lockScreenGroup.connect('key-press-event',
|
||||
Lang.bind(this, this._onLockScreenKeyPress));
|
||||
this._lockScreenGroup.connect('scroll-event',
|
||||
Lang.bind(this, this._onLockScreenScroll));
|
||||
Main.ctrlAltTabManager.addGroup(this._lockScreenGroup, _("Lock"), 'changes-prevent-symbolic');
|
||||
@@ -456,6 +452,9 @@ const ScreenShield = new Lang.Class({
|
||||
this._updateBackgrounds();
|
||||
Main.layoutManager.connect('monitors-changed', Lang.bind(this, this._updateBackgrounds));
|
||||
|
||||
this._arrowAnimationId = 0;
|
||||
this._arrowWatchId = 0;
|
||||
this._arrowActiveWatchId = 0;
|
||||
this._arrowContainer = new St.BoxLayout({ style_class: 'screen-shield-arrows',
|
||||
vertical: true,
|
||||
x_align: Clutter.ActorAlign.CENTER,
|
||||
@@ -507,14 +506,18 @@ const ScreenShield = new Lang.Class({
|
||||
this._screenSaverDBus = new ShellDBus.ScreenSaverDBus(this);
|
||||
|
||||
this._inhibitor = null;
|
||||
this._aboutToSuspend = false;
|
||||
this._loginManager = LoginManager.getLoginManager();
|
||||
this._loginManager.connect('prepare-for-sleep',
|
||||
Lang.bind(this, this._prepareForSleep));
|
||||
this._inhibitSuspend();
|
||||
|
||||
this._loginSession = this._loginManager.getCurrentSessionProxy();
|
||||
this._loginSession.connectSignal('Lock', Lang.bind(this, function() { this.lock(false); }));
|
||||
this._loginSession.connectSignal('Unlock', Lang.bind(this, function() { this.deactivate(false); }));
|
||||
this._loginManager.getCurrentSessionProxy(Lang.bind(this,
|
||||
function(sessionProxy) {
|
||||
this._loginSession = sessionProxy;
|
||||
this._loginSession.connectSignal('Lock', Lang.bind(this, function() { this.lock(false); }));
|
||||
this._loginSession.connectSignal('Unlock', Lang.bind(this, function() { this.deactivate(false); }));
|
||||
}));
|
||||
|
||||
this._settings = new Gio.Settings({ schema: SCREENSAVER_SCHEMA });
|
||||
|
||||
@@ -547,9 +550,7 @@ const ScreenShield = new Lang.Class({
|
||||
|
||||
let bgManager = new Background.BackgroundManager({ container: widget,
|
||||
monitorIndex: monitorIndex,
|
||||
effects: Meta.BackgroundEffects.BLUR | Meta.BackgroundEffects.DESATURATE,
|
||||
controlPosition: false });
|
||||
bgManager.background.saturation = 0.6;
|
||||
|
||||
this._bgManagers.push(bgManager);
|
||||
|
||||
@@ -561,6 +562,7 @@ const ScreenShield = new Lang.Class({
|
||||
this._bgManagers[i].destroy();
|
||||
|
||||
this._bgManagers = [];
|
||||
this._backgroundGroup.destroy_all_children();
|
||||
|
||||
for (let i = 0; i < Main.layoutManager.monitors.length; i++)
|
||||
this._createBackground(i);
|
||||
@@ -590,28 +592,28 @@ const ScreenShield = new Lang.Class({
|
||||
return this._isModal;
|
||||
},
|
||||
|
||||
_onLockScreenKeyRelease: function(actor, event) {
|
||||
_onLockScreenKeyPress: function(actor, event) {
|
||||
let symbol = event.get_key_symbol();
|
||||
let unichar = event.get_key_unicode();
|
||||
|
||||
// Do nothing if the lock screen is not fully shown.
|
||||
// This avoids reusing the previous (and stale) unlock
|
||||
// dialog if esc is pressed while the curtain is going
|
||||
// down after cancel.
|
||||
// Similarly, don't bump if the lock screen is not showing or is
|
||||
// animating, as the bump overrides the animation and would
|
||||
// remove any onComplete handler.
|
||||
|
||||
if (this._lockScreenState != MessageTray.State.SHOWN)
|
||||
return false;
|
||||
|
||||
if (symbol == Clutter.KEY_Escape ||
|
||||
symbol == Clutter.KEY_Return ||
|
||||
symbol == Clutter.KEY_KP_Enter) {
|
||||
this._liftShield(false, 0);
|
||||
return true;
|
||||
}
|
||||
let isEnter = (symbol == Clutter.KEY_Return || symbol == Clutter.KEY_KP_Enter);
|
||||
if (!isEnter && !(GLib.unichar_isprint(unichar) || symbol == Clutter.KEY_Escape))
|
||||
return false;
|
||||
|
||||
this._bumpLockScreen();
|
||||
this._ensureUnlockDialog(true, true);
|
||||
|
||||
if (GLib.unichar_isgraph(unichar))
|
||||
this._dialog.addCharacter(unichar);
|
||||
|
||||
this._liftShield(true, 0);
|
||||
return true;
|
||||
},
|
||||
|
||||
@@ -649,6 +651,8 @@ const ScreenShield = new Lang.Class({
|
||||
},
|
||||
|
||||
_prepareForSleep: function(loginManager, aboutToSuspend) {
|
||||
this._aboutToSuspend = aboutToSuspend;
|
||||
|
||||
if (aboutToSuspend) {
|
||||
if (!this._settings.get_boolean(LOCK_ENABLED_KEY)) {
|
||||
this._uninhibitSuspend();
|
||||
@@ -849,21 +853,6 @@ const ScreenShield = new Lang.Class({
|
||||
this._hideLockScreen(false, 0);
|
||||
},
|
||||
|
||||
_bumpLockScreen: function() {
|
||||
Tweener.removeTweens(this._lockScreenGroup);
|
||||
Tweener.addTween(this._lockScreenGroup,
|
||||
{ y: -BUMP_SIZE,
|
||||
time: BUMP_TIME / 2,
|
||||
transition: 'easeOutQuad',
|
||||
onComplete: function() {
|
||||
Tweener.addTween(this,
|
||||
{ y: 0,
|
||||
time: BUMP_TIME / 2,
|
||||
transition: 'easeInQuad' });
|
||||
}
|
||||
});
|
||||
},
|
||||
|
||||
_hideLockScreenComplete: function() {
|
||||
if (Main.sessionMode.currentMode == 'lock-screen')
|
||||
Main.sessionMode.popMode('lock-screen');
|
||||
@@ -917,14 +906,12 @@ const ScreenShield = new Lang.Class({
|
||||
|
||||
|
||||
let time = global.get_current_time();
|
||||
this._dialog.connect('loaded', Lang.bind(this, function() {
|
||||
if (!this._dialog.open(time, onPrimary)) {
|
||||
// This is kind of an impossible error: we're already modal
|
||||
// by the time we reach this...
|
||||
log('Could not open login dialog: failed to acquire grab');
|
||||
this.deactivate(true);
|
||||
}
|
||||
}));
|
||||
if (!this._dialog.open(time, onPrimary)) {
|
||||
// This is kind of an impossible error: we're already modal
|
||||
// by the time we reach this...
|
||||
log('Could not open login dialog: failed to acquire grab');
|
||||
this.deactivate(true);
|
||||
}
|
||||
|
||||
this._dialog.connect('failed', Lang.bind(this, this._onUnlockFailed));
|
||||
this._dialog.connect('unlocked', Lang.bind(this, this._onUnlockSucceded));
|
||||
@@ -990,16 +977,60 @@ const ScreenShield = new Lang.Class({
|
||||
Main.sessionMode.pushMode('lock-screen');
|
||||
},
|
||||
|
||||
_startArrowAnimation: function() {
|
||||
this._arrowActiveWatchId = 0;
|
||||
|
||||
if (!this._arrowAnimationId) {
|
||||
this._arrowAnimationId = Mainloop.timeout_add(6000, Lang.bind(this, this._animateArrows));
|
||||
this._animateArrows();
|
||||
}
|
||||
|
||||
if (!this._arrowWatchId)
|
||||
this._arrowWatchId = this.idleMonitor.add_idle_watch(ARROW_IDLE_TIME,
|
||||
Lang.bind(this, this._pauseArrowAnimation));
|
||||
},
|
||||
|
||||
_pauseArrowAnimation: function() {
|
||||
if (this._arrowAnimationId) {
|
||||
Mainloop.source_remove(this._arrowAnimationId);
|
||||
this._arrowAnimationId = 0;
|
||||
}
|
||||
|
||||
if (!this._arrowActiveWatchId)
|
||||
this._arrowActiveWatchId = this.idleMonitor.add_user_active_watch(Lang.bind(this, this._startArrowAnimation));
|
||||
},
|
||||
|
||||
_stopArrowAnimation: function() {
|
||||
if (this._arrowAnimationId) {
|
||||
Mainloop.source_remove(this._arrowAnimationId);
|
||||
this._arrowAnimationId = 0;
|
||||
}
|
||||
if (this._arrowActiveWatchId) {
|
||||
this.idleMonitor.remove_watch(this._arrowActiveWatchId);
|
||||
this._arrowActiveWatchId = 0;
|
||||
}
|
||||
if (this._arrowWatchId) {
|
||||
this.idleMonitor.remove_watch(this._arrowWatchId);
|
||||
this._arrowWatchId = 0;
|
||||
}
|
||||
},
|
||||
|
||||
_checkArrowAnimation: function() {
|
||||
let idleTime = this.idleMonitor.get_idletime();
|
||||
|
||||
if (idleTime < ARROW_IDLE_TIME)
|
||||
this._startArrowAnimation();
|
||||
else
|
||||
this._pauseArrowAnimation();
|
||||
},
|
||||
|
||||
_lockScreenShown: function() {
|
||||
if (this._dialog && !this._isGreeter) {
|
||||
this._dialog.destroy();
|
||||
this._dialog = null;
|
||||
}
|
||||
|
||||
if (this._arrowAnimationId)
|
||||
Mainloop.source_remove(this._arrowAnimationId);
|
||||
this._arrowAnimationId = Mainloop.timeout_add(6000, Lang.bind(this, this._animateArrows));
|
||||
this._animateArrows();
|
||||
this._checkArrowAnimation();
|
||||
|
||||
let motionId = global.stage.connect('captured-event', function(stage, event) {
|
||||
if (event.type() == Clutter.EventType.MOTION) {
|
||||
@@ -1021,7 +1052,8 @@ const ScreenShield = new Lang.Class({
|
||||
if (prevIsActive != this._isActive)
|
||||
this.emit('active-changed');
|
||||
|
||||
this._uninhibitSuspend();
|
||||
if (this._aboutToSuspend)
|
||||
this._uninhibitSuspend();
|
||||
|
||||
this.emit('lock-screen-shown');
|
||||
},
|
||||
@@ -1061,12 +1093,9 @@ const ScreenShield = new Lang.Class({
|
||||
this._notificationsBox = null;
|
||||
}
|
||||
|
||||
this._lockScreenContentsBox.destroy();
|
||||
this._stopArrowAnimation();
|
||||
|
||||
if (this._arrowAnimationId) {
|
||||
Mainloop.source_remove(this._arrowAnimationId);
|
||||
this._arrowAnimationId = 0;
|
||||
}
|
||||
this._lockScreenContentsBox.destroy();
|
||||
|
||||
this._hasLockScreen = false;
|
||||
},
|
||||
@@ -1178,62 +1207,3 @@ const ScreenShield = new Lang.Class({
|
||||
},
|
||||
});
|
||||
Signals.addSignalMethods(ScreenShield.prototype);
|
||||
|
||||
/* Fallback code to handle session locking using gnome-screensaver,
|
||||
in case the required GDM dependency is not there
|
||||
*/
|
||||
const ScreenShieldFallback = new Lang.Class({
|
||||
Name: 'ScreenShieldFallback',
|
||||
|
||||
_init: function() {
|
||||
Util.spawn(['gnome-screensaver']);
|
||||
|
||||
this._proxy = new Gio.DBusProxy({ g_connection: Gio.DBus.session,
|
||||
g_name: 'org.gnome.ScreenSaver',
|
||||
g_object_path: '/org/gnome/ScreenSaver',
|
||||
g_interface_name: 'org.gnome.ScreenSaver',
|
||||
g_flags: (Gio.DBusProxyFlags.DO_NOT_AUTO_START |
|
||||
Gio.DBusProxyFlags.DO_NOT_LOAD_PROPERTIES),
|
||||
});
|
||||
this._proxy.init(null);
|
||||
|
||||
this._proxy.connect('g-signal', Lang.bind(this, this._onSignal));
|
||||
this._proxy.connect('notify::g-name-owner', Lang.bind(this, this._onNameOwnerChanged));
|
||||
},
|
||||
|
||||
_onNameOwnerChanged: function(object, pspec) {
|
||||
if (this._proxy.g_name_owner)
|
||||
[this._locked] = this._proxy.call_sync('GetActive', null,
|
||||
Gio.DBusCallFlags.NONE, -1, null).deep_unpack();
|
||||
else
|
||||
this._locked = false;
|
||||
|
||||
this.emit('active-changed', this._locked);
|
||||
},
|
||||
|
||||
_onSignal: function(proxy, senderName, signalName, params) {
|
||||
if (signalName == 'ActiveChanged') {
|
||||
[this._locked] = params.deep_unpack();
|
||||
this.emit('active-changed', this._locked);
|
||||
}
|
||||
},
|
||||
|
||||
get locked() {
|
||||
return this._locked;
|
||||
},
|
||||
|
||||
lock: function() {
|
||||
this._proxy.call('Lock', null, Gio.DBusCallFlags.NONE, -1, null,
|
||||
Lang.bind(this, function(proxy, result) {
|
||||
proxy.call_finish(result);
|
||||
|
||||
this.emit('lock-screen-shown');
|
||||
}));
|
||||
},
|
||||
|
||||
unlock: function() {
|
||||
this._proxy.call('SetActive', GLib.Variant.new('(b)', false),
|
||||
Gio.DBusCallFlags.NONE, -1, null, null);
|
||||
},
|
||||
});
|
||||
Signals.addSignalMethods(ScreenShieldFallback.prototype);
|
||||
|
||||
@@ -4,6 +4,7 @@ const Clutter = imports.gi.Clutter;
|
||||
const Lang = imports.lang;
|
||||
const Gtk = imports.gi.Gtk;
|
||||
const Meta = imports.gi.Meta;
|
||||
const Signals = imports.signals;
|
||||
const St = imports.gi.St;
|
||||
const Atk = imports.gi.Atk;
|
||||
|
||||
@@ -13,6 +14,7 @@ const Main = imports.ui.main;
|
||||
const Overview = imports.ui.overview;
|
||||
const Separator = imports.ui.separator;
|
||||
const Search = imports.ui.search;
|
||||
const Util = imports.misc.util;
|
||||
|
||||
const MAX_LIST_SEARCH_RESULTS_ROWS = 3;
|
||||
const MAX_GRID_SEARCH_RESULTS_ROWS = 1;
|
||||
@@ -102,6 +104,7 @@ const ListSearchResult = new Lang.Class({
|
||||
y_fill: false,
|
||||
x_align: St.Align.START,
|
||||
y_align: St.Align.START });
|
||||
this.actor.label_actor = title;
|
||||
|
||||
if (this.metaInfo['description']) {
|
||||
let description = new St.Label({ style_class: 'list-search-result-description' });
|
||||
@@ -139,6 +142,7 @@ const GridSearchResult = new Lang.Class({
|
||||
}
|
||||
|
||||
this.actor.set_child(content);
|
||||
this.actor.label_actor = content.label_actor;
|
||||
|
||||
let draggable = DND.makeDraggable(this.actor);
|
||||
draggable.connect('drag-begin',
|
||||
@@ -227,9 +231,14 @@ const ListSearchResults = new Lang.Class({
|
||||
this._pendingClear = true;
|
||||
},
|
||||
|
||||
_keyFocusIn: function(icon) {
|
||||
this.emit('key-focus-in', icon);
|
||||
},
|
||||
|
||||
renderResults: function(metas) {
|
||||
for (let i = 0; i < metas.length; i++) {
|
||||
let display = new ListSearchResult(this.provider, metas[i], this._terms);
|
||||
display.actor.connect('key-focus-in', Lang.bind(this, this._keyFocusIn));
|
||||
this._content.add_actor(display.actor);
|
||||
}
|
||||
},
|
||||
@@ -246,6 +255,7 @@ const ListSearchResults = new Lang.Class({
|
||||
return null;
|
||||
}
|
||||
});
|
||||
Signals.addSignalMethods(ListSearchResults.prototype);
|
||||
|
||||
const GridSearchResults = new Lang.Class({
|
||||
Name: 'GridSearchResults',
|
||||
@@ -288,9 +298,14 @@ const GridSearchResults = new Lang.Class({
|
||||
this._pendingClear = true;
|
||||
},
|
||||
|
||||
_keyFocusIn: function(icon) {
|
||||
this.emit('key-focus-in', icon);
|
||||
},
|
||||
|
||||
renderResults: function(metas) {
|
||||
for (let i = 0; i < metas.length; i++) {
|
||||
let display = new GridSearchResult(this.provider, metas[i], this._terms);
|
||||
display.actor.connect('key-focus-in', Lang.bind(this, this._keyFocusIn));
|
||||
this._grid.addItem(display.actor);
|
||||
}
|
||||
},
|
||||
@@ -307,6 +322,7 @@ const GridSearchResults = new Lang.Class({
|
||||
return null;
|
||||
}
|
||||
});
|
||||
Signals.addSignalMethods(GridSearchResults.prototype);
|
||||
|
||||
const SearchResults = new Lang.Class({
|
||||
Name: 'SearchResults',
|
||||
@@ -366,6 +382,10 @@ const SearchResults = new Lang.Class({
|
||||
return false;
|
||||
},
|
||||
|
||||
_keyFocusIn: function(provider, icon) {
|
||||
Util.ensureActorVisibleInScrollView(this._scrollView, icon);
|
||||
},
|
||||
|
||||
createProviderMeta: function(provider) {
|
||||
let providerBox = new St.BoxLayout({ style_class: 'search-section',
|
||||
vertical: true });
|
||||
@@ -379,6 +399,8 @@ const SearchResults = new Lang.Class({
|
||||
resultDisplay = new GridSearchResults(provider);
|
||||
}
|
||||
|
||||
resultDisplay.connect('key-focus-in', Lang.bind(this, this._keyFocusIn));
|
||||
|
||||
let resultDisplayBin = new St.Bin({ child: resultDisplay.actor,
|
||||
x_fill: true,
|
||||
y_fill: true });
|
||||
@@ -557,6 +579,7 @@ const ProviderIcon = new Lang.Class({
|
||||
this.parent({ style_class: 'search-provider-icon',
|
||||
reactive: true,
|
||||
can_focus: true,
|
||||
accessible_name: provider.appInfo.get_name(),
|
||||
track_hover: true });
|
||||
|
||||
this._content = new St.Widget({ layout_manager: new Clutter.BinLayout() });
|
||||
|
||||
@@ -79,12 +79,13 @@ const _modes = {
|
||||
},
|
||||
|
||||
'initial-setup': {
|
||||
hasWindows: true,
|
||||
isPrimary: true,
|
||||
components: ['keyring'],
|
||||
components: ['networkAgent', 'keyring'],
|
||||
panel: {
|
||||
left: [],
|
||||
center: ['dateMenu'],
|
||||
right: ['a11yGreeter', 'keyboard', 'volume']
|
||||
center: [],
|
||||
right: ['a11yGreeter', 'keyboard', 'volume', 'battery']
|
||||
}
|
||||
},
|
||||
|
||||
@@ -158,12 +159,7 @@ function listModes() {
|
||||
const SessionMode = new Lang.Class({
|
||||
Name: 'SessionMode',
|
||||
|
||||
_init: function() {
|
||||
global.connect('notify::session-mode', Lang.bind(this, this._sync));
|
||||
this._modes = _modes;
|
||||
this._modeStack = [DEFAULT_MODE];
|
||||
this._sync();
|
||||
|
||||
init: function() {
|
||||
_getModes(Lang.bind(this, function(modes) {
|
||||
this._modes = modes;
|
||||
let primary = modes[global.session_mode] &&
|
||||
@@ -171,6 +167,8 @@ const SessionMode = new Lang.Class({
|
||||
let mode = primary ? global.session_mode : 'user';
|
||||
this._modeStack = [mode];
|
||||
this._sync();
|
||||
|
||||
this.emit('sessions-loaded');
|
||||
}));
|
||||
},
|
||||
|
||||
|
||||
@@ -97,7 +97,7 @@ const GnomeShell = new Lang.Class({
|
||||
*/
|
||||
Eval: function(code) {
|
||||
if (!global.settings.get_boolean('development-tools'))
|
||||
return [false, null];
|
||||
return [false, ''];
|
||||
|
||||
let returnValue;
|
||||
let success;
|
||||
@@ -397,7 +397,7 @@ const ScreenSaverDBus = new Lang.Class({
|
||||
if (active)
|
||||
this._screenShield.activate(true);
|
||||
else
|
||||
this._screenShield.unlock(false);
|
||||
this._screenShield.deactivate(false);
|
||||
},
|
||||
|
||||
GetActive: function() {
|
||||
|
||||
@@ -82,11 +82,6 @@ const EntryMenu = new Lang.Class({
|
||||
this.actor.grab_key_focus();
|
||||
},
|
||||
|
||||
close: function(animate) {
|
||||
this._entry.grab_key_focus();
|
||||
this.parent(animate);
|
||||
},
|
||||
|
||||
_updateCopyItem: function() {
|
||||
let selection = this._entry.clutter_text.get_selection();
|
||||
this._copyItem.setSensitive(!this._entry.clutter_text.password_char &&
|
||||
@@ -171,4 +166,10 @@ function addContextMenu(entry, params) {
|
||||
entry.connect('button-press-event', Lang.bind(null, _onButtonPressEvent, entry));
|
||||
|
||||
entry.connect('popup-menu', Lang.bind(null, _onPopup, entry));
|
||||
|
||||
entry.connect('destroy', function() {
|
||||
entry.menu.destroy();
|
||||
entry.menu = null;
|
||||
entry._menuManager = null;
|
||||
});
|
||||
}
|
||||
|
||||
@@ -337,14 +337,14 @@ const InputSourceIndicator = new Lang.Class({
|
||||
Main.wm.addKeybinding('switch-input-source',
|
||||
new Gio.Settings({ schema: "org.gnome.desktop.wm.keybindings" }),
|
||||
Meta.KeyBindingFlags.REVERSES,
|
||||
Shell.KeyBindingMode.ALL,
|
||||
Shell.KeyBindingMode.ALL & ~Shell.KeyBindingMode.MESSAGE_TRAY,
|
||||
Lang.bind(this, this._switchInputSource));
|
||||
this._keybindingActionBackward =
|
||||
Main.wm.addKeybinding('switch-input-source-backward',
|
||||
new Gio.Settings({ schema: "org.gnome.desktop.wm.keybindings" }),
|
||||
Meta.KeyBindingFlags.REVERSES |
|
||||
Meta.KeyBindingFlags.REVERSED,
|
||||
Shell.KeyBindingMode.ALL,
|
||||
Shell.KeyBindingMode.ALL & ~Shell.KeyBindingMode.MESSAGE_TRAY,
|
||||
Lang.bind(this, this._switchInputSource));
|
||||
this._settings = new Gio.Settings({ schema: DESKTOP_INPUT_SOURCES_SCHEMA });
|
||||
this._settings.connect('changed::' + KEY_CURRENT_INPUT_SOURCE, Lang.bind(this, this._currentInputSourceChanged));
|
||||
@@ -416,6 +416,11 @@ const InputSourceIndicator = new Lang.Class({
|
||||
let oldSource;
|
||||
[oldSource, this._currentSource] = [this._currentSource, newSource];
|
||||
|
||||
if (oldSource) {
|
||||
oldSource.menuItem.setOrnament(PopupMenu.Ornament.NONE);
|
||||
oldSource.indicatorLabel.hide();
|
||||
}
|
||||
|
||||
if (!newSource || (nVisibleSources < 2 && !newSource.properties)) {
|
||||
// This source index might be invalid if we weren't able
|
||||
// to build a menu item for it, so we hide ourselves since
|
||||
@@ -430,12 +435,7 @@ const InputSourceIndicator = new Lang.Class({
|
||||
|
||||
this.actor.show();
|
||||
|
||||
if (oldSource) {
|
||||
oldSource.menuItem.setShowDot(false);
|
||||
oldSource.indicatorLabel.hide();
|
||||
}
|
||||
|
||||
newSource.menuItem.setShowDot(true);
|
||||
newSource.menuItem.setOrnament(PopupMenu.Ornament.DOT);
|
||||
newSource.indicatorLabel.show();
|
||||
|
||||
this._buildPropSection(newSource.properties);
|
||||
@@ -459,6 +459,7 @@ const InputSourceIndicator = new Lang.Class({
|
||||
|
||||
this._inputSources = {};
|
||||
this._ibusSources = {};
|
||||
this._currentSource = null;
|
||||
|
||||
let inputSourcesByShortName = {};
|
||||
|
||||
@@ -487,7 +488,7 @@ const InputSourceIndicator = new Lang.Class({
|
||||
let is = new InputSource(type, id, displayName, shortName, i);
|
||||
|
||||
is.connect('activate', Lang.bind(this, function() {
|
||||
if (this._currentSource.index == is.index)
|
||||
if (this._currentSource && this._currentSource.index == is.index)
|
||||
return;
|
||||
this._settings.set_value(KEY_CURRENT_INPUT_SOURCE,
|
||||
GLib.Variant.new_uint32(is.index));
|
||||
@@ -660,7 +661,8 @@ const InputSourceIndicator = new Lang.Class({
|
||||
item.prop = prop;
|
||||
radioGroup.push(item);
|
||||
item.radioGroup = radioGroup;
|
||||
item.setShowDot(prop.get_state() == IBus.PropState.CHECKED);
|
||||
item.setOrnament(prop.get_state() == IBus.PropState.CHECKED ?
|
||||
PopupMenu.Ornament.DOT : PopupMenu.Ornament.NONE);
|
||||
item.connect('activate', Lang.bind(this, function() {
|
||||
if (item.prop.get_state() == IBus.PropState.CHECKED)
|
||||
return;
|
||||
@@ -668,12 +670,12 @@ const InputSourceIndicator = new Lang.Class({
|
||||
let group = item.radioGroup;
|
||||
for (let i = 0; i < group.length; ++i) {
|
||||
if (group[i] == item) {
|
||||
item.setShowDot(true);
|
||||
item.setOrnament(PopupMenu.Ornament.DOT);
|
||||
item.prop.set_state(IBus.PropState.CHECKED);
|
||||
this._ibusManager.activateProperty(item.prop.get_key(),
|
||||
IBus.PropState.CHECKED);
|
||||
} else {
|
||||
group[i].setShowDot(false);
|
||||
group[i].setOrnament(PopupMenu.Ornament.NONE);
|
||||
group[i].prop.set_state(IBus.PropState.UNCHECKED);
|
||||
this._ibusManager.activateProperty(group[i].prop.get_key(),
|
||||
IBus.PropState.UNCHECKED);
|
||||
@@ -703,7 +705,7 @@ const InputSourceIndicator = new Lang.Class({
|
||||
item.prop = prop;
|
||||
item.connect('activate', Lang.bind(this, function() {
|
||||
this._ibusManager.activateProperty(item.prop.get_key(),
|
||||
IBus.PropState.CHECKED);
|
||||
item.prop.get_state());
|
||||
}));
|
||||
break;
|
||||
|
||||
|
||||
@@ -5,17 +5,10 @@ const Gio = imports.gi.Gio;
|
||||
const Lang = imports.lang;
|
||||
const NetworkManager = imports.gi.NetworkManager;
|
||||
const NMClient = imports.gi.NMClient;
|
||||
const NMGtk = imports.gi.NMGtk;
|
||||
const Signals = imports.signals;
|
||||
const St = imports.gi.St;
|
||||
|
||||
// Some of the new code depends on as-yet-unreleased NM
|
||||
var NMGtk;
|
||||
try {
|
||||
NMGtk = imports.gi.NMGtk;
|
||||
} catch(e) {
|
||||
NMGtk = null;
|
||||
}
|
||||
|
||||
const Main = imports.ui.main;
|
||||
const PanelMenu = imports.ui.panelMenu;
|
||||
const PopupMenu = imports.ui.popupMenu;
|
||||
@@ -34,7 +27,6 @@ const NMConnectionCategory = {
|
||||
};
|
||||
|
||||
const NMAccessPointSecurity = {
|
||||
UNKNOWN: 0,
|
||||
NONE: 1,
|
||||
WEP: 2,
|
||||
WPA_PSK: 3,
|
||||
@@ -52,20 +44,6 @@ const NM80211ApSecurityFlags = NetworkManager['80211ApSecurityFlags'];
|
||||
// (the remaining are placed into More…)
|
||||
const NUM_VISIBLE_NETWORKS = 5;
|
||||
|
||||
function macToArray(string) {
|
||||
return string.split(':').map(function(el) {
|
||||
return parseInt(el, 16);
|
||||
});
|
||||
}
|
||||
|
||||
function macCompare(one, two) {
|
||||
for (let i = 0; i < 6; i++) {
|
||||
if (one[i] != two[i])
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
function ssidCompare(one, two) {
|
||||
if (!one || !two)
|
||||
return false;
|
||||
@@ -130,8 +108,7 @@ const NMNetworkMenuItem = new Lang.Class({
|
||||
this._icons.add_actor(this._signalIcon);
|
||||
|
||||
this._secureIcon = new St.Icon({ style_class: 'popup-menu-icon' });
|
||||
if (this.bestAP._secType != NMAccessPointSecurity.UNKNOWN &&
|
||||
this.bestAP._secType != NMAccessPointSecurity.NONE)
|
||||
if (this.bestAP._secType != NMAccessPointSecurity.NONE)
|
||||
this._secureIcon.icon_name = 'network-wireless-encrypted-symbolic';
|
||||
this._icons.add_actor(this._secureIcon);
|
||||
},
|
||||
@@ -153,18 +130,12 @@ const NMWirelessSectionTitleMenuItem = new Lang.Class({
|
||||
Name: 'NMWirelessSectionTitleMenuItem',
|
||||
Extends: PopupMenu.PopupSwitchMenuItem,
|
||||
|
||||
_init: function(client, property, title, params) {
|
||||
params = params || { };
|
||||
params.style_class = 'popup-subtitle-menu-item';
|
||||
this.parent(title, false, params);
|
||||
_init: function(client) {
|
||||
this.parent(_("Wi-Fi"), false, { style_class: 'popup-subtitle-menu-item' });
|
||||
|
||||
this._client = client;
|
||||
this._property = property + '_enabled';
|
||||
this._propertyHardware = property + '_hardware_enabled';
|
||||
this._setEnabledFunc = property + '_set_enabled';
|
||||
|
||||
this._client.connect('notify::' + property + '-enabled', Lang.bind(this, this._propertyChanged));
|
||||
this._client.connect('notify::' + property + '-hardware-enabled', Lang.bind(this, this._propertyChanged));
|
||||
this._client.connect('notify::wireless-enabled', Lang.bind(this, this._propertyChanged));
|
||||
this._client.connect('notify::wireless-hardware-enabled', Lang.bind(this, this._propertyChanged));
|
||||
|
||||
this._propertyChanged();
|
||||
},
|
||||
@@ -186,12 +157,12 @@ const NMWirelessSectionTitleMenuItem = new Lang.Class({
|
||||
activate: function(event) {
|
||||
this.parent(event);
|
||||
|
||||
this._client[this._setEnabledFunc](this._switch.state);
|
||||
this._client.wireless_set_enabled(this._switch.state);
|
||||
},
|
||||
|
||||
_propertyChanged: function() {
|
||||
this._softwareEnabled = this._client[this._property];
|
||||
this._hardwareEnabled = this._client[this._propertyHardware];
|
||||
this._softwareEnabled = this._client.wireless_enabled;
|
||||
this._hardwareEnabled = this._client.wireless_hardware_enabled;
|
||||
|
||||
let enabled = this._softwareEnabled && this._hardwareEnabled;
|
||||
this.setToggleState(enabled);
|
||||
@@ -315,7 +286,6 @@ const NMDevice = new Lang.Class({
|
||||
|
||||
this._activeConnection = null;
|
||||
this._activeConnectionItem = null;
|
||||
this._autoConnectionItem = null;
|
||||
this._overflowItem = null;
|
||||
|
||||
this.statusItem = new PopupMenu.PopupSwitchMenuItem('', this.connected, { style_class: 'popup-subtitle-menu-item' });
|
||||
@@ -402,13 +372,9 @@ const NMDevice = new Lang.Class({
|
||||
},
|
||||
|
||||
_activateAutomaticConnection: function() {
|
||||
let connection = this._createAutomaticConnection();
|
||||
if (connection) {
|
||||
this._client.add_and_activate_connection(connection, this.device, null, null);
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
let connection = new NetworkManager.Connection();
|
||||
this._client.add_and_activate_connection(connection, this.device, null, null);
|
||||
return true;
|
||||
},
|
||||
|
||||
get connected() {
|
||||
@@ -502,11 +468,6 @@ const NMDevice = new Lang.Class({
|
||||
this.statusItem.label.text = this.device._description;
|
||||
},
|
||||
|
||||
// protected
|
||||
_createAutomaticConnection: function() {
|
||||
throw new TypeError('Invoking pure virtual function NMDevice.createAutomaticConnection');
|
||||
},
|
||||
|
||||
_queueCreateSection: function() {
|
||||
if (this._deferredWorkId) {
|
||||
this._clearSection();
|
||||
@@ -517,7 +478,6 @@ const NMDevice = new Lang.Class({
|
||||
_clearSection: function() {
|
||||
// Clear everything
|
||||
this.section.removeAll();
|
||||
this._autoConnectionItem = null;
|
||||
this._activeConnectionItem = null;
|
||||
this._overflowItem = null;
|
||||
for (let i = 0; i < this._connections.length; i++) {
|
||||
@@ -556,14 +516,6 @@ const NMDevice = new Lang.Class({
|
||||
} else
|
||||
this.section.addMenuItem(obj.item);
|
||||
}
|
||||
} else if (this._autoConnectionName) {
|
||||
this._autoConnectionItem = new PopupMenu.PopupMenuItem(this._autoConnectionName);
|
||||
this._autoConnectionItem.connect('activate', Lang.bind(this, function() {
|
||||
let connection = this._createAutomaticConnection();
|
||||
if (connection)
|
||||
this._client.add_and_activate_connection(connection, this.device, null, null);
|
||||
}));
|
||||
this.section.addMenuItem(this._autoConnectionItem);
|
||||
}
|
||||
},
|
||||
|
||||
@@ -588,7 +540,7 @@ const NMDevice = new Lang.Class({
|
||||
title = _("Connected (private)");
|
||||
}
|
||||
this._activeConnectionItem = new PopupMenu.PopupMenuItem(title, { reactive: false });
|
||||
this._activeConnectionItem.setShowDot(true);
|
||||
this._activeConnectionItem.setOrnament(PopupMenu.Ornament.DOT);
|
||||
},
|
||||
|
||||
_deviceStateChanged: function(device, newstate, oldstate, reason) {
|
||||
@@ -665,24 +617,10 @@ const NMDeviceWired = new Lang.Class({
|
||||
|
||||
_init: function(client, device, connections) {
|
||||
device._description = _("Wired");
|
||||
this._autoConnectionName = _("Auto Ethernet");
|
||||
this.category = NMConnectionCategory.WIRED;
|
||||
|
||||
this.parent(client, device, connections);
|
||||
},
|
||||
|
||||
_createAutomaticConnection: function() {
|
||||
let connection = new NetworkManager.Connection();
|
||||
let uuid = NetworkManager.utils_uuid_generate();
|
||||
connection.add_setting(new NetworkManager.SettingWired());
|
||||
connection.add_setting(new NetworkManager.SettingConnection({
|
||||
uuid: uuid,
|
||||
id: this._autoConnectionName,
|
||||
type: NetworkManager.SETTING_WIRED_SETTING_NAME,
|
||||
autoconnect: true
|
||||
}));
|
||||
return connection;
|
||||
}
|
||||
});
|
||||
|
||||
const NMDeviceModem = new Lang.Class({
|
||||
@@ -723,13 +661,10 @@ const NMDeviceModem = new Lang.Class({
|
||||
this._connectionType = NetworkManager.SETTING_GSM_SETTING_NAME;
|
||||
}
|
||||
|
||||
if (is_wwan) {
|
||||
if (is_wwan)
|
||||
this.category = NMConnectionCategory.WWAN;
|
||||
this._autoConnectionName = _("Auto broadband");
|
||||
} else {
|
||||
else
|
||||
this.category = NMConnectionCategory.WIRED;
|
||||
this._autoConnectionName = _("Auto dial-up");
|
||||
}
|
||||
|
||||
if (this.mobileDevice) {
|
||||
this._operatorNameId = this.mobileDevice.connect('notify::operator-name', Lang.bind(this, function() {
|
||||
@@ -824,50 +759,20 @@ const NMDeviceBluetooth = new Lang.Class({
|
||||
|
||||
_init: function(client, device, connections) {
|
||||
device._description = _("Bluetooth");
|
||||
this._autoConnectionName = this._makeConnectionName(device);
|
||||
device.connect('notify::name', Lang.bind(this, this._updateAutoConnectionName));
|
||||
|
||||
this.category = NMConnectionCategory.WWAN;
|
||||
|
||||
this.parent(client, device, connections);
|
||||
},
|
||||
|
||||
_createAutomaticConnection: function() {
|
||||
let connection = new NetworkManager.Connection;
|
||||
let uuid = NetworkManager.utils_uuid_generate();
|
||||
connection.add_setting(new NetworkManager.SettingBluetooth);
|
||||
connection.add_setting(new NetworkManager.SettingConnection({
|
||||
uuid: uuid,
|
||||
id: this._autoConnectionName,
|
||||
type: NetworkManager.SETTING_BLUETOOTH_SETTING_NAME,
|
||||
autoconnect: false
|
||||
}));
|
||||
return connection;
|
||||
},
|
||||
|
||||
_activateAutomaticConnection: function() {
|
||||
// FIXME: DUN devices are configured like modems, so
|
||||
// we need to spawn the mobile wizard
|
||||
// We need to spawn the mobile wizard
|
||||
// but the network panel doesn't support bluetooth at the moment
|
||||
// so we just create an empty connection and hope
|
||||
// that this phone supports PAN
|
||||
|
||||
return this.parent();
|
||||
},
|
||||
|
||||
_makeConnectionName: function(device) {
|
||||
let name = device.name;
|
||||
if (name)
|
||||
return _("Auto %s").format(name);
|
||||
else
|
||||
return _("Auto bluetooth");
|
||||
},
|
||||
|
||||
_updateAutoConnectionName: function() {
|
||||
this._autoConnectionName = this._makeConnectionName(this.device);
|
||||
|
||||
this._queueCreateSection();
|
||||
this._updateStatusItem();
|
||||
}
|
||||
});
|
||||
|
||||
@@ -903,20 +808,20 @@ const NMDeviceWireless = new Lang.Class({
|
||||
}
|
||||
|
||||
let pos = this._findNetwork(ap);
|
||||
let obj;
|
||||
let network;
|
||||
if (pos != -1) {
|
||||
obj = this._networks[pos];
|
||||
obj.accessPoints.push(ap);
|
||||
network = this._networks[pos];
|
||||
network.accessPoints.push(ap);
|
||||
} else {
|
||||
obj = { ssid: ap.get_ssid(),
|
||||
mode: ap.mode,
|
||||
security: this._getApSecurityType(ap),
|
||||
connections: [ ],
|
||||
item: null,
|
||||
accessPoints: [ ap ]
|
||||
network = { ssid: ap.get_ssid(),
|
||||
mode: ap.mode,
|
||||
security: this._getApSecurityType(ap),
|
||||
connections: [ ],
|
||||
item: null,
|
||||
accessPoints: [ ap ]
|
||||
};
|
||||
obj.ssidText = ssidToLabel(obj.ssid);
|
||||
this._networks.push(obj);
|
||||
network.ssidText = ssidToLabel(network.ssid);
|
||||
this._networks.push(network);
|
||||
}
|
||||
ap._updateId = ap.connect('notify::strength', Lang.bind(this, this._onApStrengthChanged));
|
||||
|
||||
@@ -924,8 +829,8 @@ const NMDeviceWireless = new Lang.Class({
|
||||
for (let j = 0; j < validConnections.length; j++) {
|
||||
let connection = validConnections[j];
|
||||
if (ap.connection_valid(connection) &&
|
||||
obj.connections.indexOf(connection) == -1) {
|
||||
obj.connections.push(connection);
|
||||
network.connections.indexOf(connection) == -1) {
|
||||
network.connections.push(connection);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -934,16 +839,7 @@ const NMDeviceWireless = new Lang.Class({
|
||||
for (let i = 0; i < this._networks.length; i++)
|
||||
sortAccessPoints(this._networks[i].accessPoints);
|
||||
|
||||
if (this.device.active_access_point) {
|
||||
let networkPos = this._findNetwork(this.device.active_access_point);
|
||||
|
||||
if (networkPos == -1) // the connected access point is invisible
|
||||
this._activeNetwork = null;
|
||||
else
|
||||
this._activeNetwork = this._networks[networkPos];
|
||||
} else {
|
||||
this._activeNetwork = null;
|
||||
}
|
||||
this._activeApChanged();
|
||||
this._networks.sort(this._networkSortFunction);
|
||||
|
||||
this._apChangedId = device.connect('notify::active-access-point', Lang.bind(this, this._activeApChanged));
|
||||
@@ -1090,9 +986,9 @@ const NMDeviceWireless = new Lang.Class({
|
||||
|
||||
_findExistingNetwork: function(accessPoint) {
|
||||
for (let i = 0; i < this._networks.length; i++) {
|
||||
let apObj = this._networks[i];
|
||||
for (let j = 0; j < apObj.accessPoints.length; j++) {
|
||||
if (apObj.accessPoints[j] == accessPoint)
|
||||
let network = this._networks[i];
|
||||
for (let j = 0; j < network.accessPoints.length; j++) {
|
||||
if (network.accessPoints[j] == accessPoint)
|
||||
return { network: i, ap: j };
|
||||
}
|
||||
}
|
||||
@@ -1140,30 +1036,30 @@ const NMDeviceWireless = new Lang.Class({
|
||||
}
|
||||
|
||||
let pos = this._findNetwork(accessPoint);
|
||||
let apObj;
|
||||
let network;
|
||||
let needsupdate = false;
|
||||
|
||||
if (pos != -1) {
|
||||
apObj = this._networks[pos];
|
||||
if (apObj.accessPoints.indexOf(accessPoint) != -1) {
|
||||
network = this._networks[pos];
|
||||
if (network.accessPoints.indexOf(accessPoint) != -1) {
|
||||
log('Access point was already seen, not adding again');
|
||||
return;
|
||||
}
|
||||
|
||||
Util.insertSorted(apObj.accessPoints, accessPoint, function(one, two) {
|
||||
Util.insertSorted(network.accessPoints, accessPoint, function(one, two) {
|
||||
return two.strength - one.strength;
|
||||
});
|
||||
if (apObj.item)
|
||||
apObj.item.updateBestAP(apObj.accessPoints[0]);
|
||||
if (network.item)
|
||||
network.item.updateBestAP(network.accessPoints[0]);
|
||||
} else {
|
||||
apObj = { ssid: accessPoint.get_ssid(),
|
||||
mode: accessPoint.mode,
|
||||
security: this._getApSecurityType(accessPoint),
|
||||
connections: [ ],
|
||||
item: null,
|
||||
accessPoints: [ accessPoint ]
|
||||
};
|
||||
apObj.ssidText = ssidToLabel(apObj.ssid);
|
||||
network = { ssid: accessPoint.get_ssid(),
|
||||
mode: accessPoint.mode,
|
||||
security: this._getApSecurityType(accessPoint),
|
||||
connections: [ ],
|
||||
item: null,
|
||||
accessPoints: [ accessPoint ]
|
||||
};
|
||||
network.ssidText = ssidToLabel(network.ssid);
|
||||
}
|
||||
accessPoint._updateId = accessPoint.connect('notify::strength', Lang.bind(this, this._onApStrengthChanged));
|
||||
|
||||
@@ -1171,14 +1067,14 @@ const NMDeviceWireless = new Lang.Class({
|
||||
for (let i = 0; i < this._connections.length; i++) {
|
||||
let connection = this._connections[i].connection;
|
||||
if (accessPoint.connection_valid(connection) &&
|
||||
apObj.connections.indexOf(connection) == -1) {
|
||||
apObj.connections.push(connection);
|
||||
network.connections.indexOf(connection) == -1) {
|
||||
network.connections.push(connection);
|
||||
}
|
||||
}
|
||||
|
||||
if (pos != -1)
|
||||
this._networks.splice(pos, 1);
|
||||
let newPos = Util.insertSorted(this._networks, apObj, this._networkSortFunction);
|
||||
let newPos = Util.insertSorted(this._networks, network, this._networkSortFunction);
|
||||
|
||||
// Queue an update of the UI if we changed the order
|
||||
if (newPos != pos)
|
||||
@@ -1198,28 +1094,28 @@ const NMDeviceWireless = new Lang.Class({
|
||||
return;
|
||||
}
|
||||
|
||||
let apObj = this._networks[res.network];
|
||||
apObj.accessPoints.splice(res.ap, 1);
|
||||
let network = this._networks[res.network];
|
||||
network.accessPoints.splice(res.ap, 1);
|
||||
|
||||
if (apObj.accessPoints.length == 0) {
|
||||
if (this._activeNetwork == apObj)
|
||||
if (network.accessPoints.length == 0) {
|
||||
if (this._activeNetwork == network)
|
||||
this._activeNetwork = null;
|
||||
|
||||
if (apObj.item)
|
||||
apObj.item.destroy();
|
||||
if (network.item)
|
||||
network.item.destroy();
|
||||
|
||||
if (this._overflowItem) {
|
||||
if (!apObj.isMore) {
|
||||
if (!network.isMore) {
|
||||
// we removed an item in the main menu, and we have a more submenu
|
||||
// we need to extract the first item in more and move it to the submenu
|
||||
|
||||
let item = this._overflowItem.menu.firstMenuItem;
|
||||
if (item && item._apObj) {
|
||||
if (item && item._network) {
|
||||
item.destroy();
|
||||
// clear the cycle, and allow the construction of the new item
|
||||
item._apObj.item = null;
|
||||
item._network.item = null;
|
||||
|
||||
this._createNetworkItem(item._apObj, NUM_VISIBLE_NETWORKS-1);
|
||||
this._createNetworkItem(item._network, NUM_VISIBLE_NETWORKS-1);
|
||||
} else {
|
||||
log('The more... menu was existing and empty! This should not happen');
|
||||
}
|
||||
@@ -1238,14 +1134,14 @@ const NMDeviceWireless = new Lang.Class({
|
||||
let okPrev = true, okNext = true;
|
||||
|
||||
if (res.network > 0)
|
||||
okPrev = this._networkSortFunction(this._networks[res.network - 1], apObj) >= 0;
|
||||
okPrev = this._networkSortFunction(this._networks[res.network - 1], network) >= 0;
|
||||
if (res.network < this._networks.length-1)
|
||||
okNext = this._networkSortFunction(this._networks[res.network + 1], apObj) <= 0;
|
||||
okNext = this._networkSortFunction(this._networks[res.network + 1], network) <= 0;
|
||||
|
||||
if (!okPrev || !okNext)
|
||||
this._queueCreateSection();
|
||||
else if (apObj.item)
|
||||
apObj.item.updateBestAP(apObj.accessPoints[0]);
|
||||
else if (network.item)
|
||||
network.item.updateBestAP(network.accessPoints[0]);
|
||||
}
|
||||
},
|
||||
|
||||
@@ -1284,20 +1180,20 @@ const NMDeviceWireless = new Lang.Class({
|
||||
|
||||
let forceupdate = false;
|
||||
for (let i = 0; i < this._networks.length; i++) {
|
||||
let apObj = this._networks[i];
|
||||
let connections = apObj.connections;
|
||||
let network = this._networks[i];
|
||||
let connections = network.connections;
|
||||
for (let k = 0; k < connections.length; k++) {
|
||||
if (connections[k].get_uuid() == connection.get_uuid()) {
|
||||
// remove the connection from the access point group
|
||||
connections.splice(k);
|
||||
connections.splice(k, 1);
|
||||
forceupdate = forceupdate || connections.length == 0;
|
||||
|
||||
if (forceupdate)
|
||||
break;
|
||||
|
||||
if (apObj.item) {
|
||||
if (apObj.item instanceof PopupMenu.PopupSubMenuMenuItem) {
|
||||
let items = apObj.item.menu._getMenuItems();
|
||||
if (network.item) {
|
||||
if (network.item instanceof PopupMenu.PopupSubMenuMenuItem) {
|
||||
let items = network.item.menu._getMenuItems();
|
||||
if (items.length == 2) {
|
||||
// we need to update the connection list to convert this to a normal item
|
||||
forceupdate = true;
|
||||
@@ -1310,8 +1206,8 @@ const NMDeviceWireless = new Lang.Class({
|
||||
}
|
||||
}
|
||||
} else {
|
||||
apObj.item.destroy();
|
||||
apObj.item = null;
|
||||
network.item.destroy();
|
||||
network.item = null;
|
||||
}
|
||||
}
|
||||
break;
|
||||
@@ -1337,13 +1233,13 @@ const NMDeviceWireless = new Lang.Class({
|
||||
// find an appropriate access point
|
||||
let forceupdate = false;
|
||||
for (let i = 0; i < this._networks.length; i++) {
|
||||
let apObj = this._networks[i];
|
||||
let network = this._networks[i];
|
||||
|
||||
// Check if connection is valid for any of these access points
|
||||
for (let k = 0; k < apObj.accessPoints.length; k++) {
|
||||
let ap = apObj.accessPoints[k];
|
||||
for (let k = 0; k < network.accessPoints.length; k++) {
|
||||
let ap = network.accessPoints[k];
|
||||
if (ap.connection_valid(connection)) {
|
||||
apObj.connections.push(connection);
|
||||
network.connections.push(connection);
|
||||
// this potentially changes the sorting order
|
||||
forceupdate = true;
|
||||
break;
|
||||
@@ -1364,55 +1260,30 @@ const NMDeviceWireless = new Lang.Class({
|
||||
else
|
||||
title = _("Connected (private)");
|
||||
|
||||
if (this._activeNetwork)
|
||||
this._activeConnectionItem = new NMNetworkMenuItem(this.device.active_access_point, undefined,
|
||||
{ reactive: false });
|
||||
else
|
||||
this._activeConnectionItem = new PopupMenu.PopupImageMenuItem(title,
|
||||
'network-wireless-connected-symbolic',
|
||||
{ reactive: false });
|
||||
this._activeConnectionItem.setShowDot(true);
|
||||
this._activeConnectionItem = new NMNetworkMenuItem(this.device.active_access_point, undefined,
|
||||
{ reactive: false });
|
||||
this._activeConnectionItem.setOrnament(PopupMenu.Ornament.DOT);
|
||||
},
|
||||
|
||||
_createAutomaticConnection: function(apObj) {
|
||||
let name;
|
||||
let ssid = NetworkManager.utils_ssid_to_utf8(apObj.ssid);
|
||||
if (ssid) {
|
||||
/* TRANSLATORS: this the automatic wireless connection name (including the network name) */
|
||||
name = _("Auto %s").format(ssid);
|
||||
} else
|
||||
name = _("Auto wireless");
|
||||
|
||||
let connection = new NetworkManager.Connection();
|
||||
connection.add_setting(new NetworkManager.SettingWireless());
|
||||
connection.add_setting(new NetworkManager.SettingConnection({
|
||||
id: name,
|
||||
autoconnect: true, // NetworkManager will know to ignore this if appropriate
|
||||
uuid: NetworkManager.utils_uuid_generate(),
|
||||
type: NetworkManager.SETTING_WIRELESS_SETTING_NAME
|
||||
}));
|
||||
return connection;
|
||||
},
|
||||
|
||||
_createNetworkItem: function(apObj, position) {
|
||||
if(!apObj.accessPoints || apObj.accessPoints.length == 0) {
|
||||
_createNetworkItem: function(network, position) {
|
||||
if(!network.accessPoints || network.accessPoints.length == 0) {
|
||||
// this should not happen, but I have no idea why it happens
|
||||
return;
|
||||
}
|
||||
|
||||
if(apObj.connections.length > 0) {
|
||||
if (apObj.connections.length == 1) {
|
||||
apObj.item = this._createAPItem(apObj.connections[0], apObj, false);
|
||||
if(network.connections.length > 0) {
|
||||
if (network.connections.length == 1) {
|
||||
network.item = this._createAPItem(network.connections[0], network, false);
|
||||
} else {
|
||||
let title = apObj.ssidText;
|
||||
apObj.item = new PopupMenu.PopupSubMenuMenuItem(title);
|
||||
for (let i = 0; i < apObj.connections.length; i++)
|
||||
apObj.item.menu.addMenuItem(this._createAPItem(apObj.connections[i], apObj, true));
|
||||
let title = network.ssidText;
|
||||
network.item = new PopupMenu.PopupSubMenuMenuItem(title);
|
||||
for (let i = 0; i < network.connections.length; i++)
|
||||
network.item.menu.addMenuItem(this._createAPItem(network.connections[i], network, true));
|
||||
}
|
||||
} else {
|
||||
apObj.item = new NMNetworkMenuItem(apObj.accessPoints[0]);
|
||||
apObj.item.connect('activate', Lang.bind(this, function() {
|
||||
let accessPoints = apObj.accessPoints;
|
||||
network.item = new NMNetworkMenuItem(network.accessPoints[0]);
|
||||
network.item.connect('activate', Lang.bind(this, function() {
|
||||
let accessPoints = network.accessPoints;
|
||||
if ( (accessPoints[0]._secType == NMAccessPointSecurity.WPA2_ENT)
|
||||
|| (accessPoints[0]._secType == NMAccessPointSecurity.WPA_ENT)) {
|
||||
// 802.1x-enabled APs require further configuration, so they're
|
||||
@@ -1420,23 +1291,23 @@ const NMDeviceWireless = new Lang.Class({
|
||||
Util.spawn(['gnome-control-center', 'network', 'connect-8021x-wifi',
|
||||
this.device.get_path(), accessPoints[0].dbus_path]);
|
||||
} else {
|
||||
let connection = this._createAutomaticConnection(apObj);
|
||||
let connection = new NetworkManager.Connection();
|
||||
this._client.add_and_activate_connection(connection, this.device, accessPoints[0].dbus_path, null)
|
||||
}
|
||||
}));
|
||||
}
|
||||
apObj.item._apObj = apObj;
|
||||
network.item._network = network;
|
||||
|
||||
if (position < NUM_VISIBLE_NETWORKS) {
|
||||
apObj.isMore = false;
|
||||
this.section.addMenuItem(apObj.item, position);
|
||||
network.isMore = false;
|
||||
this.section.addMenuItem(network.item, position);
|
||||
} else {
|
||||
if (!this._overflowItem) {
|
||||
this._overflowItem = new PopupMenu.PopupSubMenuMenuItem(_("More…"));
|
||||
this.section.addMenuItem(this._overflowItem);
|
||||
}
|
||||
this._overflowItem.menu.addMenuItem(apObj.item, position - NUM_VISIBLE_NETWORKS);
|
||||
apObj.isMore = true;
|
||||
this._overflowItem.menu.addMenuItem(network.item, position - NUM_VISIBLE_NETWORKS);
|
||||
network.isMore = true;
|
||||
}
|
||||
},
|
||||
|
||||
@@ -1452,13 +1323,13 @@ const NMDeviceWireless = new Lang.Class({
|
||||
let activeOffset = this._activeConnectionItem ? 1 : 0;
|
||||
|
||||
for(let j = 0; j < this._networks.length; j++) {
|
||||
let apObj = this._networks[j];
|
||||
if (apObj == this._activeNetwork) {
|
||||
let network = this._networks[j];
|
||||
if (network == this._activeNetwork) {
|
||||
activeOffset--;
|
||||
continue;
|
||||
}
|
||||
|
||||
this._createNetworkItem(apObj, j + activeOffset);
|
||||
this._createNetworkItem(network, j + activeOffset);
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1680,11 +1551,9 @@ const NMApplet = new Lang.Class({
|
||||
|
||||
// Virtual device types
|
||||
this._vtypes = { };
|
||||
if (NMGtk) {
|
||||
this._vtypes[NetworkManager.SETTING_VLAN_SETTING_NAME] = NMDeviceVirtual;
|
||||
this._vtypes[NetworkManager.SETTING_BOND_SETTING_NAME] = NMDeviceVirtual;
|
||||
this._vtypes[NetworkManager.SETTING_BRIDGE_SETTING_NAME] = NMDeviceVirtual;
|
||||
}
|
||||
this._vtypes[NetworkManager.SETTING_VLAN_SETTING_NAME] = NMDeviceVirtual;
|
||||
this._vtypes[NetworkManager.SETTING_BOND_SETTING_NAME] = NMDeviceVirtual;
|
||||
this._vtypes[NetworkManager.SETTING_BRIDGE_SETTING_NAME] = NMDeviceVirtual;
|
||||
|
||||
// Connection types
|
||||
this._ctypes = { };
|
||||
@@ -1696,11 +1565,9 @@ const NMApplet = new Lang.Class({
|
||||
this._ctypes[NetworkManager.SETTING_CDMA_SETTING_NAME] = NMConnectionCategory.WWAN;
|
||||
this._ctypes[NetworkManager.SETTING_GSM_SETTING_NAME] = NMConnectionCategory.WWAN;
|
||||
this._ctypes[NetworkManager.SETTING_INFINIBAND_SETTING_NAME] = NMConnectionCategory.WIRED;
|
||||
if (NMGtk) {
|
||||
this._ctypes[NetworkManager.SETTING_VLAN_SETTING_NAME] = NMConnectionCategory.VIRTUAL;
|
||||
this._ctypes[NetworkManager.SETTING_BOND_SETTING_NAME] = NMConnectionCategory.VIRTUAL;
|
||||
this._ctypes[NetworkManager.SETTING_BRIDGE_SETTING_NAME] = NMConnectionCategory.VIRTUAL;
|
||||
}
|
||||
this._ctypes[NetworkManager.SETTING_VLAN_SETTING_NAME] = NMConnectionCategory.VIRTUAL;
|
||||
this._ctypes[NetworkManager.SETTING_BOND_SETTING_NAME] = NMConnectionCategory.VIRTUAL;
|
||||
this._ctypes[NetworkManager.SETTING_BRIDGE_SETTING_NAME] = NMConnectionCategory.VIRTUAL;
|
||||
this._ctypes[NetworkManager.SETTING_VPN_SETTING_NAME] = NMConnectionCategory.VPN;
|
||||
|
||||
NMClient.Client.new_async(null, Lang.bind(this, this._clientGot));
|
||||
@@ -1768,7 +1635,7 @@ const NMApplet = new Lang.Class({
|
||||
this._devices.wireless = {
|
||||
section: new PopupMenu.PopupMenuSection(),
|
||||
devices: [ ],
|
||||
item: this._makeToggleItem('wireless', _("Wi-Fi"))
|
||||
item: this._makeWirelessToggle()
|
||||
};
|
||||
this._devices.wireless.section.addMenuItem(this._devices.wireless.item);
|
||||
this._devices.wireless.section.actor.hide();
|
||||
@@ -1815,14 +1682,14 @@ const NMApplet = new Lang.Class({
|
||||
}
|
||||
},
|
||||
|
||||
_makeToggleItem: function(type, title) {
|
||||
let item = new NMWirelessSectionTitleMenuItem(this._client, type, title);
|
||||
_makeWirelessToggle: function() {
|
||||
let item = new NMWirelessSectionTitleMenuItem(this._client);
|
||||
item.connect('enabled-changed', Lang.bind(this, function(item, enabled) {
|
||||
let devices = this._devices[type].devices;
|
||||
let devices = this._devices.wireless.devices;
|
||||
devices.forEach(function(dev) {
|
||||
dev.setEnabled(enabled);
|
||||
});
|
||||
this._syncSectionTitle(type);
|
||||
this._syncSectionTitle('wireless');
|
||||
}));
|
||||
return item;
|
||||
},
|
||||
@@ -1900,19 +1767,12 @@ const NMApplet = new Lang.Class({
|
||||
},
|
||||
|
||||
_syncDeviceNames: function() {
|
||||
if (NMGtk) {
|
||||
let names = NMGtk.utils_disambiguate_device_names(this._nmDevices);
|
||||
for (let i = 0; i < this._nmDevices.length; i++) {
|
||||
let device = this._nmDevices[i];
|
||||
device._description = names[i];
|
||||
if (device._delegate)
|
||||
device._delegate.syncDescription();
|
||||
}
|
||||
} else {
|
||||
for (let i = 0; i < this._nmDevices.length; i++) {
|
||||
let device = this._nmDevices[i];
|
||||
let names = NMGtk.utils_disambiguate_device_names(this._nmDevices);
|
||||
for (let i = 0; i < this._nmDevices.length; i++) {
|
||||
let device = this._nmDevices[i];
|
||||
device._description = names[i];
|
||||
if (device._delegate)
|
||||
device._delegate.syncDescription();
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
@@ -1948,11 +1808,6 @@ const NMApplet = new Lang.Class({
|
||||
wrapper._deviceStateChangedId = wrapper.connect('state-changed', Lang.bind(this, function(dev) {
|
||||
this._syncSectionTitle(dev.category);
|
||||
}));
|
||||
wrapper._destroyId = wrapper.connect('destroy', function(wrapper) {
|
||||
wrapper.disconnect(wrapper._activationFailedId);
|
||||
wrapper.disconnect(wrapper._deviceStateChangedId);
|
||||
wrapper.disconnect(wrapper._destroyId);
|
||||
});
|
||||
|
||||
let section = this._devices[wrapper.category].section;
|
||||
section.addMenuItem(wrapper.statusItem);
|
||||
@@ -1984,6 +1839,8 @@ const NMApplet = new Lang.Class({
|
||||
},
|
||||
|
||||
_removeDeviceWrapper: function(wrapper) {
|
||||
wrapper.disconnect(wrapper._activationFailedId);
|
||||
wrapper.disconnect(wrapper._deviceStateChangedId);
|
||||
wrapper.destroy();
|
||||
|
||||
let devices = this._devices[wrapper.category].devices;
|
||||
@@ -2134,25 +1991,7 @@ const NMApplet = new Lang.Class({
|
||||
return false;
|
||||
},
|
||||
|
||||
_readConnections: function() {
|
||||
let connections = this._settings.list_connections();
|
||||
for (let i = 0; i < connections.length; i++) {
|
||||
let connection = connections[i];
|
||||
if (this._ignoreConnection(connection))
|
||||
continue;
|
||||
if (connection._updatedId) {
|
||||
// connection was already seen (for example because NetworkManager was restarted)
|
||||
continue;
|
||||
}
|
||||
connection._removedId = connection.connect('removed', Lang.bind(this, this._connectionRemoved));
|
||||
connection._updatedId = connection.connect('updated', Lang.bind(this, this._updateConnection));
|
||||
|
||||
this._updateConnection(connection);
|
||||
this._connections.push(connection);
|
||||
}
|
||||
},
|
||||
|
||||
_newConnection: function(settings, connection) {
|
||||
_addConnection: function(connection) {
|
||||
if (this._ignoreConnection(connection))
|
||||
return;
|
||||
if (connection._updatedId) {
|
||||
@@ -2165,14 +2004,22 @@ const NMApplet = new Lang.Class({
|
||||
|
||||
this._updateConnection(connection);
|
||||
this._connections.push(connection);
|
||||
},
|
||||
|
||||
_readConnections: function() {
|
||||
let connections = this._settings.list_connections();
|
||||
connections.forEach(Lang.bind(this, this._addConnection));
|
||||
},
|
||||
|
||||
_newConnection: function(settings, connection) {
|
||||
this._addConnection(connection);
|
||||
this._updateIcon();
|
||||
},
|
||||
|
||||
_connectionRemoved: function(connection) {
|
||||
let pos = this._connections.indexOf(connection);
|
||||
if (pos != -1)
|
||||
this._connections.splice(connection);
|
||||
this._connections.splice(connection, 1);
|
||||
|
||||
let section = connection._section;
|
||||
|
||||
|
||||
@@ -27,35 +27,6 @@ const LoginDialog = imports.gdm.loginDialog;
|
||||
// The timeout before going back automatically to the lock screen (in seconds)
|
||||
const IDLE_TIMEOUT = 2 * 60;
|
||||
|
||||
function versionCompare(required, reference) {
|
||||
required = required.split('.');
|
||||
reference = reference.split('.');
|
||||
|
||||
for (let i = 0; i < required.length; i++) {
|
||||
if (required[i] != reference[i])
|
||||
return required[i] < reference[i];
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
function isSupported() {
|
||||
try {
|
||||
let params = GLib.Variant.new('(ss)', ['org.gnome.DisplayManager.Manager', 'Version']);
|
||||
let result = Gio.DBus.system.call_sync('org.gnome.DisplayManager',
|
||||
'/org/gnome/DisplayManager/Manager',
|
||||
'org.freedesktop.DBus.Properties',
|
||||
'Get', params, null,
|
||||
Gio.DBusCallFlags.NONE,
|
||||
-1, null);
|
||||
|
||||
let version = result.deep_unpack()[0].deep_unpack();
|
||||
return versionCompare('3.5.91', version);
|
||||
} catch(e) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
const UnlockDialog = new Lang.Class({
|
||||
Name: 'UnlockDialog',
|
||||
Extends: ModalDialog.ModalDialog,
|
||||
@@ -76,6 +47,7 @@ const UnlockDialog = new Lang.Class({
|
||||
|
||||
this._greeterClient = new Gdm.Client();
|
||||
this._userVerifier = new GdmUtil.ShellUserVerifier(this._greeterClient, { reauthenticationOnly: true });
|
||||
this._userVerified = false;
|
||||
|
||||
this._userVerifier.connect('ask-question', Lang.bind(this, this._onAskQuestion));
|
||||
this._userVerifier.connect('show-message', Lang.bind(this, this._showMessage));
|
||||
@@ -98,6 +70,7 @@ const UnlockDialog = new Lang.Class({
|
||||
|
||||
this._promptEntry = new St.Entry({ style_class: 'login-dialog-prompt-entry',
|
||||
can_focus: true });
|
||||
this._promptEntry.clutter_text.connect('activate', Lang.bind(this, this._doUnlock));
|
||||
this._promptEntry.clutter_text.set_password_char('\u25cf');
|
||||
ShellEntry.addContextMenu(this._promptEntry, { isPassword: true });
|
||||
this.setInitialKeyFocus(this._promptEntry);
|
||||
@@ -118,7 +91,8 @@ const UnlockDialog = new Lang.Class({
|
||||
this._promptLoginHint.hide();
|
||||
this.contentLayout.add_actor(this._promptLoginHint);
|
||||
|
||||
this._workSpinner = new Panel.AnimatedIcon('process-working.svg', LoginDialog.WORK_SPINNER_ICON_SIZE);
|
||||
let spinnerIcon = global.datadir + '/theme/process-working.svg';
|
||||
this._workSpinner = new Panel.AnimatedIcon(spinnerIcon, LoginDialog.WORK_SPINNER_ICON_SIZE);
|
||||
this._workSpinner.actor.opacity = 0;
|
||||
|
||||
this.allowCancel = false;
|
||||
@@ -169,11 +143,6 @@ const UnlockDialog = new Lang.Class({
|
||||
let batch = new Batch.Hold();
|
||||
this._userVerifier.begin(this._userName, batch);
|
||||
|
||||
GLib.idle_add(GLib.PRIORITY_DEFAULT, Lang.bind(this, function() {
|
||||
this.emit('loaded');
|
||||
return false;
|
||||
}));
|
||||
|
||||
Main.ctrlAltTabManager.addGroup(this.dialogLayout, _("Unlock Window"), 'dialog-password-symbolic');
|
||||
|
||||
this._idleMonitor = new GnomeDesktop.IdleMonitor();
|
||||
@@ -282,18 +251,35 @@ const UnlockDialog = new Lang.Class({
|
||||
this._userVerifier.answerQuery(query, this._promptEntry.text);
|
||||
},
|
||||
|
||||
_onVerificationComplete: function() {
|
||||
_finishUnlock: function() {
|
||||
this._userVerifier.clear();
|
||||
this.emit('unlocked');
|
||||
},
|
||||
|
||||
_onVerificationComplete: function() {
|
||||
this._userVerified = true;
|
||||
if (!this._userVerifier.hasPendingMessages) {
|
||||
this._finishUnlock();
|
||||
} else {
|
||||
let signalId = this._userVerifier.connect('no-more-messages',
|
||||
Lang.bind(this, function() {
|
||||
this._userVerifier.disconnect(signalId);
|
||||
this._finishUnlock();
|
||||
}));
|
||||
}
|
||||
},
|
||||
|
||||
_onReset: function() {
|
||||
this.emit('failed');
|
||||
if (!this._userVerified) {
|
||||
this._userVerifier.clear();
|
||||
this.emit('failed');
|
||||
}
|
||||
},
|
||||
|
||||
_onVerificationFailed: function() {
|
||||
this._currentQuery = null;
|
||||
this._firstQuestion = true;
|
||||
this._userVerified = false;
|
||||
|
||||
this._promptEntry.text = '';
|
||||
this._promptEntry.clutter_text.set_password_char('\u25cf');
|
||||
@@ -333,4 +319,8 @@ const UnlockDialog = new Lang.Class({
|
||||
|
||||
this.destroy();
|
||||
},
|
||||
|
||||
addCharacter: function(unichar) {
|
||||
this._promptEntry.clutter_text.insert_unichar(unichar);
|
||||
},
|
||||
});
|
||||
|
||||
@@ -600,7 +600,8 @@ const UserMenuButton = new Lang.Class({
|
||||
Lang.bind(this, this._updateHaveShutdown));
|
||||
|
||||
Main.sessionMode.connect('updated', Lang.bind(this, this._sessionUpdated));
|
||||
Main.screenShield.connect('locked-changed', Lang.bind(this, this._updatePresenceIcon));
|
||||
if (Main.screenShield)
|
||||
Main.screenShield.connect('locked-changed', Lang.bind(this, this._updatePresenceIcon));
|
||||
this._sessionUpdated();
|
||||
},
|
||||
|
||||
@@ -656,7 +657,7 @@ const UserMenuButton = new Lang.Class({
|
||||
|
||||
_updateLockScreen: function() {
|
||||
let allowLockScreen = !this._lockdownSettings.get_boolean(DISABLE_LOCK_SCREEN_KEY);
|
||||
this._lockScreenItem.actor.visible = allowLockScreen;
|
||||
this._lockScreenItem.actor.visible = allowLockScreen && LoginManager.canLock();
|
||||
},
|
||||
|
||||
_updateInstallUpdates: function() {
|
||||
@@ -864,7 +865,8 @@ const UserMenuButton = new Lang.Class({
|
||||
_onLoginScreenActivate: function() {
|
||||
this.menu.close(BoxPointer.PopupAnimation.NONE);
|
||||
Main.overview.hide();
|
||||
Main.screenShield.lock(false);
|
||||
if (Main.screenShield)
|
||||
Main.screenShield.lock(false);
|
||||
Gdm.goto_login_session_sync(null);
|
||||
},
|
||||
|
||||
@@ -915,8 +917,10 @@ const UserMenuButton = new Lang.Class({
|
||||
session.user.get_real_name() : session.username;
|
||||
|
||||
if (session.info.remote)
|
||||
/* Translators: Remote here refers to a remote session, like a ssh login */
|
||||
userLabelText = _("%s (remote)").format(userName);
|
||||
else if (session.info.type == "tty")
|
||||
/* Translators: Console here refers to a tty like a VT console */
|
||||
userLabelText = _("%s (console)").format(userName);
|
||||
else
|
||||
userLabelText = userName;
|
||||
|
||||
@@ -150,6 +150,14 @@ const ViewSelector = new Lang.Class({
|
||||
Shell.KeyBindingMode.NORMAL |
|
||||
Shell.KeyBindingMode.OVERVIEW,
|
||||
Lang.bind(this, this._toggleAppsPage));
|
||||
|
||||
Main.wm.addKeybinding('toggle-overview',
|
||||
new Gio.Settings({ schema: SHELL_KEYBINDINGS_SCHEMA }),
|
||||
Meta.KeyBindingFlags.NONE,
|
||||
Shell.KeyBindingMode.NORMAL |
|
||||
Shell.KeyBindingMode.OVERVIEW,
|
||||
Lang.bind(Main.overview, Main.overview.toggle));
|
||||
|
||||
},
|
||||
|
||||
_toggleAppsPage: function() {
|
||||
@@ -178,6 +186,10 @@ const ViewSelector = new Lang.Class({
|
||||
Main.overview.fadeInDesktop();
|
||||
},
|
||||
|
||||
setWorkspacesFullGeometry: function(geom) {
|
||||
this._workspacesDisplay.setWorkspacesFullGeometry(geom);
|
||||
},
|
||||
|
||||
hide: function() {
|
||||
this._workspacesDisplay.hide();
|
||||
},
|
||||
|
||||
@@ -11,12 +11,14 @@ const Layout = imports.ui.layout;
|
||||
const Main = imports.ui.main;
|
||||
const Panel = imports.ui.panel;
|
||||
|
||||
// we could make these gsettings
|
||||
const FISH_NAME = 'wanda';
|
||||
const FISH_FILENAME = 'wanda.png';
|
||||
const FISH_SPEED = 300;
|
||||
const FISH_COMMAND = 'fortune';
|
||||
// The size of an individual frame in the animation
|
||||
const FISH_HEIGHT = 22;
|
||||
const FISH_WIDTH = 36;
|
||||
|
||||
const GNOME_PANEL_PIXMAPDIR = '../gnome-panel/fish';
|
||||
const FISH_GROUP = 'Fish Animation';
|
||||
|
||||
const MAGIC_FISH_KEY = 'free the fish';
|
||||
@@ -26,33 +28,16 @@ const WandaIcon = new Lang.Class({
|
||||
Extends: IconGrid.BaseIcon,
|
||||
|
||||
_init : function(fish, label, params) {
|
||||
this._fish = fish;
|
||||
let file = GLib.build_filenamev([global.datadir, GNOME_PANEL_PIXMAPDIR, fish + '.fish']);
|
||||
|
||||
if (GLib.file_test(file, GLib.FileTest.EXISTS)) {
|
||||
this._keyfile = new GLib.KeyFile();
|
||||
this._keyfile.load_from_file(file, GLib.KeyFileFlags.NONE);
|
||||
|
||||
this._imageFile = GLib.build_filenamev([global.datadir, GNOME_PANEL_PIXMAPDIR,
|
||||
this._keyfile.get_string(FISH_GROUP, 'image')]);
|
||||
|
||||
let tmpPixbuf = GdkPixbuf.Pixbuf.new_from_file(this._imageFile);
|
||||
|
||||
this._imgHeight = tmpPixbuf.height;
|
||||
this._imgWidth = tmpPixbuf.width / this._keyfile.get_integer(FISH_GROUP, 'frames');
|
||||
} else {
|
||||
this._imageFile = null;
|
||||
}
|
||||
|
||||
this.parent(label, params);
|
||||
|
||||
this._fish = fish;
|
||||
this._imageFile = GLib.build_filenamev([global.datadir, fish + '.png']);
|
||||
|
||||
this._imgHeight = FISH_HEIGHT;
|
||||
this._imgWidth = FISH_WIDTH;
|
||||
},
|
||||
|
||||
createIcon: function(iconSize) {
|
||||
if (!this._imageFile) {
|
||||
return new St.Icon({ icon_name: 'face-smile',
|
||||
icon_size: iconSize });
|
||||
}
|
||||
|
||||
this._animations = new Panel.Animation(this._imageFile, this._imgWidth, this._imgHeight, FISH_SPEED);
|
||||
this._animations.play();
|
||||
return this._animations.actor;
|
||||
|
||||
@@ -172,8 +172,9 @@ const WindowManager = new Lang.Class({
|
||||
this.addKeybinding('open-application-menu',
|
||||
new Gio.Settings({ schema: SHELL_KEYBINDINGS_SCHEMA }),
|
||||
Meta.KeyBindingFlags.NONE,
|
||||
Shell.KeyBindingMode.NORMAL,
|
||||
Lang.bind(this, this._openAppMenu));
|
||||
Shell.KeyBindingMode.NORMAL |
|
||||
Shell.KeyBindingMode.TOPBAR_POPUP,
|
||||
Lang.bind(this, this._toggleAppMenu));
|
||||
|
||||
Main.overview.connect('showing', Lang.bind(this, function() {
|
||||
for (let i = 0; i < this._dimmedWindows.length; i++)
|
||||
@@ -679,8 +680,8 @@ const WindowManager = new Lang.Class({
|
||||
Main.ctrlAltTabManager.popup(backwards, binding.get_name(), binding.get_mask());
|
||||
},
|
||||
|
||||
_openAppMenu : function(display, screen, window, event, binding) {
|
||||
Main.panel.openAppMenu();
|
||||
_toggleAppMenu : function(display, screen, window, event, binding) {
|
||||
Main.panel.toggleAppMenu();
|
||||
},
|
||||
|
||||
_showWorkspaceSwitcher : function(display, screen, window, binding) {
|
||||
|
||||
@@ -121,15 +121,33 @@ const WindowClone = new Lang.Class({
|
||||
return this._slot;
|
||||
},
|
||||
|
||||
// Find the actor just below us, respecting reparenting done
|
||||
// by DND code
|
||||
getActualStackAbove: function() {
|
||||
if (this._stackAbove == null)
|
||||
return null;
|
||||
|
||||
if (this.inDrag || this._zooming) {
|
||||
if (this._stackAbove._delegate)
|
||||
return this._stackAbove._delegate.getActualStackAbove();
|
||||
else
|
||||
return null;
|
||||
} else {
|
||||
return this._stackAbove;
|
||||
}
|
||||
},
|
||||
|
||||
setStackAbove: function (actor) {
|
||||
this._stackAbove = actor;
|
||||
if (this.inDrag)
|
||||
// We'll fix up the stack after the drag
|
||||
return;
|
||||
if (this._stackAbove == null)
|
||||
|
||||
let actualAbove = this.getActualStackAbove();
|
||||
if (actualAbove == null)
|
||||
this.actor.lower_bottom();
|
||||
else
|
||||
this.actor.raise(this._stackAbove);
|
||||
this.actor.raise(actualAbove);
|
||||
},
|
||||
|
||||
destroy: function () {
|
||||
@@ -735,13 +753,6 @@ const LayoutStrategy = new Lang.Class({
|
||||
layout.space = space;
|
||||
},
|
||||
|
||||
_getDistance: function (row, actor) {
|
||||
let dist_x = actor.x - row.x;
|
||||
let dist_y = actor.y - row.y;
|
||||
|
||||
return Math.sqrt(Math.pow(dist_x, 2) + Math.pow(dist_y, 2));
|
||||
},
|
||||
|
||||
computeWindowSlots: function(layout, area) {
|
||||
this._computeRowSizes(layout);
|
||||
|
||||
@@ -749,28 +760,36 @@ const LayoutStrategy = new Lang.Class({
|
||||
|
||||
let slots = [];
|
||||
|
||||
let y = 0;
|
||||
// Do this in three parts.
|
||||
let height = 0;
|
||||
for (let i = 0; i < rows.length; i++) {
|
||||
let row = rows[i];
|
||||
row.x = area.x + (area.width - row.width) / 2;
|
||||
row.y = area.y + y;
|
||||
y += row.height + this._rowSpacing;
|
||||
row.windows.sort(Lang.bind(this, function(a, b) {
|
||||
return this._getDistance(row, a.realWindow) - this._getDistance(row, b.realWindow);
|
||||
}));
|
||||
height += row.height + this._rowSpacing;
|
||||
}
|
||||
|
||||
let height = y - this._rowSpacing;
|
||||
let baseY = (area.height - height) / 2;
|
||||
height -= this._rowSpacing;
|
||||
|
||||
let y = 0;
|
||||
|
||||
for (let i = 0; i < rows.length; i++) {
|
||||
let row = rows[i];
|
||||
|
||||
// If this window layout row doesn't fit in the actual
|
||||
// geometry, then apply an additional scale to it.
|
||||
row.additionalScale = Math.min(1, area.width / row.width, area.height / height);
|
||||
|
||||
row.x = area.x + (Math.max(area.width - row.width, 0) / 2) * row.additionalScale;
|
||||
row.y = area.y + (y + Math.max(area.height - height, 0) / 2) * row.additionalScale;
|
||||
y += row.height + this._rowSpacing;
|
||||
}
|
||||
|
||||
for (let i = 0; i < rows.length; i++) {
|
||||
let row = rows[i];
|
||||
row.y += baseY;
|
||||
let x = row.x;
|
||||
for (let j = 0; j < row.windows.length; j++) {
|
||||
let window = row.windows[j];
|
||||
|
||||
let s = scale * this._computeWindowScale(window);
|
||||
let s = scale * this._computeWindowScale(window) * row.additionalScale;
|
||||
let cellWidth = window.actor.width * s;
|
||||
let cellHeight = window.actor.height * s;
|
||||
|
||||
@@ -814,6 +833,13 @@ const UnalignedLayoutStrategy = new Lang.Class({
|
||||
return false;
|
||||
},
|
||||
|
||||
_sortRow: function(row) {
|
||||
// Sort windows horizontally to minimize travel distance
|
||||
row.windows.sort(function(a, b) {
|
||||
return a.realWindow.x - b.realWindow.x;
|
||||
});
|
||||
},
|
||||
|
||||
computeLayout: function(windows, layout) {
|
||||
let numRows = layout.numRows;
|
||||
|
||||
@@ -844,6 +870,7 @@ const UnalignedLayoutStrategy = new Lang.Class({
|
||||
row.windows.push(window);
|
||||
row.fullWidth += width;
|
||||
} else {
|
||||
this._sortRow(row);
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -865,6 +892,14 @@ const UnalignedLayoutStrategy = new Lang.Class({
|
||||
}
|
||||
});
|
||||
|
||||
function padArea(area, padding) {
|
||||
return {
|
||||
x: area.x + padding.left,
|
||||
y: area.y + padding.top,
|
||||
width: area.width - padding.left - padding.right,
|
||||
height: area.height - padding.top - padding.bottom,
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* @metaWorkspace: a #Meta.Workspace, or null
|
||||
@@ -876,10 +911,19 @@ const Workspace = new Lang.Class({
|
||||
// When dragging a window, we use this slot for reserve space.
|
||||
this._reservedSlot = null;
|
||||
this.metaWorkspace = metaWorkspace;
|
||||
this._x = 0;
|
||||
this._y = 0;
|
||||
this._width = 0;
|
||||
this._height = 0;
|
||||
|
||||
// The full geometry is the geometry we should try and position
|
||||
// windows for. The actual geometry we allocate may be less than
|
||||
// this, like if the workspace switcher is slid out.
|
||||
this._fullGeometry = null;
|
||||
|
||||
// The actual geometry is the geometry we need to arrange windows
|
||||
// in. If this is a smaller area than the full geometry, we'll
|
||||
// do some simple aspect ratio like math to fit the layout calculated
|
||||
// for the full geometry into this area.
|
||||
this._actualGeometry = null;
|
||||
|
||||
this._currentLayout = null;
|
||||
|
||||
this.monitorIndex = monitorIndex;
|
||||
this._monitor = Main.layoutManager.monitors[this.monitorIndex];
|
||||
@@ -908,7 +952,7 @@ const Workspace = new Lang.Class({
|
||||
this._windowOverlays = [];
|
||||
for (let i = 0; i < windows.length; i++) {
|
||||
if (this._isOverviewWindow(windows[i])) {
|
||||
this._addWindowClone(windows[i]);
|
||||
this._addWindowClone(windows[i], true);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -929,23 +973,22 @@ const Workspace = new Lang.Class({
|
||||
|
||||
this._positionWindowsFlags = 0;
|
||||
this._positionWindowsId = 0;
|
||||
|
||||
this._currentLayout = null;
|
||||
},
|
||||
|
||||
setGeometry: function(x, y, width, height) {
|
||||
this._x = x;
|
||||
this._y = y;
|
||||
this._width = width;
|
||||
this._height = height;
|
||||
setFullGeometry: function(geom) {
|
||||
this._fullGeometry = geom;
|
||||
this._recalculateWindowPositions(WindowPositionFlags.NONE);
|
||||
},
|
||||
|
||||
setActualGeometry: function(geom) {
|
||||
this._actualGeometry = geom;
|
||||
|
||||
Meta.later_add(Meta.LaterType.BEFORE_REDRAW, Lang.bind(this, function() {
|
||||
this._dropRect.set_position(x, y);
|
||||
this._dropRect.set_size(width, height);
|
||||
this._dropRect.set_position(geom.x, geom.y);
|
||||
this._dropRect.set_size(geom.width, geom.height);
|
||||
this._updateWindowPositions(WindowPositionFlags.NONE);
|
||||
return false;
|
||||
}));
|
||||
|
||||
this.positionWindows(WindowPositionFlags.NONE);
|
||||
},
|
||||
|
||||
_lookupIndex: function (metaWindow) {
|
||||
@@ -973,37 +1016,32 @@ const Workspace = new Lang.Class({
|
||||
clone = null;
|
||||
|
||||
this._reservedSlot = clone;
|
||||
this._currentLayout = null;
|
||||
this.positionWindows(WindowPositionFlags.ANIMATE);
|
||||
this._recalculateWindowPositions(WindowPositionFlags.ANIMATE);
|
||||
},
|
||||
|
||||
/**
|
||||
* positionWindows:
|
||||
* @flags:
|
||||
* INITIAL - this is the initial positioning of the windows.
|
||||
* ANIMATE - Indicates that we need animate changing position.
|
||||
*/
|
||||
positionWindows: function(flags) {
|
||||
_recalculateWindowPositions: function(flags) {
|
||||
this._positionWindowsFlags |= flags;
|
||||
|
||||
if (this._positionWindowsId > 0)
|
||||
return;
|
||||
|
||||
this._positionWindowsId = Meta.later_add(Meta.LaterType.BEFORE_REDRAW, Lang.bind(this, function() {
|
||||
this._realPositionWindows(this._positionWindowsFlags);
|
||||
this._realRecalculateWindowPositions(this._positionWindowsFlags);
|
||||
this._positionWindowsFlags = 0;
|
||||
this._positionWindowsId = 0;
|
||||
return false;
|
||||
}));
|
||||
},
|
||||
|
||||
_realPositionWindows : function(flags) {
|
||||
_realRecalculateWindowPositions: function(flags) {
|
||||
if (this._repositionWindowsId > 0) {
|
||||
Mainloop.source_remove(this._repositionWindowsId);
|
||||
this._repositionWindowsId = 0;
|
||||
}
|
||||
|
||||
let clones = this._windows.slice();
|
||||
if (clones.length == 0)
|
||||
return;
|
||||
|
||||
clones.sort(function(a, b) {
|
||||
return a.metaWindow.get_stable_sequence() - b.metaWindow.get_stable_sequence();
|
||||
@@ -1012,11 +1050,25 @@ const Workspace = new Lang.Class({
|
||||
if (this._reservedSlot)
|
||||
clones.push(this._reservedSlot);
|
||||
|
||||
this._currentLayout = this._computeLayout(clones);
|
||||
this._updateWindowPositions(flags);
|
||||
},
|
||||
|
||||
_updateWindowPositions: function(flags) {
|
||||
if (this._currentLayout == null) {
|
||||
this._recalculateWindowPositions(flags);
|
||||
return;
|
||||
}
|
||||
|
||||
let initialPositioning = flags & WindowPositionFlags.INITIAL;
|
||||
let animate = flags & WindowPositionFlags.ANIMATE;
|
||||
|
||||
// Start the animations
|
||||
let slots = this._computeAllWindowSlots(clones);
|
||||
let layout = this._currentLayout;
|
||||
let strategy = layout.strategy;
|
||||
|
||||
let [, , padding] = this._getSpacingAndPadding();
|
||||
let area = padArea(this._actualGeometry, padding);
|
||||
let slots = strategy.computeWindowSlots(layout, area);
|
||||
|
||||
let currentWorkspace = global.screen.get_active_workspace();
|
||||
let isOnCurrentWorkspace = this.metaWorkspace == null || this.metaWorkspace == currentWorkspace;
|
||||
@@ -1033,11 +1085,23 @@ const Workspace = new Lang.Class({
|
||||
if (clone.inDrag)
|
||||
continue;
|
||||
|
||||
clone.slot = [x, y, clone.actor.width * scale, clone.actor.height * scale];
|
||||
let cloneWidth = clone.actor.width * scale;
|
||||
let cloneHeight = clone.actor.height * scale;
|
||||
clone.slot = [x, y, cloneWidth, cloneHeight];
|
||||
|
||||
if (overlay && initialPositioning)
|
||||
if (overlay && (initialPositioning || !clone.positioned))
|
||||
overlay.hide();
|
||||
|
||||
if (!clone.positioned) {
|
||||
// This window appeared after the overview was already up
|
||||
// Grow the clone from the center of the slot
|
||||
clone.actor.x = x + cloneWidth / 2;
|
||||
clone.actor.y = y + cloneHeight / 2;
|
||||
clone.actor.scale_x = 0;
|
||||
clone.actor.scale_y = 0;
|
||||
clone.positioned = true;
|
||||
}
|
||||
|
||||
if (animate && isOnCurrentWorkspace) {
|
||||
if (!metaWindow.showing_on_its_workspace()) {
|
||||
/* Hidden windows should fade in and grow
|
||||
@@ -1118,8 +1182,8 @@ const Workspace = new Lang.Class({
|
||||
let [x, y, mask] = global.get_pointer();
|
||||
|
||||
let pointerHasMoved = (this._cursorX != x && this._cursorY != y);
|
||||
let inWorkspace = (this._x < x && x < this._x + this._width &&
|
||||
this._y < y && y < this._y + this._height);
|
||||
let inWorkspace = (this._fullGeometry.x < x && x < this._fullGeometry.x + this._fullGeometry.width &&
|
||||
this._fullGeometry.y < y && y < this._fullGeometry.y + this._fullGeometry.height);
|
||||
|
||||
if (pointerHasMoved && inWorkspace) {
|
||||
// store current cursor position
|
||||
@@ -1134,7 +1198,7 @@ const Workspace = new Lang.Class({
|
||||
return true;
|
||||
}
|
||||
|
||||
this.positionWindows(WindowPositionFlags.ANIMATE);
|
||||
this._recalculateWindowPositions(WindowPositionFlags.ANIMATE);
|
||||
return false;
|
||||
},
|
||||
|
||||
@@ -1223,7 +1287,7 @@ const Workspace = new Lang.Class({
|
||||
if (!this._isMyWindow(win) || !this._isOverviewWindow(win))
|
||||
return;
|
||||
|
||||
let [clone, overlay] = this._addWindowClone(win);
|
||||
let [clone, overlay] = this._addWindowClone(win, false);
|
||||
|
||||
if (win._overviewHint) {
|
||||
let x = win._overviewHint.x - this.actor.x;
|
||||
@@ -1232,20 +1296,14 @@ const Workspace = new Lang.Class({
|
||||
delete win._overviewHint;
|
||||
|
||||
clone.slot = [x, y, clone.actor.width * scale, clone.actor.height * scale];
|
||||
clone.positioned = true;
|
||||
clone.actor.set_position (x, y);
|
||||
clone.actor.set_scale (scale, scale);
|
||||
clone.overlay.relayout(false);
|
||||
} else {
|
||||
// Position new windows at the top corner of the workspace rather
|
||||
// than where they were placed for real to avoid the window
|
||||
// being clipped to the workspaceView. Its not really more
|
||||
// natural for the window to suddenly appear in the overview
|
||||
// on some seemingly random location anyway.
|
||||
clone.actor.set_position (this._x, this._y);
|
||||
}
|
||||
|
||||
this._currentLayout = null;
|
||||
this.positionWindows(WindowPositionFlags.ANIMATE);
|
||||
this._recalculateWindowPositions(WindowPositionFlags.ANIMATE);
|
||||
},
|
||||
|
||||
_windowAdded : function(metaWorkspace, metaWin) {
|
||||
@@ -1282,13 +1340,8 @@ const Workspace = new Lang.Class({
|
||||
|
||||
// Animate the full-screen to Overview transition.
|
||||
zoomToOverview : function() {
|
||||
this._currentLayout = null;
|
||||
|
||||
// Position and scale the windows.
|
||||
if (Main.overview.animationInProgress)
|
||||
this.positionWindows(WindowPositionFlags.ANIMATE | WindowPositionFlags.INITIAL);
|
||||
else
|
||||
this.positionWindows(WindowPositionFlags.INITIAL);
|
||||
this._recalculateWindowPositions(WindowPositionFlags.ANIMATE | WindowPositionFlags.INITIAL);
|
||||
},
|
||||
|
||||
// Animates the return from Overview mode
|
||||
@@ -1388,10 +1441,11 @@ const Workspace = new Lang.Class({
|
||||
},
|
||||
|
||||
// Create a clone of a (non-desktop) window and add it to the window list
|
||||
_addWindowClone : function(win) {
|
||||
_addWindowClone : function(win, positioned) {
|
||||
let clone = new WindowClone(win, this);
|
||||
let overlay = new WindowOverlay(clone, this._windowOverlaysGroup);
|
||||
clone.overlay = overlay;
|
||||
clone.positioned = positioned;
|
||||
|
||||
clone.connect('selected',
|
||||
Lang.bind(this, this._onCloneSelected));
|
||||
@@ -1411,7 +1465,7 @@ const Workspace = new Lang.Class({
|
||||
}));
|
||||
clone.connect('size-changed',
|
||||
Lang.bind(this, function() {
|
||||
this.positionWindows(0);
|
||||
this._recalculateWindowPositions(WindowPositionFlags.NONE);
|
||||
}));
|
||||
|
||||
this.actor.add_actor(clone.actor);
|
||||
@@ -1460,12 +1514,14 @@ const Workspace = new Lang.Class({
|
||||
}
|
||||
},
|
||||
|
||||
_computeLayout: function(windows, area, rowSpacing, columnSpacing) {
|
||||
_getBestLayout: function(windows, area, rowSpacing, columnSpacing) {
|
||||
// We look for the largest scale that allows us to fit the
|
||||
// largest row/tallest column on the workspace.
|
||||
|
||||
let lastLayout = {};
|
||||
|
||||
let strategy = new UnalignedLayoutStrategy(this._monitor, rowSpacing, columnSpacing);
|
||||
|
||||
for (let numRows = 1; ; numRows++) {
|
||||
let numColumns = Math.ceil(windows.length / numRows);
|
||||
|
||||
@@ -1475,8 +1531,6 @@ const Workspace = new Lang.Class({
|
||||
if (numColumns == lastLayout.numColumns)
|
||||
break;
|
||||
|
||||
let strategy = new UnalignedLayoutStrategy(this._monitor, rowSpacing, columnSpacing);
|
||||
|
||||
let layout = { area: area, strategy: strategy, numRows: numRows, numColumns: numColumns };
|
||||
strategy.computeLayout(windows, layout);
|
||||
strategy.computeScaleAndSpace(layout);
|
||||
@@ -1490,18 +1544,7 @@ const Workspace = new Lang.Class({
|
||||
return lastLayout;
|
||||
},
|
||||
|
||||
_rectEqual: function(one, two) {
|
||||
if (one == two)
|
||||
return true;
|
||||
|
||||
return (one.x == two.x &&
|
||||
one.y == two.y &&
|
||||
one.width == two.width &&
|
||||
one.height == two.height);
|
||||
},
|
||||
|
||||
_computeAllWindowSlots: function(windows) {
|
||||
let totalWindows = windows.length;
|
||||
_getSpacingAndPadding: function() {
|
||||
let node = this.actor.get_theme_node();
|
||||
|
||||
// Window grid spacing
|
||||
@@ -1514,21 +1557,14 @@ const Workspace = new Lang.Class({
|
||||
right: node.get_padding(St.Side.RIGHT),
|
||||
};
|
||||
|
||||
if (!totalWindows)
|
||||
return [];
|
||||
|
||||
let closeButtonHeight, captionHeight;
|
||||
let leftBorder, rightBorder;
|
||||
if (this._windowOverlays.length) {
|
||||
// All of the overlays have the same chrome sizes,
|
||||
// so just pick the first one.
|
||||
let overlay = this._windowOverlays[0];
|
||||
[closeButtonHeight, captionHeight] = overlay.chromeHeights();
|
||||
[leftBorder, rightBorder] = overlay.chromeWidths();
|
||||
} else {
|
||||
[closeButtonHeight, captionHeight] = [0, 0];
|
||||
[leftBorder, rightBorder] = [0, 0];
|
||||
}
|
||||
|
||||
// All of the overlays have the same chrome sizes,
|
||||
// so just pick the first one.
|
||||
let overlay = this._windowOverlays[0];
|
||||
[closeButtonHeight, captionHeight] = overlay.chromeHeights();
|
||||
[leftBorder, rightBorder] = overlay.chromeWidths();
|
||||
|
||||
rowSpacing += captionHeight;
|
||||
columnSpacing += (rightBorder + leftBorder) / 2;
|
||||
@@ -1537,25 +1573,13 @@ const Workspace = new Lang.Class({
|
||||
padding.left += leftBorder;
|
||||
padding.right += rightBorder;
|
||||
|
||||
let area = {
|
||||
x: this._x + padding.left,
|
||||
y: this._y + padding.top,
|
||||
width: this._width - padding.left - padding.right,
|
||||
height: this._height - padding.top - padding.bottom,
|
||||
};
|
||||
return [rowSpacing, columnSpacing, padding];
|
||||
},
|
||||
|
||||
if (!this._currentLayout)
|
||||
this._currentLayout = this._computeLayout(windows, area, rowSpacing, columnSpacing);
|
||||
|
||||
let layout = this._currentLayout;
|
||||
let strategy = layout.strategy;
|
||||
|
||||
if (!this._rectEqual(area, layout.area)) {
|
||||
layout.area = area;
|
||||
strategy.computeScaleAndSpace(layout);
|
||||
}
|
||||
|
||||
return strategy.computeWindowSlots(layout, area);
|
||||
_computeLayout: function(windows) {
|
||||
let [rowSpacing, columnSpacing, padding] = this._getSpacingAndPadding();
|
||||
let area = padArea(this._fullGeometry, padding);
|
||||
return this._getBestLayout(windows, area, rowSpacing, columnSpacing);
|
||||
},
|
||||
|
||||
_onCloneSelected : function (clone, time) {
|
||||
|
||||
@@ -62,12 +62,35 @@ const WindowClone = new Lang.Class({
|
||||
this.inDrag = false;
|
||||
},
|
||||
|
||||
// Find the actor just below us, respecting reparenting done
|
||||
// by DND code
|
||||
getActualStackAbove: function() {
|
||||
if (this._stackAbove == null)
|
||||
return null;
|
||||
|
||||
if (this.inDrag) {
|
||||
if (this._stackAbove._delegate)
|
||||
return this._stackAbove._delegate.getActualStackAbove();
|
||||
else
|
||||
return null;
|
||||
} else {
|
||||
return this._stackAbove;
|
||||
}
|
||||
},
|
||||
|
||||
setStackAbove: function (actor) {
|
||||
this._stackAbove = actor;
|
||||
if (this._stackAbove == null)
|
||||
|
||||
// Don't apply the new stacking now, it will be applied
|
||||
// when dragging ends and window are stacked again
|
||||
if (actor.inDrag)
|
||||
return;
|
||||
|
||||
let actualAbove = this.getActualStackAbove();
|
||||
if (actualAbove == null)
|
||||
this.actor.lower_bottom();
|
||||
else
|
||||
this.actor.raise(this._stackAbove);
|
||||
this.actor.raise(actualAbove);
|
||||
},
|
||||
|
||||
destroy: function () {
|
||||
@@ -361,9 +384,8 @@ const WorkspaceThumbnail = new Lang.Class({
|
||||
},
|
||||
|
||||
destroy : function() {
|
||||
this.actor.destroy();
|
||||
this._bgManager.destroy();
|
||||
this._bgManager = null;
|
||||
if (this.actor)
|
||||
this.actor.destroy();
|
||||
},
|
||||
|
||||
workspaceRemoved : function() {
|
||||
@@ -384,6 +406,11 @@ const WorkspaceThumbnail = new Lang.Class({
|
||||
_onDestroy: function(actor) {
|
||||
this.workspaceRemoved();
|
||||
|
||||
if (this._bgManager) {
|
||||
this._bgManager.destroy();
|
||||
this._bgManager = null;
|
||||
}
|
||||
|
||||
this._windows = [];
|
||||
this.actor = null;
|
||||
},
|
||||
@@ -535,6 +562,7 @@ const ThumbnailsBox = new Lang.Class({
|
||||
this._dropPlaceholderPos = -1;
|
||||
this._dropPlaceholder = new St.Bin({ style_class: 'placeholder' });
|
||||
this.actor.add_actor(this._dropPlaceholder);
|
||||
this._spliceIndex = -1;
|
||||
|
||||
this._targetScale = 0;
|
||||
this._scale = 0;
|
||||
@@ -717,6 +745,8 @@ const ThumbnailsBox = new Lang.Class({
|
||||
return win.get_workspace() >= newWorkspaceIndex;
|
||||
});
|
||||
|
||||
this._spliceIndex = newWorkspaceIndex;
|
||||
|
||||
// ... move them down one.
|
||||
windows.forEach(function(win) {
|
||||
win.meta_window.change_workspace_by_index(win.get_workspace() + 1,
|
||||
@@ -738,6 +768,14 @@ const ThumbnailsBox = new Lang.Class({
|
||||
WORKSPACE_KEEP_ALIVE_TIME);
|
||||
}
|
||||
|
||||
// Start the animation on the workspace (which is actually
|
||||
// an old one which just became empty)
|
||||
let thumbnail = this._thumbnails[newWorkspaceIndex];
|
||||
this._setThumbnailState(thumbnail, ThumbnailState.NEW);
|
||||
thumbnail.slidePosition = 1;
|
||||
|
||||
this._queueUpdateStates();
|
||||
|
||||
return true;
|
||||
} else {
|
||||
return false;
|
||||
@@ -825,7 +863,8 @@ const ThumbnailsBox = new Lang.Class({
|
||||
this._thumbnails.push(thumbnail);
|
||||
this.actor.add_actor(thumbnail.actor);
|
||||
|
||||
if (start > 0) { // not the initial fill
|
||||
if (start > 0 && this._spliceIndex == -1) {
|
||||
// not the initial fill, and not splicing via DND
|
||||
thumbnail.state = ThumbnailState.NEW;
|
||||
thumbnail.slidePosition = 1; // start slid out
|
||||
this._haveNewThumbnails = true;
|
||||
@@ -840,6 +879,9 @@ const ThumbnailsBox = new Lang.Class({
|
||||
|
||||
// The thumbnails indicator actually needs to be on top of the thumbnails
|
||||
this._indicator.raise_top();
|
||||
|
||||
// Clear the splice index, we got the message
|
||||
this._spliceIndex = -1;
|
||||
},
|
||||
|
||||
removeThumbnails: function(start, count) {
|
||||
|
||||
@@ -23,6 +23,18 @@ const MAX_WORKSPACES = 16;
|
||||
|
||||
const OVERRIDE_SCHEMA = 'org.gnome.shell.overrides';
|
||||
|
||||
function rectEqual(one, two) {
|
||||
if (one == two)
|
||||
return true;
|
||||
|
||||
if (!one || !two)
|
||||
return false;
|
||||
|
||||
return (one.x == two.x &&
|
||||
one.y == two.y &&
|
||||
one.width == two.width &&
|
||||
one.height == two.height);
|
||||
}
|
||||
|
||||
const WorkspacesView = new Lang.Class({
|
||||
Name: 'WorkspacesView',
|
||||
@@ -43,10 +55,9 @@ const WorkspacesView = new Lang.Class({
|
||||
this._updateWorkspaceActors(false);
|
||||
}));
|
||||
|
||||
this._width = 0;
|
||||
this._height = 0;
|
||||
this._x = 0;
|
||||
this._y = 0;
|
||||
this._fullGeometry = null;
|
||||
this._actualGeometry = null;
|
||||
|
||||
this._spacing = 0;
|
||||
this._animating = false; // tweening
|
||||
this._scrolling = false; // swipe-scrolling
|
||||
@@ -85,8 +96,8 @@ const WorkspacesView = new Lang.Class({
|
||||
this._overviewShownId =
|
||||
Main.overview.connect('shown',
|
||||
Lang.bind(this, function() {
|
||||
this.actor.set_clip(this._x, this._y,
|
||||
this._width, this._height);
|
||||
this.actor.set_clip(this._fullGeometry.x, this._fullGeometry.y,
|
||||
this._fullGeometry.width, this._fullGeometry.height);
|
||||
}));
|
||||
|
||||
this.scrollAdjustment = new St.Adjustment({ value: activeWorkspaceIndex,
|
||||
@@ -124,10 +135,8 @@ const WorkspacesView = new Lang.Class({
|
||||
continue;
|
||||
|
||||
let ws = new Workspace.Workspace(null, i);
|
||||
ws.setGeometry(monitors[i].x,
|
||||
monitors[i].y,
|
||||
monitors[i].width,
|
||||
monitors[i].height);
|
||||
ws.setFullGeometry(monitors[i]);
|
||||
ws.setActualGeometry(monitors[i]);
|
||||
global.overlay_group.add_actor(ws.actor);
|
||||
this._extraWorkspaces.push(ws);
|
||||
}
|
||||
@@ -139,18 +148,24 @@ const WorkspacesView = new Lang.Class({
|
||||
this._extraWorkspaces = [];
|
||||
},
|
||||
|
||||
setGeometry: function(x, y, width, height) {
|
||||
if (this._x == x && this._y == y &&
|
||||
this._width == width && this._height == height)
|
||||
return;
|
||||
setFullGeometry: function(geom) {
|
||||
if (rectEqual(this._fullGeometry, geom))
|
||||
return;
|
||||
|
||||
this._width = width;
|
||||
this._height = height;
|
||||
this._x = x;
|
||||
this._y = y;
|
||||
this._fullGeometry = geom;
|
||||
|
||||
for (let i = 0; i < this._workspaces.length; i++)
|
||||
this._workspaces[i].setGeometry(x, y, width, height);
|
||||
this._workspaces[i].setFullGeometry(geom);
|
||||
},
|
||||
|
||||
setActualGeometry: function(geom) {
|
||||
if (rectEqual(this._actualGeometry, geom))
|
||||
return;
|
||||
|
||||
this._actualGeometry = geom;
|
||||
|
||||
for (let i = 0; i < this._workspaces.length; i++)
|
||||
this._workspaces[i].setActualGeometry(geom);
|
||||
},
|
||||
|
||||
_lookupWorkspaceForMetaWindow: function (metaWindow) {
|
||||
@@ -210,7 +225,7 @@ const WorkspacesView = new Lang.Class({
|
||||
|
||||
Tweener.removeTweens(workspace.actor);
|
||||
|
||||
let y = (w - active) * (this._height + this._spacing);
|
||||
let y = (w - active) * (this._fullGeometry.height + this._spacing);
|
||||
|
||||
if (showAnimation) {
|
||||
let params = { y: y,
|
||||
@@ -281,8 +296,9 @@ const WorkspacesView = new Lang.Class({
|
||||
|
||||
if (newNumWorkspaces > oldNumWorkspaces) {
|
||||
for (let w = oldNumWorkspaces; w < newNumWorkspaces; w++) {
|
||||
this._workspaces[w].setGeometry(this._x, this._y,
|
||||
this._width, this._height);
|
||||
this._workspaces[w].setFullGeometry(this._fullGeometry);
|
||||
if (this._actualGeometry)
|
||||
this._workspaces[w].setActualGeometry(this._actualGeometry);
|
||||
this.actor.add_actor(this._workspaces[w].actor);
|
||||
}
|
||||
|
||||
@@ -386,6 +402,15 @@ const WorkspacesView = new Lang.Class({
|
||||
let current = Math.round(adj.value);
|
||||
|
||||
if (active != current) {
|
||||
if (!this._workspaces[current]) {
|
||||
// The current workspace was destroyed. This could happen
|
||||
// when you are on the last empty workspace, and consolidate
|
||||
// windows using the thumbnail bar.
|
||||
// In that case, the intended behavior is to stay on the empty
|
||||
// workspace, which is the last one, so pick it.
|
||||
current = this._workspaces.length - 1;
|
||||
}
|
||||
|
||||
let metaWorkspace = this._workspaces[current].metaWorkspace;
|
||||
metaWorkspace.activate(global.get_current_time());
|
||||
}
|
||||
@@ -421,7 +446,7 @@ const WorkspacesDisplay = new Lang.Class({
|
||||
|
||||
_init: function() {
|
||||
this.actor = new St.Widget({ clip_to_allocation: true });
|
||||
this.actor.connect('notify::allocation', Lang.bind(this, this._updateWorkspacesGeometry));
|
||||
this.actor.connect('notify::allocation', Lang.bind(this, this._updateWorkspacesActualGeometry));
|
||||
this.actor.connect('parent-set', Lang.bind(this, this._parentSet));
|
||||
|
||||
let clickAction = new Clutter.ClickAction()
|
||||
@@ -475,6 +500,8 @@ const WorkspacesDisplay = new Lang.Class({
|
||||
|
||||
this._notifyOpacityId = 0;
|
||||
this._scrollEventId = 0;
|
||||
|
||||
this._fullGeometry = null;
|
||||
},
|
||||
|
||||
_onPan: function(action) {
|
||||
@@ -563,7 +590,8 @@ const WorkspacesDisplay = new Lang.Class({
|
||||
this._workspacesViews.push(view);
|
||||
}
|
||||
|
||||
this._updateWorkspacesGeometry();
|
||||
this._updateWorkspacesFullGeometry();
|
||||
this._updateWorkspacesActualGeometry();
|
||||
|
||||
for (let i = 0; i < this._workspacesViews.length; i++)
|
||||
global.overlay_group.add_actor(this._workspacesViews[i].actor);
|
||||
@@ -623,31 +651,48 @@ const WorkspacesDisplay = new Lang.Class({
|
||||
}));
|
||||
},
|
||||
|
||||
_updateWorkspacesGeometry: function() {
|
||||
// This geometry should always be the fullest geometry
|
||||
// the workspaces switcher can ever be allocated, as if
|
||||
// the sliding controls were never slid in at all.
|
||||
setWorkspacesFullGeometry: function(geom) {
|
||||
this._fullGeometry = geom;
|
||||
this._updateWorkspacesFullGeometry();
|
||||
},
|
||||
|
||||
_updateWorkspacesFullGeometry: function() {
|
||||
if (!this._workspacesViews.length)
|
||||
return;
|
||||
|
||||
let fullWidth = this.actor.allocation.x2 - this.actor.allocation.x1;
|
||||
let fullHeight = this.actor.allocation.y2 - this.actor.allocation.y1;
|
||||
|
||||
let width = fullWidth;
|
||||
let height = fullHeight;
|
||||
|
||||
let [x, y] = this.actor.get_transformed_position();
|
||||
|
||||
let rtl = (Clutter.get_default_text_direction () == Clutter.TextDirection.RTL);
|
||||
|
||||
let monitors = Main.layoutManager.monitors;
|
||||
let m = 0;
|
||||
for (let i = 0; i < monitors.length; i++) {
|
||||
if (i == this._primaryIndex) {
|
||||
this._workspacesViews[m].setGeometry(x, y, width, height);
|
||||
this._workspacesViews[m].setFullGeometry(this._fullGeometry);
|
||||
m++;
|
||||
} else if (!this._workspacesOnlyOnPrimary) {
|
||||
this._workspacesViews[m].setGeometry(monitors[i].x,
|
||||
monitors[i].y,
|
||||
monitors[i].width,
|
||||
monitors[i].height);
|
||||
this._workspacesViews[m].setFullGeometry(monitors[i]);
|
||||
m++;
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
_updateWorkspacesActualGeometry: function() {
|
||||
if (!this._workspacesViews.length)
|
||||
return;
|
||||
|
||||
let [x, y] = this.actor.get_transformed_position();
|
||||
let width = this.actor.allocation.x2 - this.actor.allocation.x1;
|
||||
let height = this.actor.allocation.y2 - this.actor.allocation.y1;
|
||||
let geometry = { x: x, y: y, width: width, height: height };
|
||||
|
||||
let monitors = Main.layoutManager.monitors;
|
||||
let m = 0;
|
||||
for (let i = 0; i < monitors.length; i++) {
|
||||
if (i == this._primaryIndex) {
|
||||
this._workspacesViews[m].setActualGeometry(geometry);
|
||||
m++;
|
||||
} else if (!this._workspacesOnlyOnPrimary) {
|
||||
this._workspacesViews[m].setActualGeometry(monitors[i]);
|
||||
m++;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -28,6 +28,7 @@ gu
|
||||
he
|
||||
hi
|
||||
hu
|
||||
ia
|
||||
id
|
||||
it
|
||||
ja
|
||||
@@ -60,6 +61,7 @@ sr@latin
|
||||
sv
|
||||
ta
|
||||
te
|
||||
tg
|
||||
th
|
||||
tr
|
||||
ug
|
||||
|
||||
@@ -55,6 +55,7 @@ js/ui/viewSelector.js
|
||||
js/ui/wanda.js
|
||||
js/ui/windowAttentionHandler.js
|
||||
src/calendar-server/evolution-calendar.desktop.in.in
|
||||
# Please do not remove this file from POTFILES.in. Run "git submodule init && git submodule update" to get it.
|
||||
src/gvc/gvc-mixer-control.c
|
||||
src/main.c
|
||||
src/shell-app.c
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
239
po/el.po
239
po/el.po
@@ -5,8 +5,8 @@ msgstr ""
|
||||
"Project-Id-Version: gnome-shell.po.master\n"
|
||||
"Report-Msgid-Bugs-To: http://bugzilla.gnome.org/enter_bug.cgi?product=gnome-"
|
||||
"shell&keywords=I18N+L10N&component=general\n"
|
||||
"POT-Creation-Date: 2013-03-02 23:02+0000\n"
|
||||
"PO-Revision-Date: 2013-03-03 13:22+0300\n"
|
||||
"POT-Creation-Date: 2013-04-19 02:48+0000\n"
|
||||
"PO-Revision-Date: 2013-04-25 08:11+0300\n"
|
||||
"Last-Translator: Dimitris Spingos (Δημήτρης Σπίγγος) <dmtrs32@gmail.com>\n"
|
||||
"Language-Team: team@gnome.gr\n"
|
||||
"Language: el\n"
|
||||
@@ -40,10 +40,14 @@ msgid "Focus the active notification"
|
||||
msgstr "Εστίαση στην ενεργή ειδοποίηση"
|
||||
|
||||
#: ../data/50-gnome-shell-system.xml.in.h:4
|
||||
msgid "Show the overview"
|
||||
msgstr "Εμφάνιση της επισκόπησης"
|
||||
|
||||
#: ../data/50-gnome-shell-system.xml.in.h:5
|
||||
msgid "Show all applications"
|
||||
msgstr "Προβολή όλων των εφαρμογών"
|
||||
|
||||
#: ../data/50-gnome-shell-system.xml.in.h:5
|
||||
#: ../data/50-gnome-shell-system.xml.in.h:6
|
||||
msgid "Open the application menu"
|
||||
msgstr "Άνοιγμα του μενού εφαρμογών"
|
||||
|
||||
@@ -223,45 +227,55 @@ msgstr ""
|
||||
"επισκόπησης ενεργειών."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:25
|
||||
#| msgid "Keybinding to open the \"Show Applications\" view"
|
||||
msgid "Keybinding to open the overview"
|
||||
msgstr "Συνδυασμός πλήκτρων για το άνοιγμα της επισκόπησης"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:26
|
||||
#| msgid "Keybinding to open the \"Show Applications\" view"
|
||||
msgid "Keybinding to open the Activities Overview."
|
||||
msgstr "Συνδυασμός πλήκτρων για το άνοιγμα της προβολής ενέργειες."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:27
|
||||
msgid "Keybinding to toggle the visibility of the message tray"
|
||||
msgstr "Συνδυασμός πλήκτρων για την ορατότητα της περιοχής ειδοποιήσεων"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:26
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:28
|
||||
msgid "Keybinding to toggle the visibility of the message tray."
|
||||
msgstr "Συνδυασμός πλήκτρων για την ορατότητα της περιοχής ειδοποιήσεων."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:27
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:29
|
||||
msgid "Keybinding to focus the active notification"
|
||||
msgstr "Ο συνδυασμός πλήκτρων για εστίαση της ενεργής ειδοποίησης"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:28
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:30
|
||||
msgid "Keybinding to focus the active notification."
|
||||
msgstr "Ο συνδυασμός πλήκτρων για εστίαση της ενεργής ειδοποίησης."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:29
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:31
|
||||
msgid "Keybinding to toggle the screen recorder"
|
||||
msgstr "Συνδυασμός πλήκτρων για την εναλλαγή της μαγνητοσκόπησης οθόνης"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:30
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:32
|
||||
msgid "Keybinding to start/stop the builtin screen recorder."
|
||||
msgstr ""
|
||||
"Συνδυασμός πλήκτρων για το άνοιγμα/κλείσιμο της ενσωματωμένης "
|
||||
"μαγνητοσκόπησης οθόνης."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:31
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:33
|
||||
msgid "Which keyboard to use"
|
||||
msgstr "Ποιο πληκτρολόγιο θα χρησιμοποιηθεί"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:32
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:34
|
||||
msgid "The type of keyboard to use."
|
||||
msgstr "Ο τύπος του πληκτρολογίου που θα χρησιμοποιηθεί."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:33
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:35
|
||||
msgid "Framerate used for recording screencasts."
|
||||
msgstr ""
|
||||
"Ο ρυθμός καρέ που θα χρησιμοποιηθεί για την καταγραφή του βίντεο οθόνης."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:34
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:36
|
||||
msgid ""
|
||||
"The framerate of the resulting screencast recordered by GNOME Shell's "
|
||||
"screencast recorder in frames-per-second."
|
||||
@@ -269,13 +283,13 @@ msgstr ""
|
||||
"Ο ρυθμός καρέ του στιγμιότυπου που παράγεται από τον εγγραφέα βίντεο οθόνης "
|
||||
"του GNOME Shell σε καρέ ανά δευτερόλεπτο."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:35
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:37
|
||||
msgid "The gstreamer pipeline used to encode the screencast"
|
||||
msgstr ""
|
||||
"Ο δίαυλος του gstreamer που χρησιμοποιήθηκε για την κωδικοποίηση του βίντεο "
|
||||
"οθόνης"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:37
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:39
|
||||
#, no-c-format
|
||||
msgid ""
|
||||
"Sets the GStreamer pipeline used to encode recordings. It follows the syntax "
|
||||
@@ -303,12 +317,12 @@ msgstr ""
|
||||
"χρησιμοποιείται ως παράδειγμα για το πιθανό βέλτιστο αριθμό πυρήνων του "
|
||||
"συστήματος."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:38
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:40
|
||||
msgid "File extension used for storing the screencast"
|
||||
msgstr ""
|
||||
"Επέκταση αρχείου που θα χρησιμοποιηθεί για την αποθήκευση του βίντεο οθόνης"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:39
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:41
|
||||
msgid ""
|
||||
"The filename for recorded screencasts will be a unique filename based on the "
|
||||
"current date, and use this extension. It should be changed when recording to "
|
||||
@@ -318,11 +332,11 @@ msgstr ""
|
||||
"βασισμένο στην τρέχουσα ημερομηνία και θα χρησιμοποιεί αυτή την επέκταση. Θα "
|
||||
"πρέπει να αλλάζει όταν γίνεται εγγραφή σε διαφορετικό πρότυπο περιέκτη."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:40
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:42
|
||||
msgid "The application icon mode."
|
||||
msgstr "Η κατάσταση εικονιδίου εφαρμογής."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:41
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:43
|
||||
msgid ""
|
||||
"Configures how the windows are shown in the switcher. Valid possibilities "
|
||||
"are 'thumbnail-only' (shows a thumbnail of the window), 'app-icon-"
|
||||
@@ -333,22 +347,22 @@ msgstr ""
|
||||
"παραθύρου), 'app-icon-only' (εμφανίζει μόνο το εικονίδιο της εφαρμογής) ή "
|
||||
"'both' - και τα δύο."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:42
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:44
|
||||
msgid "Attach modal dialog to the parent window"
|
||||
msgstr "Προσάρτηση αναγκαστικού διαλόγου στο γονικό παράθυρο"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:43
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:45
|
||||
msgid ""
|
||||
"This key overrides the key in org.gnome.mutter when running GNOME Shell."
|
||||
msgstr ""
|
||||
"Αυτό το κλειδί υπερισχύει του κλειδιού στο org.gnome.mutter όταν εκτελείται "
|
||||
"το κέλυφος GNOME."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:44
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:46
|
||||
msgid "Arrangement of buttons on the titlebar"
|
||||
msgstr "Διάταξη των κουμπιών στη γραμμή τίτλου"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:45
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:47
|
||||
msgid ""
|
||||
"This key overrides the key in org.gnome.desktop.wm.preferences when running "
|
||||
"GNOME Shell."
|
||||
@@ -356,17 +370,17 @@ msgstr ""
|
||||
"Αυτό το κλειδί υπερισχύει του κλειδιού στο org.gnome.desktop.wm.preferences "
|
||||
"όταν εκτελείται το κέλυφος GNOME."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:46
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:48
|
||||
msgid "Enable edge tiling when dropping windows on screen edges"
|
||||
msgstr ""
|
||||
"Ενεργοποίηση της παράθεσης άκρων όταν αποθέτετε παράθυρα στις άκρες της "
|
||||
"οθόνης"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:47
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:49
|
||||
msgid "Workspaces are managed dynamically"
|
||||
msgstr "Οι χώροι εργασίας διαχειρίζονται δυναμικά"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:48
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:50
|
||||
msgid "Workspaces only on primary monitor"
|
||||
msgstr "Χώροι εργασίας μόνο στην κύρια οθόνη"
|
||||
|
||||
@@ -388,43 +402,42 @@ msgstr ""
|
||||
"πολλαπλών επιλογών."
|
||||
|
||||
#: ../js/gdm/loginDialog.js:405
|
||||
#| msgid "Session..."
|
||||
msgid "Session…"
|
||||
msgstr "Συνεδρία…"
|
||||
|
||||
#. translators: this message is shown below the user list on the
|
||||
#. login screen. It can be activated to reveal an entry for
|
||||
#. manually entering the username.
|
||||
#: ../js/gdm/loginDialog.js:629
|
||||
#: ../js/gdm/loginDialog.js:630
|
||||
msgid "Not listed?"
|
||||
msgstr "Δεν είστε στη λίστα;"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:783 ../js/ui/components/networkAgent.js:137
|
||||
#: ../js/ui/components/polkitAgent.js:162 ../js/ui/endSessionDialog.js:375
|
||||
#: ../js/gdm/loginDialog.js:787 ../js/ui/components/networkAgent.js:137
|
||||
#: ../js/ui/components/polkitAgent.js:162 ../js/ui/endSessionDialog.js:376
|
||||
#: ../js/ui/extensionDownloader.js:195 ../js/ui/shellMountOperation.js:399
|
||||
#: ../js/ui/status/bluetooth.js:415 ../js/ui/unlockDialog.js:126
|
||||
#: ../js/ui/userMenu.js:932
|
||||
#: ../js/ui/status/bluetooth.js:415 ../js/ui/unlockDialog.js:100
|
||||
#: ../js/ui/userMenu.js:938
|
||||
msgid "Cancel"
|
||||
msgstr "Ακύρωση"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:799
|
||||
#: ../js/gdm/loginDialog.js:803
|
||||
msgctxt "button"
|
||||
msgid "Sign In"
|
||||
msgstr "Σύνδεση"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:799
|
||||
#: ../js/gdm/loginDialog.js:803
|
||||
msgid "Next"
|
||||
msgstr "Επόμενο"
|
||||
|
||||
#. TTLS and PEAP are actually much more complicated, but this complication
|
||||
#. is not visible here since we only care about phase2 authentication
|
||||
#. (and don't even care of which one)
|
||||
#: ../js/gdm/loginDialog.js:904 ../js/ui/components/networkAgent.js:260
|
||||
#: ../js/gdm/loginDialog.js:918 ../js/ui/components/networkAgent.js:260
|
||||
#: ../js/ui/components/networkAgent.js:278
|
||||
msgid "Username: "
|
||||
msgstr "Όνομα χρήστη: "
|
||||
|
||||
#: ../js/gdm/loginDialog.js:1157
|
||||
#: ../js/gdm/loginDialog.js:1174
|
||||
msgid "Login Window"
|
||||
msgstr "Παράθυρο σύνδεσης"
|
||||
|
||||
@@ -433,8 +446,8 @@ msgstr "Παράθυρο σύνδεσης"
|
||||
msgid "Power"
|
||||
msgstr "Ενέργεια"
|
||||
|
||||
#: ../js/gdm/powerMenu.js:93 ../js/ui/userMenu.js:694 ../js/ui/userMenu.js:698
|
||||
#: ../js/ui/userMenu.js:814
|
||||
#: ../js/gdm/powerMenu.js:93 ../js/ui/userMenu.js:696 ../js/ui/userMenu.js:700
|
||||
#: ../js/ui/userMenu.js:816
|
||||
msgid "Suspend"
|
||||
msgstr "Αναστολή"
|
||||
|
||||
@@ -442,58 +455,58 @@ msgstr "Αναστολή"
|
||||
msgid "Restart"
|
||||
msgstr "Επανεκκίνηση"
|
||||
|
||||
#: ../js/gdm/powerMenu.js:103 ../js/ui/userMenu.js:696
|
||||
#: ../js/ui/userMenu.js:698 ../js/ui/userMenu.js:813 ../js/ui/userMenu.js:936
|
||||
#: ../js/gdm/powerMenu.js:103 ../js/ui/userMenu.js:698
|
||||
#: ../js/ui/userMenu.js:700 ../js/ui/userMenu.js:815 ../js/ui/userMenu.js:942
|
||||
msgid "Power Off"
|
||||
msgstr "Απενεργοποίηση"
|
||||
|
||||
#: ../js/gdm/util.js:182
|
||||
#: ../js/gdm/util.js:249
|
||||
msgid "Authentication error"
|
||||
msgstr "Σφάλμα πιστοποίησης"
|
||||
|
||||
#. Translators: this message is shown below the password entry field
|
||||
#. to indicate the user can swipe their finger instead
|
||||
#: ../js/gdm/util.js:299
|
||||
#: ../js/gdm/util.js:366
|
||||
msgid "(or swipe finger)"
|
||||
msgstr "(ή περάστε το δάκτυλο σας)"
|
||||
|
||||
#: ../js/gdm/util.js:324
|
||||
#: ../js/gdm/util.js:391
|
||||
#, c-format
|
||||
msgid "(e.g., user or %s)"
|
||||
msgstr "(π.χ χρήστης ή %s)"
|
||||
|
||||
#: ../js/misc/util.js:94
|
||||
#: ../js/misc/util.js:97
|
||||
msgid "Command not found"
|
||||
msgstr "Δε βρέθηκε η εντολή"
|
||||
|
||||
#. Replace "Error invoking GLib.shell_parse_argv: " with
|
||||
#. something nicer
|
||||
#: ../js/misc/util.js:127
|
||||
#: ../js/misc/util.js:130
|
||||
msgid "Could not parse command:"
|
||||
msgstr "Δεν ήταν δυνατό να επεξεργαστεί η εντολή:"
|
||||
|
||||
#: ../js/misc/util.js:135
|
||||
#: ../js/misc/util.js:138
|
||||
#, c-format
|
||||
msgid "Execution of '%s' failed:"
|
||||
msgstr "Η εκτέλεση του '%s' απέτυχε:"
|
||||
|
||||
#: ../js/ui/appDisplay.js:348
|
||||
#: ../js/ui/appDisplay.js:349
|
||||
msgid "Frequent"
|
||||
msgstr "Συχνό"
|
||||
|
||||
#: ../js/ui/appDisplay.js:355
|
||||
#: ../js/ui/appDisplay.js:356
|
||||
msgid "All"
|
||||
msgstr "Όλα"
|
||||
|
||||
#: ../js/ui/appDisplay.js:913
|
||||
#: ../js/ui/appDisplay.js:914
|
||||
msgid "New Window"
|
||||
msgstr "Νέο παράθυρο"
|
||||
|
||||
#: ../js/ui/appDisplay.js:916 ../js/ui/dash.js:284
|
||||
#: ../js/ui/appDisplay.js:917 ../js/ui/dash.js:284
|
||||
msgid "Remove from Favorites"
|
||||
msgstr "Αφαίρεση από τα αγαπημένα"
|
||||
|
||||
#: ../js/ui/appDisplay.js:917
|
||||
#: ../js/ui/appDisplay.js:918
|
||||
msgid "Add to Favorites"
|
||||
msgstr "Προσθήκη στα αγαπημένα"
|
||||
|
||||
@@ -507,7 +520,7 @@ msgstr "Tο %s προστέθηκε στα αγαπημένα σας."
|
||||
msgid "%s has been removed from your favorites."
|
||||
msgstr "Tο %s αφαιρέθηκε από τα αγαπημένα σας."
|
||||
|
||||
#: ../js/ui/backgroundMenu.js:19 ../js/ui/userMenu.js:787
|
||||
#: ../js/ui/backgroundMenu.js:19 ../js/ui/userMenu.js:789
|
||||
msgid "Settings"
|
||||
msgstr "Ρυθμίσεις"
|
||||
|
||||
@@ -530,7 +543,7 @@ msgctxt "event list time"
|
||||
msgid "%H\\u2236%M"
|
||||
msgstr "%Ω\\u2236%Λ"
|
||||
|
||||
#. Transators: Shown in calendar event list, if 12h format,
|
||||
#. Translators: Shown in calendar event list, if 12h format,
|
||||
#. \u2236 is a ratio character, similar to : and \u2009 is
|
||||
#. a thin space
|
||||
#: ../js/ui/calendar.js:77
|
||||
@@ -632,35 +645,35 @@ msgid "S"
|
||||
msgstr "Σ"
|
||||
|
||||
#. Translators: Text to show if there are no events
|
||||
#: ../js/ui/calendar.js:692
|
||||
#: ../js/ui/calendar.js:720
|
||||
msgid "Nothing Scheduled"
|
||||
msgstr "Τίποτα προγραμματισμένο"
|
||||
|
||||
#. Translators: Shown on calendar heading when selected day occurs on current year
|
||||
#: ../js/ui/calendar.js:708
|
||||
#: ../js/ui/calendar.js:736
|
||||
msgctxt "calendar heading"
|
||||
msgid "%A, %B %d"
|
||||
msgstr "%A, %B %d"
|
||||
|
||||
#. Translators: Shown on calendar heading when selected day occurs on different year
|
||||
#: ../js/ui/calendar.js:711
|
||||
#: ../js/ui/calendar.js:739
|
||||
msgctxt "calendar heading"
|
||||
msgid "%A, %B %d, %Y"
|
||||
msgstr "%A, %B %d, %Y"
|
||||
|
||||
#: ../js/ui/calendar.js:721
|
||||
#: ../js/ui/calendar.js:749
|
||||
msgid "Today"
|
||||
msgstr "Σήμερα"
|
||||
|
||||
#: ../js/ui/calendar.js:725
|
||||
#: ../js/ui/calendar.js:753
|
||||
msgid "Tomorrow"
|
||||
msgstr "Αύριο"
|
||||
|
||||
#: ../js/ui/calendar.js:736
|
||||
#: ../js/ui/calendar.js:764
|
||||
msgid "This week"
|
||||
msgstr "Αυτή η εβδομάδα"
|
||||
|
||||
#: ../js/ui/calendar.js:744
|
||||
#: ../js/ui/calendar.js:772
|
||||
msgid "Next week"
|
||||
msgstr "Επόμενη εβδομάδα"
|
||||
|
||||
@@ -676,12 +689,12 @@ msgstr "Αποσυνδέθηκε εξωτερικός δίσκος"
|
||||
msgid "Removable Devices"
|
||||
msgstr "Αφαιρούμενες συσκευές"
|
||||
|
||||
#: ../js/ui/components/autorunManager.js:593
|
||||
#: ../js/ui/components/autorunManager.js:594
|
||||
#, c-format
|
||||
msgid "Open with %s"
|
||||
msgstr "Άνοιγμα με %s"
|
||||
|
||||
#: ../js/ui/components/autorunManager.js:619
|
||||
#: ../js/ui/components/autorunManager.js:620
|
||||
msgid "Eject"
|
||||
msgstr "Εξαγωγή"
|
||||
|
||||
@@ -790,7 +803,7 @@ msgid "Sorry, that didn't work. Please try again."
|
||||
msgstr "Συγνώμη, αυτό δεν λειτούργησε. Παρακαλώ προσπαθήστε ξανά."
|
||||
|
||||
#. Translators: this is a filename used for screencast recording
|
||||
#: ../js/ui/components/recorder.js:48
|
||||
#: ../js/ui/components/recorder.js:47
|
||||
#, no-c-format
|
||||
msgid "Screencast from %d %t"
|
||||
msgstr "Βίντεο οθόνης από %d %t"
|
||||
@@ -1037,7 +1050,7 @@ msgstr "Προβολή λογαριασμού"
|
||||
msgid "Unknown reason"
|
||||
msgstr "Άγνωστος λόγος"
|
||||
|
||||
#: ../js/ui/ctrlAltTab.js:29 ../js/ui/viewSelector.js:97
|
||||
#: ../js/ui/ctrlAltTab.js:29 ../js/ui/viewSelector.js:96
|
||||
msgid "Windows"
|
||||
msgstr "Παράθυρα"
|
||||
|
||||
@@ -1066,7 +1079,7 @@ msgstr "Ρυθμίσεις ημερομηνίας & ώρας"
|
||||
#. Translators: This is the date format to use when the calendar popup is
|
||||
#. * shown - it is shown just below the time in the shell (e.g. "Tue 9:29 AM").
|
||||
#.
|
||||
#: ../js/ui/dateMenu.js:205
|
||||
#: ../js/ui/dateMenu.js:215
|
||||
msgid "%A %B %e, %Y"
|
||||
msgstr "%A %B %e, %Y"
|
||||
|
||||
@@ -1235,7 +1248,6 @@ msgid "Remove"
|
||||
msgstr "Αφαίρεση"
|
||||
|
||||
#: ../js/ui/messageTray.js:1501
|
||||
#| msgid "No Messages"
|
||||
msgid "Clear Messages"
|
||||
msgstr "Καθαρισμός μηνυμάτων"
|
||||
|
||||
@@ -1243,15 +1255,15 @@ msgstr "Καθαρισμός μηνυμάτων"
|
||||
msgid "Notification Settings"
|
||||
msgstr "Ρυθμίσεις ειδοποιήσεων"
|
||||
|
||||
#: ../js/ui/messageTray.js:1707
|
||||
#: ../js/ui/messageTray.js:1709
|
||||
msgid "No Messages"
|
||||
msgstr "Κανένα μήνυμα"
|
||||
|
||||
#: ../js/ui/messageTray.js:1787
|
||||
#: ../js/ui/messageTray.js:1785
|
||||
msgid "Message Tray"
|
||||
msgstr "Περιοχή ειδοποιήσεων"
|
||||
|
||||
#: ../js/ui/messageTray.js:2864
|
||||
#: ../js/ui/messageTray.js:2813
|
||||
msgid "System Information"
|
||||
msgstr "Πληροφορίες συστήματος"
|
||||
|
||||
@@ -1260,14 +1272,14 @@ msgctxt "program"
|
||||
msgid "Unknown"
|
||||
msgstr "Άγνωστο"
|
||||
|
||||
#: ../js/ui/overviewControls.js:460 ../js/ui/screenShield.js:153
|
||||
#: ../js/ui/overviewControls.js:463 ../js/ui/screenShield.js:149
|
||||
#, c-format
|
||||
msgid "%d new message"
|
||||
msgid_plural "%d new messages"
|
||||
msgstr[0] "%d νέο μήνυμα"
|
||||
msgstr[1] "%d νέα μηνύματα"
|
||||
|
||||
#: ../js/ui/overview.js:82
|
||||
#: ../js/ui/overview.js:84
|
||||
msgid "Undo"
|
||||
msgstr "Αναίρεση"
|
||||
|
||||
@@ -1279,22 +1291,21 @@ msgstr "Επισκόπηση"
|
||||
#. in the search entry when no search is
|
||||
#. active; it should not exceed ~30
|
||||
#. characters.
|
||||
#: ../js/ui/overview.js:284
|
||||
#| msgid "Type to search..."
|
||||
#: ../js/ui/overview.js:271
|
||||
msgid "Type to search…"
|
||||
msgstr "Πληκτρολογήστε για αναζήτηση…"
|
||||
|
||||
#: ../js/ui/panel.js:613
|
||||
#: ../js/ui/panel.js:633
|
||||
msgid "Quit"
|
||||
msgstr "Έξοδος"
|
||||
|
||||
#. Translators: If there is no suitable word for "Activities"
|
||||
#. in your language, you can use the word for "Overview".
|
||||
#: ../js/ui/panel.js:642
|
||||
#: ../js/ui/panel.js:657
|
||||
msgid "Activities"
|
||||
msgstr "Δραστηριότητες"
|
||||
|
||||
#: ../js/ui/panel.js:983
|
||||
#: ../js/ui/panel.js:954
|
||||
msgid "Top Bar"
|
||||
msgstr "Πάνω μπάρα"
|
||||
|
||||
@@ -1307,32 +1318,32 @@ msgstr "Πάνω μπάρα"
|
||||
msgid "toggle-switch-us"
|
||||
msgstr "toggle-switch-intl"
|
||||
|
||||
#: ../js/ui/runDialog.js:205
|
||||
#: ../js/ui/runDialog.js:74
|
||||
msgid "Enter a Command"
|
||||
msgstr "Εισαγωγή εντολής"
|
||||
|
||||
#: ../js/ui/runDialog.js:241
|
||||
#: ../js/ui/runDialog.js:110
|
||||
msgid "Close"
|
||||
msgstr "Κλείσιμο"
|
||||
|
||||
#. Translators: This is a time format for a date in
|
||||
#. long format
|
||||
#: ../js/ui/screenShield.js:90
|
||||
#: ../js/ui/screenShield.js:86
|
||||
msgid "%A, %B %d"
|
||||
msgstr "%A, %B %d"
|
||||
|
||||
#: ../js/ui/screenShield.js:155
|
||||
#: ../js/ui/screenShield.js:151
|
||||
#, c-format
|
||||
msgid "%d new notification"
|
||||
msgid_plural "%d new notifications"
|
||||
msgstr[0] "%d νέα ειδοποίηση"
|
||||
msgstr[1] "%d νέες ειδοποιήσεις"
|
||||
|
||||
#: ../js/ui/screenShield.js:442 ../js/ui/userMenu.js:805
|
||||
#: ../js/ui/screenShield.js:438 ../js/ui/userMenu.js:807
|
||||
msgid "Lock"
|
||||
msgstr "Κλείδωμα"
|
||||
|
||||
#: ../js/ui/screenShield.js:639
|
||||
#: ../js/ui/screenShield.js:641
|
||||
msgid "GNOME needs to lock the screen"
|
||||
msgstr "Το GNOME χρειάζεται να κλειδώσει την οθόνη"
|
||||
|
||||
@@ -1343,21 +1354,19 @@ msgstr "Το GNOME χρειάζεται να κλειδώσει την οθόν
|
||||
#.
|
||||
#. XXX: another option is to kick the user into the gdm login
|
||||
#. screen, where we're not affected by grabs
|
||||
#: ../js/ui/screenShield.js:758 ../js/ui/screenShield.js:1169
|
||||
#| msgid "Unable to connect to %s"
|
||||
#: ../js/ui/screenShield.js:762 ../js/ui/screenShield.js:1198
|
||||
msgid "Unable to lock"
|
||||
msgstr "Αδυναμία κλειδώματος"
|
||||
|
||||
#: ../js/ui/screenShield.js:759 ../js/ui/screenShield.js:1170
|
||||
#: ../js/ui/screenShield.js:763 ../js/ui/screenShield.js:1199
|
||||
msgid "Lock was blocked by an application"
|
||||
msgstr "Το κλείδωμα εμποδίστηκε από μια εφαρμογή"
|
||||
|
||||
#: ../js/ui/searchDisplay.js:431
|
||||
#| msgid "Searching..."
|
||||
#: ../js/ui/searchDisplay.js:453
|
||||
msgid "Searching…"
|
||||
msgstr "Αναζήτηση…"
|
||||
|
||||
#: ../js/ui/searchDisplay.js:475
|
||||
#: ../js/ui/searchDisplay.js:497
|
||||
msgid "No results."
|
||||
msgstr "Δε βρέθηκαν αποτελέσματα."
|
||||
|
||||
@@ -1369,11 +1378,11 @@ msgstr "Αντιγραφή"
|
||||
msgid "Paste"
|
||||
msgstr "Επικόλληση"
|
||||
|
||||
#: ../js/ui/shellEntry.js:105
|
||||
#: ../js/ui/shellEntry.js:101
|
||||
msgid "Show Text"
|
||||
msgstr "Εμφάνιση κειμένου"
|
||||
|
||||
#: ../js/ui/shellEntry.js:107
|
||||
#: ../js/ui/shellEntry.js:103
|
||||
msgid "Hide Text"
|
||||
msgstr "Απόκρυψη κειμένου"
|
||||
|
||||
@@ -1385,7 +1394,7 @@ msgstr "Κωδικός"
|
||||
msgid "Remember Password"
|
||||
msgstr "Απομνημόνευση κωδικού"
|
||||
|
||||
#: ../js/ui/shellMountOperation.js:403 ../js/ui/unlockDialog.js:140
|
||||
#: ../js/ui/shellMountOperation.js:403 ../js/ui/unlockDialog.js:114
|
||||
msgid "Unlock"
|
||||
msgstr "Ξεκλείδωμα"
|
||||
|
||||
@@ -1449,12 +1458,10 @@ msgid "Visibility"
|
||||
msgstr "Ορατότητα"
|
||||
|
||||
#: ../js/ui/status/bluetooth.js:59
|
||||
#| msgid "Send Files to Device..."
|
||||
msgid "Send Files to Device…"
|
||||
msgstr "Αποστολή αρχείων σε συσκευή…"
|
||||
|
||||
#: ../js/ui/status/bluetooth.js:60
|
||||
#| msgid "Set Up a New Device..."
|
||||
msgid "Set Up a New Device…"
|
||||
msgstr "Ρύθμιση νέας συσκευής…"
|
||||
|
||||
@@ -1481,7 +1488,6 @@ msgid "connecting..."
|
||||
msgstr "σύνδεση..."
|
||||
|
||||
#: ../js/ui/status/bluetooth.js:239
|
||||
#| msgid "Send Files..."
|
||||
msgid "Send Files…"
|
||||
msgstr "Αποστολή αρχείων…"
|
||||
|
||||
@@ -1694,7 +1700,6 @@ msgstr "Ρυθμίσεις τροφοδοσίας"
|
||||
#. 0 is reported when UPower does not have enough data
|
||||
#. to estimate battery life
|
||||
#: ../js/ui/status/power.js:99
|
||||
#| msgid "Estimating..."
|
||||
msgid "Estimating…"
|
||||
msgstr "Υπολογισμός…"
|
||||
|
||||
@@ -1794,59 +1799,59 @@ msgstr "Ένταση ήχου"
|
||||
msgid "Microphone"
|
||||
msgstr "Μικρόφωνο"
|
||||
|
||||
#: ../js/ui/unlockDialog.js:151
|
||||
#: ../js/ui/unlockDialog.js:125
|
||||
msgid "Log in as another user"
|
||||
msgstr "Είσοδος ως άλλος χρήστης"
|
||||
|
||||
#: ../js/ui/unlockDialog.js:177
|
||||
#: ../js/ui/unlockDialog.js:146
|
||||
msgid "Unlock Window"
|
||||
msgstr "Ξεκλείδωμα παραθύρου"
|
||||
|
||||
#: ../js/ui/userMenu.js:192
|
||||
#: ../js/ui/userMenu.js:193
|
||||
msgid "Available"
|
||||
msgstr "Διαθέσιμος-η"
|
||||
|
||||
#: ../js/ui/userMenu.js:195
|
||||
#: ../js/ui/userMenu.js:196
|
||||
msgid "Busy"
|
||||
msgstr "Απασχολημένος-η"
|
||||
|
||||
#: ../js/ui/userMenu.js:198
|
||||
#: ../js/ui/userMenu.js:199
|
||||
msgid "Invisible"
|
||||
msgstr "Αόρατος-η"
|
||||
|
||||
#: ../js/ui/userMenu.js:201
|
||||
#: ../js/ui/userMenu.js:202
|
||||
msgid "Away"
|
||||
msgstr "Απουσιάζει"
|
||||
|
||||
#: ../js/ui/userMenu.js:204
|
||||
#: ../js/ui/userMenu.js:205
|
||||
msgid "Idle"
|
||||
msgstr "Αδρανής"
|
||||
|
||||
#: ../js/ui/userMenu.js:207
|
||||
#: ../js/ui/userMenu.js:208
|
||||
msgid "Offline"
|
||||
msgstr "Εκτός σύνδεσης"
|
||||
|
||||
#: ../js/ui/userMenu.js:779
|
||||
#: ../js/ui/userMenu.js:781
|
||||
msgid "Notifications"
|
||||
msgstr "Ειδοποιήσεις"
|
||||
|
||||
#: ../js/ui/userMenu.js:795
|
||||
#: ../js/ui/userMenu.js:797
|
||||
msgid "Switch User"
|
||||
msgstr "Αλλαγή χρήστη"
|
||||
|
||||
#: ../js/ui/userMenu.js:800
|
||||
#: ../js/ui/userMenu.js:802
|
||||
msgid "Log Out"
|
||||
msgstr "Αποσύνδεση"
|
||||
|
||||
#: ../js/ui/userMenu.js:820
|
||||
#: ../js/ui/userMenu.js:822
|
||||
msgid "Install Updates & Restart"
|
||||
msgstr "Εγκατάσταση ενημερώσεων & επανεκκίνηση"
|
||||
|
||||
#: ../js/ui/userMenu.js:838
|
||||
#: ../js/ui/userMenu.js:840
|
||||
msgid "Your chat status will be set to busy"
|
||||
msgstr "Η κατάσταση συνομιλίας σας θα ορισθεί σε απασχολημένος"
|
||||
|
||||
#: ../js/ui/userMenu.js:839
|
||||
#: ../js/ui/userMenu.js:841
|
||||
msgid ""
|
||||
"Notifications are now disabled, including chat messages. Your online status "
|
||||
"has been adjusted to let others know that you might not see their messages."
|
||||
@@ -1855,34 +1860,36 @@ msgstr ""
|
||||
"κατάσταση σας έχει ορισθεί έτσι ώστε να γίνεται γνωστό ότι πιθανόν να μην "
|
||||
"δείτε τα μηνύματα τους."
|
||||
|
||||
#: ../js/ui/userMenu.js:885
|
||||
#: ../js/ui/userMenu.js:888
|
||||
msgid "Other users are logged in."
|
||||
msgstr "Και άλλοι χρήστες είναι συνδεμένοι."
|
||||
|
||||
#: ../js/ui/userMenu.js:890
|
||||
#: ../js/ui/userMenu.js:893
|
||||
msgid "Shutting down might cause them to lose unsaved work."
|
||||
msgstr ""
|
||||
"Κλείνοντας μπορεί να τους προκαλέσετε την απώλεια αναποθήκευτης εργασίας."
|
||||
|
||||
#: ../js/ui/userMenu.js:916
|
||||
#. Translators: Remote here refers to a remote session, like a ssh login
|
||||
#: ../js/ui/userMenu.js:921
|
||||
#, c-format
|
||||
msgid "%s (remote)"
|
||||
msgstr "%s (απομακρυσμένο)"
|
||||
|
||||
#: ../js/ui/userMenu.js:918
|
||||
#. Translators: Console here refers to a tty like a VT console
|
||||
#: ../js/ui/userMenu.js:924
|
||||
#, c-format
|
||||
msgid "%s (console)"
|
||||
msgstr "%s (κονσόλα)"
|
||||
|
||||
#: ../js/ui/viewSelector.js:101
|
||||
#: ../js/ui/viewSelector.js:100
|
||||
msgid "Applications"
|
||||
msgstr "Εφαρμογές"
|
||||
|
||||
#: ../js/ui/viewSelector.js:105
|
||||
#: ../js/ui/viewSelector.js:104
|
||||
msgid "Search"
|
||||
msgstr "Αναζήτηση"
|
||||
|
||||
#: ../js/ui/wanda.js:92
|
||||
#: ../js/ui/wanda.js:77
|
||||
#, c-format
|
||||
msgid ""
|
||||
"Sorry, no wisdom for you today:\n"
|
||||
@@ -1891,7 +1898,7 @@ msgstr ""
|
||||
"Συγγνώμη, κανένα απόφθεγμα για εσάς σήμερα:\n"
|
||||
"%s"
|
||||
|
||||
#: ../js/ui/wanda.js:96
|
||||
#: ../js/ui/wanda.js:81
|
||||
#, c-format
|
||||
msgid "%s the Oracle says"
|
||||
msgstr "%s ο Προφήτης λέει"
|
||||
|
||||
1164
po/en_GB.po
1164
po/en_GB.po
File diff suppressed because it is too large
Load Diff
240
po/es.po
240
po/es.po
@@ -10,8 +10,8 @@ msgstr ""
|
||||
"Project-Id-Version: gnome-shell.master\n"
|
||||
"Report-Msgid-Bugs-To: http://bugzilla.gnome.org/enter_bug.cgi?product=gnome-"
|
||||
"shell&keywords=I18N+L10N&component=general\n"
|
||||
"POT-Creation-Date: 2013-03-02 23:02+0000\n"
|
||||
"PO-Revision-Date: 2013-03-04 13:44+0100\n"
|
||||
"POT-Creation-Date: 2013-04-19 02:48+0000\n"
|
||||
"PO-Revision-Date: 2013-04-22 17:40+0200\n"
|
||||
"Last-Translator: Daniel Mustieles <daniel.mustieles@gmail.com>\n"
|
||||
"Language-Team: Español <gnome-es-list@gnome.org>\n"
|
||||
"Language: \n"
|
||||
@@ -42,10 +42,14 @@ msgid "Focus the active notification"
|
||||
msgstr "Dar el foco a la notificación activa"
|
||||
|
||||
#: ../data/50-gnome-shell-system.xml.in.h:4
|
||||
msgid "Show the overview"
|
||||
msgstr "Mostrar la vista general"
|
||||
|
||||
#: ../data/50-gnome-shell-system.xml.in.h:5
|
||||
msgid "Show all applications"
|
||||
msgstr "Mostrar todas las aplicaciones"
|
||||
|
||||
#: ../data/50-gnome-shell-system.xml.in.h:5
|
||||
#: ../data/50-gnome-shell-system.xml.in.h:6
|
||||
msgid "Open the application menu"
|
||||
msgstr "Abrir el menú de la aplicación"
|
||||
|
||||
@@ -223,42 +227,52 @@ msgstr ""
|
||||
"de actividades."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:25
|
||||
#| msgid "Keybinding to open the \"Show Applications\" view"
|
||||
msgid "Keybinding to open the overview"
|
||||
msgstr "Asociación de teclas para la vista general"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:26
|
||||
#| msgid "Keybinding to open the \"Show Applications\" view"
|
||||
msgid "Keybinding to open the Activities Overview."
|
||||
msgstr "Asociación de teclas para abrir la Vista de actividades"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:27
|
||||
msgid "Keybinding to toggle the visibility of the message tray"
|
||||
msgstr "Asociación de teclas cambiar la visibilidad de la bandeja de mensajes"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:26
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:28
|
||||
msgid "Keybinding to toggle the visibility of the message tray."
|
||||
msgstr "Asociación de teclas cambiar la visibilidad de la bandeja de mensajes."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:27
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:29
|
||||
msgid "Keybinding to focus the active notification"
|
||||
msgstr "Asociación de teclas para dar el foco a la notificación activa"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:28
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:30
|
||||
msgid "Keybinding to focus the active notification."
|
||||
msgstr "Asociación de teclas para dar el foco a la notificación activa."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:29
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:31
|
||||
msgid "Keybinding to toggle the screen recorder"
|
||||
msgstr "Asociación de teclas cambiar el grabador de pantalla"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:30
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:32
|
||||
msgid "Keybinding to start/stop the builtin screen recorder."
|
||||
msgstr "Asociación de teclas para iniciar/detener el grabador de pantalla."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:31
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:33
|
||||
msgid "Which keyboard to use"
|
||||
msgstr "Qué teclado usar"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:32
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:34
|
||||
msgid "The type of keyboard to use."
|
||||
msgstr "El tipo de teclado que usar."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:33
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:35
|
||||
msgid "Framerate used for recording screencasts."
|
||||
msgstr "Tasa de fotogramas usada para grabar «screencast»."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:34
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:36
|
||||
msgid ""
|
||||
"The framerate of the resulting screencast recordered by GNOME Shell's "
|
||||
"screencast recorder in frames-per-second."
|
||||
@@ -266,11 +280,11 @@ msgstr ""
|
||||
"La tasa de fotogramas de la grabación resultante grabada por el grabador de "
|
||||
"«screencast» de GNOME Shell, en fotogramas por segundo."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:35
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:37
|
||||
msgid "The gstreamer pipeline used to encode the screencast"
|
||||
msgstr "La tubería de gstreamer usada para codificar el «screencast»"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:37
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:39
|
||||
#, no-c-format
|
||||
msgid ""
|
||||
"Sets the GStreamer pipeline used to encode recordings. It follows the syntax "
|
||||
@@ -296,11 +310,11 @@ msgstr ""
|
||||
"threads=%T ! queue ! webmmux» y graba en WEBM usando el códec VP8. Se usa %T "
|
||||
"como marcador de posición para el número de hilos óptimos en el sistema."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:38
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:40
|
||||
msgid "File extension used for storing the screencast"
|
||||
msgstr "Extensión de archivo que usar para almacenar los «screencast»"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:39
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:41
|
||||
msgid ""
|
||||
"The filename for recorded screencasts will be a unique filename based on the "
|
||||
"current date, and use this extension. It should be changed when recording to "
|
||||
@@ -310,11 +324,11 @@ msgstr ""
|
||||
"basado en la fecha actual y usará esta extensión. Se debería cambiar al "
|
||||
"grabar en otro formato contenedor diferente."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:40
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:42
|
||||
msgid "The application icon mode."
|
||||
msgstr "El modo de icono de la aplicación."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:41
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:43
|
||||
msgid ""
|
||||
"Configures how the windows are shown in the switcher. Valid possibilities "
|
||||
"are 'thumbnail-only' (shows a thumbnail of the window), 'app-icon-"
|
||||
@@ -324,21 +338,21 @@ msgstr ""
|
||||
"son «thumbnail-only» (muestra una miniatura de la ventana), «app-icon-"
|
||||
"only» (sólo muestra el icono de la aplicación) «both»."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:42
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:44
|
||||
msgid "Attach modal dialog to the parent window"
|
||||
msgstr "Acoplar un diálogo modal a la ventana padre"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:43
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:45
|
||||
msgid ""
|
||||
"This key overrides the key in org.gnome.mutter when running GNOME Shell."
|
||||
msgstr ""
|
||||
"Esta clave sobreescribe la clave en org.gnome.mutter al ejecutar GNOME Shell."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:44
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:46
|
||||
msgid "Arrangement of buttons on the titlebar"
|
||||
msgstr "Orden de los botones en la barra de título"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:45
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:47
|
||||
msgid ""
|
||||
"This key overrides the key in org.gnome.desktop.wm.preferences when running "
|
||||
"GNOME Shell."
|
||||
@@ -346,17 +360,17 @@ msgstr ""
|
||||
"Esta clave sobreescribe la clave en org.gnome.desktop.wm.preferences al "
|
||||
"ejecutar GNOME Shell."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:46
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:48
|
||||
msgid "Enable edge tiling when dropping windows on screen edges"
|
||||
msgstr ""
|
||||
"Activar el mosaico en los bordes al arrastrar ventanas a los bordes de la "
|
||||
"ventana"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:47
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:49
|
||||
msgid "Workspaces are managed dynamically"
|
||||
msgstr "Las áreas de trabajo se gestionan dinámicamente"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:48
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:50
|
||||
msgid "Workspaces only on primary monitor"
|
||||
msgstr "Áreas de trabajo solo en la pantalla principal"
|
||||
|
||||
@@ -375,43 +389,42 @@ msgstr ""
|
||||
"Seleccione una extensión que configurar usando la caja combinada de arriba."
|
||||
|
||||
#: ../js/gdm/loginDialog.js:405
|
||||
#| msgid "Session..."
|
||||
msgid "Session…"
|
||||
msgstr "Sesión…"
|
||||
|
||||
#. translators: this message is shown below the user list on the
|
||||
#. login screen. It can be activated to reveal an entry for
|
||||
#. manually entering the username.
|
||||
#: ../js/gdm/loginDialog.js:629
|
||||
#: ../js/gdm/loginDialog.js:630
|
||||
msgid "Not listed?"
|
||||
msgstr "¿No está en la lista?"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:783 ../js/ui/components/networkAgent.js:137
|
||||
#: ../js/ui/components/polkitAgent.js:162 ../js/ui/endSessionDialog.js:375
|
||||
#: ../js/gdm/loginDialog.js:787 ../js/ui/components/networkAgent.js:137
|
||||
#: ../js/ui/components/polkitAgent.js:162 ../js/ui/endSessionDialog.js:376
|
||||
#: ../js/ui/extensionDownloader.js:195 ../js/ui/shellMountOperation.js:399
|
||||
#: ../js/ui/status/bluetooth.js:415 ../js/ui/unlockDialog.js:126
|
||||
#: ../js/ui/userMenu.js:932
|
||||
#: ../js/ui/status/bluetooth.js:415 ../js/ui/unlockDialog.js:100
|
||||
#: ../js/ui/userMenu.js:938
|
||||
msgid "Cancel"
|
||||
msgstr "Cancelar"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:799
|
||||
#: ../js/gdm/loginDialog.js:803
|
||||
msgctxt "button"
|
||||
msgid "Sign In"
|
||||
msgstr "Iniciar sesión"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:799
|
||||
#: ../js/gdm/loginDialog.js:803
|
||||
msgid "Next"
|
||||
msgstr "Siguiente"
|
||||
|
||||
#. TTLS and PEAP are actually much more complicated, but this complication
|
||||
#. is not visible here since we only care about phase2 authentication
|
||||
#. (and don't even care of which one)
|
||||
#: ../js/gdm/loginDialog.js:904 ../js/ui/components/networkAgent.js:260
|
||||
#: ../js/gdm/loginDialog.js:918 ../js/ui/components/networkAgent.js:260
|
||||
#: ../js/ui/components/networkAgent.js:278
|
||||
msgid "Username: "
|
||||
msgstr "Nombre de usuario:"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:1157
|
||||
#: ../js/gdm/loginDialog.js:1174
|
||||
msgid "Login Window"
|
||||
msgstr "Ventana de inicio de sesión"
|
||||
|
||||
@@ -420,8 +433,8 @@ msgstr "Ventana de inicio de sesión"
|
||||
msgid "Power"
|
||||
msgstr "Energía"
|
||||
|
||||
#: ../js/gdm/powerMenu.js:93 ../js/ui/userMenu.js:694 ../js/ui/userMenu.js:698
|
||||
#: ../js/ui/userMenu.js:814
|
||||
#: ../js/gdm/powerMenu.js:93 ../js/ui/userMenu.js:696 ../js/ui/userMenu.js:700
|
||||
#: ../js/ui/userMenu.js:816
|
||||
msgid "Suspend"
|
||||
msgstr "Suspender"
|
||||
|
||||
@@ -429,58 +442,58 @@ msgstr "Suspender"
|
||||
msgid "Restart"
|
||||
msgstr "Reiniciar"
|
||||
|
||||
#: ../js/gdm/powerMenu.js:103 ../js/ui/userMenu.js:696
|
||||
#: ../js/ui/userMenu.js:698 ../js/ui/userMenu.js:813 ../js/ui/userMenu.js:936
|
||||
#: ../js/gdm/powerMenu.js:103 ../js/ui/userMenu.js:698
|
||||
#: ../js/ui/userMenu.js:700 ../js/ui/userMenu.js:815 ../js/ui/userMenu.js:942
|
||||
msgid "Power Off"
|
||||
msgstr "Apagar"
|
||||
|
||||
#: ../js/gdm/util.js:182
|
||||
#: ../js/gdm/util.js:249
|
||||
msgid "Authentication error"
|
||||
msgstr "Error de autenticación"
|
||||
|
||||
#. Translators: this message is shown below the password entry field
|
||||
#. to indicate the user can swipe their finger instead
|
||||
#: ../js/gdm/util.js:299
|
||||
#: ../js/gdm/util.js:366
|
||||
msgid "(or swipe finger)"
|
||||
msgstr "(o pase el dedo)"
|
||||
|
||||
#: ../js/gdm/util.js:324
|
||||
#: ../js/gdm/util.js:391
|
||||
#, c-format
|
||||
msgid "(e.g., user or %s)"
|
||||
msgstr "(ej., usuario o %s)"
|
||||
|
||||
#: ../js/misc/util.js:94
|
||||
#: ../js/misc/util.js:97
|
||||
msgid "Command not found"
|
||||
msgstr "Comando no encontrado"
|
||||
|
||||
#. Replace "Error invoking GLib.shell_parse_argv: " with
|
||||
#. something nicer
|
||||
#: ../js/misc/util.js:127
|
||||
#: ../js/misc/util.js:130
|
||||
msgid "Could not parse command:"
|
||||
msgstr "No se pudo analizar el comando:"
|
||||
|
||||
#: ../js/misc/util.js:135
|
||||
#: ../js/misc/util.js:138
|
||||
#, c-format
|
||||
msgid "Execution of '%s' failed:"
|
||||
msgstr "Falló la ejecución de «%s»:"
|
||||
|
||||
#: ../js/ui/appDisplay.js:348
|
||||
#: ../js/ui/appDisplay.js:349
|
||||
msgid "Frequent"
|
||||
msgstr "Frecuentes"
|
||||
|
||||
#: ../js/ui/appDisplay.js:355
|
||||
#: ../js/ui/appDisplay.js:356
|
||||
msgid "All"
|
||||
msgstr "Todas"
|
||||
|
||||
#: ../js/ui/appDisplay.js:913
|
||||
#: ../js/ui/appDisplay.js:914
|
||||
msgid "New Window"
|
||||
msgstr "Ventana nueva"
|
||||
|
||||
#: ../js/ui/appDisplay.js:916 ../js/ui/dash.js:284
|
||||
#: ../js/ui/appDisplay.js:917 ../js/ui/dash.js:284
|
||||
msgid "Remove from Favorites"
|
||||
msgstr "Quitar de los favoritos"
|
||||
|
||||
#: ../js/ui/appDisplay.js:917
|
||||
#: ../js/ui/appDisplay.js:918
|
||||
msgid "Add to Favorites"
|
||||
msgstr "Añadir a los favoritos"
|
||||
|
||||
@@ -494,7 +507,7 @@ msgstr "Se ha añadido %s a sus favoritos."
|
||||
msgid "%s has been removed from your favorites."
|
||||
msgstr "Se ha quitado %s de sus favoritos."
|
||||
|
||||
#: ../js/ui/backgroundMenu.js:19 ../js/ui/userMenu.js:787
|
||||
#: ../js/ui/backgroundMenu.js:19 ../js/ui/userMenu.js:789
|
||||
msgid "Settings"
|
||||
msgstr "Configuración"
|
||||
|
||||
@@ -517,7 +530,7 @@ msgctxt "event list time"
|
||||
msgid "%H\\u2236%M"
|
||||
msgstr "%H\\u2236%M"
|
||||
|
||||
#. Transators: Shown in calendar event list, if 12h format,
|
||||
#. Translators: Shown in calendar event list, if 12h format,
|
||||
#. \u2236 is a ratio character, similar to : and \u2009 is
|
||||
#. a thin space
|
||||
#: ../js/ui/calendar.js:77
|
||||
@@ -619,35 +632,35 @@ msgid "S"
|
||||
msgstr "S"
|
||||
|
||||
#. Translators: Text to show if there are no events
|
||||
#: ../js/ui/calendar.js:692
|
||||
#: ../js/ui/calendar.js:720
|
||||
msgid "Nothing Scheduled"
|
||||
msgstr "Nada programado"
|
||||
|
||||
#. Translators: Shown on calendar heading when selected day occurs on current year
|
||||
#: ../js/ui/calendar.js:708
|
||||
#: ../js/ui/calendar.js:736
|
||||
msgctxt "calendar heading"
|
||||
msgid "%A, %B %d"
|
||||
msgstr "%A, %d de %B"
|
||||
|
||||
#. Translators: Shown on calendar heading when selected day occurs on different year
|
||||
#: ../js/ui/calendar.js:711
|
||||
#: ../js/ui/calendar.js:739
|
||||
msgctxt "calendar heading"
|
||||
msgid "%A, %B %d, %Y"
|
||||
msgstr "%A, %d de %B de %Y"
|
||||
|
||||
#: ../js/ui/calendar.js:721
|
||||
#: ../js/ui/calendar.js:749
|
||||
msgid "Today"
|
||||
msgstr "Hoy"
|
||||
|
||||
#: ../js/ui/calendar.js:725
|
||||
#: ../js/ui/calendar.js:753
|
||||
msgid "Tomorrow"
|
||||
msgstr "Mañana"
|
||||
|
||||
#: ../js/ui/calendar.js:736
|
||||
#: ../js/ui/calendar.js:764
|
||||
msgid "This week"
|
||||
msgstr "Esta semana"
|
||||
|
||||
#: ../js/ui/calendar.js:744
|
||||
#: ../js/ui/calendar.js:772
|
||||
msgid "Next week"
|
||||
msgstr "La semana que viene"
|
||||
|
||||
@@ -663,12 +676,12 @@ msgstr "Dispositivo externo desconectado"
|
||||
msgid "Removable Devices"
|
||||
msgstr "Dispositivos extraíbles"
|
||||
|
||||
#: ../js/ui/components/autorunManager.js:593
|
||||
#: ../js/ui/components/autorunManager.js:594
|
||||
#, c-format
|
||||
msgid "Open with %s"
|
||||
msgstr "Abrir con %s"
|
||||
|
||||
#: ../js/ui/components/autorunManager.js:619
|
||||
#: ../js/ui/components/autorunManager.js:620
|
||||
msgid "Eject"
|
||||
msgstr "Expulsar"
|
||||
|
||||
@@ -777,7 +790,7 @@ msgid "Sorry, that didn't work. Please try again."
|
||||
msgstr "Inténtelo de nuevo,"
|
||||
|
||||
#. Translators: this is a filename used for screencast recording
|
||||
#: ../js/ui/components/recorder.js:48
|
||||
#: ../js/ui/components/recorder.js:47
|
||||
#, no-c-format
|
||||
msgid "Screencast from %d %t"
|
||||
msgstr "Screencast desde %d %t"
|
||||
@@ -1024,7 +1037,7 @@ msgstr "Ver cuenta"
|
||||
msgid "Unknown reason"
|
||||
msgstr "Razón desconocida"
|
||||
|
||||
#: ../js/ui/ctrlAltTab.js:29 ../js/ui/viewSelector.js:97
|
||||
#: ../js/ui/ctrlAltTab.js:29 ../js/ui/viewSelector.js:96
|
||||
msgid "Windows"
|
||||
msgstr "Ventanas"
|
||||
|
||||
@@ -1053,7 +1066,7 @@ msgstr "Configuración de hora y fecha"
|
||||
#. Translators: This is the date format to use when the calendar popup is
|
||||
#. * shown - it is shown just below the time in the shell (e.g. "Tue 9:29 AM").
|
||||
#.
|
||||
#: ../js/ui/dateMenu.js:205
|
||||
#: ../js/ui/dateMenu.js:215
|
||||
msgid "%A %B %e, %Y"
|
||||
msgstr "%A, %e de %B de %Y"
|
||||
|
||||
@@ -1219,7 +1232,6 @@ msgid "Remove"
|
||||
msgstr "Quitar"
|
||||
|
||||
#: ../js/ui/messageTray.js:1501
|
||||
#| msgid "No Messages"
|
||||
msgid "Clear Messages"
|
||||
msgstr "Limpiar mensajes"
|
||||
|
||||
@@ -1227,15 +1239,15 @@ msgstr "Limpiar mensajes"
|
||||
msgid "Notification Settings"
|
||||
msgstr "Configuración de las notificaciones"
|
||||
|
||||
#: ../js/ui/messageTray.js:1707
|
||||
#: ../js/ui/messageTray.js:1709
|
||||
msgid "No Messages"
|
||||
msgstr "No hay mensajes"
|
||||
|
||||
#: ../js/ui/messageTray.js:1787
|
||||
#: ../js/ui/messageTray.js:1785
|
||||
msgid "Message Tray"
|
||||
msgstr "Bandeja de mensajes"
|
||||
|
||||
#: ../js/ui/messageTray.js:2864
|
||||
#: ../js/ui/messageTray.js:2813
|
||||
msgid "System Information"
|
||||
msgstr "Información del sistema"
|
||||
|
||||
@@ -1244,14 +1256,14 @@ msgctxt "program"
|
||||
msgid "Unknown"
|
||||
msgstr "Desconocido"
|
||||
|
||||
#: ../js/ui/overviewControls.js:460 ../js/ui/screenShield.js:153
|
||||
#: ../js/ui/overviewControls.js:463 ../js/ui/screenShield.js:149
|
||||
#, c-format
|
||||
msgid "%d new message"
|
||||
msgid_plural "%d new messages"
|
||||
msgstr[0] "%d mensaje nuevo"
|
||||
msgstr[1] "%d mensajes nuevos"
|
||||
|
||||
#: ../js/ui/overview.js:82
|
||||
#: ../js/ui/overview.js:84
|
||||
msgid "Undo"
|
||||
msgstr "Deshacer"
|
||||
|
||||
@@ -1263,22 +1275,21 @@ msgstr "Vista general"
|
||||
#. in the search entry when no search is
|
||||
#. active; it should not exceed ~30
|
||||
#. characters.
|
||||
#: ../js/ui/overview.js:284
|
||||
#| msgid "Type to search..."
|
||||
#: ../js/ui/overview.js:271
|
||||
msgid "Type to search…"
|
||||
msgstr "Escribir para buscar…"
|
||||
|
||||
#: ../js/ui/panel.js:613
|
||||
#: ../js/ui/panel.js:633
|
||||
msgid "Quit"
|
||||
msgstr "Salir"
|
||||
|
||||
#. Translators: If there is no suitable word for "Activities"
|
||||
#. in your language, you can use the word for "Overview".
|
||||
#: ../js/ui/panel.js:642
|
||||
#: ../js/ui/panel.js:657
|
||||
msgid "Activities"
|
||||
msgstr "Actividades"
|
||||
|
||||
#: ../js/ui/panel.js:983
|
||||
#: ../js/ui/panel.js:954
|
||||
msgid "Top Bar"
|
||||
msgstr "Barra superior"
|
||||
|
||||
@@ -1291,32 +1302,32 @@ msgstr "Barra superior"
|
||||
msgid "toggle-switch-us"
|
||||
msgstr "toggle-switch-intl"
|
||||
|
||||
#: ../js/ui/runDialog.js:205
|
||||
#: ../js/ui/runDialog.js:74
|
||||
msgid "Enter a Command"
|
||||
msgstr "Introducir un comando"
|
||||
|
||||
#: ../js/ui/runDialog.js:241
|
||||
#: ../js/ui/runDialog.js:110
|
||||
msgid "Close"
|
||||
msgstr "Cerrar"
|
||||
|
||||
#. Translators: This is a time format for a date in
|
||||
#. long format
|
||||
#: ../js/ui/screenShield.js:90
|
||||
#: ../js/ui/screenShield.js:86
|
||||
msgid "%A, %B %d"
|
||||
msgstr "%A, %d de %B"
|
||||
|
||||
#: ../js/ui/screenShield.js:155
|
||||
#: ../js/ui/screenShield.js:151
|
||||
#, c-format
|
||||
msgid "%d new notification"
|
||||
msgid_plural "%d new notifications"
|
||||
msgstr[0] "%d notificación nueva"
|
||||
msgstr[1] "%d notificaciones nuevas"
|
||||
|
||||
#: ../js/ui/screenShield.js:442 ../js/ui/userMenu.js:805
|
||||
#: ../js/ui/screenShield.js:438 ../js/ui/userMenu.js:807
|
||||
msgid "Lock"
|
||||
msgstr "Bloquear"
|
||||
|
||||
#: ../js/ui/screenShield.js:639
|
||||
#: ../js/ui/screenShield.js:641
|
||||
msgid "GNOME needs to lock the screen"
|
||||
msgstr "GNOME necesita bloquear la pantalla"
|
||||
|
||||
@@ -1327,22 +1338,19 @@ msgstr "GNOME necesita bloquear la pantalla"
|
||||
#.
|
||||
#. XXX: another option is to kick the user into the gdm login
|
||||
#. screen, where we're not affected by grabs
|
||||
#: ../js/ui/screenShield.js:758 ../js/ui/screenShield.js:1169
|
||||
#| msgid "Unable to connect to %s"
|
||||
#: ../js/ui/screenShield.js:762 ../js/ui/screenShield.js:1198
|
||||
msgid "Unable to lock"
|
||||
msgstr "No se pudo bloquear"
|
||||
|
||||
#: ../js/ui/screenShield.js:759 ../js/ui/screenShield.js:1170
|
||||
#| msgid "No such application"
|
||||
#: ../js/ui/screenShield.js:763 ../js/ui/screenShield.js:1199
|
||||
msgid "Lock was blocked by an application"
|
||||
msgstr "Una aplicación impidió el bloqueo"
|
||||
|
||||
#: ../js/ui/searchDisplay.js:431
|
||||
#| msgid "Searching..."
|
||||
#: ../js/ui/searchDisplay.js:453
|
||||
msgid "Searching…"
|
||||
msgstr "Buscando…"
|
||||
|
||||
#: ../js/ui/searchDisplay.js:475
|
||||
#: ../js/ui/searchDisplay.js:497
|
||||
msgid "No results."
|
||||
msgstr "No se encontraron resultados."
|
||||
|
||||
@@ -1354,11 +1362,11 @@ msgstr "Copiar"
|
||||
msgid "Paste"
|
||||
msgstr "Pegar"
|
||||
|
||||
#: ../js/ui/shellEntry.js:105
|
||||
#: ../js/ui/shellEntry.js:101
|
||||
msgid "Show Text"
|
||||
msgstr "Mostrar texto"
|
||||
|
||||
#: ../js/ui/shellEntry.js:107
|
||||
#: ../js/ui/shellEntry.js:103
|
||||
msgid "Hide Text"
|
||||
msgstr "Ocultar texto"
|
||||
|
||||
@@ -1370,7 +1378,7 @@ msgstr "Contraseña"
|
||||
msgid "Remember Password"
|
||||
msgstr "Recordar contraseña"
|
||||
|
||||
#: ../js/ui/shellMountOperation.js:403 ../js/ui/unlockDialog.js:140
|
||||
#: ../js/ui/shellMountOperation.js:403 ../js/ui/unlockDialog.js:114
|
||||
msgid "Unlock"
|
||||
msgstr "Desbloquear"
|
||||
|
||||
@@ -1434,12 +1442,10 @@ msgid "Visibility"
|
||||
msgstr "Visibilidad"
|
||||
|
||||
#: ../js/ui/status/bluetooth.js:59
|
||||
#| msgid "Send Files to Device..."
|
||||
msgid "Send Files to Device…"
|
||||
msgstr "Enviar archivos al dispositivo…"
|
||||
|
||||
#: ../js/ui/status/bluetooth.js:60
|
||||
#| msgid "Set Up a New Device..."
|
||||
msgid "Set Up a New Device…"
|
||||
msgstr "Configurar un dispositivo nuevo…"
|
||||
|
||||
@@ -1466,7 +1472,6 @@ msgid "connecting..."
|
||||
msgstr "conectando…"
|
||||
|
||||
#: ../js/ui/status/bluetooth.js:239
|
||||
#| msgid "Send Files..."
|
||||
msgid "Send Files…"
|
||||
msgstr "Enviar archivos…"
|
||||
|
||||
@@ -1679,7 +1684,6 @@ msgstr "Configuración de energía"
|
||||
#. 0 is reported when UPower does not have enough data
|
||||
#. to estimate battery life
|
||||
#: ../js/ui/status/power.js:99
|
||||
#| msgid "Estimating..."
|
||||
msgid "Estimating…"
|
||||
msgstr "Estimando…"
|
||||
|
||||
@@ -1779,59 +1783,59 @@ msgstr "Volumen"
|
||||
msgid "Microphone"
|
||||
msgstr "Micrófono"
|
||||
|
||||
#: ../js/ui/unlockDialog.js:151
|
||||
#: ../js/ui/unlockDialog.js:125
|
||||
msgid "Log in as another user"
|
||||
msgstr "Iniciar sesión como otro usuario"
|
||||
|
||||
#: ../js/ui/unlockDialog.js:177
|
||||
#: ../js/ui/unlockDialog.js:146
|
||||
msgid "Unlock Window"
|
||||
msgstr "Desbloquear ventana"
|
||||
|
||||
#: ../js/ui/userMenu.js:192
|
||||
#: ../js/ui/userMenu.js:193
|
||||
msgid "Available"
|
||||
msgstr "Disponible"
|
||||
|
||||
#: ../js/ui/userMenu.js:195
|
||||
#: ../js/ui/userMenu.js:196
|
||||
msgid "Busy"
|
||||
msgstr "Ocupado"
|
||||
|
||||
#: ../js/ui/userMenu.js:198
|
||||
#: ../js/ui/userMenu.js:199
|
||||
msgid "Invisible"
|
||||
msgstr "Invisible"
|
||||
|
||||
#: ../js/ui/userMenu.js:201
|
||||
#: ../js/ui/userMenu.js:202
|
||||
msgid "Away"
|
||||
msgstr "Ausente"
|
||||
|
||||
#: ../js/ui/userMenu.js:204
|
||||
#: ../js/ui/userMenu.js:205
|
||||
msgid "Idle"
|
||||
msgstr "Inactivo"
|
||||
|
||||
#: ../js/ui/userMenu.js:207
|
||||
#: ../js/ui/userMenu.js:208
|
||||
msgid "Offline"
|
||||
msgstr "Desconectado"
|
||||
|
||||
#: ../js/ui/userMenu.js:779
|
||||
#: ../js/ui/userMenu.js:781
|
||||
msgid "Notifications"
|
||||
msgstr "Notificaciones"
|
||||
|
||||
#: ../js/ui/userMenu.js:795
|
||||
#: ../js/ui/userMenu.js:797
|
||||
msgid "Switch User"
|
||||
msgstr "Cambiar de usuario"
|
||||
|
||||
#: ../js/ui/userMenu.js:800
|
||||
#: ../js/ui/userMenu.js:802
|
||||
msgid "Log Out"
|
||||
msgstr "Cerrar la sesión"
|
||||
|
||||
#: ../js/ui/userMenu.js:820
|
||||
#: ../js/ui/userMenu.js:822
|
||||
msgid "Install Updates & Restart"
|
||||
msgstr "Instalar actualizaciones y reiniciar"
|
||||
|
||||
#: ../js/ui/userMenu.js:838
|
||||
#: ../js/ui/userMenu.js:840
|
||||
msgid "Your chat status will be set to busy"
|
||||
msgstr "Su estado del chat se establecerá a «ocupado»"
|
||||
|
||||
#: ../js/ui/userMenu.js:839
|
||||
#: ../js/ui/userMenu.js:841
|
||||
msgid ""
|
||||
"Notifications are now disabled, including chat messages. Your online status "
|
||||
"has been adjusted to let others know that you might not see their messages."
|
||||
@@ -1840,33 +1844,35 @@ msgstr ""
|
||||
"chat. Su estado en línea se ha ajustado para que otros sepan que puede no "
|
||||
"leer sus mensajes."
|
||||
|
||||
#: ../js/ui/userMenu.js:885
|
||||
#: ../js/ui/userMenu.js:888
|
||||
msgid "Other users are logged in."
|
||||
msgstr "Hay otros usuarios con la sesión iniciada"
|
||||
|
||||
#: ../js/ui/userMenu.js:890
|
||||
#: ../js/ui/userMenu.js:893
|
||||
msgid "Shutting down might cause them to lose unsaved work."
|
||||
msgstr "Apagar puede hacer que pierdan el trabajo que no hayan guardado."
|
||||
|
||||
#: ../js/ui/userMenu.js:916
|
||||
#. Translators: Remote here refers to a remote session, like a ssh login
|
||||
#: ../js/ui/userMenu.js:921
|
||||
#, c-format
|
||||
msgid "%s (remote)"
|
||||
msgstr "%s (remoto)"
|
||||
|
||||
#: ../js/ui/userMenu.js:918
|
||||
#. Translators: Console here refers to a tty like a VT console
|
||||
#: ../js/ui/userMenu.js:924
|
||||
#, c-format
|
||||
msgid "%s (console)"
|
||||
msgstr "%s (consola)"
|
||||
|
||||
#: ../js/ui/viewSelector.js:101
|
||||
#: ../js/ui/viewSelector.js:100
|
||||
msgid "Applications"
|
||||
msgstr "Aplicaciones"
|
||||
|
||||
#: ../js/ui/viewSelector.js:105
|
||||
#: ../js/ui/viewSelector.js:104
|
||||
msgid "Search"
|
||||
msgstr "Buscar"
|
||||
|
||||
#: ../js/ui/wanda.js:92
|
||||
#: ../js/ui/wanda.js:77
|
||||
#, c-format
|
||||
msgid ""
|
||||
"Sorry, no wisdom for you today:\n"
|
||||
@@ -1875,7 +1881,7 @@ msgstr ""
|
||||
"Hoy no tiene ningún mensaje:\n"
|
||||
"%s"
|
||||
|
||||
#: ../js/ui/wanda.js:96
|
||||
#: ../js/ui/wanda.js:81
|
||||
#, c-format
|
||||
msgid "%s the Oracle says"
|
||||
msgstr "%s el oráculo dice"
|
||||
|
||||
275
po/et.po
275
po/et.po
@@ -13,8 +13,8 @@ msgstr ""
|
||||
"Project-Id-Version: gnome-shell MASTER\n"
|
||||
"Report-Msgid-Bugs-To: http://bugzilla.gnome.org/enter_bug.cgi?product=gnome-"
|
||||
"shell&keywords=I18N+L10N&component=general\n"
|
||||
"POT-Creation-Date: 2012-12-09 13:03+0000\n"
|
||||
"PO-Revision-Date: 2012-12-19 16:47+0300\n"
|
||||
"POT-Creation-Date: 2013-03-11 22:02+0000\n"
|
||||
"PO-Revision-Date: 2013-03-12 16:28+0300\n"
|
||||
"Last-Translator: Mattias Põldaru <mahfiaz@gmail.com>\n"
|
||||
"Language-Team: Estonian <>\n"
|
||||
"Language: et\n"
|
||||
@@ -104,6 +104,16 @@ msgid ""
|
||||
"favorites area."
|
||||
msgstr "Nendele tunnustele vastavaid rakendusi kuvatakse lemmikutes."
|
||||
|
||||
msgid "List of categories that should be displayed as folders"
|
||||
msgstr "Kategooriad, mida tuleb kuvada kaustadena"
|
||||
|
||||
msgid ""
|
||||
"Each category name in this list will be represented as folder in the "
|
||||
"application view, rather than being displayed inline in the main view."
|
||||
msgstr ""
|
||||
"Kõiki selles loetelus olevaid kategooriaid kuvatakse rakenduste vaates "
|
||||
"kaustadena, mitte peavaates teistega koos."
|
||||
|
||||
msgid "History for command (Alt-F2) dialog"
|
||||
msgstr "Käsudialoogi (Alt-F2) ajalugu"
|
||||
|
||||
@@ -135,12 +145,6 @@ msgstr ""
|
||||
"See võti keelab automaatse 'Logi välja' menüükirje peitmise, kui arvutis on "
|
||||
"üks kasutaja ning avatud üks seanss."
|
||||
|
||||
msgid "Show full name in the user menu"
|
||||
msgstr "Kasutajamenüüs näidatakse kasutaja tervet nime"
|
||||
|
||||
msgid "Whether the users full name is shown in the user menu or not."
|
||||
msgstr "Kas kasutajamenüüs näidatakse kasutaja kogu nime või mitte."
|
||||
|
||||
msgid ""
|
||||
"Whether to remember password for mounting encrypted or remote filesystems"
|
||||
msgstr ""
|
||||
@@ -299,12 +303,8 @@ msgstr "Laiendus"
|
||||
msgid "Select an extension to configure using the combobox above."
|
||||
msgstr "Vali seadistatav laiendus kasutades ülemist valikukasti."
|
||||
|
||||
msgid "Session..."
|
||||
msgstr "Seanss..."
|
||||
|
||||
msgctxt "title"
|
||||
msgid "Sign In"
|
||||
msgstr "Sisselogimine"
|
||||
msgid "Session…"
|
||||
msgstr "Seanss…"
|
||||
|
||||
#. translators: this message is shown below the user list on the
|
||||
#. login screen. It can be activated to reveal an entry for
|
||||
@@ -368,16 +368,12 @@ msgstr "Käsku pole võimalik analüüsida:"
|
||||
msgid "Execution of '%s' failed:"
|
||||
msgstr "'%s' käivitamine nurjus:"
|
||||
|
||||
#. Translators: Filter to display all applications
|
||||
msgid "Frequent"
|
||||
msgstr "Sage"
|
||||
|
||||
msgid "All"
|
||||
msgstr "Kõik"
|
||||
|
||||
msgid "APPLICATIONS"
|
||||
msgstr "RAKENDUSED"
|
||||
|
||||
msgid "SETTINGS"
|
||||
msgstr "SEADED"
|
||||
|
||||
msgid "New Window"
|
||||
msgstr "Uus aken"
|
||||
|
||||
@@ -395,6 +391,12 @@ msgstr "%s lisati lemmikutesse."
|
||||
msgid "%s has been removed from your favorites."
|
||||
msgstr "%s eemaldati lemmikutest."
|
||||
|
||||
msgid "Settings"
|
||||
msgstr "Sätted"
|
||||
|
||||
msgid "Change Background…"
|
||||
msgstr "Muuda tausta…"
|
||||
|
||||
#. Translators: Shown in calendar event list for all day events
|
||||
#. * Keep it short, best if you can use less then 10 characters
|
||||
#.
|
||||
@@ -402,15 +404,18 @@ msgctxt "event list time"
|
||||
msgid "All Day"
|
||||
msgstr "Kogu päev"
|
||||
|
||||
#. Translators: Shown in calendar event list, if 24h format
|
||||
#. Translators: Shown in calendar event list, if 24h format,
|
||||
#. \u2236 is a ratio character, similar to :
|
||||
msgctxt "event list time"
|
||||
msgid "%H:%M"
|
||||
msgstr "%H:%M"
|
||||
msgid "%H\\u2236%M"
|
||||
msgstr "%H\\u2236%M"
|
||||
|
||||
#. Transators: Shown in calendar event list, if 12h format
|
||||
#. Transators: Shown in calendar event list, if 12h format,
|
||||
#. \u2236 is a ratio character, similar to : and \u2009 is
|
||||
#. a thin space
|
||||
msgctxt "event list time"
|
||||
msgid "%l:%M %p"
|
||||
msgstr "%l:%M %p"
|
||||
msgid "%l\\u2236%M\\u2009%p"
|
||||
msgstr "%l\\u2236%M\\u2009%p"
|
||||
|
||||
#. Translators: Calendar grid abbreviation for Sunday.
|
||||
#. *
|
||||
@@ -517,6 +522,12 @@ msgstr "Käesolev nädal"
|
||||
msgid "Next week"
|
||||
msgstr "Järgmine nädal"
|
||||
|
||||
msgid "External drive connected"
|
||||
msgstr "Väline ketas ühendati"
|
||||
|
||||
msgid "External drive disconnected"
|
||||
msgstr "Väline ketas eemaldati"
|
||||
|
||||
msgid "Removable Devices"
|
||||
msgstr "Eemaldatavad seadmed"
|
||||
|
||||
@@ -801,12 +812,20 @@ msgstr "Aknad"
|
||||
msgid "Show Applications"
|
||||
msgstr "Rakenduste kuvamine"
|
||||
|
||||
msgid "Date and Time Settings"
|
||||
msgstr "Kuupäeva ja kellaaja sätted"
|
||||
#. Translators: this is the name of the dock/favorites area on
|
||||
#. the left of the overview
|
||||
msgid "Dash"
|
||||
msgstr "Dokk"
|
||||
|
||||
msgid "Open Calendar"
|
||||
msgstr "Ava kalender"
|
||||
|
||||
msgid "Open Clocks"
|
||||
msgstr "Ava kell"
|
||||
|
||||
msgid "Date & Time Settings"
|
||||
msgstr "Kuupäeva ja kella sätted"
|
||||
|
||||
#. Translators: This is the date format to use when the calendar popup is
|
||||
#. * shown - it is shown just below the time in the shell (e.g. "Tue 9:29 AM").
|
||||
#.
|
||||
@@ -897,9 +916,6 @@ msgstr "Paigalda"
|
||||
msgid "Download and install '%s' from extensions.gnome.org?"
|
||||
msgstr "Kas laadida alla ja paigaldada '%s' aadressilt extensions.gnome.org?"
|
||||
|
||||
msgid "tray"
|
||||
msgstr "salv"
|
||||
|
||||
msgid "Keyboard"
|
||||
msgstr "Klaviatuur"
|
||||
|
||||
@@ -920,6 +936,8 @@ msgstr "Näita vigu"
|
||||
msgid "Enabled"
|
||||
msgstr "Lubatud"
|
||||
|
||||
#. translators:
|
||||
#. * The device has been disabled
|
||||
msgid "Disabled"
|
||||
msgstr "Keelatud"
|
||||
|
||||
@@ -944,6 +962,12 @@ msgstr "Ava"
|
||||
msgid "Remove"
|
||||
msgstr "Eemalda"
|
||||
|
||||
msgid "Clear Messages"
|
||||
msgstr "Kustuta teated"
|
||||
|
||||
msgid "Notification Settings"
|
||||
msgstr "Märguannete sätted"
|
||||
|
||||
msgid "No Messages"
|
||||
msgstr "Teateid pole"
|
||||
|
||||
@@ -957,6 +981,12 @@ msgctxt "program"
|
||||
msgid "Unknown"
|
||||
msgstr "Tundmatu"
|
||||
|
||||
#, c-format
|
||||
msgid "%d new message"
|
||||
msgid_plural "%d new messages"
|
||||
msgstr[0] "%d uus sõnum"
|
||||
msgstr[1] "%d uut sõnumit"
|
||||
|
||||
msgid "Undo"
|
||||
msgstr "Võta tagasi"
|
||||
|
||||
@@ -967,13 +997,8 @@ msgstr "Ülevaade"
|
||||
#. in the search entry when no search is
|
||||
#. active; it should not exceed ~30
|
||||
#. characters.
|
||||
msgid "Type to search..."
|
||||
msgstr "Otsing..."
|
||||
|
||||
#. Translators: this is the name of the dock/favorites area on
|
||||
#. the left of the overview
|
||||
msgid "Dash"
|
||||
msgstr "Dokk"
|
||||
msgid "Type to search…"
|
||||
msgstr "Otsing…"
|
||||
|
||||
msgid "Quit"
|
||||
msgstr "Sulge"
|
||||
@@ -1005,12 +1030,6 @@ msgstr "Sulge"
|
||||
msgid "%A, %B %d"
|
||||
msgstr "%A, %d. %B"
|
||||
|
||||
#, c-format
|
||||
msgid "%d new message"
|
||||
msgid_plural "%d new messages"
|
||||
msgstr[0] "%d uus sõnum"
|
||||
msgstr[1] "%d uut sõnumit"
|
||||
|
||||
#, c-format
|
||||
msgid "%d new notification"
|
||||
msgid_plural "%d new notifications"
|
||||
@@ -1020,8 +1039,24 @@ msgstr[1] "%d uut märguannet"
|
||||
msgid "Lock"
|
||||
msgstr "Lukusta"
|
||||
|
||||
msgid "Searching..."
|
||||
msgstr "Otsimine..."
|
||||
msgid "GNOME needs to lock the screen"
|
||||
msgstr "GNOME peab ekraani lukustama"
|
||||
|
||||
#. We could not become modal, so we can't activate the
|
||||
#. screenshield. The user is probably very upset at this
|
||||
#. point, but any application using global grabs is broken
|
||||
#. Just tell him to stop using this app
|
||||
#.
|
||||
#. XXX: another option is to kick the user into the gdm login
|
||||
#. screen, where we're not affected by grabs
|
||||
msgid "Unable to lock"
|
||||
msgstr "Pole võimalik lukustada"
|
||||
|
||||
msgid "Lock was blocked by an application"
|
||||
msgstr "Rakendus blokeeris lukustamise"
|
||||
|
||||
msgid "Searching…"
|
||||
msgstr "Otsing…"
|
||||
|
||||
msgid "No results."
|
||||
msgstr "Tulemused puuduvad."
|
||||
@@ -1089,11 +1124,11 @@ msgstr "Bluetooth"
|
||||
msgid "Visibility"
|
||||
msgstr "Nähtavus"
|
||||
|
||||
msgid "Send Files to Device..."
|
||||
msgstr "Failide saatmine seadmesse..."
|
||||
msgid "Send Files to Device…"
|
||||
msgstr "Failide saatmine seadmesse…"
|
||||
|
||||
msgid "Set up a New Device..."
|
||||
msgstr "Uue seadme häälestamine..."
|
||||
msgid "Set Up a New Device…"
|
||||
msgstr "Uue seadme häälestamine…"
|
||||
|
||||
msgid "Bluetooth Settings"
|
||||
msgstr "Bluetoothi sätted"
|
||||
@@ -1111,8 +1146,8 @@ msgstr "ühenduse katkestamine..."
|
||||
msgid "connecting..."
|
||||
msgstr "ühendumine..."
|
||||
|
||||
msgid "Send Files..."
|
||||
msgstr "Failide saatmine..."
|
||||
msgid "Send Files…"
|
||||
msgstr "Failide saatmine…"
|
||||
|
||||
msgid "Keyboard Settings"
|
||||
msgstr "Klaviatuurisätted"
|
||||
@@ -1173,7 +1208,7 @@ msgstr "Olgu"
|
||||
msgid "Show Keyboard Layout"
|
||||
msgstr "Klaviatuuripaigutuse kuvamine"
|
||||
|
||||
msgid "Region and Language Settings"
|
||||
msgid "Region & Language Settings"
|
||||
msgstr "Asukoha ja keele sätted"
|
||||
|
||||
msgid "Volume, network, battery"
|
||||
@@ -1212,17 +1247,23 @@ msgstr "pole saadaval"
|
||||
msgid "connection failed"
|
||||
msgstr "ühendumine nurjus"
|
||||
|
||||
msgid "More..."
|
||||
msgstr "Veel..."
|
||||
msgid "More…"
|
||||
msgstr "Veel…"
|
||||
|
||||
#. TRANSLATORS: this is the indication that a connection for another logged in user is active,
|
||||
#. and we cannot access its settings (including the name)
|
||||
msgid "Connected (private)"
|
||||
msgstr "Ühendatud (privaatne)"
|
||||
|
||||
msgid "Wired"
|
||||
msgstr "Juhtmega"
|
||||
|
||||
msgid "Auto Ethernet"
|
||||
msgstr "Automaatne ethernet"
|
||||
|
||||
msgid "Mobile broadband"
|
||||
msgstr "Mobiiliühendus"
|
||||
|
||||
msgid "Auto broadband"
|
||||
msgstr "Automaatne lairibaühendus"
|
||||
|
||||
@@ -1269,8 +1310,8 @@ msgstr "Toitesätted..."
|
||||
|
||||
#. 0 is reported when UPower does not have enough data
|
||||
#. to estimate battery life
|
||||
msgid "Estimating..."
|
||||
msgstr "Andmete kogumine..."
|
||||
msgid "Estimating…"
|
||||
msgstr "Andmete kogumine…"
|
||||
|
||||
#, c-format
|
||||
msgid "%d hour remaining"
|
||||
@@ -1304,10 +1345,10 @@ msgctxt "percent of battery remaining"
|
||||
msgid "%d%%"
|
||||
msgstr "%d%%"
|
||||
|
||||
msgid "AC adapter"
|
||||
msgstr "Võrgutoite adapter"
|
||||
msgid "AC Adapter"
|
||||
msgstr "Laadija"
|
||||
|
||||
msgid "Laptop battery"
|
||||
msgid "Laptop Battery"
|
||||
msgstr "Sülearvuti aku"
|
||||
|
||||
msgid "UPS"
|
||||
@@ -1322,10 +1363,10 @@ msgstr "Hiir"
|
||||
msgid "PDA"
|
||||
msgstr "Elektronmärkmik"
|
||||
|
||||
msgid "Cell phone"
|
||||
msgid "Cell Phone"
|
||||
msgstr "Mobiiltelefon"
|
||||
|
||||
msgid "Media player"
|
||||
msgid "Media Player"
|
||||
msgstr "Meediaesitaja"
|
||||
|
||||
msgid "Tablet"
|
||||
@@ -1338,6 +1379,9 @@ msgctxt "device"
|
||||
msgid "Unknown"
|
||||
msgstr "Tundmatu"
|
||||
|
||||
msgid "Volume changed"
|
||||
msgstr "Helivaljus muutus"
|
||||
|
||||
#. Translators: This is the label for audio volume
|
||||
msgid "Volume"
|
||||
msgstr "Helivaljus"
|
||||
@@ -1372,9 +1416,6 @@ msgstr "Ühendamata"
|
||||
msgid "Notifications"
|
||||
msgstr "Märguanded"
|
||||
|
||||
msgid "Settings"
|
||||
msgstr "Sätted"
|
||||
|
||||
msgid "Switch User"
|
||||
msgstr "Vaheta kasutajat"
|
||||
|
||||
@@ -1394,6 +1435,22 @@ msgstr ""
|
||||
"Märguanded on nüüd keelatud, sealhulgas vestlusteated. Sinu netiolekut "
|
||||
"muudeti, et teised teaksid, et sa ei pruugi nende teateid näha."
|
||||
|
||||
msgid "Other users are logged in."
|
||||
msgstr "Teised kasutajad on sisse logitud."
|
||||
|
||||
msgid "Shutting down might cause them to lose unsaved work."
|
||||
msgstr "Väljalülitamine võib põhjustada salvestamata töö kaotsimineku."
|
||||
|
||||
#. Translators: Remote here refers to a remote session, like a ssh login
|
||||
#, c-format
|
||||
msgid "%s (remote)"
|
||||
msgstr "%s (kaugühendus)"
|
||||
|
||||
#. Translators: Console here refers to a tty like a VT console
|
||||
#, c-format
|
||||
msgid "%s (console)"
|
||||
msgstr "%s (konsool)"
|
||||
|
||||
msgid "Applications"
|
||||
msgstr "Rakendused"
|
||||
|
||||
@@ -1412,9 +1469,6 @@ msgstr ""
|
||||
msgid "%s the Oracle says"
|
||||
msgstr "Oraakel %s ütleb"
|
||||
|
||||
msgid "Your favorite Easter Egg"
|
||||
msgstr "Sinu lemmiküllatusmuna"
|
||||
|
||||
#, c-format
|
||||
msgid "'%s' is ready"
|
||||
msgstr "'%s' on valmis"
|
||||
@@ -1422,6 +1476,25 @@ msgstr "'%s' on valmis"
|
||||
msgid "Evolution Calendar"
|
||||
msgstr "Evolutioni kalender"
|
||||
|
||||
#. translators:
|
||||
#. * The number of sound outputs on a particular device
|
||||
#, c-format
|
||||
msgid "%u Output"
|
||||
msgid_plural "%u Outputs"
|
||||
msgstr[0] "%u väljund"
|
||||
msgstr[1] "%u väljundit"
|
||||
|
||||
#. translators:
|
||||
#. * The number of sound inputs on a particular device
|
||||
#, c-format
|
||||
msgid "%u Input"
|
||||
msgid_plural "%u Inputs"
|
||||
msgstr[0] "%u sisend"
|
||||
msgstr[1] "%u sisendit"
|
||||
|
||||
msgid "System Sounds"
|
||||
msgstr "Süsteemi helid"
|
||||
|
||||
msgid "Print version"
|
||||
msgstr "Printimise versioon"
|
||||
|
||||
@@ -1444,15 +1517,48 @@ msgstr "Paroolid ei kattu."
|
||||
msgid "Password cannot be blank"
|
||||
msgstr "Parool ei saa olla tühi"
|
||||
|
||||
msgid "United Kingdom"
|
||||
msgstr "Suurbritannia"
|
||||
|
||||
msgid "Default"
|
||||
msgstr "Vaikimisi"
|
||||
|
||||
msgid "Authentication dialog was dismissed by the user"
|
||||
msgstr "Kasutaja katkestas autentimisdialoogi"
|
||||
|
||||
#~ msgid "Show full name in the user menu"
|
||||
#~ msgstr "Kasutajamenüüs näidatakse kasutaja tervet nime"
|
||||
|
||||
#~ msgid "Whether the users full name is shown in the user menu or not."
|
||||
#~ msgstr "Kas kasutajamenüüs näidatakse kasutaja kogu nime või mitte."
|
||||
|
||||
#~ msgctxt "title"
|
||||
#~ msgid "Sign In"
|
||||
#~ msgstr "Sisselogimine"
|
||||
|
||||
#~ msgid "APPLICATIONS"
|
||||
#~ msgstr "RAKENDUSED"
|
||||
|
||||
#~ msgid "SETTINGS"
|
||||
#~ msgstr "SEADED"
|
||||
|
||||
#~ msgctxt "event list time"
|
||||
#~ msgid "%H:%M"
|
||||
#~ msgstr "%H:%M"
|
||||
|
||||
#~ msgctxt "event list time"
|
||||
#~ msgid "%l:%M %p"
|
||||
#~ msgstr "%l:%M %p"
|
||||
|
||||
#~ msgid "tray"
|
||||
#~ msgstr "salv"
|
||||
|
||||
#~ msgid "More..."
|
||||
#~ msgstr "Veel..."
|
||||
|
||||
#~ msgid "Your favorite Easter Egg"
|
||||
#~ msgstr "Sinu lemmiküllatusmuna"
|
||||
|
||||
#~ msgid "United Kingdom"
|
||||
#~ msgstr "Suurbritannia"
|
||||
|
||||
#~ msgid "Default"
|
||||
#~ msgstr "Vaikimisi"
|
||||
|
||||
#~ msgid "Subscription request"
|
||||
#~ msgstr "Tellimuse päring"
|
||||
|
||||
@@ -1471,28 +1577,9 @@ msgstr "Kasutaja katkestas autentimisdialoogi"
|
||||
#~ msgid "Reconnect"
|
||||
#~ msgstr "Ühendu uuesti"
|
||||
|
||||
#~ msgid "Wired"
|
||||
#~ msgstr "Juhtmega"
|
||||
|
||||
#~ msgid "Wireless"
|
||||
#~ msgstr "Juhtmeta"
|
||||
|
||||
#~ msgid "Mobile broadband"
|
||||
#~ msgstr "Mobiiliühendus"
|
||||
|
||||
#~ msgid "%u Output"
|
||||
#~ msgid_plural "%u Outputs"
|
||||
#~ msgstr[0] "%u väljund"
|
||||
#~ msgstr[1] "%u väljundit"
|
||||
|
||||
#~ msgid "%u Input"
|
||||
#~ msgid_plural "%u Inputs"
|
||||
#~ msgstr[0] "%u sisend"
|
||||
#~ msgstr[1] "%u sisendit"
|
||||
|
||||
#~ msgid "System Sounds"
|
||||
#~ msgstr "Süsteemi helid"
|
||||
|
||||
#~ msgid "disabled OpenSearch providers"
|
||||
#~ msgstr "keelatud OpenSearch pakkujad"
|
||||
|
||||
|
||||
219
po/gl.po
219
po/gl.po
@@ -10,10 +10,9 @@
|
||||
msgid ""
|
||||
msgstr ""
|
||||
"Project-Id-Version: gnome-shell master\n"
|
||||
"Report-Msgid-Bugs-To: http://bugzilla.gnome.org/enter_bug.cgi?product=gnome-"
|
||||
"shell&keywords=I18N+L10N&component=general\n"
|
||||
"POT-Creation-Date: 2013-03-02 23:02+0000\n"
|
||||
"PO-Revision-Date: 2013-03-04 12:40+0200\n"
|
||||
"Report-Msgid-Bugs-To: \n"
|
||||
"POT-Creation-Date: 2013-04-18 01:27+0200\n"
|
||||
"PO-Revision-Date: 2013-04-18 01:42+0200\n"
|
||||
"Last-Translator: Fran Dieguez <frandieguez@gnome.org>\n"
|
||||
"Language-Team: gnome-l10n-gl@gnome.org\n"
|
||||
"Language: gl\n"
|
||||
@@ -30,7 +29,7 @@ msgstr "Capturas de pantalla"
|
||||
|
||||
#: ../data/50-gnome-shell-screenshot.xml.in.h:2
|
||||
msgid "Record a screencast"
|
||||
msgstr "Gravar unha gravación de pantalla"
|
||||
msgstr "Facer unha gravación da pantalla"
|
||||
|
||||
#: ../data/50-gnome-shell-system.xml.in.h:1
|
||||
msgid "System"
|
||||
@@ -63,16 +62,16 @@ msgstr "Xestor de xanelas e inicio de aplicativos"
|
||||
#: ../data/gnome-shell-extension-prefs.desktop.in.in.h:1
|
||||
#: ../js/extensionPrefs/main.js:153
|
||||
msgid "GNOME Shell Extension Preferences"
|
||||
msgstr "Preferencias de extensións de GNOME Shell"
|
||||
msgstr "Preferencias das extensións de GNOME Shell"
|
||||
|
||||
#: ../data/gnome-shell-extension-prefs.desktop.in.in.h:2
|
||||
msgid "Configure GNOME Shell Extensions"
|
||||
msgstr "Configurar as extensións de GNOME Shell"
|
||||
msgstr "Configure as extensións de GNOME Shell"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:1
|
||||
msgid "Enable internal tools useful for developers and testers from Alt-F2"
|
||||
msgstr ""
|
||||
"Activar as ferramentas internas útiles para os desenvolvedores e probadores, "
|
||||
"Activar as ferramentas internas útiles para os desenvolvedores e probadores "
|
||||
"usando Alt-F2"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:2
|
||||
@@ -85,7 +84,7 @@ msgstr ""
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:3
|
||||
msgid "Uuids of extensions to enable"
|
||||
msgstr "Uuid das extensións que activar"
|
||||
msgstr "UUIDs das extensións a activar"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:4
|
||||
msgid ""
|
||||
@@ -375,43 +374,42 @@ msgstr ""
|
||||
"Seleccione unha extensión que configurar usando a caixa combinada de arriba."
|
||||
|
||||
#: ../js/gdm/loginDialog.js:405
|
||||
#| msgid "Session..."
|
||||
msgid "Session…"
|
||||
msgstr "Sesión…"
|
||||
|
||||
#. translators: this message is shown below the user list on the
|
||||
#. login screen. It can be activated to reveal an entry for
|
||||
#. manually entering the username.
|
||||
#: ../js/gdm/loginDialog.js:629
|
||||
#: ../js/gdm/loginDialog.js:630
|
||||
msgid "Not listed?"
|
||||
msgstr "Non está na lista?"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:783 ../js/ui/components/networkAgent.js:137
|
||||
#: ../js/ui/components/polkitAgent.js:162 ../js/ui/endSessionDialog.js:375
|
||||
#: ../js/gdm/loginDialog.js:787 ../js/ui/components/networkAgent.js:137
|
||||
#: ../js/ui/components/polkitAgent.js:162 ../js/ui/endSessionDialog.js:376
|
||||
#: ../js/ui/extensionDownloader.js:195 ../js/ui/shellMountOperation.js:399
|
||||
#: ../js/ui/status/bluetooth.js:415 ../js/ui/unlockDialog.js:126
|
||||
#: ../js/ui/userMenu.js:932
|
||||
#: ../js/ui/status/bluetooth.js:415 ../js/ui/unlockDialog.js:100
|
||||
#: ../js/ui/userMenu.js:938
|
||||
msgid "Cancel"
|
||||
msgstr "Cancelar"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:799
|
||||
#: ../js/gdm/loginDialog.js:803
|
||||
msgctxt "button"
|
||||
msgid "Sign In"
|
||||
msgstr "Iniciar sesión"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:799
|
||||
#: ../js/gdm/loginDialog.js:803
|
||||
msgid "Next"
|
||||
msgstr "Seguinte"
|
||||
|
||||
#. TTLS and PEAP are actually much more complicated, but this complication
|
||||
#. is not visible here since we only care about phase2 authentication
|
||||
#. (and don't even care of which one)
|
||||
#: ../js/gdm/loginDialog.js:904 ../js/ui/components/networkAgent.js:260
|
||||
#: ../js/gdm/loginDialog.js:918 ../js/ui/components/networkAgent.js:260
|
||||
#: ../js/ui/components/networkAgent.js:278
|
||||
msgid "Username: "
|
||||
msgstr "Nome de usuario: "
|
||||
|
||||
#: ../js/gdm/loginDialog.js:1157
|
||||
#: ../js/gdm/loginDialog.js:1174
|
||||
msgid "Login Window"
|
||||
msgstr "Xanela de inicio de sesión"
|
||||
|
||||
@@ -420,8 +418,8 @@ msgstr "Xanela de inicio de sesión"
|
||||
msgid "Power"
|
||||
msgstr "Apagar"
|
||||
|
||||
#: ../js/gdm/powerMenu.js:93 ../js/ui/userMenu.js:694 ../js/ui/userMenu.js:698
|
||||
#: ../js/ui/userMenu.js:814
|
||||
#: ../js/gdm/powerMenu.js:93 ../js/ui/userMenu.js:696 ../js/ui/userMenu.js:700
|
||||
#: ../js/ui/userMenu.js:816
|
||||
msgid "Suspend"
|
||||
msgstr "Suspender"
|
||||
|
||||
@@ -429,58 +427,58 @@ msgstr "Suspender"
|
||||
msgid "Restart"
|
||||
msgstr "Reiniciar"
|
||||
|
||||
#: ../js/gdm/powerMenu.js:103 ../js/ui/userMenu.js:696
|
||||
#: ../js/ui/userMenu.js:698 ../js/ui/userMenu.js:813 ../js/ui/userMenu.js:936
|
||||
#: ../js/gdm/powerMenu.js:103 ../js/ui/userMenu.js:698
|
||||
#: ../js/ui/userMenu.js:700 ../js/ui/userMenu.js:815 ../js/ui/userMenu.js:942
|
||||
msgid "Power Off"
|
||||
msgstr "Apagar"
|
||||
|
||||
#: ../js/gdm/util.js:182
|
||||
#: ../js/gdm/util.js:249
|
||||
msgid "Authentication error"
|
||||
msgstr "Erro de autenticación"
|
||||
|
||||
#. Translators: this message is shown below the password entry field
|
||||
#. to indicate the user can swipe their finger instead
|
||||
#: ../js/gdm/util.js:299
|
||||
#: ../js/gdm/util.js:366
|
||||
msgid "(or swipe finger)"
|
||||
msgstr "(ou pase o dedo)"
|
||||
|
||||
#: ../js/gdm/util.js:324
|
||||
#: ../js/gdm/util.js:391
|
||||
#, c-format
|
||||
msgid "(e.g., user or %s)"
|
||||
msgstr "(p.ex., usuario ou %s)"
|
||||
|
||||
#: ../js/misc/util.js:94
|
||||
#: ../js/misc/util.js:97
|
||||
msgid "Command not found"
|
||||
msgstr "Orde non atopada"
|
||||
|
||||
#. Replace "Error invoking GLib.shell_parse_argv: " with
|
||||
#. something nicer
|
||||
#: ../js/misc/util.js:127
|
||||
#: ../js/misc/util.js:130
|
||||
msgid "Could not parse command:"
|
||||
msgstr "Non foi posíbel analizar a orde:"
|
||||
|
||||
#: ../js/misc/util.js:135
|
||||
#: ../js/misc/util.js:138
|
||||
#, c-format
|
||||
msgid "Execution of '%s' failed:"
|
||||
msgstr "Produciuse un fallo na execución de «%s»:"
|
||||
|
||||
#: ../js/ui/appDisplay.js:348
|
||||
#: ../js/ui/appDisplay.js:349
|
||||
msgid "Frequent"
|
||||
msgstr "Frecuentes"
|
||||
|
||||
#: ../js/ui/appDisplay.js:355
|
||||
#: ../js/ui/appDisplay.js:356
|
||||
msgid "All"
|
||||
msgstr "Todos"
|
||||
|
||||
#: ../js/ui/appDisplay.js:913
|
||||
#: ../js/ui/appDisplay.js:914
|
||||
msgid "New Window"
|
||||
msgstr "Xanela nova"
|
||||
|
||||
#: ../js/ui/appDisplay.js:916 ../js/ui/dash.js:284
|
||||
#: ../js/ui/appDisplay.js:917 ../js/ui/dash.js:284
|
||||
msgid "Remove from Favorites"
|
||||
msgstr "Retirar dos marcadores"
|
||||
|
||||
#: ../js/ui/appDisplay.js:917
|
||||
#: ../js/ui/appDisplay.js:918
|
||||
msgid "Add to Favorites"
|
||||
msgstr "Engadir aos favoritos"
|
||||
|
||||
@@ -494,7 +492,7 @@ msgstr "%s foi engadido aos seus favoritos."
|
||||
msgid "%s has been removed from your favorites."
|
||||
msgstr "%s retirouse dos seus marcadores."
|
||||
|
||||
#: ../js/ui/backgroundMenu.js:19 ../js/ui/userMenu.js:787
|
||||
#: ../js/ui/backgroundMenu.js:19 ../js/ui/userMenu.js:789
|
||||
msgid "Settings"
|
||||
msgstr "Preferencias"
|
||||
|
||||
@@ -517,7 +515,7 @@ msgctxt "event list time"
|
||||
msgid "%H\\u2236%M"
|
||||
msgstr "%H\\u2236%M"
|
||||
|
||||
#. Transators: Shown in calendar event list, if 12h format,
|
||||
#. Translators: Shown in calendar event list, if 12h format,
|
||||
#. \u2236 is a ratio character, similar to : and \u2009 is
|
||||
#. a thin space
|
||||
#: ../js/ui/calendar.js:77
|
||||
@@ -619,35 +617,35 @@ msgid "S"
|
||||
msgstr "S"
|
||||
|
||||
#. Translators: Text to show if there are no events
|
||||
#: ../js/ui/calendar.js:692
|
||||
#: ../js/ui/calendar.js:720
|
||||
msgid "Nothing Scheduled"
|
||||
msgstr "Nada programado"
|
||||
|
||||
#. Translators: Shown on calendar heading when selected day occurs on current year
|
||||
#: ../js/ui/calendar.js:708
|
||||
#: ../js/ui/calendar.js:736
|
||||
msgctxt "calendar heading"
|
||||
msgid "%A, %B %d"
|
||||
msgstr "%A, %d de %B"
|
||||
|
||||
#. Translators: Shown on calendar heading when selected day occurs on different year
|
||||
#: ../js/ui/calendar.js:711
|
||||
#: ../js/ui/calendar.js:739
|
||||
msgctxt "calendar heading"
|
||||
msgid "%A, %B %d, %Y"
|
||||
msgstr "%A, %d de %B de %Y"
|
||||
|
||||
#: ../js/ui/calendar.js:721
|
||||
#: ../js/ui/calendar.js:749
|
||||
msgid "Today"
|
||||
msgstr "Hoxe"
|
||||
|
||||
#: ../js/ui/calendar.js:725
|
||||
#: ../js/ui/calendar.js:753
|
||||
msgid "Tomorrow"
|
||||
msgstr "Mañá"
|
||||
|
||||
#: ../js/ui/calendar.js:736
|
||||
#: ../js/ui/calendar.js:764
|
||||
msgid "This week"
|
||||
msgstr "Esta semana"
|
||||
|
||||
#: ../js/ui/calendar.js:744
|
||||
#: ../js/ui/calendar.js:772
|
||||
msgid "Next week"
|
||||
msgstr "A vindeira semana"
|
||||
|
||||
@@ -663,12 +661,12 @@ msgstr "Unidade externa desconectada"
|
||||
msgid "Removable Devices"
|
||||
msgstr "Dispositivos extraíbeis"
|
||||
|
||||
#: ../js/ui/components/autorunManager.js:593
|
||||
#: ../js/ui/components/autorunManager.js:594
|
||||
#, c-format
|
||||
msgid "Open with %s"
|
||||
msgstr "Abrir con %s"
|
||||
|
||||
#: ../js/ui/components/autorunManager.js:619
|
||||
#: ../js/ui/components/autorunManager.js:620
|
||||
msgid "Eject"
|
||||
msgstr "Expulsar"
|
||||
|
||||
@@ -777,7 +775,7 @@ msgid "Sorry, that didn't work. Please try again."
|
||||
msgstr "Desculpe, iso non funcionou. Ténteo de novo."
|
||||
|
||||
#. Translators: this is a filename used for screencast recording
|
||||
#: ../js/ui/components/recorder.js:48
|
||||
#: ../js/ui/components/recorder.js:47
|
||||
#, no-c-format
|
||||
msgid "Screencast from %d %t"
|
||||
msgstr "Screencast desde %d %t"
|
||||
@@ -1024,7 +1022,7 @@ msgstr "Ver conta"
|
||||
msgid "Unknown reason"
|
||||
msgstr "Razón descoñecida"
|
||||
|
||||
#: ../js/ui/ctrlAltTab.js:29 ../js/ui/viewSelector.js:97
|
||||
#: ../js/ui/ctrlAltTab.js:29 ../js/ui/viewSelector.js:96
|
||||
msgid "Windows"
|
||||
msgstr "Xanelas"
|
||||
|
||||
@@ -1040,7 +1038,7 @@ msgstr "Taboleiro"
|
||||
|
||||
#: ../js/ui/dateMenu.js:91
|
||||
msgid "Open Calendar"
|
||||
msgstr "Abrir o calendario"
|
||||
msgstr "Abrir Calendario"
|
||||
|
||||
#: ../js/ui/dateMenu.js:96
|
||||
msgid "Open Clocks"
|
||||
@@ -1053,7 +1051,7 @@ msgstr "Preferencias de data e hora"
|
||||
#. Translators: This is the date format to use when the calendar popup is
|
||||
#. * shown - it is shown just below the time in the shell (e.g. "Tue 9:29 AM").
|
||||
#.
|
||||
#: ../js/ui/dateMenu.js:205
|
||||
#: ../js/ui/dateMenu.js:215
|
||||
msgid "%A %B %e, %Y"
|
||||
msgstr "%a, %e de %B, %Y"
|
||||
|
||||
@@ -1071,7 +1069,7 @@ msgstr "Saír da sesión"
|
||||
#: ../js/ui/endSessionDialog.js:65
|
||||
msgid "Click Log Out to quit these applications and log out of the system."
|
||||
msgstr ""
|
||||
"Prema sobre «Saír da sesión» para saír deses aplicativos e saír da sesión do "
|
||||
"Prema en «Saír da sesión» para pechar estes aplicativos e saír da sesión do "
|
||||
"sistema."
|
||||
|
||||
#: ../js/ui/endSessionDialog.js:67
|
||||
@@ -1090,7 +1088,7 @@ msgstr[1] "A súa sesión pecharase automaticamente en %d segundos."
|
||||
|
||||
#: ../js/ui/endSessionDialog.js:76
|
||||
msgid "Logging out of the system."
|
||||
msgstr "Saíndo da sesión."
|
||||
msgstr "Saíndo da sesión do sistema."
|
||||
|
||||
#: ../js/ui/endSessionDialog.js:78
|
||||
msgctxt "button"
|
||||
@@ -1104,7 +1102,7 @@ msgstr "Apagar"
|
||||
|
||||
#: ../js/ui/endSessionDialog.js:84
|
||||
msgid "Click Power Off to quit these applications and power off the system."
|
||||
msgstr "Prema sobre «Apagar» para saír deses aplicativos e apagar o sistema."
|
||||
msgstr "Prema sobre «Apagar» para pechar estes aplicativos e apagar o sistema."
|
||||
|
||||
#: ../js/ui/endSessionDialog.js:86
|
||||
#, c-format
|
||||
@@ -1134,7 +1132,7 @@ msgstr "Reiniciar"
|
||||
|
||||
#: ../js/ui/endSessionDialog.js:101
|
||||
msgid "Click Restart to quit these applications and restart the system."
|
||||
msgstr "Prema «Reiniciar» para saír deses aplicativos e reiniciar o sistema."
|
||||
msgstr "Prema «Reiniciar» para pechar estes aplicativos e reiniciar o sistema."
|
||||
|
||||
#: ../js/ui/endSessionDialog.js:103
|
||||
#, c-format
|
||||
@@ -1169,7 +1167,7 @@ msgstr "Non hai ningunha extensión instalada"
|
||||
#: ../js/ui/lookingGlass.js:747
|
||||
#, c-format
|
||||
msgid "%s has not emitted any errors."
|
||||
msgstr "%s non xerou ningún erro."
|
||||
msgstr "%s non emitiu ningún erro."
|
||||
|
||||
#: ../js/ui/lookingGlass.js:753
|
||||
msgid "Hide Errors"
|
||||
@@ -1195,7 +1193,7 @@ msgstr "Erro"
|
||||
|
||||
#: ../js/ui/lookingGlass.js:773
|
||||
msgid "Out of date"
|
||||
msgstr "Caducado"
|
||||
msgstr "Obsoleto"
|
||||
|
||||
#: ../js/ui/lookingGlass.js:775
|
||||
msgid "Downloading"
|
||||
@@ -1218,7 +1216,6 @@ msgid "Remove"
|
||||
msgstr "Retirar"
|
||||
|
||||
#: ../js/ui/messageTray.js:1501
|
||||
#| msgid "No Messages"
|
||||
msgid "Clear Messages"
|
||||
msgstr "Limpar mensaxes"
|
||||
|
||||
@@ -1226,15 +1223,15 @@ msgstr "Limpar mensaxes"
|
||||
msgid "Notification Settings"
|
||||
msgstr "Preferencias das notificacións"
|
||||
|
||||
#: ../js/ui/messageTray.js:1707
|
||||
#: ../js/ui/messageTray.js:1709
|
||||
msgid "No Messages"
|
||||
msgstr "Non hai mensaxes"
|
||||
|
||||
#: ../js/ui/messageTray.js:1787
|
||||
#: ../js/ui/messageTray.js:1785
|
||||
msgid "Message Tray"
|
||||
msgstr "Bandexa de mensaxes"
|
||||
|
||||
#: ../js/ui/messageTray.js:2864
|
||||
#: ../js/ui/messageTray.js:2813
|
||||
msgid "System Information"
|
||||
msgstr "Información do sistema"
|
||||
|
||||
@@ -1243,14 +1240,14 @@ msgctxt "program"
|
||||
msgid "Unknown"
|
||||
msgstr "Descoñecido"
|
||||
|
||||
#: ../js/ui/overviewControls.js:460 ../js/ui/screenShield.js:153
|
||||
#: ../js/ui/overviewControls.js:463 ../js/ui/screenShield.js:149
|
||||
#, c-format
|
||||
msgid "%d new message"
|
||||
msgid_plural "%d new messages"
|
||||
msgstr[0] "%d mensaxe nova"
|
||||
msgstr[1] "%d mensaxes novas"
|
||||
|
||||
#: ../js/ui/overview.js:82
|
||||
#: ../js/ui/overview.js:84
|
||||
msgid "Undo"
|
||||
msgstr "Desfacer"
|
||||
|
||||
@@ -1262,22 +1259,21 @@ msgstr "Vista xeral"
|
||||
#. in the search entry when no search is
|
||||
#. active; it should not exceed ~30
|
||||
#. characters.
|
||||
#: ../js/ui/overview.js:284
|
||||
#| msgid "Type to search..."
|
||||
#: ../js/ui/overview.js:271
|
||||
msgid "Type to search…"
|
||||
msgstr "Escriba para buscar…"
|
||||
|
||||
#: ../js/ui/panel.js:613
|
||||
#: ../js/ui/panel.js:633
|
||||
msgid "Quit"
|
||||
msgstr "Saír"
|
||||
|
||||
#. Translators: If there is no suitable word for "Activities"
|
||||
#. in your language, you can use the word for "Overview".
|
||||
#: ../js/ui/panel.js:642
|
||||
#: ../js/ui/panel.js:657
|
||||
msgid "Activities"
|
||||
msgstr "Actividades"
|
||||
|
||||
#: ../js/ui/panel.js:983
|
||||
#: ../js/ui/panel.js:954
|
||||
msgid "Top Bar"
|
||||
msgstr "Barra superior"
|
||||
|
||||
@@ -1290,34 +1286,34 @@ msgstr "Barra superior"
|
||||
msgid "toggle-switch-us"
|
||||
msgstr "toggle-switch-intl"
|
||||
|
||||
#: ../js/ui/runDialog.js:205
|
||||
#: ../js/ui/runDialog.js:74
|
||||
msgid "Enter a Command"
|
||||
msgstr "Escriba unha orde"
|
||||
|
||||
#: ../js/ui/runDialog.js:241
|
||||
#: ../js/ui/runDialog.js:110
|
||||
msgid "Close"
|
||||
msgstr "Pechar"
|
||||
|
||||
#. Translators: This is a time format for a date in
|
||||
#. long format
|
||||
#: ../js/ui/screenShield.js:90
|
||||
#: ../js/ui/screenShield.js:86
|
||||
msgid "%A, %B %d"
|
||||
msgstr "%A, %d de %B"
|
||||
|
||||
#: ../js/ui/screenShield.js:155
|
||||
#: ../js/ui/screenShield.js:151
|
||||
#, c-format
|
||||
msgid "%d new notification"
|
||||
msgid_plural "%d new notifications"
|
||||
msgstr[0] "%d notificación nova"
|
||||
msgstr[1] "%d notificacións novas"
|
||||
|
||||
#: ../js/ui/screenShield.js:442 ../js/ui/userMenu.js:805
|
||||
#: ../js/ui/screenShield.js:438 ../js/ui/userMenu.js:807
|
||||
msgid "Lock"
|
||||
msgstr "Bloquear"
|
||||
|
||||
#: ../js/ui/screenShield.js:639
|
||||
#: ../js/ui/screenShield.js:641
|
||||
msgid "GNOME needs to lock the screen"
|
||||
msgstr "GNOME debe bloquear a pantalla"
|
||||
msgstr "GNOME precisa bloquear a pantalla"
|
||||
|
||||
#. We could not become modal, so we can't activate the
|
||||
#. screenshield. The user is probably very upset at this
|
||||
@@ -1326,22 +1322,19 @@ msgstr "GNOME debe bloquear a pantalla"
|
||||
#.
|
||||
#. XXX: another option is to kick the user into the gdm login
|
||||
#. screen, where we're not affected by grabs
|
||||
#: ../js/ui/screenShield.js:758 ../js/ui/screenShield.js:1169
|
||||
#| msgid "Unable to connect to %s"
|
||||
#: ../js/ui/screenShield.js:762 ../js/ui/screenShield.js:1198
|
||||
msgid "Unable to lock"
|
||||
msgstr "Non foi posíbel bloquear"
|
||||
|
||||
#: ../js/ui/screenShield.js:759 ../js/ui/screenShield.js:1170
|
||||
#| msgid "No such application"
|
||||
#: ../js/ui/screenShield.js:763 ../js/ui/screenShield.js:1199
|
||||
msgid "Lock was blocked by an application"
|
||||
msgstr "O bloqueo foi impedido por un aplicativo"
|
||||
msgstr "Un aplicativo impediu o bloqueo"
|
||||
|
||||
#: ../js/ui/searchDisplay.js:431
|
||||
#| msgid "Searching..."
|
||||
#: ../js/ui/searchDisplay.js:453
|
||||
msgid "Searching…"
|
||||
msgstr "Buscando…"
|
||||
|
||||
#: ../js/ui/searchDisplay.js:475
|
||||
#: ../js/ui/searchDisplay.js:497
|
||||
msgid "No results."
|
||||
msgstr "Sen resultados."
|
||||
|
||||
@@ -1353,11 +1346,11 @@ msgstr "Copiar"
|
||||
msgid "Paste"
|
||||
msgstr "Pegar"
|
||||
|
||||
#: ../js/ui/shellEntry.js:105
|
||||
#: ../js/ui/shellEntry.js:101
|
||||
msgid "Show Text"
|
||||
msgstr "Mostrar texto"
|
||||
|
||||
#: ../js/ui/shellEntry.js:107
|
||||
#: ../js/ui/shellEntry.js:103
|
||||
msgid "Hide Text"
|
||||
msgstr "Ocultar texto"
|
||||
|
||||
@@ -1367,9 +1360,9 @@ msgstr "Contrasinal"
|
||||
|
||||
#: ../js/ui/shellMountOperation.js:391
|
||||
msgid "Remember Password"
|
||||
msgstr "Lembrar o contrasinal"
|
||||
msgstr "Lembrar contrasinal"
|
||||
|
||||
#: ../js/ui/shellMountOperation.js:403 ../js/ui/unlockDialog.js:140
|
||||
#: ../js/ui/shellMountOperation.js:403 ../js/ui/unlockDialog.js:114
|
||||
msgid "Unlock"
|
||||
msgstr "Desbloquear"
|
||||
|
||||
@@ -1433,12 +1426,10 @@ msgid "Visibility"
|
||||
msgstr "Visibilidade"
|
||||
|
||||
#: ../js/ui/status/bluetooth.js:59
|
||||
#| msgid "Send Files to Device..."
|
||||
msgid "Send Files to Device…"
|
||||
msgstr "Enviar ficheiros ao dispositivo…"
|
||||
|
||||
#: ../js/ui/status/bluetooth.js:60
|
||||
#| msgid "Set Up a New Device..."
|
||||
msgid "Set Up a New Device…"
|
||||
msgstr "Configurar un dispositivo novo…"
|
||||
|
||||
@@ -1465,7 +1456,6 @@ msgid "connecting..."
|
||||
msgstr "conectando…"
|
||||
|
||||
#: ../js/ui/status/bluetooth.js:239
|
||||
#| msgid "Send Files..."
|
||||
msgid "Send Files…"
|
||||
msgstr "Enviar ficheiros…"
|
||||
|
||||
@@ -1547,7 +1537,7 @@ msgstr "Mostrar a distribución do teclado"
|
||||
|
||||
#: ../js/ui/status/keyboard.js:373
|
||||
msgid "Region & Language Settings"
|
||||
msgstr "Configuración rexional e de idioma"
|
||||
msgstr "Preferencias de rexión e idioma"
|
||||
|
||||
#: ../js/ui/status/lockScreenMenu.js:43
|
||||
msgid "Volume, network, battery"
|
||||
@@ -1592,7 +1582,7 @@ msgstr "non dispoñíbel"
|
||||
|
||||
#: ../js/ui/status/network.js:493 ../js/ui/status/network.js:1551
|
||||
msgid "connection failed"
|
||||
msgstr "conexión fallida"
|
||||
msgstr "conexión fallada"
|
||||
|
||||
#: ../js/ui/status/network.js:552 ../js/ui/status/network.js:1435
|
||||
#: ../js/ui/status/network.js:1627
|
||||
@@ -1678,7 +1668,6 @@ msgstr "Preferencias de enerxía"
|
||||
#. 0 is reported when UPower does not have enough data
|
||||
#. to estimate battery life
|
||||
#: ../js/ui/status/power.js:99
|
||||
#| msgid "Estimating..."
|
||||
msgid "Estimating…"
|
||||
msgstr "Estimando…"
|
||||
|
||||
@@ -1778,59 +1767,59 @@ msgstr "Volume"
|
||||
msgid "Microphone"
|
||||
msgstr "Micrófono"
|
||||
|
||||
#: ../js/ui/unlockDialog.js:151
|
||||
#: ../js/ui/unlockDialog.js:125
|
||||
msgid "Log in as another user"
|
||||
msgstr "Iniciar sesión como outro usuario"
|
||||
|
||||
#: ../js/ui/unlockDialog.js:177
|
||||
#: ../js/ui/unlockDialog.js:146
|
||||
msgid "Unlock Window"
|
||||
msgstr "Desbloquear xanela"
|
||||
|
||||
#: ../js/ui/userMenu.js:192
|
||||
#: ../js/ui/userMenu.js:193
|
||||
msgid "Available"
|
||||
msgstr "Dispoñíbel"
|
||||
|
||||
#: ../js/ui/userMenu.js:195
|
||||
#: ../js/ui/userMenu.js:196
|
||||
msgid "Busy"
|
||||
msgstr "Ocupado"
|
||||
|
||||
#: ../js/ui/userMenu.js:198
|
||||
#: ../js/ui/userMenu.js:199
|
||||
msgid "Invisible"
|
||||
msgstr "Invisíbel"
|
||||
|
||||
#: ../js/ui/userMenu.js:201
|
||||
#: ../js/ui/userMenu.js:202
|
||||
msgid "Away"
|
||||
msgstr "Ausente"
|
||||
|
||||
#: ../js/ui/userMenu.js:204
|
||||
#: ../js/ui/userMenu.js:205
|
||||
msgid "Idle"
|
||||
msgstr "Inactivo"
|
||||
|
||||
#: ../js/ui/userMenu.js:207
|
||||
#: ../js/ui/userMenu.js:208
|
||||
msgid "Offline"
|
||||
msgstr "Desconectado"
|
||||
|
||||
#: ../js/ui/userMenu.js:779
|
||||
#: ../js/ui/userMenu.js:781
|
||||
msgid "Notifications"
|
||||
msgstr "Notificacións"
|
||||
|
||||
#: ../js/ui/userMenu.js:795
|
||||
#: ../js/ui/userMenu.js:797
|
||||
msgid "Switch User"
|
||||
msgstr "Cambiar de usuario"
|
||||
|
||||
#: ../js/ui/userMenu.js:800
|
||||
#: ../js/ui/userMenu.js:802
|
||||
msgid "Log Out"
|
||||
msgstr "Saír da sesión"
|
||||
|
||||
#: ../js/ui/userMenu.js:820
|
||||
#: ../js/ui/userMenu.js:822
|
||||
msgid "Install Updates & Restart"
|
||||
msgstr "Instalar actualizacións e reiniciar"
|
||||
|
||||
#: ../js/ui/userMenu.js:838
|
||||
#: ../js/ui/userMenu.js:840
|
||||
msgid "Your chat status will be set to busy"
|
||||
msgstr "O seu estado de conversa definirase como «ocupado»"
|
||||
msgstr "O seu estado de conversa estabelecerase a «ocupado»"
|
||||
|
||||
#: ../js/ui/userMenu.js:839
|
||||
#: ../js/ui/userMenu.js:841
|
||||
msgid ""
|
||||
"Notifications are now disabled, including chat messages. Your online status "
|
||||
"has been adjusted to let others know that you might not see their messages."
|
||||
@@ -1839,33 +1828,35 @@ msgstr ""
|
||||
"conversa. O seu estado de conexión axustouse para que outros saiban que non "
|
||||
"quere ver as súas mensaxes."
|
||||
|
||||
#: ../js/ui/userMenu.js:885
|
||||
#: ../js/ui/userMenu.js:888
|
||||
msgid "Other users are logged in."
|
||||
msgstr "Hai outros usuarios conectados."
|
||||
|
||||
#: ../js/ui/userMenu.js:890
|
||||
#: ../js/ui/userMenu.js:893
|
||||
msgid "Shutting down might cause them to lose unsaved work."
|
||||
msgstr "Se apaga o computador pode perder o traballo que non gardou."
|
||||
|
||||
#: ../js/ui/userMenu.js:916
|
||||
#. Translators: Remote here refers to a remote session, like a ssh login
|
||||
#: ../js/ui/userMenu.js:921
|
||||
#, c-format
|
||||
msgid "%s (remote)"
|
||||
msgstr "%s (remoto)"
|
||||
|
||||
#: ../js/ui/userMenu.js:918
|
||||
#. Translators: Console here refers to a tty like a VT console
|
||||
#: ../js/ui/userMenu.js:924
|
||||
#, c-format
|
||||
msgid "%s (console)"
|
||||
msgstr "%s (consola)"
|
||||
|
||||
#: ../js/ui/viewSelector.js:101
|
||||
#: ../js/ui/viewSelector.js:100
|
||||
msgid "Applications"
|
||||
msgstr "Aplicativos"
|
||||
|
||||
#: ../js/ui/viewSelector.js:105
|
||||
#: ../js/ui/viewSelector.js:104
|
||||
msgid "Search"
|
||||
msgstr "Buscar"
|
||||
|
||||
#: ../js/ui/wanda.js:92
|
||||
#: ../js/ui/wanda.js:77
|
||||
#, c-format
|
||||
msgid ""
|
||||
"Sorry, no wisdom for you today:\n"
|
||||
@@ -1874,7 +1865,7 @@ msgstr ""
|
||||
"Hoxe non ten ningunha mensaxe:\n"
|
||||
"%s"
|
||||
|
||||
#: ../js/ui/wanda.js:96
|
||||
#: ../js/ui/wanda.js:81
|
||||
#, c-format
|
||||
msgid "%s the Oracle says"
|
||||
msgstr "%s o oráculo dí"
|
||||
|
||||
157
po/nb.po
157
po/nb.po
@@ -6,10 +6,10 @@
|
||||
# Torstein Adolf Winterseth <kvikende@fsfe.org>, 2010.
|
||||
msgid ""
|
||||
msgstr ""
|
||||
"Project-Id-Version: gnome-shell 3.7.x\n"
|
||||
"Project-Id-Version: gnome-shell 3.8.x\n"
|
||||
"Report-Msgid-Bugs-To: \n"
|
||||
"POT-Creation-Date: 2013-03-04 14:14+0100\n"
|
||||
"PO-Revision-Date: 2013-03-04 14:15+0100\n"
|
||||
"POT-Creation-Date: 2013-04-03 13:31+0200\n"
|
||||
"PO-Revision-Date: 2013-04-03 13:31+0200\n"
|
||||
"Last-Translator: Kjartan Maraas <kmaraas@gnome.org>\n"
|
||||
"Language-Team: Norwegian bokmål <i18n-nb@lister.ping.uio.no>\n"
|
||||
"Language: \n"
|
||||
@@ -295,7 +295,8 @@ msgstr "Fest modal dialog til opphavsvinduet"
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:43
|
||||
msgid ""
|
||||
"This key overrides the key in org.gnome.mutter when running GNOME Shell."
|
||||
msgstr "Denne nøkkelen overstyrer nøkkelen i org.gnome.mutter når GNOME Shell kjøres."
|
||||
msgstr ""
|
||||
"Denne nøkkelen overstyrer nøkkelen i org.gnome.mutter når GNOME Shell kjøres."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:44
|
||||
msgid "Arrangement of buttons on the titlebar"
|
||||
@@ -305,7 +306,9 @@ msgstr "Plassering av knappene på tittellinjen"
|
||||
msgid ""
|
||||
"This key overrides the key in org.gnome.desktop.wm.preferences when running "
|
||||
"GNOME Shell."
|
||||
msgstr "Denne nøkkelen overstyrer nøkkelen i org.gnome.desktop.wm.preferences når GNOME Shell kjøres."
|
||||
msgstr ""
|
||||
"Denne nøkkelen overstyrer nøkkelen i org.gnome.desktop.wm.preferences når "
|
||||
"GNOME Shell kjøres."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:46
|
||||
msgid "Enable edge tiling when dropping windows on screen edges"
|
||||
@@ -339,36 +342,36 @@ msgstr "Økt …"
|
||||
#. translators: this message is shown below the user list on the
|
||||
#. login screen. It can be activated to reveal an entry for
|
||||
#. manually entering the username.
|
||||
#: ../js/gdm/loginDialog.js:629
|
||||
#: ../js/gdm/loginDialog.js:630
|
||||
msgid "Not listed?"
|
||||
msgstr "Ikke listet?"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:783 ../js/ui/components/networkAgent.js:137
|
||||
#: ../js/gdm/loginDialog.js:786 ../js/ui/components/networkAgent.js:137
|
||||
#: ../js/ui/components/polkitAgent.js:162 ../js/ui/endSessionDialog.js:375
|
||||
#: ../js/ui/extensionDownloader.js:195 ../js/ui/shellMountOperation.js:399
|
||||
#: ../js/ui/status/bluetooth.js:415 ../js/ui/unlockDialog.js:126
|
||||
#: ../js/ui/userMenu.js:934
|
||||
#: ../js/ui/status/bluetooth.js:415 ../js/ui/unlockDialog.js:99
|
||||
#: ../js/ui/userMenu.js:938
|
||||
msgid "Cancel"
|
||||
msgstr "Avbryt"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:799
|
||||
#: ../js/gdm/loginDialog.js:802
|
||||
msgctxt "button"
|
||||
msgid "Sign In"
|
||||
msgstr "Logg inn"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:799
|
||||
#: ../js/gdm/loginDialog.js:802
|
||||
msgid "Next"
|
||||
msgstr "Neste"
|
||||
|
||||
#. TTLS and PEAP are actually much more complicated, but this complication
|
||||
#. is not visible here since we only care about phase2 authentication
|
||||
#. (and don't even care of which one)
|
||||
#: ../js/gdm/loginDialog.js:904 ../js/ui/components/networkAgent.js:260
|
||||
#: ../js/gdm/loginDialog.js:917 ../js/ui/components/networkAgent.js:260
|
||||
#: ../js/ui/components/networkAgent.js:278
|
||||
msgid "Username: "
|
||||
msgstr "Brukernavn: "
|
||||
|
||||
#: ../js/gdm/loginDialog.js:1157
|
||||
#: ../js/gdm/loginDialog.js:1173
|
||||
msgid "Login Window"
|
||||
msgstr "Innloggingsvindu"
|
||||
|
||||
@@ -377,8 +380,8 @@ msgstr "Innloggingsvindu"
|
||||
msgid "Power"
|
||||
msgstr "Strøm"
|
||||
|
||||
#: ../js/gdm/powerMenu.js:93 ../js/ui/userMenu.js:695 ../js/ui/userMenu.js:699
|
||||
#: ../js/ui/userMenu.js:815
|
||||
#: ../js/gdm/powerMenu.js:93 ../js/ui/userMenu.js:696 ../js/ui/userMenu.js:700
|
||||
#: ../js/ui/userMenu.js:816
|
||||
msgid "Suspend"
|
||||
msgstr "Hvilemodus"
|
||||
|
||||
@@ -386,58 +389,58 @@ msgstr "Hvilemodus"
|
||||
msgid "Restart"
|
||||
msgstr "Start på nytt"
|
||||
|
||||
#: ../js/gdm/powerMenu.js:103 ../js/ui/userMenu.js:697
|
||||
#: ../js/ui/userMenu.js:699 ../js/ui/userMenu.js:814 ../js/ui/userMenu.js:938
|
||||
#: ../js/gdm/powerMenu.js:103 ../js/ui/userMenu.js:698
|
||||
#: ../js/ui/userMenu.js:700 ../js/ui/userMenu.js:815 ../js/ui/userMenu.js:942
|
||||
msgid "Power Off"
|
||||
msgstr "Slå av"
|
||||
|
||||
#: ../js/gdm/util.js:182
|
||||
#: ../js/gdm/util.js:249
|
||||
msgid "Authentication error"
|
||||
msgstr "Autentiseringsfeil"
|
||||
|
||||
#. Translators: this message is shown below the password entry field
|
||||
#. to indicate the user can swipe their finger instead
|
||||
#: ../js/gdm/util.js:299
|
||||
#: ../js/gdm/util.js:366
|
||||
msgid "(or swipe finger)"
|
||||
msgstr "(eller dra finger)"
|
||||
|
||||
#: ../js/gdm/util.js:324
|
||||
#: ../js/gdm/util.js:391
|
||||
#, c-format
|
||||
msgid "(e.g., user or %s)"
|
||||
msgstr "(f.eks. bruker eller %s)"
|
||||
|
||||
#: ../js/misc/util.js:94
|
||||
#: ../js/misc/util.js:97
|
||||
msgid "Command not found"
|
||||
msgstr "Kommando ikke funnet"
|
||||
|
||||
#. Replace "Error invoking GLib.shell_parse_argv: " with
|
||||
#. something nicer
|
||||
#: ../js/misc/util.js:127
|
||||
#: ../js/misc/util.js:130
|
||||
msgid "Could not parse command:"
|
||||
msgstr "Klarte ikke å lese kommando:"
|
||||
|
||||
#: ../js/misc/util.js:135
|
||||
#: ../js/misc/util.js:138
|
||||
#, c-format
|
||||
msgid "Execution of '%s' failed:"
|
||||
msgstr "Kjøring av «%s» feilet:"
|
||||
|
||||
#: ../js/ui/appDisplay.js:348
|
||||
#: ../js/ui/appDisplay.js:349
|
||||
msgid "Frequent"
|
||||
msgstr "Ofte"
|
||||
|
||||
#: ../js/ui/appDisplay.js:355
|
||||
#: ../js/ui/appDisplay.js:356
|
||||
msgid "All"
|
||||
msgstr "Alle"
|
||||
|
||||
#: ../js/ui/appDisplay.js:913
|
||||
#: ../js/ui/appDisplay.js:914
|
||||
msgid "New Window"
|
||||
msgstr "Nytt vindu"
|
||||
|
||||
#: ../js/ui/appDisplay.js:916 ../js/ui/dash.js:284
|
||||
#: ../js/ui/appDisplay.js:917 ../js/ui/dash.js:284
|
||||
msgid "Remove from Favorites"
|
||||
msgstr "Fjern fra favoritter"
|
||||
|
||||
#: ../js/ui/appDisplay.js:917
|
||||
#: ../js/ui/appDisplay.js:918
|
||||
msgid "Add to Favorites"
|
||||
msgstr "Legg til i favoritter"
|
||||
|
||||
@@ -451,7 +454,7 @@ msgstr "%s ble lagt til i dine favoritter."
|
||||
msgid "%s has been removed from your favorites."
|
||||
msgstr "%s ble fjernet fra dine favoritter."
|
||||
|
||||
#: ../js/ui/backgroundMenu.js:19 ../js/ui/userMenu.js:788
|
||||
#: ../js/ui/backgroundMenu.js:19 ../js/ui/userMenu.js:789
|
||||
msgid "Settings"
|
||||
msgstr "Innstillinger"
|
||||
|
||||
@@ -474,7 +477,7 @@ msgctxt "event list time"
|
||||
msgid "%H\\u2236%M"
|
||||
msgstr "%H\\u2336%M"
|
||||
|
||||
#. Transators: Shown in calendar event list, if 12h format,
|
||||
#. Translators: Shown in calendar event list, if 12h format,
|
||||
#. \u2236 is a ratio character, similar to : and \u2009 is
|
||||
#. a thin space
|
||||
#: ../js/ui/calendar.js:77
|
||||
@@ -576,35 +579,35 @@ msgid "S"
|
||||
msgstr "Lø"
|
||||
|
||||
#. Translators: Text to show if there are no events
|
||||
#: ../js/ui/calendar.js:692
|
||||
#: ../js/ui/calendar.js:720
|
||||
msgid "Nothing Scheduled"
|
||||
msgstr "Ingenting planlagt"
|
||||
|
||||
#. Translators: Shown on calendar heading when selected day occurs on current year
|
||||
#: ../js/ui/calendar.js:708
|
||||
#: ../js/ui/calendar.js:736
|
||||
msgctxt "calendar heading"
|
||||
msgid "%A, %B %d"
|
||||
msgstr "%A %B %d"
|
||||
|
||||
#. Translators: Shown on calendar heading when selected day occurs on different year
|
||||
#: ../js/ui/calendar.js:711
|
||||
#: ../js/ui/calendar.js:739
|
||||
msgctxt "calendar heading"
|
||||
msgid "%A, %B %d, %Y"
|
||||
msgstr "%A %B %d, %Y"
|
||||
|
||||
#: ../js/ui/calendar.js:721
|
||||
#: ../js/ui/calendar.js:749
|
||||
msgid "Today"
|
||||
msgstr "I dag"
|
||||
|
||||
#: ../js/ui/calendar.js:725
|
||||
#: ../js/ui/calendar.js:753
|
||||
msgid "Tomorrow"
|
||||
msgstr "I morgen"
|
||||
|
||||
#: ../js/ui/calendar.js:736
|
||||
#: ../js/ui/calendar.js:764
|
||||
msgid "This week"
|
||||
msgstr "Denne uken"
|
||||
|
||||
#: ../js/ui/calendar.js:744
|
||||
#: ../js/ui/calendar.js:772
|
||||
msgid "Next week"
|
||||
msgstr "Neste uke"
|
||||
|
||||
@@ -620,12 +623,12 @@ msgstr "Ekstern stasjon koblet fra"
|
||||
msgid "Removable Devices"
|
||||
msgstr "Avtagbare enheter"
|
||||
|
||||
#: ../js/ui/components/autorunManager.js:593
|
||||
#: ../js/ui/components/autorunManager.js:594
|
||||
#, c-format
|
||||
msgid "Open with %s"
|
||||
msgstr "Åpne med %s"
|
||||
|
||||
#: ../js/ui/components/autorunManager.js:619
|
||||
#: ../js/ui/components/autorunManager.js:620
|
||||
msgid "Eject"
|
||||
msgstr "Løs ut"
|
||||
|
||||
@@ -1007,7 +1010,7 @@ msgstr "Innstillinger for dato og klokkeslett"
|
||||
#. Translators: This is the date format to use when the calendar popup is
|
||||
#. * shown - it is shown just below the time in the shell (e.g. "Tue 9:29 AM").
|
||||
#.
|
||||
#: ../js/ui/dateMenu.js:205
|
||||
#: ../js/ui/dateMenu.js:215
|
||||
msgid "%A %B %e, %Y"
|
||||
msgstr "%a %e %B, %Y"
|
||||
|
||||
@@ -1181,15 +1184,15 @@ msgstr "Tøm meldinger"
|
||||
msgid "Notification Settings"
|
||||
msgstr "Innstillinger for varsling"
|
||||
|
||||
#: ../js/ui/messageTray.js:1707
|
||||
#: ../js/ui/messageTray.js:1709
|
||||
msgid "No Messages"
|
||||
msgstr "Ingen meldinger"
|
||||
|
||||
#: ../js/ui/messageTray.js:1787
|
||||
#: ../js/ui/messageTray.js:1782
|
||||
msgid "Message Tray"
|
||||
msgstr "Meldingstrau"
|
||||
|
||||
#: ../js/ui/messageTray.js:2864
|
||||
#: ../js/ui/messageTray.js:2810
|
||||
msgid "System Information"
|
||||
msgstr "Systeminformasjon"
|
||||
|
||||
@@ -1198,14 +1201,14 @@ msgctxt "program"
|
||||
msgid "Unknown"
|
||||
msgstr "Ukjent"
|
||||
|
||||
#: ../js/ui/overviewControls.js:460 ../js/ui/screenShield.js:153
|
||||
#: ../js/ui/overviewControls.js:463 ../js/ui/screenShield.js:149
|
||||
#, c-format
|
||||
msgid "%d new message"
|
||||
msgid_plural "%d new messages"
|
||||
msgstr[0] "%d ny melding"
|
||||
msgstr[1] "%d nye meldinger"
|
||||
|
||||
#: ../js/ui/overview.js:82
|
||||
#: ../js/ui/overview.js:84
|
||||
msgid "Undo"
|
||||
msgstr "Angre"
|
||||
|
||||
@@ -1217,21 +1220,21 @@ msgstr "Oversikt"
|
||||
#. in the search entry when no search is
|
||||
#. active; it should not exceed ~30
|
||||
#. characters.
|
||||
#: ../js/ui/overview.js:284
|
||||
#: ../js/ui/overview.js:271
|
||||
msgid "Type to search…"
|
||||
msgstr "Skriv for å søke …"
|
||||
|
||||
#: ../js/ui/panel.js:613
|
||||
#: ../js/ui/panel.js:612
|
||||
msgid "Quit"
|
||||
msgstr "Avslutt"
|
||||
|
||||
#. Translators: If there is no suitable word for "Activities"
|
||||
#. in your language, you can use the word for "Overview".
|
||||
#: ../js/ui/panel.js:642
|
||||
#: ../js/ui/panel.js:636
|
||||
msgid "Activities"
|
||||
msgstr "Aktiviteter"
|
||||
|
||||
#: ../js/ui/panel.js:983
|
||||
#: ../js/ui/panel.js:933
|
||||
msgid "Top Bar"
|
||||
msgstr "Topp-panel"
|
||||
|
||||
@@ -1244,32 +1247,32 @@ msgstr "Topp-panel"
|
||||
msgid "toggle-switch-us"
|
||||
msgstr "toggle-switch-intl"
|
||||
|
||||
#: ../js/ui/runDialog.js:205
|
||||
#: ../js/ui/runDialog.js:73
|
||||
msgid "Enter a Command"
|
||||
msgstr "Oppgi en kommando"
|
||||
|
||||
#: ../js/ui/runDialog.js:241
|
||||
#: ../js/ui/runDialog.js:109
|
||||
msgid "Close"
|
||||
msgstr "Lukk"
|
||||
|
||||
#. Translators: This is a time format for a date in
|
||||
#. long format
|
||||
#: ../js/ui/screenShield.js:90
|
||||
#: ../js/ui/screenShield.js:86
|
||||
msgid "%A, %B %d"
|
||||
msgstr "%A, %B %d"
|
||||
|
||||
#: ../js/ui/screenShield.js:155
|
||||
#: ../js/ui/screenShield.js:151
|
||||
#, c-format
|
||||
msgid "%d new notification"
|
||||
msgid_plural "%d new notifications"
|
||||
msgstr[0] "%d ny varsling"
|
||||
msgstr[1] "%d nye varslinger"
|
||||
|
||||
#: ../js/ui/screenShield.js:442 ../js/ui/userMenu.js:806
|
||||
#: ../js/ui/screenShield.js:438 ../js/ui/userMenu.js:807
|
||||
msgid "Lock"
|
||||
msgstr "Lås"
|
||||
|
||||
#: ../js/ui/screenShield.js:639
|
||||
#: ../js/ui/screenShield.js:640
|
||||
msgid "GNOME needs to lock the screen"
|
||||
msgstr "GNOME må låse skjermen"
|
||||
|
||||
@@ -1280,19 +1283,19 @@ msgstr "GNOME må låse skjermen"
|
||||
#.
|
||||
#. XXX: another option is to kick the user into the gdm login
|
||||
#. screen, where we're not affected by grabs
|
||||
#: ../js/ui/screenShield.js:758 ../js/ui/screenShield.js:1169
|
||||
#: ../js/ui/screenShield.js:761 ../js/ui/screenShield.js:1197
|
||||
msgid "Unable to lock"
|
||||
msgstr "Kan ikke låse"
|
||||
|
||||
#: ../js/ui/screenShield.js:759 ../js/ui/screenShield.js:1170
|
||||
#: ../js/ui/screenShield.js:762 ../js/ui/screenShield.js:1198
|
||||
msgid "Lock was blocked by an application"
|
||||
msgstr "Låsing ble stoppet av et program"
|
||||
|
||||
#: ../js/ui/searchDisplay.js:431
|
||||
#: ../js/ui/searchDisplay.js:453
|
||||
msgid "Searching…"
|
||||
msgstr "Søker …"
|
||||
|
||||
#: ../js/ui/searchDisplay.js:475
|
||||
#: ../js/ui/searchDisplay.js:497
|
||||
msgid "No results."
|
||||
msgstr "Ingen resultater."
|
||||
|
||||
@@ -1304,11 +1307,11 @@ msgstr "Kopier"
|
||||
msgid "Paste"
|
||||
msgstr "Lim inn"
|
||||
|
||||
#: ../js/ui/shellEntry.js:105
|
||||
#: ../js/ui/shellEntry.js:106
|
||||
msgid "Show Text"
|
||||
msgstr "Vis tekst"
|
||||
|
||||
#: ../js/ui/shellEntry.js:107
|
||||
#: ../js/ui/shellEntry.js:108
|
||||
msgid "Hide Text"
|
||||
msgstr "Skjul tekst"
|
||||
|
||||
@@ -1320,7 +1323,7 @@ msgstr "Passord"
|
||||
msgid "Remember Password"
|
||||
msgstr "Husk passord"
|
||||
|
||||
#: ../js/ui/shellMountOperation.js:403 ../js/ui/unlockDialog.js:140
|
||||
#: ../js/ui/shellMountOperation.js:403 ../js/ui/unlockDialog.js:113
|
||||
msgid "Unlock"
|
||||
msgstr "Lås opp"
|
||||
|
||||
@@ -1725,11 +1728,11 @@ msgstr "Volum"
|
||||
msgid "Microphone"
|
||||
msgstr "Mikrofon"
|
||||
|
||||
#: ../js/ui/unlockDialog.js:151
|
||||
#: ../js/ui/unlockDialog.js:124
|
||||
msgid "Log in as another user"
|
||||
msgstr "Logg inn som en annen bruker"
|
||||
|
||||
#: ../js/ui/unlockDialog.js:177
|
||||
#: ../js/ui/unlockDialog.js:145
|
||||
msgid "Unlock Window"
|
||||
msgstr "Lås opp vindu"
|
||||
|
||||
@@ -1757,27 +1760,27 @@ msgstr "Ledig"
|
||||
msgid "Offline"
|
||||
msgstr "Frakoblet"
|
||||
|
||||
#: ../js/ui/userMenu.js:780
|
||||
#: ../js/ui/userMenu.js:781
|
||||
msgid "Notifications"
|
||||
msgstr "Varslinger"
|
||||
|
||||
#: ../js/ui/userMenu.js:796
|
||||
#: ../js/ui/userMenu.js:797
|
||||
msgid "Switch User"
|
||||
msgstr "Bytt bruker"
|
||||
|
||||
#: ../js/ui/userMenu.js:801
|
||||
#: ../js/ui/userMenu.js:802
|
||||
msgid "Log Out"
|
||||
msgstr "Logg ut"
|
||||
|
||||
#: ../js/ui/userMenu.js:821
|
||||
#: ../js/ui/userMenu.js:822
|
||||
msgid "Install Updates & Restart"
|
||||
msgstr "Installer oppdateringer og start på nytt"
|
||||
|
||||
#: ../js/ui/userMenu.js:839
|
||||
#: ../js/ui/userMenu.js:840
|
||||
msgid "Your chat status will be set to busy"
|
||||
msgstr "Din pratestatus vil bli satt til opptatt"
|
||||
|
||||
#: ../js/ui/userMenu.js:840
|
||||
#: ../js/ui/userMenu.js:841
|
||||
msgid ""
|
||||
"Notifications are now disabled, including chat messages. Your online status "
|
||||
"has been adjusted to let others know that you might not see their messages."
|
||||
@@ -1786,22 +1789,24 @@ msgstr ""
|
||||
"tilkoblingsstatus er justert for å la andre vite at du kanskje ikke ser "
|
||||
"deres meldinger."
|
||||
|
||||
#: ../js/ui/userMenu.js:886
|
||||
#: ../js/ui/userMenu.js:888
|
||||
msgid "Other users are logged in."
|
||||
msgstr "Andre brukere er logget inn."
|
||||
|
||||
#: ../js/ui/userMenu.js:891
|
||||
#: ../js/ui/userMenu.js:893
|
||||
msgid "Shutting down might cause them to lose unsaved work."
|
||||
msgstr ""
|
||||
"Hvis du slår av vil dette kunne medføre at de mister arbeid som ikke er "
|
||||
"lagret."
|
||||
|
||||
#: ../js/ui/userMenu.js:918
|
||||
#. Translators: Remote here refers to a remote session, like a ssh login
|
||||
#: ../js/ui/userMenu.js:921
|
||||
#, c-format
|
||||
msgid "%s (remote)"
|
||||
msgstr "%s (ekstern)"
|
||||
|
||||
#: ../js/ui/userMenu.js:920
|
||||
#. Translators: Console here refers to a tty like a VT console
|
||||
#: ../js/ui/userMenu.js:924
|
||||
#, c-format
|
||||
msgid "%s (console)"
|
||||
msgstr "%s (konsoll)"
|
||||
@@ -1814,7 +1819,7 @@ msgstr "Programmer"
|
||||
msgid "Search"
|
||||
msgstr "Søk"
|
||||
|
||||
#: ../js/ui/wanda.js:92
|
||||
#: ../js/ui/wanda.js:77
|
||||
#, c-format
|
||||
msgid ""
|
||||
"Sorry, no wisdom for you today:\n"
|
||||
@@ -1823,7 +1828,7 @@ msgstr ""
|
||||
"Beklager, ingen visdom til deg i dag:\n"
|
||||
"%s"
|
||||
|
||||
#: ../js/ui/wanda.js:96
|
||||
#: ../js/ui/wanda.js:81
|
||||
#, c-format
|
||||
msgid "%s the Oracle says"
|
||||
msgstr "Orakelet sier %s"
|
||||
|
||||
307
po/pl.po
307
po/pl.po
@@ -6,14 +6,15 @@
|
||||
# -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
|
||||
# Piotr Drąg <piotrdrag@gmail.com>, 2009-2013.
|
||||
# Tomasz Dominikowski <dominikowski@gmail.com>, 2009.
|
||||
# Wojciech Szczęsny <wszczesny@aviary.pl>, 2013.
|
||||
# Aviary.pl <gnomepl@aviary.pl>, 2009-2013.
|
||||
msgid ""
|
||||
msgstr ""
|
||||
"Project-Id-Version: gnome-shell\n"
|
||||
"Report-Msgid-Bugs-To: \n"
|
||||
"POT-Creation-Date: 2013-02-24 01:52+0100\n"
|
||||
"PO-Revision-Date: 2013-02-24 01:53+0100\n"
|
||||
"Last-Translator: Piotr Drąg <piotrdrag@gmail.com>\n"
|
||||
"POT-Creation-Date: 2013-04-02 15:54+0200\n"
|
||||
"PO-Revision-Date: 2013-04-02 15:55+0200\n"
|
||||
"Last-Translator: Wojciech Szczęsny <wszczesny@aviary.pl>\n"
|
||||
"Language-Team: Polish <gnomepl@aviary.pl>\n"
|
||||
"Language: pl\n"
|
||||
"MIME-Version: 1.0\n"
|
||||
@@ -61,7 +62,7 @@ msgid "Window management and application launching"
|
||||
msgstr "Zarządzanie oknami i uruchamianiem programów"
|
||||
|
||||
#: ../data/gnome-shell-extension-prefs.desktop.in.in.h:1
|
||||
#: ../js/extensionPrefs/main.js:152
|
||||
#: ../js/extensionPrefs/main.js:153
|
||||
msgid "GNOME Shell Extension Preferences"
|
||||
msgstr "Preferencje rozszerzenia powłoki GNOME"
|
||||
|
||||
@@ -80,7 +81,7 @@ msgid ""
|
||||
"Allows access to internal debugging and monitoring tools using the Alt-F2 "
|
||||
"dialog."
|
||||
msgstr ""
|
||||
"Umożliwia dostęp do wewnętrznych narzędzi debugowania i monitorowania "
|
||||
"Umożliwia dostęp do wewnętrznych narzędzi debugowania i monitorowania, "
|
||||
"używając okna dialogowego Alt-F2."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:3
|
||||
@@ -96,9 +97,9 @@ msgid ""
|
||||
msgstr ""
|
||||
"Rozszerzenia powłoki GNOME posiadają własność UUID; ten klucz zawiera "
|
||||
"rozszerzenia, które powinny zostać wczytane. Każde rozszerzenie, które ma "
|
||||
"zostać wczytane musi znajdować się na tej liście. Można także manipulować tą "
|
||||
"listą za pomocą metod EnableExtension i DisableExtension usługi D-Bus na org."
|
||||
"gnome.Shell."
|
||||
"zostać wczytane, musi znajdować się na tej liście. Można także manipulować "
|
||||
"tą listą za pomocą metod EnableExtension i DisableExtension usługi D-Bus na "
|
||||
"org.gnome.Shell."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:5
|
||||
msgid "Whether to collect stats about applications usage"
|
||||
@@ -112,7 +113,7 @@ msgid ""
|
||||
"remove already saved data."
|
||||
msgstr ""
|
||||
"Powłoka zwykle monitoruje aktywne programy, aby przedstawiać najczęściej "
|
||||
"używane (np. aktywatory programów). Mimo, że te dane nie są publiczne, można "
|
||||
"używane (np. aktywatory programów). Mimo że te dane nie są publiczne, można "
|
||||
"wyłączyć je z powodu prywatności. Proszę zauważyć, że wyłączenie nie "
|
||||
"spowoduje usunięcia już zapisanych danych."
|
||||
|
||||
@@ -138,7 +139,7 @@ msgid ""
|
||||
"application view, rather than being displayed inline in the main view."
|
||||
msgstr ""
|
||||
"Każda nazwa kategorii na tej liście będzie przedstawiana jako katalog w "
|
||||
"widoku programów, zamiast wyświetlać ją bezpośrednio w głównym widoku."
|
||||
"widoku programów, zamiast wyświetlania jej bezpośrednio w głównym widoku."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:11
|
||||
msgid "History for command (Alt-F2) dialog"
|
||||
@@ -286,7 +287,7 @@ msgstr ""
|
||||
"Ustawia potok biblioteki GStreamer używany do zakodowania nagrań. Używa "
|
||||
"składni programu gst-launch. Potok powinien posiadać niepołączony odpływ, "
|
||||
"gdzie jest nagrywane. Zwykle taki posiada, a wyjście będzie zapisywane do "
|
||||
"pliku wyjściowego. Mimo, że potok może sam zająć się swoim wyjściem, można "
|
||||
"pliku wyjściowego. Mimo że potok może sam zająć się swoim wyjściem, można "
|
||||
"także wysłać wyjście do serwera icecast przez polecenie shout2send lub "
|
||||
"podobne. Jeśli nie zostanie ustawione lub ustawione na pustą wartość, to "
|
||||
"zostanie użyty domyślny potok. Jest nim obecnie \"vp8enc min_quantizer=13 "
|
||||
@@ -359,20 +360,20 @@ msgstr "Dynamiczne zarządzanie obszarami roboczymi"
|
||||
msgid "Workspaces only on primary monitor"
|
||||
msgstr "Obszary robocze tylko na pierwszym monitorze"
|
||||
|
||||
#: ../js/extensionPrefs/main.js:124
|
||||
#: ../js/extensionPrefs/main.js:125
|
||||
#, c-format
|
||||
msgid "There was an error loading the preferences dialog for %s:"
|
||||
msgstr ""
|
||||
"Wystąpił błąd podczas wczytywania okna preferencji dla rozszerzenia %s:"
|
||||
|
||||
#: ../js/extensionPrefs/main.js:164
|
||||
#: ../js/extensionPrefs/main.js:165
|
||||
msgid "Extension"
|
||||
msgstr "Rozszerzenie"
|
||||
|
||||
#: ../js/extensionPrefs/main.js:188
|
||||
#: ../js/extensionPrefs/main.js:189
|
||||
msgid "Select an extension to configure using the combobox above."
|
||||
msgstr ""
|
||||
"Proszę wybrać rozszerzenie do skonfigurowania używając powyższego pola "
|
||||
"Proszę wybrać rozszerzenie do skonfigurowania, używając powyższego pola "
|
||||
"wyboru."
|
||||
|
||||
#: ../js/gdm/loginDialog.js:405
|
||||
@@ -382,36 +383,36 @@ msgstr "Sesja…"
|
||||
#. translators: this message is shown below the user list on the
|
||||
#. login screen. It can be activated to reveal an entry for
|
||||
#. manually entering the username.
|
||||
#: ../js/gdm/loginDialog.js:629
|
||||
#: ../js/gdm/loginDialog.js:630
|
||||
msgid "Not listed?"
|
||||
msgstr "Inny użytkownik?"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:783 ../js/ui/components/networkAgent.js:137
|
||||
#: ../js/gdm/loginDialog.js:786 ../js/ui/components/networkAgent.js:137
|
||||
#: ../js/ui/components/polkitAgent.js:162 ../js/ui/endSessionDialog.js:375
|
||||
#: ../js/ui/extensionDownloader.js:195 ../js/ui/shellMountOperation.js:399
|
||||
#: ../js/ui/status/bluetooth.js:415 ../js/ui/unlockDialog.js:126
|
||||
#: ../js/ui/userMenu.js:932
|
||||
#: ../js/ui/status/bluetooth.js:415 ../js/ui/unlockDialog.js:99
|
||||
#: ../js/ui/userMenu.js:938
|
||||
msgid "Cancel"
|
||||
msgstr "Anuluj"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:799
|
||||
#: ../js/gdm/loginDialog.js:802
|
||||
msgctxt "button"
|
||||
msgid "Sign In"
|
||||
msgstr "Zaloguj"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:799
|
||||
#: ../js/gdm/loginDialog.js:802
|
||||
msgid "Next"
|
||||
msgstr "Dalej"
|
||||
|
||||
#. TTLS and PEAP are actually much more complicated, but this complication
|
||||
#. is not visible here since we only care about phase2 authentication
|
||||
#. (and don't even care of which one)
|
||||
#: ../js/gdm/loginDialog.js:904 ../js/ui/components/networkAgent.js:260
|
||||
#: ../js/gdm/loginDialog.js:917 ../js/ui/components/networkAgent.js:260
|
||||
#: ../js/ui/components/networkAgent.js:278
|
||||
msgid "Username: "
|
||||
msgstr "Nazwa użytkownika: "
|
||||
|
||||
#: ../js/gdm/loginDialog.js:1157
|
||||
#: ../js/gdm/loginDialog.js:1173
|
||||
msgid "Login Window"
|
||||
msgstr "Okno logowania"
|
||||
|
||||
@@ -420,8 +421,8 @@ msgstr "Okno logowania"
|
||||
msgid "Power"
|
||||
msgstr "Zasilanie"
|
||||
|
||||
#: ../js/gdm/powerMenu.js:93 ../js/ui/userMenu.js:694 ../js/ui/userMenu.js:698
|
||||
#: ../js/ui/userMenu.js:814
|
||||
#: ../js/gdm/powerMenu.js:93 ../js/ui/userMenu.js:696 ../js/ui/userMenu.js:700
|
||||
#: ../js/ui/userMenu.js:816
|
||||
msgid "Suspend"
|
||||
msgstr "Uśpij"
|
||||
|
||||
@@ -429,58 +430,58 @@ msgstr "Uśpij"
|
||||
msgid "Restart"
|
||||
msgstr "Uruchom ponownie"
|
||||
|
||||
#: ../js/gdm/powerMenu.js:103 ../js/ui/userMenu.js:696
|
||||
#: ../js/ui/userMenu.js:698 ../js/ui/userMenu.js:813 ../js/ui/userMenu.js:936
|
||||
#: ../js/gdm/powerMenu.js:103 ../js/ui/userMenu.js:698
|
||||
#: ../js/ui/userMenu.js:700 ../js/ui/userMenu.js:815 ../js/ui/userMenu.js:942
|
||||
msgid "Power Off"
|
||||
msgstr "Wyłącz komputer"
|
||||
|
||||
#: ../js/gdm/util.js:182
|
||||
#: ../js/gdm/util.js:249
|
||||
msgid "Authentication error"
|
||||
msgstr "Błąd uwierzytelniania"
|
||||
|
||||
#. Translators: this message is shown below the password entry field
|
||||
#. to indicate the user can swipe their finger instead
|
||||
#: ../js/gdm/util.js:299
|
||||
#: ../js/gdm/util.js:366
|
||||
msgid "(or swipe finger)"
|
||||
msgstr "(lub przeciągnięcie palca)"
|
||||
|
||||
#: ../js/gdm/util.js:324
|
||||
#: ../js/gdm/util.js:391
|
||||
#, c-format
|
||||
msgid "(e.g., user or %s)"
|
||||
msgstr "(np. użytkownik lub %s)"
|
||||
|
||||
#: ../js/misc/util.js:94
|
||||
#: ../js/misc/util.js:97
|
||||
msgid "Command not found"
|
||||
msgstr "Nie odnaleziono polecenia"
|
||||
|
||||
#. Replace "Error invoking GLib.shell_parse_argv: " with
|
||||
#. something nicer
|
||||
#: ../js/misc/util.js:127
|
||||
#: ../js/misc/util.js:130
|
||||
msgid "Could not parse command:"
|
||||
msgstr "Nie można przetworzyć polecenia:"
|
||||
|
||||
#: ../js/misc/util.js:135
|
||||
#: ../js/misc/util.js:138
|
||||
#, c-format
|
||||
msgid "Execution of '%s' failed:"
|
||||
msgstr "Wykonanie polecenia \"%s\" się nie powiodło:"
|
||||
|
||||
#: ../js/ui/appDisplay.js:348
|
||||
#: ../js/ui/appDisplay.js:349
|
||||
msgid "Frequent"
|
||||
msgstr "Często używane"
|
||||
|
||||
#: ../js/ui/appDisplay.js:355
|
||||
#: ../js/ui/appDisplay.js:356
|
||||
msgid "All"
|
||||
msgstr "Wszystkie"
|
||||
|
||||
#: ../js/ui/appDisplay.js:913
|
||||
#: ../js/ui/appDisplay.js:914
|
||||
msgid "New Window"
|
||||
msgstr "Nowe okno"
|
||||
|
||||
#: ../js/ui/appDisplay.js:916 ../js/ui/dash.js:284
|
||||
#: ../js/ui/appDisplay.js:917 ../js/ui/dash.js:284
|
||||
msgid "Remove from Favorites"
|
||||
msgstr "Usuń z ulubionych"
|
||||
|
||||
#: ../js/ui/appDisplay.js:917
|
||||
#: ../js/ui/appDisplay.js:918
|
||||
msgid "Add to Favorites"
|
||||
msgstr "Dodaj do ulubionych"
|
||||
|
||||
@@ -494,7 +495,7 @@ msgstr "Program %s został dodany do ulubionych."
|
||||
msgid "%s has been removed from your favorites."
|
||||
msgstr "Program %s został usunięty z ulubionych."
|
||||
|
||||
#: ../js/ui/backgroundMenu.js:19 ../js/ui/userMenu.js:787
|
||||
#: ../js/ui/backgroundMenu.js:19 ../js/ui/userMenu.js:789
|
||||
msgid "Settings"
|
||||
msgstr "Ustawienia"
|
||||
|
||||
@@ -517,7 +518,7 @@ msgctxt "event list time"
|
||||
msgid "%H\\u2236%M"
|
||||
msgstr "%H\\u2236%M"
|
||||
|
||||
#. Transators: Shown in calendar event list, if 12h format,
|
||||
#. Translators: Shown in calendar event list, if 12h format,
|
||||
#. \u2236 is a ratio character, similar to : and \u2009 is
|
||||
#. a thin space
|
||||
#: ../js/ui/calendar.js:77
|
||||
@@ -619,35 +620,35 @@ msgid "S"
|
||||
msgstr "S"
|
||||
|
||||
#. Translators: Text to show if there are no events
|
||||
#: ../js/ui/calendar.js:692
|
||||
#: ../js/ui/calendar.js:720
|
||||
msgid "Nothing Scheduled"
|
||||
msgstr "Nic nie zaplanowano"
|
||||
|
||||
#. Translators: Shown on calendar heading when selected day occurs on current year
|
||||
#: ../js/ui/calendar.js:708
|
||||
#: ../js/ui/calendar.js:736
|
||||
msgctxt "calendar heading"
|
||||
msgid "%A, %B %d"
|
||||
msgstr "%A, %e %B"
|
||||
|
||||
#. Translators: Shown on calendar heading when selected day occurs on different year
|
||||
#: ../js/ui/calendar.js:711
|
||||
#: ../js/ui/calendar.js:739
|
||||
msgctxt "calendar heading"
|
||||
msgid "%A, %B %d, %Y"
|
||||
msgstr "%A, %e %B %Y"
|
||||
|
||||
#: ../js/ui/calendar.js:721
|
||||
#: ../js/ui/calendar.js:749
|
||||
msgid "Today"
|
||||
msgstr "Dzisiaj"
|
||||
|
||||
#: ../js/ui/calendar.js:725
|
||||
#: ../js/ui/calendar.js:753
|
||||
msgid "Tomorrow"
|
||||
msgstr "Jutro"
|
||||
|
||||
#: ../js/ui/calendar.js:736
|
||||
#: ../js/ui/calendar.js:764
|
||||
msgid "This week"
|
||||
msgstr "Ten tydzień"
|
||||
|
||||
#: ../js/ui/calendar.js:744
|
||||
#: ../js/ui/calendar.js:772
|
||||
msgid "Next week"
|
||||
msgstr "Następny tydzień"
|
||||
|
||||
@@ -663,12 +664,12 @@ msgstr "Odłączono dysk zewnętrzny"
|
||||
msgid "Removable Devices"
|
||||
msgstr "Urządzenia wymienne"
|
||||
|
||||
#: ../js/ui/components/autorunManager.js:593
|
||||
#: ../js/ui/components/autorunManager.js:594
|
||||
#, c-format
|
||||
msgid "Open with %s"
|
||||
msgstr "Otwórz za pomocą %s"
|
||||
|
||||
#: ../js/ui/components/autorunManager.js:619
|
||||
#: ../js/ui/components/autorunManager.js:620
|
||||
msgid "Eject"
|
||||
msgstr "Wysuń"
|
||||
|
||||
@@ -811,39 +812,39 @@ msgid "Mute"
|
||||
msgstr "Wycisz"
|
||||
|
||||
#. Translators: this is the word "Yesterday" followed by a time string. i.e. "Yesterday, 14:30"
|
||||
#: ../js/ui/components/telepathyClient.js:938
|
||||
#: ../js/ui/components/telepathyClient.js:942
|
||||
#, no-c-format
|
||||
msgid "<b>Yesterday</b>, <b>%H:%M</b>"
|
||||
msgstr "<b>Wczoraj</b> o <b>%H:%M</b>"
|
||||
|
||||
#. Translators: this is the week day name followed by a time string. i.e. "Monday, 14:30
|
||||
#: ../js/ui/components/telepathyClient.js:944
|
||||
#: ../js/ui/components/telepathyClient.js:948
|
||||
#, no-c-format
|
||||
msgid "<b>%A</b>, <b>%H:%M</b>"
|
||||
msgstr "<b>%A</b> o <b>%H:%M</b>"
|
||||
|
||||
#. Translators: this is the month name and day number followed by a time string. i.e. "May 25, 14:30"
|
||||
#: ../js/ui/components/telepathyClient.js:949
|
||||
#: ../js/ui/components/telepathyClient.js:953
|
||||
#, no-c-format
|
||||
msgid "<b>%B</b> <b>%d</b>, <b>%H:%M</b>"
|
||||
msgstr "<b>%d</b> <b>%B</b>, <b>%H:%M</b>"
|
||||
|
||||
#. Translators: this is the month name, day number, year number followed by a time string. i.e. "May 25 2012, 14:30"
|
||||
#: ../js/ui/components/telepathyClient.js:953
|
||||
#: ../js/ui/components/telepathyClient.js:957
|
||||
#, no-c-format
|
||||
msgid "<b>%B</b> <b>%d</b> <b>%Y</b>, <b>%H:%M</b> "
|
||||
msgstr "<b>%d</b> <b>%B</b> <b>%Y</b>, <b>%H:%M</b> "
|
||||
|
||||
#. Translators: this is the other person changing their old IM name to their new
|
||||
#. IM name.
|
||||
#: ../js/ui/components/telepathyClient.js:981
|
||||
#: ../js/ui/components/telepathyClient.js:985
|
||||
#, c-format
|
||||
msgid "%s is now known as %s"
|
||||
msgstr "Użytkownik %s jest teraz znany jako %s"
|
||||
|
||||
#. translators: argument is a room name like
|
||||
#. * room@jabber.org for example.
|
||||
#: ../js/ui/components/telepathyClient.js:1084
|
||||
#: ../js/ui/components/telepathyClient.js:1088
|
||||
#, c-format
|
||||
msgid "Invitation to %s"
|
||||
msgstr "Zaproszenie do pokoju %s"
|
||||
@@ -851,38 +852,38 @@ msgstr "Zaproszenie do pokoju %s"
|
||||
#. translators: first argument is the name of a contact and the second
|
||||
#. * one the name of a room. "Alice is inviting you to join room@jabber.org
|
||||
#. * for example.
|
||||
#: ../js/ui/components/telepathyClient.js:1092
|
||||
#: ../js/ui/components/telepathyClient.js:1096
|
||||
#, c-format
|
||||
msgid "%s is inviting you to join %s"
|
||||
msgstr "Użytkownik %s zaprasza do dołączenia do pokoju %s"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1094
|
||||
#: ../js/ui/components/telepathyClient.js:1133
|
||||
#: ../js/ui/components/telepathyClient.js:1173
|
||||
#: ../js/ui/components/telepathyClient.js:1236
|
||||
#: ../js/ui/components/telepathyClient.js:1098
|
||||
#: ../js/ui/components/telepathyClient.js:1137
|
||||
#: ../js/ui/components/telepathyClient.js:1177
|
||||
#: ../js/ui/components/telepathyClient.js:1240
|
||||
msgid "Decline"
|
||||
msgstr "Odmów"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1095
|
||||
#: ../js/ui/components/telepathyClient.js:1174
|
||||
#: ../js/ui/components/telepathyClient.js:1237
|
||||
#: ../js/ui/components/telepathyClient.js:1099
|
||||
#: ../js/ui/components/telepathyClient.js:1178
|
||||
#: ../js/ui/components/telepathyClient.js:1241
|
||||
msgid "Accept"
|
||||
msgstr "Zaakceptuj"
|
||||
|
||||
#. translators: argument is a contact name like Alice for example.
|
||||
#: ../js/ui/components/telepathyClient.js:1125
|
||||
#: ../js/ui/components/telepathyClient.js:1129
|
||||
#, c-format
|
||||
msgid "Video call from %s"
|
||||
msgstr "Wideorozmowa z użytkownikiem %s"
|
||||
|
||||
#. translators: argument is a contact name like Alice for example.
|
||||
#: ../js/ui/components/telepathyClient.js:1128
|
||||
#: ../js/ui/components/telepathyClient.js:1132
|
||||
#, c-format
|
||||
msgid "Call from %s"
|
||||
msgstr "Rozmowa z użytkownikiem %s"
|
||||
|
||||
#. translators: this is a button label (verb), not a noun
|
||||
#: ../js/ui/components/telepathyClient.js:1135
|
||||
#: ../js/ui/components/telepathyClient.js:1139
|
||||
msgid "Answer"
|
||||
msgstr "Odbierz"
|
||||
|
||||
@@ -891,111 +892,111 @@ msgstr "Odbierz"
|
||||
#. * file name. The string will be something
|
||||
#. * like: "Alice is sending you test.ogg"
|
||||
#.
|
||||
#: ../js/ui/components/telepathyClient.js:1167
|
||||
#: ../js/ui/components/telepathyClient.js:1171
|
||||
#, c-format
|
||||
msgid "%s is sending you %s"
|
||||
msgstr "Użytkownik %s przysyła plik %s"
|
||||
|
||||
#. To translators: The parameter is the contact's alias
|
||||
#: ../js/ui/components/telepathyClient.js:1202
|
||||
#: ../js/ui/components/telepathyClient.js:1206
|
||||
#, c-format
|
||||
msgid "%s would like permission to see when you are online"
|
||||
msgstr "Użytkownik %s prosi o uprawnienie do wyświetlania stanu"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1294
|
||||
#: ../js/ui/components/telepathyClient.js:1298
|
||||
msgid "Network error"
|
||||
msgstr "Błąd sieci"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1296
|
||||
#: ../js/ui/components/telepathyClient.js:1300
|
||||
msgid "Authentication failed"
|
||||
msgstr "Uwierzytelnienie się nie powiodło"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1298
|
||||
#: ../js/ui/components/telepathyClient.js:1302
|
||||
msgid "Encryption error"
|
||||
msgstr "Błąd szyfrowania"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1300
|
||||
#: ../js/ui/components/telepathyClient.js:1304
|
||||
msgid "Certificate not provided"
|
||||
msgstr "Nie podano certyfikatu"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1302
|
||||
#: ../js/ui/components/telepathyClient.js:1306
|
||||
msgid "Certificate untrusted"
|
||||
msgstr "Certyfikat jest niezaufany"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1304
|
||||
#: ../js/ui/components/telepathyClient.js:1308
|
||||
msgid "Certificate expired"
|
||||
msgstr "Certyfikat wygasł"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1306
|
||||
#: ../js/ui/components/telepathyClient.js:1310
|
||||
msgid "Certificate not activated"
|
||||
msgstr "Certyfikat nie został aktywowany"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1308
|
||||
#: ../js/ui/components/telepathyClient.js:1312
|
||||
msgid "Certificate hostname mismatch"
|
||||
msgstr "Nazwa komputera certyfikatu się nie zgadza"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1310
|
||||
#: ../js/ui/components/telepathyClient.js:1314
|
||||
msgid "Certificate fingerprint mismatch"
|
||||
msgstr "Odcisk palca certyfikatu się nie zgadza"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1312
|
||||
#: ../js/ui/components/telepathyClient.js:1316
|
||||
msgid "Certificate self-signed"
|
||||
msgstr "Certyfikat został samodzielnie podpisany"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1314
|
||||
#: ../js/ui/components/telepathyClient.js:1318
|
||||
msgid "Status is set to offline"
|
||||
msgstr "Stan jest ustawiony na offline"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1316
|
||||
#: ../js/ui/components/telepathyClient.js:1320
|
||||
msgid "Encryption is not available"
|
||||
msgstr "Szyfrowanie jest niedostępne"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1318
|
||||
#: ../js/ui/components/telepathyClient.js:1322
|
||||
msgid "Certificate is invalid"
|
||||
msgstr "Certyfikat jest nieprawidłowy"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1320
|
||||
#: ../js/ui/components/telepathyClient.js:1324
|
||||
msgid "Connection has been refused"
|
||||
msgstr "Odrzucono połączenie"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1322
|
||||
#: ../js/ui/components/telepathyClient.js:1326
|
||||
msgid "Connection can't be established"
|
||||
msgstr "Nie można nawiązać połączenia"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1324
|
||||
#: ../js/ui/components/telepathyClient.js:1328
|
||||
msgid "Connection has been lost"
|
||||
msgstr "Utracono połączenie"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1326
|
||||
#: ../js/ui/components/telepathyClient.js:1330
|
||||
msgid "This account is already connected to the server"
|
||||
msgstr "To konto jest już połączone z serwerem"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1328
|
||||
#: ../js/ui/components/telepathyClient.js:1332
|
||||
msgid ""
|
||||
"Connection has been replaced by a new connection using the same resource"
|
||||
msgstr ""
|
||||
"Połączenie zostało zastąpione nowym z wykorzystaniem tego samego zasobu"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1330
|
||||
#: ../js/ui/components/telepathyClient.js:1334
|
||||
msgid "The account already exists on the server"
|
||||
msgstr "Konto już istnieje na serwerze"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1332
|
||||
#: ../js/ui/components/telepathyClient.js:1336
|
||||
msgid "Server is currently too busy to handle the connection"
|
||||
msgstr "Serwer jest obecnie zbyt zajęty, aby obsłużyć połączenie"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1334
|
||||
#: ../js/ui/components/telepathyClient.js:1338
|
||||
msgid "Certificate has been revoked"
|
||||
msgstr "Certyfikat został unieważniony"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1336
|
||||
#: ../js/ui/components/telepathyClient.js:1340
|
||||
msgid ""
|
||||
"Certificate uses an insecure cipher algorithm or is cryptographically weak"
|
||||
msgstr ""
|
||||
"Certyfikat używa niezabezpieczonego algorytmu szyfrowania lub jest "
|
||||
"kryptograficznie słaby"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1338
|
||||
#: ../js/ui/components/telepathyClient.js:1342
|
||||
msgid ""
|
||||
"The length of the server certificate, or the depth of the server certificate "
|
||||
"chain, exceed the limits imposed by the cryptography library"
|
||||
@@ -1003,26 +1004,26 @@ msgstr ""
|
||||
"Długość certyfikatu serwera lub głębokość jego łańcucha przekracza "
|
||||
"ograniczenia nałożone przez bibliotekę kryptograficzną"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1340
|
||||
#: ../js/ui/components/telepathyClient.js:1344
|
||||
msgid "Internal error"
|
||||
msgstr "Błąd wewnętrzny"
|
||||
|
||||
#. translators: argument is the account name, like
|
||||
#. * name@jabber.org for example.
|
||||
#: ../js/ui/components/telepathyClient.js:1350
|
||||
#: ../js/ui/components/telepathyClient.js:1354
|
||||
#, c-format
|
||||
msgid "Unable to connect to %s"
|
||||
msgstr "Nie można połączyć się z kontem %s"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1355
|
||||
#: ../js/ui/components/telepathyClient.js:1359
|
||||
msgid "View account"
|
||||
msgstr "Wyświetl konto"
|
||||
|
||||
#: ../js/ui/components/telepathyClient.js:1394
|
||||
#: ../js/ui/components/telepathyClient.js:1398
|
||||
msgid "Unknown reason"
|
||||
msgstr "Nieznana przyczyna"
|
||||
|
||||
#: ../js/ui/ctrlAltTab.js:29 ../js/ui/viewSelector.js:97
|
||||
#: ../js/ui/ctrlAltTab.js:29 ../js/ui/viewSelector.js:96
|
||||
msgid "Windows"
|
||||
msgstr "Okna"
|
||||
|
||||
@@ -1051,7 +1052,7 @@ msgstr "Ustawienia daty i czasu"
|
||||
#. Translators: This is the date format to use when the calendar popup is
|
||||
#. * shown - it is shown just below the time in the shell (e.g. "Tue 9:29 AM").
|
||||
#.
|
||||
#: ../js/ui/dateMenu.js:205
|
||||
#: ../js/ui/dateMenu.js:215
|
||||
msgid "%A %B %e, %Y"
|
||||
msgstr "%A, %e %B %Y"
|
||||
|
||||
@@ -1212,23 +1213,23 @@ msgstr "Wyświetl źródło"
|
||||
msgid "Web Page"
|
||||
msgstr "Strona WWW"
|
||||
|
||||
#: ../js/ui/messageTray.js:1177
|
||||
#: ../js/ui/messageTray.js:1182
|
||||
msgid "Open"
|
||||
msgstr "Otwórz"
|
||||
|
||||
#: ../js/ui/messageTray.js:1184
|
||||
#: ../js/ui/messageTray.js:1189
|
||||
msgid "Remove"
|
||||
msgstr "Usuń"
|
||||
|
||||
#: ../js/ui/messageTray.js:1496
|
||||
#: ../js/ui/messageTray.js:1501
|
||||
msgid "Clear Messages"
|
||||
msgstr "Wyczyść wiadomości"
|
||||
|
||||
#: ../js/ui/messageTray.js:1523
|
||||
#: ../js/ui/messageTray.js:1528
|
||||
msgid "Notification Settings"
|
||||
msgstr "Ustawienia powiadomień"
|
||||
|
||||
#: ../js/ui/messageTray.js:1702
|
||||
#: ../js/ui/messageTray.js:1709
|
||||
msgid "No Messages"
|
||||
msgstr "Brak wiadomości"
|
||||
|
||||
@@ -1236,7 +1237,7 @@ msgstr "Brak wiadomości"
|
||||
msgid "Message Tray"
|
||||
msgstr "Obszar powiadamiania"
|
||||
|
||||
#: ../js/ui/messageTray.js:2857
|
||||
#: ../js/ui/messageTray.js:2810
|
||||
msgid "System Information"
|
||||
msgstr "Informacje systemowe"
|
||||
|
||||
@@ -1245,11 +1246,19 @@ msgctxt "program"
|
||||
msgid "Unknown"
|
||||
msgstr "Nieznany"
|
||||
|
||||
#: ../js/ui/overview.js:81
|
||||
#: ../js/ui/overviewControls.js:463 ../js/ui/screenShield.js:149
|
||||
#, c-format
|
||||
msgid "%d new message"
|
||||
msgid_plural "%d new messages"
|
||||
msgstr[0] "%d nowa wiadomość"
|
||||
msgstr[1] "%d nowe wiadomości"
|
||||
msgstr[2] "%d nowych wiadomości"
|
||||
|
||||
#: ../js/ui/overview.js:84
|
||||
msgid "Undo"
|
||||
msgstr "Cofnij"
|
||||
|
||||
#: ../js/ui/overview.js:124
|
||||
#: ../js/ui/overview.js:129
|
||||
msgid "Overview"
|
||||
msgstr "Podgląd"
|
||||
|
||||
@@ -1257,21 +1266,21 @@ msgstr "Podgląd"
|
||||
#. in the search entry when no search is
|
||||
#. active; it should not exceed ~30
|
||||
#. characters.
|
||||
#: ../js/ui/overview.js:272
|
||||
#: ../js/ui/overview.js:271
|
||||
msgid "Type to search…"
|
||||
msgstr "Wyszukiwanie…"
|
||||
|
||||
#: ../js/ui/panel.js:613
|
||||
#: ../js/ui/panel.js:612
|
||||
msgid "Quit"
|
||||
msgstr "Zakończ"
|
||||
|
||||
#. Translators: If there is no suitable word for "Activities"
|
||||
#. in your language, you can use the word for "Overview".
|
||||
#: ../js/ui/panel.js:642
|
||||
#: ../js/ui/panel.js:636
|
||||
msgid "Activities"
|
||||
msgstr "Podgląd"
|
||||
|
||||
#: ../js/ui/panel.js:983
|
||||
#: ../js/ui/panel.js:933
|
||||
msgid "Top Bar"
|
||||
msgstr "Górny pasek"
|
||||
|
||||
@@ -1284,29 +1293,21 @@ msgstr "Górny pasek"
|
||||
msgid "toggle-switch-us"
|
||||
msgstr "toggle-switch-intl"
|
||||
|
||||
#: ../js/ui/runDialog.js:205
|
||||
#: ../js/ui/runDialog.js:73
|
||||
msgid "Enter a Command"
|
||||
msgstr "Proszę wprowadzić polecenie"
|
||||
|
||||
#: ../js/ui/runDialog.js:241
|
||||
#: ../js/ui/runDialog.js:109
|
||||
msgid "Close"
|
||||
msgstr "Zamknij"
|
||||
|
||||
#. Translators: This is a time format for a date in
|
||||
#. long format
|
||||
#: ../js/ui/screenShield.js:90
|
||||
#: ../js/ui/screenShield.js:86
|
||||
msgid "%A, %B %d"
|
||||
msgstr "%A, %e %B"
|
||||
|
||||
#: ../js/ui/screenShield.js:153
|
||||
#, c-format
|
||||
msgid "%d new message"
|
||||
msgid_plural "%d new messages"
|
||||
msgstr[0] "%d nowa wiadomość"
|
||||
msgstr[1] "%d nowe wiadomości"
|
||||
msgstr[2] "%d nowych wiadomości"
|
||||
|
||||
#: ../js/ui/screenShield.js:155
|
||||
#: ../js/ui/screenShield.js:151
|
||||
#, c-format
|
||||
msgid "%d new notification"
|
||||
msgid_plural "%d new notifications"
|
||||
@@ -1314,11 +1315,11 @@ msgstr[0] "%d nowe powiadomienie"
|
||||
msgstr[1] "%d nowe powiadomienia"
|
||||
msgstr[2] "%d nowych powiadomień"
|
||||
|
||||
#: ../js/ui/screenShield.js:442 ../js/ui/userMenu.js:805
|
||||
#: ../js/ui/screenShield.js:438 ../js/ui/userMenu.js:807
|
||||
msgid "Lock"
|
||||
msgstr "Zablokuj ekran"
|
||||
|
||||
#: ../js/ui/screenShield.js:638
|
||||
#: ../js/ui/screenShield.js:640
|
||||
msgid "GNOME needs to lock the screen"
|
||||
msgstr "Środowisko GNOME musi zablokować ekran"
|
||||
|
||||
@@ -1329,19 +1330,19 @@ msgstr "Środowisko GNOME musi zablokować ekran"
|
||||
#.
|
||||
#. XXX: another option is to kick the user into the gdm login
|
||||
#. screen, where we're not affected by grabs
|
||||
#: ../js/ui/screenShield.js:757 ../js/ui/screenShield.js:1168
|
||||
#: ../js/ui/screenShield.js:761 ../js/ui/screenShield.js:1197
|
||||
msgid "Unable to lock"
|
||||
msgstr "Nie można zablokować"
|
||||
|
||||
#: ../js/ui/screenShield.js:758 ../js/ui/screenShield.js:1169
|
||||
#: ../js/ui/screenShield.js:762 ../js/ui/screenShield.js:1198
|
||||
msgid "Lock was blocked by an application"
|
||||
msgstr "Blokowanie zostało zablokowane przez program"
|
||||
|
||||
#: ../js/ui/searchDisplay.js:431
|
||||
#: ../js/ui/searchDisplay.js:453
|
||||
msgid "Searching…"
|
||||
msgstr "Wyszukiwanie…"
|
||||
|
||||
#: ../js/ui/searchDisplay.js:475
|
||||
#: ../js/ui/searchDisplay.js:497
|
||||
msgid "No results."
|
||||
msgstr "Brak wyników."
|
||||
|
||||
@@ -1353,11 +1354,11 @@ msgstr "Skopiuj"
|
||||
msgid "Paste"
|
||||
msgstr "Wklej"
|
||||
|
||||
#: ../js/ui/shellEntry.js:105
|
||||
#: ../js/ui/shellEntry.js:106
|
||||
msgid "Show Text"
|
||||
msgstr "Wyświetl tekst"
|
||||
|
||||
#: ../js/ui/shellEntry.js:107
|
||||
#: ../js/ui/shellEntry.js:108
|
||||
msgid "Hide Text"
|
||||
msgstr "Ukryj tekst"
|
||||
|
||||
@@ -1369,7 +1370,7 @@ msgstr "Hasło"
|
||||
msgid "Remember Password"
|
||||
msgstr "Zapamiętanie hasła"
|
||||
|
||||
#: ../js/ui/shellMountOperation.js:403 ../js/ui/unlockDialog.js:140
|
||||
#: ../js/ui/shellMountOperation.js:403 ../js/ui/unlockDialog.js:113
|
||||
msgid "Unlock"
|
||||
msgstr "Odblokuj"
|
||||
|
||||
@@ -1778,59 +1779,59 @@ msgstr "Głośność"
|
||||
msgid "Microphone"
|
||||
msgstr "Mikrofon"
|
||||
|
||||
#: ../js/ui/unlockDialog.js:151
|
||||
#: ../js/ui/unlockDialog.js:124
|
||||
msgid "Log in as another user"
|
||||
msgstr "Zaloguj jako inny użytkownik"
|
||||
|
||||
#: ../js/ui/unlockDialog.js:177
|
||||
#: ../js/ui/unlockDialog.js:145
|
||||
msgid "Unlock Window"
|
||||
msgstr "Okno odblokowania"
|
||||
|
||||
#: ../js/ui/userMenu.js:192
|
||||
#: ../js/ui/userMenu.js:193
|
||||
msgid "Available"
|
||||
msgstr "Dostępny"
|
||||
|
||||
#: ../js/ui/userMenu.js:195
|
||||
#: ../js/ui/userMenu.js:196
|
||||
msgid "Busy"
|
||||
msgstr "Zajęty"
|
||||
|
||||
#: ../js/ui/userMenu.js:198
|
||||
#: ../js/ui/userMenu.js:199
|
||||
msgid "Invisible"
|
||||
msgstr "Niewidoczny"
|
||||
|
||||
#: ../js/ui/userMenu.js:201
|
||||
#: ../js/ui/userMenu.js:202
|
||||
msgid "Away"
|
||||
msgstr "Nieobecny"
|
||||
|
||||
#: ../js/ui/userMenu.js:204
|
||||
#: ../js/ui/userMenu.js:205
|
||||
msgid "Idle"
|
||||
msgstr "Bezczynny"
|
||||
|
||||
#: ../js/ui/userMenu.js:207
|
||||
#: ../js/ui/userMenu.js:208
|
||||
msgid "Offline"
|
||||
msgstr "Offline"
|
||||
|
||||
#: ../js/ui/userMenu.js:779
|
||||
#: ../js/ui/userMenu.js:781
|
||||
msgid "Notifications"
|
||||
msgstr "Powiadomienia"
|
||||
|
||||
#: ../js/ui/userMenu.js:795
|
||||
#: ../js/ui/userMenu.js:797
|
||||
msgid "Switch User"
|
||||
msgstr "Przełącz użytkownika"
|
||||
|
||||
#: ../js/ui/userMenu.js:800
|
||||
#: ../js/ui/userMenu.js:802
|
||||
msgid "Log Out"
|
||||
msgstr "Wyloguj się"
|
||||
|
||||
#: ../js/ui/userMenu.js:820
|
||||
#: ../js/ui/userMenu.js:822
|
||||
msgid "Install Updates & Restart"
|
||||
msgstr "Zaktualizuj i uruchom ponownie"
|
||||
|
||||
#: ../js/ui/userMenu.js:838
|
||||
#: ../js/ui/userMenu.js:840
|
||||
msgid "Your chat status will be set to busy"
|
||||
msgstr "Stan komunikatora zostanie ustawiony na \"zajęty\""
|
||||
|
||||
#: ../js/ui/userMenu.js:839
|
||||
#: ../js/ui/userMenu.js:841
|
||||
msgid ""
|
||||
"Notifications are now disabled, including chat messages. Your online status "
|
||||
"has been adjusted to let others know that you might not see their messages."
|
||||
@@ -1840,33 +1841,35 @@ msgstr ""
|
||||
"użytkownik tego komputera może nie zobaczyć przychodzących od nich "
|
||||
"wiadomości."
|
||||
|
||||
#: ../js/ui/userMenu.js:885
|
||||
#: ../js/ui/userMenu.js:888
|
||||
msgid "Other users are logged in."
|
||||
msgstr "Inni użytkownicy są zalogowani."
|
||||
|
||||
#: ../js/ui/userMenu.js:890
|
||||
#: ../js/ui/userMenu.js:893
|
||||
msgid "Shutting down might cause them to lose unsaved work."
|
||||
msgstr "Wyłączenie komputera może spowodować utratę danych."
|
||||
|
||||
#: ../js/ui/userMenu.js:916
|
||||
#. Translators: Remote here refers to a remote session, like a ssh login
|
||||
#: ../js/ui/userMenu.js:921
|
||||
#, c-format
|
||||
msgid "%s (remote)"
|
||||
msgstr "%s (zdalnie)"
|
||||
|
||||
#: ../js/ui/userMenu.js:918
|
||||
#. Translators: Console here refers to a tty like a VT console
|
||||
#: ../js/ui/userMenu.js:924
|
||||
#, c-format
|
||||
msgid "%s (console)"
|
||||
msgstr "%s (konsola)"
|
||||
|
||||
#: ../js/ui/viewSelector.js:101
|
||||
#: ../js/ui/viewSelector.js:100
|
||||
msgid "Applications"
|
||||
msgstr "Programy"
|
||||
|
||||
#: ../js/ui/viewSelector.js:105
|
||||
#: ../js/ui/viewSelector.js:104
|
||||
msgid "Search"
|
||||
msgstr "Wyszukiwanie"
|
||||
|
||||
#: ../js/ui/wanda.js:92
|
||||
#: ../js/ui/wanda.js:77
|
||||
#, c-format
|
||||
msgid ""
|
||||
"Sorry, no wisdom for you today:\n"
|
||||
@@ -1875,7 +1878,7 @@ msgstr ""
|
||||
"Nic mądrego na dzisiaj:\n"
|
||||
"%s"
|
||||
|
||||
#: ../js/ui/wanda.js:96
|
||||
#: ../js/ui/wanda.js:81
|
||||
#, c-format
|
||||
msgid "%s the Oracle says"
|
||||
msgstr "Wyrocznia %s przemawia"
|
||||
|
||||
193
po/ru.po
193
po/ru.po
@@ -15,8 +15,8 @@ msgstr ""
|
||||
"Project-Id-Version: gnome-shell\n"
|
||||
"Report-Msgid-Bugs-To: http://bugzilla.gnome.org/enter_bug.cgi?product=gnome-"
|
||||
"shell&keywords=I18N+L10N&component=general\n"
|
||||
"POT-Creation-Date: 2013-03-03 12:52+0000\n"
|
||||
"PO-Revision-Date: 2013-03-03 23:21+0400\n"
|
||||
"POT-Creation-Date: 2013-03-14 18:11+0000\n"
|
||||
"PO-Revision-Date: 2013-03-22 21:02+0400\n"
|
||||
"Last-Translator: Yuri Myasoedov <omerta13@yandex.ru>\n"
|
||||
"Language-Team: русский <gnome-cyr@gnome.org>\n"
|
||||
"Language: ru\n"
|
||||
@@ -142,11 +142,11 @@ msgstr ""
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:11
|
||||
msgid "History for command (Alt-F2) dialog"
|
||||
msgstr "История команд диалога (Alt-F2)"
|
||||
msgstr "История команд диалогового окна (Alt-F2)"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:12
|
||||
msgid "History for the looking glass dialog"
|
||||
msgstr "История просмотра прозрачного диалога"
|
||||
msgstr "История просмотра прозрачного диалогового окна"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:13
|
||||
msgid ""
|
||||
@@ -223,11 +223,11 @@ msgstr "Комбинация клавиш для перехода в режим
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:25
|
||||
msgid "Keybinding to toggle the visibility of the message tray"
|
||||
msgstr "Комбинация клавиш для показа и скрытия панели сообщений"
|
||||
msgstr "Комбинация клавиш для отображения или скрытия панели сообщений"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:26
|
||||
msgid "Keybinding to toggle the visibility of the message tray."
|
||||
msgstr "Комбинация клавиш для показа и скрытия панели сообщений."
|
||||
msgstr "Комбинация клавиш для отображения или скрытия панели сообщений."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:27
|
||||
msgid "Keybinding to focus the active notification"
|
||||
@@ -239,12 +239,13 @@ msgstr "Комбинация клавиш для перевода фокуса
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:29
|
||||
msgid "Keybinding to toggle the screen recorder"
|
||||
msgstr "Комбинация клавиш для включения и выключения средства записи экрана"
|
||||
msgstr "Комбинация клавиш для включения или выключения средства записи экрана"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:30
|
||||
msgid "Keybinding to start/stop the builtin screen recorder."
|
||||
msgstr ""
|
||||
"Комбинация клавиш для запуска и останова встроенного средства записи экрана."
|
||||
"Комбинация клавиш для запуска или остановки встроенного средства записи "
|
||||
"экрана."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:31
|
||||
msgid "Which keyboard to use"
|
||||
@@ -263,8 +264,8 @@ msgid ""
|
||||
"The framerate of the resulting screencast recordered by GNOME Shell's "
|
||||
"screencast recorder in frames-per-second."
|
||||
msgstr ""
|
||||
"Частота смены кадров в скринкасте, записанном с помощью GNOME Shell (кадров/"
|
||||
"сек)."
|
||||
"Частота смены кадров (кадров/сек) скринкаста, записанного с помощью GNOME "
|
||||
"Shell."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:35
|
||||
msgid "The gstreamer pipeline used to encode the screencast"
|
||||
@@ -299,7 +300,7 @@ msgstr ""
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:38
|
||||
msgid "File extension used for storing the screencast"
|
||||
msgstr "Расширение файла, использующееся для хранения скринкастов"
|
||||
msgstr "Расширение файла, используемое при сохранении скринкастов"
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:39
|
||||
msgid ""
|
||||
@@ -307,9 +308,9 @@ msgid ""
|
||||
"current date, and use this extension. It should be changed when recording to "
|
||||
"a different container format."
|
||||
msgstr ""
|
||||
"Имя файла записанного скринкаста будет уникальным именем, основанным на "
|
||||
"текущей дате, и использует это расширение. Оно должно быть изменено, если "
|
||||
"запись выполняется в другой контейнерный формат."
|
||||
"Имя файла записанного скринкаста будет уникальным, основанным на текущей "
|
||||
"дате и используемом расширении. Оно должно быть изменено, если запись "
|
||||
"выполняется в другой формат контейнера."
|
||||
|
||||
#: ../data/org.gnome.shell.gschema.xml.in.in.h:40
|
||||
msgid "The application icon mode."
|
||||
@@ -364,7 +365,7 @@ msgstr "Рабочие места только на основном монит
|
||||
#: ../js/extensionPrefs/main.js:125
|
||||
#, c-format
|
||||
msgid "There was an error loading the preferences dialog for %s:"
|
||||
msgstr "При загрузке диалога параметров для %s произошла ошибка:"
|
||||
msgstr "При загрузке диалогового окна параметров для %s произошла ошибка:"
|
||||
|
||||
#: ../js/extensionPrefs/main.js:165
|
||||
msgid "Extension"
|
||||
@@ -381,46 +382,46 @@ msgstr "Сеанс…"
|
||||
#. translators: this message is shown below the user list on the
|
||||
#. login screen. It can be activated to reveal an entry for
|
||||
#. manually entering the username.
|
||||
#: ../js/gdm/loginDialog.js:629
|
||||
#: ../js/gdm/loginDialog.js:630
|
||||
msgid "Not listed?"
|
||||
msgstr "Нет в списке?"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:783 ../js/ui/components/networkAgent.js:137
|
||||
#: ../js/gdm/loginDialog.js:784 ../js/ui/components/networkAgent.js:137
|
||||
#: ../js/ui/components/polkitAgent.js:162 ../js/ui/endSessionDialog.js:375
|
||||
#: ../js/ui/extensionDownloader.js:195 ../js/ui/shellMountOperation.js:399
|
||||
#: ../js/ui/status/bluetooth.js:415 ../js/ui/unlockDialog.js:126
|
||||
#: ../js/ui/userMenu.js:934
|
||||
#: ../js/ui/status/bluetooth.js:415 ../js/ui/unlockDialog.js:98
|
||||
#: ../js/ui/userMenu.js:938
|
||||
msgid "Cancel"
|
||||
msgstr "Отмена"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:799
|
||||
#: ../js/gdm/loginDialog.js:800
|
||||
msgctxt "button"
|
||||
msgid "Sign In"
|
||||
msgstr "Войти"
|
||||
|
||||
#: ../js/gdm/loginDialog.js:799
|
||||
#: ../js/gdm/loginDialog.js:800
|
||||
msgid "Next"
|
||||
msgstr "Следующий"
|
||||
msgstr "Далее"
|
||||
|
||||
#. TTLS and PEAP are actually much more complicated, but this complication
|
||||
#. is not visible here since we only care about phase2 authentication
|
||||
#. (and don't even care of which one)
|
||||
#: ../js/gdm/loginDialog.js:904 ../js/ui/components/networkAgent.js:260
|
||||
#: ../js/gdm/loginDialog.js:915 ../js/ui/components/networkAgent.js:260
|
||||
#: ../js/ui/components/networkAgent.js:278
|
||||
msgid "Username: "
|
||||
msgstr "Имя пользователя: "
|
||||
|
||||
#: ../js/gdm/loginDialog.js:1157
|
||||
#: ../js/gdm/loginDialog.js:1159
|
||||
msgid "Login Window"
|
||||
msgstr "Окно входа в систему"
|
||||
|
||||
#. Translators: accessible name of the power menu in the login screen
|
||||
#: ../js/gdm/powerMenu.js:36
|
||||
msgid "Power"
|
||||
msgstr "Питание"
|
||||
msgstr "Электропитание"
|
||||
|
||||
#: ../js/gdm/powerMenu.js:93 ../js/ui/userMenu.js:695 ../js/ui/userMenu.js:699
|
||||
#: ../js/ui/userMenu.js:815
|
||||
#: ../js/gdm/powerMenu.js:93 ../js/ui/userMenu.js:696 ../js/ui/userMenu.js:700
|
||||
#: ../js/ui/userMenu.js:816
|
||||
msgid "Suspend"
|
||||
msgstr "Ждущий режим"
|
||||
|
||||
@@ -428,14 +429,14 @@ msgstr "Ждущий режим"
|
||||
msgid "Restart"
|
||||
msgstr "Перезапустить"
|
||||
|
||||
#: ../js/gdm/powerMenu.js:103 ../js/ui/userMenu.js:697
|
||||
#: ../js/ui/userMenu.js:699 ../js/ui/userMenu.js:814 ../js/ui/userMenu.js:938
|
||||
#: ../js/gdm/powerMenu.js:103 ../js/ui/userMenu.js:698
|
||||
#: ../js/ui/userMenu.js:700 ../js/ui/userMenu.js:815 ../js/ui/userMenu.js:942
|
||||
msgid "Power Off"
|
||||
msgstr "Выключить"
|
||||
|
||||
#: ../js/gdm/util.js:182
|
||||
msgid "Authentication error"
|
||||
msgstr "Ошибка подтверждения подлинности"
|
||||
msgstr "Ошибка проверки подлинности"
|
||||
|
||||
#. Translators: this message is shown below the password entry field
|
||||
#. to indicate the user can swipe their finger instead
|
||||
@@ -448,38 +449,38 @@ msgstr "(или проведите пальцем по считывающему
|
||||
msgid "(e.g., user or %s)"
|
||||
msgstr "(например, пользователь или %s)"
|
||||
|
||||
#: ../js/misc/util.js:94
|
||||
#: ../js/misc/util.js:97
|
||||
msgid "Command not found"
|
||||
msgstr "Команда не найдена"
|
||||
|
||||
#. Replace "Error invoking GLib.shell_parse_argv: " with
|
||||
#. something nicer
|
||||
#: ../js/misc/util.js:127
|
||||
#: ../js/misc/util.js:130
|
||||
msgid "Could not parse command:"
|
||||
msgstr "Не удалось разобрать команду:"
|
||||
|
||||
#: ../js/misc/util.js:135
|
||||
#: ../js/misc/util.js:138
|
||||
#, c-format
|
||||
msgid "Execution of '%s' failed:"
|
||||
msgstr "Не удалось выполнить «%s»:"
|
||||
|
||||
#: ../js/ui/appDisplay.js:348
|
||||
#: ../js/ui/appDisplay.js:325
|
||||
msgid "Frequent"
|
||||
msgstr "Часто используемые"
|
||||
msgstr "Популярные"
|
||||
|
||||
#: ../js/ui/appDisplay.js:355
|
||||
#: ../js/ui/appDisplay.js:332
|
||||
msgid "All"
|
||||
msgstr "Все"
|
||||
|
||||
#: ../js/ui/appDisplay.js:913
|
||||
#: ../js/ui/appDisplay.js:890
|
||||
msgid "New Window"
|
||||
msgstr "Новое окно"
|
||||
|
||||
#: ../js/ui/appDisplay.js:916 ../js/ui/dash.js:284
|
||||
#: ../js/ui/appDisplay.js:893 ../js/ui/dash.js:284
|
||||
msgid "Remove from Favorites"
|
||||
msgstr "Удалить из избранного"
|
||||
|
||||
#: ../js/ui/appDisplay.js:917
|
||||
#: ../js/ui/appDisplay.js:894
|
||||
msgid "Add to Favorites"
|
||||
msgstr "Добавить в избранное"
|
||||
|
||||
@@ -493,7 +494,7 @@ msgstr "Приложение %s добавлено в избранное."
|
||||
msgid "%s has been removed from your favorites."
|
||||
msgstr "Приложение %s удалено из избранного."
|
||||
|
||||
#: ../js/ui/backgroundMenu.js:19 ../js/ui/userMenu.js:788
|
||||
#: ../js/ui/backgroundMenu.js:19 ../js/ui/userMenu.js:789
|
||||
msgid "Settings"
|
||||
msgstr "Параметры"
|
||||
|
||||
@@ -618,35 +619,35 @@ msgid "S"
|
||||
msgstr "Сб"
|
||||
|
||||
#. Translators: Text to show if there are no events
|
||||
#: ../js/ui/calendar.js:692
|
||||
#: ../js/ui/calendar.js:720
|
||||
msgid "Nothing Scheduled"
|
||||
msgstr "Нет событий"
|
||||
|
||||
#. Translators: Shown on calendar heading when selected day occurs on current year
|
||||
#: ../js/ui/calendar.js:708
|
||||
#: ../js/ui/calendar.js:736
|
||||
msgctxt "calendar heading"
|
||||
msgid "%A, %B %d"
|
||||
msgstr "%A, %B %d"
|
||||
|
||||
#. Translators: Shown on calendar heading when selected day occurs on different year
|
||||
#: ../js/ui/calendar.js:711
|
||||
#: ../js/ui/calendar.js:739
|
||||
msgctxt "calendar heading"
|
||||
msgid "%A, %B %d, %Y"
|
||||
msgstr "%A, %B %d, %Y"
|
||||
|
||||
#: ../js/ui/calendar.js:721
|
||||
#: ../js/ui/calendar.js:749
|
||||
msgid "Today"
|
||||
msgstr "Сегодня"
|
||||
|
||||
#: ../js/ui/calendar.js:725
|
||||
#: ../js/ui/calendar.js:753
|
||||
msgid "Tomorrow"
|
||||
msgstr "Завтра"
|
||||
|
||||
#: ../js/ui/calendar.js:736
|
||||
#: ../js/ui/calendar.js:764
|
||||
msgid "This week"
|
||||
msgstr "Эта неделя"
|
||||
|
||||
#: ../js/ui/calendar.js:744
|
||||
#: ../js/ui/calendar.js:772
|
||||
msgid "Next week"
|
||||
msgstr "Следующая неделя"
|
||||
|
||||
@@ -743,7 +744,7 @@ msgstr "Для широкополосного мобильного устрой
|
||||
|
||||
#: ../js/ui/components/networkAgent.js:330
|
||||
msgid "PIN: "
|
||||
msgstr "PIN: "
|
||||
msgstr "PIN-код: "
|
||||
|
||||
#: ../js/ui/components/networkAgent.js:336
|
||||
msgid "Mobile broadband network password"
|
||||
@@ -772,7 +773,7 @@ msgstr "Подтвердить"
|
||||
#. * for instance.
|
||||
#: ../js/ui/components/polkitAgent.js:256 ../js/ui/shellMountOperation.js:383
|
||||
msgid "Sorry, that didn't work. Please try again."
|
||||
msgstr "Извините, это не сработало. Попробуйте снова."
|
||||
msgstr "Не удалось подтвердить подлинность. Попробуйте снова."
|
||||
|
||||
#. Translators: this is a filename used for screencast recording
|
||||
#: ../js/ui/components/recorder.js:48
|
||||
@@ -1020,7 +1021,7 @@ msgstr "Показать учётную запись"
|
||||
msgid "Unknown reason"
|
||||
msgstr "Неизвестная причина"
|
||||
|
||||
#: ../js/ui/ctrlAltTab.js:29 ../js/ui/viewSelector.js:97
|
||||
#: ../js/ui/ctrlAltTab.js:29 ../js/ui/viewSelector.js:96
|
||||
msgid "Windows"
|
||||
msgstr "Окна"
|
||||
|
||||
@@ -1049,7 +1050,7 @@ msgstr "Настроить дату и время"
|
||||
#. Translators: This is the date format to use when the calendar popup is
|
||||
#. * shown - it is shown just below the time in the shell (e.g. "Tue 9:29 AM").
|
||||
#.
|
||||
#: ../js/ui/dateMenu.js:205
|
||||
#: ../js/ui/dateMenu.js:215
|
||||
msgid "%A %B %e, %Y"
|
||||
msgstr "%A, %e %B, %Y"
|
||||
|
||||
@@ -1057,7 +1058,7 @@ msgstr "%A, %e %B, %Y"
|
||||
#, c-format
|
||||
msgctxt "title"
|
||||
msgid "Log Out %s"
|
||||
msgstr "Завершить сеанс пользователя %s"
|
||||
msgstr "Завершение сеанса пользователя %s"
|
||||
|
||||
#: ../js/ui/endSessionDialog.js:64
|
||||
msgctxt "title"
|
||||
@@ -1228,15 +1229,15 @@ msgstr "Очистить список сообщений"
|
||||
msgid "Notification Settings"
|
||||
msgstr "Параметры уведомлений"
|
||||
|
||||
#: ../js/ui/messageTray.js:1707
|
||||
#: ../js/ui/messageTray.js:1711
|
||||
msgid "No Messages"
|
||||
msgstr "Нет сообщений"
|
||||
|
||||
#: ../js/ui/messageTray.js:1787
|
||||
#: ../js/ui/messageTray.js:1784
|
||||
msgid "Message Tray"
|
||||
msgstr "Панель сообщений"
|
||||
|
||||
#: ../js/ui/messageTray.js:2864
|
||||
#: ../js/ui/messageTray.js:2816
|
||||
msgid "System Information"
|
||||
msgstr "Системная информация"
|
||||
|
||||
@@ -1245,7 +1246,7 @@ msgctxt "program"
|
||||
msgid "Unknown"
|
||||
msgstr "Неизвестно"
|
||||
|
||||
#: ../js/ui/overviewControls.js:460 ../js/ui/screenShield.js:153
|
||||
#: ../js/ui/overviewControls.js:463 ../js/ui/screenShield.js:148
|
||||
#, c-format
|
||||
msgid "%d new message"
|
||||
msgid_plural "%d new messages"
|
||||
@@ -1253,7 +1254,7 @@ msgstr[0] "%d новое сообщение"
|
||||
msgstr[1] "%d новых сообщения"
|
||||
msgstr[2] "%d новых сообщений"
|
||||
|
||||
#: ../js/ui/overview.js:82
|
||||
#: ../js/ui/overview.js:84
|
||||
msgid "Undo"
|
||||
msgstr "Отменить"
|
||||
|
||||
@@ -1265,21 +1266,21 @@ msgstr "Обзор"
|
||||
#. in the search entry when no search is
|
||||
#. active; it should not exceed ~30
|
||||
#. characters.
|
||||
#: ../js/ui/overview.js:284
|
||||
#: ../js/ui/overview.js:271
|
||||
msgid "Type to search…"
|
||||
msgstr "Найти…"
|
||||
|
||||
#: ../js/ui/panel.js:613
|
||||
#: ../js/ui/panel.js:612
|
||||
msgid "Quit"
|
||||
msgstr "Закрыть"
|
||||
|
||||
#. Translators: If there is no suitable word for "Activities"
|
||||
#. in your language, you can use the word for "Overview".
|
||||
#: ../js/ui/panel.js:642
|
||||
#: ../js/ui/panel.js:636
|
||||
msgid "Activities"
|
||||
msgstr "Обзор"
|
||||
|
||||
#: ../js/ui/panel.js:983
|
||||
#: ../js/ui/panel.js:933
|
||||
msgid "Top Bar"
|
||||
msgstr "Верхняя панель"
|
||||
|
||||
@@ -1292,33 +1293,33 @@ msgstr "Верхняя панель"
|
||||
msgid "toggle-switch-us"
|
||||
msgstr "toggle-switch-intl"
|
||||
|
||||
#: ../js/ui/runDialog.js:205
|
||||
#: ../js/ui/runDialog.js:73
|
||||
msgid "Enter a Command"
|
||||
msgstr "Введите команду"
|
||||
|
||||
#: ../js/ui/runDialog.js:241
|
||||
#: ../js/ui/runDialog.js:109
|
||||
msgid "Close"
|
||||
msgstr "Закрыть"
|
||||
|
||||
#. Translators: This is a time format for a date in
|
||||
#. long format
|
||||
#: ../js/ui/screenShield.js:90
|
||||
#: ../js/ui/screenShield.js:85
|
||||
msgid "%A, %B %d"
|
||||
msgstr "%d %B, %A"
|
||||
|
||||
#: ../js/ui/screenShield.js:155
|
||||
#: ../js/ui/screenShield.js:150
|
||||
#, c-format
|
||||
msgid "%d new notification"
|
||||
msgid_plural "%d new notifications"
|
||||
msgstr[0] "%d новые уведомление"
|
||||
msgstr[1] "%d новых уведомленя"
|
||||
msgstr[0] "%d новое уведомление"
|
||||
msgstr[1] "%d новых уведомления"
|
||||
msgstr[2] "%d новых уведомлений"
|
||||
|
||||
#: ../js/ui/screenShield.js:442 ../js/ui/userMenu.js:806
|
||||
#: ../js/ui/screenShield.js:437 ../js/ui/userMenu.js:807
|
||||
msgid "Lock"
|
||||
msgstr "Заблокировать"
|
||||
|
||||
#: ../js/ui/screenShield.js:639
|
||||
#: ../js/ui/screenShield.js:635
|
||||
msgid "GNOME needs to lock the screen"
|
||||
msgstr "GNOME необходимо заблокировать экран"
|
||||
|
||||
@@ -1329,19 +1330,19 @@ msgstr "GNOME необходимо заблокировать экран"
|
||||
#.
|
||||
#. XXX: another option is to kick the user into the gdm login
|
||||
#. screen, where we're not affected by grabs
|
||||
#: ../js/ui/screenShield.js:758 ../js/ui/screenShield.js:1169
|
||||
#: ../js/ui/screenShield.js:756 ../js/ui/screenShield.js:1151
|
||||
msgid "Unable to lock"
|
||||
msgstr "Не удалось заблокировать"
|
||||
|
||||
#: ../js/ui/screenShield.js:759 ../js/ui/screenShield.js:1170
|
||||
#: ../js/ui/screenShield.js:757 ../js/ui/screenShield.js:1152
|
||||
msgid "Lock was blocked by an application"
|
||||
msgstr "Блокировано помешало приложение"
|
||||
msgstr "Блокировке помешало приложение"
|
||||
|
||||
#: ../js/ui/searchDisplay.js:431
|
||||
#: ../js/ui/searchDisplay.js:451
|
||||
msgid "Searching…"
|
||||
msgstr "Поиск…"
|
||||
|
||||
#: ../js/ui/searchDisplay.js:475
|
||||
#: ../js/ui/searchDisplay.js:495
|
||||
msgid "No results."
|
||||
msgstr "Нет результатов."
|
||||
|
||||
@@ -1353,11 +1354,11 @@ msgstr "Копировать"
|
||||
msgid "Paste"
|
||||
msgstr "Вставить"
|
||||
|
||||
#: ../js/ui/shellEntry.js:105
|
||||
#: ../js/ui/shellEntry.js:106
|
||||
msgid "Show Text"
|
||||
msgstr "Показать текст"
|
||||
|
||||
#: ../js/ui/shellEntry.js:107
|
||||
#: ../js/ui/shellEntry.js:108
|
||||
msgid "Hide Text"
|
||||
msgstr "Скрыть текст"
|
||||
|
||||
@@ -1369,7 +1370,7 @@ msgstr "Пароль"
|
||||
msgid "Remember Password"
|
||||
msgstr "Запомнить пароль"
|
||||
|
||||
#: ../js/ui/shellMountOperation.js:403 ../js/ui/unlockDialog.js:140
|
||||
#: ../js/ui/shellMountOperation.js:403 ../js/ui/unlockDialog.js:112
|
||||
msgid "Unlock"
|
||||
msgstr "Разблокировать"
|
||||
|
||||
@@ -1670,7 +1671,7 @@ msgstr "Батарея"
|
||||
|
||||
#: ../js/ui/status/power.js:81
|
||||
msgid "Power Settings"
|
||||
msgstr "Параметры питания"
|
||||
msgstr "Параметры электропитания"
|
||||
|
||||
#. 0 is reported when UPower does not have enough data
|
||||
#. to estimate battery life
|
||||
@@ -1778,11 +1779,11 @@ msgstr "Громкость"
|
||||
msgid "Microphone"
|
||||
msgstr "Микрофон"
|
||||
|
||||
#: ../js/ui/unlockDialog.js:151
|
||||
#: ../js/ui/unlockDialog.js:123
|
||||
msgid "Log in as another user"
|
||||
msgstr "Войти от имени другого пользователя"
|
||||
|
||||
#: ../js/ui/unlockDialog.js:177
|
||||
#: ../js/ui/unlockDialog.js:144
|
||||
msgid "Unlock Window"
|
||||
msgstr "Разблокировать окно"
|
||||
|
||||
@@ -1810,27 +1811,27 @@ msgstr "Бездействует"
|
||||
msgid "Offline"
|
||||
msgstr "Не в сети"
|
||||
|
||||
#: ../js/ui/userMenu.js:780
|
||||
#: ../js/ui/userMenu.js:781
|
||||
msgid "Notifications"
|
||||
msgstr "Уведомления"
|
||||
|
||||
#: ../js/ui/userMenu.js:796
|
||||
#: ../js/ui/userMenu.js:797
|
||||
msgid "Switch User"
|
||||
msgstr "Сменить пользователя"
|
||||
|
||||
#: ../js/ui/userMenu.js:801
|
||||
#: ../js/ui/userMenu.js:802
|
||||
msgid "Log Out"
|
||||
msgstr "Выйти из системы"
|
||||
|
||||
#: ../js/ui/userMenu.js:821
|
||||
#: ../js/ui/userMenu.js:822
|
||||
msgid "Install Updates & Restart"
|
||||
msgstr "Установить обновления и выполнить перезагрузку"
|
||||
|
||||
#: ../js/ui/userMenu.js:839
|
||||
#: ../js/ui/userMenu.js:840
|
||||
msgid "Your chat status will be set to busy"
|
||||
msgstr "Будет установлен статус «не беспокоить»"
|
||||
|
||||
#: ../js/ui/userMenu.js:840
|
||||
#: ../js/ui/userMenu.js:841
|
||||
msgid ""
|
||||
"Notifications are now disabled, including chat messages. Your online status "
|
||||
"has been adjusted to let others know that you might not see their messages."
|
||||
@@ -1838,33 +1839,35 @@ msgstr ""
|
||||
"Уведомления отключены, включая сообщения в чате. Ваш статус доступности "
|
||||
"изменён, чтобы другие знали, что вы возможно не видите их сообщения."
|
||||
|
||||
#: ../js/ui/userMenu.js:886
|
||||
#: ../js/ui/userMenu.js:888
|
||||
msgid "Other users are logged in."
|
||||
msgstr "В системе имеются сеансы других пользователей."
|
||||
msgstr "В системе имеются открытые сеансы других пользователей."
|
||||
|
||||
#: ../js/ui/userMenu.js:891
|
||||
#: ../js/ui/userMenu.js:893
|
||||
msgid "Shutting down might cause them to lose unsaved work."
|
||||
msgstr "Завершение работы может привести к потере несохранённых изменений."
|
||||
|
||||
#: ../js/ui/userMenu.js:918
|
||||
#. Translators: Remote here refers to a remote session, like a ssh login
|
||||
#: ../js/ui/userMenu.js:921
|
||||
#, c-format
|
||||
msgid "%s (remote)"
|
||||
msgstr "%s (удалённый)"
|
||||
|
||||
#: ../js/ui/userMenu.js:920
|
||||
#. Translators: Console here refers to a tty like a VT console
|
||||
#: ../js/ui/userMenu.js:924
|
||||
#, c-format
|
||||
msgid "%s (console)"
|
||||
msgstr "%s (консоль)"
|
||||
|
||||
#: ../js/ui/viewSelector.js:101
|
||||
#: ../js/ui/viewSelector.js:100
|
||||
msgid "Applications"
|
||||
msgstr "Приложения"
|
||||
|
||||
#: ../js/ui/viewSelector.js:105
|
||||
#: ../js/ui/viewSelector.js:104
|
||||
msgid "Search"
|
||||
msgstr "Поиск"
|
||||
|
||||
#: ../js/ui/wanda.js:92
|
||||
#: ../js/ui/wanda.js:77
|
||||
#, c-format
|
||||
msgid ""
|
||||
"Sorry, no wisdom for you today:\n"
|
||||
@@ -1873,7 +1876,7 @@ msgstr ""
|
||||
"Извините, на сегодня нет никаких советов:\n"
|
||||
"%s"
|
||||
|
||||
#: ../js/ui/wanda.js:96
|
||||
#: ../js/ui/wanda.js:81
|
||||
#, c-format
|
||||
msgid "%s the Oracle says"
|
||||
msgstr "Оракул говорит: «%s»"
|
||||
|
||||
615
po/sr@latin.po
615
po/sr@latin.po
File diff suppressed because it is too large
Load Diff
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user