Como usar uma variável para uma chave em um literal de object JavaScript?

Por que o seguinte trabalho?

.stop().animate( { 'top' : 10 }, 10 ); 

Considerando que isso não funciona:

 var thetop = 'top'; .stop().animate( { thetop : 10 }, 10 ); 

Para torná-lo ainda mais claro: No momento, não consigo passar uma propriedade CSS para a function animada como uma variável.

{ thetop : 10 } é um literal de object válido. O código criará um object com uma propriedade denominada thetop que tenha um valor de 10. Os dois thetop a seguir são os mesmos:

 obj = { thetop : 10 }; obj = { "thetop" : 10 }; 

No ES5 e anteriores, você não pode usar uma variável como um nome de propriedade dentro de um literal de object. Sua única opção é fazer o seguinte:

 var thetop = "top"; // create the object literal var aniArgs = {}; // Assign the variable property name with a value of 10 aniArgs[thetop] = 10; // Pass the resulting object to the animate method .stop().animate( aniArgs, 10 ); 

ES6 define ComputedPropertyName como parte da gramática para literais de object, que permite escrever o código da seguinte forma:

 var thetop = "top", obj = { [thetop]: 10 }; console.log(obj.top); // -> 10 

Você pode usar essa nova syntax nas versões mais recentes de cada navegador principal.

Com o ECMAScript 2015, agora você pode fazer isso diretamente na declaração de objects com a notação de colchetes:

 var obj = { [key]: value } 

Onde key pode ser qualquer tipo de expressão (por exemplo, uma variável) retornando um valor.

Então aqui seu código ficaria assim:

 .stop().animate({ [thetop]: 10 }, 10) 

Onde thetop será substituído pelo valor da variável.

ES5 citação que diz que não deve funcionar

Especificações: http://www.ecma-international.org/ecma-262/5.1/#sec-11.1.5

Nome da propriedade :

  • IdentifierName
  • StringLiteral
  • NuméricoLiteral

[…]

A produção PropertyName: IdentifierName é avaliada da seguinte maneira:

  1. Retorne o valor String contendo a mesma seqüência de caracteres que o IdentifierName.

A produção PropertyName: StringLiteral é avaliada da seguinte maneira:

  1. Retorna o valor SV [String] do StringLiteral.

A produção PropertyName: NumericLiteral é avaliada da seguinte maneira:

  1. Seja nbr o resultado da formação do valor do NumeralLiteral.
  2. Retornar ToString (nbr).

Isso significa que:

  • { theTop : 10 } é exatamente o mesmo que { 'theTop' : 10 }

    O PropertyName theTop é um IdentifierName , portanto, é convertido para o valor da string 'theTop' , que é o valor da string 'theTop' .

  • Não é possível escrever inicializadores de object (literais) com chaves variables.

    As únicas três opções são IdentifierName (expande para string literal), StringLiteral e NumericLiteral (também se expande para uma string).

As regras foram alteradas para o ES6: https://stackoverflow.com/a/2274327/895245

Eu usei o seguinte para adicionar uma propriedade com um nome “dynamic” para um object:

 var key = 'top'; $('#myElement').animate( (function(o) { o[key]=10; return o;})({left: 20, width: 100}), 10 ); 

key é o nome da nova propriedade.

O object das propriedades passadas para animate será {left: 20, width: 100, top: 10}

Isso é apenas usar a notação [] necessária, conforme recomendado pelas outras respostas, mas com menos linhas de código!

Adicionando colchetes ao redor da variável funciona bem para mim. Tente isso

 var thetop = 'top'; .stop().animate( { [thetop] : 10 }, 10 ); 

Dado código:

 var thetop = 'top'; .stop().animate( { thetop : 10 }, 10 ); 

Tradução:

 var thetop = 'top'; var config = { thetop : 10 }; // config.thetop = 10 .stop().animate(config, 10); 

Como você pode ver, a { thetop : 10 } não faz uso da variável thetop . Em vez disso, cria um object com uma chave chamada thetop . Se você quer que a chave seja o valor da variável thetop , então você terá que usar colchetes ao redor do thetop :

 var thetop = 'top'; var config = { [thetop] : 10 }; // config.top = 10 .stop().animate(config, 10); 

A syntax de colchetes foi introduzida com o ES6. Nas versões anteriores do JavaScript, você teria que fazer o seguinte:

 var thetop = 'top'; var config = ( obj = {}, obj['' + thetop] = 10, obj ); // config.top = 10 .stop().animate(config, 10); 

Desta forma também você pode alcançar o resultado desejado

 var jsonobj={}; var count=0; $(document).on('click','#btnadd', function() { jsonobj[count]=new Array({ "1" : $("#txtone").val()},{ "2" : $("#txttwo").val()}); count++; console.clear(); console.log(jsonobj); }); 
  value 1 value 2