neo_rad 0.4.0

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 (146) hide show
  1. checksums.yaml +7 -0
  2. data/History.txt +112 -0
  3. data/License.txt +282 -0
  4. data/Manifest.txt +144 -0
  5. data/README.rdoc +1 -0
  6. data/Rakefile +142 -0
  7. data/bin/rad +302 -0
  8. data/lib/examples/add_hysteresis.rb +13 -0
  9. data/lib/examples/basic_blink.rb +10 -0
  10. data/lib/examples/blink_m_address_assignment.rb +104 -0
  11. data/lib/examples/blink_m_hello.rb +14 -0
  12. data/lib/examples/blink_m_multi.rb +61 -0
  13. data/lib/examples/blink_with_serial.rb +16 -0
  14. data/lib/examples/configure_pa_lcd_boot.rb +91 -0
  15. data/lib/examples/debounce_methods.rb +49 -0
  16. data/lib/examples/external_variable_fu.rb +26 -0
  17. data/lib/examples/external_variables.rb +32 -0
  18. data/lib/examples/first_sound.rb +23 -0
  19. data/lib/examples/frequency_generator.rb +30 -0
  20. data/lib/examples/hello_array.rb +48 -0
  21. data/lib/examples/hello_array2.rb +112 -0
  22. data/lib/examples/hello_array_eeprom.rb +59 -0
  23. data/lib/examples/hello_clock.rb +84 -0
  24. data/lib/examples/hello_eeprom.rb +51 -0
  25. data/lib/examples/hello_eeprom_lcdpa.rb +81 -0
  26. data/lib/examples/hello_format_print.rb +94 -0
  27. data/lib/examples/hello_lcd_charset.rb +75 -0
  28. data/lib/examples/hello_pa_lcd.rb +59 -0
  29. data/lib/examples/hello_servos.rb +88 -0
  30. data/lib/examples/hello_spectra_sound.rb +38 -0
  31. data/lib/examples/hello_world.rb +11 -0
  32. data/lib/examples/hello_xbee.rb +12 -0
  33. data/lib/examples/hysteresis_duel.rb +39 -0
  34. data/lib/examples/i2c_with_clock_chip.rb +124 -0
  35. data/lib/examples/midi_beat_box.rb +86 -0
  36. data/lib/examples/midi_scales.rb +94 -0
  37. data/lib/examples/motor_knob.rb +30 -0
  38. data/lib/examples/servo_buttons.rb +23 -0
  39. data/lib/examples/servo_calibrate_continuous.rb +92 -0
  40. data/lib/examples/servo_throttle.rb +40 -0
  41. data/lib/examples/software_serial.rb +10 -0
  42. data/lib/examples/sparkfun_lcd.rb +48 -0
  43. data/lib/examples/spectra_soft_pot.rb +34 -0
  44. data/lib/examples/times_method.rb +8 -0
  45. data/lib/examples/toggle.rb +10 -0
  46. data/lib/examples/twitter.rb +57 -0
  47. data/lib/examples/two_wire.rb +14 -0
  48. data/lib/libraries/AFSoftSerial/AFSoftSerial.cpp +321 -0
  49. data/lib/libraries/AFSoftSerial/AFSoftSerial.h +61 -0
  50. data/lib/libraries/AFSoftSerial/keywords.txt +18 -0
  51. data/lib/libraries/AF_XPort/AF_XPort.cpp +166 -0
  52. data/lib/libraries/AF_XPort/AF_XPort.h +48 -0
  53. data/lib/libraries/DS1307/DS1307.cpp +162 -0
  54. data/lib/libraries/DS1307/DS1307.h +66 -0
  55. data/lib/libraries/DS1307/keywords.txt +18 -0
  56. data/lib/libraries/FrequencyTimer2/FrequencyTimer2.cpp +144 -0
  57. data/lib/libraries/FrequencyTimer2/FrequencyTimer2.h +42 -0
  58. data/lib/libraries/FrequencyTimer2/keywords.txt +22 -0
  59. data/lib/libraries/I2CEEPROM/I2CEEPROM.cpp +120 -0
  60. data/lib/libraries/I2CEEPROM/I2CEEPROM.h +70 -0
  61. data/lib/libraries/I2CEEPROM/keywords.txt +21 -0
  62. data/lib/libraries/LoopTimer/LoopTimer.cpp +35 -0
  63. data/lib/libraries/LoopTimer/LoopTimer.h +34 -0
  64. data/lib/libraries/LoopTimer/keywords.txt +27 -0
  65. data/lib/libraries/OneWire/OneWire.cpp +194 -0
  66. data/lib/libraries/OneWire/OneWire.h +63 -0
  67. data/lib/libraries/OneWire/keywords.txt +35 -0
  68. data/lib/libraries/OneWire/readme.txt +13 -0
  69. data/lib/libraries/SWSerLCDpa/SWSerLCDpa.cpp +296 -0
  70. data/lib/libraries/SWSerLCDpa/SWSerLCDpa.h +69 -0
  71. data/lib/libraries/SWSerLCDsf/SWSerLCDsf.cpp +311 -0
  72. data/lib/libraries/SWSerLCDsf/SWSerLCDsf.h +67 -0
  73. data/lib/libraries/Servo/Servo.cpp +192 -0
  74. data/lib/libraries/Servo/Servo.h +61 -0
  75. data/lib/libraries/Stepper/Stepper.cpp +220 -0
  76. data/lib/libraries/Stepper/Stepper.h +86 -0
  77. data/lib/libraries/Stepper/keywords.txt +28 -0
  78. data/lib/libraries/Wire/Wire.cpp +262 -0
  79. data/lib/libraries/Wire/Wire.h +67 -0
  80. data/lib/libraries/Wire/keywords.txt +31 -0
  81. data/lib/libraries/Wire/twi.h +57 -0
  82. data/lib/libraries/Wire/utility/twi.c +449 -0
  83. data/lib/libraries/Wire/utility/twi.h +57 -0
  84. data/lib/plugins/bitwise_ops.rb +54 -0
  85. data/lib/plugins/blink.rb +25 -0
  86. data/lib/plugins/blink_m.rb +356 -0
  87. data/lib/plugins/debounce.rb +138 -0
  88. data/lib/plugins/debug_output_to_lcd.rb +71 -0
  89. data/lib/plugins/hysteresis.rb +52 -0
  90. data/lib/plugins/input_output_state.rb +84 -0
  91. data/lib/plugins/lcd_padding.rb +58 -0
  92. data/lib/plugins/mem_test.rb +37 -0
  93. data/lib/plugins/midi.rb +60 -0
  94. data/lib/plugins/parallax_ping.rb +50 -0
  95. data/lib/plugins/servo_pulse.rb +31 -0
  96. data/lib/plugins/servo_setup.rb +86 -0
  97. data/lib/plugins/smoother.rb +54 -0
  98. data/lib/plugins/spark_fun_serial_lcd.rb +100 -0
  99. data/lib/plugins/spectra_symbol.rb +79 -0
  100. data/lib/plugins/twitter_connect.rb +145 -0
  101. data/lib/rad/README.rdoc +5 -0
  102. data/lib/rad/arduino_plugin.rb +246 -0
  103. data/lib/rad/arduino_sketch.rb +628 -0
  104. data/lib/rad/darwin_installer.rb +23 -0
  105. data/lib/rad/generators/makefile/makefile.erb +243 -0
  106. data/lib/rad/generators/makefile/makefile.rb +38 -0
  107. data/lib/rad/hardware_library.rb +813 -0
  108. data/lib/rad/init.rb +15 -0
  109. data/lib/rad/linux_installer.rb +132 -0
  110. data/lib/rad/progressbar.rb +236 -0
  111. data/lib/rad/rad_processor.rb +128 -0
  112. data/lib/rad/rad_rewriter.rb +94 -0
  113. data/lib/rad/rad_type_checker.rb +26 -0
  114. data/lib/rad/sim/arduino_sketch.rb +57 -0
  115. data/lib/rad/sketch_compiler.rb +47 -0
  116. data/lib/rad/tasks/build_and_make.rake +210 -0
  117. data/lib/rad/tasks/rad.rb +2 -0
  118. data/lib/rad/todo.txt +13 -0
  119. data/lib/rad/variable_processing.rb +153 -0
  120. data/lib/rad/version.rb +9 -0
  121. data/lib/rad.rb +5 -0
  122. data/scripts/txt2html +67 -0
  123. data/setup.rb +1585 -0
  124. data/spec/examples/hello_world.rb +11 -0
  125. data/spec/examples/serial_motor.rb +12 -0
  126. data/spec/models/arduino_sketch_spec.rb +82 -0
  127. data/spec/models/sketch_compiler_spec.rb +96 -0
  128. data/spec/models/spec_helper.rb +2 -0
  129. data/spec/sim/hello_world_spec.rb +42 -0
  130. data/spec/spec.opts +1 -0
  131. data/test/hello_world_test/Makefile +436 -0
  132. data/test/hello_world_test/hello_world.cpp +23 -0
  133. data/test/test_array_processing.rb +179 -0
  134. data/test/test_plugin_loading.rb +151 -0
  135. data/test/test_translation_post_processing.rb +185 -0
  136. data/test/test_variable_processing.rb +238 -0
  137. data/website/examples/assembler_test.rb.html +73 -0
  138. data/website/examples/gps_reader.rb.html +39 -0
  139. data/website/examples/hello_world.rb.html +38 -0
  140. data/website/examples/serial_motor.rb.html +41 -0
  141. data/website/index.html +178 -0
  142. data/website/index.txt +64 -0
  143. data/website/javascripts/rounded_corners_lite.inc.js +285 -0
  144. data/website/stylesheets/screen.css +169 -0
  145. data/website/template.rhtml +48 -0
  146. metadata +222 -0
@@ -0,0 +1,47 @@
1
+ # TODO:
2
+ # compilation
3
+ # gather pieces of code we need as strings
4
+ # translate non-loop methods
5
+ # do plugin stuff
6
+ # deal with examples/ exception
7
+ # manage upload process
8
+ # compose_setup should move in here entirely
9
+
10
+ # require 'arduino_sketch'
11
+
12
+ class SketchCompiler
13
+ attr_accessor :path, :body, :klass, :target_dir, :name
14
+
15
+ def initialize path_to_sketch
16
+ @path = File.expand_path(path_to_sketch)
17
+ @body = open(@path).read
18
+ @name = @path.split("/").last.split(".").first
19
+ @klass = @name.split(".").first.split("_").collect{|c| c.capitalize}.join("")
20
+ @target_dir = parent_dir
21
+ end
22
+
23
+ def parent_dir
24
+ self.path.split("/")[0..@path.split("/").length-2].join("/")
25
+ end
26
+
27
+ def build_dir
28
+ "#{self.target_dir}/#{self.name}"
29
+ end
30
+
31
+ def create_build_dir! optional_path_prefix=nil
32
+ self.target_dir = optional_path_prefix if optional_path_prefix
33
+ mkdir_p build_dir
34
+ end
35
+
36
+ def process_constants
37
+ self.body.gsub!("HIGH", "1")
38
+ self.body.gsub!("LOW", "0")
39
+ self.body.gsub!("ON", "1")
40
+ self.body.gsub!("OFF", "0")
41
+ end
42
+
43
+ def sketch_methods
44
+ self.body.scan(/^\s*def\s.\w*/).collect{ |m| m.gsub(/\s*def\s*/, "") }
45
+ end
46
+
47
+ end
@@ -0,0 +1,210 @@
1
+ require File.expand_path(File.dirname(__FILE__) + "/../init.rb")
2
+ require 'ruby_to_ansi_c'
3
+
4
+ C_VAR_TYPES = "unsigned|int|long|double|str|char|byte|bool"
5
+
6
+ # incredibly primitive tests
7
+ # rake test:compile or rake test:upload
8
+ # runs through all sketches in the example directory
9
+
10
+ def run_tests(sketch, type)
11
+ sh %{rake make:#{type} sketch=examples/#{sketch}}
12
+ end
13
+
14
+ namespace :test do
15
+
16
+ desc "iterate through all the sketches in the example directory"
17
+ task :upload => :gather do
18
+ @examples.each {|e| run_tests(e, "upload")}
19
+ end
20
+
21
+ task :compile => :gather do
22
+
23
+ @examples.each {|e| run_tests(e, "compile")}
24
+ end
25
+
26
+ desc "gather all tests"
27
+ task :gather do # => "make:upload" do
28
+ @examples = []
29
+ if ENV['sketch']
30
+ @examples << ENV['sketch']
31
+ else
32
+ Dir.entries( File.expand_path("#{RAD_ROOT}/examples/") ).each do |f|
33
+ @examples << f.split('.').first if (f =~ /\.rb$/)
34
+ end
35
+ end
36
+ end
37
+
38
+ end
39
+
40
+
41
+ namespace :make do
42
+
43
+ desc "compile the sketch and then upload it to your Arduino board"
44
+ task :upload => :compile do
45
+ if Makefile.hardware_params['physical_reset']
46
+ puts "Reset the Arduino and hit enter.\n==If your board doesn't need it, you can turn off this prompt in config/software.yml=="
47
+ STDIN.gets.chomp
48
+ end
49
+ sh %{cd #{@sketch.build_dir}; make upload}
50
+ end
51
+
52
+ desc "generate a makefile and use it to compile the .cpp"
53
+ task :compile => [:clean_sketch_dir, "build:sketch"] do # should also depend on "build:sketch"
54
+ Makefile.compose_for_sketch( @sketch.build_dir )
55
+
56
+ # not allowed? sh %{export PATH=#{Makefile.software_params[:arduino_root]}/tools/avr/bin:$PATH}
57
+ sh %{cd #{@sketch.build_dir}; make depend; make}
58
+ end
59
+
60
+ desc "generate a makefile and use it to compile the .cpp using the current .cpp file"
61
+ task :compile_cpp => ["build:sketch_dir", "build:gather_required_plugins", "build:plugin_setup", "build:setup", :clean_sketch_dir] do # should also depend on "build:sketch"
62
+ Makefile.compose_for_sketch( @sketch.build_dir )
63
+ # not allowed? sh %{export PATH=#{Makefile.software_params[:arduino_root]}/tools/avr/bin:$PATH}
64
+ sh %{cd #{@sketch.build_dir}; make depend; make}
65
+ end
66
+
67
+ desc "generate a makefile and use it to compile the .cpp and upload it using current .cpp file"
68
+ task :upload_cpp => ["build:sketch_dir", "build:gather_required_plugins", "build:plugin_setup", "build:setup", :clean_sketch_dir] do # should also depend on "build:sketch"
69
+ Makefile.compose_for_sketch( @sketch.build_dir )
70
+ # not allowed? sh %{export PATH=#{Makefile.software_params[:arduino_root]}/tools/avr/bin:$PATH}
71
+ sh %{cd #{@sketch.build_dir}; make depend; make upload}
72
+ end
73
+
74
+ task :clean_sketch_dir => ["build:file_list", "build:sketch_dir"] do
75
+ FileList.new(Dir.entries("#{@sketch.build_dir}")).exclude("#{@sketch.name}.cpp").exclude(/^\./).each do |f|
76
+ sh %{rm #{@sketch.build_dir}/#{f}}
77
+ end
78
+ end
79
+
80
+ end
81
+
82
+ namespace :build do
83
+
84
+ desc "actually build the sketch"
85
+ task :sketch => [:file_list, :sketch_dir, :gather_required_plugins, :plugin_setup, :setup] do
86
+ c_methods = []
87
+ sketch_signatures = []
88
+ # until we better understand RubyToC let's see what's happening on errors
89
+ @sketch.sketch_methods.each do |meth|
90
+ raw_rtc_meth = RADProcessor.translate(constantize(@sketch.klass), meth)
91
+ puts "Translator Error: #{raw_rtc_meth.inspect}" if raw_rtc_meth =~ /\/\/ ERROR:/
92
+ c_methods << raw_rtc_meth unless meth == "setup"
93
+ # treat the setup method differently
94
+ @additional_setup = [] if meth == "setup"
95
+ raw_rtc_meth.each {|m| @additional_setup << ArduinoSketch.add_to_setup(m) } if meth == "setup"
96
+ end
97
+ c_methods.each {|meth| sketch_signatures << "#{meth.scan(/^\w*\s?\*?\n.*\)/)[0].gsub("\n", " ")};" }
98
+ clean_c_methods = []
99
+ # remove external variables that were previously injected
100
+ c_methods.join("\n").each { |meth| clean_c_methods << ArduinoSketch.post_process_ruby_to_c_methods(meth) }
101
+ c_methods_with_timer = clean_c_methods.join.gsub(/loop\(\)\s\{/,"loop() {")
102
+ # last chance to add/change setup
103
+ @setup[2] << sketch_signatures.join("\n") unless sketch_signatures.empty?
104
+ # add special setup method to existing setup if present
105
+ if @additional_setup
106
+ @setup[2] << "void additional_setup();" # declaration
107
+ @setup[4] << "\tadditional_setup();" # call from setup
108
+ @setup[5] << @additional_setup.join("") #
109
+ end
110
+ result = "#{@setup.join( "\n" )}\n#{c_methods_with_timer}\n"
111
+ File.open("#{@sketch.build_dir}/#{@sketch.name}.cpp", "w"){|f| f << result}
112
+ end
113
+
114
+ # needs to write the library include and the method signatures
115
+ desc "build setup function"
116
+ task :setup do
117
+ eval "class #{@sketch.klass} < ArduinoSketch; end;"
118
+
119
+ @@as = HardwareLibrary.new
120
+
121
+ delegate_methods = @@as.methods - Object.new.methods
122
+ delegate_methods.reject!{|m| m == "compose_setup"}
123
+
124
+ delegate_methods.each do |meth|
125
+ constantize(@sketch.klass).module_eval <<-CODE
126
+ def self.#{meth}(*args)
127
+ @@as.#{meth}(*args)
128
+ end
129
+ CODE
130
+ end
131
+ # allow variable declaration without quotes: @foo = int
132
+ ["long","unsigned","int","byte","short"].each do |type|
133
+ constantize(@sketch.klass).module_eval <<-CODE
134
+ def self.#{type}
135
+ return "#{type}"
136
+ end
137
+ CODE
138
+ end
139
+
140
+ @sketch.process_constants
141
+
142
+ eval ArduinoSketch.pre_process(@sketch.body)
143
+ @@as.process_external_vars(constantize(@sketch.klass))
144
+ @setup = @@as.compose_setup
145
+ end
146
+
147
+ desc "add plugin methods"
148
+ task :plugin_setup do
149
+ $plugins_to_load.each do |name|
150
+ klass = name.split(".").first.split("_").collect{|c| c.capitalize}.join("")
151
+ eval "class #{klass} < ArduinoPlugin; end;"
152
+
153
+ @@ps = ArduinoPlugin.new
154
+ plugin_delegate_methods = @@ps.methods - Object.new.methods
155
+ plugin_delegate_methods.reject!{|m| m == "compose_setup"}
156
+
157
+ plugin_delegate_methods.each do |meth|
158
+ constantize(klass).module_eval <<-CODE
159
+ def self.#{meth}(*args)
160
+ @@ps.#{meth}(*args)
161
+ end
162
+ CODE
163
+ end
164
+
165
+ eval ArduinoPlugin.process(File.read("vendor/plugins/#{name}"))
166
+
167
+ end
168
+ @@no_plugins = ArduinoPlugin.new if @plugin_names.empty?
169
+ end
170
+
171
+ desc "determine which plugins to load based on use of methods in sketch"
172
+ task :gather_required_plugins do
173
+ @plugin_names.each do |name|
174
+ ArduinoPlugin.check_for_plugin_use(@sketch.body, File.read("vendor/plugins/#{name}"), name )
175
+ end
176
+ puts "#{$plugins_to_load.length} of #{$plugin_methods_hash.length} plugins are being loaded: #{$plugins_to_load.join(", ")}"
177
+ end
178
+
179
+ desc "setup target directory named after your sketch class"
180
+ task :sketch_dir => [:file_list] do
181
+ @sketch.create_build_dir!
182
+ end
183
+
184
+ task :file_list do
185
+ # take another look at this, since if the root directory name is changed, everything breaks
186
+ # perhaps we generate a constant when the project is generated an pop it here or in the init file
187
+ if ENV['sketch']
188
+ @sketch = SketchCompiler.new File.expand_path("#{ENV['sketch']}.rb")
189
+ else
190
+ # assume the only .rb file in the sketch dir is the sketch:
191
+ @sketch = SketchCompiler.new Dir.glob("#{File.expand_path(File.dirname(__FILE__))}/../../../*.rb").first
192
+ end
193
+
194
+ @plugin_names = []
195
+ Dir.entries( File.expand_path("#{RAD_ROOT}/vendor/plugins/") ).each do |f|
196
+ if (f =~ /\.rb$/)
197
+ @plugin_names << f
198
+ end
199
+ end
200
+ end
201
+ end
202
+
203
+ #yoinked from Rails
204
+ def constantize(camel_cased_word)
205
+ unless /\A(?:::)?([A-Z]\w*(?:::[A-Z]\w*)*)\z/ =~ camel_cased_word
206
+ raise NameError, "#{camel_cased_word.inspect} is not a valid constant name!"
207
+ end
208
+
209
+ Object.module_eval("::#{$1}", __FILE__, __LINE__)
210
+ end
@@ -0,0 +1,2 @@
1
+ require 'rake'
2
+ Dir["#{File.dirname(__FILE__)}/*.rake"].each { |ext| load ext }
data/lib/rad/todo.txt ADDED
@@ -0,0 +1,13 @@
1
+ TODO:
2
+ =====
3
+
4
+ Future:
5
+ - complete library system: script/install library some_library
6
+ - bin/rad:
7
+ - setup and use a ~/.rad for new project defaults
8
+ - put repository on git
9
+ - project gallery (examples with movies)
10
+ - testing framework
11
+ - implement wire lib
12
+ - subclasses of ArduinoSketch (should just work, but what are they for?)
13
+ - simulator
@@ -0,0 +1,153 @@
1
+ module ExternalVariableProcessing
2
+ # issues
3
+ # testing
4
+ # add checking for colon
5
+
6
+
7
+ ## need to clean this up
8
+ ## need to test
9
+ def process_external_vars(klass)
10
+ vars = eval "#{klass}.instance_variables"
11
+ local_vars = []
12
+ vars.each { |v| local_vars << ":#{v.gsub("@", "")}" }
13
+ loc_vars = local_vars.join(", ")
14
+ # add accessors 
15
+ klass.module_eval "class << self; attr_accessor #{loc_vars} end"
16
+ local_vars.each do |symbol|
17
+ name = symbol.gsub(":","")
18
+ t_var = eval "#{klass}.#{name}"
19
+ pre_process_vars(name, t_var)
20
+ end
21
+ end
22
+
23
+
24
+ def pre_process_vars(name, var)
25
+ # puts
26
+ # puts
27
+ case var
28
+ when Integer
29
+ # puts "pre_process: #{name}, #{var}, #{var.inspect} got #{var.class} 29"
30
+ value = var
31
+ type = "int"
32
+ post_process_vars(name, type, value)
33
+ when Float
34
+ # puts "pre_process: #{name}, #{var}, #{var.inspect} got #{var.class} 34"
35
+ value = var
36
+ type = "float"
37
+ post_process_vars(name, type, value)
38
+ when String
39
+ # puts "pre_process: #{name}, #{var.inspect} got #{var.class} on 39"
40
+ if var.match(",").nil? && var =~ /long|byte|unsigned|int|short/
41
+ # puts "pre_process #{name}, #{var.inspect} got #{var.class} level three sublevel"
42
+ type = var
43
+ value = nil
44
+ post_process_vars(name, type, value)
45
+ else
46
+ value = var.split(",").first.lstrip
47
+ type = var.split(",")[1].nil? ? nil : var.split(",")[1].lstrip
48
+ translate_variables( name , type, value )
49
+ end
50
+ when TrueClass
51
+ # puts "pre_process: #{name}, #{var}, #{var.inspect} got #{var.class} on 50"
52
+ value = 1
53
+ type = "bool"
54
+ post_process_vars(name, type, value)
55
+ when FalseClass
56
+ # puts "pre_process: #{name}, #{var}, #{var.inspect} got #{var.class} on 55"
57
+ value = 0
58
+ type = "bool"
59
+ post_process_vars(name, type, value)
60
+ when Array
61
+ post_process_arrays(name, var)
62
+ else
63
+ raise ArgumentError, "not sure what to do here... got #{name} with value #{var} which is a #{var.class}"
64
+ end
65
+ end
66
+
67
+
68
+ def translate_variables(name, type = nil, value = nil)
69
+
70
+ unless type.nil?
71
+ check_variable_type(type)
72
+ end
73
+
74
+ # classify the values
75
+ if value.class == Fixnum
76
+ # puts "translate_variables: #{name}, #{value}, #{type} is a fixnum, got #{value.class} on 74"
77
+ elsif value.class == Float
78
+ # puts "translate_variables: #{name}, #{value}, #{type} is a float, got #{value.class} on 76"
79
+ elsif value =~ /^-(\d|x)*$/
80
+ value = value.to_i
81
+ type = "int" if type.nil?
82
+ elsif value =~ /^-(\d|\.|x)*$/
83
+ value = value.to_f
84
+ unless type.nil?
85
+ raise ArgumentError, "#{value} should be a float got #{type}" unless type == "float"
86
+ end
87
+ type = "float" if type.nil?
88
+
89
+ elsif value[0,1] !~ /\d/
90
+ # puts value[0,1]
91
+ # puts "translate_variables: #{name}, #{value}, #{type} is a number of some type, got #{value.class} on 79"
92
+ type = "char*"
93
+ value = "\"#{value}\""
94
+ elsif value !~ /(\.|x)/
95
+ # puts "translate_variables: #{name}, #{value}, #{type} is an integer, got #{value.class} on 83"
96
+ value = value.to_i
97
+ type = "int" if type.nil?
98
+ elsif value =~ /(\d*\.\d*)/ # and no
99
+ # puts "translate_variables: #{name}, #{value}, #{type} is a float, got #{value.class} on 87"
100
+ value = value.to_f
101
+ type = "float"
102
+ elsif value =~ /0x\d\d/
103
+ # puts "translate_variables: #{name}, #{value}, #{type} is a byte, got #{value.class} on 91"
104
+ type = "byte"
105
+ else
106
+ raise ArgumentError, "not sure what to do with a value of #{value} with a type like #{type}"
107
+ end
108
+
109
+ post_process_vars(name, type, value)
110
+ end
111
+
112
+
113
+
114
+ def post_process_vars(name, type, value = nil)
115
+ value = " = #{value}" if value
116
+ $external_var_identifiers << "__#{name}" unless $external_var_identifiers.include?("__#{name}")
117
+ $external_vars << "#{type} __#{name}#{value};"
118
+ end
119
+
120
+ def post_process_arrays(name, var)
121
+ type = c_type(var[0])
122
+ $array_types[name] = type
123
+ assignment = var.inspect.gsub("[","{").gsub("]","}")
124
+ c_style_array = "#{type} __#{name}[] = #{assignment};"
125
+ $external_var_identifiers << "__#{name}" unless $external_var_identifiers.include?("__#{name}")
126
+ $external_array_vars << c_style_array unless $external_array_vars.include?(c_style_array)
127
+ end
128
+
129
+ def check_variable_type(type)
130
+ unless type =~ /#{C_VAR_TYPES}/
131
+ raise ArgumentError, "the following variable types are supported \n #{C_VAR_TYPES.gsub("|",", ")} got #{type}"
132
+ end
133
+ end
134
+
135
+ def c_type(typ)
136
+ type =
137
+ case typ
138
+ when Integer
139
+ "int"
140
+ when String
141
+ "char*"
142
+ when TrueClass
143
+ "bool"
144
+ when FalseClass
145
+ "bool"
146
+ else
147
+ raise "Bug! Unknown type #{typ.inspect} in c_type"
148
+ end
149
+
150
+ type
151
+ end
152
+
153
+ end
@@ -0,0 +1,9 @@
1
+ module Rad #:nodoc:
2
+ module VERSION #:nodoc:
3
+ MAJOR = 0
4
+ MINOR = 3
5
+ TINY = 1
6
+
7
+ STRING = [MAJOR, MINOR, TINY].join('.')
8
+ end
9
+ end
data/lib/rad.rb ADDED
@@ -0,0 +1,5 @@
1
+ module Rad
2
+ end
3
+
4
+ require 'rad/version'
5
+ require 'rad/init'
data/scripts/txt2html ADDED
@@ -0,0 +1,67 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'rubygems'
4
+ require 'redcloth'
5
+ require 'syntax/convertors/html'
6
+ require 'erb'
7
+ require File.dirname(__FILE__) + '/../lib/rad/version.rb'
8
+
9
+ version = Rad::VERSION::STRING
10
+ download = 'http://rubyforge.org/projects/rad'
11
+
12
+ class Fixnum
13
+ def ordinal
14
+ # teens
15
+ return 'th' if (10..19).include?(self % 100)
16
+ # others
17
+ case self % 10
18
+ when 1: return 'st'
19
+ when 2: return 'nd'
20
+ when 3: return 'rd'
21
+ else return 'th'
22
+ end
23
+ end
24
+ end
25
+
26
+ class Time
27
+ def pretty
28
+ return "#{mday}#{mday.ordinal} #{strftime('%B')} #{year}"
29
+ end
30
+ end
31
+
32
+ def convert_syntax(syntax, source)
33
+ return Syntax::Convertors::HTML.for_syntax(syntax).convert(source).gsub(%r!^<pre>|</pre>$!,'')
34
+ end
35
+
36
+ if ARGV.length >= 1
37
+ src, template = ARGV
38
+ template ||= File.dirname(__FILE__) + '/../website/template.rhtml'
39
+
40
+ else
41
+ puts("Usage: #{File.split($0).last} source.txt [template.rhtml] > output.html")
42
+ exit!
43
+ end
44
+
45
+ template = ERB.new(File.open(template).read)
46
+
47
+ title = nil
48
+ body = nil
49
+ File.open(src) do |fsrc|
50
+ title_text = fsrc.readline
51
+ body_text = fsrc.read
52
+ syntax_items = []
53
+ body_text.gsub!(%r!<(pre|code)[^>]*?syntax=['"]([^'"]+)[^>]*>(.*?)</>!m){
54
+ ident = syntax_items.length
55
+ element, syntax, source = $1, $2, $3
56
+ syntax_items << "<#{element} class='syntax'>#{convert_syntax(syntax, source)}</#{element}>"
57
+ "syntax-temp-#{ident}"
58
+ }
59
+ title = RedCloth.new(title_text).to_html.gsub(%r!<.*?>!,'').strip
60
+ body = RedCloth.new(body_text).to_html
61
+ body.gsub!(%r!(?:<pre><code>)?syntax-temp-(d+)(?:</code></pre>)?!){ syntax_items[$1.to_i] }
62
+ end
63
+ stat = File.stat(src)
64
+ created = stat.ctime
65
+ modified = stat.mtime
66
+
67
+ $stdout << template.result(binding)