rwdlanguage 0.01

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (187) hide show
  1. data/Readme.txt +475 -0
  2. data/bin/rwdlanguage +19 -0
  3. data/code/01rwdcore/01rwdcore.rb +29 -0
  4. data/code/01rwdcore/02helptexthashbegin.rb +16 -0
  5. data/code/01rwdcore/03helptexthash.rb +21 -0
  6. data/code/01rwdcore/jumplinkcommand.rb +36 -0
  7. data/code/01rwdcore/openhelpwindow.rb +38 -0
  8. data/code/01rwdcore/returntomain.rb +10 -0
  9. data/code/01rwdcore/rundocuments.rb +10 -0
  10. data/code/01rwdcore/runeditconfiguration.rb +10 -0
  11. data/code/01rwdcore/runhelpabout.rb +15 -0
  12. data/code/01rwdcore/runopentinkerdocument.rb +7 -0
  13. data/code/01rwdcore/runtab.rb +15 -0
  14. data/code/01rwdcore/rwdtinkerversion.rb +22 -0
  15. data/code/01rwdcore/rwdwindowreturn.rb +9 -0
  16. data/code/01rwdcore/selectiontab.rb +11 -0
  17. data/code/01rwdcore/setuphelpaboutoptions.rb +15 -0
  18. data/code/01rwdcore/setuptinkerdocuments.rb +7 -0
  19. data/code/01rwdcore/test_cases.rb +158 -0
  20. data/code/01rwdcore/test_harness.rb +20 -0
  21. data/code/01rwdcore/uploadreturns.rb +65 -0
  22. data/code/dd0viewphoto/dd0viewphoto.rb +5 -0
  23. data/code/superant.com.language/0uninstallapplet.rb +22 -0
  24. data/code/superant.com.language/googlelang.rb +25 -0
  25. data/code/superant.com.language/helptexthashload.rb +22 -0
  26. data/code/superant.com.language/loadconfigurationrecord.rb +22 -0
  27. data/code/superant.com.language/loadconfigurationvariables.rb +14 -0
  28. data/code/superant.com.language/openhelpwindow.rb +24 -0
  29. data/code/superant.com.language/rubySteak.rb +40 -0
  30. data/code/superant.com.language/runappletwindow.rb +12 -0
  31. data/code/superant.com.language/runrwdshellwindow.rb +12 -0
  32. data/code/superant.com.language/runrwdwordsbackwindow.rb +10 -0
  33. data/code/superant.com.language/rwdtinkerversion.rb +10 -0
  34. data/code/superant.com.language/saveconfigurationrecord.rb +20 -0
  35. data/code/superant.com.language/test_cases.rb +20 -0
  36. data/code/superant.com.rwdtinkerbackwindow/changelocale.rb +84 -0
  37. data/code/superant.com.rwdtinkerbackwindow/diagnostictab.rb +19 -0
  38. data/code/superant.com.rwdtinkerbackwindow/initiateapplets.rb +169 -0
  39. data/code/superant.com.rwdtinkerbackwindow/installgemapplet.rb +38 -0
  40. data/code/superant.com.rwdtinkerbackwindow/installremotegem.rb +20 -0
  41. data/code/superant.com.rwdtinkerbackwindow/listgemdirs.rb +12 -0
  42. data/code/superant.com.rwdtinkerbackwindow/listgemzips.rb +55 -0
  43. data/code/superant.com.rwdtinkerbackwindow/listinstalledfiles.rb +14 -0
  44. data/code/superant.com.rwdtinkerbackwindow/listzips.rb +37 -0
  45. data/code/superant.com.rwdtinkerbackwindow/loadconfigurationrecord.rb +24 -0
  46. data/code/superant.com.rwdtinkerbackwindow/loadconfigurationvariables.rb +14 -0
  47. data/code/superant.com.rwdtinkerbackwindow/network.rb +87 -0
  48. data/code/superant.com.rwdtinkerbackwindow/openappletname.rb +19 -0
  49. data/code/superant.com.rwdtinkerbackwindow/openhelpwindowtinkerwin2.rb +40 -0
  50. data/code/superant.com.rwdtinkerbackwindow/remotegemlist.rb +24 -0
  51. data/code/superant.com.rwdtinkerbackwindow/removeapplet.rb +46 -0
  52. data/code/superant.com.rwdtinkerbackwindow/removeappletvariables.rb +52 -0
  53. data/code/superant.com.rwdtinkerbackwindow/runremoteinstall.rb +11 -0
  54. data/code/superant.com.rwdtinkerbackwindow/runrwdtinkerbackwindow.rb +15 -0
  55. data/code/superant.com.rwdtinkerbackwindow/rwdtinkerwin2version.rb +13 -0
  56. data/code/superant.com.rwdtinkerbackwindow/saveconfigurationrecord.rb +19 -0
  57. data/code/superant.com.rwdtinkerbackwindow/showlocaleoptions.rb +9 -0
  58. data/code/superant.com.rwdtinkerbackwindow/viewappletcontents.rb +23 -0
  59. data/code/superant.com.rwdtinkerbackwindow/viewgemappletcontents.rb +24 -0
  60. data/code/superant.com.rwdtinkerbackwindow/viewlogfile.rb +16 -0
  61. data/code/superant.com.thesaurus/clearhttpview3.rb +9 -0
  62. data/code/superant.com.thesaurus/listwordlookup.rb +37 -0
  63. data/code/superant.com.thesaurus/runappletwindow.rb +12 -0
  64. data/code/superant.com.words/dictlookup.rb +20 -0
  65. data/code/superant.com.words/runrwdwordsbackwindow.rb +10 -0
  66. data/code/superant.com.words/rwdtinkerversion.rb +10 -0
  67. data/code/zz0applicationend/zz0end.rb +5 -0
  68. data/configuration/rwdtinker.dist +15 -0
  69. data/configuration/rwdwlanguage.dist +21 -0
  70. data/configuration/tinkerwin2variables.dist +23 -0
  71. data/gui/00coreguibegin/applicationguitop.rwd +9 -0
  72. data/gui/frontwindow0/cc0openphoto.rwd +22 -0
  73. data/gui/frontwindowselections/00selectiontabbegin.rwd +11 -0
  74. data/gui/frontwindowselections/jumplinkcommands.rwd +15 -0
  75. data/gui/frontwindowselections/wwselectionend.rwd +3 -0
  76. data/gui/frontwindowtdocuments/00documentbegin.rwd +6 -0
  77. data/gui/frontwindowtdocuments/tinkerdocuments.rwd +14 -0
  78. data/gui/frontwindowtdocuments/zzdocumentend.rwd +8 -0
  79. data/gui/helpaboutbegin/zzzrwdlasttab.rwd +6 -0
  80. data/gui/helpaboutbegin/zzzzhelpscreenstart.rwd +3 -0
  81. data/gui/helpaboutbegin/zzzzzzhelpabouttab.rwd +15 -0
  82. data/gui/helpaboutzend/helpscreenend.rwd +3 -0
  83. data/gui/helpaboutzend/zhelpscreenstart2.rwd +3 -0
  84. data/gui/helpaboutzend/zzzzhelpabout2.rwd +15 -0
  85. data/gui/helpaboutzend/zzzzhelpscreen2end.rwd +3 -0
  86. data/gui/tinkerbackwindows/superant.com.language/1appname.rwd +4 -0
  87. data/gui/tinkerbackwindows/superant.com.language/22google.rwd +38 -0
  88. data/gui/tinkerbackwindows/superant.com.language/44germany.rwd +19 -0
  89. data/gui/tinkerbackwindows/superant.com.language/67viewconfiguration.rwd +27 -0
  90. data/gui/tinkerbackwindows/superant.com.language/77jumplinkcommands.rwd +17 -0
  91. data/gui/tinkerbackwindows/superant.com.language/z9end.rwd +6 -0
  92. data/gui/tinkerbackwindows/superant.com.tinkerbackwindow/1appname.rwd +5 -0
  93. data/gui/tinkerbackwindows/superant.com.tinkerbackwindow/40rwdlistzips.rwd +41 -0
  94. data/gui/tinkerbackwindows/superant.com.tinkerbackwindow/45installremotezip.rwd +44 -0
  95. data/gui/tinkerbackwindows/superant.com.tinkerbackwindow/50rwdlistapplets.rwd +44 -0
  96. data/gui/tinkerbackwindows/superant.com.tinkerbackwindow/60editconfiguration.rwd +30 -0
  97. data/gui/tinkerbackwindows/superant.com.tinkerbackwindow/70rwddiagnostics.rwd +29 -0
  98. data/gui/tinkerbackwindows/superant.com.tinkerbackwindow/75rwdlogfile.rwd +20 -0
  99. data/gui/tinkerbackwindows/superant.com.tinkerbackwindow/80localechanger.rwd +17 -0
  100. data/gui/tinkerbackwindows/superant.com.tinkerbackwindow/81jumplinkcommands.rwd +17 -0
  101. data/gui/tinkerbackwindows/superant.com.tinkerbackwindow/9backend.rwd +6 -0
  102. data/gui/tinkerbackwindows/superant.com.tinkerhelpwindow/1appname.rwd +31 -0
  103. data/gui/tinkerbackwindows/superant.com.tinkerhelpwindow/9end.rwd +4 -0
  104. data/gui/tinkerbackwindows/superant.com.versionwindow/1appname.rwd +19 -0
  105. data/gui/tinkerbackwindows/superant.com.versionwindow/helpaboutwindow.rwd +17 -0
  106. data/gui/tinkerbackwindows/superant.com.words/1appname.rwd +4 -0
  107. data/gui/tinkerbackwindows/superant.com.words/1dictionary.rwd +19 -0
  108. data/gui/tinkerbackwindows/superant.com.words/4thesaurus.rwd +36 -0
  109. data/gui/tinkerbackwindows/superant.com.words/77jumplinkcommands.rwd +17 -0
  110. data/gui/tinkerbackwindows/superant.com.words/z9end.rwd +6 -0
  111. data/gui/zzcoreguiend/yy9rwdend.rwd +4 -0
  112. data/init.rb +179 -0
  113. data/installed/rwdwlanguage.inf +24 -0
  114. data/installed/temp.rb +1 -0
  115. data/lang/en/rwdcore/en.po +197 -0
  116. data/lang/en/rwdlanguage/en.po +32 -0
  117. data/lang/es/rwdcore/es.po +184 -0
  118. data/lang/es/rwdlanguage/en.po +32 -0
  119. data/lang/fr/rwdcore/fr.po +169 -0
  120. data/lang/fr/rwdlanguage/en.po +32 -0
  121. data/lang/hi/rwdcore/hi.po +173 -0
  122. data/lang/hi/rwdlanguage/en.po +32 -0
  123. data/lang/ja/rwdcore/ja.po +171 -0
  124. data/lang/ja/rwdlanguage/en.po +32 -0
  125. data/lang/nl/rwdcore/nl.po +169 -0
  126. data/lang/nl/rwdlanguage/en.po +32 -0
  127. data/lib/dict.rb +438 -0
  128. data/lib/g_translate.rb +43 -0
  129. data/lib/g_translate/client.rb +84 -0
  130. data/lib/g_translate/translator.rb +57 -0
  131. data/lib/ger-eng.txt +111283 -0
  132. data/lib/oothesaurus.rb +76 -0
  133. data/lib/rconftool.rb +387 -0
  134. data/lib/rwd/browser.rb +123 -0
  135. data/lib/rwd/ftools.rb +174 -0
  136. data/lib/rwd/mime.rb +328 -0
  137. data/lib/rwd/net.rb +877 -0
  138. data/lib/rwd/ruby.rb +889 -0
  139. data/lib/rwd/rwd.rb +1425 -0
  140. data/lib/rwd/sgml.rb +236 -0
  141. data/lib/rwd/thread.rb +63 -0
  142. data/lib/rwd/tree.rb +371 -0
  143. data/lib/rwd/xml.rb +101 -0
  144. data/lib/rwdthemes/default.rwd +317 -0
  145. data/lib/rwdthemes/pda.rwd +72 -0
  146. data/lib/rwdthemes/windowslike.rwd +171 -0
  147. data/lib/rwdtinker/rwdcodedir.rb +56 -0
  148. data/lib/rwdtinker/rwdguidir.rb +57 -0
  149. data/lib/rwdtinker/rwdlangdir.rb +60 -0
  150. data/lib/rwdtinker/rwdtinkertools.rb +25 -0
  151. data/lib/zip/ioextras.rb +155 -0
  152. data/lib/zip/stdrubyext.rb +111 -0
  153. data/lib/zip/tempfile_bugfixed.rb +195 -0
  154. data/lib/zip/zip.rb +1847 -0
  155. data/lib/zip/zipfilesystem.rb +609 -0
  156. data/lib/zip/ziprequire.rb +90 -0
  157. data/rwd_files/HowTo_Language.txt +179 -0
  158. data/rwd_files/HowTo_Tinker.txt +515 -0
  159. data/rwd_files/HowTo_TinkerWin2.txt +202 -0
  160. data/rwd_files/Readme.txt +57 -0
  161. data/rwd_files/RubyWebDialogs.html +6 -0
  162. data/rwd_files/Tinkerhelptexthash.txt +84 -0
  163. data/rwd_files/favicon.ico +0 -0
  164. data/rwd_files/log/rwdtinker.log +726 -0
  165. data/rwd_files/rdoc-style.css +175 -0
  166. data/rwd_files/rwdapplications.html +76 -0
  167. data/rwd_files/rwdlanguagehelpfiles.txt +34 -0
  168. data/rwd_files/tinker.png +0 -0
  169. data/rwdconfig.dist +24 -0
  170. data/rwdlanguage.rb +1 -0
  171. data/tests/RubyGauge.rb +179 -0
  172. data/tests/checkdepends.sh +4 -0
  173. data/tests/cleancnf.sh +6 -0
  174. data/tests/makedist-rwdwlanguage.rb +56 -0
  175. data/tests/makedist.rb +66 -0
  176. data/tests/rdep.rb +354 -0
  177. data/tests/totranslate.lang +93 -0
  178. data/zips/rwdwcalc-0.63.zip +0 -0
  179. data/zips/rwdwfoldeditor-0.08.zip +0 -0
  180. data/zips/rwdwhypernote-0.16.zip +0 -0
  181. data/zips/rwdwlanguage-0.01.zip +0 -0
  182. data/zips/rwdwmovies-0.98.zip +0 -0
  183. data/zips/rwdwruby-1.08.zip +0 -0
  184. data/zips/temp.rb +1 -0
  185. data/zips/tinkerbellw-0.04.zip +0 -0
  186. data/zips/wrubyslippers-1.08.zip +0 -0
  187. metadata +246 -0
data/lib/rwd/rwd.rb ADDED
@@ -0,0 +1,1425 @@
1
+ require "lib/rwd/ruby"
2
+ require "lib/rwd/xml"
3
+ require "lib/rwd/net"
4
+ require "lib/rwd/browser"
5
+ require "lib/rwd/thread"
6
+ require "md5"
7
+ require "rbconfig"
8
+
9
+
10
+
11
+ begin
12
+ require "win32ole"
13
+ require "win32/registry"
14
+ rescue LoadError
15
+ $".push "win32ole.so"
16
+ $".push "win32/registry.rb"
17
+ end
18
+
19
+ $rwd_exit = ARGV.include?("--rwd-exit") # Hack ???
20
+ $rwd_exit = true if defined?(REQUIRE2LIB)
21
+ $rwd_debug = ($rwd_debug or $DEBUG or false)
22
+ $rwd_border = ($rwd_border or 0)
23
+ $rwd_dir = Dir.pwd
24
+ $rwd_files = File.expand_path("rwd_files", Dir.pwd)
25
+ $rwd_html = {}
26
+
27
+ ARGV.delete_if do |arg|
28
+ arg =~ /^--rwd-/
29
+ end
30
+
31
+ RWDEmptyline = "..."
32
+
33
+ #module RWD
34
+
35
+ rcfile = nil
36
+ s = ENV["HOME"] ; s = File.expand_path(".rwdrc", s) unless s.nil? ; rcfile = s if (not s.nil? and rcfile.nil? and File.file?(s))
37
+ s = ENV["USERPROFILE"] ; s = File.expand_path("rwd.cfg", s) unless s.nil? ; rcfile = s if (not s.nil? and rcfile.nil? and File.file?(s))
38
+ s = ENV["windir"] ; s = File.expand_path("rwd.cfg", s) unless s.nil? ; rcfile = s if (not s.nil? and rcfile.nil? and File.file?(s))
39
+
40
+ AL = "align='left'"
41
+ AC = "align='center'"
42
+ AR = "align='right'"
43
+ VA = "valign='middle'"
44
+
45
+ Format = "\n<!-- %-10s %-10s -->\t"
46
+
47
+ unless rcfile.nil?
48
+ puts "Reading #{rcfile} ..."
49
+
50
+ Hash.file(rcfile).each do |k, v|
51
+ ENV[k] = v unless ENV.include?(k)
52
+ end
53
+ end
54
+
55
+ if ENV["RWDTHEME"]
56
+ if ENV["RWDTHEME"] = "PDA"
57
+ load 'lib/rwdthemes/default.rwd'
58
+ end
59
+ if ENV["RWDTHEME"] = "DEFAULT"
60
+ $rwdtinkerlog.info "rwd: loading theme DEFAULT"
61
+
62
+ load 'lib/rwdthemes/default.rwd'
63
+ end
64
+ if ENV["RWDTHEME"] = "WINDOWSLOOKALIKE"
65
+ load 'lib/rwdthemes/windowslike.rwd'
66
+ end
67
+ else
68
+ load 'lib/rwdthemes/default.rwd'
69
+ end
70
+
71
+ ENV["RWDBROWSER"] = (ENV["RWDBROWSER"] or defaultbrowser) or puts "No browser found."
72
+ ENV["RWDPORTS"] = (ENV["RWDPORTS"] or "7701-7709")
73
+ ENV["RWDTHEME"] = (ENV["RWDTHEME"] or "DEFAULT")
74
+
75
+ #trap("INT") {puts "Terminating..." ; exit}
76
+
77
+ $SAFE = 0
78
+
79
+ class IE
80
+ def initialize(url)
81
+ @ie = WIN32OLE.new("InternetExplorer.Application")
82
+ @ev = WIN32OLE_EVENT.new(@ie, "DWebBrowserEvents2")
83
+
84
+ @ie.navigate(url)
85
+
86
+ @ie.menubar = false
87
+ @ie.toolbar = false
88
+ @ie.addressbar = false
89
+ @ie.statusbar = false
90
+
91
+ @ie.visible = true
92
+
93
+ at_exit do
94
+ @ie.visible = false
95
+ end
96
+
97
+ @ev.on_event("OnQuit") do
98
+ Thread.main.exit
99
+ end
100
+
101
+ Thread.new do
102
+ loop do
103
+ WIN32OLE_EVENT.message_loop
104
+ end
105
+ end
106
+ end
107
+ end
108
+
109
+ class Array
110
+ def rwd_options(emptyline=nil)
111
+ if emptyline.nil?
112
+ a = self
113
+ else
114
+ a = [emptyline].concat(self)
115
+ end
116
+
117
+ a.numsort.collect{|s| "<option>#{s.to_s.to_html}</option>" }.join("\n")
118
+ end
119
+
120
+ def rwd_method(method)
121
+ res = ""
122
+
123
+ self.each do |s|
124
+ s = s.join("/") if s.kind_of?(Array)
125
+ s2 = s.dup
126
+ s2[0..0] = s2[0..0].upcase
127
+ res = res + "<p align='left'><a action='#{method}/#{s.to_html}'>#{s2.to_html}</a></p>"
128
+ end
129
+
130
+ return res
131
+ end
132
+
133
+ def rwd_row(key=nil, value=nil, bold=false)
134
+ res = ""
135
+
136
+ res = res + "<row valign='top'>"
137
+ res = res + "<radio name='#{key.to_html}' value='#{value.to_html}'/>" unless key.nil?
138
+ res = res + self.collect{|s| "<p align='#{(s.kind_of?(Numeric) or s =~ /^\d+\.\d+$/) ? "right" : "left"}'>#{"<b>" if bold}#{s.to_s.to_html}#{"</b>" if bold}</p>"}.join("")
139
+ res = res + "</row>"
140
+
141
+ return res
142
+ end
143
+
144
+ def rwd_table(headers=nil, highlightrows=[])
145
+ res = ""
146
+
147
+ highlightrows = [highlightrows].flatten
148
+
149
+ n = -1
150
+
151
+ res = res + "<table>"
152
+ res = res + headers.rwd_row(nil, nil, true) unless headers.nil?
153
+ res = res + self.collect{|a| a.rwd_row(nil, nil, highlightrows.include?(n+=1))}.join("")
154
+ res = res + "</table>"
155
+
156
+ return res
157
+ end
158
+
159
+ def rwd_headers(emptyfield=false)
160
+ res = ""
161
+
162
+ res = res + "<row>"
163
+ res = res + "<p/>" if emptyfield
164
+ res = res + self.collect{|s| "<p align='left'><b>#{s.to_html}</b></p>" }.join("")
165
+ res = res + "</row>"
166
+
167
+ return res
168
+ end
169
+
170
+ def rwd_form(prefix, values=[], twoparts=0, options={})
171
+ res = []
172
+
173
+ res << "<table>"
174
+ self.each_index do |n|
175
+ name = "#{prefix.to_html}#{self[n].downcase.to_html}"
176
+
177
+ res << "<row>"
178
+ res << "<p align='right'>"
179
+ res << "#{self[n].to_html}:"
180
+ res << "</p>"
181
+
182
+ if options.keys.include?(self[n])
183
+ res << "<select name='#{name}'>"
184
+ res << options[self[n]].rwd_options(RWDEmptyline)
185
+ res << "</select>"
186
+ else
187
+ s = ""
188
+
189
+ s << "<text name='#{name}'"
190
+ s << " value='#{values[n].to_s.to_html}'" if n < values.length
191
+ s << "/>"
192
+
193
+ res << s
194
+ end
195
+
196
+ res << "</row>"
197
+
198
+ if twoparts > 0 and n == twoparts-1
199
+ res << "<row><empty/></row>"
200
+ end
201
+ end
202
+ res << "</table>"
203
+
204
+ return res.join("\n")
205
+ end
206
+ end
207
+
208
+ class Hash
209
+ def rwd_table(field=nil, joinwith=nil, headers=nil)
210
+ res = []
211
+
212
+ res << "<table>"
213
+ res << headers.rwd_headers((not field.nil?)) if not headers.nil?
214
+ self.keys.numsort.each do |key|
215
+ key2 = key
216
+ value2 = self[key]
217
+
218
+ key2 = key2.join(joinwith) if key2.kind_of?(Array)
219
+ value2 = [value2] if value2.kind_of?(String)
220
+
221
+ res << value2.rwd_row(field, key2)
222
+ end
223
+ res << "</table>"
224
+
225
+ res.join("\n")
226
+ end
227
+ end
228
+
229
+ class EVTable
230
+ def rwd_table(field=nil, joinwith=@sep)
231
+ super(field, joinwith, @headers)
232
+ end
233
+
234
+ def rwd_form(prefix="", key=nil, twoparts=false)
235
+ values = self[key] if not key.nil?
236
+ values = [] if values.nil?
237
+ options = {}
238
+
239
+ if File.file?(oldlocation("constraints.tsv"))
240
+ table = File.basename(@file).gsub(/\.tsv$/, "")
241
+
242
+ TSVFile.new(oldlocation("constraints.tsv")).subset(["Table", "Constraint"], [table, "key"], ["Column", "Value"]).values.each do |column, table2|
243
+ options[column] = TSVFile.new(oldlocation("#{table2}.tsv")).keys.collect{|a| a.join("\t")}
244
+ end
245
+ end
246
+
247
+ @headers.rwd_form(prefix, values, twoparts ? @key : 0, options)
248
+ end
249
+
250
+ def rwd_metadata
251
+ res = []
252
+
253
+ res << "<table>"
254
+ res << "<row>"
255
+ res << " <empty/>"
256
+ res << " <text name='header_new' value=''/>"
257
+ res << "</row>"
258
+ @headers.each_index do |n|
259
+ res << "<row>"
260
+ res << " <text name='header_#{n}_old' value='#{@headers[n]}'/>"
261
+ res << " <text name='header_#{n}_new' value=''/>"
262
+ res << "</row>"
263
+ end
264
+ res << "</table>"
265
+
266
+ return res.join("\n")
267
+ end
268
+ end
269
+
270
+ class OpenTag
271
+ def prechildren(res, before, after, varshtml, varsstring, switches, help, oneormorefields, firstaction, tabs, tab, pda=false)
272
+ bef = before[-1]
273
+ res << Format % ["Before", @subtype] if ($rwd_debug and not bef.nil?)
274
+ res << bef if not bef.nil?
275
+
276
+ res << Format % ["Pre", @subtype] if $rwd_debug
277
+
278
+ align = AC
279
+ align = "align='#{@args["align"]}'" if @args.include?("align")
280
+
281
+ valign = VA
282
+ valign = "valign='#{@args["valign"]}'" if @args.include?("valign")
283
+
284
+ value1 = ""
285
+ value1 = varshtml[@args["name"]] if varshtml.include?(@args["name"])
286
+ value1 = @args["value"] if @args.include?("value")
287
+
288
+ value2 = ""
289
+ value2 = varsstring[@args["name"]] if varsstring.include?(@args["name"])
290
+ value2 = @args["value"] if @args.include?("value")
291
+
292
+ cellspacing = 3
293
+ cellspacing = 0 if pda
294
+
295
+ case @subtype
296
+ when "application"
297
+ when "window", "helpwindow"
298
+ args = @args.deep_dup
299
+
300
+ args["nohelpbutton"] = (not help)
301
+
302
+ template = $rwd_html_1
303
+ # template = $rwd_html_PDA_1 if pda
304
+
305
+ res << (template(template, args))
306
+ when "p" then res << "<p #{align}>"
307
+ when "pre" then res << "<pre #{align}>"
308
+ when "big" then res << "<p #{align}><big>"
309
+ when "small" then res << "<p #{align}><small>"
310
+ when "list" then res << "<ul #{align}>"
311
+ when "item" then res << "<li #{align}>"
312
+ when "empty" then res << "<p><br>"
313
+ when "image"
314
+ width = "width='#{@args["width"]}" if @args.include?("width")
315
+ height = "height='#{@args["height"]}'" if @args.include?("height")
316
+
317
+ res << "<img src='#{@args["src"]}' alt='#{@args["alt"]}' #{width} #{height}>"
318
+ when "progressbar"
319
+ width = 200
320
+
321
+ res << "<table>"
322
+ res << " <tr>"
323
+ res << " <td colspan='2'><img src='rwd_pixel.gif' height='1' width='#{width+5}'></td>"
324
+ res << " </tr>"
325
+ res << " <tr>"
326
+ res << " <td bgcolor='#DDDDDD'><img src='rwd_pixel.gif' height='10' width='#{(width*@args["value"].to_f).to_i}'></td>"
327
+ res << " <td bgcolor='#EEEEEE'><img src='rwd_pixel.gif' height='10' width='#{(width*(1.0-@args["value"].to_f)).to_i}'></td>"
328
+ res << " </tr>"
329
+ res << "</table>"
330
+ when "br" then res << "<br>"
331
+ when "hr" then res << "<hr>"
332
+ when "b" then res << "<b>"
333
+ when "i" then res << "<i>"
334
+ when "a"
335
+ if @args.include?("href")
336
+ res << "<a href='#{@args["href"]}' target='#{@args["target"] or "_blank"}'>"
337
+ else
338
+ res << "<a href='javascript:document.bodyform.rwd_action.value=\"#{@args["action"]}\";document.bodyform.submit();'>"
339
+ end
340
+ when "vertical" then res << "<table #{AC} border='#{$rwd_border}' cellspacing='#{cellspacing}' cellpadding='0'>"
341
+ when "horizontal" then res << "<table #{AC} border='#{$rwd_border}' cellspacing='#{cellspacing}' cellpadding='0'><tr #{align} #{valign}>"
342
+ when "table" then res << "<table #{AC} border='#{$rwd_border}' cellspacing='#{cellspacing}' cellpadding='0'>"
343
+ when "row" then res << "<tr #{align} #{valign}>"
344
+ when "hidden" then res << "<p #{align}><input name='#{@args["name"]}' value='#{value1}' type='hidden'>"
345
+ when "text"
346
+ maxlength = ""
347
+ maxlength = "maxlength='%s'" % @args["maxlength"] if @args.include?("maxlength")
348
+ size = ""
349
+ size = "size='%s'" % @args["size"] if @args.include?("size")
350
+ size = "size='%s'" % 10 if pda
351
+ res << "<p #{align}><input name='#{@args["name"]}' value='#{value1}' type='text' #{maxlength} #{size}>"
352
+ oneormorefields << "true"
353
+ when "textarea"
354
+ res << "<p #{align}><textarea name='#{@args["name"]}' rows='25' cols='80'>#{value2.crlf}</textarea>"
355
+ oneormorefields << "true"
356
+ when "password"
357
+ maxlength = ""
358
+ maxlength = "maxlength='%s'" % @args["maxlength"] if @args.include?("maxlength")
359
+ size = ""
360
+ size = "size='%s'" % 10 if pda
361
+ res << "<p #{align}><input name='#{@args["name"]}' value='#{value1}' type='password' #{maxlength} #{size}>"
362
+ oneormorefields << "true"
363
+ when "checkbox"
364
+ if varshtml[@args["name"]] == "on"
365
+ switches[@args["name"]] = true
366
+ res << "<p #{align}><input name='#{@args["name"]}' checked='on' type='checkbox'>"
367
+ else
368
+ switches[@args["name"]] = false
369
+ res << "<p #{align}><input name='#{@args["name"]}' type='checkbox'>"
370
+ end
371
+ oneormorefields << "true"
372
+ when "radio"
373
+ if varshtml[@args["name"]] == value1 # ??? 1 or 2?
374
+ res << "<p #{align}><input name='#{@args["name"]}' checked='on' value='#{value1}' type='radio'>"
375
+ else
376
+ res << "<p #{align}><input name='#{@args["name"]}' value='#{value1}' type='radio'>"
377
+ end
378
+ oneormorefields << "true"
379
+ when "select"
380
+ res << "<select #{align} name='#{@args["name"]}' width='#{@args["width"]} size='#{@args["size"]}'>" # ??? Misschien nog iets met 'multiple'?
381
+ name = @args["name"]
382
+ $select = varshtml[name]
383
+ oneormorefields << "true"
384
+ when "option"
385
+ if $select == @children[0].text
386
+ res << "<option selected='true'>"
387
+ else
388
+ res << "<option>"
389
+ end
390
+ when "button"
391
+ res << "<input type='submit' value='#{@args["caption"]}' onclick='document.bodyform.rwd_action.value=\"#{@args["action"]}\";'>"
392
+ firstaction << @args["action"] if (firstaction.empty? and @args.include?("action"))
393
+ oneormorefields << "true"
394
+ when "back"
395
+ res << "<input type='submit' value='Back' onclick='document.bodyform.rwd_action.value=\"rwd_back\";'>"
396
+ firstaction << "rwd_back" if firstaction.empty?
397
+ oneormorefields << "true"
398
+ when "cancel"
399
+ res << "<input type='submit' value='Cancel' onclick='document.bodyform.rwd_action.value=\"rwd_cancel\";'>"
400
+ firstaction << "rwd_cancel" if firstaction.empty?
401
+ oneormorefields << "true"
402
+ when "help"
403
+ res << "<input type='submit' value='Help' onclick='document.bodyform.rwd_action.value=\"rwd_help\";'>"
404
+ firstaction << "rwd_help" if firstaction.empty?
405
+ oneormorefields << "true"
406
+ when "quit"
407
+ res << "<input type='submit' value='Quit' onclick='document.bodyform.rwd_action.value=\"rwd_quit\";'>"
408
+ firstaction << "rwd_quit" if firstaction.empty?
409
+ oneormorefields << "true"
410
+ when "close"
411
+ res << "<input type='submit' value='Close' onclick='window.close();'>"
412
+ firstaction << "rwd_quit" if firstaction.empty?
413
+ oneormorefields << "true"
414
+ when "main"
415
+ res << "<input type='submit' value='Main' onclick='document.bodyform.rwd_action.value=\"rwd_main\";'>"
416
+ firstaction << "rwd_main" if firstaction.empty?
417
+ oneormorefields << "true"
418
+ when "reset"
419
+ res << "<input type='reset' value='Reset'>"
420
+ firstaction << "rwd_quit" if firstaction.empty? # ???
421
+ oneormorefields << "true"
422
+ when "closewindow"
423
+ #res << "<script type='text/javascript'>\n" # ???
424
+ #res << "<!--\n"
425
+ #res << " window.close();\n"
426
+ #res << "//-->\n"
427
+ #res << "</script>"
428
+ when "tabs"
429
+ res << "<table #{AC} border='#{$rwd_border}' cellspacing='0' cellpadding='0'>"
430
+ res << " <tr #{AL}>"
431
+ res << " <td #{AL} class='tabs'>"
432
+ res << " <table #{AL} border='#{$rwd_border}' cellspacing='0' cellpadding='0'>"
433
+ res << " <tr #{AL}>"
434
+ #res << " <td class='notab'>&nbsp;</td>"
435
+ tabs.each do |obj|
436
+ name = obj.args["name"]
437
+ caption = obj.args["caption"]
438
+
439
+ res << "<td #{AL} class='notab'>&nbsp;</td>" unless obj == tabs[0]
440
+
441
+ if name == tab
442
+ res << "<td #{AC} class='activetab'><tt>&nbsp;#{caption}&nbsp;</tt></td>"
443
+ else
444
+ res << "<td #{AC} class='passivetab'><a href='javascript:document.bodyform.rwd_action.value=\"rwd_tab_#{name}\";document.bodyform.submit();'><tt>&nbsp;#{caption}&nbsp;</tt></a></td>"
445
+ end
446
+ end
447
+ res << " <td class='notab' width='100%'>&nbsp;</td>"
448
+ res << " </tr>"
449
+ res << " </table>"
450
+ res << " </td>"
451
+ res << " </tr>"
452
+ res << " <tr #{align}>"
453
+ res << " <td #{align} class='tabblad'>"
454
+ when "tab"
455
+ res << "<table #{AC} border='#{$rwd_border}' cellspacing='3' cellpadding='0'>"
456
+ when "panel"
457
+ level = (@args["level"] or "normal")
458
+ res << "<table #{AC} border='#{$rwd_border}' cellspacing='0' cellpadding='0'>"
459
+ res << " <tr #{align}>"
460
+ res << " <td #{align} class='panel1'>" if level == "normal"
461
+ res << " <td #{align} class='panel1high'>" if level == "high"
462
+ res << " <td #{align} class='panel1low'>" if level == "low"
463
+ res << " <table #{AC} border='#{$rwd_border}' cellspacing='0' cellpadding='0'>"
464
+ res << " <tr #{align}>"
465
+ res << " <td #{align} class='panel2'>" if level == "normal"
466
+ res << " <td #{align} class='panel2high'>" if level == "high"
467
+ res << " <td #{align} class='panel2low'>" if level == "low"
468
+ res << " <table #{AC} border='#{$rwd_border}' cellspacing='3' cellpadding='0'>"
469
+ else
470
+ puts "<#{@subtype}>"
471
+ res << "&lt;#{@subtype}&gt;"
472
+ end
473
+
474
+ bef = nil
475
+ aft = nil
476
+
477
+ case @subtype
478
+ when "vertical", "window", "helpwindow", "tab", "panel"
479
+ res << Format % ["AftPre", @subtype] if $rwd_debug
480
+ if @args.include?("spacing")
481
+ s = "<tr><td>&nbsp;</td></tr>" * (@args["spacing"].to_i)
482
+ else
483
+ s = ""
484
+ end
485
+ bef = "#{s}<tr #{align} #{valign}><td #{align}>"
486
+ aft = "</td></tr>"
487
+ when "horizontal", "row"
488
+ res << Format % ["AftPre", @subtype] if $rwd_debug
489
+ bef = "<td #{align}>"
490
+ aft = "</td>"
491
+ end
492
+
493
+ before.push(bef)
494
+ after.push(aft)
495
+ end
496
+
497
+ def postchildren(res, before, after, varshtml, varsstring, switches, help, oneormorefields, firstaction, tabs, tab, pda=false)
498
+ case @subtype
499
+ when "vertical", "window", "helpwindow", "tab", "panel"
500
+ res << Format % ["BefPost", @subtype] if $rwd_debug
501
+ if @args.include?("spacing")
502
+ res << "<tr><td>&nbsp;</td></tr>" * (@args["spacing"].to_i)
503
+ end
504
+ when "horizontal", "row"
505
+ res << Format % ["BefPost", @subtype] if $rwd_debug
506
+ end
507
+
508
+ res << Format % ["Post", @subtype] if $rwd_debug
509
+
510
+ case @subtype
511
+ when "application"
512
+ when "window", "helpwindow"
513
+ args = @args.deep_dup
514
+
515
+ args["nohelpbutton"] = (not help)
516
+
517
+ template = $rwd_html_2
518
+ template = $rwd_html_PDA_2 if pda
519
+
520
+ res << (template(template, args))
521
+ when "p" then res << "</p>"
522
+ when "pre" then res << "</pre>"
523
+ when "big" then res << "</big></p>"
524
+ when "small" then res << "</small></p>"
525
+ when "list" then res << "</ul>"
526
+ when "item" then res << "</li>"
527
+ when "empty" then res << "</p>"
528
+ when "image" then res << ""
529
+ when "progressbar" then res << ""
530
+ when "br" then res << ""
531
+ when "hr" then res << ""
532
+ when "b" then res << "</b>"
533
+ when "i" then res << "</i>"
534
+ when "a" then res << "</a>"
535
+ when "vertical" then res << "</table>"
536
+ when "horizontal" then res << "</tr></table>"
537
+ when "table" then res << "</table>"
538
+ when "row" then res << "</tr>"
539
+ when "hidden" then res << "</p>"
540
+ when "text" then res << "</p>"
541
+ when "textarea" then res << "</p>"
542
+ when "password" then res << "</p>"
543
+ when "checkbox" then res << "</p>"
544
+ when "radio" then res << "</p>"
545
+ when "select"
546
+ res << "</select>"
547
+ $select = nil
548
+ when "option" then res << "</option>"
549
+ when "button" then res << ""
550
+ when "back" then res << ""
551
+ when "cancel" then res << ""
552
+ when "help" then res << ""
553
+ when "quit" then res << ""
554
+ when "close" then res << ""
555
+ when "main" then res << ""
556
+ when "reset" then res << ""
557
+ when "closewindow" then res << ""
558
+ when "tabs"
559
+ res << " </td>"
560
+ res << " </tr>"
561
+ res << "</table>"
562
+ when "tab"
563
+ res << "</table>"
564
+ when "panel"
565
+ res << " </table>"
566
+ res << " </td>"
567
+ res << " </tr>"
568
+ res << " </table>"
569
+ res << " </td>"
570
+ res << " </tr>"
571
+ res << "</table>"
572
+ else
573
+ puts "</#{@subtype}>"
574
+ res << "&lt;/#{@subtype}&gt;"
575
+ end
576
+
577
+ before.pop
578
+ after.pop
579
+
580
+ aft = after[-1]
581
+ res << Format % ["After", @subtype] if ($rwd_debug and not aft.nil?)
582
+ res << aft if not aft.nil?
583
+ end
584
+
585
+ def template(html, vars)
586
+ res = []
587
+
588
+ a = {}
589
+
590
+ vars.each do |k, v|
591
+ a[k.upcase] = v
592
+ end
593
+
594
+ logo = nil
595
+ logo = File.expand_path(vars["logo"], $rwd_files) if vars.include?("logo")
596
+ logo = nil unless logo.nil? or File.file?(logo)
597
+
598
+ watermark = nil
599
+ watermark = File.expand_path(vars["watermark"], $rwd_files) if vars.include?("watermark")
600
+ watermark = nil unless watermark.nil? or File.file?(watermark)
601
+
602
+ a["LOGO"] = "" unless not logo.nil?
603
+ a["WATERMARK"] = "" unless not watermark.nil?
604
+
605
+ a["HELPBUTTON"] = (not (vars["nohelpbutton"]))
606
+ a["BACKBUTTONS"] = (not (vars["nobackbuttons"]))
607
+ a["BACKBUTTONS"] = (not (vars["nobackbuttons"]))
608
+ a["CLOSEBUTTON"] = (not (vars["noclosebutton"]))
609
+
610
+ if a.include?("WIDTH")
611
+ a["WIDTH1"] = "width='#{a["WIDTH"]}'"
612
+ a["WIDTH2"] = a["WIDTH"]
613
+ else
614
+ a["WIDTH1"] = " "
615
+ a["WIDTH2"] = "1"
616
+ end
617
+
618
+ html.split(/\r*\n/).each do |line|
619
+ if line =~ /%[A-Z0-9]+%/
620
+ a.each do |k, v|
621
+ v = false if (v.kind_of?(String) and v.empty?)
622
+
623
+ if line.include?("%#{k}%")
624
+ line.gsub!("%#{k}%", "#{v}") if v
625
+ end
626
+ end
627
+
628
+ line = "<!-- #{line.scan(/%[A-Z0-9]+%/).join(" ")} -->" if line =~ /%[A-Z0-9]+%/
629
+ end
630
+
631
+ res << line
632
+ end
633
+
634
+ res.join("\n")
635
+ end
636
+ end
637
+
638
+ class Text
639
+ def prechildren(res, before, after, varshtml, varsstring, switches, help, oneormorefields, firstaction, tabs, tab, pda=false)
640
+ if not @text.scan(/[^ \t\r\n]/).empty?
641
+ res << Format % ["Text", ""] if $rwd_debug
642
+ res << "#{@text}"
643
+ end
644
+ end
645
+ end
646
+
647
+ class RWDTree < XML
648
+ end
649
+
650
+ class RWDWindow
651
+ @@windows = {} # Kind of caching.
652
+ @@helpwindows = {} # Kind of caching.
653
+
654
+ def initialize(rwd, window=nil)
655
+ rwd = rwd.join("\n") if rwd.kind_of?(Array)
656
+
657
+ if @@windows[rwd].nil?
658
+ @@windows[rwd] = {}
659
+ @@helpwindows[rwd] = {}
660
+
661
+ tree = XML.new(rwd)
662
+
663
+ tree.parse(OpenTag, "window") do |type, obj|
664
+ $rwd_appvars.each{|k, v| obj.args[k] = v}
665
+ @@windows[rwd][obj.args["name"]] = obj.to_h
666
+ end
667
+
668
+ tree.parse(OpenTag, "helpwindow") do |type, obj|
669
+ $rwd_appvars.each{|k, v| obj.args[k] = v}
670
+ @@helpwindows[rwd][obj.args["name"]] = obj.to_h
671
+ end
672
+ end
673
+
674
+ @rwd = (@@windows[rwd][window] or "").dup
675
+ @helprwd = (@@helpwindows[rwd][window] or "").dup
676
+ end
677
+
678
+ def render(pda, action=nil, vars=Hash.new, switches=Hash.new, help=false, tab="")
679
+ varshtml = Hash.new
680
+ varsstring = Hash.new
681
+ oneormorefields = ""
682
+ firstaction = ""
683
+ html = []
684
+
685
+ vars = vars.deep_dup
686
+
687
+ begin # error wrap
688
+
689
+ vars.each do |key, value|
690
+ if not key.empty?
691
+ if value.respond_to? "to_s"
692
+ @rwd.gsub!(/%%#{key}%%/, value.to_s)
693
+ @rwd.gsub!(/%#{key}%/, value.to_s.to_html)
694
+
695
+ @helprwd.gsub!(/%%#{key}%%/, value.to_s)
696
+ @helprwd.gsub!(/%#{key}%/, value.to_s.to_html)
697
+
698
+ varshtml[key] = value.to_s.to_html
699
+ varsstring[key] = value.to_s
700
+ end
701
+ end
702
+ end
703
+
704
+ windowobject = RWDTree.new(@rwd).children.dup.delete_if{|obj| obj.subtype != "window"}[0]
705
+ helpobject = RWDTree.new(@helprwd).children.dup.delete_if{|obj| obj.subtype != "helpwindow"}[0]
706
+
707
+ tabsobj = windowobject.children.dup.delete_if{|obj| obj.subtype != "tabs"}[0]
708
+
709
+ if not tabsobj.nil?
710
+ tabs = tabsobj.children.dup.delete_if{|obj| (not obj.kind_of?(OpenTag)) or (obj.subtype != "tab")}
711
+
712
+ if tab.empty?
713
+ tab = tabs[0].args["name"]
714
+ end
715
+
716
+ tabsobj.children.delete_if{|obj| (obj.kind_of?(OpenTag)) and (obj.subtype == "tab") and obj.args["name"] != tab}
717
+ end
718
+
719
+ if help
720
+ helpobject.parsetree("prechildren", "postchildren", html, [""], [""], varshtml, varsstring, switches, false, oneormorefields, firstaction, tabs, tab, pda)
721
+ else
722
+ windowobject.parsetree("prechildren", "postchildren", html, [""], [""], varshtml, varsstring, switches, (not @helprwd.empty?), oneormorefields, firstaction, tabs, tab, pda)
723
+ end
724
+
725
+ html = html.join("") # ???
726
+
727
+ html.gsub!(/%%*[[:alnum:]_\-]+%%*/, "") if not $rwd_debug
728
+ html.gsub!(/%%/, "%")
729
+ html.gsub!(/\n\n*/, "\n")
730
+
731
+ if oneormorefields.empty?
732
+ focus = ""
733
+ else
734
+ focus = "document.bodyform.elements[0].focus();"
735
+ end
736
+
737
+ firstaction = action if windowobject.args.keys.include?("refresh") unless action.nil?
738
+
739
+ html.gsub!(/\$RWD_FIRSTACTION\$/ , firstaction)
740
+ html.gsub!(/\$RWD_FOCUS\$/ , focus)
741
+
742
+ html
743
+ end
744
+
745
+ rescue
746
+ $rwdtinkerlog.error "error in RWDWindow - render method"
747
+
748
+ end
749
+ end
750
+
751
+
752
+ class RWDMessage < RWDWindow
753
+ def initialize(msg)
754
+ super("<window title='RWD Message' nobackbuttons noclosebutton><p>#{msg}</p><back/></window>")
755
+ end
756
+ end
757
+
758
+ class RWDError < RWDWindow
759
+ def initialize(msg)
760
+ super("<window title='RWD Error' nobackbuttons noclosebutton><p><b>Error:</b> #{msg}</p><back/></window>")
761
+ end
762
+ end
763
+
764
+ class RWDProgressBar < RWDWindow
765
+ def initialize(refresh, progress)
766
+ s = ""
767
+ s << "<window title='RWD Progress' nobackbuttons noclosebutton refresh='#{refresh}'>"
768
+ if progress.length == 1
769
+ progress.each do |caption, value|
770
+ s << "<p>#{caption}</p><progressbar value='#{value}'/><p>#{(100*value).to_i}%%</p>"
771
+ end
772
+ else
773
+ s << "<table>"
774
+ progress.each do |caption, value|
775
+ s << "<row><p align='left'>#{caption}</p><progressbar value='#{value}'/><p align='right'>#{(100*value).to_i}%%</p></row>"
776
+ end
777
+ s << "</table>"
778
+ end
779
+ s << "<cancel/>"
780
+ s << "</window>"
781
+ super(s)
782
+ end
783
+ end
784
+
785
+ class RWDDone < RWDWindow
786
+ def initialize(exitbrowser)
787
+ super("<window title='RWD Message' nobackbuttons noclosebutton><p>Done.</p><i>(Some browsers don't close,<br>because of security reasons.)</i><horizontal><close/>#{exitbrowser ? "" : "<button caption='Again'/>"}</horizontal>#{exitbrowser ? "<closewindow/>" : ""}</window>")
788
+ end
789
+ end
790
+
791
+ class RWDialog
792
+
793
+ def initialize(xml)
794
+ @rwd_xml = $rwd_gui_tinker
795
+ # change from default ev - was xml
796
+ @rwd_exitbrowser = false
797
+ @rwd_history = []
798
+ @rwd_ignore_vars = []
799
+ @rwd_call_after_back = []
800
+ @rwd_time = Time.now
801
+
802
+ $rwd_appvars = {} if $rwd_appvars.nil?
803
+ XML.new(xml).parse(OpenTag, "application") do |type, obj|
804
+ obj.args.deep_dup.each do |k, v|
805
+ $rwd_appvars[k] = v
806
+ end
807
+ end
808
+ end
809
+
810
+ def self.file(rwdfile, *args)
811
+ new(File.new(rwdfile).readlines, *args)
812
+ end
813
+
814
+ def serve(port=nil, auth=nil, realm=self.class.to_s)
815
+ exit if $rwd_exit
816
+
817
+ raise "RWD is not initialized." if @rwd_xml.nil?
818
+
819
+ low, high = ENV["RWDPORTS"].split(/[^\d+]/)
820
+ high = low if high.nil?
821
+ low, high = low.to_i, high.to_i
822
+
823
+ io = nil
824
+
825
+ port, io = TCPServer.freeport(low, high, (not auth.nil?)) if port.nil?
826
+ raise "No free TCP port." if port.nil?
827
+
828
+ port = port.to_i
829
+
830
+ @rwd_server = RWDServer.new(self, port, io, auth, realm)
831
+
832
+ self
833
+ end
834
+
835
+
836
+
837
+ def render(res, path, post, download, downloadfile, pda, sessionid)
838
+ # Avoid a timeout.
839
+
840
+ @rwd_time = Time.now
841
+
842
+ # Initialize some vars.
843
+
844
+ vars = Hash.new if vars.nil?
845
+ @rwd_switches = Hash.new if @rwd_switches.nil?
846
+
847
+ done = false
848
+ help = false
849
+ back = false
850
+ tab = ""
851
+ @rwd_progress_thread = nil
852
+ @rwd_msgtype = nil if @rwd_progress_thread.nil?
853
+ @rwd_download = nil
854
+ @rwd_download_file = nil
855
+
856
+ # Switches are used for checkboxes.
857
+
858
+ @rwd_switches.each do |key, value|
859
+ vars[key] = "off"
860
+ end
861
+
862
+ @rwd_switches = Hash.new
863
+
864
+ # Copy the vars from the window to vars. vars wil later on be copied to instance variables.
865
+
866
+ post.sort.each do |key, value|
867
+ puts "Post: #{key} -> #{value.from_html.inspect}" if $rwd_debug
868
+ $rwdtinkerlog.info "Post: #{key} -> #{value.from_html.inspect}\n"
869
+
870
+ vars[key] = value.from_html
871
+ $rwdtinkerlog.info "rwd: #{value.from_html}\n"
872
+
873
+ end
874
+
875
+ # Stack handling for rwd_action, rwd_window and rwd_tab.
876
+
877
+ @rwd_action = vars["rwd_action"] if vars.include?("rwd_action")
878
+ @rwd_action, @rwd_args = @rwd_action.split(/\//, 2) unless @rwd_action.nil?
879
+ @rwd_action, rest = @rwd_action.split(/\?/) unless @rwd_action.nil?
880
+
881
+ @rwd_refresh_action = (@rwd_action or @rwd_refresh_action or "main")
882
+
883
+ unless rest.nil?
884
+ rest.each do |s|
885
+ k, v = s.split(/=/, 2)
886
+ vars[k] = v
887
+ end
888
+ end
889
+
890
+ if @rwd_action == "rwd_cancel"
891
+ @rwd_progress_thread.kill unless @rwd_progress_thread.nil?
892
+ @rwd_progress_thread = nil
893
+ @rwd_action = "rwd_back"
894
+ end
895
+
896
+ @rwd_history = [["main", [], "main", ""]] if @rwd_history.empty?
897
+
898
+ if @rwd_action =~ /^rwd_tab_/
899
+ @rwd_tab = @rwd_action.sub(/^rwd_tab_/, "")
900
+ @rwd_history[-1][3] = @rwd_tab
901
+ else
902
+ case @rwd_action
903
+ when "rwd_back"
904
+ @rwd_history.pop
905
+ @rwd_action = (@rwd_history[-1] or [nil, nil, nil])[0]
906
+ @rwd_args = (@rwd_history[-1] or [nil, nil, nil])[1]
907
+ @rwd_window = (@rwd_history[-1] or [nil, nil, nil])[2]
908
+ @rwd_tab = (@rwd_history[-1] or [nil, nil, nil])[3]
909
+ back = true
910
+ when "rwd_help"
911
+ help = true
912
+ when "rwd_main"
913
+ @rwd_action = nil
914
+ @rwd_window = nil
915
+ @rwd_tab = nil
916
+ @rwd_history = []
917
+ when "rwd_quit"
918
+ done = true
919
+ else
920
+ end
921
+
922
+ # History stuff
923
+
924
+ @rwd_history = @rwd_history[-100..-1] if @rwd_history.length >= 100
925
+ @rwd_action = "main" if @rwd_action.nil?
926
+ @rwd_action = "main" if @rwd_action.empty?
927
+ @rwd_window = "main" if @rwd_window.nil?
928
+ @rwd_window = "main" if @rwd_window.empty?
929
+ @rwd_tab = "" if @rwd_tab.nil?
930
+ @rwd_args = [] if @rwd_args.nil?
931
+ @rwd_args = [] if @rwd_action == "main"
932
+
933
+ vars["rwd_action"] = @rwd_action
934
+ vars["rwd_window"] = @rwd_window
935
+ vars["rwd_tab"] = @rwd_tab
936
+
937
+ # Copy vars from window to instance.
938
+
939
+ vars.each do |k, v|
940
+ $rwdtinkerlog.info "rwd: Post: #{k} -> #{v}\n"
941
+
942
+ if ((not k.empty?) and k.scan(/^rwd_/).empty? and not @rwd_ignore_vars.include?("@#{k}"))
943
+
944
+ instance_eval "@#{k} = ''"
945
+ instance_variable_set("@#{k}", vars.fetch("#{k}"))
946
+ $rwdtinkerlog.info "rwd: Post: #{k} -> #{v}\n"
947
+
948
+ end
949
+ end
950
+
951
+ # Callback.
952
+
953
+ if (not back) or @rwd_call_after_back.include?(@rwd_action)
954
+ unless @rwd_action =~ /^rwd_/
955
+
956
+ $rwdtinkerlog.debug "Method: #{@rwd_action}(#{@rwd_args})"
957
+
958
+ if methods.include?(@rwd_action)
959
+ method(@rwd_action).call(*@rwd_args)
960
+ else
961
+ puts "Method '%s' is not defined." % @rwd_action
962
+ end
963
+ end
964
+
965
+ # History stuff
966
+
967
+ @rwd_history = [["main", [], "main", ""]] if @rwd_action == "main"
968
+ @rwd_history = [["main", [], "main", ""]] if @rwd_history.empty?
969
+
970
+ a = [@rwd_action, @rwd_args, @rwd_window, @rwd_tab]
971
+
972
+ @rwd_history.push a if (@rwd_history[-1] != a or not @rwd_msgtype.nil?)
973
+
974
+ if @rwd_window == "rwd_back"
975
+ @rwd_history.pop
976
+ @rwd_history.pop
977
+ @rwd_action = (@rwd_history[-1] or [nil, nil, nil])[0]
978
+ @rwd_args = (@rwd_history[-1] or [nil, nil, nil])[1]
979
+ @rwd_window = (@rwd_history[-1] or [nil, nil, nil])[2]
980
+ @rwd_tab = (@rwd_history[-1] or [nil, nil, nil])[3]
981
+ end
982
+ end
983
+ end
984
+
985
+ # Copy vars from instance to window.
986
+
987
+ instance_variables.each do |k|
988
+ k.sub!(/^@/, "")
989
+ instance_eval "vars['#{k}'] = @#{k}.to_s" if (k.scan(/^rwd_/).empty? and not @rwd_ignore_vars.include?("@#{k}"))
990
+ end
991
+
992
+ # just ignore.
993
+
994
+ vars.sort.each do |key, value|
995
+ puts "Pre: #{key} -> #{value.inspect}" if $rwd_debug
996
+ end
997
+
998
+
999
+ # Answer to browser.
1000
+
1001
+ if done
1002
+ res << RWDDone.new(@rwd_exitbrowser).render(pda)
1003
+ else
1004
+ if not @rwd_download.nil?
1005
+ puts "Download: #{@rwd_window}" if $rwd_debug
1006
+
1007
+ download << @rwd_download
1008
+ downloadfile << @rwd_download_file
1009
+ else
1010
+ if not @rwd_progress_thread.nil?
1011
+ res << RWDProgressBar.new(@rwd_progress_refresh, @rwd_progress_progress).render(pda, @rwd_refresh_action)
1012
+ else
1013
+ if not @rwd_msgtype.nil?
1014
+ res << RWDMessage.new(@rwd_msg).render(pda) if @rwd_msgtype == "message"
1015
+ res << RWDError.new(@rwd_msg).render(pda) if @rwd_msgtype == "error"
1016
+ res << @rwd_msg if @rwd_msgtype == "text"
1017
+ else
1018
+ puts "Window: #{@rwd_window}" if $rwd_debug
1019
+ puts "Tab: #{@rwd_tab}" if $rwd_debug
1020
+
1021
+ begin # error block
1022
+ if @rwd_window.empty?
1023
+ @rwd_window = "main"
1024
+ end
1025
+ res << RWDWindow.new($rwd_gui_tinker, @rwd_window).render(pda, @rwd_refresh_action, vars, @rwd_switches, help, @rwd_tab)
1026
+ rescue
1027
+
1028
+ $rwdtinkerlog.error "rwd: error in render"
1029
+
1030
+ end
1031
+ end
1032
+ end
1033
+ end
1034
+ end
1035
+
1036
+ return done
1037
+ end
1038
+
1039
+ def samewindow?
1040
+ @rwd_history[-1][2] == @rwd_window
1041
+ end
1042
+
1043
+ def message(msg, &block)
1044
+ @rwd_msg = msg
1045
+ @rwd_msgtype = "message"
1046
+ end
1047
+
1048
+ def error(msg, &block)
1049
+ @rwd_msg = msg
1050
+ @rwd_msgtype = "error"
1051
+ end
1052
+
1053
+ def text(msg)
1054
+ @rwd_msg = "<html><body><pre>#{msg}</pre></body></html>"
1055
+ @rwd_msgtype = "text"
1056
+ end
1057
+
1058
+ def progressbar(refresh, *progress)
1059
+ @rwd_progress_refresh = (refresh or 1)
1060
+ @rwd_progress_progress = []
1061
+
1062
+ while not progress.empty?
1063
+ s = (progress.shift or "")
1064
+ if s.kind_of?(Array)
1065
+ caption, value = s
1066
+ value = (value or 0.0).to_f
1067
+ else
1068
+ caption = s
1069
+ value = (progress.shift or 0.0).to_f
1070
+ end
1071
+
1072
+ @rwd_progress_progress << [caption, value]
1073
+ end
1074
+
1075
+ if @rwd_progress_thread.nil?
1076
+ @rwd_progress_progress.each do |a|
1077
+ a[1] = 0.0
1078
+ end
1079
+
1080
+ @rwd_progress_thread =
1081
+ Thread.new do
1082
+ yield
1083
+ end
1084
+ Thread.pass
1085
+ end
1086
+
1087
+ @rwd_progress_thread = nil unless @rwd_progress_thread.alive?
1088
+ end
1089
+
1090
+ def download(data, filename="")
1091
+ @rwd_download = data
1092
+ @rwd_download_file = filename
1093
+ end
1094
+
1095
+ def exitbrowser
1096
+ @rwd_exitbrowser = true
1097
+ end
1098
+
1099
+ def timeout(timeout, interval=1)
1100
+ @rwd_timeout = timeout
1101
+
1102
+ unless @rwd_timeout_thread
1103
+ @rwd_timeout_thread =
1104
+ Thread.new do
1105
+ loop do
1106
+ if Time.now - @rwd_time > @rwd_timeout
1107
+
1108
+ $rwdtinkerlog.info "rwd: Exiting due to timeout (#{@rwd_timeout} seconds)."
1109
+
1110
+ exit 1
1111
+ end
1112
+ sleep interval
1113
+ end
1114
+ end
1115
+ end
1116
+ end
1117
+ end
1118
+
1119
+ class RWDLogin < RWDialog
1120
+ def initialize(realm)
1121
+ super("<window name='main' title='RWD Login for #{realm}' nobackbuttons noclosebutton><table><row><p align='right'>Username:</p><text name='rwd_a'/></row><row><p align='right'>Password:</p><password name='rwd_b'/></row></table><button caption='Login'/></window>")
1122
+ end
1123
+ end
1124
+
1125
+ class RWDTimeOut < RWDialog
1126
+ def initialize
1127
+ super("<window name='main' title='RWD Error' nobackbuttons noclosebutton><p><b>Error:</b> Session has expired.</p><button caption='New session'/></window>")
1128
+ end
1129
+ end
1130
+
1131
+ class SessionCleanup
1132
+ def initialize(sessions, interval, timeout)
1133
+ every(interval) do
1134
+ sessions.delete_if do |id, session|
1135
+ time = Time.now.to_i - session.lastaccess.to_i
1136
+
1137
+ puts "Session %s deleted" % id if time > timeout
1138
+
1139
+ time > timeout
1140
+ end
1141
+ end
1142
+ end
1143
+ end
1144
+
1145
+ class Sessions
1146
+ def initialize(rack, cleanup)
1147
+ @rack = rack.to_s
1148
+ @cleanup = SessionCleanup.new(self, 3600, 24*3600) if cleanup
1149
+ @sessions = {}
1150
+ end
1151
+
1152
+ def [](sessionid)
1153
+ @sessions[sessionid]
1154
+ end
1155
+
1156
+ def []=(sessionid, value)
1157
+ @sessions[sessionid] = value
1158
+ end
1159
+
1160
+ def delete(sessionid)
1161
+ @sessions.delete(sessionid)
1162
+ end
1163
+
1164
+ def delete_if(&block)
1165
+ @sessions.delete_if{|k, v| block.call(k, v)}
1166
+ end
1167
+
1168
+ def include?(sessionid)
1169
+ @sessions.include?(sessionid)
1170
+ end
1171
+ end
1172
+
1173
+ class RWDSession < Hash
1174
+ attr_reader :sessionid
1175
+ attr_reader :lastaccess
1176
+ attr_reader :authenticated
1177
+ attr_writer :authenticated
1178
+
1179
+ def initialize(sessionid=nil)
1180
+ @sessionid = sessionid
1181
+ @lastaccess = Time.now
1182
+ @authenticated = false
1183
+ end
1184
+
1185
+ def touch
1186
+ @lastaccess = Time.now
1187
+ end
1188
+
1189
+ def render(res, path, post, download, downloadfile, pda=false)
1190
+ done = self["object"].render(res, path, post, download, downloadfile, pda, @sessionid)
1191
+
1192
+ res.gsub!(/\$RWD_SESSION\$/, done ? "" : "#{@sessionid}")
1193
+
1194
+ return done
1195
+ end
1196
+ end
1197
+
1198
+ class RWDServer
1199
+ def initialize(obj, port, io, auth, realm)
1200
+ @object = obj
1201
+ @localbrowsing = false
1202
+ @browserstarted = false
1203
+ @sessions = Sessions.new(obj.class, (not auth.nil?))
1204
+
1205
+ if auth.nil?
1206
+ @localbrowsing = true
1207
+
1208
+ if ENV.include?("RWDBROWSER") and not ENV["RWDBROWSER"].nil? and not ENV["RWDBROWSER"].empty?
1209
+ @browserstarted = true
1210
+ @object.exitbrowser
1211
+
1212
+ # Start browser.
1213
+
1214
+ @browserthread =
1215
+ Thread.new do
1216
+ $rwdtinkerlog.warn "rwd: Starting the browser..."
1217
+
1218
+
1219
+ #if ENV["RWDBROWSER"].downcase =~ /iexplore/ # ???
1220
+ #@ie = IE.new("http://localhost:#{port}/")
1221
+ #else
1222
+ browser = ENV["RWDBROWSER"].dup
1223
+ url = "http://localhost:%s/" % [port]
1224
+
1225
+ re = /[$%]1\b/
1226
+ command = "%s \"%s\"" % [browser, url]
1227
+ command = browser.gsub(re, url) if browser =~ re
1228
+
1229
+ command.gsub!(/%port%/, port.to_s)
1230
+
1231
+ system(command) or $rwdtinkerlog.error "Starting of the browser failed, or the browser terminated abnormally.\nCommand => #{command}"
1232
+ #end
1233
+
1234
+ puts "The browser has terminated."
1235
+ end
1236
+ end
1237
+ end
1238
+
1239
+ # Start server.
1240
+
1241
+ portio = port
1242
+ portio = [port, io] unless io.nil?
1243
+ threadlimiter = ThreadLimiter.new(1)
1244
+
1245
+ HTTPServer.serve(portio, (not auth.nil?)) do |req, resp|
1246
+ threadlimiter.wait do
1247
+ vars = {}
1248
+ req.vars.each do |k, v|
1249
+ vars[k] = v.join("\t")
1250
+ end
1251
+ pad = (req.request.path or "/")
1252
+
1253
+ if auth.kind_of? String
1254
+ file = "#{home}/#{auth}"
1255
+ auths = {}
1256
+ auths = Hash.file(file) if File.file?(file)
1257
+ else
1258
+ auths = auth
1259
+ end
1260
+
1261
+ #oldsessionid = vars["rwd_session"]
1262
+ oldsessionid = req.cookies["sessionid"]
1263
+
1264
+ # Retrieve session.
1265
+
1266
+ session = @sessions[oldsessionid]
1267
+
1268
+ # Eventually create new session.
1269
+
1270
+ if session.nil?
1271
+ sessionid = MD5.new(req.peeraddr[3].to_s + @object.inspect.to_s + ("%1.6f" % Time.now.to_f)).to_s while (sessionid == nil or @sessions.include?(sessionid))
1272
+ session = RWDSession.new(sessionid)
1273
+
1274
+ if auth.nil?
1275
+ session["object"] = @object
1276
+ else
1277
+ session["object"] = @object.clone
1278
+ end
1279
+
1280
+ if oldsessionid.nil? or oldsessionid.empty?
1281
+ if not auth.nil? and not auth.empty? and not session.authenticated and pad !~ /^\/rwd_/
1282
+
1283
+ # Check authentication
1284
+
1285
+ us = vars["rwd_a"]
1286
+ pa = vars["rwd_b"]
1287
+
1288
+ if us.nil? or pa.nil? or auths[us] != pa
1289
+ session = RWDSession.new
1290
+ session["object"] = RWDLogin.new(realm)
1291
+ pad = "/"
1292
+ else
1293
+ session.authenticated = true
1294
+ @sessions[session.sessionid] = session
1295
+ end
1296
+ else
1297
+ session.authenticated = true
1298
+ @sessions[session.sessionid] = session
1299
+ end
1300
+ else
1301
+ session = RWDSession.new
1302
+ session["object"] = RWDTimeOut.new
1303
+ end
1304
+
1305
+ vars = {}
1306
+ end
1307
+
1308
+ # Avoid timeout.
1309
+
1310
+ session.touch
1311
+
1312
+ if pad == "/"
1313
+
1314
+ # Serve methods/callbacks.
1315
+
1316
+ # Build new page.
1317
+
1318
+ download = ""
1319
+ downloadfile = ""
1320
+ res = ""
1321
+
1322
+ done = session.render(res, pad, vars, download, downloadfile, req.pda?)
1323
+
1324
+ begin
1325
+ if download.empty?
1326
+ resp["Content-Type"] = "text/html"
1327
+ if done
1328
+ resp.cookies["sessionid"] = ""
1329
+ else
1330
+ resp.cookies["sessionid"] = session.sessionid
1331
+ end
1332
+
1333
+ resp << res
1334
+ else
1335
+ resp["Content-Type"] = "application/octet-stream"
1336
+ resp["Content-Disposition"] = "attachment;"
1337
+ resp["Content-Disposition"] = "attachment; filename=%s" % downloadfile unless downloadfile.empty?
1338
+
1339
+ resp << download
1340
+ end
1341
+ rescue
1342
+
1343
+ $rwdtinkerlog.error "rwd: Sending response to browser failed."
1344
+ @sessions.delete(session.sessionid)
1345
+ end
1346
+
1347
+ # Eventually delete this session.
1348
+
1349
+ if done
1350
+ @sessions.delete(session.sessionid)
1351
+
1352
+ if @localbrowsing
1353
+ resp.stop
1354
+
1355
+ if @browserstarted and not @browserthread.nil? and @browserthread.alive?
1356
+ resp.stop do
1357
+
1358
+ $rwdtinkerlog.warn "rwd: Waiting for the browser to terminate..."
1359
+
1360
+ @browserthread.join
1361
+ end
1362
+ end
1363
+ end
1364
+ end
1365
+
1366
+ else
1367
+
1368
+ # Serve files.
1369
+
1370
+ if pad == "/rwd_pixel.gif"
1371
+ resp["Cache-Control"] = "max-age=86400"
1372
+ resp["Content-Type"] = "image/gif"
1373
+ resp << $rwd_pixel
1374
+ else
1375
+ if session.authenticated
1376
+ pwd = Dir.pwd
1377
+ file = File.expand_path(pad.gsub(/^\/*/, ""), $rwd_files)
1378
+
1379
+ if not file.index(pwd) == 0
1380
+ resp["Content-Type"] = "text/html"
1381
+ resp.response = "HTTP/1.0 400 BAD REQUEST"
1382
+ resp << "<html><body><p><b>Bad Request.</b> (<tt>#{pad}</tt>)</p></body></html>"
1383
+ elsif File.file?(file)
1384
+ resp << File.new(file, "rb").read rescue nil
1385
+ else
1386
+ resp["Content-Type"] = "text/html"
1387
+ resp.response = "HTTP/1.0 404 NOT FOUND"
1388
+ resp << "<html><body><p><b>Not found.</b> (<tt>#{pad}</tt>)</p></body></html>"
1389
+ end
1390
+ else
1391
+ resp["Content-Type"] = "text/html"
1392
+ resp.response = "HTTP/1.0 ??? NOT AUTHORIZED"
1393
+ resp << "<html><body><p><b>Not Authorized.</b></p></body></html>"
1394
+ end
1395
+ end
1396
+
1397
+ end
1398
+
1399
+ end
1400
+ end
1401
+ end
1402
+ end
1403
+
1404
+
1405
+
1406
+ $rwd_pixel = "
1407
+ R0lGODlhAQABAMIAAAAAAP///+7u7kREiP///////////////yH5BAEKAAMA
1408
+ LAAAAAABAAEAAAMCOAkAOw==
1409
+ ".unpack("m").shift
1410
+
1411
+ $rwd_logo = "
1412
+ R0lGODlhEAAQAMIAAAAAAP///+7u7kREiP///////////////yH5BAEKAAQA
1413
+ LAAAAAAQABAAAANCSErQ/k21QKulrIrNu8heuAGUcJ0BuQVD676DasK0zNKv
1414
+ jefB+oo6l6AxBAx7M2HRePQph5xga0RsJqfELPI2DSUAADs=
1415
+ ".unpack("m").shift
1416
+
1417
+
1418
+ $rwd_html_1, $rwd_html_2 = $rwd_html[ENV["RWDTHEME"]].split(/^\s*%BODY%\s*\r*$/)
1419
+ #if ENV["RWDTHEME"] == "PDA"
1420
+ #$rwd_html_PDA_1, $rwd_html_PDA_2 = $rwd_html["PDA"].split(/^\s*%BODY%\s*\r*$/)
1421
+ #end
1422
+ #end
1423
+ #
1424
+ #class RWDialog < RWD::RWDialog
1425
+ #end