I have a sortable list of fixtures that is populated from an observableArray using the foreach binding. One of the parameters in each fixture in the array is position.
That position reflects the order that the fixtures are sorted in. By default when the fixtures are inserted using foreach, the position numbers are in the correct order, but when you sort the list by dragging the items, the position number is updated using jQuery:
$( "#picks" ).sortable({
revert: true,
placeholder: "placeholder",
containment: 'parent',
axis: "y",
handle: '.dragHandle',
update: function() {
for (var i = 1; i <= $('#picks li').length; i++) {
$('#picks li:nth-child('+i+')').find('span.num').text(i);
}
}
});
So, the position numbers do change, but since the numbers are updated without referencing the observable, the observable itself isn't updated. My question is, how can I update the observable using the update function tied to the jQuery sortable.
I do not want make the number an input, so using an input with a value binding was not an option!
Demo Fiddle
You need a binding handler for your sortable. If you mess with the DOM outside of a binding handler, you have problems like this. The author even provides links to some demo fiddles at the bottom of the github page.
Related
having many events to manage, I opted for a select to dissect the events and drop them in the calendar, I made this <https://jsfiddle.net/max1974/mr5yxe7o/4/>
but I am faced with 2 problems .....
1 ° Initially the objects in the select drop into the calendar, but then if you select other items from the select the drop stops working.
2 ° while I drop the object from the mouse disappears and reappears only when I release it.
Could you help me please.
Please see my complete working jsfiddle:
https://jsfiddle.net/gq8eofyL/
You have to use helper() function to clone the element object inside select2 and avoid relative position hiding the element outside the select2 main <span>.
Like in this example:
helper: function(){
return '<li class="select2-selection__choice ui-draggable ui-draggable-handle">'+$(this).attr('title')+'</li>';
}});
In addition, use Select2 events: https://select2.org/programmatic-control/events
in order to re-initialize draggables when Select2 recreates the elements, everytime you select/remove the elements (see my comment1 above):
function initSelectDraggable(){
$("ul.select2-selection__rendered li").each(function(){
$(this).data('event', {
title: $.trim($(this).text()),
stick: true
});
$(this).draggable({
revert: true,
revertDuration: 0,
helper: function()
{
return '<li class="select2-selection__choice ui-draggable ui-draggable-handle">'+$(this).attr('title')+'</li>';
}
});
});
}
Thanks it works great, now the problem remains that when I drop the event I lose data-id, data-num that I would need to save them in the DB and the event remains blue in the calendar instead of the chosen color.
Thanks again to everyone jsfiddle.net/max1974/bmqdax0f/57/
I'm using the Kendo for Angular grid in an Angular 4 application. I have selectable set to 'true', a column in my grid with the kendo-grid-checkbox-column, and selectionChange set to a function that takes the event parameter as an argument.
In my selectionChange handler, the selectedRows array on the event parameter only has one value in it, regardless of how many rows are selected.
Thanks,
James
My code:
onGridSelectionChange(event: SelectionEvent) {
debugger;
console.log(event.selectedRows.length); // this is always 1
};
<kendo-grid *ngIf='!isLoading' style="width:100%; height: inherit;" class="ag-fresh" [data]='gridView' [selectable]="true"
[pageSize]='pageSize' [skip]='skip' [pageable]='true' (pageChange)='onGridPageChange($event)'
(selectionChange)='onGridSelectionChange($event)'>
You are using the wrong event of the grid. You should use selectedKeysChange
<kendo-grid ...
[kendoGridSelectBy]="'id'"
(selectedKeysChange)="selectedKeysChange($event)">
...
</kendo-grid>
Also, you have to set the field used to select the row (kendoGridSelectBy). In this example it's the ID.
Get the selection:
selectedKeysChange(rows: number[]) {
console.log(rows);
}
Take a look at the following example:
EXAMPLE
All selected keys are kept in a collection (mySelection) that we can also manipulate to select/deselect rows programmatically. Instead of keeping the keys, you can keep the whole objects, representing the selected data items instead (bind kendoGridSelectBy to a function that will return eventArgs.dataItem).
change [selectable]="true" to:
[selectable]="{enabled: true, mode: 'multiple'}"
when I added the mode: 'multiple' I was able to get the list..
I have an interactive basket whereby the user can drag and drop an item into the basket. However, the same item cannot be placed in the basket twice (but it remains visible, albeit faded), so once it is in the basket, the draggable property must be disabled.
I tried doing this:
$("#product_badges li:not(.on)").draggable({
// Options here
});
However, as this just initiates the draggable() property, the element is still draggable even if I do add the on class to it when it has been dropped.
I therefore cannot see a way of achieving this without having several instances for the draggable property like so:
$("#product_badges li:not(.on)").each(function(){
$(this).draggable({
// Options here
}
});
With the above method I can then call the individual product_badge and disable dragging like so:
This only gets called once the item has been placed into the basket (dropped)
$('.item',$('#product_badges')).draggable('disable');
Is there a better way of achieving this? Can you set an HTML element to only be draggable if it does not have a particular class?
Update
See example here: http://jsfiddle.net/mB6GK/2/
use the cancel property.
$("#product_badges li").draggable({ cancel: ".no" })
fiddle:
http://jsfiddle.net/sGguz/
You could use the start event,
$("#container").draggable({
start: function( event, ui )
{ return !$(ui.helper).hasClass('nodrop'); }});
http://jsfiddle.net/mB6GK/4/
I have a jquery range slider that I am using to select a percentage of color for an overall image and it can have a dynamic number of handles based on how many elements the user decides to use. I am trying to display the percentage for each of the individual handles of the slider in the handles themselves. I have not had luck in figuring this one out and I'm hoping to get some help/direction.
I have found a number of examples on the net that have selected the ".ui-slider-handle" and then modified the text but I can only seem to get this to change one or all of them to the same text. I also got the slider object and then got its children, then iterated through the children and tried changing the text val for each but it never changes it. Any ideas?
This doesn't work:
myslider.slider({
min: 0,
max: 100,
orientation: 'vertical',
values: handles,
slide: function( event, ui ) {
var handleText = $(this)[0].children[0].text;
handleText = "Test";
console.log("val should be changed: ",handleText);
//The below line works, however it changes them all to the same value
//myslider.find("a.ui-slider-handle").text(ui.values);
}
});
Edited answer: You can use each() to do what you want (and here's a working jsFiddle):
myslider.find("a.ui-slider-handle").each(function( index ) {
$(this).text(ui.values[index]);
});
Let's break it down:
myslider.find("a.ui-slider-handle") - get all the handle objects, just like you're doing right now.
.each(function( index ) { - apply a function to each element that we just found, using its index in the jQuery object as an argument. each() is what's doing the heavy lifting; more on it here.
$(this).text(ui.values[index]); - make this handle's text the value from our values object that corresponds to this handle's index.
}); - close up the shop.
That should do the trick!
Note: myslider.find("a.ui-slider-handle").text(ui.values); didn't work because, while it selected all the correct handles, it just assigned them one value - your values sequence. You need to use the above method to break up the contents of values and apply them to the handles separately.
As the question states, I'm trying to combine jQuery UI's Selectable and Draggable functions into a working drag-n-drop interface with the user being able to select multiple divs and move those divs into jQuery Droppables.
Here is the code I have to allow the user to select divs across a row in a table:
$('tr').selectable({
filter: 'div',
selected: function(event, ui) {
$(ui.selected).draggable({
containment: 'document',
axis: 'y',
snap: true,
snapMode: 'inner',
revert: 'invalid',
opacity: 0.8,
drag: function(e, ui) {
$('.ui-selected').css({
top : ui.position.top //Y-Axis Only
});
$('.ui-selected').addClass('ui-draggable-dragging');
},
stop: function() {
$('.ui-selected').removeClass('ui-selected ui-draggable');
}
});
}
});
As you can see, I've tried adding the known classes that jQuery UI adds to elements being dragged/selected/etc, but the only element that seems to act as an actual draggable is the one that the user has clicked on (is actually dragging).
My desire is to have the user drag the entire selected group, and have them all act as draggables (ie: revert on invalid, snap to droppable, etc)
Does anyone have any idea how to do this or where to go from here?
Also, here is a jsfiddle to demonstrate exactly what I mean (and where I'm currently at on this). You might have to resize the results view so the table cells are all the same width.
Simulate the behavior.
when selecting multiple item just mark them as selected manually (e.g. checkbox, add custom style, etc)
when dragging use draggable option helper to define custom clone helper : function(){
return "<p>custom item</p>"
},
this will hide individual items. And you can customize as you want.
Custom drop implementation which using those selected items to append into the proper place.