From 374226e6b7003eee4950613286682b96d43e5d77 Mon Sep 17 00:00:00 2001 From: Miguel de Benito Date: Sat, 7 Apr 2012 12:02:10 +0000 Subject: [PATCH] More documentation for widgets --- devel/scheme/gui/scheme-gui-advanced.en.tm | 54 ++++ devel/scheme/gui/scheme-gui-intro.en.tm | 335 ++++++++++++++++++++ devel/scheme/gui/scheme-gui-reference.en.tm | 21 ++ devel/scheme/gui/scheme-gui.en.tm | 249 +++------------ 4 files changed, 447 insertions(+), 212 deletions(-) create mode 100644 devel/scheme/gui/scheme-gui-advanced.en.tm create mode 100644 devel/scheme/gui/scheme-gui-intro.en.tm create mode 100644 devel/scheme/gui/scheme-gui-reference.en.tm diff --git a/devel/scheme/gui/scheme-gui-advanced.en.tm b/devel/scheme/gui/scheme-gui-advanced.en.tm new file mode 100644 index 0000000..d7df1a9 --- /dev/null +++ b/devel/scheme/gui/scheme-gui-advanced.en.tm @@ -0,0 +1,54 @@ + + + + +<\body> + + + + + + + <\scm> + aligned + + + + + + + + + + + From the definitions... + + <\verbatim> + ((== x '---) '$---) + + ((== x '===) (gui-make '(glue #f #f 0 5))) + + ((== x '======) (gui-make '(glue #f #f 0 15))) + + ((== x '/) '$/) + + ((== x '//) (gui-make '(glue #f #f 5 0))) + + ((== x '///) (gui-make '(glue #f #f 15 0))) + + ((== x '\\) (gui-make '(glue #t #f 5 0))) + + ((== x '\\\) (gui-make '(glue #t #f 15 0))) + + ((== x (string-\symbol "\|")) '$/) + + + + + Refresh widgets reevaluate their contents every time a command is + executed... + + + + \; + \ No newline at end of file diff --git a/devel/scheme/gui/scheme-gui-intro.en.tm b/devel/scheme/gui/scheme-gui-intro.en.tm new file mode 100644 index 0000000..da3c60a --- /dev/null +++ b/devel/scheme/gui/scheme-gui-intro.en.tm @@ -0,0 +1,335 @@ + + + + +<\body> + + + + + In you create visual interfaces using . This word + means either the basic building blocks you have at your disposal, like + buttons, popup lists, etc. or the collections of those into dialogs, menus + or whatever. This rather loose concept might be confusing, especially when + we refer to what usually are know as dialogs as widgets, but it makes sense + because all sorts of widgets can be aggregated to build more complicated + ones as well.<\footnote> + If you miss some particular ``building block'' from your OS, you might + see whether it's feasible as an aggregation of simpler ones or try and + play with the UI interface code in C++ (but you'll have to add it for + every supported platform!). + + + A complete reference with all the available widgets is + , some more examples are here and + here. + + To create a widget, you'll want to use to define a new one. + The call to this function uses its particular syntax, with many keywords + for the creation of widgets. You can see the whole list of keywords in the + table inside , + but we'll start with some buttons.\ + + + + Execute the following two lines to get the unavoidable example and leave + your mouse over the ``Hello'' button. + + <\session|scheme|default> + <\input|Scheme] > + (tm-widget (example1) ("Hello" "world!")) + + + <\input|Scheme] > + (top-window example1 "A first try") + + + + As you can see, buttons are implicitly created by simply writing a list + with the button's title and a tooltip to be displayed when the user hovers + over the button. A bit confusing, and also ugly, because this is intended + for buttons. What you probably want is + this: + + <\session|scheme|default> + <\input|Scheme] > + (tm-widget (example2) (explicit-buttons ("Hello" (noop)))) + + + <\input|Scheme] > + (top-window example2 "A nicer button") + + + + The second argument is now a command to be executed when the user + clicks the button, in this case a no-operation, or . Try + changing it for or anything that suits you. + + The next step is to add some text next to the button, i.e. a label. This is + done with the keyword, as in , but in order + to have both widgets sit side by side, you'll need a + >, such as : + + <\session|scheme|default> + <\unfolded-io|Scheme] > + (tm-widget (example3) + + \ \ (hlist\ + + \ \ \ \ (text "Hello")\ + + \ \ \ \ (explicit-buttons ("world" (display "!\\n"))))) + <|unfolded-io> + \; + + + <\input|Scheme] > + (top-window example3 "Some text") + + + + That was nice, but as you see, the two widgets are packed together until + you resize the window. We need to explicitly tell to insert some + space between them: + + <\session|scheme|default> + <\unfolded-io|Scheme] > + (tm-widget (example3) + + \ \ (hlist\ + + \ \ \ \ (text "Hello") + + \ \ \ \ \\\ + + \ \ \ \ (explicit-buttons ("world" (display "!\\n"))))) + <|unfolded-io> + \; + + + <\input|Scheme] > + (top-window example3 "Some text") + + + + The special symbol \\> is just one of the + predefined .\ + + + + Let's see how you create a dialog. To get started here is one little + example taken from : + + <\session|scheme|default> + <\unfolded-io|Scheme] > + (tm-widget (widget1) + + \ \ (centered + + \ \ \ \ (aligned + + \ \ \ \ \ \ (item (text "First:") + + \ \ \ \ \ \ \ \ (toggle (display* "First " answer "\\n") #f)) + + \ \ \ \ \ \ (item (text "Second:") + + \ \ \ \ \ \ \ \ (toggle (display* "Second " answer "\\n") #f))))) + <|unfolded-io> + \; + + + + The keyword is clear, but not so much: it + builds two column tables, with each row of type . As you can see, + each takes two arguments, which can be of + type. + + The is another example of a widget which triggers a + command whenever it's clicked, or toggled in this case. The second argument + stands for the default state of the . + + Again, in order to display this you create a and give it a + title. + + <\session|scheme|default> + <\input|Scheme] > + (top-window widget1 "Two toggle widgets") + + + + You'll notice that the created window is too small and the title is not + wholly displayed. You can force it to be of a certain size using + : + + <\session|scheme|default> + <\unfolded-io|Scheme] > + (tm-widget (widget1) + + \ \ (centered + + \ \ \ \ (resize "500px" "200px" + + \ \ \ \ \ \ (aligned + + \ \ \ \ \ \ \ \ (item (text "First:") + + \ \ \ \ \ \ \ \ \ \ (toggle (display* "First " answer "\\n") #f)) + + \ \ \ \ \ \ \ \ (item (text "Second:") + + \ \ \ \ \ \ \ \ \ \ (toggle (display* "Second " answer "\\n") #f)))))) + <|unfolded-io> + \; + + + <\input|Scheme] > + (top-window widget1 "A bigger window") + + + + + + is one of the several available container or . + + If you want to add the usual buttons you use like in + the following example. Notice that the widget now accepts one parameter + which will be called when the user clicks the ``Ok'' button. + + <\session|scheme|default> + <\unfolded-io|Scheme] > + (tm-widget (widget1-buttons cmd) + + \ \ (centered + + \ \ \ \ (aligned + + \ \ \ \ \ \ (item (text "First:") + + \ \ \ \ \ \ \ \ (toggle (display* "First " answer "\\n") #f)) + + \ \ \ \ \ \ (item (text "Second:") + + \ \ \ \ \ \ \ \ (toggle (display* "Second " answer "\\n") #f)))) + + \ \ (bottom-buttons \\ ("Ok" (cmd "Ok")))) + <|unfolded-io> + \; + + + + Since the widget now needs an argument, we must use another function to + display it, namely , which will also close the window + after the button has been clicked. + + <\session|scheme|default> + <\input|Scheme] > + (dialogue-window widget1-buttons (lambda (arg) (display* arg "\\n")) + "Two toggles") + + + + That special at the bottom \> inserts as before + whitespace, but it stretches and aligns the to the + right (). This is just another example of a + , of which there are more described + . + + As you can see, the approach we've shown has a shortcoming: there's no way + to access all the values of the different widgets in your dialog at the + same time. Of course you can use the function passed to your + widget to perform some computations, but in case you need to retrieve or + store complicated data, what you need is a form (See + ). + + + + As explained in the available widgets can be + used to create menu items and dialog windows, but you may want to create + more complex dialogs to perform more complicated tasks. Forms provide one + mechanism to do this. They allow you to define multiple named fields of + several types, whose values are stored in a hash table You can retrieve and + return the values of this hash when the user clicks a button using the + functions and . + + In the following example you can see that the syntax is pretty much the + same as for regular widgets, but you must prefix the keywords with + : + + <\session|scheme|default> + <\folded-io|Scheme] > + (tm-widget (form3 cmd) + + \ \ (resize "500px" "500px" + + \ \ \ \ (padded + + \ \ \ \ \ \ (form "Test" + + \ \ \ \ \ \ \ \ (aligned + + \ \ \ \ \ \ \ \ \ \ (item (text "Input:") + + \ \ \ \ \ \ \ \ \ \ \ \ (form-input "fieldname1" "string" '("one") + "1w")) + + \ \ \ \ \ \ \ \ \ \ (item === ===) + + \ \ \ \ \ \ \ \ \ \ (item (text "Enum:") + + \ \ \ \ \ \ \ \ \ \ \ \ (form-enum "fieldname2" '("one" "two" "three") + "two" "1w")) + + \ \ \ \ \ \ \ \ \ \ (item === ===) + + \ \ \ \ \ \ \ \ \ \ (item (text "Choice:") + + \ \ \ \ \ \ \ \ \ \ \ \ (form-choice "fieldname3" '("one" "two" + "three") "one")) + + \ \ \ \ \ \ \ \ \ \ (item === ===) + + \ \ \ \ \ \ \ \ \ \ (item (text "Choices:") + + \ \ \ \ \ \ \ \ \ \ \ \ (form-choices "fieldname4"\ + + \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ '("one" "two" + "three")\ + + \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ '("one" "two")))) + + \ \ \ \ \ \ \ \ (bottom-buttons + + \ \ \ \ \ \ \ \ \ \ ("Cancel" (cmd "cancel")) \\ + + \ \ \ \ \ \ \ \ \ \ ("Ok" + + \ \ \ \ \ \ \ \ \ \ \ (display* (form-fields) " -\ " + (form-values) "\\n") + + \ \ \ \ \ \ \ \ \ \ \ (cmd "ok"))))))) + <|folded-io> + ((guile-user) (guile-user)) + + + <\input|Scheme] > + (dialogue-window form3 (lambda (x) (display* x "\\n")) "Test of form3") + + + + A complete list of the widgets you can embed in a form is in the table + inside . + + \; + + team.> + + + \ No newline at end of file diff --git a/devel/scheme/gui/scheme-gui-reference.en.tm b/devel/scheme/gui/scheme-gui-reference.en.tm new file mode 100644 index 0000000..9c00e36 --- /dev/null +++ b/devel/scheme/gui/scheme-gui-reference.en.tm @@ -0,0 +1,21 @@ + + + + +<\body> + + + This should be a comprehensive list of all the widgets available to the + user. + + \; + + team.> + + + \ No newline at end of file diff --git a/devel/scheme/gui/scheme-gui.en.tm b/devel/scheme/gui/scheme-gui.en.tm index 4c7de4c..55f7ac6 100644 --- a/devel/scheme/gui/scheme-gui.en.tm +++ b/devel/scheme/gui/scheme-gui.en.tm @@ -1,224 +1,49 @@ - + <\body> - + Most of the user interface to is dynamically created from within - the interpreted scheme code. Imagine you want to implement some feature - which requires interaction with the user. One possible approach is to use - the facility , which will either popoup a dialog or ask in - the footer bar, based in metadata you provide inside your 'd - function. See for more on this topic. However, - automatically generated stuff is not always the best approach, so you might - want to explicitly design your interface placing it inside a complicated - dialog. + the interpreted scheme code. New menus and buttons can be added, or the + existing ones reused and rearranged, even the main editor can be embedded + anywhere. - + Imagine you want to implement some feature which requires interaction with + the user. One possible approach is to use the facility , + which according to the user's preferences will either popoup a dialog or + ask in the footer bar, based in metadata you provide inside your + 'd function. See for more on this + topic. However, automatically generated stuff is not always the best + approach, so you might want to explicitly design your interface placing it + inside a complicated dialog. The following sections should help with that. - In you create visual interfaces using . This word - means either the basic building blocks you have at your disposal, like - buttons, popup lists, etc. or the collections of those into dialogs, menus - or whatever. The latter can be aggregated to build more complicated ones as - well.<\footnote> - If you miss some particular ``building block'' from your OS, you might - see whether it's feasible as an aggregation of simpler ones or try and - play with the UI interface code in C++ (but you'll have to add it for - every supported platform!). - + <\traverse> + - Let's see how you create a dialog. First you'll want to use - to define a new widget. The call to this function uses its particular - syntax, with many keywords for the creation of widgets. You can see the - whole list in the table inside - . - Here is one little example taken from : + - <\session|scheme|default> - <\unfolded-io|Scheme] > - (tm-widget (widget1) - - \ \ (centered - - \ \ \ \ (aligned - - \ \ \ \ \ \ (item (text "First:") - - \ \ \ \ \ \ \ \ (toggle (display* "First " answer "\\n") #f)) - - \ \ \ \ \ \ (item (text "Second:") - - \ \ \ \ \ \ \ \ (toggle (display* "Second " answer "\\n") #f))))) - <|unfolded-io> - \; - - - - In order to display this you create a and give it a title. - - <\session|scheme|default> - <\input|Scheme] > - (top-window widget1 "Two toggle widgets") - - - - You'll notice that the created window is too small and the title is not - wholly displayed. You can force it to be of a certain size using - : - - <\session|scheme|default> - <\unfolded-io|Scheme] > - (tm-widget (widget1) - - \ \ (centered - - \ \ \ \ (resize "500px" "200px" - - \ \ \ \ \ \ (aligned - - \ \ \ \ \ \ \ \ (item (text "First:") - - \ \ \ \ \ \ \ \ \ \ (toggle (display* "First " answer "\\n") #f)) - - \ \ \ \ \ \ \ \ (item (text "Second:") - - \ \ \ \ \ \ \ \ \ \ (toggle (display* "Second " answer "\\n") #f)))))) - <|unfolded-io> - ((guile-user) (kernel gui menu-test)) - - - <\input|Scheme] > - (top-window widget1 "A bigger window") - - - <\input|Scheme] > - \; - - - - - - If you want to add the usual buttons you use like in - the following example. Notice the widget now accepts one parameter - which will be called when the user clicks the ``Ok'' button. This - will also automatically close the window.\ - - <\session|scheme|default> - <\unfolded-io|Scheme] > - (tm-widget (form2 cmd) - - \ \ (centered - - \ \ \ \ (aligned - - \ \ \ \ \ \ (item (text "First:") - - \ \ \ \ \ \ \ \ (toggle (display* "First " answer "\\n") #f)) - - \ \ \ \ \ \ (item (text "Second:") - - \ \ \ \ \ \ \ \ (toggle (display* "Second " answer "\\n") #f)))) - - \ \ (bottom-buttons \\ ("Ok" (cmd "Ok")))) - <|unfolded-io> - \; - - - - Since the widget now needs an argument, we must use another function to - display it, namely , like this: - - <\session|scheme|default> - <\input|Scheme] > - (dialogue-window form2 (lambda (arg) (display* arg "\\n")) "Two - toggles") - - - - As you can see, this approach has a shortcoming: there's no way to access - all the values of the different widgets in your dialog at the same time. Of - course you can use the function passed to your widget to perform - some computations, but in case you need to retrieve or store complicated - data, what you need is a form (See ). - - - - As explained in the available widgets can be - used to create menu items and dialog windows, but you may want to create - more complex dialogs to perform more complicated tasks. Forms provide one - mechanism to do this. They allow you to define multiple named fields of - several types, whose values are stored in a . - You can retrieve and return the values of this hash when the user clicks a - button using the functions and . - - In the following example you can see that the syntax is pretty much the - same as for regular widgets, but you must prefix your widgets with - : - - <\session|scheme|default> - <\folded-io|Scheme] > - (tm-widget (form3 cmd) - - \ \ (resize "500px" "500px" - - \ \ \ \ (padded - - \ \ \ \ \ \ (form "Test" - - \ \ \ \ \ \ \ \ (aligned - - \ \ \ \ \ \ \ \ \ \ (item (text "Input:") - - \ \ \ \ \ \ \ \ \ \ \ \ (form-input "fieldname1" "string" '("one") - "1w")) - - \ \ \ \ \ \ \ \ \ \ (item === ===) - - \ \ \ \ \ \ \ \ \ \ (item (text "Enum:") - - \ \ \ \ \ \ \ \ \ \ \ \ (form-enum "fieldname2" '("one" "two" "three") - "two" "1w")) - - \ \ \ \ \ \ \ \ \ \ (item === ===) - - \ \ \ \ \ \ \ \ \ \ (item (text "Choice:") - - \ \ \ \ \ \ \ \ \ \ \ \ (form-choice "fieldname3" '("one" "two" - "three") "one")) - - \ \ \ \ \ \ \ \ \ \ (item === ===) - - \ \ \ \ \ \ \ \ \ \ (item (text "Choices:") - - \ \ \ \ \ \ \ \ \ \ \ \ (form-choices "fieldname4"\ - - \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ '("one" "two" - "three")\ - - \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ '("one" "two")))) - - \ \ \ \ \ \ \ \ (bottom-buttons - - \ \ \ \ \ \ \ \ \ \ ("Cancel" (cmd "cancel")) \\ - - \ \ \ \ \ \ \ \ \ \ ("Ok" - - \ \ \ \ \ \ \ \ \ \ \ (display* (form-fields) " -\ " - (form-values) "\\n") - - \ \ \ \ \ \ \ \ \ \ \ (cmd "ok"))))))) - <|folded-io> - ((guile-user) (guile-user)) - - - <\input|Scheme] > - (dialogue-window form3 (lambda (x) (display* x "\\n")) "Test of form3") - - - - A complete list of the widgets you can embed in a form is in the table - inside . + + \; - \ No newline at end of file + + team.> + + + + +<\initial> + <\collection> + + + \ No newline at end of file