Merge lp:~docky-core/plank/keybindings into lp:plank

Proposed by Rico Tzschichholz
Status: Work in progress
Proposed branch: lp:~docky-core/plank/keybindings
Merge into: lp:plank
Diff against target: 874 lines (+637/-1)
9 files modified
data/net.launchpad.plank.gschema.xml.in.in (+16/-0)
lib/DockController.vala (+18/-0)
lib/DockPreferences.vala (+9/-0)
lib/DockRenderer.vala (+74/-0)
lib/Drawing/DockTheme.vala (+86/-0)
lib/HideManager.vala (+5/-1)
lib/KeybindingManager.vala (+405/-0)
lib/Makefile.am (+1/-0)
lib/libplank.symbols (+23/-0)
To merge this branch: bzr merge lp:~docky-core/plank/keybindings
Reviewer Review Type Date Requested Status
Sergey "Shnatsel" Davidoff Pending
Danielle Foré Pending
Review via email: mp+261315@code.launchpad.net

Description of the change

Add keybindings support

Still considered work-in-progress!
* It is probably better to disable this feature by default.
* Add settings UI changes
* Support bindings for more than 10 items
* Don't stop events with "modifiers" only

To post a comment you must log in.
lp:~docky-core/plank/keybindings updated
1310. By Rico Tzschichholz

drawing: Use Gtk.IconTheme in a thread-safe way

1311. By Rico Tzschichholz

lib: Avoid some superfluous string-copying

1312. By Rico Tzschichholz

dockitem: Add the "surface == null" surface-status

1313. By Rico Tzschichholz

logger: Partial rewrite, with strip down to the "nearly" bare minimum

1314. By Rico Tzschichholz

worker: Make ThreadPool non-exclusive and use GLib.get_num_processors()

1315. By Rico Tzschichholz

filedockitem: Drop unused code

1316. By Rico Tzschichholz

build: Fix make distcheck

1317. By Rico Tzschichholz

drawingservice: Use string-array directly and don't copy to Gee.ArrayList

1318. By Rico Tzschichholz

po: Update translations

1319. By Rico Tzschichholz

src: Use more reasonable class-name and namespace-structure

1320. By Rico Tzschichholz

renderer: Schedule unhide-on-start callback "as late as possible"

1321. By Rico Tzschichholz

dockitem: Schedule icon-theme-changed callback "as late as possible"

1322. By Rico Tzschichholz

drawingservice: Make icon_theme creation thread-safe

1323. By Rico Tzschichholz

renderer: Move frame-time handling into AnimatedRenderer

Make AnimatedRenderer-class responsible to perform and schedule redraws.

1324. By Rico Tzschichholz

animatedrenderer: Use Gdk.FrameClock to determine frame-time

Conditionally use Gdk.FrameClock if Gtk+ >= 3.8 is available

1325. By Rico Tzschichholz

Revert "items: Use threaded icon-drawing for all items"

Too unstable for being usable!

1326. By Rico Tzschichholz

Add RTL support and enable it depending on the locale setting

Reverse items placement.
Mirror position for vertical docks.
Invert alignments for horizonzal docks.
Mirror badge and progress-bar.

1327. By Rico Tzschichholz

po: Update translations

1328. By Rico Tzschichholz

animatedrenderer: Always initialize frame if a redraw is scheduled

1329. By Rico Tzschichholz

po: Update translations

1330. By Rico Tzschichholz

dockrenderer: Guard duration-calculations which are used for animations

1331. By Rico Tzschichholz

Update symbols

1332. By Rico Tzschichholz

color: Avoid double setting of out-vars in hsv_to_rgb

1333. By Rico Tzschichholz

color: Clarify documention of set_min/max_* methods

1334. By Rico Tzschichholz

hidemanager: Add dodge-active hide-mode

1335. By Rico Tzschichholz

prefswindow: Use Gtk.Stack if available

1336. By Rico Tzschichholz

build: Drop dependency on gnome-common

1337. By Rico Tzschichholz

prefswindow: Allow closing the window using "Escape"

1338. By Rico Tzschichholz

po: Update translations

1339. By Rico Tzschichholz

ui: Tweak minimum gtk+ version for conditional 3.4 support

1340. By Rico Tzschichholz

build: Make sure to enable maintainer-mode by default

1341. By Rico Tzschichholz

Add icon-zoom preferences and expose gui-settings

1342. By Rico Tzschichholz

Add optional zoom animation when hovering dock-items

1343. By Rico Tzschichholz

Add ability to cache multiple sizes of drawn items

1344. By Rico Tzschichholz

Update symbols

1345. By Rico Tzschichholz

po: Update translation template

1346. By Rico Tzschichholz

surfacecache: Add missing mutex-unlock

1347. By Rico Tzschichholz

po: Update translations

1348. By Rico Tzschichholz

lib: Make sure to bind "plank" textdomain for library users

1349. By Rico Tzschichholz

lib: Replace non-constant string-concatenation with string.printf()

1350. By Rico Tzschichholz

appdockitem: Always indicate running application despite its window-count

1351. By Rico Tzschichholz

tests: Add google-mock support

1352. By kay van der Zander

gmock: Add tests for Color

1353. By Rico Tzschichholz

hidemanager: Rework enter/leave-event handling to determine "Hovered"

This removes handling of send_event and use "Disabled" for visible menu.

1354. By Rico Tzschichholz

po: Update translations

1355. By Rico Tzschichholz

ui: Fix "Icon Zoom" label spanning

1356. By Rico Tzschichholz

dockwindow: Reinstate "handling of send_event" to fix broken internal DnD

Regression of r1353

1357. By Rico Tzschichholz

surfacecache: Fix build with gee-1.0

1358. By Rico Tzschichholz

dockcontainer: Update element's RemoveTime on add/replace accordingly

1359. By Rico Tzschichholz

lib: Commonize naming of fields which are holding handler/timer-ids

Adjust some explictly typed assignments too.

1360. By Rico Tzschichholz

dockrenderer: Use animated_draw() and don't listen to HoveredItem changes

1361. By Rico Tzschichholz

dockrenderer: Do not forcefully unhide the dock if it already is

If we do it will cause the dock to hide and unhide again on startup.

1362. By Rico Tzschichholz

Revert "dockrenderer: Use animated_draw() and don't listen to HoveredItem changes"

1363. By Rico Tzschichholz

positionmanager: Make item's background-region always cover dock's background from bottom up

1364. By Rico Tzschichholz

po: Update translations

1365. By Rico Tzschichholz

hidemanager: Don't use actual cursor coords of leave-notify-event

If we received a leave-notify-event then don't be silly and make sure
update_hovered_with_coords() will set Hovered to false by passing
(-1, -1).

1366. By Rico Tzschichholz

hidemanager: Reinstate "handling of send_event" to avoid confusion with menu

Regression of r1353

1367. By Rico Tzschichholz

dockrenderer: Output the Cairo.SurfaceType used by Gtk+

1368. By Rico Tzschichholz

positionmanager: Fix background-size calculation with enabled icon-zoom

We need to take the zoomed icon-size into account to properly adjust the
horizontal padding for the background-sizing while differentiating
between first and last item.

1369. By xapantu

hidemanager: Ignore pressure-reveal for 'absolute' input-devices

1370. By Rico Tzschichholz

dockelement: Make using -Werror=pointer-to-int-cast pass

1371. By Rico Tzschichholz

dockwindow: Make using -Werror=unused-result pass

1372. By Rico Tzschichholz

dockrenderer: Adjust shadow-size if window-scale-factor > 1 aka HiDPI

1373. By Rico Tzschichholz

po: Update translations

1374. By Rico Tzschichholz

lib: Cast some callbacks to avoid the creation of wrappers

1375. By Rico Tzschichholz

build: Require cairo >= 1.10

1376. By Rico Tzschichholz

lib: Cast some callbacks to avoid the creation of wrappers

1377. By Rico Tzschichholz

dbusmanager: Fix naming of fields which are holding handler/timer-ids

1378. By Rico Tzschichholz

dockrenderer: Avoid usage of Cairo.SurfaceType.COGL

1379. By Rico Tzschichholz

build: Clean bamf/gtk+ version check

1380. By Rico Tzschichholz

itemfactory: Make get_launcher_from_dockitem() a bit more safer/verbose

1381. By Rico Tzschichholz

dockcontainer: Add remove_all()

1382. By Rico Tzschichholz

dockrenderer: Guard against empty dock (which ideally won't happen)

1383. By Rico Tzschichholz

dockcontroller: Clean out old default-provider after replacing it

1384. By Rico Tzschichholz

dockcontainer: Optimize prepend()

1385. By Rico Tzschichholz

po: Update translations

1386. By Rico Tzschichholz

itemfactory: Avoid a string-copying

1387. By Rico Tzschichholz

positionmanager: Demote criticals of get_draw_value_for_item() to debug/warning

1388. By Rico Tzschichholz

Prepare 0.10.0 release

1389. By Rico Tzschichholz

Back to development

1390. By Mike Gabriel

animatedrenderer: Fix typo in error message

1391. By Rico Tzschichholz

build: Require valac >= 0.24.0 and obsolete conditionals

1392. By Rico Tzschichholz

po: Update translations

1393. By Rico Tzschichholz

po: Update translations

1394. By Rico Tzschichholz

filedockitem: Correctly display filenames with underscores in folder-menu

1395. By Rico Tzschichholz

positionmanager: Just return primary_monitor if empty plug_name was given

1396. By Rico Tzschichholz

positionmanager: Add verbose output for monitor_geo_changed

1397. By Rico Tzschichholz

dockitemprovider: Insert items where the data was dropped

If there is currently no HoveredItem try to determine the nearest one as
drop-point.

1398. By Rico Tzschichholz

lib: Tweak method signature of file-monitor callbacks

1399. By Rico Tzschichholz

lib: FileMonitorEvent is a simple enum not a flag

1400. By Rico Tzschichholz

lib: Avoid some superfluous reference-taking

1401. By Rico Tzschichholz

plankdockitem: Open "preferences" on left-click instead of "about"

1402. By Rico Tzschichholz

defaultappprovider: Don't ignore opened applications if Wnck doesn't know

Better don't rely on Wnck if Bamf reported an opened application. If an
application is for whatever reason replacing or renaming its window on
startup we might drop it while Wnck reports a window-count of 0.

1403. By Rico Tzschichholz

transientdockitem: Delayed reloading of the window-icon if needed

If the window-icon was null on the first try then schedule a 2nd one.

1404. By Rico Tzschichholz

lib: Actually pass e.g. -lm to the linker by adding it to *_LIBADD

1405. By Rico Tzschichholz

po: Update translations

1406. By Rico Tzschichholz

Prepare 0.10.1 release

1407. By Rico Tzschichholz

Back to development

1408. By Rico Tzschichholz

build: Be more rebust for parallel building

1409. By Rico Tzschichholz

dockrenderer: Don't request a redraw if "transient_items" is empty

1410. By Rico Tzschichholz

dockrenderer: Use non-linear transition in/out the "zoom" state

Increase transition-time to 200ms and use cubic-easing.

1411. By Rico Tzschichholz

easing: Some optimization, avoid vala's struct-copying by using pointers

1412. By Rico Tzschichholz

build: Be more rebust for parallel building

1413. By Rico Tzschichholz

easing: Use proper codestyle for ANIMATION_MODES while it is a const

1414. By Rico Tzschichholz

dockrenderer: Factor out jump-calculation into easing_bounce

1415. By Rico Tzschichholz

dockrenderer: Define and use some internal constants

1416. By Rico Tzschichholz

po: Update translations

1417. By Rico Tzschichholz

Add docklets support (internal/private)

Based on initially proposed docky 3.0 branch

1418. By Rico Tzschichholz

Add GSettings support and transition DockPreferences to it

1419. By Rico Tzschichholz

Update symbols

1420. By Rico Tzschichholz

po: Don't translate gschema for now

1421. By Rico Tzschichholz

Drop nested namespaces

1422. By Rico Tzschichholz

Rename DockSurface to Surface

1423. By Rico Tzschichholz

Rename AnimatedRenderer to Renderer

1424. By Rico Tzschichholz

build: Bump api and library version

1425. By Rico Tzschichholz

Keep existing theme and dockitem-files working and update them

1426. By Rico Tzschichholz

Update NEWS

1427. By Rico Tzschichholz

dockitem: Remove merge-conflict cruft

1428. By Danielle Foré

data: Improve strings of GSettings schema

1430. By Rico Tzschichholz

settings: Use unowned var and avoid ref'ing in loop

1431. By Rico Tzschichholz

docklets: Move to public API

1432. By Rico Tzschichholz

docklets: Make Docklet an interface and do follow up changes

1433. By Rico Tzschichholz

Add non-functional docklets-gui

1434. By Rico Tzschichholz

docs: Fix build

1435. By Rico Tzschichholz

build: Fix make distcheck

1436. By Rico Tzschichholz

tests: Set PLANK_DOCKLET_DIRS to docklets builddir for test-environment

1437. By Rico Tzschichholz

build: Add "run" target for conveniently running plank uninstalled

So running "make run" from the top_builddir will start the just built
plank with the required environment variables to actually pick things up
from the current builddir.

1438. By Rico Tzschichholz

services: Don't leak array-container of ObjectClass.list_properties()

ObjectClass.list_properties() transfers the container which needs to be
freed. If valac 0.26 is availble this can be managed.

1439. By Rico Tzschichholz

preferences: Cache various strings to avoid retrieving them several times

1440. By Rico Tzschichholz

settings: Cache class-type-name string

1441. By Rico Tzschichholz

tests: Make sure to use "test1" as dock-name

1442. By Rico Tzschichholz

dockitem: Don't leak array-container of ObjectClass.list_properties()

1443. By Rico Tzschichholz

Add methods to check some desktop environment types

1444. By Rico Tzschichholz

trash: Implement perform_empty_trash()

Only try using Nautilus on "GNOME" and "Unity" enviroments

1445. By Rico Tzschichholz

theme: Add "CascadeHide" option

If true it will cause background and icons to unhide/hide with different
speeds so they will leave/hit the screen-edge at the same time.

1446. By Rico Tzschichholz

po: Update translations

1447. By Rico Tzschichholz

dragmanager: Don't grab input and abort this drag if DragItem is null

1448. By Rico Tzschichholz

dockwindow: Be more persuasive to get the window where is should be

1449. By Rico Tzschichholz

po: Update translations

1450. By Rico Tzschichholz

Use fixed ObjectClass.list_properties() of valac 0.31/32 if available

1451. By Rico Tzschichholz

dockitem: Actually use internal constant ITEM_INVALID_DURATION

1452. By Rico Tzschichholz

po: Make use of "translator-credits" for Gtk.AboutDialog

1453. By Rico Tzschichholz

po: Update translations

1454. By Rico Tzschichholz

lib: Add internal compatibility wrapper for gtk+ 3.19.1+

1455. By Rico Tzschichholz

widgets: Adjust custom widgets for gtk+ 3.19.1+

1456. By Rico Tzschichholz

theme: Create and use custom Gtk.StyleContext

1457. By Rico Tzschichholz

dragmanager: Better handling if the actual selection-data is null

1458. By Rico Tzschichholz

dockitem: Only use file-monitor for "file://"-icon-files

1459. By Rico Tzschichholz

build: Add "run-debug" target for running plank uninstalled within gdb

1460. By Rico Tzschichholz

lib: Move HoverWindow instance into DockController

1461. By Rico Tzschichholz

dragmanager: Show descriptive tooltip on external-dnd actions

1462. By Rico Tzschichholz

dragmanager: desktop-files are special and deserve the drop-to-dock text

1463. By Rico Tzschichholz

po: Update translations

1464. By Rico Tzschichholz

po: Update translations

1465. By Rico Tzschichholz

data: Update appdata to 0.6+ format

1466. By Rico Tzschichholz

appdata: Make "summary" translatable, re-use tweaked desktop-file comment

1467. By Rico Tzschichholz

po: Update translations

1468. By Rico Tzschichholz

Welcome to 2016

1469. By Rico Tzschichholz

Use clamp() instead of min(max())

1470. By Rico Tzschichholz

dockpreferences: No need to notify about external changes of DockItems

1471. By Rico Tzschichholz

dockcontroller: Serialize possible DockItems change on start-up

1472. By Rico Tzschichholz

dockcontroller: Fix r1471 and actually save DockItems change on start-up

1473. By Rico Tzschichholz

color: Fix mess-up of r1469

1474. By Rico Tzschichholz

filedockitem: Hide "Keep in Dock" wile LockItems is enabled

1475. By Rico Tzschichholz

po: Update translations

1476. By Rico Tzschichholz

dockrenderer: Don't apply window-scale-factor twice on foreground-icon-size

Regression of r1343

1477. By Rico Tzschichholz

applicationdockitem: Check LauncherEntry values for actual changes

Also restrict the precision of "progress".

1478. By Rico Tzschichholz

items: Reduce redraw requests on LauncherEntry updates

1479. By Rico Tzschichholz

items: Fix build without dbusmenu-glib

1480. By Rico Tzschichholz

unity: Handle bad LauncherAPI clients which have an insane update-rate

Skip/hold requests if they are arriving within a defined threshold of
32ms after the previous one.

This avoids plank to freeze while not being able to handle all requests.

1481. By Rico Tzschichholz

positionmanager: Expand dock on external-drag without enabled zoom too

Also try harder to insert dropped elements at the actually desired spot.

1482. By Rico Tzschichholz

unity: Allow a specific amount of fast-updates before skipping/delaying

Cope with applications which are firing update-requests for multiple
application-uris at the same time.

1483. By Rico Tzschichholz

Revert "dockpreferences: No need to notify about external changes of DockItems"

This breaks GLib.Settings.bind() so that DockItems never get saved.

1484. By Rico Tzschichholz

Allow and handle uris with "docklet" scheme

1485. By Rico Tzschichholz

tests: Drop PreferencesWindow test

1486. By Rico Tzschichholz

Add some functionality to docklets GUI

Drag'n'drop or double-click a docklet to add it.

1487. By Rico Tzschichholz

settings: Must take reference of matched ParamSpec

Not doing so results in an undefined behaviour while things ran out of
scope when calling GSettings.bind().

This reverts r1430

1488. By Rico Tzschichholz

build: Fix gtk+-3.0 < 3.10 (non-HiDPI)

1489. By Rico Tzschichholz

preferenceswindow: Allow changing the backing DockController

1490. By Rico Tzschichholz

unity: Expose API to handle LauncherEntry DBus clients

1491. By Rico Tzschichholz

po: Update translations

1492. By Rico Tzschichholz

Cast callbacks to GLib.SourceFunc where possible

1493. By Rico Tzschichholz

unity: Use the real sender-name given by NameOwnerChanged

1494. By Rico Tzschichholz

build: Add autogen.sh to tarball

Conveniently rebuild/update the autotools downstream.

1495. By Rico Tzschichholz

po: Update translations

1496. By Rico Tzschichholz

examples: Add UnityClient example

1497. By Rico Tzschichholz

abstractmain: Use new GLib.Application commandline handling API

Require glib >= 2.40

1498. By Rico Tzschichholz

build: Drop support for gee-1.0

1499. By Rico Tzschichholz

build: Drop obsololete glib conditionals and bump vala's target-glib

1500. By Rico Tzschichholz

build: Drop support for gtk+ < 3.10

1501. By Rico Tzschichholz

ui: Use valac's gtktemplate support

1502. By Rico Tzschichholz

po: Update translations

1503. By Rico Tzschichholz

lib: Update symbols

1504. By Rico Tzschichholz

build: Only cairo >= 1.13 is required for HiDPI

1505. By Rico Tzschichholz

tests: Make sure to quit "dock" test application

1506. By Rico Tzschichholz

preferenceswindow: Keep translated "Preferences" string around for now

1507. By Rico Tzschichholz

docktheme: Adjust draw-position item-badge to avoid cropped shadow

1508. By Rico Tzschichholz

positionmanager: Partly restore original icon-zoom

1509. By Rico Tzschichholz

dockitem: Handle file-monitor event where current launcher was target

If "other" of FileMonitorEvent.MOVED matches our current launcher-file
than it got replaced by a new file, so avoid doing anything other than
loading possible new information.

1510. By Rico Tzschichholz

items: Handle "PinnedOnly" in DefaultApplicationDockItemProvider

This is more efficient than doing this in the DockController. Only the
actually effected items are created/purged on a settings change.

1511. By Rico Tzschichholz

factories: Generalize "dockitem-file" loader

1512. By Rico Tzschichholz

items: Add LauncherEntry's transient-items only if allowed

Regression of r1510

1513. By Rico Tzschichholz

Add "simple and experimental" multi-dock support

Running multiple concurrent instances while using "-n|--name"
is still possible.

There are no exposed GUI controls, therefore the newly added
"enabled-docks" settings-key should be used.

1514. By Rico Tzschichholz

items: Add transient-items only if allowed

1515. By Rico Tzschichholz

Update NEWS

1516. By Rico Tzschichholz

po: Update translations

1517. By Rico Tzschichholz

utils: Add internal create_settings() and try_create_settings()

... and make use of them where possible.

1518. By Rico Tzschichholz

utils: Add internal string_split_combine()

1519. By Rico Tzschichholz

utils: Add internal file_is_dockitem()

1520. By Rico Tzschichholz

settings: Allow to specify gsetting's bind-flags

1521. By Rico Tzschichholz

Follow the environment's setting whether to show notifications or not

If false, urgent-bounce and urgent-glow animations are disabled.

1522. By Rico Tzschichholz

lib: Move DockItemDrawValue and its dependencies to top-level namespace

1523. By Rico Tzschichholz

docs: Fix build

1524. By Rico Tzschichholz

controller: If the item-count has changed do a more thorough size-update

1525. By Rico Tzschichholz

positionmanager: Drop redundant call of update_regions()

1526. By Rico Tzschichholz

surfacecache: Force allow-downscale if drawing-time is insanely high

If drawing-time of a single surface exceeds a certains limit (30ms) and
"flags" is NONE then set ALLOW_DOWNSCALE to make it less demanding.

Also mark the created surface, so the DockRenderer can try to ease things
out for later draw requests.

1527. By Rico Tzschichholz

services: Rename internal Offsettings to EnvironmentSettings

1528. By Rico Tzschichholz

Check existence of keys in 3rd-party GSchemas before using them

Accessing a non-existing key is a fatal error for GSettings.

1529. By Rico Tzschichholz

po: Update translations

1530. By Rico Tzschichholz

prefs: Add TooltipsEnabled setting

This controls whether to show tooltips on hovering items with the cursor.
Tooltips showing up to descibe ongoing DnD-actions are not impacted.

It is enabled by default.

1531. By Rico Tzschichholz

hidemanager: TOUCHPAD devices are able to perform pressure on a barrier

1532. By Rico Tzschichholz

preferenceswindow: Hide "auto-pinning" setting

1533. By Rico Tzschichholz

preferenceswindow: Hide "show-dock-item" setting

Make "show-dock-item" default to false

1534. By Rico Tzschichholz

data: Some tweaking of the default themes

1535. By Rico Tzschichholz

Update README

1536. By Rico Tzschichholz

Update NEWS

1537. By Rico Tzschichholz

Prepare 0.11.0 release

1538. By Rico Tzschichholz

Back to development

1539. By Rico Tzschichholz

system: Use DesktopAppInfo.from_filename() to set desktop-filename

If the filename property is not set then an empty string will be send out
via org.gtk.gio.DesktopAppInfo rather than the proper desktop-filename
that we actually have. This is used for startup-notifications by Bamf.

1540. By Rico Tzschichholz

po: Update translations

1541. By Rico Tzschichholz

dockletmanager: Only handle properly named docklet-libraries

1542. By Rico Tzschichholz

controller: Actually emmit elements_changed() to make DBusClient work

1543. By Rico Tzschichholz

vapi: Sync libbamf3.vapi with 0.5.3~bzr0+16.04.20160322.1-0ubuntu1

1544. By Rico Tzschichholz

applicationdockitem: Force indicator-update if running-state changed

1545. By Rico Tzschichholz

applicationdockitem: Use child-* signals of Bamf.View

The window-* signals are emitted too early and the internal window/xid
caches of Bamf aren't updated yet.

1546. By Rico Tzschichholz

po: Update translations

1547. By Rico Tzschichholz

Prepare 0.11.1 release

1548. By Rico Tzschichholz

Back to development

1549. By Rico Tzschichholz

lib: Update symbols

1550. By Rico Tzschichholz

surface: Some minor cleaning

1551. By Rico Tzschichholz

drawing/color: Add support for HSL and some convenience functions

1552. By Rico Tzschichholz

clippy: Pass correct index in menu-item-callback

1553. By Rico Tzschichholz

clippy: text parameter of ClipboardTextReceivedFunc is allowed to be null

1554. By Rico Tzschichholz

po: Update translations

1555. By Rico Tzschichholz

clippy: Need to own the clipboard's content before allowed to clear it

1556. By Rico Tzschichholz

po: Update translations

1557. By Rico Tzschichholz

build: Require valac >= 0.26.0 and drop obsolete conditionals

1558. By Rico Tzschichholz

lib: Use vala's Cairo.Surface.get/set_device_scale() bindings

1559. By Rico Tzschichholz

vapi: Drop internal copy of x11.vapi

1560. By Rico Tzschichholz

lib: Add and enforce some file-count limits

This is just a safe-guard to prevent plank from "blowing up" if we are
about to handle an unreasonable amount of files.

1561. By Rico Tzschichholz

docklets: Fill in some descriptions and not leave them blank

1562. By Rico Tzschichholz

Prepare 0.11.2 release

1563. By Rico Tzschichholz

Back to development

1564. By Rico Tzschichholz

po: Update translations

1565. By Rico Tzschichholz

Add CPUMonitor docklet

1566. By Rico Tzschichholz

po: Update translations

1567. By Rico Tzschichholz

appdata: Add some keywords and translate-url

1568. By Rico Tzschichholz

tests: Fix type mismatch

1569. By Rico Tzschichholz

clippy: Move generic-typed field initializer to construct

1570. By Rico Tzschichholz

po: Update translations

1571. By Rico Tzschichholz

surfacecache: Never clear the cache completely

1572. By Rico Tzschichholz

po: Update translations

1573. By Rico Tzschichholz

Make use of vala's native Regex support where possible

1574. By Rico Tzschichholz

vapi: Avoid "Deprecated" warning for libbamf3

1575. By Rico Tzschichholz

windows: Hide tooltips if the user performed action on a dockitem

Obviously tooltips will be hidden on appearance of the menu. In addition
to that it will hide on click- and scroll-events too now.

This avoids obstructing maybe important windows parts the user wants to
interact with.

1576. By Rico Tzschichholz

appdockitem: Don't over-react on user-visible changes and keep transients

Dropping an running application here is a bit harsh in case of transient
items. If a splashscreen is shown then this bit changes along the
starting process and is fatal for not-pinned items.

1577. By Rico Tzschichholz

appdockitem: Trust bamf with providing us the window-count

1578. By Rico Tzschichholz

filedockitem: Use the file's display-name where possible

This is the proper string to use for user-visible references to a file.

1579. By Rico Tzschichholz

Drop references to gthread-2.0

This is deprecated and obsolete since glib 2.32.0.

1580. By Rico Tzschichholz

logger: Reinstate null-check for non-initialized calling

1581. By Rico Tzschichholz

unity: Fix spelling error

1582. By Rico Tzschichholz

Prepare 0.11.3 release

1583. By Rico Tzschichholz

Back to development

1584. By Rico Tzschichholz

Welcome to 2017

Unmerged revisions

1586. By Rico Tzschichholz

keybindingsmanager: Use gdk_window_add/remove_filter()

1585. By Rico Tzschichholz

Add initial support for Keybindings to access items

There is the possiblity to define base-modifier key to trigger
keybindings-overlay and an additional modifier key for optional
item-action. The first 10 items will have an active binding.

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'data/net.launchpad.plank.gschema.xml.in.in'
2--- data/net.launchpad.plank.gschema.xml.in.in 2016-03-09 08:51:55 +0000
3+++ data/net.launchpad.plank.gschema.xml.in.in 2017-01-16 09:48:10 +0000
4@@ -71,11 +71,27 @@
5 <_summary>Icon Size</_summary>
6 <_description>The size of dock items, in pixels.</_description>
7 </key>
8+ <key name="item-accelerator" type="s">
9+ <default>'Super_L'</default>
10+ <_summary>The base modifier-key for item keybinding shortcuts</_summary>
11+ <_description></_description>
12+ </key>
13 <key name="items-alignment" enum='GtkAlignType'>
14 <default>'center'</default>
15 <_summary>The alignment of dock items</_summary>
16 <_description>Possible values are "fill", "start", "end", and "center".</_description>
17 </key>
18+ <key name="item-option-accelerator" type="s">
19+ <default>'Shift_L'</default>
20+ <_summary>The additional modifier-key for optional item keybinding shortcuts</_summary>
21+ <_description></_description>
22+ </key>
23+ <key name="keybinding-unhide-delay" type="i">
24+ <range min="0"/>
25+ <default>400</default>
26+ <_summary>Keybinding unhide delay</_summary>
27+ <_description>Length of the delay before showing keybinding-overlay the dock, in milliseconds.</_description>
28+ </key>
29 <key name="lock-items" type="b">
30 <default>false</default>
31 <_summary>Lock dock items</_summary>
32
33=== modified file 'lib/DockController.vala'
34--- lib/DockController.vala 2016-03-23 19:51:11 +0000
35+++ lib/DockController.vala 2017-01-16 09:48:10 +0000
36@@ -40,6 +40,7 @@
37 public DockRenderer renderer { get; protected set; }
38 public DockWindow window { get; protected set; }
39 public HoverWindow hover { get; protected set; }
40+ public KeybindingManager keybinding_manager { get; protected set; }
41
42 public DockItemProvider? default_provider { get; private set; }
43
44@@ -100,6 +101,7 @@
45 window = new DockWindow (this);
46 hover = new HoverWindow ();
47 renderer = new DockRenderer (this, window);
48+ keybinding_manager = new KeybindingManager (this);
49 }
50
51 ~DockController ()
52@@ -140,6 +142,14 @@
53 renderer.initialize ();
54
55 window.show_all ();
56+
57+ // FIXME maybe do this on a separate thread while this takes some time if X is stalling
58+ // putting it into an idle at least gives the illusion of starting up fast ;-)
59+ Idle.add (() => {
60+ keybinding_manager.initialize ();
61+
62+ return false;
63+ });
64 }
65
66 /**
67@@ -224,6 +234,14 @@
68 }
69 }
70
71+ public void virtual_click_item_at (int pos, PopupButton button)
72+ {
73+ if (visible_items.size < pos + 1)
74+ return;
75+
76+ visible_items[pos].clicked (button, 0, Gtk.get_current_event_time ());
77+ }
78+
79 protected override void update_visible_elements ()
80 {
81 base.update_visible_elements ();
82
83=== modified file 'lib/DockPreferences.vala'
84--- lib/DockPreferences.vala 2016-03-04 15:54:48 +0000
85+++ lib/DockPreferences.vala 2017-01-16 09:48:10 +0000
86@@ -90,6 +90,15 @@
87 [Description(nick = "tooltips-enabled", blurb = "Whether to show tooltips when items are hovered.")]
88 public bool TooltipsEnabled { get; set; }
89
90+ [Description(nick = "item-accelerator", blurb = "The base modifier-key for item keybinding shortcuts.")]
91+ public string ItemAccelerator { get; set; }
92+
93+ [Description(nick = "item-option-accelerator", blurb = "The additional modifier-key for optional item keybinding shortcuts.")]
94+ public string ItemOptionAccelerator { get; set; }
95+
96+ [Description(nick = "keybinding-unhide-delay", blurb = "Time (in ms) to wait before showing keybinding-overlay the dock.")]
97+ public uint KeybindingUnhideDelay { get; set; }
98+
99 /**
100 * {@inheritDoc}
101 */
102
103=== modified file 'lib/DockRenderer.vala'
104--- lib/DockRenderer.vala 2016-06-01 09:48:44 +0000
105+++ lib/DockRenderer.vala 2017-01-16 09:48:10 +0000
106@@ -29,6 +29,11 @@
107 public DockTheme theme { get; private set; }
108
109 /**
110+ * If the dock should show the keybindings and which.
111+ */
112+ public Keybinding VisibleKeybinding { get; set; default = 0; }
113+
114+ /**
115 * The current progress [0.0..1.0] of the hide-animation of the dock.
116 */
117 [CCode (notify = false)]
118@@ -62,13 +67,16 @@
119 Surface? indicator_buffer = null;
120 Surface? urgent_indicator_buffer = null;
121 Surface? urgent_glow_buffer = null;
122+ Gee.HashMap<uint, Surface> keybinding_buffers;
123
124 int64 last_hide = 0LL;
125 int64 last_hovered_changed = 0LL;
126+ int64 last_keybinding = 0LL;
127
128 bool screen_is_composited = false;
129 bool show_notifications = true;
130 uint reset_position_manager_timer_id = 0U;
131+ uint keybindings_timer_id = 0U;
132 int window_scale_factor = 1;
133 bool is_first_frame = true;
134 bool zoom_changed = false;
135@@ -98,6 +106,7 @@
136 {
137 transient_items = new Gee.HashSet<DockItem> ();
138 current_items = new Gee.ArrayList<unowned DockItem> ();
139+ keybinding_buffers = new Gee.HashMap<uint, Surface> ();
140 #if BENCHMARK
141 benchmark = new Gee.ArrayList<string> ();
142 #endif
143@@ -129,6 +138,46 @@
144 controller.window.notify["HoveredItem"].disconnect (animated_draw);
145 }
146
147+ /**
148+ * Unhide the dock immediately if needed and show keybindings after a short delay
149+ */
150+ public void show_keybindings ()
151+ {
152+ if (keybindings_timer_id > 0U)
153+ return;
154+
155+ keybindings_timer_id = Timeout.add (controller.prefs.KeybindingUnhideDelay, () => {
156+ keybindings_timer_id = 0U;
157+ last_keybinding = GLib.get_monotonic_time ();
158+ VisibleKeybinding |= Keybinding.ITEMS;
159+
160+ animated_draw ();
161+
162+ return false;
163+ });
164+ }
165+
166+ /**
167+ * Hide keybindings immediately and hide the dock if needed
168+ */
169+ public void hide_keybindings ()
170+ {
171+ if (keybindings_timer_id > 0U) {
172+ Source.remove (keybindings_timer_id);
173+ keybindings_timer_id = 0U;
174+ }
175+
176+ if (VisibleKeybinding != 0) {
177+ var now = GLib.get_monotonic_time ();
178+ if (now - last_keybinding > controller.prefs.KeybindingUnhideDelay * 1000)
179+ last_keybinding = now;
180+
181+ VisibleKeybinding = 0;
182+ }
183+
184+ animated_draw ();
185+ }
186+
187 void prefs_changed (Object prefs, ParamSpec prop)
188 {
189 switch (prop.name) {
190@@ -213,6 +262,8 @@
191 urgent_indicator_buffer = null;
192 urgent_glow_buffer = null;
193
194+ keybinding_buffers.clear ();
195+
196 animated_draw ();
197 }
198
199@@ -839,6 +890,26 @@
200 // draw indicators
201 if (draw_value.show_indicator && item.Indicator != IndicatorState.NONE)
202 draw_indicator_state (cr, draw_value.hover_region, item.Indicator, item.State);
203+
204+ // draw keybinding overlay
205+ var keybinding_time = frame_time - last_keybinding;
206+ opacity = double.min (1, keybinding_time / (double) (theme.HideTime * 1000));
207+ if (VisibleKeybinding == 0)
208+ opacity = 1 - opacity;
209+ if (opacity > 0) {
210+ //FIXME Use letters for for 10+ items
211+ var number = (item.Position + 1) % 10;
212+ var is_option = ((VisibleKeybinding & Keybinding.ITEMS_OPTION) == Keybinding.ITEMS_OPTION);
213+ var index = (is_option ? number + 1024 : number);
214+
215+ Surface? keybinding_surface = null;
216+ if ((keybinding_surface = keybinding_buffers.get (index)) == null) {
217+ keybinding_surface = theme.create_keybinding (icon_size / 2, number.to_string (), item_buffer, is_option);
218+ keybinding_buffers.set (index, keybinding_surface);
219+ }
220+ cr.set_source_surface (keybinding_surface.Internal, draw_region.x + icon_size / 4, draw_region.y + icon_size / 4);
221+ cr.paint_with_alpha (opacity);
222+ }
223 }
224
225 void draw_item_shadow (Cairo.Context cr, DockItem item, DockItemDrawValue draw_value)
226@@ -1109,6 +1180,9 @@
227 return true;
228 }
229
230+ if (frame_time - last_keybinding <= theme.HideTime * 1000)
231+ return true;
232+
233 if (transient_items.size > 0)
234 return true;
235
236
237=== modified file 'lib/Drawing/DockTheme.vala'
238--- lib/Drawing/DockTheme.vala 2016-03-12 15:14:09 +0000
239+++ lib/Drawing/DockTheme.vala 2017-01-16 09:48:10 +0000
240@@ -276,6 +276,92 @@
241 }
242
243 /**
244+ * Creates a keybinding overlay
245+ *
246+ * @param size the size of the surface
247+ * @param text the string to show
248+ * @param model existing surface to use as basis of new surface
249+ * @param is_option slightly different style for another function
250+ * @return a new dock surface with the keybinding overlay drawn on it
251+ */
252+ public Surface create_keybinding (int size, string text, Surface model, bool is_option = false)
253+ {
254+ Logger.verbose ("DockTheme.create_keybinding (size = %i, text = %s)", size, text);
255+
256+ var surface = new Surface.with_surface (size, size, model);
257+ surface.clear ();
258+
259+ if (size <= 0)
260+ return surface;
261+
262+ var cr = surface.Context;
263+
264+ var line_width = 2.0;
265+ var padding = Math.ceil (size / 12.0);
266+ double x = line_width / 2.0;
267+ double y = line_width / 2.0;
268+ double height = size - 2 * line_width;
269+ double width = size - 2 * line_width;
270+
271+ cr.set_line_width (line_width);
272+
273+ Cairo.Pattern stroke, fill;
274+
275+ // draw outline shadow
276+ stroke = new Cairo.Pattern.rgba (0.2, 0.2, 0.2, 0.3);
277+ draw_rounded_line (cr, x, y, width + line_width, height, true, true, stroke, null);
278+
279+ // draw filled gradient with outline
280+ stroke = new Cairo.Pattern.linear (0, y, 0, y + height);
281+ stroke.add_color_stop_rgba (0.2, 0.0, 0.0, 0.0, 0.9);
282+ stroke.add_color_stop_rgba (0.8, 0.0, 0.0, 0.0, 0.8);
283+ fill = new Cairo.Pattern.linear (0, y, 0, y + height);
284+ fill.add_color_stop_rgba (0.1, 0.0, 0.0, 0.0, 0.8);
285+ fill.add_color_stop_rgba (0.9, 0.0, 0.0, 0.0, 0.9);
286+ draw_rounded_line (cr, x, y, width, height, true, true, stroke, fill);
287+
288+ // draw inline highlight
289+ if (!is_option)
290+ stroke = new Cairo.Pattern.rgba (0.9, 0.9, 0.9, 0.1);
291+ else
292+ stroke = new Cairo.Pattern.rgba (0.9, 0.9, 0.9, 0.9);
293+ draw_rounded_line (cr, x + line_width, y + line_width, width - 2 * line_width, height - 2 * line_width, true, true, stroke, null);
294+
295+ var layout = new Pango.Layout (Gdk.pango_context_get ());
296+ layout.set_width ((int) (width * Pango.SCALE));
297+ layout.set_ellipsize (Pango.EllipsizeMode.NONE);
298+
299+ var font_description = new Gtk.Style ().font_desc;
300+ font_description.set_absolute_size ((int) (height * Pango.SCALE));
301+ font_description.set_weight (Pango.Weight.BOLD);
302+ layout.set_font_description (font_description);
303+
304+ layout.set_text (text, -1);
305+ Pango.Rectangle ink_rect, logical_rect;
306+ layout.get_pixel_extents (out ink_rect, out logical_rect);
307+
308+ var scale = double.min (1.0, double.min ((width - 2.0 * padding - 2.0 * line_width) / (double) logical_rect.width, (height - 2.0 * padding) / (double) logical_rect.height));
309+
310+ cr.set_source_rgba (1.0, 1.0, 1.0, 0.2);
311+
312+ cr.move_to (x + Math.floor (width / 2.0 - scale * logical_rect.width / 2.0), y + Math.floor (height / 2.0 - scale * logical_rect.height / 2.0));
313+
314+ // draw text
315+ cr.save ();
316+ if (scale < 1)
317+ cr.scale (scale, scale);
318+
319+ cr.set_line_width (line_width);
320+ Pango.cairo_layout_path (cr, layout);
321+ cr.stroke_preserve ();
322+ cr.set_source_rgba (1.0, 1.0, 1.0, 0.95);
323+ cr.fill ();
324+ cr.restore ();
325+
326+ return surface;
327+ }
328+
329+ /**
330 * Draws an active glow for an item.
331 *
332 * @param surface the surface to draw onto
333
334=== modified file 'lib/HideManager.vala'
335--- lib/HideManager.vala 2016-03-08 22:15:30 +0000
336+++ lib/HideManager.vala 2017-01-16 09:48:10 +0000
337@@ -137,6 +137,8 @@
338 unowned DockWindow window = controller.window;
339 unowned Wnck.Screen wnck_screen = Wnck.Screen.get_default ();
340
341+ controller.renderer.notify["VisibleKeybinding"].connect (update_hovered);
342+
343 #if HAVE_BARRIERS
344 initialize_barriers_support ();
345 #endif
346@@ -159,6 +161,7 @@
347 unowned Wnck.Screen wnck_screen = Wnck.Screen.get_default ();
348
349 controller.prefs.notify.disconnect (prefs_changed);
350+ controller.renderer.notify["VisibleKeybinding"].disconnect (update_hovered);
351
352 window.enter_notify_event.disconnect (handle_enter_notify_event);
353 window.leave_notify_event.disconnect (handle_leave_notify_event);
354@@ -215,6 +218,7 @@
355 unowned PositionManager position_manager = controller.position_manager;
356 unowned DockWindow window = controller.window;
357 unowned DragManager drag_manager = controller.drag_manager;
358+ unowned DockRenderer renderer = controller.renderer;
359
360 freeze_notify ();
361
362@@ -233,7 +237,7 @@
363 }
364
365 // disable hiding if menu is visible or drags are active
366- var disabled = (window.menu_is_visible () || drag_manager.InternalDragActive || drag_manager.ExternalDragActive);
367+ var disabled = (window.menu_is_visible () || renderer.VisibleKeybinding > 0 || drag_manager.InternalDragActive || drag_manager.ExternalDragActive);
368 if (Disabled != disabled) {
369 Disabled = disabled;
370 update_needed = true;
371
372=== added file 'lib/KeybindingManager.vala'
373--- lib/KeybindingManager.vala 1970-01-01 00:00:00 +0000
374+++ lib/KeybindingManager.vala 2017-01-16 09:48:10 +0000
375@@ -0,0 +1,405 @@
376+//
377+// Copyright (C) 2012 Rico Tzschichholz
378+//
379+// This program is free software: you can redistribute it and/or modify
380+// it under the terms of the GNU General Public License as published by
381+// the Free Software Foundation, either version 3 of the License, or
382+// (at your option) any later version.
383+//
384+// This program is distributed in the hope that it will be useful,
385+// but WITHOUT ANY WARRANTY; without even the implied warranty of
386+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
387+// GNU General Public License for more details.
388+//
389+// You should have received a copy of the GNU General Public License
390+// along with this program. If not, see <http://www.gnu.org/licenses/>.
391+//
392+
393+namespace Plank
394+{
395+ [Flags]
396+ public enum Keybinding {
397+ ITEMS = 1 << 0,
398+ ITEMS_OPTION = 1 << 1
399+ }
400+
401+ /**
402+ * This class is in charge to grab keybindings on the X11 display
403+ * and filter X11-events and passing on such events to the registed
404+ * handler methods.
405+ */
406+ public class KeybindingManager : GLib.Object
407+ {
408+ /**
409+ * The controller for this dock.
410+ */
411+ public DockController controller { private get; construct; }
412+
413+ /**
414+ * list of bound keybindings
415+ */
416+ Gee.ArrayList<Binding> bindings = new Gee.ArrayList<Binding> ();
417+
418+ /**
419+ * locked modifiers used to grab all keys whatever lock key
420+ * is pressed.
421+ */
422+ static uint[] ignored_masks = {
423+ 0,
424+ Gdk.ModifierType.MOD2_MASK, // NUM_LOCK
425+ Gdk.ModifierType.LOCK_MASK, // CAPS_LOCK
426+ Gdk.ModifierType.MOD5_MASK, // SCROLL_LOCK
427+ Gdk.ModifierType.MOD2_MASK | Gdk.ModifierType.LOCK_MASK,
428+ Gdk.ModifierType.MOD2_MASK | Gdk.ModifierType.MOD5_MASK,
429+ Gdk.ModifierType.LOCK_MASK | Gdk.ModifierType.MOD5_MASK,
430+ Gdk.ModifierType.MOD2_MASK | Gdk.ModifierType.LOCK_MASK | Gdk.ModifierType.MOD5_MASK
431+ };
432+
433+ /**
434+ * Helper class to store keybinding
435+ */
436+ class Binding
437+ {
438+ public string accelerator;
439+ public uint8 keycode;
440+ public Gdk.ModifierType modifiers;
441+ public KeybindingHandlerFunc handler;
442+
443+ public Binding (string _accelerator, uint8 _keycode,
444+ Gdk.ModifierType _modifiers, owned KeybindingHandlerFunc _handler)
445+ {
446+ accelerator = _accelerator;
447+ keycode = _keycode;
448+ modifiers = _modifiers;
449+ handler = _handler;
450+ }
451+ }
452+
453+ /**
454+ * Keybinding func needed to bind key to handler
455+ *
456+ * @param event passing on gdk event
457+ */
458+ public delegate void KeybindingHandlerFunc (X.Event event);
459+
460+ public KeybindingManager (DockController controller)
461+ {
462+ GLib.Object (controller: controller);
463+ }
464+
465+ construct
466+ {
467+ gdk_window_add_filter (null, (Gdk.FilterFunc) xevent_filter);
468+ }
469+
470+ ~KeybindingManager ()
471+ {
472+ unbind_all ();
473+
474+ gdk_window_remove_filter (null, (Gdk.FilterFunc) xevent_filter);
475+ }
476+
477+ public void initialize ()
478+ {
479+ var item_accel = controller.prefs.ItemAccelerator;
480+ var item_option_accel = controller.prefs.ItemOptionAccelerator;
481+
482+ var mod = KeybindingManager.convert_to_modifier_only (item_accel);
483+ var option_mod = KeybindingManager.convert_to_modifier_only (item_option_accel);
484+
485+ if (controller.prefs.ItemAccelerator == "") {
486+ warning ("%s is not a modifier! Keybindings will not be available!", item_accel);
487+ return;
488+ }
489+
490+ // bind base accelerator
491+ if (!bind (item_accel, controller.renderer.show_keybindings)
492+ || !bind ("<Release>" + item_accel, controller.renderer.hide_keybindings)) {
493+ warning ("Keybindings will not be available!");
494+ return;
495+ }
496+
497+ bind (mod + "1", () => { controller.virtual_click_item_at (0, PopupButton.LEFT); });
498+ bind (mod + "2", () => { controller.virtual_click_item_at (1, PopupButton.LEFT); });
499+ bind (mod + "3", () => { controller.virtual_click_item_at (2, PopupButton.LEFT); });
500+ bind (mod + "4", () => { controller.virtual_click_item_at (3, PopupButton.LEFT); });
501+ bind (mod + "5", () => { controller.virtual_click_item_at (4, PopupButton.LEFT); });
502+ bind (mod + "6", () => { controller.virtual_click_item_at (5, PopupButton.LEFT); });
503+ bind (mod + "7", () => { controller.virtual_click_item_at (6, PopupButton.LEFT); });
504+ bind (mod + "8", () => { controller.virtual_click_item_at (7, PopupButton.LEFT); });
505+ bind (mod + "9", () => { controller.virtual_click_item_at (8, PopupButton.LEFT); });
506+ bind (mod + "0", () => { controller.virtual_click_item_at (9, PopupButton.LEFT); });
507+
508+ // bind option accelerator
509+ if (item_option_accel == "") {
510+ warning ("%s is not a modifier! Optional keybindings will not be available!", item_option_accel);
511+ return;
512+ }
513+
514+ bind (mod + item_option_accel, () => {
515+ controller.renderer.VisibleKeybinding |= Keybinding.ITEMS_OPTION;
516+ controller.renderer.animated_draw ();
517+ });
518+ bind ("<Release>" + mod + item_option_accel, () => {
519+ controller.renderer.VisibleKeybinding &= ~Keybinding.ITEMS_OPTION;
520+ controller.renderer.animated_draw ();
521+ });
522+ bind ("<Release>" + option_mod + item_option_accel, controller.renderer.hide_keybindings);
523+
524+ bind (mod + option_mod + "1", () => { controller.virtual_click_item_at (0, PopupButton.MIDDLE); });
525+ bind (mod + option_mod + "2", () => { controller.virtual_click_item_at (1, PopupButton.MIDDLE); });
526+ bind (mod + option_mod + "3", () => { controller.virtual_click_item_at (2, PopupButton.MIDDLE); });
527+ bind (mod + option_mod + "4", () => { controller.virtual_click_item_at (3, PopupButton.MIDDLE); });
528+ bind (mod + option_mod + "5", () => { controller.virtual_click_item_at (4, PopupButton.MIDDLE); });
529+ bind (mod + option_mod + "6", () => { controller.virtual_click_item_at (5, PopupButton.MIDDLE); });
530+ bind (mod + option_mod + "7", () => { controller.virtual_click_item_at (6, PopupButton.MIDDLE); });
531+ bind (mod + option_mod + "8", () => { controller.virtual_click_item_at (7, PopupButton.MIDDLE); });
532+ bind (mod + option_mod + "9", () => { controller.virtual_click_item_at (8, PopupButton.MIDDLE); });
533+ bind (mod + option_mod + "0", () => { controller.virtual_click_item_at (9, PopupButton.MIDDLE); });
534+ }
535+
536+ /**
537+ * Bind accelerator to given handler
538+ *
539+ * @param accelerator accelerator parsable by Gtk.accelerator_parse
540+ * @param handler handler called when given accelerator is pressed
541+ * @return wether the bind was successful or not
542+ */
543+ public bool bind (string accelerator, owned KeybindingHandlerFunc handler)
544+ {
545+ Logger.verbose ("Binding key " + accelerator);
546+
547+ // convert accelerator
548+ uint keysym;
549+ Gdk.ModifierType modmask;
550+ Gtk.accelerator_parse (accelerator, out keysym, out modmask);
551+
552+ unowned X.Display display = Gdk.X11.get_default_xdisplay ();
553+ var xid = Gdk.X11.get_default_root_xwindow ();
554+
555+ uint8 keycode = display.keysym_to_keycode (keysym);
556+ if (keycode == 0)
557+ return false;
558+
559+ var keystr = X.keysym_to_string (keysym);
560+ if (keystr == null)
561+ return false;
562+
563+ // FIXME somethings is wrong with the SUPER modifier between the GDK and X values
564+ // so replace SUPER_MASK with MOD4_MASK
565+ if ((modmask & Gdk.ModifierType.SUPER_MASK) == Gdk.ModifierType.SUPER_MASK)
566+ modmask = (modmask & ~Gdk.ModifierType.SUPER_MASK) | Gdk.ModifierType.MOD4_MASK;
567+
568+ // trap XErrors to avoid closing of application
569+ // even when grabing of key fails
570+ Gdk.error_trap_push ();
571+
572+ // grab key finally
573+ // also grab all keys which are combined with a lock key such NumLock
574+ foreach (var ignored_mask in ignored_masks) {
575+ Gdk.error_trap_push ();
576+ display.grab_key (keycode, modmask | ignored_mask, xid, false, X.GrabMode.Async, X.GrabMode.Async);
577+
578+ // wait until all X request have been processed
579+ Gdk.flush ();
580+ var result = Gdk.error_trap_pop ();
581+ if (result != X.ErrorCode.SUCCESS) {
582+ warning ("Failed to bind key 0x%X ('%s') with modifiers 0x%X", keycode, keystr, modmask);
583+ if (result == X.ErrorCode.BAD_ACCESS)
584+ debug ("Some other program is already using the key 0x%X ('%s') with modifiers 0x%X as a binding", keycode, keystr, modmask | ignored_mask);
585+ return false;
586+ }
587+ }
588+
589+ Gdk.error_trap_pop ();
590+
591+ Logger.verbose ("Successfully bound key 0x%X ('%s') with modifiers 0x%X", keycode, keystr, modmask);
592+
593+ // if this is a key-released binding then add corresponding modifiermask
594+ // for keycode to our modmask if it is a modifier
595+ if ((modmask & Gdk.ModifierType.RELEASE_MASK) == Gdk.ModifierType.RELEASE_MASK)
596+ modmask |= get_modmask_for_keycode (keycode);
597+
598+ // store binding
599+ var binding = new Binding (accelerator, keycode, modmask, handler);
600+ bindings.add (binding);
601+
602+ return true;
603+ }
604+
605+ /**
606+ * Unbind given accelerator.
607+ *
608+ * @param accelerator accelerator parsable by Gtk.accelerator_parse
609+ */
610+ public void unbind (string accelerator)
611+ {
612+ Logger.verbose ("Unbinding key " + accelerator);
613+
614+ unowned X.Display display = Gdk.X11.get_default_xdisplay ();
615+ var xid = Gdk.X11.get_default_root_xwindow ();
616+
617+ // unbind all keys with given accelerator
618+ var remove_bindings = new Gee.ArrayList<Binding> ();
619+ foreach (var binding in bindings) {
620+ if (str_equal (accelerator, binding.accelerator)) {
621+ // if this is a key-released binding then remove corresponding modifiermask
622+ // for keycode to our modmask if it is a modifier which we added on bind
623+ if ((binding.modifiers & Gdk.ModifierType.RELEASE_MASK) == Gdk.ModifierType.RELEASE_MASK)
624+ binding.modifiers &= ~get_modmask_for_keycode (binding.keycode);
625+
626+ foreach (var ignored_mask in ignored_masks)
627+ display.ungrab_key (binding.keycode, binding.modifiers | ignored_mask, xid);
628+ remove_bindings.add (binding);
629+ }
630+ }
631+
632+ // remove unbound keys
633+ bindings.remove_all (remove_bindings);
634+ }
635+
636+ /**
637+ * Unbind all registered bindings.
638+ */
639+ public void unbind_all ()
640+ {
641+ unowned X.Display display = Gdk.X11.get_default_xdisplay ();
642+ var xid = Gdk.X11.get_default_root_xwindow ();
643+
644+ // unbind all keys
645+ foreach (var binding in bindings)
646+ foreach (var ignored_mask in ignored_masks) {
647+ // if this is a key-released binding then remove corresponding modifiermask
648+ // for keycode to our modmask if it is a modifier which we added on bind
649+ if ((binding.modifiers & Gdk.ModifierType.RELEASE_MASK) != 0)
650+ binding.modifiers &= ~get_modmask_for_keycode (binding.keycode);
651+
652+ display.ungrab_key (binding.keycode, binding.modifiers | ignored_mask, xid);
653+ }
654+
655+ bindings.clear ();
656+ }
657+
658+ /**
659+ * Event filter method needed to fetch X.Events
660+ */
661+ [CCode (instance_pos = -1)]
662+ Gdk.FilterReturn xevent_filter (Gdk.XEvent gdk_xevent, Gdk.Event gdk_event)
663+ {
664+ var filter_return = Gdk.FilterReturn.CONTINUE;
665+ X.Event* xevent = (X.Event*) gdk_xevent;
666+
667+ if (xevent->type != X.EventType.KeyPress && xevent->type != X.EventType.KeyRelease)
668+ return filter_return;
669+
670+ // remove NumLock, CapsLock and ScrollLock from key state
671+ uint event_mods = (xevent->xkey.state & ~(ignored_masks[7]));
672+
673+ foreach (var binding in bindings) {
674+ if (xevent->xkey.keycode != binding.keycode)
675+ continue;
676+
677+ if ((xevent->type == X.EventType.KeyPress && (binding.modifiers == event_mods))
678+ || (xevent->type == X.EventType.KeyRelease
679+ && (binding.modifiers & Gdk.ModifierType.RELEASE_MASK) == Gdk.ModifierType.RELEASE_MASK
680+ && (binding.modifiers & ~Gdk.ModifierType.RELEASE_MASK) == event_mods)) {
681+
682+ binding.handler (*xevent);
683+
684+ // don't pass this event any futher
685+ filter_return = Gdk.FilterReturn.REMOVE;
686+ }
687+ }
688+
689+ return filter_return;
690+ }
691+
692+ /**
693+ * Convert the given accelerator to a modifier only accelerator.
694+ * This will convert the key to a modifier if possible and append it.
695+ *
696+ * @param accelerator accelerator parsable by Gtk.accelerator_parse
697+ */
698+ public static string convert_to_modifier_only (string accelerator)
699+ {
700+ uint keysym;
701+ Gdk.ModifierType modmask;
702+ Gtk.accelerator_parse (accelerator, out keysym, out modmask);
703+
704+ unowned X.Display display = Gdk.X11.get_default_xdisplay ();
705+ uint8 keycode = display.keysym_to_keycode (keysym);
706+
707+ if (keycode > 0)
708+ modmask |= get_modmask_for_keycode (keycode);
709+
710+ return get_accelerator_for_modmask (modmask);
711+ }
712+
713+ static string get_accelerator_for_modmask (Gdk.ModifierType modmask)
714+ {
715+ string result = "";
716+
717+ if ((modmask & Gdk.ModifierType.CONTROL_MASK) == Gdk.ModifierType.CONTROL_MASK)
718+ result += "<Ctrl>";
719+ if ((modmask & Gdk.ModifierType.MOD1_MASK) == Gdk.ModifierType.MOD1_MASK)
720+ result += "<Alt>";
721+ if ((modmask & Gdk.ModifierType.SHIFT_MASK) == Gdk.ModifierType.SHIFT_MASK)
722+ result += "<Shift>";
723+ if ((modmask & Gdk.ModifierType.META_MASK) == Gdk.ModifierType.META_MASK)
724+ result += "<AltGr>";
725+ if ((modmask & Gdk.ModifierType.HYPER_MASK) == Gdk.ModifierType.HYPER_MASK)
726+ result += "";
727+ if (((modmask & Gdk.ModifierType.SUPER_MASK) == Gdk.ModifierType.SUPER_MASK
728+ || (modmask & Gdk.ModifierType.MOD4_MASK) == Gdk.ModifierType.MOD4_MASK))
729+ result += "<Super>";
730+
731+ return result;
732+ }
733+
734+ /**
735+ * Convert keycode to ModifierType if it is a modifier
736+ * otherwise return 0x0
737+ */
738+ static Gdk.ModifierType get_modmask_for_keycode (uint keycode)
739+ {
740+ Gdk.ModifierType modmask;
741+
742+ unowned X.Display display = Gdk.X11.get_default_xdisplay ();
743+ var i = 0;
744+ var keysym = display.keycode_to_keysym ((uint8)keycode, i);
745+
746+ switch (keysym) {
747+ case Gdk.Key.Control_L:
748+ case Gdk.Key.Control_R:
749+ modmask = Gdk.ModifierType.CONTROL_MASK;
750+ break;
751+ case Gdk.Key.Alt_L:
752+ case Gdk.Key.Alt_R:
753+ modmask = Gdk.ModifierType.MOD1_MASK;
754+ break;
755+ case Gdk.Key.Shift_L:
756+ case Gdk.Key.Shift_R:
757+ modmask = Gdk.ModifierType.SHIFT_MASK;
758+ break;
759+ case Gdk.Key.Meta_L:
760+ case Gdk.Key.Meta_R:
761+ modmask = Gdk.ModifierType.META_MASK;
762+ break;
763+ case Gdk.Key.Hyper_L:
764+ case Gdk.Key.Hyper_R:
765+ modmask = Gdk.ModifierType.HYPER_MASK;
766+ break;
767+ case Gdk.Key.Super_L:
768+ case Gdk.Key.Super_R:
769+ // FIXME somethings is wrong with the SUPER modifier between the GDK and X values
770+ modmask = Gdk.ModifierType.MOD4_MASK; //Gdk.ModifierType.SUPER_MASK;
771+ break;
772+ default:
773+ modmask = 0x0;
774+ break;
775+ }
776+
777+ return modmask;
778+ }
779+ }
780+}
781
782=== modified file 'lib/Makefile.am'
783--- lib/Makefile.am 2016-02-28 12:06:16 +0000
784+++ lib/Makefile.am 2017-01-16 09:48:10 +0000
785@@ -65,6 +65,7 @@
786 DockRenderer.vala \
787 DragManager.vala \
788 HideManager.vala \
789+ KeybindingManager.vala \
790 PositionManager.vala \
791 DBus/Client.vala \
792 DBus/Interfaces.vala \
793
794=== modified file 'lib/libplank.symbols'
795--- lib/libplank.symbols 2016-04-10 09:00:49 +0000
796+++ lib/libplank.symbols 2017-01-16 09:48:10 +0000
797@@ -130,6 +130,7 @@
798 plank_dock_controller_get_hide_manager
799 plank_dock_controller_get_hover
800 plank_dock_controller_get_Items
801+plank_dock_controller_get_keybinding_manager
802 plank_dock_controller_get_launchers_folder
803 plank_dock_controller_get_name
804 plank_dock_controller_get_position_manager
805@@ -143,9 +144,11 @@
806 plank_dock_controller_set_drag_manager
807 plank_dock_controller_set_hide_manager
808 plank_dock_controller_set_hover
809+plank_dock_controller_set_keybinding_manager
810 plank_dock_controller_set_position_manager
811 plank_dock_controller_set_renderer
812 plank_dock_controller_set_window
813+plank_dock_controller_virtual_click_item_at
814 plank_dock_element_accept_drop
815 plank_dock_element_as_uri
816 plank_dock_element_can_accept_drop
817@@ -289,7 +292,10 @@
818 plank_dock_preferences_get_HideDelay
819 plank_dock_preferences_get_HideMode
820 plank_dock_preferences_get_IconSize
821+plank_dock_preferences_get_ItemAccelerator
822+plank_dock_preferences_get_ItemOptionAccelerator
823 plank_dock_preferences_get_ItemsAlignment
824+plank_dock_preferences_get_KeybindingUnhideDelay
825 plank_dock_preferences_get_LockItems
826 plank_dock_preferences_get_Monitor
827 plank_dock_preferences_get_Offset
828@@ -313,7 +319,10 @@
829 plank_dock_preferences_set_HideDelay
830 plank_dock_preferences_set_HideMode
831 plank_dock_preferences_set_IconSize
832+plank_dock_preferences_set_ItemAccelerator
833+plank_dock_preferences_set_ItemOptionAccelerator
834 plank_dock_preferences_set_ItemsAlignment
835+plank_dock_preferences_set_KeybindingUnhideDelay
836 plank_dock_preferences_set_LockItems
837 plank_dock_preferences_set_Monitor
838 plank_dock_preferences_set_Offset
839@@ -332,14 +341,19 @@
840 plank_dock_renderer_get_local_cursor
841 plank_dock_renderer_get_theme
842 plank_dock_renderer_get_type
843+plank_dock_renderer_get_VisibleKeybinding
844 plank_dock_renderer_get_zoom_in_progress
845+plank_dock_renderer_hide_keybindings
846 plank_dock_renderer_initialize
847 plank_dock_renderer_new
848 plank_dock_renderer_reset_buffers
849+plank_dock_renderer_set_VisibleKeybinding
850+plank_dock_renderer_show_keybindings
851 plank_dock_renderer_update_local_cursor
852 plank_dock_theme_construct
853 plank_dock_theme_create_background
854 plank_dock_theme_create_indicator
855+plank_dock_theme_create_keybinding
856 plank_dock_theme_create_urgent_glow
857 plank_dock_theme_draw_active_glow
858 plank_dock_theme_draw_item_count
859@@ -473,6 +487,15 @@
860 plank_item_factory_make_element
861 plank_item_factory_new
862 plank_item_state_get_type
863+plank_keybinding_get_type
864+plank_keybinding_manager_bind
865+plank_keybinding_manager_construct
866+plank_keybinding_manager_convert_to_modifier_only
867+plank_keybinding_manager_get_type
868+plank_keybinding_manager_initialize
869+plank_keybinding_manager_new
870+plank_keybinding_manager_unbind
871+plank_keybinding_manager_unbind_all
872 plank_logger_get_DisplayLevel
873 plank_logger_get_type
874 plank_logger_initialize

Subscribers

People subscribed via source and target branches

to status/vote changes: