#lang scheme
(require "code-write.ss"
"mreddesigner-misc.ss")
(define/provide (flat-prop->prop val)
(cond [(is-a? val property<%>) val]
[(atom? val)
(make-object prop:atom% val)]
[(list? val)
(make-object prop:atom% val)] [else
(printf "flat-prop->prop: Don't know what to do with ~a\n" val)]
))
(define/provide (prop->val p)
(cond [(is-a? p property<%>)
(send p get-value)]
[(symbol? p) (list 'quote p)]
[(list? p) (cons 'list (map prop->val p))]
[else p]
))
(define/provide property<%>
(interface () get-value generate-code))
(define (prop-value%% c%)
(class* (code-write%% c%) (property<%>)
(super-new)
(init-field value)
(code-fields value)
(field [update-callback #f])
(define/public (get-value) value)
(define/public (set-value v)
(set! value v)
(update) )
(define/public (generate-code)
value
)
(define/public (set-update-callback proc) (set! update-callback proc))
(define/public (update)
(when update-callback (update-callback this)))
))
(define prop:value%
(class (prop-value%% object%)
(super-new)
(inherit-field value)
(define/override (generate-code)
(prop->val value))
))
(define/provide prop:field-id%
(class prop:value%
(init-field field-id [option #f] [necessary #f] [no-code #f] [hidden #f])
(code-fields field-id option necessary no-code hidden)
(super-new)
(getter field-id necessary no-code hidden)
(getter/setter option)
(inherit-field value)
(define/public (get-prop) value)
(define/override (get-value)
(send value get-value))
(define/override (update)
(send value update))
(define/public (option-symbol [prefix ""])
(symbol-append* prefix field-id))
(define/public (option-keyword [prefix ""])
(symbol->keyword (option-symbol prefix)))
(define/public (generate-option [prefix ""])
(if option
(list (option-keyword prefix)
(list (option-symbol prefix) (send value generate-code)))
'()))
(define/override (generate-code [prefix ""])
(if option
(option-symbol prefix)
(send value generate-code)))
))
(define/provide prop:atom%
(class prop:value% (super-new)))
(define/provide (prop:atom v)
(new prop:atom% [value v]))
(define/provide prop:boolean%
(class prop:value%
(init-field label)
(code-fields label)
(getter label)
(super-new)))
(define/provide (prop:bool label v)
(new prop:boolean% [label label] [value v]))
(define/provide prop:file%
(class prop:value% (super-new)))
(define/provide (prop:file v)
(new prop:file% [value v]))
(define/provide prop:one-of%
(class prop:value%
[init-field choices]
(field [prop-choices choices])
(super-new)
(code-fields choices)
(getter prop-choices)
))
(define/provide (prop:one-of choices val)
(make-object prop:one-of% choices val))
(define prop:value-list%
(class prop:value%
(super-new)
(inherit-field value)
(define/override (get-value)
(map-send get-value value))
(define/override (generate-code)
(cons 'list (map-send generate-code value)))
))
(define/provide prop:some-of%
(class prop:value%
(init-field choices)
(super-new)
(inherit-field value)
(code-fields choices)
(getter choices)
(define/override (generate-code)
(list 'quote value))
))
(define/provide (prop:some-of choices val-list)
(make-object prop:some-of% choices val-list))
(define/provide prop:group%
(class prop:value%
(super-new)
(inherit-field value)
(define/public (get-props) value)
(define/override (get-value)
(map-send get-value value))
(define/override (generate-code)
(cons 'list (map-send generate-code value)))
(define/override (update) (for-each-send update value))
))
(define/provide (prop:group . vlist)
(make-object prop:group% (map flat-prop->prop vlist)))
(define/provide prop:popup%
(class prop:value%
(super-new)
(inherit-field value)
(define/public (get-prop) value)
(define/override (get-value)
(send value get-value))
(define/override (generate-code)
(send value generate-code))
(define/override (update)
(send value update))
))
(define/provide (prop:popup val)
(make-object prop:popup% (flat-prop->prop val)))
(define/provide prop:code%
(class prop:value%
(super-new)
(init-field value-code)
(define/override (code-write-args)
(list (list 'value value-code)
(list 'value-code (list 'quote value-code))))
(setter value-code)
(define/override (generate-code)
value-code)
))
(provide prop:code)
(define-syntax-rule (prop:code fun)
(new prop:code% [value fun]
[value-code 'fun]))
(provide prop:code-set-value)
(define-syntax-rule (prop:code-set-value prop fun)
(begin
(send prop set-value-code 'fun)
(send prop set-value fun)))
(define/provide prop:proc%
(class prop:value%
(inherit-field value)
(super-new)
(init-field prop-code)
(code-fields prop-code)
(setter prop-code)
(define/public (get-prop) value)
(define/override (get-value)
((send prop-code get-value) (send value get-value)))
(define/override (generate-code)
(list (send prop-code generate-code)
(send value generate-code)))
))
(provide prop:proc)
(define-syntax-rule (prop:proc v fun)
(new prop:proc% [value (flat-prop->prop v)]
[prop-code (prop:code fun)]))