Юзай промисы и async/await (синтаксический сахар). и setInterval/setTimeout
Поясню: setInterval и setTimeout - они асинхронные, и работают с коллбеками (которые вызываются по интервалу или таймауту).
Но чтобы не упереться в callback hell (большая вложенность коллбэков), можно обернуть эти функции в промисы. А вызывать сами
промисы с помощью синтаксического сахара async/await.
Первоначально замени свой цикл на вышеупомянутие функции с коллбэками, а потом займешься украшательством, если понадобится.
Если коллбек один, и внутри вложенных коллбеков нет, то промисы и асинк не нужны, и так сойдет )