Problem with IF/OR

Problem with IF/OR

murmanator
Advocate Advocate
1,053 Views
7 Replies
Message 1 of 8

Problem with IF/OR

murmanator
Advocate
Advocate

Good Afternoon Forum,

 

I have this program which allows the user to select a color from a pre-defined list for a particular plant when that plant is inserted. You can see from the code the plant is called "Bougainvillea Bush". RIght above that you will see the entire list of plants which have custom colors. I have been unable so far to incorporate any of the other plant types into the list to be able to select a color from a pre-defined set. Whenever I copy the code to define the color list, I cannot get it to work. I think my problem is with the IF/OR function or maybe with the placement of the code. The working code is:

 

;;; USE : (PLANTINSERT "PLANTTYPE" "PLANTNAME" "BOTANICALNAME")
(DEFUN PLANTINSERT (PLANTTYPE PLANTNAME PLNTBOTNM / COLR PNT SCL prntstr)
(GV)
(0V)
(SETVAR 'CMDECHO 1)
(setvar 'nomutt 0)
(dict-put PLANTNAME "botanical" (strcase PLNTBOTNM T))
(GETPLNTSIZ PLANTNAME)
(if (or (= PLANTNAME "Crape Myrtle")
(= PLANTNAME "Oleander")
(= PLANTNAME "Oleander Bush")
(= PLANTNAME "Dwarf Oleander")
(= PLANTNAME "Hibiscus")
(= PLANTNAME "Katie Ruellia")
(= PLANTNAME "Lady Banks Rose")
(= PLANTNAME "Rose")
(= PLANTNAME "Bougainvillea Bush")
(= PLANTNAME "Lemon")
(= PLANTNAME "Lime")
(= PLANTNAME "Orange")
(= PLANTNAME "Grapefruit")
(= PLANTNAME "Apricot")
(= PLANTNAME "Tangerine")
(= PLANTNAME "Tangelo")
(= PLANTNAME "Nectarine")
)
(if (= PLANTNAME "Bougainvillea Bush")
(progn
(initget 1 "OUG ANG ARB LA RAI RAS ROS SUP TEM")
(setq COLR (GETKWORD "\n\t\ *>> Select Type [bOUGainvillea sp./bANGkok red/bARBara karst/LA jolla/RAInbow gold/RASberry ice/ROSenka/SUPerstition gold/TEMple fire]: "))
(cond ((= COLR "OUG") (setq COLR "Bougainvillea sp."))
((= COLR "ANG") (setq COLR "Bangkok Red"))
((= COLR "ARB") (setq COLR "Barbara Karst"))
((= COLR "LA") (setq COLR "La Jolla"))
((= COLR "RAI") (setq COLR "Rainbow Gold"))
((= COLR "RAS") (setq COLR "Rasberry Ice"))
((= COLR "ROS") (setq COLR "Rosenka"))
((= COLR "SUP") (setq COLR "Superstition Gold"))
((= COLR "TEM") (setq COLR "Temple Fire"))
)

(dict-put PLANTNAME "COLOR" (strcase COLR))
)
(progn (setq prntstr (strcat "\n\t\ =>> What Color " PLANTNAME " : "))
(dict-put PLANTNAME "COLOR" (setq COLR (getstring T prntstr)))
)
)
)

 

And I was trying to insert this:

 

(if (= PLANTNAME "Orange")
(progn
(initget 1 "ARI NAV BLO VAL TRO")
(setq COLR (GETKWORD "\n\t\ *>> Select Type [ARIzona Sweet/NAVel/BLOod/VALencia/TROvita]: "))
(cond ((= COLR "ARI") (setq COLR "Arizona Sweet"))
((= COLR "NAV") (setq COLR "Navel"))
((= COLR "BLO") (setq COLR "Blood"))
((= COLR "VAL") (setq COLR "Valencia"))
((= COLR "TRO") (setq COLR "Trovita"))
)
(dict-put PLANTNAME "COLOR" (strcase COLR))
)
(progn (setq prntstr (strcat "\n\t\ =>> What Color " PLANTNAME " : "))
(dict-put PLANTNAME "COLOR" (setq COLR (getstring T prntstr)))
)
)

 

Thanks for looking and for any help in advance.

Matt

0 Likes
1,054 Views
7 Replies
Replies (7)
Message 2 of 8

hmsilva
Mentor
Mentor

Hi Matt,

the if function allows to test one expression and if true, do something, if not true, do something else...

If you need to have multiple test expressions in your code you should use the cond function

ex.

(cond ((= PLANTNAME "Bougainvillea Bush")
       ;; do the "Bougainvillea Bush" stuff
      )
      ((= PLANTNAME "Orange")
       ;; do the "Orange" stuff
      )
      ((= PLANTNAME "Hibiscus")
       ;; do the "Hibiscus" stuff
      )
      ;; and so on
)

Hope this helps,
Henrique

 

EESignature

0 Likes
Message 3 of 8

scot-65
Advisor
Advisor
[At the end of your "or" statement wrap a (progn ... );progn to the section of code]

Looks like a simple 2 popup_list dialog will be better
(and even a third popup_list for size of plant).
Are all colors shown to be used for all plants?
(No= This will be tricky in a dialog but doable)
I'm having a hard time figuring out the "dict-put" function.

Look into MEMBER for the if/or line
(if (member PLNTNAME (list "Crape Myrtle" "Rose" "Apple"...))
(progn
...
);progn
);if

Or better yet change the if/or to a COND.
(cond
((= PLANTNAME "Orange") (*make a call to a subroutine here* with or without attributes))
((= PLANTNAME "Apple") (*a separate subroutine with a different list of colors*))
((= PLANTNAME "Banana") (*or an attribute 'flag' directing to the appropriate color list in a single subroutine*))
(T (alert "New species detected."))
);cond

Scattered hints here.

???

Scot-65
A gift of extraordinary Common Sense does not require an Acronym Suffix to be added to my given name.

0 Likes
Message 4 of 8

hmsilva
Mentor
Mentor

Your code, with some modifications...

 

;;; USE : (PLANTINSERT "PLANTTYPE" "PLANTNAME" "BOTANICALNAME")
(defun PLANTINSERT (PLANTTYPE PLANTNAME PLNTBOTNM / COLR PNT SCL prntstr)
   (if (wcmatch PLANTNAME
                "Crape Myrtle,Oleander,Hibiscus,Katie Ruellia,Lady Banks Rose,Rose,Bougainvillea Bush,Lemon,Lime,Orange,Grapefruit,Apricot,Tangerine,Tangelo,Nectarine"
       )
      (progn
         (GV)
         (0V)
         (SETVAR 'CMDECHO 1)
         (setvar 'nomutt 0)
         (dict-put PLANTNAME "botanical" (strcase PLNTBOTNM T))
         (GETPLNTSIZ PLANTNAME)
         (cond ((= PLANTNAME "Bougainvillea Bush")
                (initget 1 "OUG ANG ARB LA RAI RAS ROS SUP TEM")
                (setq COLR (getkword
                              "\n\t\ *>> Select Type [bOUGainvillea sp./bANGkok red/bARBara karst/LA jolla/RAInbow gold/RASberry ice/ROSenka/SUPerstition gold/TEMple fire]: "
                           )
                )
                (setq COLR (nth (vl-position COLR '("OUG" "ANG" "ARB" "LA" "RAI" "RAS" "ROS" "SUP" "TEM"))
                                '("Bougainvillea sp." "Bangkok Red" "Barbara Karst" "La Jolla" "Rainbow Gold" "Rasberry Ice" "Rosenka" "Superstition Gold" "Temple Fire")
                           )
                )
                (dict-put PLANTNAME "COLOR" (strcase COLR))
               )
               ((= PLANTNAME "Orange")
                (initget 1 "ARI NAV BLO VAL TRO")
                (setq COLR (getkword "\n\t\ *>> Select Type [ARIzona Sweet/NAVel/BLOod/VALencia/TROvita]: "))
                (setq COLR (nth (vl-position COLR '("ARI" "NAV" "BLO" "VAL" "TRO"))
                                '("Arizona Sweet" "Navel" "Blood" "Valencia" "Trovita")
                           )
                )
                (dict-put PLANTNAME "COLOR" (strcase COLR))
               )
               (T
                (setq prntstr (strcat "\n\t\ =>> What Color " PLANTNAME " : "))
                (dict-put PLANTNAME "COLOR" (setq COLR (getstring T prntstr)))
               )
         ) ; cond
      ) ; progn
      (princ "\nWrong PLANTNAME... ")
   ) ; if
   (princ)
) ; defun

 

Hope this helps,
Henrique

EESignature

0 Likes
Message 5 of 8

murmanator
Advocate
Advocate

That did it, Henrique, thank you again. I had to move the last defun parenthesis down to the end of the total statement in order to include the size and location selectors, and also moved (GETPLNTSIZ PLANTNAME) to before the watch list statement so that that function included plants not in the watch list, but it all looks like its working now. Thank you so much!

0 Likes
Message 6 of 8

hmsilva
Mentor
Mentor

@murmanator wrote:

That did it, Henrique, thank you again. I had to move the last defun parenthesis down to the end of the total statement in order to include the size and location selectors, and also moved (GETPLNTSIZ PLANTNAME) to before the watch list statement so that that function included plants not in the watch list, but it all looks like its working now. Thank you so much!


 

You're welcome, murmanator
Glad you got a solution!

Henrique

EESignature

0 Likes
Message 7 of 8

Kent1Cooper
Consultant
Consultant

@hmsilva wrote:

.... 

....
((= PLANTNAME "Orange")
  (initget 1 "ARI NAV BLO VAL TRO")
  (setq COLR (getkword "\n\t\ *>> Select Type [ARIzona Sweet/NAVel/BLOod/VALencia/TROvita]: "))
  (setq COLR
(nth
(vl-position COLR '("ARI" "NAV" "BLO" "VAL" "TRO")) '("Arizona Sweet" "Navel" "Blood" "Valencia" "Trovita") ); nth ); setq (dict-put PLANTNAME "COLOR" (strcase COLR)) ) ....

 

....

Some thoughts occurred to me that led to this suggestion of a simplification that's also, I think, an operational improvement.  I'll use the example of that one PLANTNAME condition for "Orange" quoted above, just because it will take less space here than the "Bougainvillea Bush" condition.  You could replace it with this [and similarly in others]:

 

((= PLANTNAME "Orange")
  (setq str "ARIzona-sweet NAVel BLOod VALencia TROvita")
  (initget 1 str)
  (dict-put PLANTNAME "COLOR"
    (strcase
      (vl-string-subst
        " " "-"
        (getkword (strcat "\n\t\ *>> Select Type [" (vl-string-translate "- " " //" str) "]: "))
      ); vl-str...
    ); strcase
  ); dict-put
); ["Orange" condition]

The simplifications are:

 

1)  It spells out the possibilities only once [the 'str' variable], and modifies that slightly for one of the [only two] places where it's used, instead of spelling them out in different ways in four different places.  It has the hyphen within the two-word option because it uses the string un-modified in (initget), which can't handle two-word options.  But it converts that to a space and converts the spaces to slashes for the prompt in (getkword), resulting in the same prompt from the User's point of view, and also converts the hyphen to a space for the ultimate output into the (dict-put) function.

 

2)  It doesn't need the 'COLR' variable at all, much less two settings of a value into it, nor the associated (nth) & (vl-position) functions needed for that second setting.

 

The operational improvement is that the User can give their chosen option in the same ways that they can in typical AutoCAD option choices, specifically, they can type more than just the capital letters in each option in the prompt, if they want.  For the NAVel option, they can type "NAV" or "nav" [or other case combinations of those three letters] just as they can in the other approach.  But they can also type out the whole word "NAVEL" or "navel" [or likewise any case combination], or even [however unlikely] just "nave" if they happen to hit Enter one character short of the whole word.  In the other approach, typing "NAVEL" will result in an "Invalid option keyword" message and a re-prompt, which I expect a User would find puzzling, since they should be able to type it that way, given the prompt's wording and the usual way these things work.

 

Similarly, in the Bougainvillea condition, where the capitalized parts of some options are not the starting letters, it could potentially be even more puzzling to a User under the other approach.  My suggested approach will accept the typing in of letters preceding the capitalized ones [as long as the capitalized ones are included], such as "BOUG", whereas the other approach will consider that invalid, and will accept only some case combination of "OUG" for that choice.

Kent Cooper, AIA
Message 8 of 8

hmsilva
Mentor
Mentor

@Kent1Cooper wrote:
Some thoughts occurred to me that led to this suggestion of a simplification that's also, I think, an operational improvement.  I'll use the example of that one PLANTNAME condition for "Orange" quoted above, just because it will take less space here than the "Bougainvillea Bush" condition.  You could replace it with this [and similarly in others]:

 

((= PLANTNAME "Orange")
  (setq str "ARIzona-sweet NAVel BLOod VALencia TROvita")
  (initget 1 str)
  (dict-put PLANTNAME "COLOR"
    (strcase
      (vl-string-subst
        " " "-"
        (getkword (strcat "\n\t\ *>> Select Type [" (vl-string-translate "- " " //" str) "]: "))
      ); vl-str...
    ); strcase
  ); dict-put
); ["Orange" condition]

...


Nicely done!

 

Henrique

EESignature

0 Likes