Search code examples
javascriptember.jsbooleancomputed-properties

Why is "or" working but "and" is not in my Ember.ComputedProperty?


I think I'll feel stupid once I see the answer, but I can't wrap my head around why or is working but and isn't on this ComputedProperty. The tutorial suggested I'd need to use and, but I can't figure out how I'd do that if this doesn't work.

To start with I am new to Ember and familiar but not really comfortable with javascript, which is why I assume I'm having difficulty understanding what is going on here.

I have two properties that I need to both be true before a button isDisabled. I pass each of them to their own properties that reverse their boolean state so isDisabled remains active on a button until the original properties are both flipped.

contact.js

emailAddress: '',
  message: '',

  //**original properties**
  isValid: Ember.computed.match('emailAddress', /^.+@.+\..+$/),//starts as false
  validMessage: Ember.computed.gte('message.length', 5),//starts as false

  //**my reversing boolean properties**
  notYet: Ember.computed.not('isValid'),//starts as true
  notNow: Ember.computed.not('validMessage'),//starts as true


//isDisabled must be true to be active disabling button
  isDisabled: Ember.computed.or('notYet', 'notNow'),//starts as true

If I put in the correct emailAddress format:

emailAddress = true
notYet = false
isDisabled = true //still

If I then put a validMessage of 5 characters or more

  validMessage = true
  notNow = false
  isDisabled = false //now

Why does "or" work for this, why doesn't "and" or "not"?


Solution

  • Thats just De Morgan's laws.

    What you want is to be the button only be enabled when both values are valid. So you want the button be be active when isValid and validMessage.

    This means you want to button to be disabled when not(isValid and validMessage).

    Due to de Morgan's law this is equivalent to (not isValid) or (not validMessage).

    Because notYet is equal to not isValid it follows that (not isValid) or (not validMessage) is equal to notYet or (not validMessage).

    And because notNow is equal to not validMessage it follows that notYet or (not validMessage) is equal to notYet or notNow.

    And thats exactly your isDisabled. Thats why your code works. Just simple math. And of course in this context notYet or notNow would be something else. However this would be equivalent:

    isEnabled: Ember.computed.and('isValid', 'validMessage'),
    isDisabled: Ember.computed.not('isEnabled'),