我觉得我想得太过分了,但是我坚持了下来。 JavaScript是否有能力允许其他功能(来自相同或不同的JS文件)与功能挂钩?
澄清一下,如果我在编写的函数中创建一个数组,是否可以在解析之前允许其他JS文件挂接该数组以修改该数组?还是我需要构建某种系统来管理所有“挂钩”?如果可能的话,我想避免使用全局窗口变量,但是会起作用。
为了争辩,我们假设它们按照我列出的顺序运行(忽略我在此处创建的竞争条件)。
var animals = ['cat', 'dog'];
animals = hookIntoThis(animals); //Allow other functions or files to add/modify animals to the array here
console.log(animals); //--> "cat", "dog", "elephant"
hookIntoThis()
实际上并不是对任何东西的引用,而这正是我要让其他函数/文件(如果存在)修改数组的地方。
function addMoreAnimals(animals){ //This would somehow listen for that hook from main.js
animals.push('elephant');
animals.push('lion');
return animals;
}
function noLions(animals){ //This would also hook into that function from main.js to modify the array
if ( animals.indexOf('lion') >= 0 ){
animals.splice(animals.indexOf('lion'), 1); //Just for the sake of example
}
return animals;
}
起初,我以为自定义DOM事件/侦听器会起作用,但是(据我所知)这是单向的。我可以触发甚至将动物数组传递给DOM事件,但是除非使用全局窗口变量,否则我将无法获取任何数据 back 。
如果这是一个过于简单的概念和/或重复的问题,我深表歉意。在发布之前,我做了很多搜索。
答案 0 :(得分:0)
我认为,如果main
不知道哪些其他模块将要修改animals
,自定义事件侦听器就是正确的选择。
如果您知道所有钩子将同步执行,则可以在主线程完成后让main
在微任务中完成其主要工作(修改后),例如:
// main.js
let modifiableAnimals = ['cat', 'dog'];
window.addEventListener('customHook', ({ detail: modifyFn }) => {
modifiableAnimals = modifyFn(modifiableAnimals);
});
Promise.resolve()
.then(() => {
console.log(modifiableAnimals);
});
// other.js
window.dispatchEvent(
new CustomEvent(
'customHook',
{
detail: (animals) => {
animals.push('elephant');
animals.push('lion');
return animals;
}
}
)
);
// whatever.js
window.dispatchEvent(
new CustomEvent(
'customHook',
{
detail: (animals) => {
if ( animals.indexOf('lion') >= 0 ){
animals.splice(animals.indexOf('lion'), 1); //Just for the sake of example
}
return animals;
}
}
)
);
如果您知道现有数组仅将被变异(并且不必重新分配),则可以对其进行简化:
// main.js
const modifiableAnimals = ['cat', 'dog'];
window.addEventListener('customHook', ({ detail: modifyFn }) => {
modifyFn(modifiableAnimals);
});
Promise.resolve()
.then(() => {
console.log(modifiableAnimals);
});
// other.js
window.dispatchEvent(
new CustomEvent(
'customHook',
{
detail: (animals) => {
animals.push('elephant');
animals.push('lion');
}
}
)
);
// whatever.js
window.dispatchEvent(
new CustomEvent(
'customHook',
{
detail: (animals) => {
if ( animals.indexOf('lion') >= 0 ){
animals.splice(animals.indexOf('lion'), 1); //Just for the sake of example
}
}
}
)
);
这仍然很奇怪,IMO。如果可能的话,我考虑与main.js
和其他文件建立一个 else 接口,并使用处理程序调用{{1}}函数:
main.js