I have this code:
<select multiple="multiple" class="image-picker show-html">
<option data-img-src="http://placehold.it/125x200" value="1">SportField 1</option>
<option data-img-src="http://placehold.it/125x200" value="2">SportField 2</option>
<option data-img-src="http://placehold.it/125x200" value="3">SportField 3</option>
<option data-img-src="http://placehold.it/125x200" value="4">SportField 4</option>
</select>
And then using Image Picker Plugin I wrote this piece of code:
<script>
$(function() {
$("select").imagepicker({
show_label: true,
changed: function() {
},
clicked: function() {
},
selected: function() {
console.log(this.attr('value'));
}
})
});
</script>
What I need here and need some help from community is allow just some certain of choices. Right now the only choices allowed are:
SportField1-SportField2
SportField3-SportField4
SportField1-SportField2-SportField3-SportField4
What this means? When I pick the SportField1 I can select SportField2 meaning adjacent images but if you can see the latest allowed choice is the fourth SportField. How I can achieve this?
EDIT
Based on #Ruud suggestions I made the following changes, the HTML code is this one:
<select name="choice" id="choice">
<option value="1">A</option>
<option value="2">B</option>
<option value="3">C</option>
<option value="4">D</option>
<option value="5">AB</option>
<option value="6">CD</option>
<option value="7">ABCD</option>
</select>
<img src="http://placehold.it/125x200" data-id="A">
<img src="http://placehold.it/125x200" data-id="B">
<img src="http://placehold.it/125x200" data-id="C">
<img src="http://placehold.it/125x200" data-id="D">
<script>
$(function() {
$('choice').change(function() {
});
});
</script>
Now to explain a bit:
if I pick choice A in select then image with data-id=1 should get a line (this can be done by CSS)
if I pick choice B in select then image with data-id=2 should get a line (this can be done by CSS)
if I pick choice C in select then image with data-id=3 should get a line (this can be done by CSS)
if I pick choice D in select then image with data-id=4 should get a line (this can be done by CSS)
if I pick choice AB in select then image with data-id=1 and image with data-id=2 should get a line (this can be done by CSS)
if I pick choice CD in select then image with data-id=3 and image with data-id=3 should get a line (this can be done by CSS)
if I pick choice ABCD in select then all images should get a line (this can be done by CSS)
How I can achieve this on SELECT change?
The following function checks whether a particular image belongs in the current selection.
It does require you to use the picture IDs (e.g. ABCD) in the option's value; this seemed more logical to me than the 'magic numbers' 1-7.
function isSelected(selector, image) {
return selector.find(':selected').text().indexOf(image.data('id')) >= 0;
};
It wasn't clear to me what you meant by "image should get a line", so I just made a simple demo that applies a CSS class to the selected images.
Please note I added the hash in $('#choice'); choice is an id, not a tag name.
$(function() {
$('#choice').change(function() {
var choice = $(this); // = $('#choice');
var allImages = $('img');
var selectedImages = allImages.filter(function() { return isSelected(choice, $(this)); });
allImages.removeClass('myprecious');
selectedImages.addClass('myprecious');
});
});
FYC, here's a demo: http://jsfiddle.net/UrKBZ/
Related
I have some javascript in one of my survey questions that changes the formatting of a certain field. It works great, but I would like to apply the same code to several other questions. Obviously, I can simply copy and paste onto each question, but is there any way to have the code set in a single location so that it is more maintainable? I've looked on a number of forums but haven't been able to find a solution. Thanks in advance for your help.
EDIT:
Here is the JavaScript code that I would like to be repeated for multiple questions:
{
/*Place your JavaScript here to run when the page is fully displayed*/
jQuery("#"+this.questionId+" select option:first-child").text("Select one");
jQuery("#"+ this.questionId + " option").each(function () {
if (jQuery(this).text().includes("\"\"")) {
jQuery(this).hide();
}else{
title = jQuery(this).text()
title = title.match(/".*"/)
if(title != null && title[0].length > 30){
newTitle = title[0].match(/^.{30}.*?\s/)[0]
if(newTitle != title){
newTitle = newTitle + "...\""
}
text = jQuery(this).text()
jQuery(this).text(text.replace(title[0],newTitle))
}
}
});
});
Basically, there is some embedded data preloaded for each contact, and several questions involve a dropdown menu that allows users to select which of their data elements was relevant to a project. This code ensures that blank or missing data does not get included in the dropdown, and also if the option is too many characters long, it gets truncated. Multiple questions include the same dropdown options, but differ in other ways.
Make your code a function and put it in the Qualtrics header. Call the function from each question where it applies.
In the header:
<script>
myFunction(qobj) {
jQuery("#"+qobj.questionId+" select option:first-child")...etc...
}
</script>
Then in your questions:
Qualtrics.SurveyEngine.addOnload(function() {
myFunction(this);
});
Add the same class to each of your question (I chose myQuestion class) then query it.
Loop through each select and find the option:first-child and then find the options and loop through each of them.
$('.myQuestion select').each(function(selectIndex, select){
// loop through each select
// for each select find all the options
$(this).find("option:first-child").text("Select one");
$(this).find('option').each(function(optionIndex, option){
console.log(`select (${selectIndex}) | option (${optionIndex})`);
// your code here
});
})
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="myQuestion">
<select>
<option value="volvo">Volvo</option>
<option value="saab">Saab</option>
<option value="mercedes">Mercedes</option>
<option value="audi">Audi</option>
</select>
</div>
<div class="myQuestion">
<select>
<option value="volvo">Volvo</option>
<option value="saab">Saab</option>
<option value="mercedes">Mercedes</option>
<option value="audi">Audi</option>
</select>
</div>
So I am making two dropdowns. One is dependent on the other one, as in when you choose an option in the first dropdown, the values in the other should change. I am rendering my form with Symfony3.4, so I do not have much control over it. (I do not think I can add dynamic class names/value names to it). If it is relevant, I am using Bulma css framework.
Here is what my selectboxes look like:
states:
<select name="state" id="stateSelect">
<option value="1">Lagos</option>
<option value="2">Abuja</option>
<option value="3">Rivers</option>
<option value="4">Ogun</option>
<option value="5">Oyo</option>
<option value="6">Anambra</option>
<option value="7">Enugu</option>
<option value="8">Akwa Ibom</option>
<option value="9">Adamawa</option>
...
<option value="37">Zamfara</option>
</select>
LGA (local government areas):
<select id="lgaSelect" name="areas_registration[lga]">
<optgroup label="Lagos">
<option value="1">Abule Egba</option>
<option value="2">Agege</option>
<option value="3">Ajah</option>
<option value="4">Alimosho</option>
<option value="5">Amuwo Odofin</option>
...
</optgroup>
<optgroup label="Abuja">
<option value="38">Apo</option>
<option value="39">Asokoro</option>
<option value="40">Central Area</option>
<option value="41">Chika</option>
<option value="42">Dakibiyu</option>
...
</optgroup>
....35 more optgroups
</select>
My goal is when a user chooses an option from States dropdown, the LGA dropdown should only have options relevant to the selected state. I am using optgroup label for this. What I tried in my javascript is that when the page loads, I clone the LGA dropdown, hide it, call it lgaSelectSeed and use it for seeding the original LGA dropdown: (#hiddenLgas is just an empty div)
$(function () {
var stateSelect = $("#stateSelect") || null;
var lgaSelect = $("#lgaSelect") || null;
var hiddenLga = $("#hiddenLgas") || null;
$(hiddenLga).html(lgaSelect.clone().prop('id', 'lgaSelectSeed'));
stateSelect.change(function () {
var select_class = $(this).find('option:selected').text();
var options = $(lgaSelectSeed).find('optgroup[label="' + select_class + '"]');
$(lgaSelect).html(options.children());
}
This works but there is a bug in it. If you select random options in the state dropdown, and then go up and select Lagos or Abuja, the LGA dropdown becomes blank. I have been trying to figure out for a few days why this is happening, but still cant. Is there any jquery plugin to handle this instead?
DEMO: https://jsfiddle.net/gafyvbL9/
How to replicate the bug: In the states dropdown (left), choose Lagos. Then choose Anambra. Then choose Lagos again, then choose Anambra. You can see that the LGA dropdown (right) becomes empty. Why is this happening? Thanks in advance
Make a clone of the stored options so you don't remove the originals from $(hiddenLga)
Change:
$(lgaSelect).html(options.children());
To
$(lgaSelect).html(options.children().clone());
Playing with your fiddle, I think the issue is when you perform $(lgaSelect).html(), you're deleting all of the information stored there. Try storing that outside of your handler.
let $options = $('#lgaSelect').clone();
$("#stateSelect").on('change',function() {
let state = $(this).find('option:selected').text();
$("#lgaSelect").html($options.find(`optgroup[label="${state}"]`).html());
});
EDIT:
Notice the double quote in optgroup[label="${state}"]. This prevents issue with states that contain a space, like Akwa Ibom.
This is only for IE.
I have a function noted below it copies the content of the div when the div is clicked. It works fine. It used the getElementById.
I have 19 items I would like to use this for ... 'option1 - option19.
Instead of having to create 19 variables is there any other way of doing this...
I am totally a noob to this stuff....
function CopyToClip() {
var Cdiv = document.getElementById('option1');
Cdiv.contentEditable = 'true';
var controlRange;
if (document.body.createControlRange) {
controlRange = document.body.createControlRange();
controlRange.addElement(Cdiv);
controlRange.execCommand('Copy');
}
div.contentEditable = 'false';
}
I should mention that these id's are for Divs.
These divs are a show / hide based on a drop down selection.
The drop down has its on function to show the selected div.
The function is:
$(window).load(function () {
$(document).ready(function () {
$('.block').hide();
$('#option1').show();
$('#selectField').change(function () {
$('.block').hide();
$('#' + $(this).val()).fadeIn();
});
});
});
My HTML is:
<div class="col_1">
<h1>communication:</h1>
<div class="box">
<select id="selectField" style="padding-left: 20px;width:175px">
<option value="option1">Device Shipped to ASC</option>
<option value="option2">Device Received at ASC</option>
<option value="option3">ASC Shipped Device to Store</option>
<option value="option4">Device Pick-up Follow-up</option>
<option value="option5">Device Pick-up Final Reminder</option>
<option value="option6">Impress Phase Direct Feedback</option>
<option value="option7">Abandon Notice</option>
<option value="option8">Mailer Shipped to Client</option>
<option value="option9">Mailer Received by Client</option>
<option value="option10">Mailer Pick-up Notice</option>
<option value="option11">Mailer Final Pick-up Notice</option>
<option value="option12">Mailer Failed to Pick-up</option>
<option value="option13">Mailer Return Defective Device Notice</option>
<option value="option14">Mailer Final Return Defective Device Notice</option>
<option value="option15">Mailer Failed to Return Defective Device</option>
<option value="option16">Mailer Defective Device Received at ASC</option>
<option value="option17">Mailer Charges to Customer</option>
<option value="option18">Mailer Process Confirmation</option>
<option value="option19">Quote Un-replied</option>
</select>
<div id="option2" class="block" style="background-color:white" onClick="javascript:CopyToClip()"> blah </div>
Had I have 19 of this divs.
I don't know if this helps ... Sorry I am in way over my head on this one.
I had to hack things about a little, and your clipboard code will not work on all browsers:
JSFiddle: http://jsfiddle.net/THU5f/2/
function CopyToClip($div) {
var div = $div[0];
div.contentEditable = 'true';
var controlRange;
if (document.body.createControlRange) {
controlRange = document.body.createControlRange();
controlRange.addElement(div);
controlRange.execCommand('Copy');
alert("Copied: " + div.html());
}
div.contentEditable = 'false';
}
$(function () {
// Hide copy button
$('#copy').hide();
// Hide all content divs
$('.content').hide();
$('#selectField').change(function () {
// Show the copy button
$('#copy').show();
// Hide all content divs
$(".content").fadeOut();
// Show the select content div
$('#' + $(this).val()).fadeIn();
});
$('#copy').click(function(){
// Get the div the current selection points to
var $div = $('#' + $('#selectField').val());
// Copy the div to the clipboard
CopyToClip($div);
});
});
I added comments throughout. Hope this helps.
I've been working on similar thing lately. I was supposed to show/hide DIV depending on the selection. The HTML code is generated and there can be 1 to 8 selects generated, with each dependent div shown under the its select. I came up with this solution.
"Second half" of the code basically finds all select elements with given ID, loops trough them and depending on the selected value, shows or hides the div. I had to use this selectors: $('*[id*=delegate_form]') and $('*[id*=show_hidden_delegate'), because if I used $("#delegate_form") the code only affected the element with index 0. I have no idea why.
First half of the code handles the same situation on the read-only page.
I have two select boxes like so:
<select id="one">
<option value="default">Select File</option>
<option value="path/to/file1">File One</option>
<option value="path/to/file2">File Two</option>
<option value="path/to/file3">File Three</option>
</select>
<select id="two">
<option value="default">Select File</option>
<option value="path/to/file4">File Four</option>
<option value="path/to/file5">File Five</option>
<option value="path/to/file6">File Six</option>
</select>
<p class="button_image">
<a onclick="download(document.getElementById("one").value)"></a>
</p>
Here is my download function:
function download(file) {
if (file == 'default') return;
window.location = 'http://www.mysite.com/download/' + file;
}
This works fine for one select box, but I can't seem to figure out how to use the same button image. Oh yah, the p.class=button_image has background image that is a button with hover effects.
The reason I want these select boxes to be separate is because they each represent a group of files, eg, 32-bit versus 64-bit. So they cannot be combined, because it won't flow with the page design.
I've tried some if/else blocks in PHP using the getElementById but I'm getting stuck. This is what I tried and it seems to only partially work:
<?php
if ('document.getElementById(\"one\")' == 'one') {
echo "<a onclick='download(document.getElementById(\"one\").value)'></a>";
}
else if ('document.getElementById(\"two\")' == 'two') {
echo "<a onclick='download(document.getElementById(\"one\").value)'></a>";
}
?>
I should note that I don't necessarily need to use PHP in this case to solve this problem. It was just an option I tried because I'm using PHP for the server-side programming. I could be happy with any number of options, so long as they work.
Thanks.
** EDIT **
This design might be flawed. But the intention is that either a file from box one is downloaded OR a file from box two is downloaded. If one selection is made, then the other should be rest to default and vice versa. This is what I'm working on now.
** EDIT **
I ended up goign with Dawson Loudon's answer for one part and I created another function based on Barmar's comment that looks like this:
// resets other select box when selected
function reset_index(id) {
document.getElementById(id).selectedIndex = 'default';
}
An A element as a button doesn't seem appropriate, just use an img.
Anyhow, a function to use the first select with a selected option other than the first can be something like:
function getPath() {
var select;
var args = arguments;
for (var i=0, iLen=args.length; i<iLen; i++) {
select = document.getElementById(arg[i]);
if (select && select.selectedIndex > 0) {
window.location = 'http://www.mysite.com/download/' + select.value;
}
}
}
The above expects the first option to be the default selected, so if it's selected, or no option at all is selected, the select's selectedIndex will be 0 or -1 respsectively. I would ensure one option is selected by adding the selected attribute to the first one:
<option value="default" selected>Select File</option>
and the call is:
<img src="buttonImage.jpg" onclick="download('one', 'two');">
though you might want to add a class to the select elements and get them using getElementsByClassName or similar and loop over that collection, rather than hard code the ids.
Try replacing this:
<p class="button_image">
<a onclick="download(document.getElementById('one').value)"></a>
</p>
with:
<p class="button_image">
<a onclick="download(document.getElementById('one').value, document.getElementById('two').value)"></a>
</p>
and then replace your download function with this:
function download(file1,file2) {
if (file1 == 'default' && file2 == 'default'){
return;
}
else if(file1 != 'default'){
window.location = 'http://www.mysite.com/download/' + file1;
}
else{
window.location = 'http://www.mysite.com/download/' + file2;
}
}
Firstly, this is my first ever time using jQuery, so my code is not going to be the best. I'm adding a filter to my works website based off 3 drop boxes: fuel type, drive-type, and vehicle type. I want that when someone selects petrol it shows all the petrol cars, which I have managed to achieve, but now I'm a bit stuck. I now want it to show based on all 3 boxes, so if someone selects petrol, and then auto and then cars, it will show only petrol automatic cars. I can't seem to make the 3 boxes work together. so please help.
<script type="text/javascript" src="jquery.js"></script>
<script type="text/javascript">
$(document).ready(function() {
// fuels
$("#fuel").change(function() {
if ($("#fuel option[value='petrol']").attr('selected')) {
$('div[class*=petrol]').css('display','block');
}
if ($("#fuel option[value='diesel']").attr('selected')) {
$('div[class*=diesel]').css('display','block');
}
// end
//drivetype
});
$("#drive").change(function() {
if ($("#drive option[value='man']").attr('selected')) {
$('div[class*=manual]').css('display','block');
}
if ($("#drive option[value='auto']").attr('selected')) {
$('div[class*=auto]').css('display','block');
}
//end
});
// vech type
$("#type").change(function() {
if ($("#type option[value='car']").attr('selected')) {
$('div[class*=car]').css('display','block');
}
if ($("#type option[value='4']").attr('selected')) {
$('div[class*=4]').css('display','block');
}
if ($("#type option[value='7']").attr('selected')) {
$('div[class*=7]').css('display','block');
}
if ($("#type option[value='van']").attr('selected')) {
$('div[class*=van]').css('display','block');
}
// end
});
});
<select id="fuel">
<option value="none">fuel</option>
<option value="petrol">petrol</option>
<option value="diesel">diesel</option>
</select>
<select id="drive">
<option value="none">drive</option>
<option value="man">manual</option>
<option value="auto">auto</option>
</select>
<select id="type">
<option value="none">type</option>
<option value="car">car</option>
<option value="4">4x4</option>
<option value="7">people carrier</option>
<option value="van">van</option>
</select>
Basically at the time when you want to show the cars, you want to check all 3 select boxes for their values so you know which cars to show
In this case when showing cars for "auto" you need to check petrol as well as auto. when showing cars for "cars" you need to check all 3.
edit:
$("#type").change(function() {
// check previous select box value, check this box value
// output the correct cars
});
for the last one you simply check both of the previous boxes and this box and output the correct cars
Try to do something like:
$("#fuel").change(function() {
var value = $(this).val();
$(".elements_to_hide").hide(); //check if needed
$("." + value).show();
});
Please dont take it personally, but Ill give some suggestions about your code:
Try to avoid such complex constractions like: $('div[class*=diesel]').It will affect the performance.
JQuery contains build-in functions for show/hide DOM elements — .show(), .hide()
To get selected option of "select" use .val();
Hope answer will helpful for you. Best regards!