Function calls work fine, the problem is, that inside the typewrite's setTimeout callback, (when you recall typewrite), you forgotten to pass the callback and its parameters to itself, so they are defined only during the first iteration.
To make it work, pass all arguments to itself:
var txtElems = document.querySelectorAll("[data-txt]");
txtElems = Array.from(txtElems);
typewriteAll(txtElems, 70);
function typewriteAll(elemArr, delay) {
if (elemArr.length) {
typewrite(
elemArr[0],
elemArr[0].dataset.txt,
delay,
typewriteAll, elemArr.slice(1), delay
);
}
}
function typewrite(Elem, t, delay, func, arg1, arg2) {
let txt = String(t);
if(txt != ""){
Elem.innerHTML += txt[0];
setTimeout(() => {
typewrite(
Elem,
txt.slice(1, txt.length),
delay,
//here:
func,
arg1,
arg2
)
}, delay)
} else {
setTimeout(() => {
Elem.setAttribute("typing", "end");
func(arg1, arg2)
}, 10 * delay)
}
}
<div data-txt="Some text to type"></div>
<div data-txt="Some more text to type..."></div>
And if you're creating typewriter effects, I highly recommend you to use setInterval and ES6 generator functions, as they make the code much readable... and helps you avoid making such mistakes:
function typewrite(element, text, delay){
return new Promise((resolve, reject) => {
const iterator = (function*() {
try{
for(const letter of text){
element.textContent += letter
yield
}
element.setAttribute("typing", "end");
resolve()
}catch(e){
reject(e)
}finally{
clearTimeout(interval)
}
})()
const interval = setInterval(() => iterator.next(), delay);
iterator.next()
})
}
function typewriteAll(elems, delay){
return elems.reduce((acc,elem) => acc.then(() => typewrite(elem, elem.dataset.txt, delay)), Promise.resolve())
}
var txtElems = document.querySelectorAll("[data-txt]");
txtElems = Array.from(txtElems);
typewriteAll(txtElems, 70)
<div data-txt="Some text to type"></div>
<div data-txt="Some more text to type..."></div>
typewritea fat arrow function?typewritein there where you’re not passing a forth argument…!?thisinside the function, which could cause similar issues...