Estoy tratando de agregar diferentes clases a un div en función de lo que se hace clic, lo que he logrado hacer, pero necesito eliminar la clase previamente seleccionada / seleccionada y reemplazarla por la seleccionada, parece que no puedo obtener la parte eliminada Correcto. La mayoría de las soluciones que he encontrado son alternar o agregar y eliminar entre dos clases, pero no 3 o más.

Gracias

Esto es lo que he intentado hasta ahora y la parte de agregar funciona como se esperaba, pero cuando hago clic en un botón diferente, no elimina el botón anterior.

La HTML

<button id="btn-1" data-width="w-1/3">Mobile</button>
<button id="btn-2" data-width="w-2/3">Tablet</button>
<button id="btn-3" data-width="w-full">Desktop</button>

<div class="frame">
  Some Content
</div>

La Javascript

let setMobile = document.querySelector('#btn-1');
let setTablet = document.querySelector('#btn-2');
let setDesktop = document.querySelector('#btn-3');
let btns = [setMobile, setTablet, setDesktop];

function getBtnId(btn) {
    btn.addEventListener('click', function() {
        let frame = document.querySelector('.frame')
        frame.classList.add(this.dataset.width)
        if(frame.classList.contains(btns)){
            frame.classList.remove(this.dataset.width)
        }
        console.log(this.dataset.width);
    });
}

btns.forEach(getBtnId);

Básicamente, lo que estoy tratando de hacer es un marco receptivo que ajustará su ancho según lo que se haga clic.

0
Said 20 sep. 2019 a las 04:03

3 respuestas

La mejor respuesta

Puede almacenar la clase actual en una variable y usar remove() para eliminar la clase anterior con cada clic.

let setMobile = document.querySelector('#btn-1');
let setTablet = document.querySelector('#btn-2');
let setDesktop = document.querySelector('#btn-3');
let btns = [setMobile, setTablet, setDesktop];
var currentClass;

function getBtnId(btn) {
  btn.addEventListener('click', function() {
    let frame = document.querySelector('.frame')
    if (currentClass) {
      frame.classList.remove(currentClass);
    }
    currentClass = this.dataset.width;
    frame.classList.add(currentClass);
    console.log(this.dataset.width);
  });
}

btns.forEach(getBtnId);
<button id="btn-1" data-width="w-1/3">Mobile</button>
<button id="btn-2" data-width="w-2/3">Tablet</button>
<button id="btn-3" data-width="w-full">Desktop</button>

<div class="frame">
  Some Content
</div>
1
Nidhin Joseph 20 sep. 2019 a las 01:09

Aquí hay una versión generalizada para trabajar con múltiples elementos. He envuelto cada marco y botones en un elemento section. Luego, vinculé a los oyentes de eventos a las secciones y utilicé burbujeo de eventos / delegación de eventos para realizar el cambio. También he usado un atributo de datos en el marco de destino para mantener el estado actual.

function setWidthClass(event) {
  var newWidth = event.target.dataset.width;
  //This identifies a button click with our dataset
  if (newWidth) {
    //get the target div
    var target = this.querySelector(".frame");

    //if the target has a class set remove it
    if (target.dataset.width) {
      target.classList.remove(target.dataset.width);
    }

    //Add the new class 
    target.classList.add(newWidth);

    //Update the data on the target element
    target.dataset.width = newWidth;
  }
}

//Add the event listener
var sections = document.querySelectorAll(".varyWidth");
for (var i = 0; i < sections.length; i++) {
  sections[i].addEventListener("click", setWidthClass);
}
.w-third {
  color: red;
}

.w-half {
  color: blue;
}

.w-full {
  color: green;
}
<section class="varyWidth">
  <button data-width="w-third">Mobile</button>
  <button data-width="w-half">Tablet</button>
  <button data-width="w-full">Desktop</button>

  <div class="frame">
    Some Content
  </div>
</section>
<section class="varyWidth">
  <button data-width="w-third">Mobile</button>
  <button data-width="w-half">Tablet</button>
  <button data-width="w-full">Desktop</button>

  <div class="frame">
    Some Content
  </div>
</section>
<section class="varyWidth">
  <button data-width="w-third">Mobile</button>
  <button data-width="w-half">Tablet</button>
  <button data-width="w-full">Desktop</button>

  <div class="frame">
    Some Content
  </div>
</section>
1
Jon P 20 sep. 2019 a las 02:05

En lugar de rastrear la clase actual, también puede restablecerla:

let setMobile = document.querySelector('#btn-1');
let setTablet = document.querySelector('#btn-2');
let setDesktop = document.querySelector('#btn-3');
let btns = [setMobile, setTablet, setDesktop];

function getBtnId(btn) {
  btn.addEventListener('click', function() {
    let frame = document.querySelector('.frame')
    
    // reset the classList
    frame.classList = ["frame"];
    
    frame.classList.add(this.dataset.width)
    console.log(this.dataset.width);
 });
}

btns.forEach(getBtnId);
<button id="btn-1" data-width="w-1/3">Mobile</button>
<button id="btn-2" data-width="w-2/3">Tablet</button>
<button id="btn-3" data-width="w-full">Desktop</button>

<div class="frame">
  Some Content
</div>
0
j3py 20 sep. 2019 a las 01:17