简体   繁体   中英

Making variable name dynamic based on input?

I'm trying to do multiple columns (ultimately based on user selection), where each column randomizes its results independently of the rest. That means I don't know for certain how many columns there'll be, and I want to be able to repeat the function as needed. I know there's a way to do this in PHP (something like $var{$i}, iirc), but how can I do it in angular?

html looks like this:

      <tr>
        <td><button ng-click="rollDice1(1)">rand 1</button></td>
        <td><button ng-click="rollDice2(2)">rand 2</button></td>
        <td><button ng-click="rollDice3(3)">rand 3</button></td>            
      </tr>
      <tr>
        <td>{{animal1}}</td>
        <td>{{animal2}}</td>
        <td>{{animal3}}</td>
      </tr>          

In my controller, right now, I have to do one for each, which is why there's a rollDice1, rollDice2, etc. Those each look like this:

$scope.rollDice1 = function () {
  $scope.animal1 = animalRand();
  $scope.color1 = colorRand();
  $scope.size1 = sizeRand();
  $scope.age1 = randFloor(15, 1);
}; 

So there's a rollDice2, which gives me animal2, color2, etc., then a rollDice3, and so on. What I'd like to do is just have one, though, and change the variable name based on the inputted value, but I can't figure out how to get that to work. Current version is:

$scope.rollDice = function (val) {
   $scope.animal[val] = animalRand();
   $scope.color[val] = colorRand();
   $scope.size[val] = sizeRand();
   $scope.age[val] = randFloor(15, 1);
};

I've tried a few others, like $scope.animal.val, even $scope.animal{val}, but these just throw errors at me. Is there a way to do this, or am I stuck making a separate function for each, and limiting the user's options, instead?

Plnkr is here: http://plnkr.co/edit/J0mYup?p=preview

thanks in advance!

You need to use array accessor notation using a string key built from the value. Your rollDice function should look like this:

$scope.rollDice = function (val) {
   $scope["animal" + val] = animalRand();
   $scope["color" + val] = colorRand();
   $scope["size" + val] = sizeRand();
   $scope["age" + val] = randFloor(15, 1);
};

Then you can call it using rollDice(1) , rollDice(2) , etc. from your template code.


If you have a lot of these, it might make more sense to store the data in an array. You could create an array on the scope, like this:

$scope.data = [];

Then, your rollDice function would look like this:

$scope.rollDice = function (val) {
   $scope.data[val] = {
       animal: animalRand(),
       color: colorRand(),
       size: sizeRand(),
       age: randFloor(15, 1),
   };
};

You would still call rollDice the same way, but then you'd use a different method of accessing the scope data from the HTML template.

<tr>
    <td>{{data[1].animal}}</td>
    <td>{{data[2].animal}}</td>
    <td>{{data[3].animal}}</td>
</tr>

This has the added advantage of being automated using things like ngRepeat . For example, that code could be reduced to this:

<tr>
    <td ng-repeat="item in data">{{item.animal}}</td>
</tr>

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM