0

I am storing a load of button shortcut types in an array of objects. I am trying to write a directive that will return some values depending on the name of the object. Here is my array stored within the controller:

angular.module('app')
.controller('BtnCtrl', function ($scope) {
    //......rest of controller code here

    $scope.hotKeys = [
        {name: 'primaryTest', keyCode: 49, keyShortcut: "1", funcTriggered: $scope.clickFunction},
        {name: 'secondaryTest', keyCode: 50, keyShortcut: "2", funcTriggered: $scope.clickFunction}
    ]
})

In my HTML directive, I want to specify the object using the name, and then use values from this object. Here is my attempt at a directive so far:

.directive("hotKeyButton", function() {
    return {
        controller: 'BtnCtrl',
        scope: {
            hotKeys: '='
        },
        transclude: true,
        template: "<div class='key-shortcut'>{{hotKeys.keyCode}}</div><div class='hotkey-label'>Button</div>"
    };
})

So here you can see I want to use the keyCode from the relevant row of the array, but I don't know how to pass in the name. Here is my (incorrect) HTML:

<button hot-key-button name="secondaryTest" class="po-btn secondary-btn" type="submit"></button>

How do I tell my directive to pull data from the secondaryTest object?

Thanks

2 Answers 2

1

Since you are using an array for your button, I would assume you use ng-repeat on your buttons? If this is the case, you can then pass the whole button instead of the name into your directive.

<div ng-repeat="button in hotKeys">
  <button hot-key-button hot-key="button" class="po-btn secondary-btn" type="submit"></button>
</div>

.directive("hotKeyButton", function() {
    return {
        controller: 'BtnCtrl',
        scope: {
            hotKey: '=' // you should really use singular here to avoid confusion
        },
        transclude: true,
        template: "<div class='key-shortcut'>{{hotKey.keyCode}}</div><div class='hotkey-label'>Button ({{hotKey.keyShortcut}})</div>"
    };
})

Actually you are not suppose to use <div> inside <button> as per html specification, try to use <span> instead, or use a <div> to replace the <button>.


Edit: In case you are not using it like an array, you might want to consider defining your store using key-value instead of array, so you can access specific entry using its name.

$scope.hotKeys = {
    'primaryTest': {name: 'primaryTest', keyCode: 49, keyShortcut: "1", funcTriggered: $scope.clickFunction},
    'secondaryTest': {name: 'secondaryTest', keyCode: 50, keyShortcut: "2", funcTriggered: $scope.clickFunction}
}

<button hot-key-button hot-key="hotkeys.primaryTest"></button>

// or use it as a variable
<button hot-key-button hot-key="hotkeys[btnName]"></button>
Sign up to request clarification or add additional context in comments.

1 Comment

Good comments...thankyou. I do not want to use a repeater as these buttons could be in various places on the page, they won't necessarily repeat regularly. This is more a place to store my keyboard shortcuts.
0

You could loop across the array checking for matches on name. Then you would need to assign the values from the matching record to a specific value on scope and your directive template should be wired up to match that value.

angular.module('app')
    .controller('BtnCtrl', function ($scope) {
    //......rest of controller code here

    $scope.selectedKeyCode;
    $scope.hotKeys = [
        {name: 'primaryTest', keyCode: 49, keyShortcut: "1", funcTriggered: $scope.clickFunction},
        {name: 'secondaryTest', keyCode: 50, keyShortcut: "2", funcTriggered: $scope.clickFunction}
    ];

    for (i = 0; i < $scope.hotKeys.length; i++) { 
      if ($scope.hotKeys[i].name === $scope.name){
          $scope.selectedKeyCode = row.keyCode;
      }
    }

})

.directive("hotKeyButton", function() {
    return {
    controller: 'BtnCtrl',
    scope: {
        name: '='
    },
    transclude: true,
    template: "<div class='key-shortcut'>{{selectedKeyCode}}</div><div class='hotkey-label'>Button</div>"
};

})

1 Comment

Very clever. For me this still isn't displaying the values - do I need to change the HTML?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.