img_to_script 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (79) hide show
  1. checksums.yaml +7 -0
  2. data/.rubocop.yml +25 -0
  3. data/.vscode/launch.json +21 -0
  4. data/CHANGELOG.md +7 -0
  5. data/LICENSE.txt +21 -0
  6. data/README.md +271 -0
  7. data/Rakefile +16 -0
  8. data/img_to_script.gemspec +41 -0
  9. data/lib/img_to_script/abs_token_type.rb +33 -0
  10. data/lib/img_to_script/abstract_token/abs_func.rb +19 -0
  11. data/lib/img_to_script/abstract_token/abstract_token.rb +23 -0
  12. data/lib/img_to_script/abstract_token/assign_value.rb +20 -0
  13. data/lib/img_to_script/abstract_token/clear_screen.rb +16 -0
  14. data/lib/img_to_script/abstract_token/data_read.rb +19 -0
  15. data/lib/img_to_script/abstract_token/data_store.rb +19 -0
  16. data/lib/img_to_script/abstract_token/draw_chunk_by_hex_value.rb +19 -0
  17. data/lib/img_to_script/abstract_token/draw_line_by_abs_coords.rb +22 -0
  18. data/lib/img_to_script/abstract_token/draw_pixel_by_abs_coords.rb +20 -0
  19. data/lib/img_to_script/abstract_token/go_to.rb +19 -0
  20. data/lib/img_to_script/abstract_token/if_condition.rb +20 -0
  21. data/lib/img_to_script/abstract_token/loop_begin.rb +21 -0
  22. data/lib/img_to_script/abstract_token/loop_end.rb +19 -0
  23. data/lib/img_to_script/abstract_token/math_add.rb +20 -0
  24. data/lib/img_to_script/abstract_token/math_greater_than.rb +20 -0
  25. data/lib/img_to_script/abstract_token/math_mult.rb +20 -0
  26. data/lib/img_to_script/abstract_token/math_sub.rb +20 -0
  27. data/lib/img_to_script/abstract_token/move_point_to_abs_coords.rb +20 -0
  28. data/lib/img_to_script/abstract_token/parentheses.rb +19 -0
  29. data/lib/img_to_script/abstract_token/program_begin.rb +16 -0
  30. data/lib/img_to_script/abstract_token/program_end.rb +16 -0
  31. data/lib/img_to_script/abstract_token/remark.rb +19 -0
  32. data/lib/img_to_script/abstract_token/sign_func.rb +19 -0
  33. data/lib/img_to_script/abstract_token/wait.rb +19 -0
  34. data/lib/img_to_script/abstract_token.rb +8 -0
  35. data/lib/img_to_script/container.rb +26 -0
  36. data/lib/img_to_script/current_line_placeholder.rb +40 -0
  37. data/lib/img_to_script/formatter.rb +34 -0
  38. data/lib/img_to_script/generators/generator.rb +134 -0
  39. data/lib/img_to_script/generators/hex_mask/default.rb +24 -0
  40. data/lib/img_to_script/generators/hex_mask/enhanced.rb +220 -0
  41. data/lib/img_to_script/generators/hex_mask/hex_mask.rb +100 -0
  42. data/lib/img_to_script/generators/hex_mask.rb +13 -0
  43. data/lib/img_to_script/generators/run_length_encoding/horizontal.rb +78 -0
  44. data/lib/img_to_script/generators/run_length_encoding/run_length_encoding.rb +304 -0
  45. data/lib/img_to_script/generators/run_length_encoding/vertical.rb +79 -0
  46. data/lib/img_to_script/generators/run_length_encoding.rb +10 -0
  47. data/lib/img_to_script/generators/segmental/data_read_draw/data_read_draw.rb +70 -0
  48. data/lib/img_to_script/generators/segmental/data_read_draw/horizontal.rb +54 -0
  49. data/lib/img_to_script/generators/segmental/data_read_draw/vertical.rb +54 -0
  50. data/lib/img_to_script/generators/segmental/data_read_draw.rb +18 -0
  51. data/lib/img_to_script/generators/segmental/direct_draw/direct_draw.rb +62 -0
  52. data/lib/img_to_script/generators/segmental/direct_draw/horizontal.rb +16 -0
  53. data/lib/img_to_script/generators/segmental/direct_draw/vertical.rb +16 -0
  54. data/lib/img_to_script/generators/segmental/direct_draw.rb +12 -0
  55. data/lib/img_to_script/generators/segmental/horizontal_mixin.rb +32 -0
  56. data/lib/img_to_script/generators/segmental/segmental.rb +101 -0
  57. data/lib/img_to_script/generators/segmental/vertical_mixin.rb +38 -0
  58. data/lib/img_to_script/generators/segmental.rb +10 -0
  59. data/lib/img_to_script/generators.rb +27 -0
  60. data/lib/img_to_script/import.rb +5 -0
  61. data/lib/img_to_script/language_token.rb +8 -0
  62. data/lib/img_to_script/languages/mk90_basic/formatters/formatter.rb +49 -0
  63. data/lib/img_to_script/languages/mk90_basic/formatters/minificator.rb +316 -0
  64. data/lib/img_to_script/languages/mk90_basic/formatters/sliceable_tokens_mixin.rb +15 -0
  65. data/lib/img_to_script/languages/mk90_basic/formatters.rb +13 -0
  66. data/lib/img_to_script/languages/mk90_basic/mk90_basic_token.rb +59 -0
  67. data/lib/img_to_script/languages/mk90_basic/translators/mixin.rb +205 -0
  68. data/lib/img_to_script/languages/mk90_basic/translators/mk90_basic_10.rb +27 -0
  69. data/lib/img_to_script/languages/mk90_basic/translators/mk90_basic_20.rb +27 -0
  70. data/lib/img_to_script/languages/mk90_basic/translators/translator.rb +205 -0
  71. data/lib/img_to_script/languages/mk90_basic/translators.rb +13 -0
  72. data/lib/img_to_script/languages/mk90_basic.rb +17 -0
  73. data/lib/img_to_script/languages.rb +10 -0
  74. data/lib/img_to_script/task.rb +26 -0
  75. data/lib/img_to_script/translator.rb +31 -0
  76. data/lib/img_to_script/version.rb +5 -0
  77. data/lib/img_to_script.rb +19 -0
  78. data/sig/img_to_script.rbs +4 -0
  79. metadata +204 -0
@@ -0,0 +1,316 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ImgToScript
4
+ module Languages
5
+ module MK90Basic
6
+ module Formatters
7
+ #
8
+ # The aim of the minificator is to make the output as compact as
9
+ # possible, and so to save space at the MPO-10 cart.
10
+ #
11
+ # The minificator:
12
+ # 1. doesn't put spaces (as MK90's BASIC lexer ignores them);
13
+ # 2. adds as many characters to a line as possible.
14
+ # This minimizes the number of CR+LF sequences.
15
+ #
16
+ class Minificator < Formatter
17
+ SEP_BETWEEN_STATEMENTS = ":"
18
+
19
+ private
20
+
21
+ #
22
+ # Append a token to the BASIC script.
23
+ #
24
+ def _append_token(token)
25
+ @token = token
26
+ @placeholders_idx = _get_placeholders_idx
27
+
28
+ _format_token_arguments
29
+
30
+ if @token.sliceable
31
+ _process_sliceable_token
32
+ else
33
+ _process_non_sliceable_token
34
+ end
35
+ end
36
+
37
+ #
38
+ # Process a token with a statement that can be splitted and
39
+ # continued on a next line.
40
+ #
41
+ def _process_sliceable_token
42
+ @current_arg_idx = 0
43
+
44
+ _append_arg until @current_arg_idx == @args.length
45
+ end
46
+
47
+ #
48
+ # Append an argument of the sliceable statement.
49
+ #
50
+ def _append_arg
51
+ @current_arg = @args[@current_arg_idx].to_s
52
+
53
+ if @current_arg_idx.zero?
54
+ # The first argument should be handled differently (since a
55
+ # keyword should be prepended first).
56
+ _append_arg_with_keyword
57
+ else
58
+ # The rest arguments are processed in a batch.
59
+ _append_rest_sliceable_args
60
+ end
61
+
62
+ @current_arg_idx += 1
63
+ end
64
+
65
+ #
66
+ # Append the keyword of a sliceable statement, when attach an
67
+ # argument to it.
68
+ #
69
+ # There are two situations when this happens:
70
+ # 1. the argument is the first in the arguments array;
71
+ # 2. the statement was splitted and should be continued on a new line.
72
+ #
73
+ def _append_arg_with_keyword
74
+ statement = "#{@token.keyword}#{@current_arg}"
75
+
76
+ if @token.require_nl
77
+ # Statement explicitly demands to be on a new line
78
+ _append_to_new_line(statement)
79
+ return
80
+ end
81
+
82
+ if _calc_sliceable_statement_keyword_length <= @max_chars_per_line
83
+ # There is enough space in the current BASIC line to add a new keyword + the next arg. pair.
84
+ _append_to_current_line(statement)
85
+ else
86
+ # There is not enough space in the current BASIC line, create a new one.
87
+ _append_to_new_line(statement)
88
+ end
89
+ end
90
+
91
+ def _append_rest_sliceable_args
92
+ if _calc_current_line_plus_argument_length <= @max_chars_per_line
93
+ # There is enough space in the current BASIC line to add another argument.
94
+ _append_new_argument_to_current_line
95
+ else
96
+ # There is not enough space in the current BASIC line, create a new one.
97
+ _append_arg_with_keyword
98
+ end
99
+ end
100
+
101
+ #
102
+ # Append current argument of the sliceable statement to a current line.
103
+ #
104
+ def _append_new_argument_to_current_line
105
+ @script[-1] += @token.separator + @current_arg.to_s
106
+ end
107
+
108
+ #
109
+ # Length of a current line with a current argument of the sliceable
110
+ # statement.
111
+ #
112
+ # @return [Integer]
113
+ #
114
+ def _calc_current_line_plus_argument_length
115
+ _get_current_line_content.length +
116
+ @current_arg.length +
117
+ @token.separator.length
118
+ end
119
+
120
+ #
121
+ # Process a token with a statement that cannot be splitted, i.e. it
122
+ # should be lined up within a single BASIC line.
123
+ #
124
+ def _process_non_sliceable_token
125
+ _evaluate_placeholders
126
+
127
+ if @token.require_nl
128
+ # Statement explicitly demands to be on a new line.
129
+ _append_to_new_line(_non_sliceable_statement)
130
+ else
131
+ # Statement potentially can be added to a current line.
132
+ _try_to_append_non_sliceble_to_current_line
133
+ end
134
+ end
135
+
136
+ #
137
+ # Try to append a non-sliceable statement to a current line.
138
+ #
139
+ # There are situations when it can't be done:
140
+ # 1. current line is empty (that means it is not numbered yet).
141
+ # 2. there's no enough space in the current line to append the
142
+ # statement.
143
+ #
144
+ def _try_to_append_non_sliceble_to_current_line
145
+ if _get_current_line_content.empty?
146
+ _append_to_new_line(_non_sliceable_statement)
147
+ return
148
+ end
149
+
150
+ if _calc_non_sliceable_statement_length <= @max_chars_per_line
151
+ _append_to_current_line(_non_sliceable_statement)
152
+ else
153
+ _append_to_new_line(_non_sliceable_statement)
154
+ end
155
+ end
156
+
157
+ #
158
+ # Return current BASIC line, i.e. the last element of the @script
159
+ # array.
160
+ #
161
+ # @return [String]
162
+ #
163
+ def _get_current_line_content
164
+ @script[-1] || ""
165
+ end
166
+
167
+ #
168
+ # Return a formatted non-sliceable statement.
169
+ #
170
+ # @return [String]
171
+ #
172
+ def _non_sliceable_statement
173
+ @token.keyword + @args.join(@token.separator)
174
+ end
175
+
176
+ def _update_line_num
177
+ @n_line += @line_step
178
+
179
+ # Since line number has been changed, it is required to
180
+ # re-evaluate placeholders with the updated value.
181
+ _evaluate_placeholders
182
+ end
183
+
184
+ #
185
+ # Append statement to the current BASIC line.
186
+ #
187
+ # @param [String] statement
188
+ # Statement to append in a String formatted form, e.g.: "ABS(X+L)"
189
+ #
190
+ def _append_to_current_line(statement)
191
+ @script[-1] += "#{SEP_BETWEEN_STATEMENTS}#{statement}"
192
+ end
193
+
194
+ #
195
+ # Append statement to a new BASIC line.
196
+ #
197
+ # @param [String] statement
198
+ # Statement to append in a String formatted form, e.g.: "ABS(X+L)"
199
+ #
200
+ def _append_to_new_line(statement)
201
+ # Since a new line is about to be created, the line number should
202
+ # be updated first.
203
+ _update_line_num
204
+
205
+ new_line = "#{_select_line_label}#{statement}"
206
+ @script << new_line
207
+ end
208
+
209
+ #
210
+ # @return [String]
211
+ #
212
+ def _select_line_label
213
+ @number_lines ? @n_line.to_s : ""
214
+ end
215
+
216
+ #
217
+ # Full length of a non-sliceable statement.
218
+ #
219
+ # @return [Integer]
220
+ #
221
+ def _calc_non_sliceable_statement_length
222
+ _get_current_line_content.length +
223
+ _non_sliceable_statement.length +
224
+ SEP_BETWEEN_STATEMENTS.length
225
+ end
226
+
227
+ #
228
+ # Keyword + first argument length.
229
+ #
230
+ # @return [Integer]
231
+ #
232
+ def _calc_sliceable_statement_keyword_length
233
+ _get_current_line_content.length +
234
+ @token.keyword.length +
235
+ @current_arg.length +
236
+ SEP_BETWEEN_STATEMENTS.length
237
+ end
238
+
239
+ #
240
+ # Evaluate current line number placeholders in the token's arguments.
241
+ #
242
+ def _evaluate_placeholders
243
+ @placeholders_idx.each do |i|
244
+ e = @token.args[i]
245
+ @args[i] = @n_line + e.shift * @line_step
246
+ end
247
+ end
248
+
249
+ #
250
+ # For an argument what is a token (i.e. a nested token): pass the
251
+ # argument to a new instance of the minificator, and append the
252
+ # argument in a formatted form (a String).
253
+ #
254
+ # For the arguments of other types: append as is.
255
+ #
256
+ def _format_token_arguments
257
+ @args = []
258
+ @token.args.each do |arg|
259
+ if arg.is_a?(MK90Basic::MK90BasicToken)
260
+ @args.append(_format_nested_token(arg))
261
+ else
262
+ @args.append(arg)
263
+ end
264
+ end
265
+ end
266
+
267
+ #
268
+ # Format a nested token.
269
+ #
270
+ # @return [String]
271
+ #
272
+ def _format_nested_token(token)
273
+ arr = _minificator.format(
274
+ Array(token)
275
+ )
276
+
277
+ case arr.length
278
+ when 0
279
+ # @todo: warn: minificator returned an empty arr!
280
+ ""
281
+ when 1
282
+ # ok!
283
+ arr.first
284
+ else
285
+ # @todo: warn: statement doesn't fit to a single line!
286
+ arr.first
287
+ end
288
+ end
289
+
290
+ #
291
+ # Return a minificator instance to format a nested token.
292
+ #
293
+ # @return [Minificator]
294
+ # A new Minificator instance.
295
+ #
296
+ def _minificator
297
+ Minificator.new.configure do |config|
298
+ config.number_lines = false
299
+ end
300
+ end
301
+
302
+ #
303
+ # Return array of indexes of the placeholders.
304
+ #
305
+ # @return [Array<Integer>]
306
+ #
307
+ def _get_placeholders_idx
308
+ @token.args.each_index.select do |i|
309
+ @token.args[i].is_a?(CurrentLinePlaceholder)
310
+ end
311
+ end
312
+ end
313
+ end
314
+ end
315
+ end
316
+ end
@@ -0,0 +1,15 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ImgToScript
4
+ module Languages
5
+ module MK90Basic
6
+ module Formatters
7
+ #
8
+ # Methods related to the sliceable statements.
9
+ #
10
+ module SliceableTokensMixin
11
+ end
12
+ end
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,13 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ImgToScript
4
+ module Languages
5
+ module MK90Basic
6
+ #
7
+ # Namespace for the MK90 BASIC formatters.
8
+ #
9
+ module Formatters
10
+ end
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,59 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ImgToScript
4
+ module Languages
5
+ module MK90Basic
6
+ #
7
+ # Designed to be used with the MK90 BASIC translator & formatter.
8
+ #
9
+ class MK90BasicToken < LanguageToken
10
+ attr_accessor :keyword, :args, :separator, :require_nl, :sliceable
11
+
12
+ #
13
+ # Initialize a new BASIC token.
14
+ #
15
+ # @param [String] keyword
16
+ # Statement keyword (e.g.: "PRINT", "FOR", "CLS").
17
+ #
18
+ # @param [Array<Numeric, String>] args
19
+ # Statement arguments (e.g.: %i[10 20 30 40]).
20
+ #
21
+ # @param [String] separator
22
+ # Separator between arguments. Commonly a comma or
23
+ # an 'empty' string (no separation between arguments).
24
+ #
25
+ # @param [Boolean] require_nl
26
+ # Defines if the statement should be placed on a new line.
27
+ #
28
+ # @param [Boolean] sliceable
29
+ # Defines if the statement allows to 'slice' its arguments,
30
+ # to move some of them on a new line if the expression doesn't
31
+ # fit into a current line. Examples:
32
+ #
33
+ # sliceable = true:
34
+ # | <- max. characters per line limit
35
+ # 10 DATA 1, [omitted...], 8, 9, 10, 11
36
+ # => |
37
+ # 10 DATA 1, [omitted...], 8
38
+ # 20 DATA 9, 10, 11 |
39
+ #
40
+ # sliceable = false:
41
+ # |
42
+ # 10 [omitted...]:PRINT"HELLO, WORLD!"
43
+ # => |
44
+ # 10 [omitted...] |
45
+ # 20 PRINT"HELLO, WORLD!" |
46
+ #
47
+ def initialize(keyword:, args:, separator:, require_nl:, sliceable:)
48
+ @keyword = keyword
49
+ @args = args
50
+ @separator = separator
51
+ @require_nl = require_nl
52
+ @sliceable = sliceable
53
+
54
+ super()
55
+ end
56
+ end
57
+ end
58
+ end
59
+ end
@@ -0,0 +1,205 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ImgToScript
4
+ module Languages
5
+ module MK90Basic
6
+ module Translators
7
+ # rubocop:disable Metrics/ModuleLength
8
+
9
+ #
10
+ # Shared by both MK90 BAIC v.1.0 & v.2.0.
11
+ #
12
+ module Mixin
13
+ def _abs_func(token)
14
+ _function(token, "ABS")
15
+ end
16
+
17
+ def _clear_screen(token)
18
+ _single_keyword(token, "CLS")
19
+ end
20
+
21
+ def _program_end(token)
22
+ _single_keyword(token, "END")
23
+ end
24
+
25
+ def _data_store(token)
26
+ MK90BasicToken.new(
27
+ keyword: "DATA",
28
+ args: token.data,
29
+ separator: ",",
30
+ require_nl: token.require_nl,
31
+ sliceable: true
32
+ )
33
+ end
34
+
35
+ def _data_read(token)
36
+ MK90BasicToken.new(
37
+ keyword: "READ",
38
+ args: _translate_arguments(token.var_list),
39
+ separator: ",",
40
+ require_nl: token.require_nl,
41
+ sliceable: false
42
+ )
43
+ end
44
+
45
+ def _draw_line_by_abs_coords(token)
46
+ MK90BasicToken.new(
47
+ keyword: "DRAWD",
48
+ args: _translate_arguments([
49
+ token.x0,
50
+ token.y0,
51
+ token.x1,
52
+ token.y1
53
+ ]),
54
+ separator: ",",
55
+ require_nl: token.require_nl,
56
+ sliceable: false
57
+ )
58
+ end
59
+
60
+ def _draw_pixel_by_abs_coords(token)
61
+ MK90BasicToken.new(
62
+ keyword: "DRAWH",
63
+ args: _translate_arguments([
64
+ token.x,
65
+ token.y
66
+ ]),
67
+ separator: ",",
68
+ require_nl: token.require_nl,
69
+ sliceable: false
70
+ )
71
+ end
72
+
73
+ def _draw_chunk_by_hex_value(token)
74
+ MK90BasicToken.new(
75
+ keyword: "DRAWM",
76
+ args: token.hex_values,
77
+ separator: "",
78
+ require_nl: token.require_nl,
79
+ sliceable: true
80
+ )
81
+ end
82
+
83
+ def _math_add(token)
84
+ _math_operation(token, "+")
85
+ end
86
+
87
+ def _math_greater_than(token)
88
+ _math_operation(token, ">")
89
+ end
90
+
91
+ def _math_sub(token)
92
+ _math_operation(token, "-")
93
+ end
94
+
95
+ def _math_mult(token)
96
+ _math_operation(token, "*")
97
+ end
98
+
99
+ def _move_point_to_abs_coords(token)
100
+ MK90BasicToken.new(
101
+ keyword: "DRAWO",
102
+ args: _translate_arguments([
103
+ token.x,
104
+ token.y
105
+ ]),
106
+ separator: ",",
107
+ require_nl: token.require_nl,
108
+ sliceable: false
109
+ )
110
+ end
111
+
112
+ def _go_to(token)
113
+ MK90BasicToken.new(
114
+ keyword: "GOTO",
115
+ args: _translate_arguments([
116
+ token.line
117
+ ]),
118
+ separator: "",
119
+ require_nl: token.require_nl,
120
+ sliceable: false
121
+ )
122
+ end
123
+
124
+ def _loop_begin(token)
125
+ MK90BasicToken.new(
126
+ keyword: "FOR",
127
+ args: _translate_arguments([
128
+ token.var_name,
129
+ "=",
130
+ token.start_value,
131
+ "TO",
132
+ token.end_value
133
+ ]),
134
+ separator: "",
135
+ require_nl: token.require_nl,
136
+ sliceable: false
137
+ )
138
+ end
139
+
140
+ def _sign_func(token)
141
+ _function(token, "SGN")
142
+ end
143
+
144
+ def _parentheses(token)
145
+ _function(token, "")
146
+ end
147
+
148
+ def _loop_end(token)
149
+ MK90BasicToken.new(
150
+ keyword: "NEXT",
151
+ args: _translate_arguments(
152
+ [
153
+ token.var_name
154
+ ]
155
+ ),
156
+ separator: "",
157
+ require_nl: token.require_nl,
158
+ sliceable: false
159
+ )
160
+ end
161
+
162
+ def _if_condition(token)
163
+ MK90BasicToken.new(
164
+ keyword: "IF",
165
+ args: _translate_arguments([
166
+ token.expression,
167
+ "THEN",
168
+ token.consequent
169
+ ]),
170
+ separator: "",
171
+ require_nl: token.require_nl,
172
+ sliceable: false
173
+ )
174
+ end
175
+
176
+ def _wait(token)
177
+ MK90BasicToken.new(
178
+ keyword: "WAIT",
179
+ args: _translate_arguments([
180
+ token.time
181
+ ]),
182
+ separator: "",
183
+ require_nl: token.require_nl,
184
+ sliceable: false
185
+ )
186
+ end
187
+
188
+ def _remark(token)
189
+ MK90BasicToken.new(
190
+ keyword: "REM",
191
+ args: [
192
+ token.text
193
+ ],
194
+ separator: "",
195
+ require_nl: token.require_nl,
196
+ sliceable: false
197
+ )
198
+ end
199
+ end
200
+
201
+ # rubocop:enable Metrics/ModuleLength
202
+ end
203
+ end
204
+ end
205
+ end
@@ -0,0 +1,27 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ImgToScript
4
+ module Languages
5
+ module MK90Basic
6
+ module Translators
7
+ #
8
+ # Translates abstract tokens to the MK90 BASIC v.1.0 statements.
9
+ #
10
+ class MK90Basic10 < Translator
11
+ private
12
+
13
+ # MK90 BASIC v1.0 - requires the "LET" keyword
14
+ def _assign_value(token)
15
+ MK90BasicToken.new(
16
+ keyword: "LET",
17
+ args: _translate_arguments([token.left, "=", token.right]),
18
+ separator: "",
19
+ require_nl: token.require_nl,
20
+ sliceable: false
21
+ )
22
+ end
23
+ end
24
+ end
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,27 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ImgToScript
4
+ module Languages
5
+ module MK90Basic
6
+ module Translators
7
+ #
8
+ # Translates abstract tokens to the MK90 BASIC v.2.0 statements.
9
+ #
10
+ class MK90Basic20 < Translator
11
+ private
12
+
13
+ # MK90 BASIC v2.0 - doesn't require the "LET" keyword
14
+ def _assign_value(token)
15
+ MK90BasicToken.new(
16
+ keyword: "",
17
+ args: _translate_arguments([token.left, "=", token.right]),
18
+ separator: "",
19
+ require_nl: token.require_nl,
20
+ sliceable: false
21
+ )
22
+ end
23
+ end
24
+ end
25
+ end
26
+ end
27
+ end