Rectangle 27 5

places.sort(function(x, y) {
   return x.time_going_hour - y.time_going_hour || 
          x.time_going_minutes - y.time_going_minutes
})

Array.sort accepts a comparison function. The comparison function takes two arguments (here, x and y) and returns a result that is either:

x > y
x < y
x == y

This compare function first tries to return the difference of x's hour and y's hour (so that if the hour of x is greater than the hour of y, the difference is positive, and otherwise it's negative). If the hour values are equal, then the hour difference is 0, and the right-hand part of the "or" (||) is evaluated (since 0 evaluated in a boolean context is false). This right-hand expression performs the same comparison as before, but with minutes instead of hours.

In short, the comparison function sorts values by hour, and if the hours are the same for any given elements, it sub-sorts them by minutes.

@JasonBiondo If you look up sorting algorithms, some of them use a comparison operation to shift items backwards or forwards in the array/object. In this case, the subtraction of the hours from each other will yield either a negative or positive number which is then used to push that value forwards or backwards in your array/object. The minutes are then compared for secondary sorting based on that value.

@JasonBiondo I went ahead and edited in an explanation of thg435's code.

jquery - How Can I Sort a Dynamically Created JavaScript Object by Val...

javascript jquery sorting
Rectangle 27 43

JavaScript objects have no order. Even though most browsers do iterate in the same order the properties were created, there's no guarantee, so sorting is not supported on objects.

You might also be interested in what John Resig has got to say on the matter.

If you need a sort-able list, you'll have to store it as an array of objects:

var masterList = [
    { key: 1, val: "google" },
    { key: 2, val: "yahoo" },
    { key: 3, val: "msn" },
    { key: 4, val: "stackoverflow" },
    { key: 5, val: "github" },
    { key: 6, val: "jsfiddle" },
    { key: 7, val: "amazon" },
    { key: 8, val: "ebay" }
];

Then, to sort them, just use the regular array's sort method:

masterList = masterList.sort(function (a, b) {
    return a.val.localeCompare( b.val );
});

Maybe I just don't understand sort(), but this doesn't work for numerical values. Trying to sort by 'key' returns undefined function.

@dval - It's the localeCompare that's throwing you off. If you're sorting by key, then just return a - b.

list = list.sort(function(a, b){ return a.val - b.val; });

jquery - Javascript Sort key value pair object based on value - Stack ...

javascript jquery
Rectangle 27 1

you can use javascript sort method to sort the array after ever addition/push.

sort(function(a,b){
return (a["time_going_hour"]*60+a["time_going_mnutes"]) - (b["time_going_hour"]*60+b["time_going_mnutes"])
})
places

jquery - How Can I Sort a Dynamically Created JavaScript Object by Val...

javascript jquery sorting
Rectangle 27 108

You would iterate inside the object with a for loop:

for(var i in foo){
  alert(i); // alerts key
  alert(foo[i]); //alerts key's value
}
Object.keys(foo)
  .forEach(function eachKey(key) { 
    alert(key); // alerts key 
    alert(foo[key]); // alerts value
  });
"_proto_"
foo[i]
some string

@user2284570: i can be a string - no problem.

don't you mean for(var i in Object.keys(foo)) {

jquery - best way to get the key of a key/value javascript object - St...

javascript jquery
Rectangle 27 93

I can grep the array for the id, but how can I delete the entire object where id == 88

Simply filter by the opposite predicate:

var data = $.grep(data, function(e){ 
     return e.id != id; 
});

In you case where you want to delete all items with id=something is fine ... but be careful when using $.grep as it searches the full array and for long arrays it is not efficient. Sometimes you just need to check if the element exists inside the array by a given ID, then is better to use another iteration method ;)

@ArunSivan Yes, it overwrites the data variable with a new list, which is usually a much better idea.

@ArunSivan slice doesn't remove anything either. Not sure what you're getting at. If you have a specific problem yourself, you might want to ask a new question.

jquery - javascript find and remove object in array based on key value...

javascript jquery arrays object
Rectangle 27 380

The following code is now deprecated.

The following code can take work with all sorts of input names; and handle them just as you'd expect.

<!-- all of these will work! -->
<input name="honey[badger]" value="a">
<input name="wombat[]" value="b">
<input name="hello[panda][]" value="c">
<input name="animals[0][name]" value="d">
<input name="animals[0][breed]" value="e">
<input name="crazy[1][][wonky]" value="f">
<input name="dream[as][vividly][as][you][can]" value="g">
// output
{
  "honey":{
    "badger":"a"
  },
  "wombat":["b"],
  "hello":{
    "panda":["c"]
  },
  "animals":[
    {
      "name":"d",
      "breed":"e"
    }
  ],
  "crazy":[
    null,
    [
      {"wonky":"f"}
    ]
  ],
  "dream":{
    "as":{
      "vividly":{
        "as":{
          "you":{
            "can":"g"
          }
        }
      }
    }
  }
}
$('#my-form').serializeObject();
(function($){
    $.fn.serializeObject = function(){

        var self = this,
            json = {},
            push_counters = {},
            patterns = {
                "validate": /^[a-zA-Z][a-zA-Z0-9_]*(?:\[(?:\d*|[a-zA-Z0-9_]+)\])*$/,
                "key":      /[a-zA-Z0-9_]+|(?=\[\])/g,
                "push":     /^$/,
                "fixed":    /^\d+$/,
                "named":    /^[a-zA-Z0-9_]+$/
            };


        this.build = function(base, key, value){
            base[key] = value;
            return base;
        };

        this.push_counter = function(key){
            if(push_counters[key] === undefined){
                push_counters[key] = 0;
            }
            return push_counters[key]++;
        };

        $.each($(this).serializeArray(), function(){

            // skip invalid keys
            if(!patterns.validate.test(this.name)){
                return;
            }

            var k,
                keys = this.name.match(patterns.key),
                merge = this.value,
                reverse_key = this.name;

            while((k = keys.pop()) !== undefined){

                // adjust reverse_key
                reverse_key = reverse_key.replace(new RegExp("\\[" + k + "\\]$"), '');

                // push
                if(k.match(patterns.push)){
                    merge = self.build([], self.push_counter(reverse_key), merge);
                }

                // fixed
                else if(k.match(patterns.fixed)){
                    merge = self.build([], k, merge);
                }

                // named
                else if(k.match(patterns.named)){
                    merge = self.build({}, k, merge);
                }
            }

            json = $.extend(true, json, merge);
        });

        return json;
    };
})(jQuery);

So, that works pretty well. But it's misnamed: it doesn't return JSON, as the name implies. Instead, it returns an object literal. Also, it's important to check for hasOwnProperty, otherwise your arrays have anything that's attached to their prototype, like: {numbers: ["1", "3", indexOf: function(){...}]}

@frontendbeauty actually, toJSON is exactly what the spec says it should be called: developer.mozilla.org/en/JSON#toJSON()_method an unfortunate misnomer.

@Marek, I did a test for here on jsfiddle. The trick is to name your select properly. <select name="foo" multiple="multiple"> will not work in any scenario. However, if you use [], as in <select name="bar[]" multiple="multiple">, it will work just fine :)

This solution should be on top as it deals with the problem of nested keys as form element names.

json - Convert form data to JavaScript object with jQuery - Stack Over...

jquery json serialization
Rectangle 27 380

The following code is now deprecated.

The following code can take work with all sorts of input names; and handle them just as you'd expect.

<!-- all of these will work! -->
<input name="honey[badger]" value="a">
<input name="wombat[]" value="b">
<input name="hello[panda][]" value="c">
<input name="animals[0][name]" value="d">
<input name="animals[0][breed]" value="e">
<input name="crazy[1][][wonky]" value="f">
<input name="dream[as][vividly][as][you][can]" value="g">
// output
{
  "honey":{
    "badger":"a"
  },
  "wombat":["b"],
  "hello":{
    "panda":["c"]
  },
  "animals":[
    {
      "name":"d",
      "breed":"e"
    }
  ],
  "crazy":[
    null,
    [
      {"wonky":"f"}
    ]
  ],
  "dream":{
    "as":{
      "vividly":{
        "as":{
          "you":{
            "can":"g"
          }
        }
      }
    }
  }
}
$('#my-form').serializeObject();
(function($){
    $.fn.serializeObject = function(){

        var self = this,
            json = {},
            push_counters = {},
            patterns = {
                "validate": /^[a-zA-Z][a-zA-Z0-9_]*(?:\[(?:\d*|[a-zA-Z0-9_]+)\])*$/,
                "key":      /[a-zA-Z0-9_]+|(?=\[\])/g,
                "push":     /^$/,
                "fixed":    /^\d+$/,
                "named":    /^[a-zA-Z0-9_]+$/
            };


        this.build = function(base, key, value){
            base[key] = value;
            return base;
        };

        this.push_counter = function(key){
            if(push_counters[key] === undefined){
                push_counters[key] = 0;
            }
            return push_counters[key]++;
        };

        $.each($(this).serializeArray(), function(){

            // skip invalid keys
            if(!patterns.validate.test(this.name)){
                return;
            }

            var k,
                keys = this.name.match(patterns.key),
                merge = this.value,
                reverse_key = this.name;

            while((k = keys.pop()) !== undefined){

                // adjust reverse_key
                reverse_key = reverse_key.replace(new RegExp("\\[" + k + "\\]$"), '');

                // push
                if(k.match(patterns.push)){
                    merge = self.build([], self.push_counter(reverse_key), merge);
                }

                // fixed
                else if(k.match(patterns.fixed)){
                    merge = self.build([], k, merge);
                }

                // named
                else if(k.match(patterns.named)){
                    merge = self.build({}, k, merge);
                }
            }

            json = $.extend(true, json, merge);
        });

        return json;
    };
})(jQuery);

So, that works pretty well. But it's misnamed: it doesn't return JSON, as the name implies. Instead, it returns an object literal. Also, it's important to check for hasOwnProperty, otherwise your arrays have anything that's attached to their prototype, like: {numbers: ["1", "3", indexOf: function(){...}]}

@frontendbeauty actually, toJSON is exactly what the spec says it should be called: developer.mozilla.org/en/JSON#toJSON()_method an unfortunate misnomer.

@Marek, I did a test for here on jsfiddle. The trick is to name your select properly. <select name="foo" multiple="multiple"> will not work in any scenario. However, if you use [], as in <select name="bar[]" multiple="multiple">, it will work just fine :)

This solution should be on top as it deals with the problem of nested keys as form element names.

json - Convert form data to JavaScript object with jQuery - Stack Over...

jquery json serialization
Rectangle 27 380

The following code is now deprecated.

The following code can take work with all sorts of input names; and handle them just as you'd expect.

<!-- all of these will work! -->
<input name="honey[badger]" value="a">
<input name="wombat[]" value="b">
<input name="hello[panda][]" value="c">
<input name="animals[0][name]" value="d">
<input name="animals[0][breed]" value="e">
<input name="crazy[1][][wonky]" value="f">
<input name="dream[as][vividly][as][you][can]" value="g">
// output
{
  "honey":{
    "badger":"a"
  },
  "wombat":["b"],
  "hello":{
    "panda":["c"]
  },
  "animals":[
    {
      "name":"d",
      "breed":"e"
    }
  ],
  "crazy":[
    null,
    [
      {"wonky":"f"}
    ]
  ],
  "dream":{
    "as":{
      "vividly":{
        "as":{
          "you":{
            "can":"g"
          }
        }
      }
    }
  }
}
$('#my-form').serializeObject();
(function($){
    $.fn.serializeObject = function(){

        var self = this,
            json = {},
            push_counters = {},
            patterns = {
                "validate": /^[a-zA-Z][a-zA-Z0-9_]*(?:\[(?:\d*|[a-zA-Z0-9_]+)\])*$/,
                "key":      /[a-zA-Z0-9_]+|(?=\[\])/g,
                "push":     /^$/,
                "fixed":    /^\d+$/,
                "named":    /^[a-zA-Z0-9_]+$/
            };


        this.build = function(base, key, value){
            base[key] = value;
            return base;
        };

        this.push_counter = function(key){
            if(push_counters[key] === undefined){
                push_counters[key] = 0;
            }
            return push_counters[key]++;
        };

        $.each($(this).serializeArray(), function(){

            // skip invalid keys
            if(!patterns.validate.test(this.name)){
                return;
            }

            var k,
                keys = this.name.match(patterns.key),
                merge = this.value,
                reverse_key = this.name;

            while((k = keys.pop()) !== undefined){

                // adjust reverse_key
                reverse_key = reverse_key.replace(new RegExp("\\[" + k + "\\]$"), '');

                // push
                if(k.match(patterns.push)){
                    merge = self.build([], self.push_counter(reverse_key), merge);
                }

                // fixed
                else if(k.match(patterns.fixed)){
                    merge = self.build([], k, merge);
                }

                // named
                else if(k.match(patterns.named)){
                    merge = self.build({}, k, merge);
                }
            }

            json = $.extend(true, json, merge);
        });

        return json;
    };
})(jQuery);

So, that works pretty well. But it's misnamed: it doesn't return JSON, as the name implies. Instead, it returns an object literal. Also, it's important to check for hasOwnProperty, otherwise your arrays have anything that's attached to their prototype, like: {numbers: ["1", "3", indexOf: function(){...}]}

@frontendbeauty actually, toJSON is exactly what the spec says it should be called: developer.mozilla.org/en/JSON#toJSON()_method an unfortunate misnomer.

@Marek, I did a test for here on jsfiddle. The trick is to name your select properly. <select name="foo" multiple="multiple"> will not work in any scenario. However, if you use [], as in <select name="bar[]" multiple="multiple">, it will work just fine :)

This solution should be on top as it deals with the problem of nested keys as form element names.

json - Convert form data to JavaScript object with jQuery - Stack Over...

jquery json serialization
Rectangle 27 55

You can simplify this, and there's really no need for using jquery here.

var id = 88;

for(var i = 0; i < data.length; i++) {
    if(data[i].id == id) {
        data.splice(i, 1);
        break;
    }
}

Just iterate through the list, find the matching id, splice, and then break to exit your loop

+1, but you should mention that this does delete only the first item which matches.

... And if you need to delete each matched items, loop on reverse order with i=data.length; i > 0; i-- and don't use break.

i = data.length
data[i]
i=data.length -1 ; i > -1; i--

jquery - javascript find and remove object in array based on key value...

javascript jquery arrays object
Rectangle 27 31

Is this better than doing findIndex() and then splice(index, 1) on parent array?

splice mutates the originating array. With filter you have the choice.

jquery - javascript find and remove object in array based on key value...

javascript jquery arrays object
Rectangle 27 5

var obj = {
    "1": "google",
    "2": "yahoo",
    "3": "msn",
    "4": "stackoverflow",
    "5": "github",
    "6": "jsfiddle",
    "7": "amazon",
    "8": "ebay"
};

var arr = [];

for (var key in obj) {
    if (obj.hasOwnProperty(key)) {
        arr.push(obj[key]);
    }
}

alert(arr.sort());

This will sort your values in ascending order. let me give sometime will revert you with how to convert that to an object.

The only problem with this solution is that you miss the key values in the resultant array

jquery - Javascript Sort key value pair object based on value - Stack ...

javascript jquery
Rectangle 27 6

Assuming that ids are unique and you'll only have to remove the one element splice should do the trick:

var data = [
{"id":"88","name":"Lets go testing"},
{"id":"99","name":"Have fun boys and girls"},
{"id":"108","name":"You are awesome!"}
],
id = 88;

console.table(data);

$.each(data, function(i, el){
    if (this.id == id){
        data.splice(i, 1);
    }
});

console.table(data);

You have the elements in your callback function backwards. It should be each(data,function(idx,ele). I'll bill you later for the 30 min I wasted figuring that out :)

Oops. The least I can do in that case is update my answer. I feel really bad about your wasted 30 minutes of life.

jquery - javascript find and remove object in array based on key value...

javascript jquery arrays object
Rectangle 27 5

There's a new method to do this in ES6/2015 using findIndex and array spread operator:

const index = data.findIndex(obj => obj.id === id);
const newData = [
    ...data.slice(0, index),
    ...data.slice(index + 1)
]

You can turn it into a function for later reuse like this:

function remove(array, key, value) {
    const index = array.findIndex(obj => obj[key] === value);
    return index >= 0 ? [
        ...this.slice(0, index),
        ...this.slice(index + 1)
    ] : this;
}

This way you can to remove items by different keys using one method (and if there's no object that meets the criteria, you get original array returned):

const newData = remove(data, "id", "88");
const newData2 = remove(data, "name", "You are awesome!");

Or you can put it on your Array.prototype:

Array.prototype.remove = function (key, value) {
    const index = this.findIndex(obj => obj[key] === value);
    return index >= 0 ? [
        ...this.slice(0, index),
        ...this.slice(index + 1)
    ] : this;
};
const newData = data.remove("id", "88");
const newData2 = data.remove("name", "You are awesome!");

jquery - javascript find and remove object in array based on key value...

javascript jquery arrays object
Rectangle 27 4

Maybe you are looking for $.grep() function:

arr = [
  {"id":"88","name":"Lets go testing"},
  {"id":"99","name":"Have fun boys and girls"},
  {"id":"108","name":"You are awesome!"}
];

id = 88;
arr = $.grep(arr, function(data, index) {
   return data.id != id
});

jquery - javascript find and remove object in array based on key value...

javascript jquery arrays object
Rectangle 27 4

_.keys(object) Retrieve all the names of the object's properties.

_.keys({one : 1, two : 2, three : 3}); => ["one", "two", "three"]

Yes, you need an extra library, but it's so easy!

This is inferior to using Object.keys, as in Felix Kling's answer...

jquery - best way to get the key of a key/value javascript object - St...

javascript jquery
Rectangle 27 65

You can access each key individually without iterating as in:

var obj = { first: 'someVal', second: 'otherVal' };
alert(Object.keys(obj)[0]); // returns first
alert(Object.keys(obj)[1]); // returns second
const [firstKey, ...rest] = Object.keys(obj);

jquery - best way to get the key of a key/value javascript object - St...

javascript jquery
Rectangle 27 60

If you want to get all keys, ECMAScript 5 introduced Object.keys. This is only supported by newer browsers but the MDC documentation provides an alternative implementation (which also uses for...in btw):

if(!Object.keys) Object.keys = function(o){
     if (o !== Object(o))
          throw new TypeError('Object.keys called on non-object');
     var ret=[],p;
     for(p in o) if(Object.prototype.hasOwnProperty.call(o,p)) ret.push(p);
     return ret;
}

Of course if you want both, key and value, then for...in is the only reasonable solution.

p gives me the key but how do I get the value of the key? Thanks.

o[p]

jquery - best way to get the key of a key/value javascript object - St...

javascript jquery
Rectangle 27 36

var foo = { 'bar' : 'baz' }
bar
Object.keys(foo)[0]
baz
foo[Object.keys(foo)[0]]

Assuming a single object

jquery - best way to get the key of a key/value javascript object - St...

javascript jquery
Rectangle 27 2

use for each loop for accessing keys in Object or Maps in javascript

for(key in foo){
   console.log(key);//for key name in your case it will be bar
   console.log(foo[key]);// for key value in your case it will be baz
}

Note: you can also use

jquery - best way to get the key of a key/value javascript object - St...

javascript jquery
Rectangle 27 29

Responding to changes in the sort order (Step 1)

There's essentially three parts of this question that you have to solve. We'll look at all three.

The first issue we need to solve is reacting to changes in the order of sorted elements. If we check out the jQuery UI Sortable Widget's documentation, we see that it has a change event which fires whenever the sort order changes, and is perfect for our needs.

Side note: My original answer used stop instead of the change event. change is better (at least in this case) because it will report all changes in sorting, whether the change was interactive (user) or programmatic, and only if the order has actually changed. On the other hand, the sort event is only fired when the user stops sorting (releases the mouse, or lifts their finger).

Using the sort event, we can now respond to changes in sorting. The following will initialize a Sortable widget for us, and allow us to set a function to be called when the sort even fires:

var $sortableList = $("#your-list");

var sortEventHandler = function(event, ui){
    console.log("New sort order!");
};

$sortableList.sortable({
    stop: sortEventHandler
});

// You can also set the event handler on an already existing Sortable widget this way:

$sortableList.on("sortchange", sortEventHandler);

With that done, we're now ready to take on step 2:

This part is fairly simple. We just need to get an array of the elements in our sorted list. To do this, we can just ask for the children of the ul (list) element, using the jQuery function children():

var listElements = $sortableList.children();

console.log(listElements); // [ <li>, <li>, ... ]

Great, but we specifically need the element's values:

var listValues = [];

listElement.forEach(function(element){
    listValues.push(element.innerHTML);
});

console.log(listValues); // [ "Item 1", "Item 2", ... ]

Using .sortable("toArray") or .serialize() are also options.

Serialization is "the process of translating data structures or object state into a format that can be stored (for example, in a file or memory buffer, or transmitted across a network connection link)" (thanks Wikipedia!)

How you do this depends a lot on your specific needs, so we'll just discuss some of the ways you could get it done using jQuery.

If we use AJAX, we can just shoot off a request to the server with the new order. jQuery will automatically handle serializing listValues for us:

$.post("your-server.com/save_order", JSON.encode({ "items": listValues }) );

Create a form:

<form action="your-server.com/save_order" method="POST">
    <input name="items" value="" />
</form>
item
var serializedValue = $.param(listValues);

$("#ourForm > input").val(JSON.encode(listValues));
$("#ourForm").submit()
<form action="save_order.php" method="POST" style="display: none;">
<input name="new_order" value="" type="hidden" />
</form>
$(".selector").sortable({
    stop: function(event, ui) {
        var data = "";

        $("#sortable li").each(function(i, el){
            var p = $(el).text().toLowerCase().replace(" ", "_");
            data += p+"="+$(el).index()+",";
        });

        $("form > [name='new_order']").val(data.slice(0, -1));
        $("form").submit();
    }
});

And in save_order.php, you can parse the POST variable "new_order" and get the orders of Item 1, Item 2, Item 3, etc.

what is selector in this code?

@Phil_1984_ I rewrote this answer. Let me know if it helps.

Thanks. Your "Step 2" is the part I was interested in (and I think the OP too). I initially found it strange that the newly sorted element order was not made available in any of the fired events. The official docs go on about the old and new positions, but only as useless top & left pixel values. The library itself manipulates the element positions inside of the DOM for you, so doing a simple jquery selector in the event handler will give you the new order.

hey @mattsven i am new to jquery... can you please provide jsfiddel for this because i am finding difficulty to understand this

javascript - Get order of list items in a jQuery Sortable list after r...

javascript jquery