0

I'm looking to add a class to each element within an array I have using pure javascript only. My need for this is because I the application I have gives me 'very' limited html editing capability.

My Goal

" Is to emulate radio buttons by using checkboxes. "

To do this I need to add a uniqe class handle to all the elements I want to target, as not to pick up any other elements by mistake. Only then can I start manipulating thier behavior.

Essentially what I realise I need is to loop - // .classList.add("chkbox"); through the array applying .chkbox to each of the elements within it.

The only issue is, I'm unsure of the best way to do this. I've done some digging around and couldn't find anything that really matched what I'm looking for. "However, I did find this handy dandy post here about arrays!"

I think I understand how to loop through an array, but how do I target the elements within individually?

// Place elements within an array ...
var a = document.getElementsByTagName("input");
var b = []; // Contains all checkboxes ...
for (var i = 0; i < a.length; i++) {
  if (a[i].type == "checkbox") {
    b.push(a[i]);
  }
};

console.log(a);
console.log(b);

// .classList.add("classToBeAdded");

I'm not too saavy with JS so any help I could get with this issue would be awesome, and I'll give my thanks in advance.

Regards, - B.

NOTE 04 Oct:

classList.add('class') isn't supported by all browsers indeed. The element.setAttribute('class', 'here_the_class'); is better supported.

– Camille Sébastien Niessen


NOTE 05 Oct:

For those that find this thread in passing, if you're interested in the finished result, you can find an updated Jsfiddle here.

– Beaniie

8
  • 4
    sorry, just to clarify, why can't you just use actual radiobuttons? Commented Oct 4, 2017 at 14:04
  • 2
    Add class before pushing to array: a[i].classList.add('classToBeAdded'); b.push(a[i]); Commented Oct 4, 2017 at 14:04
  • @ADyson great question, it's the application I'm using it doesn't provide usability for them. I.e I can add checkboxes to my project but not radio buttons as there is no option to. :\ Commented Oct 4, 2017 at 14:05
  • 2
    Um...huh? HTML's had radio buttons forever. What kind of application are you using that doesn't support them? Commented Oct 4, 2017 at 14:05
  • 1
    Euh, won't it break really soon since java applets are being phased out in all browsers? Commented Oct 4, 2017 at 14:12

3 Answers 3

1

This should do it

[].forEach.call(b, function(el) {
    el.classList.add("chkbox");
});

Snippet with your code:

// Place elements within an array ...
var a = document.getElementsByTagName("input");
var b = []; // Contains all checkboxes ...
for (var i = 0; i < a.length; i++) {
  if (a[i].type == "checkbox") {
    b.push(a[i]);
  }
};

[].forEach.call(b, function(el) {
	el.classList.add("chkbox");
});
@import url('https://fonts.googleapis.com/css?family=Open+Sans');
* {
  margin: 0;
  padding: 0;
}

h3 {
  color: #fff !important;
  padding-left: 0 !important;
}

#txt-field {
  position: relative;
  height: 100vh;
}

#col {
  width: 40%;
  margin: 0 auto;
  position: absolute;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
}

.spacer {
  margin-bottom: .5em;
}

.original {
  background-image: linear-gradient(to bottom, rgba(0, 0, 0, 0.4) 0%, rgba(0, 0, 0, 0.4) 100%), url(http://imageshack.com/a/img661/3954/bwalqa.jpg);
  background-position: center center;
  background-repeat: no-repeat;
  -webkit-background-size: cover;
  -moz-background-size: cover;
  -o-background-size: cover;
  background-size: cover;
}

.txt {
  font-family: "Open Sans", Arial, Helvetica, sans-serif !important;
  font-weight: 200 !important;
  letter-spacing: 4px !important;
  font-size: 26px !important;
  text-transform: uppercase;
  color: #272727;
  padding: .5em;
}

.stretch {
  box-sizing: border-box;
  width: 100%;
}

.shift {
  margin-top: 9%;
}

.boxes {
  box-sizing: border-box;
  width: 100%;
  margin: auto;
  padding: 1.5em;
  background: linear-gradient(to bottom, rgba(0, 0, 0, 0.6) 0%, rgba(0, 0, 0, 0.6) 100%);
  margin-top: 1.5em;
}


/*Checkboxes styles*/

input[type="checkbox"] {
  display: none;
}

input[type="checkbox"] + label {
  display: block;
  position: relative;
  padding-left: 35px;
  margin-bottom: 20px;
  font: 14px/20px 'Open Sans', Arial, sans-serif;
  color: #ddd;
  cursor: pointer;
  -webkit-user-select: none;
  -moz-user-select: none;
  -ms-user-select: none;
}

input[type="checkbox"] + label:last-child {
  margin-bottom: 0;
}

input[type="checkbox"] + label:before {
  content: '';
  display: block;
  width: 20px;
  height: 20px;
  border: 1px solid #6cc0e5;
  position: absolute;
  left: 0;
  top: 0;
  opacity: .6;
  -webkit-transition: all .12s, border-color .08s;
  transition: all .12s, border-color .08s;
}

input[type="checkbox"]:checked + label:before {
  width: 10px;
  top: -5px;
  left: 5px;
  border-radius: 0;
  opacity: 1;
  border-top-color: transparent;
  border-left-color: transparent;
  -webkit-transform: rotate(45deg);
  transform: rotate(45deg);
}
<div id="txt-field" class="original box">

  <div id="col">

    <h3 class="txt spacer">Checkboxes acting like radio buttons...</h3>

    <div class="boxes">
      <input type="checkbox" id="box-1" checked>
      <label for="box-1">Option One</label>
    </div>
    <div class="boxes">
      <input type="checkbox" id="box-2">
      <label for="box-2">Option Two</label>
    </div>
    <div class="boxes">
      <input type="checkbox" id="box-3">
      <label for="box-3">Option Three</label>
    </div>
    <div class="boxes">
      <input type="checkbox" id="box-4">
      <label for="box-4">Option Four</label>
    </div>
  </div>
</div>

Sign up to request clarification or add additional context in comments.

Comments

1

The logic is quite simple. When a checkbox is checked, you can loop through the list of checkboxes to uncheck them. Then, check the clicked checkbox.

Edit: Not sure what you want to do with chkbox class. If you want to select checked checkbox with CSS, you can use CSS pseudo-class selector :checked. Example:

.boxes > input[type="checkbox"]:checked {
  /* CSS here */
}

// Place elements within an array ...
var a = document.getElementsByTagName("input");
var b = []; // Contains all checkboxes ...
for (var i = 0; i < a.length; i++) {
  if (a[i].type == "checkbox") {
    b.push(a[i]);
  }
};

b.forEach(function (el) {
  el.addEventListener("change", function (ev) {
    b.forEach(function (innerEl) {
      innerEl.removeAttribute("checked");
    })
    el.setAttribute("checked", "checked");
  })
})
@import url('https://fonts.googleapis.com/css?family=Open+Sans');
* {
  margin: 0;
  padding: 0;
}

h3 {
  color: #fff !important;
  padding-left: 0 !important;
}

#txt-field {
  position: relative;
  height: 100vh;
}

#col {
  width: 40%;
  margin: 0 auto;
  position: absolute;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
}

.spacer {
  margin-bottom: .5em;
}

.original {
  background-image: linear-gradient(to bottom, rgba(0, 0, 0, 0.4) 0%, rgba(0, 0, 0, 0.4) 100%), url(http://imageshack.com/a/img661/3954/bwalqa.jpg);
  background-position: center center;
  background-repeat: no-repeat;
  -webkit-background-size: cover;
  -moz-background-size: cover;
  -o-background-size: cover;
  background-size: cover;
}

.txt {
  font-family: "Open Sans", Arial, Helvetica, sans-serif !important;
  font-weight: 200 !important;
  letter-spacing: 4px !important;
  font-size: 26px !important;
  text-transform: uppercase;
  color: #272727;
  padding: .5em;
}

.stretch {
  box-sizing: border-box;
  width: 100%;
}

.shift {
  margin-top: 9%;
}

.boxes {
  box-sizing: border-box;
  width: 100%;
  margin: auto;
  padding: 1.5em;
  background: linear-gradient(to bottom, rgba(0, 0, 0, 0.6) 0%, rgba(0, 0, 0, 0.6) 100%);
  margin-top: 1.5em;
}


/*Checkboxes styles*/

input[type="checkbox"] {
  display: none;
}

input[type="checkbox"] + label {
  display: block;
  position: relative;
  padding-left: 35px;
  margin-bottom: 20px;
  font: 14px/20px 'Open Sans', Arial, sans-serif;
  color: #ddd;
  cursor: pointer;
  -webkit-user-select: none;
  -moz-user-select: none;
  -ms-user-select: none;
}

input[type="checkbox"] + label:last-child {
  margin-bottom: 0;
}

input[type="checkbox"] + label:before {
  content: '';
  display: block;
  width: 20px;
  height: 20px;
  border: 1px solid #6cc0e5;
  position: absolute;
  left: 0;
  top: 0;
  opacity: .6;
  -webkit-transition: all .12s, border-color .08s;
  transition: all .12s, border-color .08s;
}

input[type="checkbox"]:checked + label:before {
  width: 10px;
  top: -5px;
  left: 5px;
  border-radius: 0;
  opacity: 1;
  border-top-color: transparent;
  border-left-color: transparent;
  -webkit-transform: rotate(45deg);
  transform: rotate(45deg);
}
<div id="txt-field" class="original box">

  <div id="col">

    <h3 class="txt spacer">Checkboxes acting like radio buttons...</h3>

    <div class="boxes">
      <input type="checkbox" id="box-1" checked="checked">
      <label for="box-1">Option One</label>
    </div>
    <div class="boxes">
      <input type="checkbox" id="box-2">
      <label for="box-2">Option Two</label>
    </div>
    <div class="boxes">
      <input type="checkbox" id="box-3">
      <label for="box-3">Option Three</label>
    </div>
    <div class="boxes">
      <input type="checkbox" id="box-4">
      <label for="box-4">Option Four</label>
    </div>
  </div>
</div>

1 Comment

The reason I'm adding a class is for peace of mind, I have no control over the id, name, value, + attributes. so I'm adding a unique handler for elements I want to target as there are other elements besides checkboxes within the project too I.e. Text areas, Text Fields etc.
1

You can add the classlist inside the for loop like this:

// Place elements within an array ...
var a = document.getElementsByTagName("input");
var b = []; // Contains all checkboxes ...
for (var i = 0; i < a.length; i++) {
  if (a[i].type == "checkbox") {
    a[i].setAttribute("class", "classToBeAdded"); 
    b.push(a[i]);
  }
};

Tested it in your Fiddle and it seems to work

2 Comments

This seems clean but judging by your answer, how do you think it will hold up across different/older browsers?
classList.add('class') isn't supported by all browsers indeed. The element.setAttribute('class', 'here_the_class'); is better supported

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.