signalTracker: Provide monkey-patching for (dis)connectObject()

The module exports a `addObjectSignalMethods()` method that extends
the provided prototype with `connectObject()` and `disconnectObject()`
methods.

In its simplest form, `connectObject()` looks like the regular
`connect()` method, except for an additional parameter:

```js
    this._button.connectObject('clicked',
        () => this._onButtonClicked(), this);
```

The additional object can be used to disconnect all handlers on the
instance that were connected with that object, similar to
`g_signal_handlers_disconnect_by_data()` (which cannot be used
from introspection).

For objects that are subclasses of Clutter.Actor, that will happen
automatically when the actor is destroyed, similar to
`g_signal_connect_object()`.

Finally, `connectObject()` allows to conveniently connect multiple
signals at once, similar to `g_object_connect()`:

```js
    this._toggleButton.connect(
        'clicked', () => this._onClicked(),
        'notify::checked', () => this._onChecked(), this);
```

Part-of: <https://gitlab.gnome.org/GNOME/gnome-shell/-/merge_requests/1953>
This commit is contained in:
Florian Müllner
2021-08-16 00:01:40 +02:00
committed by Marge Bot
parent 96df498450
commit f45ccc9143
5 changed files with 316 additions and 0 deletions

View File

@ -26,7 +26,9 @@ try {
const { Clutter, Gio, GLib, GObject, Meta, Polkit, Shell, St } = imports.gi;
const Gettext = imports.gettext;
const Signals = imports.signals;
const System = imports.system;
const SignalTracker = imports.misc.signalTracker;
Gio._promisify(Gio.DataInputStream.prototype, 'fill_async');
Gio._promisify(Gio.DataInputStream.prototype, 'read_line_async');
@ -324,6 +326,25 @@ function init() {
GObject.gtypeNameBasedOnJSPath = true;
GObject.Object.prototype.connectObject = function (...args) {
SignalTracker.connectObject(this, ...args);
};
GObject.Object.prototype.connect_object = function (...args) {
SignalTracker.connectObject(this, ...args);
};
GObject.Object.prototype.disconnectObject = function (...args) {
SignalTracker.disconnectObject(this, ...args);
};
GObject.Object.prototype.disconnect_object = function (...args) {
SignalTracker.disconnectObject(this, ...args);
};
const _addSignalMethods = Signals.addSignalMethods;
Signals.addSignalMethods = function (prototype) {
_addSignalMethods(prototype);
SignalTracker.addObjectSignalMethods(prototype);
};
// Miscellaneous monkeypatching
_patchContainerClass(St.BoxLayout);