Will I need to hire a coder to create code that produces the typewriter effect, as seen in this video, or is there a similar effect already available within Wix Studio for non-coders? Anything where a word is replaced. Here’s a video clip. Ignore the mouse pointer, just the text and the cursor line are what I’d like. Typewriter-Effect - TechSmith Screencast
And if i would generate a type writer effect, maybe it would look something like —>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Matrix Typewriter Interface</title>
<style>
@import url('https://fonts.googleapis.com/css2?family=VT323&display=swap');
:root {
--matrix-green: #00FF41;
--matrix-dark-green: #00CC33;
--matrix-black: #0A0A0A;
--matrix-light-green: #00EE00;
}
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
body {
font-family: 'VT323', monospace;
min-height: 100vh;
display: flex;
justify-content: center;
align-items: center;
overflow: hidden;
background-color: var(--matrix-black);
color: var(--matrix-green);
position: relative;
}
/* Matrix Rain Background */
.matrix-rain {
position: fixed;
top: 0;
left: 0;
width: 100%;
height: 100%;
pointer-events: none;
overflow: hidden;
z-index: -1;
}
.matrix-column {
position: absolute;
width: 15px; /* Width of each column */
display: flex;
flex-direction: column;
white-space: pre;
}
.matrix-char {
color: var(--matrix-green);
font-size: 20px;
line-height: 20px; /* Adjust line-height to prevent gaps */
opacity: 0;
animation: fadeInOut 2s linear forwards; /* Controlled by JS */
}
.matrix-char.bright {
color: var(--matrix-light-green);
}
@keyframes fadeInOut {
0% { opacity: 0; }
20% { opacity: 1; }
80% { opacity: 1; }
100% { opacity: 0; }
}
/* Terminal Container */
.terminal-container {
width: 90%;
max-width: 900px;
background: rgba(0, 0, 0, 0.8);
border: 2px solid var(--matrix-dark-green);
box-shadow: 0 0 20px var(--matrix-dark-green), inset 0 0 10px var(--matrix-dark-green);
padding: 30px;
border-radius: 10px;
position: relative;
z-index: 1;
}
.terminal-container::before {
content: '';
position: absolute;
top: -5px;
left: -5px;
right: -5px;
bottom: -5px;
border: 2px solid var(--matrix-light-green);
border-radius: 12px;
opacity: 0.3;
animation: terminalGlow 3s infinite alternate;
z-index: -1;
}
@keyframes terminalGlow {
0% { box-shadow: 0 0 10px var(--matrix-light-green); }
100% { box-shadow: 0 0 30px var(--matrix-light-green), 0 0 40px rgba(0, 255, 65, 0.5); }
}
.terminal-header {
display: flex;
justify-content: space-between;
align-items: center;
margin-bottom: 25px;
padding-bottom: 15px;
border-bottom: 1px dashed var(--matrix-dark-green);
}
.terminal-title {
font-size: 1.5em;
color: var(--matrix-light-green);
text-shadow: 0 0 10px var(--matrix-light-green);
}
.terminal-status {
font-size: 1.1em;
color: var(--matrix-green);
text-shadow: 0 0 5px var(--matrix-green);
}
.text-display {
min-height: 200px;
background: rgba(0, 0, 0, 0.6);
border: 1px solid var(--matrix-dark-green);
padding: 20px;
white-space: pre-wrap;
word-wrap: break-word;
font-size: 1.2em;
line-height: 1.4;
color: var(--matrix-green);
box-shadow: inset 0 0 8px var(--matrix-dark-green);
overflow-y: auto; /* Allow scrolling for longer texts */
max-height: 400px; /* Limit height */
}
#typewriter-text {
display: inline;
}
.char.typed {
opacity: 1;
transition: opacity 0.05s ease-in;
}
.char.deleted {
opacity: 0;
transition: opacity 0.05s ease-out;
}
.cursor {
display: inline-block;
background-color: var(--matrix-light-green);
width: 8px;
height: 1.2em;
margin-left: 5px;
animation: matrixBlink 0.7s step-end infinite;
box-shadow: 0 0 10px var(--matrix-light-green);
}
@keyframes matrixBlink {
from, to { background-color: transparent; }
50% { background-color: var(--matrix-light-green); }
}
.stats-panel {
display: flex;
justify-content: space-around;
margin-top: 25px;
padding: 15px;
border-top: 1px dashed var(--matrix-dark-green);
color: var(--matrix-green);
font-size: 1em;
}
.stat-item {
text-align: center;
padding: 5px 10px;
border: 1px solid rgba(0, 255, 65, 0.3);
border-radius: 5px;
}
.stat-item span {
color: var(--matrix-light-green);
font-weight: bold;
text-shadow: 0 0 5px var(--matrix-light-green);
}
/* Controls */
.controls {
position: fixed;
bottom: 30px;
right: 30px;
display: grid;
grid-template-columns: repeat(2, 1fr); /* Two columns for buttons */
gap: 15px;
background: rgba(0, 0, 0, 0.9);
border: 2px solid var(--matrix-dark-green);
box-shadow: 0 0 15px var(--matrix-dark-green), inset 0 0 8px var(--matrix-dark-green);
padding: 20px;
border-radius: 10px;
z-index: 1000;
}
.control-btn, .control-select {
background-color: var(--matrix-dark-green);
color: var(--matrix-light-green);
border: 1px solid var(--matrix-green);
padding: 12px 18px;
font-size: 1em;
font-family: 'VT323', monospace;
cursor: pointer;
border-radius: 5px;
box-shadow: 0 0 8px rgba(0, 255, 65, 0.5);
transition: all 0.2s ease-in-out;
}
.control-btn:hover, .control-select:hover {
background-color: var(--matrix-green);
color: var(--matrix-black);
box-shadow: 0 0 15px var(--matrix-light-green);
transform: translateY(-2px);
}
.control-btn:active, .control-select:active {
transform: translateY(0);
box-shadow: inset 0 0 5px var(--matrix-light-green);
background-color: var(--matrix-light-green);
}
.control-select {
-webkit-appearance: none;
-moz-appearance: none;
appearance: none;
text-align: center;
padding-right: 30px; /* Space for custom arrow */
background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='%2300FF41'%3E%3Cpath d='M7 10l5 5 5-5z'/%3E%3C/svg%3E");
background-repeat: no-repeat;
background-position: right 8px center;
background-size: 20px;
}
/* Audio Visualizer (simple) */
.audio-visualizer {
position: absolute;
bottom: 0;
left: 0;
right: 0;
height: 3px;
background: linear-gradient(90deg, transparent, var(--matrix-green), var(--matrix-light-green), var(--matrix-green), transparent);
opacity: 0;
animation: visualizePulse 0.15s ease-out;
border-radius: 1.5px;
}
@keyframes visualizePulse {
0% { transform: scaleX(0); opacity: 0.5; }
50% { transform: scaleX(1); opacity: 1; }
100% { transform: scaleX(0); opacity: 0.5; }
}
/* Media Queries for Responsiveness */
@media (max-width: 768px) {
.terminal-container {
padding: 20px;
}
.terminal-title {
font-size: 1.2em;
}
.terminal-status {
font-size: 1em;
}
.text-display {
font-size: 1em;
padding: 15px;
min-height: 150px;
}
.controls {
bottom: 15px;
right: 15px;
grid-template-columns: 1fr; /* Single column on smaller screens */
padding: 15px;
}
.control-btn, .control-select {
padding: 10px 15px;
}
.stats-panel {
flex-direction: column;
gap: 10px;
}
}
</style>
</head>
<body>
<div class="matrix-rain" id="matrix-rain"></div>
<div class="terminal-container">
<div class="terminal-header">
<div class="terminal-title">>>> MTRX_OS v6.0_STABLE</div>
<div class="terminal-status" id="system-status">[ STATUS: ONLINE ]</div>
</div>
<div class="text-display">
<span id="typewriter-text"></span><span class="cursor" id="cursor"></span>
</div>
<div class="stats-panel">
<div class="stat-item">CHARACTERS: <span id="char-count">0</span></div>
<div class="stat-item">WPM: <span id="wpm">0</span></div>
<div class="stat-item">PROGRESS: <span id="progress">0</span>%</div>
<div class="stat-item">OPS_COUNT: <span id="op-count">0</span></div>
</div>
<div class="audio-visualizer" id="visualizer"></div>
</div>
<div class="controls">
<button class="control-btn" data-action="pause" title="Pause">PAUSE</button>
<button class="control-btn" data-action="resume" title="Resume">RESUME</button>
<button class="control-btn" data-action="next" title="Next Line">NEXT</button>
<button class="control-btn" data-action="restart" title="Restart Session">RESTART</button>
<button class="control-btn" data-action="toggleSpeed" title="Adjust Speed">SPEED</button>
<button class="control-btn" data-action="toggleSound" title="Toggle Sound">SOUND</button>
<select class="control-select" id="theme-select" title="Switch Theme">
<option value="matrix">MATRIX</option>
<option value="data_stream">DATA STREAM</option>
<option value="glitch">GLITCH</option>
</select>
<select class="control-select" id="sound-select" title="Select Sound Type">
<option value="synth">SYNTH</option>
<option value="digital">DIGITAL</option>
<option value="binary">BINARY</option>
</select>
</div>
<script>
document.addEventListener('DOMContentLoaded', () => {
class MatrixTypewriter {
constructor() {
this.textElement = document.getElementById('typewriter-text');
this.cursorElement = document.getElementById('cursor');
this.visualizer = document.getElementById('visualizer');
this.charCountElement = document.getElementById('char-count');
this.wpmElement = document.getElementById('wpm');
this.progressElement = document.getElementById('progress');
this.opCountElement = document.getElementById('op-count');
this.systemStatusElement = document.getElementById('system-status');
this.texts = [
"INITIALIZING_MATRIX_PROTOCOL_V6.0...",
"ESTABLISHING_NEURAL_INTERFACE_LINK...",
"RECALIBRATING_REALITY_SIMULATOR...",
"ACCESSING_ANOMALY_DATABASE_PHI-7...",
"EXECUTING_CODE_INJECTION_SEQUENCE...",
"DETECTING_UNAUTHORIZED_PRESENCE...",
"ALERT: AGENT_PROGRAM_DETECTED. EVASIVE_MANEUVERS_RECOMMENDED.",
"DECRYPTING_SECURE_COMMUNICATION_CHANNEL_0110100001101001...",
"SYNCHRONIZING_DATA_STREAM_WITH_EXTERNAL_NETWORK...",
"THE_CHOICE_IS_YOURS:_RED_PILL_OR_BLUE_PILL?",
"WELCOME_TO_THE_REAL_WORLD,_NEO."
];
this.currentTextIndex = 0;
this.currentCharIndex = 0;
this.isDeleting = false;
this.isPaused = false;
this.soundEnabled = true;
this.currentSoundType = 'synth';
this.operationCount = 0; // Renamed particleCount for Matrix theme
this.startTime = Date.now();
this.totalCharsProcessed = 0; // Renamed totalCharsTyped
this.timeoutId = null;
this.speeds = [
{ name: "SLOW", multiplier: 0.3 },
{ name: "STANDARD", multiplier: 1 },
{ name: "RAPID", multiplier: 2.5 },
{ name: "HYPER", multiplier: 5 }
];
this.currentSpeedIndex = 1; // Starts at "STANDARD"
this.themes = ['matrix', 'data_stream', 'glitch']; // Matrix specific themes
this.currentTheme = 'matrix';
this.config = {
baseTypingSpeed: 60,
typingVariance: 40,
baseDeletingSpeed: 20,
deletingVariance: 15,
delayBeforeDelete: 2500,
delayBeforeNext: 800,
punctuationPause: 300,
punctuationChance: 0.7,
punctuationChars: ['_', '.', ':', '!', '?'] // Matrix-style "punctuation"
};
this.setupAudioContext();
this.initMatrixRain();
this.setupEventListeners();
this.updateSpeedStatus();
this.setTheme(this.currentTheme);
this.start();
}
setupAudioContext() {
this.audioContext = null;
try {
this.audioContext = new (window.AudioContext || window.webkitAudioContext)();
const resumeAudio = () => {
if (this.audioContext && this.audioContext.state === 'suspended') {
this.audioContext.resume().then(() => {
console.log('AudioContext resumed successfully.');
document.removeEventListener('click', resumeAudio);
document.removeEventListener('keydown', resumeAudio);
});
}
};
document.addEventListener('click', resumeAudio);
document.addEventListener('keydown', resumeAudio);
} catch (e) {
console.error('Web Audio API not supported:', e);
this.soundEnabled = false;
}
// Matrix-themed sound profiles
this.soundProfiles = {
synth: [
{ freq: 440, type: 'sine', duration: 0.05, volume: 0.2 },
{ freq: 880, type: 'triangle', duration: 0.03, volume: 0.1 }
],
digital: [
{ freq: 1200, type: 'square', duration: 0.04, volume: 0.15 },
{ freq: 2400, type: 'sawtooth', duration: 0.02, volume: 0.07 }
],
binary: [ // More abrupt, clicky sound
{ freq: 2000, type: 'square', duration: 0.01, volume: 0.1 },
{ freq: 3000, type: 'sine', duration: 0.005, volume: 0.05 }
]
};
}
playSound() {
if (!this.soundEnabled || !this.audioContext || this.audioContext.state === 'suspended') {
return;
}
const profiles = this.soundProfiles[this.currentSoundType];
profiles.forEach(profile => {
const oscillator = this.audioContext.createOscillator();
const gainNode = this.audioContext.createGain();
oscillator.type = profile.type;
oscillator.frequency.setValueAtTime(profile.freq + (Math.random() - 0.5) * 20, this.audioContext.currentTime);
gainNode.gain.setValueAtTime(profile.volume, this.audioContext.currentTime);
gainNode.gain.exponentialRampToValueAtTime(0.0001, this.audioContext.currentTime + profile.duration);
oscillator.connect(gainNode);
gainNode.connect(this.audioContext.destination);
oscillator.start();
oscillator.stop(this.audioContext.currentTime + profile.duration + 0.02);
});
this.visualizer.style.animation = 'none';
void this.visualizer.offsetWidth; // Trigger reflow
this.visualizer.style.animation = 'visualizePulse 0.15s ease-out forwards';
}
setSound(soundType) {
if (this.soundProfiles[soundType]) {
this.currentSoundType = soundType;
document.getElementById('sound-select').value = soundType;
console.log(`Sound profile set to: ${soundType}`);
}
}
setTheme(theme) {
// This is where you would switch CSS classes on the body or apply styles directly
// For this Matrix design, we'll implement a simple "theme" effect
const body = document.body;
// Reset previous theme classes (if any, from an older design)
body.classList.remove('data_stream', 'glitch');
if (theme === 'matrix') {
// Already default, but ensures consistency
body.style.setProperty('--matrix-green', '#00FF41');
body.style.setProperty('--matrix-dark-green', '#00CC33');
body.style.setProperty('--matrix-light-green', '#00EE00');
body.style.setProperty('--matrix-black', '#0A0A0A');
this.systemStatusElement.textContent = "[ STATUS: ONLINE ]";
document.querySelector('.terminal-title').textContent = ">>> MTRX_OS v6.0_STABLE";
} else if (theme === 'data_stream') {
body.style.setProperty('--matrix-green', '#00FFFF'); /* Cyan */
body.style.setProperty('--matrix-dark-green', '#00AAAA');
body.style.setProperty('--matrix-light-green', '#00DDDD');
body.style.setProperty('--matrix-black', '#000020'); /* Dark Blue-ish */
this.systemStatusElement.textContent = "[ STATUS: DATAFLOW ]";
document.querySelector('.terminal-title').textContent = ">>> NEURAL_STREAM_ACTIVE";
} else if (theme === 'glitch') {
body.style.setProperty('--matrix-green', '#FF00FF'); /* Magenta */
body.style.setProperty('--matrix-dark-green', '#AA00AA');
body.style.setProperty('--matrix-light-green', '#DD00DD');
body.style.setProperty('--matrix-black', '#200020'); /* Dark Purple-ish */
// Add a subtle glitch effect class to body
body.classList.add('glitch');
this.systemStatusElement.textContent = "[ STATUS: GLITCHING ]";
document.querySelector('.terminal-title').textContent = ">>> SYSTEM_ERROR_0xDEADBEEF";
}
this.currentTheme = theme;
document.getElementById('theme-select').value = theme;
console.log(`Theme set to: ${theme}`);
}
// Matrix Rain Effect (new)
initMatrixRain() {
const canvas = document.createElement('canvas');
const ctx = canvas.getContext('2d');
const rainContainer = document.getElementById('matrix-rain');
rainContainer.appendChild(canvas);
let W = window.innerWidth;
let H = window.innerHeight;
canvas.width = W;
canvas.height = H;
const fontSize = 15; // Smaller font size for rain
const columns = Math.floor(W / fontSize);
const drops = [];
for (let i = 0; i < columns; i++) {
drops[i] = 1;
}
const chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789!@#$%^&*()_+-=[]{}|;:,.<>/?';
const draw = () => {
ctx.fillStyle = 'rgba(0, 0, 0, 0.05)'; // Fading effect
ctx.fillRect(0, 0, W, H);
ctx.fillStyle = varColor('--matrix-green'); // Main rain color
ctx.font = `${fontSize}px VT323`;
for (let i = 0; i < drops.length; i++) {
const text = chars.charAt(Math.floor(Math.random() * chars.length));
const x = i * fontSize;
const y = drops[i] * fontSize;
ctx.fillText(text, x, y);
if (y > H && Math.random() > 0.975) {
drops[i] = 0; // Reset drop to top
}
drops[i]++;
}
};
setInterval(draw, 33); // Animation loop for rain
// Helper to get CSS variable color
const varColor = (varName) => {
return getComputedStyle(document.body).getPropertyValue(varName);
};
window.addEventListener('resize', () => {
W = window.innerWidth;
H = window.innerHeight;
canvas.width = W;
canvas.height = H;
// Re-initialize drops for new column count if needed
const newColumns = Math.floor(W / fontSize);
if (newColumns !== columns) {
drops.length = 0; // Clear existing
for (let i = 0; i < newColumns; i++) {
drops[i] = 1;
}
}
});
}
updateStats() {
this.charCountElement.textContent = this.totalCharsProcessed;
const elapsedSeconds = (Date.now() - this.startTime) / 1000;
const wpm = elapsedSeconds > 0 ? Math.round(this.totalCharsProcessed / 5 / (elapsedSeconds / 60)) : 0;
this.wpmElement.textContent = wpm;
const progress = this.texts.length > 0 ? Math.round((this.currentTextIndex / this.texts.length) * 100) : 0;
this.progressElement.textContent = progress;
this.opCountElement.textContent = this.operationCount;
}
updateSpeedStatus() {
this.systemStatusElement.textContent = `[ STATUS: ${this.speeds[this.currentSpeedIndex].name} ]`;
}
toggleSpeed() {
this.currentSpeedIndex = (this.currentSpeedIndex + 1) % this.speeds.length;
this.updateSpeedStatus();
console.log(`Speed mode set to: ${this.speeds[this.currentSpeedIndex].name}`);
}
toggleSound() {
this.soundEnabled = !this.soundEnabled;
const soundButton = document.querySelector('[data-action="toggleSound"]');
soundButton.textContent = this.soundEnabled ? 'SOUND' : 'MUTE';
console.log(`Sound enabled: ${this.soundEnabled}`);
}
type() {
if (this.isPaused) return;
const currentFullText = this.texts[this.currentTextIndex];
if (this.currentCharIndex < currentFullText.length) {
const char = currentFullText.charAt(this.currentCharIndex);
const charSpan = document.createElement('span');
charSpan.textContent = char;
charSpan.classList.add('char', 'typed'); // Add 'typed' class for animation
this.textElement.appendChild(charSpan);
this.currentCharIndex++;
this.totalCharsProcessed++;
this.operationCount++; // Increment operations count
this.updateStats();
this.playSound();
let delay = (this.config.baseTypingSpeed + (Math.random() * this.config.typingVariance)) / this.speeds[this.currentSpeedIndex].multiplier;
if (this.config.punctuationChars.includes(char) && Math.random() < this.config.punctuationChance) {
delay += this.config.punctuationPause;
}
this.timeoutId = setTimeout(() => this.type(), delay);
} else {
this.isDeleting = true;
this.timeoutId = setTimeout(() => this.delete(), this.config.delayBeforeDelete / this.speeds[this.currentSpeedIndex].multiplier);
}
}
delete() {
if (this.isPaused) return;
if (this.currentCharIndex > 0) {
this.currentCharIndex--;
const lastCharSpan = this.textElement.lastChild;
if (lastCharSpan) {
lastCharSpan.classList.add('deleted'); // Add 'deleted' class for fade-out
setTimeout(() => lastCharSpan.remove(), 50); // Remove after brief fade
}
this.operationCount++; // Increment operations count
this.updateStats();
this.playSound();
let delay = (this.config.baseDeletingSpeed + (Math.random() * this.config.deletingVariance)) / this.speeds[this.currentSpeedIndex].multiplier;
this.timeoutId = setTimeout(() => this.delete(), delay);
} else {
this.isDeleting = false;
this.currentTextIndex = (this.currentTextIndex + 1) % this.texts.length;
this.timeoutId = setTimeout(() => this.type(), this.config.delayBeforeNext / this.speeds[this.currentSpeedIndex].multiplier);
}
}
start() {
this.startTime = Date.now();
this.totalCharsProcessed = 0;
this.operationCount = 0; // Reset operation count
this.updateStats();
this.type();
}
pause() {
this.isPaused = true;
clearTimeout(this.timeoutId);
this.cursorElement.style.animationPlayState = 'paused';
this.systemStatusElement.textContent = "[ STATUS: PAUSED ]";
console.log("Terminal paused.");
}
resume() {
if (this.isPaused) {
this.isPaused = false;
this.cursorElement.style.animationPlayState = 'running';
this.updateSpeedStatus(); // Restore speed status
if (this.isDeleting) {
this.delete();
} else {
this.type();
}
console.log("Terminal resumed.");
}
}
next() {
clearTimeout(this.timeoutId);
this.isDeleting = false;
this.currentCharIndex = 0;
this.currentTextIndex = (this.currentTextIndex + 1) % this.texts.length;
this.textElement.innerHTML = '';
this.start();
console.log("Skipping to next sequence.");
}
restart() {
clearTimeout(this.timeoutId);
this.currentTextIndex = 0;
this.currentCharIndex = 0;
this.isDeleting = false;
this.isPaused = false;
this.totalCharsProcessed = 0;
this.operationCount = 0;
this.textElement.innerHTML = '';
this.cursorElement.style.animationPlayState = 'running';
this.updateSpeedStatus(); // Restore speed status
this.start();
console.log("Terminal session restarted.");
}
setupEventListeners() {
document.querySelectorAll('.control-btn').forEach(button => {
button.addEventListener('click', (e) => {
const action = e.target.dataset.action;
if (this[action]) {
this[action]();
}
});
});
document.getElementById('sound-select').addEventListener('change', (e) => {
this.setSound(e.target.value);
});
document.getElementById('theme-select').addEventListener('change', (e) => {
this.setTheme(e.target.value);
});
}
}
new MatrixTypewriter();
});
</script>
</body>
</html>
![]()
Hello, I have this code already written, and have used it successfully on my site in the past (www.wix911.com) Happy to share it for free and help set it up for you ![]()
Feel free to reach out!

This is on the App marketplace. if you dont know code
After extensively researching these apps before writing the code for the effect I shared above, I found that most are either paid or offer free versions with significant limitations, often in exactly the areas users need most.
Hey.
Here is a velo code that will add the effect
$w.onReady(function () {
startTypewriterEffect();
addBlinkingCursor();
});
const words = ["The Future", "Everything", "Love", "Like Art"];
const typingSpeed = 100;
const erasingSpeed = 50;
const pauseBetweenWords = 1500;
const pauseAfterErase = 500;
let currentWordIndex = 0;
let isTyping = false;
function startTypewriterEffect() {
$w('#typewriterText').text = "";
typeNextWord();
}
function typeNextWord() {
if (isTyping) return;
isTyping = true;
const currentWord = words[currentWordIndex];
let currentChar = 0;
const typingInterval = setInterval(() => {
const displayText = currentWord.substring(0, currentChar + 1);
$w('#typewriterText').text = displayText;
currentChar++;
if (currentChar >= currentWord.length) {
clearInterval(typingInterval);
setTimeout(() => {
eraseCurrentWord(currentWord);
}, pauseBetweenWords);
}
}, typingSpeed);
}
function eraseCurrentWord(word) {
let currentChar = word.length;
const erasingInterval = setInterval(() => {
currentChar--;
const displayText = word.substring(0, currentChar);
$w('#typewriterText').text = displayText;
if (currentChar <= 0) {
clearInterval(erasingInterval);
currentWordIndex = (currentWordIndex + 1) % words.length;
isTyping = false;
setTimeout(() => {
typeNextWord();
}, pauseAfterErase);
}
}, erasingSpeed);
}
function addBlinkingCursor() {
let showCursor = true;
setInterval(() => {
const currentText = $w('#typewriterText').text;
if (showCursor) {
if (!currentText.endsWith('|')) {
$w('#typewriterText').text = currentText + '|';
}
} else {
if (currentText.endsWith('|')) {
$w('#typewriterText').text = currentText.slice(0, -1);
}
}
showCursor = !showCursor;
}, 500);
}
export function restartTypewriter() {
currentWordIndex = 0;
isTyping = false;
startTypewriterEffect();
}
export function updateWords(newWords) {
words.length = 0;
words.push(...newWords);
currentWordIndex = 0;
}
Use the
const typingSpeed = 100;
const erasingSpeed = 50;
const pauseBetweenWords = 1500;
const pauseAfterErase = 500;
To change the timing of the animations. 1000 = 1 Second.
Add 2 texts. In one add your static text like “Coding is” and in another text set its element ID “typewriterText” . Stack them together with 3-5px gap. Replace your words in
["The Future", "Everything", "Love", "Like Art"]
Feel free to ask any questions.
Best Regards
Thanks to all for the replies. Solved.