By using this site, you agree to the Privacy Policy and Terms of Use.
Accept
rocoderesrocoderes
  • Home
  • HTML & CSS
    • Login and Registration Form
    • Card Design
    • Loader
  • JavaScript
  • Python
  • Internet
  • Landing Pages
  • Tools
    • Google Drive Direct Download Link Generator
    • Word Count
  • Games
    • House Painter
Notification Show More
Latest News
How to set the dropdown value by clicking on a table row
Javascript – How to set the dropdown value by clicking on a table row
JavaScript
Attempting to increase the counter, when the object's tag exist
Javascript – Attempting to increase the counter, when the object’s tag exist
JavaScript
Cycle2 JS center active slide
Javascript – Cycle2 JS center active slide
JavaScript
Can import all THREE.js post processing modules as ES6 modules except OutputPass
Javascript – Can import all THREE.js post processing modules as ES6 modules except OutputPass
JavaScript
How to return closest match for an array in Google Sheets Appscript
Javascript – How to return closest match for an array in Google Sheets Appscript
JavaScript
Aa
Aa
rocoderesrocoderes
Search
  • Home
  • HTML & CSS
    • Login and Registration Form
    • Card Design
    • Loader
  • JavaScript
  • Python
  • Internet
  • Landing Pages
  • Tools
    • Google Drive Direct Download Link Generator
    • Word Count
  • Games
    • House Painter
Follow US
High Quality Design Resources for Free.
rocoderes > JavaScript > Javascript – Updating Elements Within a Custom HTML Component JS
JavaScript

Javascript – Updating Elements Within a Custom HTML Component JS

Admin
Last updated: 2024/01/07 at 6:57 AM
Admin
Share
8 Min Read
Updating Elements Within a Custom HTML Component JS

Problem:

I’ve been stuck on this problem for awhile now.
I’ve given each component a className and im using GetElementsByClassName to access each individual component.
I need to get the value of the inputs for each individual component and create a note out of it (append it to the end of the custom component).

Contents
Problem:Solution:

UI

I’ve tried using innerHTML along with adding getElementByID to the end of the note variable

if(idNumber[12] == 1){
        let note = document.getElementsByClassName("note")[0].getElementByID("title-input");
    }

function addNote() {
  //Creating the NoteComponent, Adding it to the Array and Inserting it into  
  //the document 
  let noteComponent = document.createElement("note-component");
  noteComponentArray.push(noteComponent);
  numberOfNoteComponentsAdded++;
  document.getElementById("noteWorkingArea").append(noteComponent);
  //Setting the ID on the NoteComponent 
  noteComponent.setAttribute("id", "note-component" + 
  numberOfNoteComponentsAdded);
  noteComponent.setAttribute("class", "note");
  //Setting the ID on the SubmitButton
  let SubmitButtonElement = document.getElementById("submitButton");
  let SubmitButtonID = "submitButton" + 1;
  SubmitButtonElement.setAttribute("id", SubmitButtonID);
}


// Here is my attempt at updating the elements within the components
function addNoteDetails(numberOfNote) {
  let idNumber = numberOfNote.split('');
  //document.body.insertAdjacentHTML("afterend", idNumber[12]);

  if (idNumber[12] == 1) {
    let note = document.getElementsByClassName("note")[0];
  }
  if (idNumber[12] == 2) {
    let note = document.getElementsByClassName("note")[1];
  }
  if (idNumber[12] == 3) {
    let note = document.getElementsByClassName("note")[2];
  }
  if (idNumber[12] == 4) {
    let note = document.getElementsByClassName("note")[3];
  }
}
// Here is the Custom Component
class Note extends HTMLElement {
  constructor() {
    super();
  }

  connectedCallback() {
    this.innerHTML = `
      <body>
      <div class="fixed-action-btn" id="main-note">
      <a class="btn-floating btn-large red">
      <div id="deleteDiv" onclick="deleteNoteComponent()">
      <i class="fa-solid fa-x"></i>
      </div>
      </a>
      <div class="card">
      <div class="card-content" id="cardContent">
          <div class="input-group id="add-title-area" mb-3">
              <input type="text" class="form-control" id="title-input" 
              placeholder="Note Title:">
              <div class="input-group-append">
                  <button class="btn btn-outline-secondary" 
                  id="addTitleButton" 
                  type="button" onclick="addNoteTitle()">Add</button>
              </div>
          </div>
          <textarea class="note-input" id="input-note" contenteditable="true" 
          placeholder="enter your note..."></textarea>
      </div>
      <span class="button-row">
          <button class="btn waves-effect waves-light submit-button" 
          id="submitButton"
          type="submit" name="action" 
          onclick="addNoteDetails(this.getAttribute('id'))">Submit
          </button>
      </span>
        <div id="noteButtonContainer" class="centerButtons">
        </div>
      <span class="button-row">
          <button id="deleteNote"class="btn waves-effect waves-light delete-
          button" type="default" 
          name="action" onclick="deleteNote()">Delete Note
          </button>
      </span>
      </div>
      </body>`;
  }
}
customElements.define('note-component', Note);

Solution:

The question was a bit confusing.. it wasn’t clear why you had a button to add a title to the single note, like if the input itself wasn’t enough. Did you need multiple titles?

Anyway since the problem was stated as the addNoteDetails function and yet its exact task wasn’t perfectly clear based on its content, I just sticked to

I need to get the value of the inputs for each individual component
and create a note out of it (append it to the end of the custom
component).

So here in this demo I slightly replicated your same custom element just stripping away unnecessary parts to make it easier to read and added a feature to collect all notes contained in a given container and set the #output value with their content joined.

Note that I didn’t use ids in the custom component because it was tedious to change all of them when every instance was created (by the way you limited your attempt to the textarea but it was not the only element having an id that can’t be duplicated). Plus the deleteNote function is defined in the class itself and it uses the .closest() api function to find its parent before removal.

In the end I also added an event emitSubmitEvent on your component that will be fired by the .submit button of the corresponding note. So that you can listen to it from your caller that when the event will trigger, will log the corresponding note on console. That’s not perfectly matching the request of creating a new button performing such action only when the submit is clicked… at first I thought it didn’t make sense to me but it actually does.. it would be like an extra watch button after submitting to note somewhere.

// Here is the Custom Component
class Note extends HTMLElement {
  constructor() {
    super();
    //this.attachShadow({ mode: 'open' });
  }

  connectedCallback() {   
    this.innerHTML = `      
      <div class="main-note">
         <div class="delete">
             <i class="fa-solid fa-x"></i>
         </div>
         <div class="card">
           <div class="card-content">                 
               <textarea
                class="note-input"
                contenteditable="true"
                placeholder="enter your note..."></textarea>
               <button type="button" class="submit">submit</button>
           </div>                                             
         </div>
     </div>`;
    
    //we are adding the event listener programmatically instead of using onclick attr    
    this.querySelector('.delete').addEventListener('click', this.deleteNote);    
    
    this.querySelector('.submit').addEventListener('click', this.emitSubmitEvent.bind(this));

  }
  
  deleteNote(event) {    
    this.closest('note-component').remove();
  }

  emitSubmitEvent() {
    const textareaValue = this.querySelector('.note-input').value;
    const event = new CustomEvent('submit', {
      detail: {
        text: textareaValue
      }
    });
    this.dispatchEvent(event);
  }
}
customElements.define('note-component', Note);

//adds the click event handler on #addNote that will call addNote over noteWorkingArea container
document.getElementById('addNote')
  .addEventListener('click', ()=>{
    const noteWorkingArea = document.getElementById("noteWorkingArea");
    addNote(noteWorkingArea);
  });


//adds the click event handler on #collectNotes
//that will call collectNoteContents over noteWorkingArea container
//and will set the output content as the join of all notes
document.getElementById('submit-button')
  .addEventListener('click', ()=>{
    const noteWorkingArea = document.getElementById("noteWorkingArea");
    const noteContents = collectNoteContents(noteWorkingArea);
    document.querySelector('#output')
      .innerText = noteContents;
  });

//appends a new note-component instance in the container
function addNote(container) {    
  let noteComponent = document.createElement("note-component");  
  container.append(noteComponent);
  noteComponent.setAttribute("class", "note");
  
  //listen for submit event on the notecomponent and log its note on console
  noteComponent.addEventListener('submit', (event) => {
    const noteText = event.detail.text;
    console.log(noteText);
  });
}

//defined outside the "scope" of the single notes.. 
//it will collect all the note contents in the noteWorkingArea and return the joined text
function collectNoteContents(container) {  
  let result = '';
  container.querySelectorAll('.note-input')
    .forEach(note => {
      result += note.value + "\n--------------------------\n";
    });
  return result;
}
#noteWorkingArea{
  border: dashed 4px purple;
  min-height: 2em;
  margin-bottom: 1em;
}

note-component{
  border: solid 1px gray;
  margin: 1em;
  display: block;
}

#output{
  margin-top: 1em;
  border: dashed 4px red;
  min-height: 2em;
}

button{
  cursor: pointer;
  padding: 1em;
}

textarea{
  width: 100%;
  box-sizing: border-box;
}

.submit{
  width: 100%;
}
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.4.2/css/all.min.css" integrity="sha512-z3gLpd7yknf1YoNbCzqRKc4qyor8gaKU1qmn+CShxbuBusANI9QpRohGBreCFkKxLhei6S9CQXFEbbKuqLg0DA==" crossorigin="anonymous" referrerpolicy="no-referrer" />

<!-- area were the notes (components) will be appended -->
<h2>Notes:</h2>
<div id="noteWorkingArea">
</div>

<!-- button that will append a new note inside the target -->
<button id="addNote">Add Note</button>

<!-- button to add a new note in #noteWorkingArea -->
<!-- I didn't use type=submit because there's no form in this scenario -->
<button
    id="submit-button"
    class="btn btn-primary waves-effect waves-light"    
    type="button"
    name="action">COLLECT CONTENTS</button>


<!-- where you'll see the note contents collected -->
<h2>Output:</h2>
<div id="output">
</div>

Expand snippet

Related

Subscribe to Our Newsletter

Subscribe to our newsletter to get our newest articles instantly!

Share this Article
Facebook Twitter Email Print
What do you think?
Love0
Sad0
Happy0
Sleepy0
Angry0
Dead0
Wink0
Previous Article JavaScript: How to rewrite code to use dynamic values instead of hard-coded ones? Javascript – JavaScript: How to rewrite code to use dynamic values instead of hard-coded ones?
Next Article Delete all columns inside a Column Group with Google Apps Script Javascript – Delete all columns inside a Column Group with Google Apps Script
Leave a comment Leave a comment

Leave a Reply Cancel reply

Your email address will not be published. Required fields are marked *

- Advertisement -

You Might Also Like

How to set the dropdown value by clicking on a table row

Javascript – How to set the dropdown value by clicking on a table row

February 11, 2024
Attempting to increase the counter, when the object's tag exist

Javascript – Attempting to increase the counter, when the object’s tag exist

February 11, 2024
Cycle2 JS center active slide

Javascript – Cycle2 JS center active slide

February 10, 2024
Can import all THREE.js post processing modules as ES6 modules except OutputPass

Javascript – Can import all THREE.js post processing modules as ES6 modules except OutputPass

February 10, 2024
rocoderesrocoderes
Follow US

Copyright © 2022 All Right Reserved By Rocoderes

  • Home
  • About us
  • Contact us
  • Disclaimer
Join Us!

Subscribe to our newsletter and never miss our latest news, podcasts etc.

Zero spam, Unsubscribe at any time.
Welcome Back!

Sign in to your account

Lost your password?