Calculating checkbox names ...

Guiserver, GTK-server, OpenGL, PostScript,
HTML 5, MIDI, IDE
Locked
cormullion
Posts: 2038
Joined: Tue Nov 29, 2005 8:28 pm
Location: latiitude 50N longitude 3W
Contact:

Calculating checkbox names ...

Post by cormullion »

I can't get this code to work ...

Code: Select all

(load (string (env "NEWLISPDIR") "/guiserver.lsp"))

(gs:init) 
(gs:frame 'w1 200 200 200 200 "w1")
(gs:panel 'ControlPanel)
 
; options check boxes, defined in a list
(set 'check-boxes 
  '((TheCheckBox1 "one") 
    (TheCheckBox2 "two")
   ))

(dolist (cb check-boxes)
   (gs:check-box (first cb) 'checkboxing (last cb))
   (gs:set-selected (first cb) nil)
   (gs:add-to 'ControlPanel (first cb)))

(gs:add-to 'w1 'ControlPanel)

(gs:set-visible 'w1 true)

(define (checkboxing)
  (let ((widget (args 0))
        (value  (args 1))
        (option-number {})
       )
  (and 
    (find {MAIN:TheCheckBox} widget)
    (set 'option-number (last widget)) 
    (set (sym (string {option} option-number)) (if value 1 0)))
  
  (if (= (sym (string {option} option-number)) 1)
      (gs:set-selected (string {TheCheckBox} option-number) true)
      (gs:set-selected (string {TheCheckBox} option-number) nil))
  (println {option1: } option1 { option2: } option2)
  )
) 

(set 
 'option1 0 
 'option2 0 
)
Although the check boxes work ok, and set the variables that they're supposed to, there's an error message as well each time you click on them.

I'm trying to write code that handles a load of checkboxes - so constructing the checkbox name using (sym or (string should be the best way, but doesn't seem to work... Any thoughts?

Lutz
Posts: 5289
Joined: Thu Sep 26, 2002 4:45 pm
Location: Pasadena, California
Contact:

Post by Lutz »

you are thinking in the right direction, look at the following modified code which works (but the check disappears immediately, which is another logic error?):

Code: Select all

(load (string (env "NEWLISPDIR") "/guiserver.lsp")) 

(gs:init) 
(gs:frame 'w1 200 200 200 200 "w1") 
(gs:panel 'ControlPanel) 
  
; options check boxes, defined in a list 
(set 'check-boxes 
  '((TheCheckBox1 "one") 
    (TheCheckBox2 "two") 
   )) 

(dolist (cb check-boxes) 
   (gs:check-box (first cb) 'checkboxing (last cb)) 
   (gs:set-selected (first cb) nil) 
   (gs:add-to 'ControlPanel (first cb))) 

(gs:add-to 'w1 'ControlPanel) 

(gs:set-visible 'w1 true) 

(define (checkboxing) 
(println (args)) ;;;;;;;;;;;;;;;;;;;; added this for debugging
  (let ((widget (args 0)) 
        (value  (args 1)) 
        (option-number {}) 
       ) 
  (and 
    (find {MAIN:TheCheckBox} widget) 
    (set 'option-number (last widget)) 
    (set (sym (string {option} option-number)) (if value 1 0))) 
  
  (if (= (sym (string {option} option-number)) 1) 
      (gs:set-selected (string {MAIN:TheCheckBox} option-number) true) ;;; prepended MAIN 
      (gs:set-selected (string {MAIN:TheCheckBox} option-number) nil)) 
  (println {option1: } option1 { option2: } option2) 
  ) 
) 

(set 
 'option1 0 
 'option2 0 
)

(gs:listen) ;;;;;;; added this so clicks get processed
look for the 3 modifications prefixed with lots of ;;

Lutz

cormullion
Posts: 2038
Joined: Tue Nov 29, 2005 8:28 pm
Location: latiitude 50N longitude 3W
Contact:

Post by cormullion »

Thanks! I forgot "MAIN". (And I also forgot to evaluate the constructed symbol. Duh.)

This is the whole thing.

Code: Select all

(load (string (env "NEWLISPDIR") "/guiserver.lsp"))

(gs:init) 
(gs:frame 'RegexTester 200 200 650 650 "RegexTester")
(gs:panel 'MainPanel)
(gs:set-grid-layout 'MainPanel 2 2)

(gs:text-area 'string-input 'textfield-handler)
(gs:text-pane 'regex-input 'textfield-handler)
(gs:text-pane 'output 'gs:no-action)
 
(gs:set-background 'string-input '(0.9 0.9 0.8))
(gs:set-background 'regex-input '(0.9 0.7 0.7))
(gs:set-background 'output '(0.8 0.9 0.8))

(gs:set-font 'string-input "Sans Serif" 14)
(gs:set-font 'regex-input  "Sans Serif" 14)

(gs:panel 'ControlPanel)
(gs:set-grid-layout 'ControlPanel 13 1)

; The options checkboxes, defined in a list.
(set 'checkboxes 
  '((CheckBox1  {caseless}) 
    (CheckBox2  {multiline})
    (CheckBox3  {. matches all})
    (CheckBox4  {extended})
    (CheckBox5  {anchored})
    (CheckBox6  {$ matches at end of string, not before newline})
    (CheckBox7  {-})
    (CheckBox8  {first ch, not start of line ^ shouldn't match})
    (CheckBox9  {last char, not end of line $ shouldn't match})
    (CheckBox10 {invert greediness of quantifiers})
    (CheckBox11 {empty string considered invalid})
    (CheckBox12 {UTF8})))

; make the checkboxes
(dolist (cb checkboxes)
   (gs:check-box (first cb) 'checkboxing (last cb))
   (gs:set-selected (first cb) nil)
   (gs:add-to 'ControlPanel (first cb)))

(gs:add-to 'MainPanel 'string-input 'regex-input 'output 'ControlPanel)
(gs:add-to 'RegexTester 'MainPanel)
(gs:set-visible 'RegexTester true)

; checkbox handler
(define (checkboxing)
  (let ((widget (args 0))
        (value  (args 1))
        (option-number {})
       )
  (if (find {MAIN:CheckBox} widget)
    (begin
      (set 'option-number (replace {.*?(\d+)} widget $1 0)) 
      ; option-number should now be 1 2 3 4 5 to identify the checkbox... 
      (set (sym (string {option} option-number)) (if value 1 0))
      (if (= (eval (sym (string {option} option-number))) 1)
          (gs:set-selected (string {MAIN:CheckBox} option-number) true)
          (gs:set-selected (string {MAIN:CheckBox} option-number) nil))
      ; set the option global
      (set '*opt* 
        (+ (* 1 option1) 
           (* 2 option2) 
           (* 4 option3) 
           (* 8 option4) 
           (* 16 option5)
           (* 32 option6)
           (* 64 option7)
           (* 128 option8)
           (* 256 option9)
           (* 512 option10)
           (* 1024 option11)
           (* 2048 option12)
           ))))
  ; perform the regex again with the new options
  (do-match)
 )
) 

(define (do-match)
  (set 'results {})
  (set '$1 {} '$2 {} '$3 {} '$4 {} '$5 {} '$6 {} '$7 {} '$8 {} '$9 {})
  (if (catch (regex *rgx* *strng* *opt*) 'error)
      (begin
          (for (i 0 9) (push  (string {$} i { } (if ($ i) ($ i) {}) "\n") results -1))
          (gs:set-text 'output (string "Option: " *opt* "\n" results "\n" error))
          )
      (gs:set-text 'output (string {Problem: } error))))    
      
(define (textfield-handler id text)
	(gs:get-text id 'gettextcallback-handler))

(define (gettextcallback-handler id text)
  (and
    text
    (cond
       ((= id "MAIN:string-input")
          (set '*strng* (base64-dec text)))
       ((= id "MAIN:regex-input")
          (set '*rgx* (base64-dec text)))
       true
          (gs:no-action))
    (not (for-all empty? (list *rgx* *strng* *opt*)))
    (do-match *rgx* *strng* *opt*)
   )
)

(map set '(option1 option2 option3 option4 option5 option6 option7 option8 option9 option10 option11 option12) (dup 0 12))

(set 
 '*opt* 0 
 '*strng* {newLISP supports Perl-compatible regular expressions.} 
 '*rgx* "(n.{1,3}).*(rl-)")

; initial display
(gs:set-text 'string-input *strng*)
(gs:set-text 'regex-input *rgx*)
(do-match)

(gs:listen)

Lutz
Posts: 5289
Joined: Thu Sep 26, 2002 4:45 pm
Location: Pasadena, California
Contact:

Post by Lutz »

excellent! strong contender for this year's newLISP competition :-) (-> Norman ?)

Lutz


ps: what confused me at first was an error message displayed on wrong regex options, but then reading you code, I realized it was intended, the code is correctly catching the error and displaying it. Perhaps some additional text to calm down the panicking user :-?

newdep
Posts: 2038
Joined: Mon Feb 23, 2004 7:40 pm
Location: Netherlands

Post by newdep »

It sure is !!

very nicely done this one... aaaaaa great move ;-)
-- (define? (Cornflakes))

cormullion
Posts: 2038
Joined: Tue Nov 29, 2005 8:28 pm
Location: latiitude 50N longitude 3W
Contact:

Post by cormullion »

Lutz wrote: ps: what confused me at first was an error message displayed on wrong regex options, but then reading you code, I realized it was intended, the code is correctly catching the error and displaying it. Perhaps some additional text to calm down the panicking user :-?
:) Panicking user and confused coder!

I'm not 100% confident about catch yet.. I suppose I should have called 'error something else - it's only an error message if it's an error (and catch returns nil), otherwise it's the return value (and catch doesn't return nil)? Perhaps it should be 'status' or something...

By the way - those higher options (128?) ... are weird - do they all work?

Lutz
Posts: 5289
Joined: Thu Sep 26, 2002 4:45 pm
Location: Pasadena, California
Contact:

Post by Lutz »

By the way - those higher options (128?) ... are weird - do they all work?
The options (except for REPLACE_ONCE 0x8000) are passed directly on to the PCRE library routines (part of the newLISP code base and copy of the original PCRE code base) and I have reason to believe they work. I often use 512 for un-greediness, which works well, don't have experience with 128 and 256. This document gives you more insight and also has a few examples for using options: http://newlisp.org/downloads/pcrepattern.html

Lutz

Locked