@@ -2,6 +2,7 @@ const { ipcRenderer, ipcMain } = require("electron");
22
33const defaultConfig = require ( "./defaults" ) ;
44const { getOptions, setOptions, setMenuOptions } = require ( "./plugins" ) ;
5+ const { sendToFront } = require ( "../providers/app-controls" ) ;
56
67const activePlugins = { } ;
78/**
@@ -58,6 +59,9 @@ module.exports.PluginConfig = class PluginConfig {
5859 #defaultConfig;
5960 #enableFront;
6061
62+ #subscribers = { } ;
63+ #allSubscribers = [ ] ;
64+
6165 constructor ( name , { enableFront = false , initialOptions = undefined } = { } ) {
6266 const pluginDefaultConfig = defaultConfig . plugins [ name ] || { } ;
6367 const pluginConfig = initialOptions || getOptions ( name ) || { } ;
@@ -80,11 +84,13 @@ module.exports.PluginConfig = class PluginConfig {
8084
8185 set = ( option , value ) => {
8286 this . #config[ option ] = value ;
87+ this . #onChange( option ) ;
8388 this . #save( ) ;
8489 } ;
8590
8691 toggle = ( option ) => {
8792 this . #config[ option ] = ! this . #config[ option ] ;
93+ this . #onChange( option ) ;
8894 this . #save( ) ;
8995 } ;
9096
@@ -93,7 +99,18 @@ module.exports.PluginConfig = class PluginConfig {
9399 } ;
94100
95101 setAll = ( options ) => {
96- this . #config = { ...this . #config, ...options } ;
102+ if ( ! options || typeof options !== "object" )
103+ throw new Error ( "Options must be an object." ) ;
104+
105+ let changed = false ;
106+ for ( const [ key , val ] of Object . entries ( options ) ) {
107+ if ( this . #config[ key ] !== val ) {
108+ this . #config[ key ] = val ;
109+ this . #onChange( key , false ) ;
110+ changed = true ;
111+ }
112+ }
113+ if ( changed ) this . #allSubscribers. forEach ( ( fn ) => fn ( this . #config) ) ;
97114 this . #save( ) ;
98115 } ;
99116
@@ -109,31 +126,80 @@ module.exports.PluginConfig = class PluginConfig {
109126 setAndMaybeRestart = ( option , value ) => {
110127 this . #config[ option ] = value ;
111128 setMenuOptions ( this . #name, this . #config) ;
129+ this . #onChange( option ) ;
130+ } ;
131+
132+ subscribe = ( valueName , fn ) => {
133+ this . #subscribers[ valueName ] = fn ;
134+ } ;
135+
136+ subscribeAll = ( fn ) => {
137+ this . #allSubscribers. push ( fn ) ;
112138 } ;
113139
114140 /** Called only from back */
115141 #save( ) {
116142 setOptions ( this . #name, this . #config) ;
117143 }
118144
145+ #onChange( valueName , single = true ) {
146+ this . #subscribers[ valueName ] ?. ( this . #config[ valueName ] ) ;
147+ if ( single ) this . #allSubscribers. forEach ( ( fn ) => fn ( this . #config) ) ;
148+ }
149+
119150 #setupFront( ) {
151+ const ignoredMethods = [ "subscribe" , "subscribeAll" ] ;
152+
120153 if ( process . type === "renderer" ) {
121154 for ( const [ fnName , fn ] of Object . entries ( this ) ) {
122- if ( typeof fn !== "function" ) return ;
155+ if ( typeof fn !== "function" || fn . name in ignoredMethods ) return ;
123156 this [ fnName ] = async ( ...args ) => {
124157 return await ipcRenderer . invoke (
125158 `${ this . name } -config-${ fnName } ` ,
126159 ...args ,
127160 ) ;
128161 } ;
162+
163+ this . subscribe = ( valueName , fn ) => {
164+ if ( valueName in this . #subscribers) {
165+ console . error ( `Already subscribed to ${ valueName } ` ) ;
166+ }
167+ this . #subscribers[ valueName ] = fn ;
168+ ipcRenderer . on (
169+ `${ this . name } -config-changed-${ valueName } ` ,
170+ ( _ , value ) => {
171+ fn ( value ) ;
172+ } ,
173+ ) ;
174+ ipcRenderer . send ( `${ this . name } -config-subscribe` , valueName ) ;
175+ } ;
176+
177+ this . subscribeAll = ( fn ) => {
178+ ipcRenderer . on ( `${ this . name } -config-changed` , ( _ , value ) => {
179+ fn ( value ) ;
180+ } ) ;
181+ ipcRenderer . send ( `${ this . name } -config-subscribe-all` ) ;
182+ } ;
129183 }
130184 } else if ( process . type === "browser" ) {
131185 for ( const [ fnName , fn ] of Object . entries ( this ) ) {
132- if ( typeof fn !== "function" ) return ;
186+ if ( typeof fn !== "function" || fn . name in ignoredMethods ) return ;
133187 ipcMain . handle ( `${ this . name } -config-${ fnName } ` , ( _ , ...args ) => {
134188 return fn ( ...args ) ;
135189 } ) ;
136190 }
191+
192+ ipcMain . on ( `${ this . name } -config-subscribe` , ( _ , valueName ) => {
193+ this . subscribe ( valueName , ( value ) => {
194+ sendToFront ( `${ this . name } -config-changed-${ valueName } ` , value ) ;
195+ } ) ;
196+ } ) ;
197+
198+ ipcMain . on ( `${ this . name } -config-subscribe-all` , ( ) => {
199+ this . subscribeAll ( ( value ) => {
200+ sendToFront ( `${ this . name } -config-changed` , value ) ;
201+ } ) ;
202+ } ) ;
137203 }
138204 }
139205} ;
0 commit comments