Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Knockout JS: Conditional Switch Case

My current task is to replace knockout js conditional if to switch case(or like multiple if case) to check more than two conditions. The scenario is if the user is authenticated then the toggle icon should be visible in green color and for un authenticated user the toggle icon should be in grey color. Below is the code for the scenario I stated here, IsAuthenticatedUser() is a bool value always have true or false. Now I have to change the bool(0 1) value to flag(0 1 2 3) value.

Bool representation is, 
0 - Not Authenticated - grey icon
1 - Authenticated - green icon

Flag Value
0 - Not Authenticated - grey icon
1 - Authenticated - green icon
2 - Authenticated but expired - no icon
3 - Authenticated but not yet license period started - no icon

For bool value the Knockout JS conditional separation is like,

<!-- ko if: IsAuthenticatedUser() -->
<i class="fa fa-toggle-on faIcons green" title="Active"
   data-bind="click: function (data, event) { $parent.functiongoeshere }"></i>
<!-- /ko -->

<!-- ko if: !IsNotAuthenticatedUser() -->
<i class="fa fa-toggle-on faIcons fa-rotate-180 toggleOff" title="Inactive"
   data-bind="click: function (data, event) { $parent.functiongoeshere }"></i>
<!-- /ko -->

For Flag value, I have to do something like below,

<!-- ko if: UserFlag == 1 -->
<i class="fa fa-toggle-on faIcons green" title="Active"
   data-bind="click: function (data, event) { $parent.functiongoeshere }"></i>
<!-- /ko -->

<!-- ko if: UserFlag == 0 -->
<i class="fa fa-toggle-on faIcons fa-rotate-180 toggleOff" title="Inactive"
   data-bind="click: function (data, event) { $parent.functiongoeshere }"></i>
<!-- /ko -->

<!-- ko if: UserFlag == 2 -->
<!-- No ICON -->
<!-- /ko -->

<!-- ko if: UserFlag == 2 -->
<!-- No ICON -->
<!-- /ko -->

But this is not working, So is there another way to use if for multiple condition checking or how we can user switch control to handle this scenario.

Any suggestion would be helpful.

like image 410
Jeya Suriya Muthumari Avatar asked Nov 24 '25 10:11

Jeya Suriya Muthumari


2 Answers

Instead of 4 <!-- ko if --> I would instead move the logic to the view model.

From my experience, it's always better to have as few logic as possible in the view.

Moving logic to view model allows you to unit-test your behavior, while it's difficult to test the view rendering. In addition, complex views tend to be far less readable than complex view model, because of verbose syntax which has to be used, such as <!-- ko if --> or complex data-bind.

I tried to make a simplified example matching your needs, in which the same template is displayed differently depending on the user's status. To do that, I make use of the css binding.

click on the page to change user's status.

var myVM = function() {
    var _this = this;
    _this.status = ko.observable(2);
  
    _this.authenticationStyle = ko.computed(function() {
      if (_this.status() == 0) return "anonymous";
      if (_this.status() == 1) return "expired";
      return "authenticated";
    }, this);
  
    _this.statusText = ko.computed(function() {
      if (_this.status() == 0) return "please log in";
      if (_this.status() == 1) return "please refresh";
      return "welcome";
    }, this);
};

var vm = new myVM();
ko.applyBindings(vm);

window.onclick = function() {
  var newStatus = vm.status() + 1;
  if (newStatus > 2)
    newStatus = 0;
  vm.status(newStatus);
};
.anonymous {
  display: none;
}
.expired {
  color: lightgrey;
  background-color: yellow;
}
.authenticated {
  color: black;
  background-color: green;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.2.0/knockout-min.js"></script>


<div data-bind="css: authenticationStyle">
  <div data-bind="text: statusText"></div>
</div>
like image 196
Regis Portalez Avatar answered Nov 27 '25 03:11

Regis Portalez


Your ko if: UserFlag should work, although I would change it to userFlag and you might need it to be ko if: userFlag()

Also, why not keep it simple and create a getAuthClass() function, and bind the element attributes and calculate all the icons in the viewModel?

like image 28
brianlmerritt Avatar answered Nov 27 '25 04:11

brianlmerritt



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!