javascript

examples

examples.js
/**
 * ========================================
 * 10.5 Forms and User Input - Examples
 * ========================================
 *
 * Run these examples in a browser console with appropriate HTML forms
 * or create the forms dynamically as shown.
 */

/**
 * ========================================
 * EXAMPLE 1: Creating a Form Dynamically
 * ========================================
 */
console.log('--- Example 1: Creating a Form Dynamically ---');

// Create a complete form structure
function createContactForm() {
  const form = document.createElement('form');
  form.id = 'contactForm';
  form.innerHTML = `
        <div class="form-group">
            <label for="name">Name:</label>
            <input type="text" id="name" name="name" required minlength="2">
        </div>
        
        <div class="form-group">
            <label for="email">Email:</label>
            <input type="email" id="email" name="email" required>
        </div>
        
        <div class="form-group">
            <label for="subject">Subject:</label>
            <select id="subject" name="subject">
                <option value="">Select a subject</option>
                <option value="general">General Inquiry</option>
                <option value="support">Support</option>
                <option value="feedback">Feedback</option>
            </select>
        </div>
        
        <div class="form-group">
            <label for="message">Message:</label>
            <textarea id="message" name="message" rows="4" required></textarea>
        </div>
        
        <div class="form-group">
            <label>
                <input type="checkbox" name="newsletter" value="yes">
                Subscribe to newsletter
            </label>
        </div>
        
        <button type="submit">Send Message</button>
        <button type="reset">Clear Form</button>
    `;

  return form;
}

// Usage (uncomment to test in browser):
// document.body.appendChild(createContactForm());

/**
 * ========================================
 * EXAMPLE 2: Accessing Form Elements
 * ========================================
 */
console.log('\n--- Example 2: Accessing Form Elements ---');

function demonstrateFormAccess() {
  // Assuming form exists in DOM
  const form = document.getElementById('contactForm');

  if (!form) {
    console.log('Create a form first');
    return;
  }

  // Access via elements collection
  console.log('Form elements count:', form.elements.length);
  console.log('Name field:', form.elements['name']);
  console.log('Email field:', form.elements['email']);
  console.log('First element:', form.elements[0]);

  // Iterate all form elements
  console.log('\nAll form elements:');
  for (let i = 0; i < form.elements.length; i++) {
    const element = form.elements[i];
    console.log(
      `${i}: ${element.tagName} - name="${element.name}" type="${element.type}"`
    );
  }

  // Access all forms in document
  console.log('\nAll forms in document:', document.forms.length);
}

// demonstrateFormAccess();

/**
 * ========================================
 * EXAMPLE 3: Reading Different Input Types
 * ========================================
 */
console.log('\n--- Example 3: Reading Different Input Types ---');

function createInputTypesDemo() {
  const form = document.createElement('form');
  form.id = 'inputTypesForm';
  form.innerHTML = `
        <h3>Input Types Demo</h3>
        
        <!-- Text input -->
        <input type="text" name="textInput" value="Hello World">
        
        <!-- Number input -->
        <input type="number" name="numberInput" value="42">
        
        <!-- Checkbox -->
        <input type="checkbox" name="checkboxInput" checked>
        
        <!-- Radio buttons -->
        <input type="radio" name="radioInput" value="option1" checked> Option 1
        <input type="radio" name="radioInput" value="option2"> Option 2
        
        <!-- Select -->
        <select name="selectInput">
            <option value="a">Option A</option>
            <option value="b" selected>Option B</option>
            <option value="c">Option C</option>
        </select>
        
        <!-- Multi-select -->
        <select name="multiSelect" multiple>
            <option value="1" selected>One</option>
            <option value="2" selected>Two</option>
            <option value="3">Three</option>
        </select>
        
        <!-- Range -->
        <input type="range" name="rangeInput" min="0" max="100" value="50">
        
        <!-- Color -->
        <input type="color" name="colorInput" value="#3498db">
        
        <!-- Date -->
        <input type="date" name="dateInput" value="2024-01-15">
        
        <button type="button" onclick="readAllInputs()">Read All Values</button>
    `;

  return form;
}

function readAllInputs() {
  const form = document.getElementById('inputTypesForm');
  if (!form) return;

  // Text input
  const textValue = form.elements['textInput'].value;
  console.log('Text:', textValue);

  // Number input (still returns string, need to convert)
  const numberValue = Number(form.elements['numberInput'].value);
  console.log('Number:', numberValue, typeof numberValue);

  // Checkbox
  const checkboxValue = form.elements['checkboxInput'].checked;
  console.log('Checkbox:', checkboxValue);

  // Radio buttons (find the checked one)
  const radioValue = form.querySelector(
    'input[name="radioInput"]:checked'
  ).value;
  console.log('Radio:', radioValue);

  // Select
  const selectValue = form.elements['selectInput'].value;
  console.log('Select:', selectValue);

  // Multi-select (get all selected)
  const multiSelect = form.elements['multiSelect'];
  const multiValues = [...multiSelect.selectedOptions].map((opt) => opt.value);
  console.log('Multi-select:', multiValues);

  // Range
  const rangeValue = Number(form.elements['rangeInput'].value);
  console.log('Range:', rangeValue);

  // Color
  const colorValue = form.elements['colorInput'].value;
  console.log('Color:', colorValue);

  // Date
  const dateValue = form.elements['dateInput'].value;
  console.log('Date:', dateValue);
}

/**
 * ========================================
 * EXAMPLE 4: HTML5 Form Validation
 * ========================================
 */
console.log('\n--- Example 4: HTML5 Form Validation ---');

function createValidationForm() {
  const form = document.createElement('form');
  form.id = 'validationForm';
  form.innerHTML = `
        <div>
            <label>Username (3-15 chars, letters only):</label>
            <input type="text" name="username" 
                   required 
                   minlength="3" 
                   maxlength="15" 
                   pattern="[A-Za-z]+"
                   title="Only letters allowed">
            <span class="error"></span>
        </div>
        
        <div>
            <label>Email:</label>
            <input type="email" name="email" required>
            <span class="error"></span>
        </div>
        
        <div>
            <label>Age (18-99):</label>
            <input type="number" name="age" 
                   required 
                   min="18" 
                   max="99">
            <span class="error"></span>
        </div>
        
        <div>
            <label>Website:</label>
            <input type="url" name="website">
            <span class="error"></span>
        </div>
        
        <button type="submit">Validate & Submit</button>
    `;

  // Add validation handler
  form.addEventListener('submit', function (e) {
    e.preventDefault();

    if (form.checkValidity()) {
      console.log('Form is valid! Submitting...');
      // Process form
    } else {
      console.log('Form has validation errors');
      form.reportValidity();
    }
  });

  return form;
}

/**
 * ========================================
 * EXAMPLE 5: Constraint Validation API
 * ========================================
 */
console.log('\n--- Example 5: Constraint Validation API ---');

function demonstrateValidityAPI() {
  const input = document.createElement('input');
  input.type = 'email';
  input.required = true;
  input.value = '';

  console.log('Empty required email field validity:');
  console.log('- valid:', input.validity.valid);
  console.log('- valueMissing:', input.validity.valueMissing);

  input.value = 'not-an-email';
  console.log('\nInvalid email format:');
  console.log('- valid:', input.validity.valid);
  console.log('- typeMismatch:', input.validity.typeMismatch);

  input.value = 'valid@email.com';
  console.log('\nValid email:');
  console.log('- valid:', input.validity.valid);

  // Number validation
  const numberInput = document.createElement('input');
  numberInput.type = 'number';
  numberInput.min = '10';
  numberInput.max = '20';
  numberInput.value = '5';

  console.log('\nNumber below minimum (5 with min=10):');
  console.log('- rangeUnderflow:', numberInput.validity.rangeUnderflow);

  numberInput.value = '25';
  console.log('\nNumber above maximum (25 with max=20):');
  console.log('- rangeOverflow:', numberInput.validity.rangeOverflow);
}

demonstrateValidityAPI();

/**
 * ========================================
 * EXAMPLE 6: Custom Validation
 * ========================================
 */
console.log('\n--- Example 6: Custom Validation ---');

function createPasswordForm() {
  const form = document.createElement('form');
  form.id = 'passwordForm';
  form.innerHTML = `
        <div>
            <label>Password:</label>
            <input type="password" id="password" name="password" required minlength="8">
            <small>At least 8 characters, one uppercase, one number</small>
        </div>
        
        <div>
            <label>Confirm Password:</label>
            <input type="password" id="confirmPassword" name="confirmPassword" required>
        </div>
        
        <button type="submit">Create Account</button>
    `;

  const password = form.querySelector('#password');
  const confirmPassword = form.querySelector('#confirmPassword');

  // Custom password strength validation
  function validatePasswordStrength() {
    const value = password.value;

    if (!/[A-Z]/.test(value)) {
      password.setCustomValidity('Password must contain an uppercase letter');
    } else if (!/[0-9]/.test(value)) {
      password.setCustomValidity('Password must contain a number');
    } else {
      password.setCustomValidity('');
    }
  }

  // Password match validation
  function validatePasswordMatch() {
    if (password.value !== confirmPassword.value) {
      confirmPassword.setCustomValidity("Passwords don't match");
    } else {
      confirmPassword.setCustomValidity('');
    }
  }

  password.addEventListener('input', () => {
    validatePasswordStrength();
    validatePasswordMatch();
  });

  confirmPassword.addEventListener('input', validatePasswordMatch);

  form.addEventListener('submit', function (e) {
    e.preventDefault();

    if (form.checkValidity()) {
      console.log('Passwords valid and matching!');
    } else {
      form.reportValidity();
    }
  });

  return form;
}

/**
 * ========================================
 * EXAMPLE 7: Real-time Validation Feedback
 * ========================================
 */
console.log('\n--- Example 7: Real-time Validation Feedback ---');

function createRealtimeValidationForm() {
  const form = document.createElement('form');
  form.id = 'realtimeForm';
  form.innerHTML = `
        <style>
            .valid { border-color: green; }
            .invalid { border-color: red; }
            .feedback { font-size: 12px; margin-top: 4px; }
            .feedback.success { color: green; }
            .feedback.error { color: red; }
        </style>
        
        <div>
            <label>Username:</label>
            <input type="text" id="rtUsername" required minlength="3" maxlength="20">
            <div id="usernameFeedback" class="feedback"></div>
        </div>
        
        <div>
            <label>Email:</label>
            <input type="email" id="rtEmail" required>
            <div id="emailFeedback" class="feedback"></div>
        </div>
    `;

  const username = form.querySelector('#rtUsername');
  const usernameFeedback = form.querySelector('#usernameFeedback');
  const email = form.querySelector('#rtEmail');
  const emailFeedback = form.querySelector('#emailFeedback');

  username.addEventListener('input', function () {
    const validity = this.validity;

    if (validity.valid) {
      this.classList.remove('invalid');
      this.classList.add('valid');
      usernameFeedback.textContent = '✓ Username looks good!';
      usernameFeedback.className = 'feedback success';
    } else if (validity.valueMissing) {
      this.classList.remove('valid');
      this.classList.add('invalid');
      usernameFeedback.textContent = '✗ Username is required';
      usernameFeedback.className = 'feedback error';
    } else if (validity.tooShort) {
      this.classList.remove('valid');
      this.classList.add('invalid');
      usernameFeedback.textContent = `✗ At least ${this.minLength} characters (${this.value.length}/${this.minLength})`;
      usernameFeedback.className = 'feedback error';
    }
  });

  email.addEventListener('input', function () {
    if (this.validity.valid) {
      this.classList.remove('invalid');
      this.classList.add('valid');
      emailFeedback.textContent = '✓ Valid email';
      emailFeedback.className = 'feedback success';
    } else if (this.validity.typeMismatch) {
      this.classList.remove('valid');
      this.classList.add('invalid');
      emailFeedback.textContent = '✗ Please enter a valid email';
      emailFeedback.className = 'feedback error';
    } else if (this.validity.valueMissing) {
      this.classList.remove('valid');
      this.classList.add('invalid');
      emailFeedback.textContent = '✗ Email is required';
      emailFeedback.className = 'feedback error';
    }
  });

  return form;
}

/**
 * ========================================
 * EXAMPLE 8: FormData API
 * ========================================
 */
console.log('\n--- Example 8: FormData API ---');

function demonstrateFormData() {
  // Create a form programmatically
  const form = document.createElement('form');
  form.innerHTML = `
        <input type="text" name="firstName" value="John">
        <input type="text" name="lastName" value="Doe">
        <input type="email" name="email" value="john@example.com">
        <input type="checkbox" name="interests" value="javascript" checked>
        <input type="checkbox" name="interests" value="python" checked>
        <input type="checkbox" name="interests" value="rust">
    `;

  const formData = new FormData(form);

  console.log('FormData operations:');

  // Get single value
  console.log('firstName:', formData.get('firstName'));

  // Get all values for a key (checkboxes)
  console.log('interests:', formData.getAll('interests'));

  // Check if key exists
  console.log('has email:', formData.has('email'));
  console.log('has phone:', formData.has('phone'));

  // Add new value
  formData.append('timestamp', Date.now().toString());
  console.log('timestamp:', formData.get('timestamp'));

  // Iterate entries
  console.log('\nAll entries:');
  for (const [key, value] of formData.entries()) {
    console.log(`  ${key}: ${value}`);
  }

  // Convert to object
  const dataObject = Object.fromEntries(formData);
  console.log('\nAs object:', dataObject);
  // Note: Object.fromEntries only gets LAST value for duplicate keys

  // Better conversion for multiple values
  const fullData = {};
  for (const [key, value] of formData.entries()) {
    if (fullData[key]) {
      if (Array.isArray(fullData[key])) {
        fullData[key].push(value);
      } else {
        fullData[key] = [fullData[key], value];
      }
    } else {
      fullData[key] = value;
    }
  }
  console.log('Full data with arrays:', fullData);
}

demonstrateFormData();

/**
 * ========================================
 * EXAMPLE 9: Form Submission with Fetch
 * ========================================
 */
console.log('\n--- Example 9: Form Submission with Fetch ---');

function createAjaxForm() {
  const form = document.createElement('form');
  form.id = 'ajaxForm';
  form.innerHTML = `
        <input type="text" name="title" placeholder="Title" required>
        <textarea name="content" placeholder="Content" required></textarea>
        <button type="submit">Submit</button>
        <div id="status"></div>
    `;

  const statusDiv = form.querySelector('#status');

  form.addEventListener('submit', async function (e) {
    e.preventDefault();

    const formData = new FormData(form);
    const data = Object.fromEntries(formData);

    statusDiv.textContent = 'Submitting...';

    try {
      // Simulated API call
      const response = await fetch(
        'https://jsonplaceholder.typicode.com/posts',
        {
          method: 'POST',
          headers: {
            'Content-Type': 'application/json',
          },
          body: JSON.stringify(data),
        }
      );

      if (!response.ok) {
        throw new Error(`HTTP error! status: ${response.status}`);
      }

      const result = await response.json();
      console.log('Server response:', result);
      statusDiv.textContent = `Success! Created post with ID: ${result.id}`;
      form.reset();
    } catch (error) {
      console.error('Submission error:', error);
      statusDiv.textContent = `Error: ${error.message}`;
    }
  });

  return form;
}

/**
 * ========================================
 * EXAMPLE 10: Input Events
 * ========================================
 */
console.log('\n--- Example 10: Input Events ---');

function createInputEventsDemo() {
  const container = document.createElement('div');
  container.innerHTML = `
        <h3>Input Events Demo</h3>
        <input type="text" id="eventInput" placeholder="Type something...">
        <div id="eventLog" style="height: 200px; overflow-y: auto; border: 1px solid #ccc; padding: 10px;"></div>
    `;

  const input = container.querySelector('#eventInput');
  const log = container.querySelector('#eventLog');

  function logEvent(eventName, details = '') {
    const entry = document.createElement('div');
    const time = new Date().toLocaleTimeString();
    entry.textContent = `[${time}] ${eventName} ${details}`;
    log.appendChild(entry);
    log.scrollTop = log.scrollHeight;
  }

  // Input event - fires on every change
  input.addEventListener('input', function (e) {
    logEvent('input', `value="${this.value}"`);
  });

  // Change event - fires on blur when value changed
  input.addEventListener('change', function (e) {
    logEvent('change', `value="${this.value}"`);
  });

  // Focus events
  input.addEventListener('focus', function () {
    logEvent('focus');
  });

  input.addEventListener('blur', function () {
    logEvent('blur');
  });

  // Keyboard events
  input.addEventListener('keydown', function (e) {
    logEvent('keydown', `key="${e.key}"`);
  });

  input.addEventListener('keyup', function (e) {
    logEvent('keyup', `key="${e.key}"`);
  });

  return container;
}

/**
 * ========================================
 * EXAMPLE 11: Debounced Search Input
 * ========================================
 */
console.log('\n--- Example 11: Debounced Search Input ---');

function debounce(func, delay) {
  let timeoutId;
  return function (...args) {
    clearTimeout(timeoutId);
    timeoutId = setTimeout(() => func.apply(this, args), delay);
  };
}

function createSearchInput() {
  const container = document.createElement('div');
  container.innerHTML = `
        <label>Search:</label>
        <input type="text" id="searchInput" placeholder="Type to search...">
        <div id="searchResults"></div>
    `;

  const input = container.querySelector('#searchInput');
  const results = container.querySelector('#searchResults');

  // Simulated search function
  function performSearch(query) {
    console.log(`Searching for: "${query}"`);
    results.textContent = `Searching for: "${query}"...`;

    // Simulate API delay
    setTimeout(() => {
      results.textContent = `Found 5 results for "${query}"`;
    }, 500);
  }

  // Debounced search - only fires 300ms after user stops typing
  const debouncedSearch = debounce(function (e) {
    const query = e.target.value.trim();
    if (query.length >= 2) {
      performSearch(query);
    } else {
      results.textContent = 'Type at least 2 characters';
    }
  }, 300);

  input.addEventListener('input', debouncedSearch);

  return container;
}

/**
 * ========================================
 * EXAMPLE 12: File Input Handling
 * ========================================
 */
console.log('\n--- Example 12: File Input Handling ---');

function createFileUploadForm() {
  const form = document.createElement('form');
  form.innerHTML = `
        <div>
            <label>Select files:</label>
            <input type="file" id="fileInput" multiple accept="image/*,.pdf">
        </div>
        <div id="fileList"></div>
        <div id="preview"></div>
    `;

  const fileInput = form.querySelector('#fileInput');
  const fileList = form.querySelector('#fileList');
  const preview = form.querySelector('#preview');

  fileInput.addEventListener('change', function () {
    const files = this.files;

    if (files.length === 0) {
      fileList.textContent = 'No files selected';
      return;
    }

    // Display file information
    let html = '<h4>Selected Files:</h4><ul>';
    for (const file of files) {
      const size = (file.size / 1024).toFixed(2);
      html += `<li>
                ${file.name} 
                (${file.type || 'unknown type'}, ${size} KB)
            </li>`;
    }
    html += '</ul>';
    fileList.innerHTML = html;

    // Preview images
    preview.innerHTML = '';
    for (const file of files) {
      if (file.type.startsWith('image/')) {
        const reader = new FileReader();
        reader.onload = function (e) {
          const img = document.createElement('img');
          img.src = e.target.result;
          img.style.maxWidth = '200px';
          img.style.margin = '10px';
          preview.appendChild(img);
        };
        reader.readAsDataURL(file);
      }
    }
  });

  return form;
}

/**
 * ========================================
 * EXAMPLE 13: Form with All Input Types
 * ========================================
 */
console.log('\n--- Example 13: Complete Form Example ---');

function createCompleteForm() {
  const form = document.createElement('form');
  form.id = 'completeForm';
  form.innerHTML = `
        <style>
            .form-group { margin-bottom: 15px; }
            .form-group label { display: block; margin-bottom: 5px; font-weight: bold; }
            .form-group input, .form-group select, .form-group textarea { 
                width: 100%; padding: 8px; box-sizing: border-box; 
            }
            .form-group.inline label { display: inline; font-weight: normal; }
            .error-message { color: red; font-size: 12px; }
            button { padding: 10px 20px; margin-right: 10px; cursor: pointer; }
        </style>
        
        <h2>User Registration</h2>
        
        <div class="form-group">
            <label for="username">Username *</label>
            <input type="text" id="username" name="username" required minlength="3" maxlength="20">
        </div>
        
        <div class="form-group">
            <label for="email">Email *</label>
            <input type="email" id="email" name="email" required>
        </div>
        
        <div class="form-group">
            <label for="password">Password *</label>
            <input type="password" id="password" name="password" required minlength="8">
        </div>
        
        <div class="form-group">
            <label for="birthdate">Birth Date</label>
            <input type="date" id="birthdate" name="birthdate">
        </div>
        
        <div class="form-group">
            <label for="country">Country</label>
            <select id="country" name="country">
                <option value="">Select country</option>
                <option value="us">United States</option>
                <option value="uk">United Kingdom</option>
                <option value="ca">Canada</option>
                <option value="au">Australia</option>
            </select>
        </div>
        
        <div class="form-group">
            <label>Gender</label>
            <label class="inline">
                <input type="radio" name="gender" value="male"> Male
            </label>
            <label class="inline">
                <input type="radio" name="gender" value="female"> Female
            </label>
            <label class="inline">
                <input type="radio" name="gender" value="other"> Other
            </label>
        </div>
        
        <div class="form-group">
            <label>Interests</label>
            <label class="inline">
                <input type="checkbox" name="interests" value="tech"> Technology
            </label>
            <label class="inline">
                <input type="checkbox" name="interests" value="sports"> Sports
            </label>
            <label class="inline">
                <input type="checkbox" name="interests" value="music"> Music
            </label>
        </div>
        
        <div class="form-group">
            <label for="bio">Bio</label>
            <textarea id="bio" name="bio" rows="4" placeholder="Tell us about yourself..."></textarea>
        </div>
        
        <div class="form-group">
            <label for="avatar">Profile Picture</label>
            <input type="file" id="avatar" name="avatar" accept="image/*">
        </div>
        
        <div class="form-group">
            <label class="inline">
                <input type="checkbox" name="terms" required> 
                I agree to the Terms and Conditions *
            </label>
        </div>
        
        <button type="submit">Register</button>
        <button type="reset">Clear</button>
        
        <div id="formOutput"></div>
    `;

  form.addEventListener('submit', function (e) {
    e.preventDefault();

    const formData = new FormData(form);
    const output = form.querySelector('#formOutput');

    // Build output
    let html = '<h3>Form Data:</h3><pre>';

    // Regular fields
    for (const [key, value] of formData.entries()) {
      if (value instanceof File) {
        html += `${key}: [File] ${value.name} (${value.size} bytes)\n`;
      } else {
        html += `${key}: ${value}\n`;
      }
    }

    html += '</pre>';
    output.innerHTML = html;

    console.log('Form submitted:', Object.fromEntries(formData));
  });

  form.addEventListener('reset', function () {
    form.querySelector('#formOutput').innerHTML = '';
  });

  return form;
}

/**
 * ========================================
 * EXAMPLE 14: Preventing Double Submission
 * ========================================
 */
console.log('\n--- Example 14: Preventing Double Submission ---');

function createSubmitOnceForm() {
  const form = document.createElement('form');
  form.innerHTML = `
        <input type="text" name="data" required placeholder="Enter data">
        <button type="submit" id="submitBtn">Submit</button>
        <span id="submitStatus"></span>
    `;

  const submitBtn = form.querySelector('#submitBtn');
  const status = form.querySelector('#submitStatus');

  form.addEventListener('submit', async function (e) {
    e.preventDefault();

    // Disable button immediately
    submitBtn.disabled = true;
    const originalText = submitBtn.textContent;
    submitBtn.textContent = 'Submitting...';
    status.textContent = '';

    try {
      // Simulate slow API call
      await new Promise((resolve) => setTimeout(resolve, 2000));

      // Simulate random success/failure
      if (Math.random() > 0.3) {
        status.textContent = '✓ Success!';
        status.style.color = 'green';
        form.reset();
      } else {
        throw new Error('Random server error');
      }
    } catch (error) {
      status.textContent = `✗ Error: ${error.message}`;
      status.style.color = 'red';
    } finally {
      // Re-enable button
      submitBtn.disabled = false;
      submitBtn.textContent = originalText;
    }
  });

  return form;
}

/**
 * ========================================
 * EXAMPLE 15: Dynamic Form Fields
 * ========================================
 */
console.log('\n--- Example 15: Dynamic Form Fields ---');

function createDynamicForm() {
  const form = document.createElement('form');
  form.innerHTML = `
        <div id="fieldsContainer">
            <div class="field-row">
                <input type="text" name="items[]" placeholder="Item 1" required>
                <button type="button" class="remove-btn">Remove</button>
            </div>
        </div>
        <button type="button" id="addField">+ Add Item</button>
        <button type="submit">Submit</button>
    `;

  const container = form.querySelector('#fieldsContainer');
  const addBtn = form.querySelector('#addField');
  let itemCount = 1;

  addBtn.addEventListener('click', function () {
    itemCount++;
    const newRow = document.createElement('div');
    newRow.className = 'field-row';
    newRow.innerHTML = `
            <input type="text" name="items[]" placeholder="Item ${itemCount}" required>
            <button type="button" class="remove-btn">Remove</button>
        `;
    container.appendChild(newRow);
  });

  // Event delegation for remove buttons
  container.addEventListener('click', function (e) {
    if (e.target.classList.contains('remove-btn')) {
      const rows = container.querySelectorAll('.field-row');
      if (rows.length > 1) {
        e.target.closest('.field-row').remove();
      } else {
        alert('Must have at least one item');
      }
    }
  });

  form.addEventListener('submit', function (e) {
    e.preventDefault();
    const formData = new FormData(form);
    const items = formData.getAll('items[]');
    console.log('Items:', items);
  });

  return form;
}

/**
 * ========================================
 * Running Examples
 * ========================================
 */
console.log('\n========================================');
console.log('Forms and User Input Examples');
console.log('========================================');
console.log('To run examples in browser, use these functions:');
console.log('- document.body.appendChild(createContactForm())');
console.log('- document.body.appendChild(createInputTypesDemo())');
console.log('- document.body.appendChild(createValidationForm())');
console.log('- document.body.appendChild(createPasswordForm())');
console.log('- document.body.appendChild(createRealtimeValidationForm())');
console.log('- document.body.appendChild(createAjaxForm())');
console.log('- document.body.appendChild(createInputEventsDemo())');
console.log('- document.body.appendChild(createSearchInput())');
console.log('- document.body.appendChild(createFileUploadForm())');
console.log('- document.body.appendChild(createCompleteForm())');
console.log('- document.body.appendChild(createSubmitOnceForm())');
console.log('- document.body.appendChild(createDynamicForm())');
Examples - JavaScript Tutorial | DeepML