// -*- mode: js; js-indent-level: 4; indent-tabs-mode: nil -*- // SPDX-License-Identifier: MIT OR LGPL-2.0-or-later // SPDX-FileCopyrightText: 2020 Philip Chimento /* exported _checkAccessors, _registerType */ // This is a helper module in which to put code that is common between the // legacy GObject.Class system and the new GObject.registerClass system. var _registerType = Symbol('GObject register type hook'); function _generateAccessors(pspec, propdesc, GObject) { const {name, flags} = pspec; const readable = flags & GObject.ParamFlags.READABLE; const writable = flags & GObject.ParamFlags.WRITABLE; if (!propdesc) { propdesc = { configurable: true, enumerable: true, }; } if (readable && writable) { if (!propdesc.get && !propdesc.set) { const privateName = Symbol(`__autogeneratedAccessor__${name}`); const defaultValue = pspec.get_default_value(); propdesc.get = function () { if (!(privateName in this)) this[privateName] = defaultValue; return this[privateName]; }; propdesc.set = function (value) { if (value !== this[privateName]) { this[privateName] = value; this.notify(name); } }; } else if (!propdesc.get) { propdesc.get = function () { throw new Error(`setter defined without getter for property ${name}`); }; } else if (!propdesc.set) { propdesc.set = function () { throw new Error(`getter defined without setter for property ${name}`); }; } } else if (readable && !propdesc.get) { propdesc.get = function () { throw new Error(`missing getter for read-only property ${name}`); }; } else if (writable && !propdesc.set) { propdesc.set = function () { throw new Error(`missing setter for write-only property ${name}`); }; } return propdesc; } function _checkAccessors(proto, pspec, GObject) { const {name, flags} = pspec; if (flags & GObject.ParamFlags.CONSTRUCT_ONLY) return; const underscoreName = name.replace(/-/g, '_'); const camelName = name.replace(/-([a-z])/g, match => match[1].toUpperCase()); let propdesc = Object.getOwnPropertyDescriptor(proto, name); let dashPropdesc = propdesc, underscorePropdesc, camelPropdesc; const nameIsCompound = name.includes('-'); if (nameIsCompound) { underscorePropdesc = Object.getOwnPropertyDescriptor(proto, underscoreName); camelPropdesc = Object.getOwnPropertyDescriptor(proto, camelName); if (!propdesc) propdesc = underscorePropdesc; if (!propdesc) propdesc = camelPropdesc; } const readable = flags & GObject.ParamFlags.READABLE; const writable = flags & GObject.ParamFlags.WRITABLE; if (!propdesc || (readable && !propdesc.get) || (writable && !propdesc.set)) propdesc = _generateAccessors(pspec, propdesc, GObject); if (!dashPropdesc) Object.defineProperty(proto, name, propdesc); if (nameIsCompound) { if (!underscorePropdesc) Object.defineProperty(proto, underscoreName, propdesc); if (!camelPropdesc) Object.defineProperty(proto, camelName, propdesc); } }