forked from podgorniy/javascript-toolbox
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathdecorate.js
More file actions
136 lines (115 loc) · 3.08 KB
/
decorate.js
File metadata and controls
136 lines (115 loc) · 3.08 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
/*
Small version
Adds function before or after another
*/
function decorate (initial, decorate_before, decorate_after) {
return function () {
var initial_call_result;
if (typeof decorate_before === 'function') {
decorate_before.apply(this, arguments);
}
initial_call_result = initial.apply(this, arguments);
if (typeof decorate_after === 'function') {
decorate_after.apply(this, arguments);
}
return initial_call_result;
};
}
/*
Example of use
document.write = decorate (document.write, function () {
console.log(this === document);// true;
}, function () {
console.log('DOM is updated');
});
document.write = decorate (document.write, null, function () {
console.log('After document.write');
});
*/
/*
1. add function before and after modified
2. change arguments, passed to modified
3. prevent modified from running
4. change modified returning value
*/
function decorate (initial, decorate_before, decorate_after) {
return function () {
var initial_call_result,
updated_params,
updated_result;
if (typeof decorate_before === 'function') {
updated_params = decorate_before.apply(this, arguments);
if (!updated_params) {
return;
}
}
initial_call_result = initial.apply(this, updated_params || arguments);
if (typeof decorate_after === 'function') {
updated_result = decorate_after.apply(this, arguments);
}
return updated_result === undefined ? initial_call_result : updated_result;
};
}
/*
example
// add before (logging calls before execution)
document.write = decorate(document.write, function () {
console.log('document.write called with', arguments);
return arguments;
});
// add after (logging call after execution)
document.write = decorate(document.write, null, function () {
console.log('after document.write');
});
// add before and after (profile calls)
document.write = decorate(document.write, function () {
console.profile('document.write');
return arguments;
}, function () {
console.profileEnd('document.write');
});
// prevent from executing
document.write = decorate(document.write, function () {
if (dom_is_ready()) {
return false;
} else {
return arguments;
}
});
// modify arguments
document.write = decorate(document.write, function (str) {
var args;
args = [replace_divs(str)];
return args;
}, document.write);
// change returning value
document.write = decorate(document.write, null, function () {
if (dom_is_ready()){
return true;
}
});
*/
function decorate (func, before, after) {
var res;
var key;
res = function () {
var temp_res;
var alternative_args;
var alternative_res;
if (typeof before === 'function') {
before.apply(this, arguments);
}
temp_res = func.apply(this, arguments);
if (typeof after === 'function') {
after.apply(this, arguments);
}
return temp_res;
}
res.prototype = func.prototype;
for (key in func) {
if (func.hasOwnProperty(key)) {
res[key] = func[key];
}
}
return res;
}