Commit ac851543 authored by davidstutz's avatar davidstutz

Changed checkboxName option to allow #581 + documentation + tests.

parent c5506f95
...@@ -293,6 +293,9 @@ ...@@ -293,6 +293,9 @@
return selected.substr(0, selected.length - this.delimiterText.length); return selected.substr(0, selected.length - this.delimiterText.length);
} }
}, },
checkboxName: function(option) {
return false; // no checkbox name
},
/** /**
* Create a label. * Create a label.
* *
...@@ -386,7 +389,6 @@ ...@@ -386,7 +389,6 @@
// Maximum height of the dropdown menu. // Maximum height of the dropdown menu.
// If maximum height is exceeded a scrollbar will be displayed. // If maximum height is exceeded a scrollbar will be displayed.
maxHeight: false, maxHeight: false,
checkboxName: false,
includeSelectAllOption: false, includeSelectAllOption: false,
includeSelectAllIfMoreThan: 0, includeSelectAllIfMoreThan: 0,
selectAllText: ' Select all', selectAllText: ' Select all',
...@@ -844,9 +846,11 @@ ...@@ -844,9 +846,11 @@
var $checkbox = $('<input/>').attr('type', inputType); var $checkbox = $('<input/>').attr('type', inputType);
if (this.options.checkboxName) { var name = this.options.checkboxName($element);
$checkbox.attr('name', this.options.checkboxName); if (name) {
$checkbox.attr('name', name);
} }
$label.prepend($checkbox); $label.prepend($checkbox);
var selected = $element.prop('selected') || false; var selected = $element.prop('selected') || false;
...@@ -1367,8 +1371,9 @@ ...@@ -1367,8 +1371,9 @@
if (this.options.enableClickableOptGroups && this.options.multiple) { if (this.options.enableClickableOptGroups && this.options.multiple) {
this.updateOptGroups(); this.updateOptGroups();
} }
console.log('test')
if (triggerOnDeselectAll) { if (triggerOnDeselectAll) {
console.log('test2')
this.options.onDeselectAll(); this.options.onDeselectAll();
} }
}, },
...@@ -1553,14 +1558,14 @@ ...@@ -1553,14 +1558,14 @@
if (checkedBoxesLength > 0 && checkedBoxesLength === allBoxesLength) { if (checkedBoxesLength > 0 && checkedBoxesLength === allBoxesLength) {
selectAllInput.prop("checked", true); selectAllInput.prop("checked", true);
selectAllLi.addClass(this.options.selectedClass); selectAllLi.addClass(this.options.selectedClass);
this.options.onSelectAll(true); this.options.onSelectAll();
} }
else { else {
selectAllInput.prop("checked", false); selectAllInput.prop("checked", false);
selectAllLi.removeClass(this.options.selectedClass); selectAllLi.removeClass(this.options.selectedClass);
if (checkedBoxesLength === 0) { if (checkedBoxesLength === 0) {
if (!notTriggerOnSelectAll) { if (!notTriggerOnSelectAll) {
this.options.onSelectAll(false); this.options.onDeselectAll();
} }
} }
} }
......
...@@ -1120,7 +1120,9 @@ ...@@ -1120,7 +1120,9 @@
<script type="text/javascript"> <script type="text/javascript">
$(document).ready(function() { $(document).ready(function() {
$('#example-checkboxName').multiselect({ $('#example-checkboxName').multiselect({
checkboxName: 'multiselect[]' checkboxName: function(option) {
return 'multiselect[]';
}
}); });
}); });
</script> </script>
...@@ -1138,7 +1140,9 @@ ...@@ -1138,7 +1140,9 @@
&lt;script type=&quot;text/javascript&quot;&gt; &lt;script type=&quot;text/javascript&quot;&gt;
$(document).ready(function() { $(document).ready(function() {
$('#example-checkboxName').multiselect({ $('#example-checkboxName').multiselect({
checkboxName: 'multiselect[]' checkboxName: function(option) {
return 'multiselect[]';
}
}); });
}); });
&lt;/script&gt; &lt;/script&gt;
...@@ -5720,6 +5724,99 @@ $(document).ready(function() { ...@@ -5720,6 +5724,99 @@ $(document).ready(function() {
</pre> </pre>
</div> </div>
<p>
The <code>checkboxName</code> option can also be used to assign different names to the <code>option's</code>, for example for different <code>optgroup</code>s.
</p>
<p class="alert alert-warning">
Note that in the below example, <code>$_POST</code> will contain both the <code>multiselect</code> and the <code>group1</code> as well as <code>group2</code> keys.
</p>
<div class="example">
<script type="text/javascript">
$(document).ready(function() {
$('#example-post-checkboxName').multiselect({
checkboxName: function(option) {
var $optgroup = $(option).closest('optgroup');
if ($optgroup.id == 'example-post-checkboxName-1') {
return 'group1[]';
}
else {
return 'group2[]';
}
}
});
});
</script>
<form class="form-horizontal" method="POST" action="post.php">
<div class="form-group">
<label class="col-sm-2 control-label">Multiselect</label>
<div class="col-sm-10">
<select id="example-post-checkboxName" name="multiselect[]" multiple="multiple" required>
<optgroup label="Group 1" id="example-post-checkboxName-1">
<option value="1-1">Option 1.1</option>
<option value="1-2">Option 1.2</option>
<option value="1-3">Option 1.3</option>
</optgroup>
<optgroup label="Group 1" id="example-post-checkboxName-2">
<option value="2-1">Option 2.1</option>
<option value="2-2">Option 2.2</option>
<option value="2-3">Option 2.3</option>
</optgroup>
</select>
</div>
</div>
<div class="form-group">
<div class="col-sm-offset-2 col-sm-10">
<button type="submit" class="btn btn-default">Submit</button>
</div>
</div>
</form>
</div>
<div class="highlight">
<pre class="prettyprint linenums">
&lt;script type=&quot;text/javascript&quot;&gt;
$(document).ready(function() {
$('#example-post-checkboxName').multiselect({
checkboxName: function(option) {
var $optgroup = $(option).closest('optgroup');
if ($optgroup.id == 'example-post-checkboxName-1') {
return 'group1[]';
}
else {
return 'group2[]';
}
}
});
});
&lt;/script&gt;
&lt;form class=&quot;form-horizontal&quot; method=&quot;POST&quot; action=&quot;post.php&quot;&gt;
&lt;div class=&quot;form-group&quot;&gt;
&lt;label class=&quot;col-sm-2 control-label&quot;&gt;Multiselect&lt;/label&gt;
&lt;div class=&quot;col-sm-10&quot;&gt;
&lt;select id=&quot;example-post-checkboxName&quot; name=&quot;multiselect[]&quot; multiple=&quot;multiple&quot; required&gt;
&lt;optgroup label=&quot;Group 1&quot; id=&quot;example-post-checkboxName-1&quot;&gt;
&lt;option value=&quot;1-1&quot;&gt;Option 1.1&lt;/option&gt;
&lt;option value=&quot;1-2&quot;&gt;Option 1.2&lt;/option&gt;
&lt;option value=&quot;1-3&quot;&gt;Option 1.3&lt;/option&gt;
&lt;/optgroup&gt;
&lt;optgroup label=&quot;Group 1&quot; id=&quot;example-post-checkboxName-2&quot;&gt;
&lt;option value=&quot;2-1&quot;&gt;Option 2.1&lt;/option&gt;
&lt;option value=&quot;2-2&quot;&gt;Option 2.2&lt;/option&gt;
&lt;option value=&quot;2-3&quot;&gt;Option 2.3&lt;/option&gt;
&lt;/optgroup&gt;
&lt;/select&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;div class=&quot;form-group&quot;&gt;
&lt;div class=&quot;col-sm-offset-2 col-sm-10&quot;&gt;
&lt;button type=&quot;submit&quot; class=&quot;btn btn-default&quot;&gt;Submit&lt;/button&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;/form&gt;
</pre>
</div>
<div class="page-header"> <div class="page-header">
<h2 id="keyboard-support">Keyboard Support</h2> <h2 id="keyboard-support">Keyboard Support</h2>
</div> </div>
...@@ -5821,7 +5918,9 @@ $('#example option:selected').map(function(a, item){return item.value;}); ...@@ -5821,7 +5918,9 @@ $('#example option:selected').map(function(a, item){return item.value;});
<p>Or add an appropriate name to the checkboxes:</p> <p>Or add an appropriate name to the checkboxes:</p>
<pre class="linenums prettyprint"> <pre class="linenums prettyprint">
$('#example2').multiselect({ $('#example2').multiselect({
checkboxName: 'multiselect[]' checkboxName: function(option) {
return 'multiselect[]';
}
}); });
</pre> </pre>
</dd> </dd>
...@@ -5881,7 +5980,9 @@ validator.settings.ignore = ':hidden:not(".multiselect")'; ...@@ -5881,7 +5980,9 @@ validator.settings.ignore = ':hidden:not(".multiselect")';
This issue is discussed in detail here: <a href="https://github.com/davidstutz/bootstrap-multiselect/issues/362">#362</a>. A simple solution is to use different option values for the option <code>checkboxName</code>: This issue is discussed in detail here: <a href="https://github.com/davidstutz/bootstrap-multiselect/issues/362">#362</a>. A simple solution is to use different option values for the option <code>checkboxName</code>:
<pre class="prettyprint linenums"> <pre class="prettyprint linenums">
$('.multiselect').multiselect({ $('.multiselect').multiselect({
checkboxName: _.uniqueId('multiselect_') checkboxName: function(option) {
return _.uniqueId('multiselect_');
}
}); });
</pre> </pre>
where <code>_.uniqueId('multiselect_')</code> should be replaced with a random generator. Alternatively, a unique value for <code>checkboxName</code> can be used for each multiselect. where <code>_.uniqueId('multiselect_')</code> should be replaced with a random generator. Alternatively, a unique value for <code>checkboxName</code> can be used for each multiselect.
......
...@@ -20,6 +20,9 @@ describe('Bootstrap Multiselect "Core".', function() { ...@@ -20,6 +20,9 @@ describe('Bootstrap Multiselect "Core".', function() {
buttonContainer: '<div id="multiselect-container"></div>', buttonContainer: '<div id="multiselect-container"></div>',
onInitialized: function($select) { onInitialized: function($select) {
onInitialized = true; onInitialized = true;
},
checkboxName: function($option) {
return 'value-' + $($option).attr('value');
} }
}); });
}); });
...@@ -207,6 +210,12 @@ describe('Bootstrap Multiselect "Core".', function() { ...@@ -207,6 +210,12 @@ describe('Bootstrap Multiselect "Core".', function() {
expect(onInitialized).toBe(true); expect(onInitialized).toBe(true);
}); });
it('Should correctly apply checkboxName.', function() {
$('#multiselect-container input').each(function() {
expect($(this).attr('name')).toBe('value-' + $(this).attr('value'));
});
});
afterEach(function() { afterEach(function() {
$('#multiselect').multiselect('destroy'); $('#multiselect').multiselect('destroy');
$('#multiselect').remove(); $('#multiselect').remove();
...@@ -955,24 +964,32 @@ describe('Bootstrap Multiselect "Select All".', function() { ...@@ -955,24 +964,32 @@ describe('Bootstrap Multiselect "Select All".', function() {
expect($('#multiselect-container input[value="multiselect-all"]').prop('checked')).toBe(false); expect($('#multiselect-container input[value="multiselect-all"]').prop('checked')).toBe(false);
}); });
it('Should trigger onSelectAll based on the change event.', function() { it('Should trigger onSelectAll/onDeselectAll based on the change event.', function() {
expect($('#multiselect option:selected').length).toBe(0); expect($('#multiselect option:selected').length).toBe(0);
expect($('#multiselect-container input[value="multiselect-all"]').prop('checked')).toBe(false); expect($('#multiselect-container input[value="multiselect-all"]').prop('checked')).toBe(false);
// Change all checkboxes except the select all one.
$('#multiselect-container input[value!="multiselect-all"]').prop('checked', true); $('#multiselect-container input[value!="multiselect-all"]').prop('checked', true);
$('#multiselect-container input[value!="multiselect-all"]').trigger('change'); $('#multiselect-container input[value!="multiselect-all"]').trigger('change');
expect($('#multiselect option:selected[value!="multiselect-all"]').length).toBe(99); expect($('#multiselect option:selected[value!="multiselect-all"]').length).toBe(99);
// 100 options seleted including the select all.
expect($('#multiselect option:selected').length).toBe(99); expect($('#multiselect option:selected').length).toBe(99);
expect($('#multiselect-container input[value="multiselect-all"]').prop('checked')).toBe(true); expect($('#multiselect-container input[value="multiselect-all"]').prop('checked')).toBe(true);
expect(onSelectAllTriggered).toBe(true); expect(onSelectAllTriggered).toBe(true);
console.log('t')
$('#multiselect-container input[value!="multiselect-all"]').prop('checked', false);
$('#multiselect-container input[value!="multiselect-all"]').trigger('change');
expect($('#multiselect option:selected[value!="multiselect-all"]').length).toBe(0);
expect($('#multiselect option:selected').length).toBe(0);
expect($('#multiselect-container input[value="multiselect-all"]').prop('checked')).toBe(false);
console.log('tt')
expect(onDeselectAllTriggered).toBe(true);
}); });
it('Should trigger onSelectAll based on the click event.', function() { it('Should trigger onSelectAll/onDeselectAll based on the click event.', function() {
expect($('#multiselect option:selected').length).toBe(0); expect($('#multiselect option:selected').length).toBe(0);
expect($('#multiselect-container input[value="multiselect-all"]').prop('checked')).toBe(false); expect($('#multiselect-container input[value="multiselect-all"]').prop('checked')).toBe(false);
...@@ -982,18 +999,21 @@ describe('Bootstrap Multiselect "Select All".', function() { ...@@ -982,18 +999,21 @@ describe('Bootstrap Multiselect "Select All".', function() {
expect($('#multiselect-container input[value="multiselect-all"]').prop('checked')).toBe(true); expect($('#multiselect-container input[value="multiselect-all"]').prop('checked')).toBe(true);
expect(onSelectAllTriggered).toBe(true); expect(onSelectAllTriggered).toBe(true);
$('#multiselect-container input[value!="multiselect-all"]').click();
expect($('#multiselect option:selected').length).toBe(0);
expect($('#multiselect-container input[value="multiselect-all"]').prop('checked')).toBe(false);
expect(onDeselectAllTriggered).toBe(true);
}); });
it('Should trigger onSelectAll on function call.', function() { it('Should trigger onSelectAll/onDeselectAll on function call.', function() {
$('#multiselect').multiselect('selectAll', true, true); $('#multiselect').multiselect('selectAll', true, true);
expect(onSelectAllTriggered).toBe(true); expect(onSelectAllTriggered).toBe(true);
});
it('Should not trigger onChange for select all option.', function() { $('#multiselect').multiselect('deselectAll', true, true);
fired = 0; expect(onDeselectAllTriggered).toBe(true);
expect(fired).toBe(0);
$('#multiselect-container input[value="multiselect-all"]').click();
expect(fired).toBe(0);
}); });
afterEach(function() { afterEach(function() {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment