Когда я использую, requestAnimationFrame
чтобы сделать некоторую встроенную поддерживаемую анимацию с кодом ниже:
var support = {
animationFrame: window.requestAnimationFrame ||
window.mozRequestAnimationFrame ||
window.webkitRequestAnimationFrame ||
window.msRequestAnimationFrame ||
window.oRequestAnimationFrame
};
support.animationFrame(function() {}); //error
support.animationFrame.call(window, function() {}); //right
Прямо зовет support.animationFrame
, даст ...
Uncaught TypeError: незаконный вызов
в хроме. Зачем?
источник
myObj.myAlert('this is an alert');
недопустим. Правильное использование естьmyObj.myAlert.call(window, 'this is an alert')
. Пожалуйста, прочитайте ответы правильно и постарайтесь понять это.Вы также можете использовать:
источник
var realReplaceState = history.replaceState.bind(history);
.bind(localStorage)
, а не.bind(window)
.Когда вы выполняете метод (т.е. функцию, назначенную объекту), внутри него вы можете использовать
this
переменную для ссылки на этот объект, например:Если вы назначаете метод из одного объекта в другой, его
this
переменная ссылается на новый объект, например:То же самое происходит, когда вы назначаете
requestAnimationFrame
методwindow
другому объекту. Встроенные функции, такие как эта, имеют встроенную защиту от выполнения их в другом контексте.Есть
Function.prototype.call()
функция, которая позволяет вызывать функцию в другом контексте. Вы просто должны передать его (объект, который будет использоваться в качестве контекста) в качестве первого параметра этому методу. Напримерalert.call({})
даетTypeError: Illegal invocation
. Тем не менее,alert.call(window)
работает отлично, потому что теперьalert
выполняется в своем первоначальном объеме.Если вы используете
.call()
со своим объектом так:это работает нормально, потому что
requestAnimationFrame
выполняется в областиwindow
вместо вашего объекта.Однако использовать
.call()
каждый раз, когда вы хотите вызвать этот метод, не очень элегантное решение. Вместо этого вы можете использоватьFunction.prototype.bind()
. Он имеет аналогичный эффект.call()
, но вместо вызова функции он создает новую функцию, которая всегда будет вызываться в указанном контексте. Например:Единственным недостатком
Function.prototype.bind()
является то, что это часть ECMAScript 5, которая не поддерживается в IE <= 8 . К счастью, на MDN есть полифилл .Как вы, вероятно, уже поняли, вы можете использовать,
.bind()
чтобы всегда выполнятьrequestAnimationFrame
в контекстеwindow
. Ваш код может выглядеть так:Тогда вы можете просто использовать
support.animationFrame(function() {});
.источник