blockly 7.20211209.2 → 8.0.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 (262) hide show
  1. package/blockly.d.ts +18963 -18432
  2. package/blockly.min.js +852 -844
  3. package/blockly_compressed.js +669 -664
  4. package/blockly_compressed.js.map +1 -1
  5. package/blocks/blocks.js +47 -0
  6. package/blocks/colour.js +13 -3
  7. package/blocks/lists.js +22 -13
  8. package/blocks/logic.js +13 -3
  9. package/blocks/loops.js +24 -11
  10. package/blocks/math.js +12 -3
  11. package/blocks/procedures.js +41 -27
  12. package/blocks/text.js +22 -13
  13. package/blocks/variables.js +14 -3
  14. package/blocks/variables_dynamic.js +13 -3
  15. package/blocks_compressed.js +146 -141
  16. package/blocks_compressed.js.map +1 -1
  17. package/core/block.js +1869 -1814
  18. package/core/block_drag_surface.js +201 -200
  19. package/core/block_dragger.js +377 -373
  20. package/core/block_svg.js +1593 -1479
  21. package/core/blockly.js +8 -22
  22. package/core/blocks.js +9 -2
  23. package/core/browser_events.js +22 -5
  24. package/core/bubble.js +841 -797
  25. package/core/bubble_dragger.js +213 -206
  26. package/core/bump_objects.js +2 -2
  27. package/core/clipboard.js +9 -9
  28. package/core/comment.js +353 -332
  29. package/core/common.js +46 -17
  30. package/core/component_manager.js +181 -174
  31. package/core/config.js +87 -0
  32. package/core/connection.js +595 -584
  33. package/core/connection_checker.js +242 -244
  34. package/core/connection_db.js +235 -230
  35. package/core/contextmenu.js +9 -6
  36. package/core/contextmenu_items.js +1 -2
  37. package/core/contextmenu_registry.js +93 -89
  38. package/core/css.js +474 -474
  39. package/core/delete_area.js +45 -42
  40. package/core/drag_target.js +57 -56
  41. package/core/dropdowndiv.js +153 -163
  42. package/core/events/events.js +2 -2
  43. package/core/events/events_abstract.js +89 -77
  44. package/core/events/events_block_base.js +37 -36
  45. package/core/events/events_block_change.js +130 -124
  46. package/core/events/events_block_create.js +73 -71
  47. package/core/events/events_block_delete.js +84 -82
  48. package/core/events/events_block_drag.js +50 -49
  49. package/core/events/events_block_move.js +147 -140
  50. package/core/events/events_bubble_open.js +51 -50
  51. package/core/events/events_click.js +48 -44
  52. package/core/events/events_comment_base.js +72 -69
  53. package/core/events/events_comment_change.js +63 -61
  54. package/core/events/events_comment_create.js +44 -42
  55. package/core/events/events_comment_delete.js +42 -40
  56. package/core/events/events_comment_move.js +106 -104
  57. package/core/events/events_marker_move.js +65 -64
  58. package/core/events/events_selected.js +46 -45
  59. package/core/events/events_theme_change.js +36 -35
  60. package/core/events/events_toolbox_item_select.js +46 -45
  61. package/core/events/events_trashcan_open.js +37 -36
  62. package/core/events/events_ui.js +47 -46
  63. package/core/events/events_ui_base.js +30 -29
  64. package/core/events/events_var_base.js +37 -36
  65. package/core/events/events_var_create.js +50 -48
  66. package/core/events/events_var_delete.js +50 -48
  67. package/core/events/events_var_rename.js +51 -49
  68. package/core/events/events_viewport.js +66 -65
  69. package/core/events/utils.js +29 -14
  70. package/core/events/workspace_events.js +49 -55
  71. package/core/extensions.js +4 -3
  72. package/core/field.js +1061 -997
  73. package/core/field_angle.js +462 -442
  74. package/core/field_checkbox.js +194 -182
  75. package/core/field_colour.js +519 -505
  76. package/core/field_dropdown.js +617 -598
  77. package/core/field_image.js +229 -220
  78. package/core/field_label.js +102 -91
  79. package/core/field_label_serializable.js +42 -41
  80. package/core/field_multilineinput.js +372 -358
  81. package/core/field_number.js +272 -253
  82. package/core/field_textinput.js +499 -467
  83. package/core/field_variable.js +458 -420
  84. package/core/flyout_base.js +1005 -952
  85. package/core/flyout_button.js +277 -260
  86. package/core/flyout_horizontal.js +304 -302
  87. package/core/flyout_metrics_manager.js +64 -64
  88. package/core/flyout_vertical.js +306 -300
  89. package/core/generator.js +459 -446
  90. package/core/gesture.js +829 -813
  91. package/core/grid.js +166 -163
  92. package/core/icon.js +168 -159
  93. package/core/inject.js +7 -5
  94. package/core/input.js +257 -248
  95. package/core/insertion_marker_manager.js +655 -624
  96. package/core/internal_constants.js +0 -129
  97. package/core/keyboard_nav/ast_node.js +605 -596
  98. package/core/keyboard_nav/basic_cursor.js +166 -165
  99. package/core/keyboard_nav/cursor.js +99 -97
  100. package/core/keyboard_nav/marker.js +83 -79
  101. package/core/keyboard_nav/tab_navigate_cursor.js +18 -23
  102. package/core/marker_manager.js +153 -141
  103. package/core/menu.js +377 -372
  104. package/core/menuitem.js +223 -217
  105. package/core/metrics_manager.js +403 -390
  106. package/core/mutator.js +468 -437
  107. package/core/names.js +229 -188
  108. package/core/options.js +290 -284
  109. package/core/procedures.js +29 -17
  110. package/core/registry.js +19 -16
  111. package/core/rendered_connection.js +482 -463
  112. package/core/renderers/common/block_rendering.js +9 -3
  113. package/core/renderers/common/constants.js +1119 -1112
  114. package/core/renderers/common/debug.js +14 -0
  115. package/core/renderers/common/debugger.js +338 -316
  116. package/core/renderers/common/drawer.js +380 -370
  117. package/core/renderers/common/i_path_object.js +2 -2
  118. package/core/renderers/common/info.js +626 -618
  119. package/core/renderers/common/marker_svg.js +579 -541
  120. package/core/renderers/common/path_object.js +203 -200
  121. package/core/renderers/common/renderer.js +220 -218
  122. package/core/renderers/geras/constants.js +36 -36
  123. package/core/renderers/geras/drawer.js +155 -147
  124. package/core/renderers/geras/highlight_constants.js +244 -238
  125. package/core/renderers/geras/highlighter.js +231 -179
  126. package/core/renderers/geras/info.js +392 -369
  127. package/core/renderers/geras/measurables/inline_input.js +25 -19
  128. package/core/renderers/geras/measurables/statement_input.js +23 -17
  129. package/core/renderers/geras/path_object.js +106 -121
  130. package/core/renderers/geras/renderer.js +96 -98
  131. package/core/renderers/measurables/base.js +30 -18
  132. package/core/renderers/measurables/bottom_row.js +83 -80
  133. package/core/renderers/measurables/connection.js +22 -15
  134. package/core/renderers/measurables/external_value_input.js +35 -22
  135. package/core/renderers/measurables/field.js +35 -20
  136. package/core/renderers/measurables/hat.js +18 -13
  137. package/core/renderers/measurables/icon.js +24 -17
  138. package/core/renderers/measurables/in_row_spacer.js +15 -13
  139. package/core/renderers/measurables/inline_input.js +43 -33
  140. package/core/renderers/measurables/input_connection.js +41 -28
  141. package/core/renderers/measurables/input_row.js +50 -44
  142. package/core/renderers/measurables/jagged_edge.js +14 -12
  143. package/core/renderers/measurables/next_connection.js +16 -14
  144. package/core/renderers/measurables/output_connection.js +26 -20
  145. package/core/renderers/measurables/previous_connection.js +16 -15
  146. package/core/renderers/measurables/round_corner.js +20 -18
  147. package/core/renderers/measurables/row.js +184 -168
  148. package/core/renderers/measurables/spacer_row.js +38 -23
  149. package/core/renderers/measurables/square_corner.js +18 -16
  150. package/core/renderers/measurables/statement_input.js +23 -20
  151. package/core/renderers/measurables/top_row.js +88 -85
  152. package/core/renderers/minimalist/constants.js +8 -7
  153. package/core/renderers/minimalist/drawer.js +11 -10
  154. package/core/renderers/minimalist/info.js +18 -18
  155. package/core/renderers/minimalist/renderer.js +40 -39
  156. package/core/renderers/thrasos/info.js +258 -248
  157. package/core/renderers/thrasos/renderer.js +20 -20
  158. package/core/renderers/zelos/constants.js +898 -873
  159. package/core/renderers/zelos/drawer.js +186 -169
  160. package/core/renderers/zelos/info.js +502 -479
  161. package/core/renderers/zelos/marker_svg.js +129 -115
  162. package/core/renderers/zelos/measurables/bottom_row.js +31 -30
  163. package/core/renderers/zelos/measurables/inputs.js +22 -21
  164. package/core/renderers/zelos/measurables/row_elements.js +14 -13
  165. package/core/renderers/zelos/measurables/top_row.js +34 -33
  166. package/core/renderers/zelos/path_object.js +181 -180
  167. package/core/renderers/zelos/renderer.js +91 -92
  168. package/core/scrollbar.js +759 -713
  169. package/core/scrollbar_pair.js +250 -245
  170. package/core/serialization/blocks.js +19 -9
  171. package/core/serialization/workspaces.js +3 -2
  172. package/core/shortcut_registry.js +286 -277
  173. package/core/sprites.js +31 -0
  174. package/core/theme.js +135 -141
  175. package/core/theme_manager.js +147 -143
  176. package/core/toolbox/category.js +602 -576
  177. package/core/toolbox/collapsible_category.js +226 -227
  178. package/core/toolbox/separator.js +70 -61
  179. package/core/toolbox/toolbox.js +934 -927
  180. package/core/toolbox/toolbox_item.js +115 -99
  181. package/core/tooltip.js +108 -35
  182. package/core/touch.js +8 -3
  183. package/core/touch_gesture.js +254 -251
  184. package/core/trashcan.js +606 -595
  185. package/core/utils/coordinate.js +97 -95
  186. package/core/utils/dom.js +2 -2
  187. package/core/utils/global.js +2 -0
  188. package/core/utils/rect.js +41 -37
  189. package/core/utils/sentinel.js +25 -0
  190. package/core/utils/size.js +30 -27
  191. package/core/utils/svg.js +18 -16
  192. package/core/variable_map.js +325 -341
  193. package/core/variable_model.js +55 -54
  194. package/core/variables.js +9 -2
  195. package/core/variables_dynamic.js +3 -1
  196. package/core/warning.js +126 -120
  197. package/core/widgetdiv.js +4 -4
  198. package/core/workspace.js +685 -664
  199. package/core/workspace_audio.js +124 -118
  200. package/core/workspace_comment.js +308 -298
  201. package/core/workspace_comment_svg.js +1029 -951
  202. package/core/workspace_drag_surface_svg.js +147 -140
  203. package/core/workspace_dragger.js +70 -71
  204. package/core/workspace_svg.js +2322 -2297
  205. package/core/xml.js +30 -20
  206. package/core/zoom_controls.js +431 -439
  207. package/dart_compressed.js +40 -43
  208. package/dart_compressed.js.map +1 -1
  209. package/generators/dart/colour.js +56 -64
  210. package/generators/dart/lists.js +61 -50
  211. package/generators/dart/math.js +160 -148
  212. package/generators/dart/text.js +83 -61
  213. package/generators/javascript/colour.js +37 -34
  214. package/generators/javascript/lists.js +50 -43
  215. package/generators/javascript/math.js +123 -139
  216. package/generators/javascript/text.js +67 -81
  217. package/generators/lua/colour.js +25 -23
  218. package/generators/lua/lists.js +97 -69
  219. package/generators/lua/logic.js +1 -2
  220. package/generators/lua/math.js +182 -144
  221. package/generators/lua/text.js +116 -99
  222. package/generators/php/colour.js +38 -32
  223. package/generators/php/lists.js +109 -89
  224. package/generators/php/math.js +90 -81
  225. package/generators/php/text.js +63 -61
  226. package/generators/python/colour.js +18 -18
  227. package/generators/python/lists.js +38 -30
  228. package/generators/python/loops.js +12 -8
  229. package/generators/python/math.js +104 -106
  230. package/generators/python/text.js +34 -30
  231. package/javascript_compressed.js +37 -39
  232. package/javascript_compressed.js.map +1 -1
  233. package/lua_compressed.js +39 -42
  234. package/lua_compressed.js.map +1 -1
  235. package/msg/az.js +2 -2
  236. package/msg/be.js +4 -4
  237. package/msg/cs.js +15 -15
  238. package/msg/de.js +1 -1
  239. package/msg/diq.js +1 -1
  240. package/msg/eo.js +1 -1
  241. package/msg/es.js +1 -1
  242. package/msg/fa.js +1 -1
  243. package/msg/fr.js +4 -4
  244. package/msg/he.js +1 -1
  245. package/msg/hr.js +2 -2
  246. package/msg/hy.js +2 -2
  247. package/msg/id.js +12 -12
  248. package/msg/inh.js +14 -14
  249. package/msg/ja.js +7 -7
  250. package/msg/lv.js +29 -29
  251. package/msg/pa.js +3 -3
  252. package/msg/smn.js +436 -0
  253. package/msg/te.js +1 -1
  254. package/msg/yue.js +1 -1
  255. package/msg/zh-hans.js +3 -3
  256. package/msg/zh-hant.js +3 -3
  257. package/package.json +7 -6
  258. package/php_compressed.js +38 -42
  259. package/php_compressed.js.map +1 -1
  260. package/python_compressed.js +26 -25
  261. package/python_compressed.js.map +1 -1
  262. package/blocks/all.js +0 -23
package/core/names.js CHANGED
@@ -27,23 +27,235 @@ goog.requireType('Blockly.Procedures');
27
27
 
28
28
  /**
29
29
  * Class for a database of entity names (variables, procedures, etc).
30
- * @param {string} reservedWords A comma-separated string of words that are
31
- * illegal for use as names in a language (e.g. 'new,if,this,...').
32
- * @param {string=} opt_variablePrefix Some languages need a '$' or a namespace
33
- * before all variable names (but not procedure names).
34
- * @constructor
35
30
  * @alias Blockly.Names
36
31
  */
37
- const Names = function(reservedWords, opt_variablePrefix) {
38
- this.variablePrefix_ = opt_variablePrefix || '';
39
- this.reservedDict_ = Object.create(null);
40
- if (reservedWords) {
41
- const splitWords = reservedWords.split(',');
42
- for (let i = 0; i < splitWords.length; i++) {
43
- this.reservedDict_[splitWords[i]] = true;
32
+ const Names = class {
33
+ /**
34
+ * @param {string} reservedWords A comma-separated string of words that are
35
+ * illegal for use as names in a language (e.g. 'new,if,this,...').
36
+ * @param {string=} opt_variablePrefix Some languages need a '$' or a
37
+ * namespace before all variable names (but not procedure names).
38
+ */
39
+ constructor(reservedWords, opt_variablePrefix) {
40
+ /**
41
+ * The prefix to attach to variable names in generated code.
42
+ * @type {string}
43
+ * @private
44
+ */
45
+ this.variablePrefix_ = opt_variablePrefix || '';
46
+
47
+ /**
48
+ * A dictionary of reserved words.
49
+ * @type {Object}
50
+ * @private
51
+ */
52
+ this.reservedDict_ = Object.create(null);
53
+
54
+ /**
55
+ * A map from type (e.g. name, procedure) to maps from names to generated
56
+ * names.
57
+ * @type {Object<string, Object<string, string>>}
58
+ * @private
59
+ */
60
+ this.db_ = Object.create(null);
61
+
62
+ /**
63
+ * A map from used names to booleans to avoid collisions.
64
+ * @type {Object<string, boolean>}
65
+ * @private
66
+ */
67
+ this.dbReverse_ = Object.create(null);
68
+
69
+ /**
70
+ * The variable map from the workspace, containing Blockly variable models.
71
+ * @type {?VariableMap}
72
+ * @private
73
+ */
74
+ this.variableMap_ = null;
75
+
76
+ if (reservedWords) {
77
+ const splitWords = reservedWords.split(',');
78
+ for (let i = 0; i < splitWords.length; i++) {
79
+ this.reservedDict_[splitWords[i]] = true;
80
+ }
81
+ }
82
+ this.reset();
83
+ }
84
+
85
+ /**
86
+ * Empty the database and start from scratch. The reserved words are kept.
87
+ */
88
+ reset() {
89
+ this.db_ = Object.create(null);
90
+ this.dbReverse_ = Object.create(null);
91
+ this.variableMap_ = null;
92
+ }
93
+
94
+ /**
95
+ * Set the variable map that maps from variable name to variable object.
96
+ * @param {!VariableMap} map The map to track.
97
+ */
98
+ setVariableMap(map) {
99
+ this.variableMap_ = map;
100
+ }
101
+
102
+ /**
103
+ * Get the name for a user-defined variable, based on its ID.
104
+ * This should only be used for variables of NameType VARIABLE.
105
+ * @param {string} id The ID to look up in the variable map.
106
+ * @return {?string} The name of the referenced variable, or null if there was
107
+ * no variable map or the variable was not found in the map.
108
+ * @private
109
+ */
110
+ getNameForUserVariable_(id) {
111
+ if (!this.variableMap_) {
112
+ console.warn(
113
+ 'Deprecated call to Names.prototype.getName without ' +
114
+ 'defining a variable map. To fix, add the following code in your ' +
115
+ 'generator\'s init() function:\n' +
116
+ 'Blockly.YourGeneratorName.nameDB_.setVariableMap(' +
117
+ 'workspace.getVariableMap());');
118
+ return null;
119
+ }
120
+ const variable = this.variableMap_.getVariableById(id);
121
+ if (variable) {
122
+ return variable.name;
123
+ }
124
+ return null;
125
+ }
126
+
127
+ /**
128
+ * Generate names for user variables, but only ones that are being used.
129
+ * @param {!Workspace} workspace Workspace to generate variables from.
130
+ */
131
+ populateVariables(workspace) {
132
+ const variables = Variables.allUsedVarModels(workspace);
133
+ for (let i = 0; i < variables.length; i++) {
134
+ this.getName(variables[i].getId(), NameType.VARIABLE);
135
+ }
136
+ }
137
+
138
+ /**
139
+ * Generate names for procedures.
140
+ * @param {!Workspace} workspace Workspace to generate procedures from.
141
+ */
142
+ populateProcedures(workspace) {
143
+ let procedures =
144
+ goog.module.get('Blockly.Procedures').allProcedures(workspace);
145
+ // Flatten the return vs no-return procedure lists.
146
+ procedures = procedures[0].concat(procedures[1]);
147
+ for (let i = 0; i < procedures.length; i++) {
148
+ this.getName(procedures[i][0], NameType.PROCEDURE);
149
+ }
150
+ }
151
+
152
+ /**
153
+ * Convert a Blockly entity name to a legal exportable entity name.
154
+ * @param {string} nameOrId The Blockly entity name (no constraints) or
155
+ * variable ID.
156
+ * @param {NameType|string} type The type of the name in Blockly
157
+ * ('VARIABLE', 'PROCEDURE', 'DEVELOPER_VARIABLE', etc...).
158
+ * @return {string} An entity name that is legal in the exported language.
159
+ */
160
+ getName(nameOrId, type) {
161
+ let name = nameOrId;
162
+ if (type === NameType.VARIABLE) {
163
+ const varName = this.getNameForUserVariable_(nameOrId);
164
+ if (varName) {
165
+ // Successful ID lookup.
166
+ name = varName;
167
+ }
44
168
  }
169
+ const normalizedName = name.toLowerCase();
170
+
171
+ const isVar =
172
+ type === NameType.VARIABLE || type === NameType.DEVELOPER_VARIABLE;
173
+
174
+ const prefix = isVar ? this.variablePrefix_ : '';
175
+ if (!(type in this.db_)) {
176
+ this.db_[type] = Object.create(null);
177
+ }
178
+ const typeDb = this.db_[type];
179
+ if (normalizedName in typeDb) {
180
+ return prefix + typeDb[normalizedName];
181
+ }
182
+ const safeName = this.getDistinctName(name, type);
183
+ typeDb[normalizedName] = safeName.substr(prefix.length);
184
+ return safeName;
185
+ }
186
+
187
+ /**
188
+ * Return a list of all known user-created names of a specified name type.
189
+ * @param {NameType|string} type The type of entity in Blockly
190
+ * ('VARIABLE', 'PROCEDURE', 'DEVELOPER_VARIABLE', etc...).
191
+ * @return {!Array<string>} A list of Blockly entity names (no constraints).
192
+ */
193
+ getUserNames(type) {
194
+ const typeDb = this.db_[type] || {};
195
+ return Object.keys(typeDb);
196
+ }
197
+
198
+ /**
199
+ * Convert a Blockly entity name to a legal exportable entity name.
200
+ * Ensure that this is a new name not overlapping any previously defined name.
201
+ * Also check against list of reserved words for the current language and
202
+ * ensure name doesn't collide.
203
+ * @param {string} name The Blockly entity name (no constraints).
204
+ * @param {NameType|string} type The type of entity in Blockly
205
+ * ('VARIABLE', 'PROCEDURE', 'DEVELOPER_VARIABLE', etc...).
206
+ * @return {string} An entity name that is legal in the exported language.
207
+ */
208
+ getDistinctName(name, type) {
209
+ let safeName = this.safeName_(name);
210
+ let i = '';
211
+ while (this.dbReverse_[safeName + i] ||
212
+ (safeName + i) in this.reservedDict_) {
213
+ // Collision with existing name. Create a unique name.
214
+ i = i ? i + 1 : 2;
215
+ }
216
+ safeName += i;
217
+ this.dbReverse_[safeName] = true;
218
+ const isVar =
219
+ type === NameType.VARIABLE || type === NameType.DEVELOPER_VARIABLE;
220
+ const prefix = isVar ? this.variablePrefix_ : '';
221
+ return prefix + safeName;
222
+ }
223
+
224
+ /**
225
+ * Given a proposed entity name, generate a name that conforms to the
226
+ * [_A-Za-z][_A-Za-z0-9]* format that most languages consider legal for
227
+ * variable and function names.
228
+ * @param {string} name Potentially illegal entity name.
229
+ * @return {string} Safe entity name.
230
+ * @private
231
+ */
232
+ safeName_(name) {
233
+ if (!name) {
234
+ name = Msg['UNNAMED_KEY'] || 'unnamed';
235
+ } else {
236
+ // Unfortunately names in non-latin characters will look like
237
+ // _E9_9F_B3_E4_B9_90 which is pretty meaningless.
238
+ // https://github.com/google/blockly/issues/1654
239
+ name = encodeURI(name.replace(/ /g, '_')).replace(/[^\w]/g, '_');
240
+ // Most languages don't allow names with leading numbers.
241
+ if ('0123456789'.indexOf(name[0]) !== -1) {
242
+ name = 'my_' + name;
243
+ }
244
+ }
245
+ return name;
246
+ }
247
+
248
+ /**
249
+ * Do the given two entity names refer to the same entity?
250
+ * Blockly names are case-insensitive.
251
+ * @param {string} name1 First name.
252
+ * @param {string} name2 Second name.
253
+ * @return {boolean} True if names are the same.
254
+ */
255
+ static equals(name1, name2) {
256
+ // name1.localeCompare(name2) is slower.
257
+ return name1.toLowerCase() === name2.toLowerCase();
45
258
  }
46
- this.reset();
47
259
  };
48
260
 
49
261
  /**
@@ -65,6 +277,10 @@ const NameType = {
65
277
  };
66
278
  exports.NameType = NameType;
67
279
 
280
+ // We have to export NameType here so that it is accessible under the old name
281
+ // `Blockly.Names.NameType`
282
+ Names.NameType = NameType;
283
+
68
284
  /**
69
285
  * Constant to separate developer variable names from user-defined variable
70
286
  * names when running generators.
@@ -74,179 +290,4 @@ exports.NameType = NameType;
74
290
  */
75
291
  Names.DEVELOPER_VARIABLE_TYPE = NameType.DEVELOPER_VARIABLE;
76
292
 
77
- /**
78
- * Empty the database and start from scratch. The reserved words are kept.
79
- */
80
- Names.prototype.reset = function() {
81
- this.db_ = Object.create(null);
82
- this.dbReverse_ = Object.create(null);
83
- this.variableMap_ = null;
84
- };
85
-
86
- /**
87
- * Set the variable map that maps from variable name to variable object.
88
- * @param {!VariableMap} map The map to track.
89
- */
90
- Names.prototype.setVariableMap = function(map) {
91
- this.variableMap_ = map;
92
- };
93
-
94
- /**
95
- * Get the name for a user-defined variable, based on its ID.
96
- * This should only be used for variables of NameType VARIABLE.
97
- * @param {string} id The ID to look up in the variable map.
98
- * @return {?string} The name of the referenced variable, or null if there was
99
- * no variable map or the variable was not found in the map.
100
- * @private
101
- */
102
- Names.prototype.getNameForUserVariable_ = function(id) {
103
- if (!this.variableMap_) {
104
- console.warn(
105
- 'Deprecated call to Names.prototype.getName without ' +
106
- 'defining a variable map. To fix, add the following code in your ' +
107
- 'generator\'s init() function:\n' +
108
- 'Blockly.YourGeneratorName.nameDB_.setVariableMap(' +
109
- 'workspace.getVariableMap());');
110
- return null;
111
- }
112
- const variable = this.variableMap_.getVariableById(id);
113
- if (variable) {
114
- return variable.name;
115
- }
116
- return null;
117
- };
118
-
119
- /**
120
- * Generate names for user variables, but only ones that are being used.
121
- * @param {!Workspace} workspace Workspace to generate variables from.
122
- */
123
- Names.prototype.populateVariables = function(workspace) {
124
- const variables = Variables.allUsedVarModels(workspace);
125
- for (let i = 0; i < variables.length; i++) {
126
- this.getName(variables[i].getId(), NameType.VARIABLE);
127
- }
128
- };
129
-
130
- /**
131
- * Generate names for procedures.
132
- * @param {!Workspace} workspace Workspace to generate procedures from.
133
- */
134
- Names.prototype.populateProcedures = function(workspace) {
135
- let procedures =
136
- goog.module.get('Blockly.Procedures').allProcedures(workspace);
137
- // Flatten the return vs no-return procedure lists.
138
- procedures = procedures[0].concat(procedures[1]);
139
- for (let i = 0; i < procedures.length; i++) {
140
- this.getName(procedures[i][0], NameType.PROCEDURE);
141
- }
142
- };
143
-
144
- /**
145
- * Convert a Blockly entity name to a legal exportable entity name.
146
- * @param {string} nameOrId The Blockly entity name (no constraints) or
147
- * variable ID.
148
- * @param {NameType|string} type The type of the name in Blockly
149
- * ('VARIABLE', 'PROCEDURE', 'DEVELOPER_VARIABLE', etc...).
150
- * @return {string} An entity name that is legal in the exported language.
151
- */
152
- Names.prototype.getName = function(nameOrId, type) {
153
- let name = nameOrId;
154
- if (type === NameType.VARIABLE) {
155
- const varName = this.getNameForUserVariable_(nameOrId);
156
- if (varName) {
157
- // Successful ID lookup.
158
- name = varName;
159
- }
160
- }
161
- const normalizedName = name.toLowerCase();
162
-
163
- const isVar =
164
- type === NameType.VARIABLE || type === NameType.DEVELOPER_VARIABLE;
165
-
166
- const prefix = isVar ? this.variablePrefix_ : '';
167
- if (!(type in this.db_)) {
168
- this.db_[type] = Object.create(null);
169
- }
170
- const typeDb = this.db_[type];
171
- if (normalizedName in typeDb) {
172
- return prefix + typeDb[normalizedName];
173
- }
174
- const safeName = this.getDistinctName(name, type);
175
- typeDb[normalizedName] = safeName.substr(prefix.length);
176
- return safeName;
177
- };
178
-
179
- /**
180
- * Return a list of all known user-created names of a specified name type.
181
- * @param {NameType|string} type The type of entity in Blockly
182
- * ('VARIABLE', 'PROCEDURE', 'DEVELOPER_VARIABLE', etc...).
183
- * @return {!Array<string>} A list of Blockly entity names (no constraints).
184
- */
185
- Names.prototype.getUserNames = function(type) {
186
- const typeDb = this.db_[type] || {};
187
- return Object.keys(typeDb);
188
- };
189
-
190
- /**
191
- * Convert a Blockly entity name to a legal exportable entity name.
192
- * Ensure that this is a new name not overlapping any previously defined name.
193
- * Also check against list of reserved words for the current language and
194
- * ensure name doesn't collide.
195
- * @param {string} name The Blockly entity name (no constraints).
196
- * @param {NameType|string} type The type of entity in Blockly
197
- * ('VARIABLE', 'PROCEDURE', 'DEVELOPER_VARIABLE', etc...).
198
- * @return {string} An entity name that is legal in the exported language.
199
- */
200
- Names.prototype.getDistinctName = function(name, type) {
201
- let safeName = this.safeName_(name);
202
- let i = '';
203
- while (this.dbReverse_[safeName + i] ||
204
- (safeName + i) in this.reservedDict_) {
205
- // Collision with existing name. Create a unique name.
206
- i = i ? i + 1 : 2;
207
- }
208
- safeName += i;
209
- this.dbReverse_[safeName] = true;
210
- const isVar =
211
- type === NameType.VARIABLE || type === NameType.DEVELOPER_VARIABLE;
212
- const prefix = isVar ? this.variablePrefix_ : '';
213
- return prefix + safeName;
214
- };
215
-
216
- /**
217
- * Given a proposed entity name, generate a name that conforms to the
218
- * [_A-Za-z][_A-Za-z0-9]* format that most languages consider legal for
219
- * variable and function names.
220
- * @param {string} name Potentially illegal entity name.
221
- * @return {string} Safe entity name.
222
- * @private
223
- */
224
- Names.prototype.safeName_ = function(name) {
225
- if (!name) {
226
- name = Msg['UNNAMED_KEY'] || 'unnamed';
227
- } else {
228
- // Unfortunately names in non-latin characters will look like
229
- // _E9_9F_B3_E4_B9_90 which is pretty meaningless.
230
- // https://github.com/google/blockly/issues/1654
231
- name = encodeURI(name.replace(/ /g, '_')).replace(/[^\w]/g, '_');
232
- // Most languages don't allow names with leading numbers.
233
- if ('0123456789'.indexOf(name[0]) !== -1) {
234
- name = 'my_' + name;
235
- }
236
- }
237
- return name;
238
- };
239
-
240
- /**
241
- * Do the given two entity names refer to the same entity?
242
- * Blockly names are case-insensitive.
243
- * @param {string} name1 First name.
244
- * @param {string} name2 Second name.
245
- * @return {boolean} True if names are the same.
246
- */
247
- Names.equals = function(name1, name2) {
248
- // name1.localeCompare(name2) is slower.
249
- return name1.toLowerCase() === name2.toLowerCase();
250
- };
251
-
252
293
  exports.Names = Names;