Custom styled checkbox not working properly - javascript

Currently I'm using multiple blocks of the following code as my custom styled checkbox:
<div class="row-fluid">
<div class="span12 card card-even">
<div>
<h3><label class="checkbox">
<i class="icon-check-empty"></i>
<input type="checkbox" value="1" />
</label></h3>
</div>
</div>
</div>
The JS:
jQuery.fn.extend({
shinyCheckbox: function() {
var setIcon;
setIcon = function($el) {
var checkbox, iclass;
checkbox = $el.find("input[type=checkbox]");
iclass = "";
if (checkbox.is(":checked")) {
iclass = "icon-ok";
} else {
iclass = "icon-check-empty";
}
return $el.find("i[class^=icon-]").removeClass("icon-check").removeClass("icon-check-empty").addClass(iclass);
};
this.find("input[type=checkbox]").change(function() {
return setIcon($(this).parents("label.checkbox"));
});
return this.each(function(i, el) {
return setIcon($(el));
});
}
});
$(document).ready(function() {
return $("label.checkbox").shinyCheckbox();
});
Im able to achieve my requirement by styling the icon-check-empty & icon-check classes but when i click any checkbox only the first checkbox gets activated.
How can i use the this keyword to solve the issue such that the correct checkbox is activated?

This is the way I'd do it, based on your code:
jQuery.fn.extend({
shinyCheckbox: function () {
var setIcon = function ($el) {
var checkbox = $el.find("input[type=checkbox]"), checked = checkbox.is(':checked');
checkbox.val(+checked);
return $el.find("i[class^=icon-]").removeClass("icon-check-empty icon-ok").addClass(function () {
return checked ? "icon-ok" : "icon-check-empty";
});
};
this.find("input[type=checkbox]").on('change', function () {
return setIcon($(this).closest("label.checkbox"));
});
return this.each(function (i, el) {
return setIcon($(el));
});
}
});
$(document).ready(function () {
$("label.checkbox").shinyCheckbox();
});
The main issue was that you weren't removing the icon-ok class, only the icon-check class. I also cleaned the code up a little.
Here it is working: http://jsfiddle.net/W88fk/1/

you can try
jQuery.fn.extend({
shinyCheckbox: function() {
return this.each(function() {
var el=$(this),checkbox = el.find("input[type=checkbox]");
checkbox.change(function() {
var iclass = checkbox.is(":checked")?"icon-ok":"icon-check-empty";
el.find("i[class^=icon-]").removeClass().addClass(iclass);
var cval= checkbox.is(":checked")?0:1;
checkbox.val(cval);
});
});
}
});
$(document).ready(function() {
$("label.checkbox").shinyCheckbox();
});
toogle class and value http://jsfiddle.net/rWFMm/1/

Related

Why can't I update an input element inside click event?

Why does the input element not get updated?
function route() {
let textfield = {
inputEl: document.querySelector('#textfield'),
setValue: function(str) {
this.inputEl.value = str;
}
};
textfield.inputEl.addEventListener('click', function(event) {
document.body.innerHTML += '<button id="select">Select</button>';
owner(textfield);
});
}
function owner(controller) {
document.querySelector('#select').addEventListener('click', function(event) {
controller.setValue("Hello Universe!");
});
}
route();
I know how to go around this problem but i prefer to use controller.setValue() to update the input.
UPDATED
I have updated the code below - hopefully this is closer to what you are trying to achieve.
I needed to add a container where to place the button (instead of adding it to the body) - so added a wrapper container like this:
<div id="container">
<input type="text" id="textfield" />
</div>
Then, we can append the button to it as a child, like this:
document.getElementById('container').appendChild(btn);
See updated code below
function route() {
let textfield = {
inputEl: document.querySelector('#textfield'),
setValue: function(str) {
this.inputEl.value = str;
}
};
textfield.inputEl.addEventListener('click', function(event) {
// add the button if it's not already in there
if(document.getElementById('select')){
return;
}
let btn = document.createElement('button');
btn.id = 'select';
btn.innerHTML = 'Select';
document.getElementById('container').appendChild(btn);
owner(textfield);
});
}
function owner(controller) {
document.getElementById('select').addEventListener('click', function(event) {
controller.setValue("Hello Universe!");
});
}
route();
<div id="container">
<input type="text" id="textfield" />
</div>

jQuery: Change div text on click, will not work more than once

This is my code:
var woocommerce_price_displayed = $('.product_intial_price').find('.woocommerce-Price-amount').text();
$(".yearly-package").click(function () {
var yearprice = $('#year_price').text();
$('.electro-price').find('.woocommerce-Price-amount').text(function () {
return $(this).text().replace(woocommerce_price_displayed, yearprice);
});
})
$(".halfyear-package").click(function () {
var halfyearprice = $('#halfyear_price').text();
$('.electro-price').find('.woocommerce-Price-amount').text(function () {
return $(this).text().replace(woocommerce_price_displayed, halfyearprice);
});
})
$(".single-package").click(function () {
var oneprice = $('#one_price').text();
$('.electro-price').find('.woocommerce-Price-amount').text(function () {
return $(this).text().replace(woocommerce_price_displayed, oneprice);
});
})
When div is clicked, the price will change. However, if I click again on a different button - the price will not change again.
What's wrong? Why will it work on the first click only?
This is basically the html for each pack:
<div class="ps-package single-package first-pack" data-val="1">
<div class="ps-name">Single Package</div>
<div id="one_price" class="ps-price">$99</div>
</div>
<span class="electro-price"><ins><span class="woocommerce-Price-amount amount"><span class="woocommerce-Price-currencySymbol">$</span>99.00</span></ins> <del><span class="woocommerce-Price-amount amount"><span class="woocommerce-Price-currencySymbol">$</span>150.00</span></del></span>
When I add var woocommerce_price_displayed = oneprice; for each of the function like this:
$(".halfyear-package").click(function () {
var halfyearprice = $('#halfyear_price').text();
$('.electro-price').find('.woocommerce-Price-amount').text(function () {
return $(this).text().replace(woocommerce_price_displayed, halfyearprice);
woocommerce_price_displayed = halfyearprice;
});
It will not work at all, not even once! Why?

Dropdown Value selected not changing when option selected changes Java Script

Following is Html for Drop down
<select name="fancySelect" onchange="test()" class="makeMeFancy" id="drop1">
<option value="0" selected="selected" data-skip="1" data-icon="assets/images/large/bitcoin.png" data-html-text="BTC<i&gt">BTC<span class="select_coin_button_arrow">▾</span></option>
<option value="1" data-icon="assets/images/small/bitcoin.png" data-html-text="BTC<i&gt" >BTC</option>
<option value="17" data-icon="assets/images/small/ether.png" data-html-text="ETH<i>">ETH</option>
</select>
and following is js function test()
function test() {
var e = document.getElementById("drop1");
var strUser = e.options[e.selectedIndex].value;
console.dir(strUser)
}
How to Print
Follwing is Jquery Script working on Dropdown
As code is working without Jquery Script,There seems to be problem
in following JQuery
$(document).ready(function () {
// The select element to be replaced:
var select = $('select.makeMeFancy');
var selectBoxContainer = $('<div>', {
width: select.outerWidth(),
className: 'tzSelect',
html: '<div class="selectBox"></div>'
});
var dropDown = $('<ul>', {className: 'dropDown'});
var selectBox = selectBoxContainer.find('.selectBox');
// Looping though the options of the original select element
select.find('option').each(function (i) {
var option = $(this);
if (i == select.attr('selectedIndex')) {
selectBox.html(option.text());
}
// As of jQuery 1.4.3 we can access HTML5
// data attributes with the data() method.
if (option.data('skip')) {
return true;
}
// Creating a dropdown item according to the
// data-icon and data-html-text HTML5 attributes:
var li = $('<li>', {
html: '<img src="' + option.data('icon') + '" /><span>' +
option.data('html-text') + '</span>'
});
li.click(function () {
selectBox.html(option.text());
dropDown.trigger('hide');
// When a click occurs, we are also reflecting
// the change on the original select element:
select.val(option.val());
return false;
});
dropDown.append(li);
});
selectBoxContainer.append(dropDown.hide());
select.hide().after(selectBoxContainer);
// Binding custom show and hide events on the dropDown:
dropDown.bind('show', function () {
if (dropDown.is(':animated')) {
return false;
}
selectBox.addClass('expanded');
dropDown.slideDown();
}).bind('hide', function () {
if (dropDown.is(':animated')) {
return false;
}
selectBox.removeClass('expanded');
dropDown.slideUp();
}).bind('toggle', function () {
if (selectBox.hasClass('expanded')) {
dropDown.trigger('hide');
}
else dropDown.trigger('show');
});
selectBox.click(function () {
dropDown.trigger('toggle');
return false;
});
// If we click anywhere on the page, while the
// dropdown is shown, it is going to be hidden:
$(document).click(function () {
dropDown.trigger('hide');
});
});
$(document).ready(function () {
// The select element to be replaced:
var select = $('select.makeMeFancydrop');
var selectBoxContainer = $('<div>', {
width: select.outerWidth(),
className: 'tzSelect',
html: '<div class="selectBox"></div>'
});
var dropDown = $('<ul>', {className: 'dropDown'});
var selectBox = selectBoxContainer.find('.selectBox');
// Looping though the options of the original select element
select.find('option').each(function (i) {
var option = $(this);
if (i == select.attr('selectedIndex')) {
selectBox.html(option.text());
}
// As of jQuery 1.4.3 we can access HTML5
// data attributes with the data() method.
if (option.data('skip')) {
return true;
}
// Creating a dropdown item according to the
// data-icon and data-html-text HTML5 attributes:
var li = $('<li>', {
html: '<img src="' + option.data('icon') + '" /><span>' +
option.data('html-text') + '</span>'
});
li.click(function () {
selectBox.html(option.text());
dropDown.trigger('hide');
// When a click occurs, we are also reflecting
// the change on the original select element:
select.val(option.val());
return false;
});
dropDown.append(li);
});
selectBoxContainer.append(dropDown.hide());
select.hide().after(selectBoxContainer);
// Binding custom show and hide events on the dropDown:
dropDown.bind('show', function () {
if (dropDown.is(':animated')) {
return false;
}
selectBox.addClass('expanded');
dropDown.slideDown();
}).bind('hide', function () {
if (dropDown.is(':animated')) {
return false;
}
selectBox.removeClass('expanded');
dropDown.slideUp();
}).bind('toggle', function () {
if (selectBox.hasClass('expanded')) {
dropDown.trigger('hide');
}
else dropDown.trigger('show');
});
selectBox.click(function () {
dropDown.trigger('toggle');
return false;
});
// If we click anywhere on the page, while the
// dropdown is shown, it is going to be hidden:
$(document).click(function () {
dropDown.trigger('hide');
});
});
$(document).ready(function () {
$("#drop1").click(function () {
});
});
As mentioned in comments, your HTML is completelly changed, by jQuery script you use. Btw, it is very old script, and seems compatible just with older versions of jQuery.... However, instead <select> element which is removed, now you have <ul> with .dropDown class. To get selected value, you can do something like this:
$(".dropDown li").click(function () {
console.log($(this).text())
});
Demo:
$(document).ready(function () {
// The select element to be replaced:
var select = $('select.makeMeFancy');
var selectBoxContainer = $('<div>', {
width: select.outerWidth(),
className: 'tzSelect',
html: '<div class="selectBox"></div>'
});
var dropDown = $('<ul>', {className: 'dropDown'});
var selectBox = selectBoxContainer.find('.selectBox');
// Looping though the options of the original select element
select.find('option').each(function (i) {
var option = $(this);
if (i == select.attr('selectedIndex')) {
selectBox.html(option.text());
}
// As of jQuery 1.4.3 we can access HTML5
// data attributes with the data() method.
if (option.data('skip')) {
return true;
}
// Creating a dropdown item according to the
// data-icon and data-html-text HTML5 attributes:
var li = $('<li>', {
html: '<img src="' + option.data('icon') + '" /><span>' +
option.data('html-text') + '</span>'
});
li.click(function () {
selectBox.html(option.text());
dropDown.trigger('hide');
// When a click occurs, we are also reflecting
// the change on the original select element:
select.val(option.val());
return false;
});
dropDown.append(li);
});
selectBoxContainer.append(dropDown.hide());
select.hide().after(selectBoxContainer);
// Binding custom show and hide events on the dropDown:
dropDown.bind('show', function () {
if (dropDown.is(':animated')) {
return false;
}
selectBox.addClass('expanded');
dropDown.slideDown();
}).bind('hide', function () {
if (dropDown.is(':animated')) {
return false;
}
selectBox.removeClass('expanded');
dropDown.slideUp();
}).bind('toggle', function () {
if (selectBox.hasClass('expanded')) {
dropDown.trigger('hide');
}
else dropDown.trigger('show');
});
selectBox.click(function () {
dropDown.trigger('toggle');
return false;
});
// If we click anywhere on the page, while the
// dropdown is shown, it is going to be hidden:
$(document).click(function () {
dropDown.trigger('hide');
});
});
$(document).ready(function () {
$(".dropDown li").click(function () {
console.log($(this).text())
});
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.5.1/jquery.min.js"></script>
<select name="fancySelect" onchange="test()" class="makeMeFancy" id="drop1">
<option value="0" selected="selected" data-skip="1" data-icon="assets/images/large/bitcoin.png" data-html-text="BTC<i&gt">BTC<span class="select_coin_button_arrow">▾</span></option>
<option value="1" data-icon="assets/images/small/bitcoin.png" data-html-text="BTC<i&gt" >BTC</option>
<option value="17" data-icon="assets/images/small/ether.png" data-html-text="ETH<i>">ETH</option>
</select>

Cant add a Jquery plugin inside a loop

Hi I have a JQuery plugin that takes an array of Orders and creates rows for each Order in the array. No issues here. However if one of these Orders meets a condition it should add a textbox in one of the TD cells. When I debug I can see it adding the textBox but when the next row is created which requires a textBox the previous textbox gets removed. i have this inside a close so not sure what to do. So the result is I only get textboxes in the last row.
If I add the textBox as html it works fine but I want it as a plugin as I need to bind several events KeyUp/Down MouseWheel, Click. etc
The textbox plugin control (gep_inputcontrol) just creates the html and binds events, nothing fancy.
Any help appreciated.
var _table = $('#orderTable', this);
for (var i = 0; i < params.orders.length; i++) {
var row = createRow(params.orders[i]);
_table.append(row);
}
function createRow(order){
var unmatchedStake = (order.requestedStake - order.matchedStake);
var partMatched = (unmatchedStake > 0);
var tr = $(String.format('<tr id="order_{0}" class="{1}"/>' ,order.orderId, ((i % 2) == 0) ? 'gep-altrow' : 'gep-row'));
tr.append(String.format('<td class="gep-icon gep-status">{0}</td>', order.orderStatusId));
tr.append(String.format('<td class="gep-selectionname">{0} {1} {2}</td>', GBEUtils.getEventName(order.eventClassifierFullName()), gep._settings.resources.general.polarity[order.polarityId], order.selectionName()));
tr.append(String.format('<td class="gep-odds betSlipRowPrice">{0}</td>', order.averageMatchedPrice));
tr.append(String.format('<td class="gep-unmatched betSlipRowStake">{0}</td>', com.base.formatDecimal(order.requestedStake - order.matchedStake,2)));
tr.append(String.format('<td class="gep-matched">{0}</td>', com.base.formatDecimal(order.matchedStake,2)));
tr.append(String.format('<td class="gep-action"><span class="gep-icon"/></td>', order.orderStatusId));
//var tablerow = $(String.format('#order_{0}',order.orderId), _table);
//(function (_table, tr, i, unmatchedStake, tablerow) {
if(unmatchedStake > 0)//part matched
{
$('.gep-unmatched', tr).gep_inputcontrol({
type:'STAKE',
ccSymbol:clientObject.state.ccSymbol,
value: unmatchedStake,
decimalValue:unmatchedStake,
onMouseWheeled: function(e, ev){
gep.inputControlWheeled(e, ev);
gep.calculateRowProfit(e, false);
return false;
},
onArrowClicked: function(e){
gep.onArrowClick(e);
return false;
}
});
//$('.gep-unmatched', tr).html($('.gep-unmatched', tr).html());
$('.gep-odds', tr).gep_inputcontrol({
type:'PRICE',
value:order.requestedPrice,
decimalValue:order.requestedPrice,
onMouseWheeled: function(e, ev){
gep.inputControlWheeled(e, ev);
gep.calculateRowProfit(e, false);
return false;
},
onArrowClicked: function(e){
gep.onArrowClick(e);
return false;
}
});
$('.gep-action .gep-icon', tr).addClass("gep-icon-delete");
$('.gep-icon-delete', tr).bind("click", function(){
alert("delete");
toggleCurrentBetSlipBet(this);
return false;
});
}
// })(_table, tr, i, unmatchedStake, tablerow);
return tr;
}
The textbox plugin creates a table with input box and two anchor tags.
/********************
GEP.gep_inputcontrol // stake input, price input box
********************/
(function ($) {
var _templatePrice = $('<table class="gep-inputcontrol" cellpadding="0" cellspacing="0"><tr><td rowspan="2"><input type="text" size="5" class="gep-inputcontrol-price" /></td><td><a tabindex="-1" href="javascript:void(0);" class="gep-inputup"></a></td></tr><tr><td> <a tabindex="-1" href="javascript:void(0);" class="gep-inputdown"></a> </td></tr></table>');
var _templateStake = $('<table class="gep-inputcontrol" cellpadding="0" cellspacing="0"><tr><td rowspan="2"><span class="gep-ccsymbol" /> <input type="text" size="5" class="gep-inputcontrol-stake" /> </td> <td> <a tabindex="-1" href="javascript:void(0);" class="gep-inputup"></a></td></tr><tr><td> <a tabindex="-1" href="javascript:void(0);" class="gep-inputdown"></a> </td></tr> </table>');
var _template;
var _settings = null;
var _instance;
var methods = {
init: function (options) {
_settings = options;
//options.type = 'STAKE'or 'PRICE'
_template = (options.type == 'STAKE')? _templateStake: _templatePrice;
$('.gep-ccsymbol',_template).html(options.ccSymbol);
this.html(_template);
$('input', this).attr('value', options.value);
$('input', this).attr('initialvalue', options.decimalValue);
$('input', this).attr('decimalValue', options.decimalValue);
$('input', this).bind("mousewheel", function (ev) {
_settings.onMouseWheeled.call(null, this, ev.originalEvent);
});
$('.gep-inputup', this).bind("click", function (e) {
_settings.onArrowClicked.call(null, this);
});
$('.gep-inputdown', this).bind("click", function (e) {
_settings.onArrowClicked.call(null, this);
});
_instance = this;
return this;
},
show: function (params) {
alert("show" + params);
},
hide: function () {
// GOOD
},
update: function (content) {
// !!!
}
};
$.fn.gep_inputcontrol = function (method) {
// Method calling logic
if (methods[method]) {
return methods[method].apply(this, Array.prototype.slice.call(arguments, 1));
} else if (typeof method === 'object' || !method) {
return methods.init.apply(this, arguments);
} else {
$.error('Method ' + method + ' does not exist on jQuery.gep_inputcontrol');
}
};
})(jQuery);
To elaborate a bit more, I did some small unit tests
This works..
$('.gep-odds', clientObject.liveBetsPane).gep_inputcontrol({
type: 'PRICE',
value: 5,
decimalValue: 5,
onMouseWheeled: function (e, ev) {
gep.inputControlWheeled(e, ev);
gep.calculateRowProfit(e, false);
return false;
},
onArrowClicked: function (e) {
gep.onArrowClick(e);
return false;
}
});
This does NOT work...(Only puts TEXT box in last row) But I need to do it this way as I need values of each row.
$('.gep-odds', clientObject.liveBetsPane).each(function () {
$(this).gep_inputcontrol({
type: 'PRICE',
value: 5,
decimalValue: 5,
onMouseWheeled: function (e, ev) {
gep.inputControlWheeled(e, ev);
gep.calculateRowProfit(e, false);
return false;
},
onArrowClicked: function (e) {
gep.onArrowClick(e);
return false;
}
});
});
I removed dollar from the template and it worked fine.
var _templatePrice = $('<table cla...
is now
var _templatePrice = '<table cla...
Although it sets the html for the last row it was moving for the other rows.
Thanks to me.... :)

Help With URL parameter to open tabs info

Need some help with the script below. I would like to add the ability to pass a url parameter that would open one of the tabs based on the URL#tabinfo. Any help would be great thanks.
(function ($) {
function getactTabAnc() {
return this.find('.active>a')[0];
}
function getContentId(tabAnchorS) {
return $(tabAnchorS).attr('href').replace('#', '');
}
function applyStyles(newActTabAnc) {
var actTabAnc = newActTabAnc || getactTabAnc.apply(this), activeContentId = getContentId(actTabAnc);
this.find('a').each(function () {
var $cur = $(this), curContentId = getContentId(this);
if (activeContentId === curContentId) {
$cur.closest('li').addClass('active');
$('#' + curContentId).show();
}
else {
$cur.closest('li').removeClass('active');
$('#' + curContentId).hide();
}
});
}
$.fn.tabs = function () {
return this.each(function () {
var $tabTainer = $(this);
applyStyles.apply($tabTainer);
$tabTainer.find('a').click(function (e) {
console.log('clicked');
var actTabAnc = getactTabAnc.apply($tabTainer), isActive = this === actTabAnc;
e.preventDefault();
if (!isActive) {
applyStyles.apply($tabTainer, [this]);
}
});
});
};
})(jQuery);
<ul id="tabsHolder">
<li class="active">Header 1</li>
<li>Header 2</li>
</ul>
<div id="tabId1">Content 1</div>
<div id="tabId2">Content 2</div>
Look at window.location.hash and onhashchange event. If ('onhashchange' in window) is false then you need to poll for the hash changing.
There exists libraries to abstract this away.

Categories

Resources