Best way toggle between three classes for an Element - javascript

I have 3 buttons, which on click would the change the layout to desktop , mobile and tab view. . So I'm calling the same method toggleView(), passing different param for different buttons. So i have written the method to toggle between the 3 classes. It's working fine. I feel there would be a better way to do this in Javascript. I was not able to find out by search
It would be of great help if someone suggest a optimised solution to this
<div class="responsive-buttons">
<button class="btn mb-3" type="button" #click="toggleView('preview-desktop')">Desktop</button>
<button class="btn mb-3" type="button" #click="toggleView('preview-tab')">Tablet</button>
<button class="btn mb-3" type="button" #click="toggleView('preview-mobile')">Mobile</button>
</div>
toggleView(message){
var el = document.querySelector("#previewWrapper");
if(message=='preview-desktop') {
el.classList.remove('preview-tab', 'preview-mobile');
el.classList.add(message);
} else if(message=='preview-tab') {
el.classList.remove('preview-desktop', 'preview-mobile');
el.classList.add(message);
} else if(message=='preview-mobile') {
el.classList.remove('preview-desktop', 'preview-tab');
el.classList.add(message);
}
}

Use class bindings on #previewWrapper like this:
<div id="previewWrapper" :class="previewWrapperClass" />
...
data: {
return {
currentPreviewMode: null
}
},
computed: {
previewWrapperClass () {
if (!this.currentPreviewMode) {
return null
}
return {
[this.currentPreviewMode]: true
}
}
},
methods: {
toggleView(message){
this.currentPreviewMode = message
}
}
See Class and style bindings

Related

Javascript that works outside an Alpine.js template doesn't work inside it

I have a page that uses Alpine.js for dynamically creating and removing blocks of content with form elements in them.
Part of the block is two sets of radio buttons. At the moment, people can select options from both groups, but I want to change it so that if they select an option from one group, it unchecks the value from the other and vice versa.
At the moment, what I have is:
const shirtSizes = document.querySelectorAll('.shirt-sizes'); // scope only to the parent
shirtSizes.forEach((player) => {
const kidsRadios = player.querySelectorAll('.size-kids');
const adultsRadios = player.querySelectorAll('.size-adults');
kidsRadios.forEach((kid) => {
kid.addEventListener('change', (event) => {
adultsRadios.forEach((adult) => {
adult.checked = false;
});
});
});
adultsRadios.forEach((adult) => {
adult.addEventListener('change', (event) => {
kidsRadios.forEach((kid) => {
kid.checked = false;
});
});
});
});
(That could probably be written better but that's not the problem at the moment.)
I have a CodePen that shows that working fine.
But my actual project is constructed like this:
<div x-data="addPlayers()" x-init="addNewPlayer">
<div class="mb-8">
<template x-for="(field, index) in fields" :key="index">
<input
x-model="field.kids"
type="radio"
:name="`size_kids_${index + 1}`"
:id="`size-kids-8_${index + 1}`"
value="8"
>
…
</template>
</div>
<button type="button" #click="addNewPlayer()">Add player</button>
</div>
<script>
function addPlayers() {
return {
fields: [],
addNewPlayer() {
this.fields.push({
kids: '',
adults: ''
});
calcTotal(count);
count++;
},
removePlayer(index) {
this.fields.splice(index, 1);
count = index;
calcTotal(count);
}
}
}
</script>
I've created another CodePen which might illustrate better how it's all put together and you can see in this one that the same js for resetting the radios doesn't work.
So why doesn't it work in the Alpine version? And what do I need to do to get it to work?

In jQuery, Is it possible to store a wildcard for further use in a function?

For example, if I have 4 buttons and divs such as these:
<button class="country-denmark"></button>
<button class="country-denmark"></button>
<button class="country-germany"></button>
<button class="country-norway"></button>
<div class="country-denmark"></div>
<div class="country-denmark"></div>
<div class="country-germany"></div>
<div class="country-norway"></div>
In jQuery, I have an on-click function with a wildcard selector, like this:
$("button[class^='country-']").on('click', function() {
// Add class to divs that match the wildcard of this
$("div[class^='country-']").addClass( className );
});
If I clicked on the button with the class country-germany, how could I store just the "germany" part and then find the div(s) that match that same wildcard?
I'd go with sessionStorage
But I'd also update the elements a little to make it a little more straightforward to get the intended-value:
<button class="country-denmark" data-for="denmark"></button>
<button class="country-denmark" data-for="denmark"></button>
<button class="country-germany" data-for="germany"></button>
<button class="country-norway" data-for="norway"></button>
<div class="country-denmark" data-country="denmark"></div>
<div class="country-denmark" data-country="denmark"></div>
<div class="country-germany" data-country="germany"></div>
<div class="country-norway" data-country="norway"></div>
From here you just set the item in sessionStorage:
$("button[class^='country-']").on('click', function() {
let country = $(this).data("for");
let selectedCountry;
$("div").each(function() {
if ($(this).data("country") == country) {
selectedCountry = $(this).data("country");
}
});
sessionStorage.setItem("selectedCountry", selectedCountry);
});
To read the value later, use sessionStorage.getItem()
var selectedCountry = sessionStorage.getItem("selectedCountry");
It is been quite a while since I touched jQuery, but if I remember correctly you can use jQuery-this for that.
$("button[class^='country-']").on('click', function() {
// Add class to divs that match the wildcard of this
const className = $(this).attr('class')
$(`div.${className}`).addClass( className );
});

Pass value from button in HTML to function in Javascript

I'm trying to pass some value from button, which is located in HTML document, to the Javascript function, which is located in other document, but it doesn't work. I also tried with getElementById(), but it still didn't work. What's the problem? I would appreciate any help. Thanks in advance!
index.html
<script src="../scripts/appearances_2.js"></script>
/...
<div id="appearances_2_chart">
<div>
<button id="starting" onclick="update_view('starting')">Starting players</button>
<button id="substitution" onclick="update_view('substitution')">Substitution players</button>
</div>
</div>
/...
appearances_2.js
document.addEventListener('DOMContentLoaded', function(e) {
//...
function update_view(id) {
d3.csv("../../data/appearances.csv", function(data) {
data.sort(function(b, a) {
if (id == 'starting')
{
return a.starting - b.starting;
}
else if (id == 'substitution')
{
return a.substitution - b.substitution;
}
});
/...
You can use, event as an object to be passed and access the value as (in order to get the id),
event.target.getAttribute('id')
You need to modify the button code as,
<button id="starting" onclick="update_view(event)">Starting players</button>
and in function,
update_view(event){....}
and access the id using the target object as mentioned in the first code.
Update:-
function update_view(event) {
d3.csv("../../data/appearances.csv", function (data) {
data.sort(function (b, a) {
if (event.target.getAttribute('id') === 'starting') {
return a.starting - b.starting;
}
else if (event.target.getAttribute('id') === 'substitution') {
return a.substitution - b.substitution;
}
})
})
};
<button id="starting" onclick="update_view(event)">Starting players</button>
<button id="substitution" onclick="update_view(event)">Substitution players</button>

"Twitter like" follow button

I want to create an like button like twitter, i used from this code:
$(document).ready(function(){
$('.btn-follow').on('mouseover', function(e){
if ($(this).hasClass('following')){
$(this).removeClass('btn-primary').addClass('btn-danger').text('UnFollow');
}
})
$('.btn-follow').on('mouseleave',function(e){
if ($(this).hasClass('following')){
$(this).text('Following').removeClass('btn-danger').addClass('btn-primary');
}
})
$('.btn-follow').on('click',function(e){
$(this).toggleClass('following follow')
if ($(this).hasClass('follow')){
alert('unfollow')
$(this).text('Follow').removeClass('btn-danger')
}else{
alert('follow')
$(this).text('Following')
}
})
});
and in html i have this:
<button class="btn btn-primary btn-follow following">Following</button>
<br />
<br />
<button class="btn btn-follow follow">Follow</button>
but i think it 's very dirty code and have some bugs. How i can fix this code?
Ok the main problem was css specificity not letting btn-danger class take any effect over btn-success.
So as a solution i used an empty class that i made up. To track if the button is being followed or not.
Whenever i added btn-success i added following class. And through class, as you did, i was able to track the state of the button.
With bootstrap!!!
http://jsfiddle.net/vjZRA/1/
Without bootstrap:http://jsfiddle.net/vjZRA/
Code Below:
var btn = $('.btn');
btn.click(h);
btn.hover(hin, hout);
function hin() {
if (btn.hasClass('follow')) {
btn.text('Stop Following');
btn.removeClass('btn-success');
btn.addClass('btn-danger');
} else {
btn.addClass('btn-primary');
}
}
function hout() {
if (btn.hasClass('follow')) {
btn.text('Following');
btn.removeClass('btn-danger');
btn.addClass('btn-success follow');
}
btn.removeClass('btn-primary');
}
function h() {
if (btn.hasClass('follow')) {
btn.removeClass('btn-success follow');
btn.text('Follow');
btn.removeClass('btn-danger');
} else {
btn.text('Following');
btn.addClass('btn-success follow');
}
}
and then add css in style tag or wherever you want
.follow{}

Change className for a component when a button is disabled using wicket?

For example:
<span class="button4">
<button wicket:id="saveButton" type="submit">
<wicket:message key="modalArchiveAccount.button.save" />
</button>
</span>
From java code I set this button to be enabled or disabled, the problem is that I don't know how to change the span className when button is disabled.
Wrap a WebMarkupContainer around your button
add(new WebMarkupContainer("spanId") {
{
add(new Button<String>("saveButton")){
[... button logic...]
};
}
});
<span wicket:id="spanId">
<button wicket:id="saveButton" type="submit">
<wicket:message key="modalArchiveAccount.button.save" />
</button>
</span>
then add a new AttributeModifier("class",...) or AttributeAppender("class",...) to the WebMarkupContainer that uses the same logic as you use to disable the button.
var jSpan = $('#saveButton').parent();
jSpan.removeClass( 'button4' );
jSpan.addlass( someclass );
Here is the example code:
final Button button=new Button("buttn") {
public void onSubmit() {
System.out.println("change....");
setEnabled(false);
};
};
button.add(new AttributeModifier("class", true, new Model<Serializable>() {
#Override
public Serializable getObject() {
if (button.isEnabled())
return "your_enabled_class";
else return "your_disabled_class";
}
}));

Categories

Resources