prthm11 commited on
Commit
fcc81f6
·
verified ·
1 Parent(s): b118ba7

Delete utils/block_function.py

Browse files
Files changed (1) hide show
  1. utils/block_function.py +0 -1147
utils/block_function.py DELETED
@@ -1,1147 +0,0 @@
1
- import json
2
- import copy
3
- import re
4
-
5
- def generate_blocks_from_opcodes(opcode_counts, all_block_definitions):
6
- """
7
- Generates a dictionary of Scratch-like blocks based on a list of opcodes and a reference block definition.
8
- It now correctly links parent and menu blocks using their generated unique keys, and handles various block categories.
9
- It ensures that menu blocks are only generated as children of their respective parent blocks.
10
-
11
- Args:
12
- opcode_counts (list): An array of objects, each with an 'opcode' and 'count' property.
13
- Example: [{"opcode": "motion_gotoxy", "count": 1}]
14
- all_block_definitions (dict): A comprehensive dictionary containing definitions for all block types.
15
-
16
- Returns:
17
- tuple: A tuple containing:
18
- - dict: A JSON object where keys are generated block IDs and values are the block definitions.
19
- - dict: The opcode_occurrences dictionary for consistent unique key generation across functions.
20
- """
21
- generated_blocks = {}
22
- opcode_occurrences = {} # To keep track of how many times each opcode (main or menu) has been used for unique keys
23
-
24
- # Define explicit parent-menu relationships for linking purposes
25
- # This maps main_opcode -> list of (input_field_name, menu_opcode)
26
- explicit_menu_links = {
27
- "motion_goto": [("TO", "motion_goto_menu")],
28
- "motion_glideto": [("TO", "motion_glideto_menu")],
29
- "motion_pointtowards": [("TOWARDS", "motion_pointtowards_menu")],
30
- "sensing_keypressed": [("KEY_OPTION", "sensing_keyoptions")],
31
- "sensing_of": [("OBJECT", "sensing_of_object_menu")],
32
- "sensing_touchingobject": [("TOUCHINGOBJECTMENU", "sensing_touchingobjectmenu")],
33
- "control_create_clone_of": [("CLONE_OPTION", "control_create_clone_of_menu")],
34
- "sound_play": [("SOUND_MENU", "sound_sounds_menu")],
35
- "sound_playuntildone": [("SOUND_MENU", "sound_sounds_menu")],
36
- "looks_switchcostumeto": [("COSTUME", "looks_costume")],
37
- "looks_switchbackdropto": [("BACKDROP", "looks_backdrops")],
38
- }
39
-
40
- # --- Step 1: Process explicitly requested opcodes and generate their instances and associated menus ---
41
- for item in opcode_counts:
42
- opcode = item.get("opcode")
43
- count = item.get("count", 1)
44
-
45
- if not opcode:
46
- print("Warning: Skipping item with missing 'opcode'.")
47
- continue
48
-
49
- if opcode not in all_block_definitions:
50
- print(f"Warning: Opcode '{opcode}' not found in all_block_definitions. Skipping.")
51
- continue
52
-
53
- for _ in range(count):
54
- # Increment occurrence count for the current main opcode
55
- opcode_occurrences[opcode] = opcode_occurrences.get(opcode, 0) + 1
56
- main_block_instance_num = opcode_occurrences[opcode]
57
-
58
- main_block_unique_key = f"{opcode}_{main_block_instance_num}"
59
-
60
- # Create a deep copy of the main block definition
61
- main_block_data = copy.deepcopy(all_block_definitions[opcode])
62
-
63
- # Set properties for a top-level main block
64
- main_block_data["parent"] = None
65
- main_block_data["next"] = None
66
- main_block_data["topLevel"] = True
67
- main_block_data["shadow"] = False # Main blocks are typically not shadows
68
-
69
- generated_blocks[main_block_unique_key] = main_block_data
70
-
71
- # If this main block has associated menus, generate and link them now
72
- if opcode in explicit_menu_links:
73
- for input_field_name, menu_opcode_type in explicit_menu_links[opcode]:
74
- if menu_opcode_type in all_block_definitions:
75
- # Increment the occurrence for the menu block type
76
- opcode_occurrences[menu_opcode_type] = opcode_occurrences.get(menu_opcode_type, 0) + 1
77
- menu_block_instance_num = opcode_occurrences[menu_opcode_type]
78
-
79
- menu_block_data = copy.deepcopy(all_block_definitions[menu_opcode_type])
80
-
81
- # Generate a unique key for this specific menu instance
82
- menu_unique_key = f"{menu_opcode_type}_{menu_block_instance_num}"
83
-
84
- # Set properties for a shadow menu block
85
- menu_block_data["shadow"] = True
86
- menu_block_data["topLevel"] = False
87
- menu_block_data["next"] = None
88
- menu_block_data["parent"] = main_block_unique_key # Link menu to its parent instance
89
-
90
- # Update the main block's input to point to this unique menu instance
91
- if input_field_name in main_block_data.get("inputs", {}) and \
92
- isinstance(main_block_data["inputs"][input_field_name], list) and \
93
- len(main_block_data["inputs"][input_field_name]) > 1 and \
94
- main_block_data["inputs"][input_field_name][0] == 1:
95
-
96
- main_block_data["inputs"][input_field_name][1] = menu_unique_key
97
-
98
- generated_blocks[menu_unique_key] = menu_block_data
99
-
100
- return generated_blocks, opcode_occurrences
101
-
102
- def interpret_pseudo_code_and_update_blocks(generated_blocks_json, pseudo_code, all_block_definitions, opcode_occurrences):
103
- """
104
- Interprets pseudo-code to update the generated Scratch blocks, replacing static values
105
- with dynamic values and establishing stacking/nesting logic.
106
-
107
- Args:
108
- generated_blocks_json (dict): The JSON object of pre-generated blocks.
109
- pseudo_code (str): The pseudo-code string to interpret.
110
- all_block_definitions (dict): A comprehensive dictionary containing definitions for all block types.
111
- opcode_occurrences (dict): A dictionary to keep track of opcode occurrences for unique key generation.
112
-
113
- Returns:
114
- dict: The updated JSON object of Scratch blocks.
115
- """
116
- updated_blocks = copy.deepcopy(generated_blocks_json)
117
-
118
- # Helper to find a block by opcode and optionally by a unique part of its key
119
- def find_block_by_opcode(opcode_to_find, instance_num=None, parent_key=None):
120
- for key, block in updated_blocks.items():
121
- if block["opcode"] == opcode_to_find:
122
- if instance_num is not None:
123
- # Check if the key ends with the instance number
124
- if key.endswith(f"_{instance_num}"):
125
- return key, block
126
- elif parent_key is not None:
127
- # For menu blocks, check if their parent matches
128
- if block.get("shadow") and block.get("parent") == parent_key:
129
- return key, block
130
- else:
131
- # Return the first one found if no specific instance is needed
132
- return key, block
133
- return None, None
134
-
135
- # Helper to get a unique key for a new block if needed
136
- def get_unique_key(opcode_prefix):
137
- count = 1
138
- while f"{opcode_prefix}_{count}" in updated_blocks:
139
- count += 1
140
- return f"{opcode_prefix}_{count}"
141
-
142
- lines = [line.strip() for line in pseudo_code.strip().split('\n') if line.strip()]
143
-
144
- # Track the current script and nesting
145
- current_script_head = None
146
- current_parent_stack = [] # Stores (parent_block_key, indent_level, last_child_key)
147
- indent_level = 0
148
-
149
- # Create a mapping from block name patterns to their opcodes and input details
150
- # Prioritize more specific patterns first
151
- pseudo_code_to_opcode_map = {
152
- re.compile(r"when green flag clicked"): {"opcode": "event_whenflagclicked"},
153
- re.compile(r"go to x: \((.+?)\) y: \((.+?)\)"): {"opcode": "motion_gotoxy", "input_names": ["X", "Y"]},
154
- re.compile(r"set \[(.+?) v\] to (.+)"): {"opcode": "data_setvariableto", "field_name": "VARIABLE", "input_name": "VALUE"},
155
- re.compile(r"change \[(.+?) v\] by \((.+)\)"): {"opcode": "data_changevariableby", "field_name": "VARIABLE", "input_name": "VALUE"},
156
- re.compile(r"show variable \[(.+?) v\]"): {"opcode": "data_showvariable", "field_name": "VARIABLE"},
157
- re.compile(r"hide variable \[(.+?) v\]"): {"opcode": "data_hidevariable", "field_name": "VARIABLE"},
158
- re.compile(r"forever"): {"opcode": "control_forever"},
159
- re.compile(r"glide \((.+?)\) seconds to x: \((.+?)\) y: \((.+?)\)"): {"opcode": "motion_glidesecstoxy", "input_names": ["SECS", "X", "Y"]},
160
- re.compile(r"if <\((.+)\) < \((.+)\)> then"): {"opcode": "control_if", "input_names": ["OPERAND1", "OPERAND2"], "condition_opcode": "operator_lt"},
161
- re.compile(r"if <touching \[(.+?) v\]\?> then"): {"opcode": "control_if", "input_name": "TOUCHINGOBJECTMENU", "condition_opcode": "sensing_touchingobject"},
162
- re.compile(r"set x to \((.+?)\)"): {"opcode": "motion_setx", "input_name": "X"},
163
- re.compile(r"broadcast \[(.+?) v\]"): {"opcode": "event_broadcast", "input_name": "BROADCAST_INPUT"},
164
- re.compile(r"stop \[(.+?) v\]"): {"opcode": "control_stop", "field_name": "STOP_OPTION"},
165
- re.compile(r"end"): {"opcode": "end_block"}, # Special marker for script end/C-block end
166
- }
167
-
168
- # Create a reverse lookup for reporter block opcodes based on their pseudo-code representation
169
- reporter_opcode_lookup = {}
170
- for opcode, definition in all_block_definitions.items():
171
- if definition.get("block_shape") == "Reporter Block":
172
- block_name = definition.get("block_name")
173
- if block_name:
174
- # Remove parentheses for matching
175
- clean_name = block_name.replace("(", "").replace(")", "").strip()
176
- reporter_opcode_lookup[clean_name] = opcode
177
- # Handle cases like "x position" vs "(x position)"
178
- if clean_name not in reporter_opcode_lookup:
179
- reporter_opcode_lookup[clean_name] = opcode
180
-
181
- # Function to create a new block instance
182
- def create_block_instance(opcode, opcode_occurrences, parent_key=None, is_shadow=False, is_top_level=False):
183
- # Ensure unique key generation is consistent
184
- opcode_occurrences[opcode] = opcode_occurrences.get(opcode, 0) + 1
185
- unique_key = f"{opcode}_{opcode_occurrences[opcode]}"
186
-
187
- new_block = copy.deepcopy(all_block_definitions.get(opcode, {}))
188
- if not new_block:
189
- print(f"Error: Definition for opcode '{opcode}' not found.")
190
- return None, None
191
-
192
- new_block["parent"] = parent_key
193
- new_block["next"] = None # Will be set by stacking logic
194
- new_block["topLevel"] = is_top_level
195
- new_block["shadow"] = is_shadow
196
-
197
- # Clear inputs/fields to be populated by pseudo-code parsing
198
- if "inputs" in new_block:
199
- new_block["inputs"] = {k: copy.deepcopy(v) for k, v in new_block["inputs"].items()} # Deep copy inputs
200
- for input_name in new_block["inputs"]:
201
- if isinstance(new_block["inputs"][input_name], list) and len(new_block["inputs"][input_name]) > 1:
202
- # Reset input value, keep type 1 for block reference or type 4/10 for literal
203
- if new_block["inputs"][input_name][0] == 1:
204
- new_block["inputs"][input_name][1] = None # Placeholder for linked block ID
205
- else:
206
- new_block["inputs"][input_name][1] = ["", ""] # Default empty value
207
- if "fields" in new_block:
208
- new_block["fields"] = {k: copy.deepcopy(v) for k, v in new_block["fields"].items()} # Deep copy fields
209
- for field_name in new_block["fields"]:
210
- if isinstance(new_block["fields"][field_name], list) and len(new_block["fields"][field_name]) > 0:
211
- new_block["fields"][field_name][0] = "" # Reset field value
212
-
213
- updated_blocks[unique_key] = new_block
214
- return unique_key, new_block
215
-
216
- # Helper to parse input values
217
- def parse_input_value(value_str):
218
- value_str = value_str.strip()
219
- # Handle numeric values (including those with + or - prefix)
220
- if re.fullmatch(r"[-+]?\d+(\.\d+)?", value_str):
221
- return [4, value_str] # Type 4 for number
222
- # Handle string literals (e.g., "Hello!")
223
- if value_str.startswith('"') and value_str.endswith('"'):
224
- return [10, value_str.strip('"')] # Type 10 for string
225
- # Handle variable/list names (e.g., [score v], [my list v])
226
- if value_str.startswith('[') and value_str.endswith(']'):
227
- var_name = value_str[1:-1].replace(' v', '').strip()
228
- # For inputs that expect a variable, we might need a data_variable block
229
- # For now, if it's a variable reference in an input, we'll return its name.
230
- # The calling context (e.g., set variable's field vs. an input) will determine type.
231
- return [12, var_name] # Custom type 12 for variable name, to be resolved later
232
-
233
- # Handle nested reporter blocks (e.g., (x position))
234
- if value_str.startswith('(') and value_str.endswith(')'):
235
- inner_content = value_str[1:-1].strip()
236
- # Check if it's a known reporter block
237
- if inner_content in reporter_opcode_lookup:
238
- return [3, reporter_opcode_lookup[inner_content]] # Type 3 for reporter block reference
239
- # If not a known reporter, treat as a number or string
240
- if re.fullmatch(r"[-+]?\d+(\.\d+)?", inner_content):
241
- return [4, inner_content]
242
- return [10, inner_content] # Default to string if not found in reporters
243
-
244
- # Handle boolean conditions (e.g., <(x position) < (-235)>) - these are usually handled by parent regex
245
- if value_str.startswith('<') and value_str.endswith('>'):
246
- inner_condition = value_str[1:-1].strip()
247
- # This is typically handled by the regex that matched the 'if' block itself.
248
- # If this is called for a standalone boolean, it would be a reporter.
249
- for op, def_ in all_block_definitions.items():
250
- if def_.get("block_shape") == "Boolean Block" and def_.get("block_name") and \
251
- def_["block_name"].replace("<", "").replace(">", "").strip() == inner_condition:
252
- return [2, op] # Type 2 for boolean block reference
253
- return [10, inner_condition] # Default to string if not found
254
-
255
- return [10, value_str] # Default to string literal
256
-
257
-
258
- # Main parsing loop
259
- block_stack = [] # (block_key, indent_level, last_child_key_in_scope) for tracking nesting
260
-
261
- for line_idx, raw_line in enumerate(lines):
262
- current_line_indent = len(raw_line) - len(raw_line.lstrip())
263
- line = raw_line.strip()
264
-
265
- # Adjust block_stack based on current indent level
266
- while block_stack and current_line_indent <= block_stack[-1][1]:
267
- block_stack.pop()
268
-
269
- matched_block_info = None
270
- matched_values = None
271
-
272
- # Try to match the line against known block patterns
273
- for pattern_regex, info in pseudo_code_to_opcode_map.items():
274
- match = pattern_regex.match(line)
275
- if match:
276
- matched_block_info = info
277
- matched_values = match.groups()
278
- break
279
-
280
- if not matched_block_info:
281
- print(f"Warning: Could not interpret line: '{line}'")
282
- continue
283
-
284
- opcode = matched_block_info["opcode"]
285
-
286
- # Handle 'end' block separately as it signifies closing a C-block
287
- if opcode == "end_block":
288
- if block_stack:
289
- block_stack.pop() # Pop the C-block parent
290
- continue
291
-
292
- parent_key = None
293
- if block_stack:
294
- parent_key = block_stack[-1][0] # The last block on the stack is the parent
295
-
296
- # Create the new block instance
297
- new_block_key, new_block_data = create_block_instance(
298
- opcode,
299
- opcode_occurrences,
300
- parent_key=parent_key,
301
- is_top_level=(parent_key is None)
302
- )
303
- if not new_block_key:
304
- continue
305
-
306
- # Link to previous block in the same script/nesting level
307
- if block_stack:
308
- # Update the 'next' of the previous block in the current scope
309
- last_child_key_in_scope = block_stack[-1][2] if len(block_stack[-1]) > 2 else None
310
- if last_child_key_in_scope and last_child_key_in_scope in updated_blocks:
311
- updated_blocks[last_child_key_in_scope]["next"] = new_block_key
312
-
313
- # Update the last child in the current scope
314
- block_stack[-1] = (block_stack[-1][0], block_stack[-1][1], new_block_key)
315
-
316
- # Populate inputs and fields
317
- if matched_values:
318
- # Handle specific block types with their inputs/fields
319
- if opcode == "motion_gotoxy":
320
- x_val = parse_input_value(matched_values[0])
321
- y_val = parse_input_value(matched_values[1])
322
- new_block_data["inputs"]["X"][1] = x_val[1]
323
- new_block_data["inputs"]["Y"][1] = y_val[1]
324
- new_block_data["inputs"]["X"][0] = x_val[0]
325
- new_block_data["inputs"]["Y"][0] = y_val[0]
326
- elif opcode == "data_setvariableto":
327
- var_name = matched_values[0].replace(' v', '').strip()
328
- value_parsed = parse_input_value(matched_values[1])
329
- new_block_data["fields"]["VARIABLE"][0] = var_name
330
- # Assuming variable ID is generated elsewhere or can be looked up
331
- new_block_data["fields"]["VARIABLE"][1] = f"`var_{var_name}" # Placeholder for variable ID
332
- new_block_data["inputs"]["VALUE"][0] = value_parsed[0]
333
- new_block_data["inputs"]["VALUE"][1] = value_parsed[1]
334
- elif opcode == "data_showvariable":
335
- var_name = matched_values[0].replace(' v', '').strip()
336
- new_block_data["fields"]["VARIABLE"][0] = var_name
337
- new_block_data["fields"]["VARIABLE"][1] = f"`var_{var_name}" # Placeholder for variable ID
338
- elif opcode == "motion_glidesecstoxy":
339
- secs_val = parse_input_value(matched_values[0])
340
- x_val = parse_input_value(matched_values[1])
341
- y_val = parse_input_value(matched_values[2])
342
- new_block_data["inputs"]["SECS"][1] = secs_val[1]
343
- new_block_data["inputs"]["X"][1] = x_val[1]
344
- new_block_data["inputs"]["Y"][1] = y_val[1]
345
- new_block_data["inputs"]["SECS"][0] = secs_val[0]
346
- new_block_data["inputs"]["X"][0] = x_val[0]
347
- new_block_data["inputs"]["Y"][0] = y_val[0]
348
- elif opcode == "motion_setx":
349
- x_val = parse_input_value(matched_values[0])
350
- new_block_data["inputs"]["X"][1] = x_val[1]
351
- new_block_data["inputs"]["X"][0] = x_val[0]
352
- elif opcode == "control_if":
353
- condition_opcode = matched_block_info["condition_opcode"]
354
-
355
- if condition_opcode == "operator_lt":
356
- op1_str = matched_values[0].strip()
357
- op2_str = matched_values[1].strip()
358
-
359
- op1_parsed = parse_input_value(op1_str)
360
- op2_parsed = parse_input_value(op2_str)
361
-
362
- # Create operator_lt block as a shadow input for the IF condition
363
- lt_block_key, lt_block_data = create_block_instance(
364
- "operator_lt",
365
- opcode_occurrences,
366
- parent_key=new_block_key,
367
- is_shadow=True,
368
- is_top_level=False
369
- )
370
- if lt_block_key:
371
- new_block_data["inputs"]["CONDITION"][1] = lt_block_key
372
- new_block_data["inputs"]["CONDITION"][0] = 2 # Type 2 for boolean block reference
373
-
374
- # Populate operator_lt inputs
375
- if op1_parsed[0] == 3: # If it's a reporter block
376
- op1_reporter_key, op1_reporter_data = create_block_instance(
377
- op1_parsed[1], # Opcode of the reporter
378
- opcode_occurrences,
379
- parent_key=lt_block_key,
380
- is_shadow=True,
381
- is_top_level=False
382
- )
383
- if op1_reporter_key:
384
- lt_block_data["inputs"]["OPERAND1"][1] = op1_reporter_key
385
- lt_block_data["inputs"]["OPERAND1"][0] = 3
386
- else: # Literal value
387
- lt_block_data["inputs"]["OPERAND1"][1] = op1_parsed[1]
388
- lt_block_data["inputs"]["OPERAND1"][0] = op1_parsed[0]
389
-
390
- lt_block_data["inputs"]["OPERAND2"][1] = op2_parsed[1]
391
- lt_block_data["inputs"]["OPERAND2"][0] = op2_parsed[0]
392
-
393
- elif condition_opcode == "sensing_touchingobject":
394
- sprite_name = matched_values[0].replace(' v', '').strip()
395
- touching_opcode = "sensing_touchingobject"
396
-
397
- touching_block_key, touching_block_data = create_block_instance(
398
- touching_opcode,
399
- opcode_occurrences,
400
- parent_key=new_block_key,
401
- is_shadow=True,
402
- is_top_level=False
403
- )
404
- if touching_block_key:
405
- new_block_data["inputs"]["CONDITION"][1] = touching_block_key
406
- new_block_data["inputs"]["CONDITION"][0] = 2 # Type 2 for boolean block reference
407
-
408
- # Create the menu block for TOUCHINGOBJECTMENU
409
- menu_opcode = "sensing_touchingobjectmenu"
410
- menu_key, menu_data = create_block_instance(
411
- menu_opcode,
412
- opcode_occurrences,
413
- parent_key=touching_block_key,
414
- is_shadow=True,
415
- is_top_level=False
416
- )
417
- if menu_key:
418
- touching_block_data["inputs"]["TOUCHINGOBJECTMENU"][1] = menu_key
419
- touching_block_data["inputs"]["TOUCHINGOBJECTMENU"][0] = 1 # Type 1 for block reference
420
- menu_data["fields"]["TOUCHINGOBJECTMENU"][0] = sprite_name
421
- else:
422
- print(f"Warning: Could not create touching object block for condition: '{line}'")
423
-
424
-
425
- elif opcode == "control_forever":
426
- # Forever blocks are C-blocks, so push them onto the stack
427
- block_stack.append((new_block_key, current_line_indent, None)) # (parent_key, indent, last_child_key)
428
- elif opcode == "control_stop":
429
- option = matched_values[0].replace(' v', '').strip()
430
- new_block_data["fields"]["STOP_OPTION"][0] = option
431
- elif opcode == "event_broadcast":
432
- message = matched_values[0].replace(' v', '').strip()
433
- # For broadcast, the input is usually a string literal or a variable
434
- new_block_data["inputs"]["BROADCAST_INPUT"][0] = 11 # Type 11 for broadcast input (string or variable)
435
- new_block_data["inputs"]["BROADCAST_INPUT"][1] = [10, message] # Assume string literal for now
436
- # A more robust solution would create a data_variable block if it's a variable.
437
-
438
- # For C-blocks, push onto stack to track nesting
439
- if all_block_definitions[opcode].get("block_shape") == "C-Block" and opcode != "control_if": # if is handled above
440
- block_stack.append((new_block_key, current_line_indent, None)) # (parent_key, indent, last_child_key)
441
-
442
-
443
- return updated_blocks
444
-
445
- # --- Consolidated Block Definitions from all provided JSONs ---
446
- all_block_definitions = {
447
- # motion_block.json
448
- "motion_movesteps": {
449
- "opcode": "motion_movesteps", "next": None, "parent": None,
450
- "inputs": {"STEPS": [1, [4, "10"]]}, "fields": {}, "shadow": False, "topLevel": True,
451
- "x": 464, "y": -416
452
- },
453
- "motion_turnright": {
454
- "opcode": "motion_turnright", "next": None, "parent": None,
455
- "inputs": {"DEGREES": [1, [4, "15"]]}, "fields": {}, "shadow": False, "topLevel": True,
456
- "x": 467, "y": -316
457
- },
458
- "motion_turnleft": {
459
- "opcode": "motion_turnleft", "next": None, "parent": None,
460
- "inputs": {"DEGREES": [1, [4, "15"]]}, "fields": {}, "shadow": False, "topLevel": True,
461
- "x": 464, "y": -210
462
- },
463
- "motion_goto": {
464
- "opcode": "motion_goto", "next": None, "parent": None,
465
- "inputs": {"TO": [1, "motion_goto_menu"]}, "fields": {}, "shadow": False, "topLevel": True,
466
- "x": 465, "y": -95
467
- },
468
- "motion_goto_menu": {
469
- "opcode": "motion_goto_menu", "next": None, "parent": "motion_goto",
470
- "inputs": {}, "fields": {"TO": ["_random_", None]}, "shadow": True, "topLevel": False
471
- },
472
- "motion_gotoxy": {
473
- "opcode": "motion_gotoxy", "next": None, "parent": None,
474
- "inputs": {"X": [1, [4, "0"]], "Y": [1, [4, "0"]]}, "fields": {}, "shadow": False, "topLevel": True,
475
- "x": 468, "y": 12
476
- },
477
- "motion_glideto": {
478
- "opcode": "motion_glideto", "next": None, "parent": None,
479
- "inputs": {"SECS": [1, [4, "1"]], "TO": [1, "motion_glideto_menu"]}, "fields": {}, "shadow": False, "topLevel": True,
480
- "x": 470, "y": 129
481
- },
482
- "motion_glideto_menu": {
483
- "opcode": "motion_glideto_menu", "next": None, "parent": "motion_glideto",
484
- "inputs": {}, "fields": {"TO": ["_random_", None]}, "shadow": True, "topLevel": False
485
- },
486
- "motion_glidesecstoxy": {
487
- "opcode": "motion_glidesecstoxy", "next": None, "parent": None,
488
- "inputs": {"SECS": [1, [4, "1"]], "X": [1, [4, "0"]], "Y": [1, [4, "0"]]}, "fields": {}, "shadow": False, "topLevel": True,
489
- "x": 476, "y": 239
490
- },
491
- "motion_pointindirection": {
492
- "opcode": "motion_pointindirection", "next": None, "parent": None,
493
- "inputs": {"DIRECTION": [1, [8, "90"]]}, "fields": {}, "shadow": False, "topLevel": True,
494
- "x": 493, "y": 361
495
- },
496
- "motion_pointtowards": {
497
- "opcode": "motion_pointtowards", "next": None, "parent": None,
498
- "inputs": {"TOWARDS": [1, "motion_pointtowards_menu"]}, "fields": {}, "shadow": False, "topLevel": True,
499
- "x": 492, "y": 463
500
- },
501
- "motion_pointtowards_menu": {
502
- "opcode": "motion_pointtowards_menu", "next": None, "parent": "motion_pointtowards",
503
- "inputs": {}, "fields": {"TOWARDS": ["_mouse_", None]}, "shadow": True, "topLevel": False
504
- },
505
- "motion_changexby": {
506
- "opcode": "motion_changexby", "next": None, "parent": None,
507
- "inputs": {"DX": [1, [4, "10"]]}, "fields": {}, "shadow": False, "topLevel": True,
508
- "x": 851, "y": -409
509
- },
510
- "motion_setx": {
511
- "opcode": "motion_setx", "next": None, "parent": None,
512
- "inputs": {"X": [1, [4, "0"]]}, "fields": {}, "shadow": False, "topLevel": True,
513
- "x": 864, "y": -194
514
- },
515
- "motion_changeyby": {
516
- "opcode": "motion_changeyby", "next": None, "parent": None,
517
- "inputs": {"DY": [1, [4, "10"]]}, "fields": {}, "shadow": False, "topLevel": True,
518
- "x": 861, "y": -61
519
- },
520
- "motion_sety": {
521
- "opcode": "motion_sety", "next": None, "parent": None,
522
- "inputs": {"Y": [1, [4, "0"]]}, "fields": {}, "shadow": False, "topLevel": True,
523
- "x": 864, "y": 66
524
- },
525
- "motion_ifonedgebounce": {
526
- "opcode": "motion_ifonedgebounce", "next": None, "parent": None,
527
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
528
- "x": 1131, "y": -397
529
- },
530
- "motion_setrotationstyle": {
531
- "opcode": "motion_setrotationstyle", "next": None, "parent": None,
532
- "inputs": {}, "fields": {"STYLE": ["left-right", None]}, "shadow": False, "topLevel": True,
533
- "x": 1128, "y": -287
534
- },
535
- "motion_xposition": {
536
- "opcode": "motion_xposition", "next": None, "parent": None,
537
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
538
- "x": 1193, "y": -136
539
- },
540
- "motion_yposition": {
541
- "opcode": "motion_yposition", "next": None, "parent": None,
542
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
543
- "x": 1181, "y": -64
544
- },
545
- "motion_direction": {
546
- "opcode": "motion_direction", "next": None, "parent": None,
547
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
548
- "x": 1188, "y": 21
549
- },
550
-
551
- # control_block.json
552
- "control_wait": {
553
- "opcode": "control_wait", "next": None, "parent": None,
554
- "inputs": {"DURATION": [1, [5, "1"]]}, "fields": {}, "shadow": False, "topLevel": True,
555
- "x": 337, "y": 129
556
- },
557
- "control_repeat": {
558
- "opcode": "control_repeat", "next": None, "parent": None,
559
- "inputs": {"TIMES": [1, [6, "10"]]}, "fields": {}, "shadow": False, "topLevel": True,
560
- "x": 348, "y": 265
561
- },
562
- "control_forever": {
563
- "opcode": "control_forever", "next": None, "parent": None,
564
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
565
- "x": 334, "y": 439
566
- },
567
- "control_if": {
568
- "opcode": "control_if", "next": None, "parent": None,
569
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
570
- "x": 331, "y": 597
571
- },
572
- "control_if_else": {
573
- "opcode": "control_if_else", "next": None, "parent": None,
574
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
575
- "x": 335, "y": 779
576
- },
577
- "control_wait_until": {
578
- "opcode": "control_wait_until", "next": None, "parent": None,
579
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
580
- "x": 676, "y": 285
581
- },
582
- "control_repeat_until": {
583
- "opcode": "control_repeat_until", "next": None, "parent": None,
584
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
585
- "x": 692, "y": 381
586
- },
587
- "control_stop": {
588
- "opcode": "control_stop", "next": None, "parent": None,
589
- "inputs": {}, "fields": {"STOP_OPTION": ["all", None]}, "shadow": False, "topLevel": True,
590
- "x": 708, "y": 545, "mutation": {"tagName": "mutation", "children": [], "hasnext": "false"}
591
- },
592
- "control_start_as_clone": {
593
- "opcode": "control_start_as_clone", "next": None, "parent": None,
594
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
595
- "x": 665, "y": 672
596
- },
597
- "control_create_clone_of": {
598
- "opcode": "control_create_clone_of", "next": None, "parent": None,
599
- "inputs": {"CLONE_OPTION": [1, "control_create_clone_of_menu"]}, "fields": {}, "shadow": False, "topLevel": True,
600
- "x": 648, "y": 797
601
- },
602
- "control_create_clone_of_menu": {
603
- "opcode": "control_create_clone_of_menu", "next": None, "parent": "control_create_clone_of",
604
- "inputs": {}, "fields": {"CLONE_OPTION": ["_myself_", None]}, "shadow": True, "topLevel": False
605
- },
606
- "control_delete_this_clone": {
607
- "opcode": "control_delete_this_clone", "next": None, "parent": None,
608
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
609
- "x": 642, "y": 914
610
- },
611
-
612
- # data_block.json
613
- "data_setvariableto": {
614
- "opcode": "data_setvariableto", "next": None, "parent": None,
615
- "inputs": {"VALUE": [1, [10, "0"]]}, "fields": {"VARIABLE": ["my variable", "`jEk@4|i[#Fk?(8x)AV.-my variable"]}, "shadow": False, "topLevel": True,
616
- "x": 348, "y": 241
617
- },
618
- "data_changevariableby": {
619
- "opcode": "data_changevariableby", "next": None, "parent": None,
620
- "inputs": {"VALUE": [1, [4, "1"]]}, "fields": {"VARIABLE": ["my variable", "`jEk@4|i[#Fk?(8x)AV.-my variable"]}, "shadow": False, "topLevel": True,
621
- "x": 313, "y": 363
622
- },
623
- "data_showvariable": {
624
- "opcode": "data_showvariable", "next": None, "parent": None,
625
- "inputs": {}, "fields": {"VARIABLE": ["my variable", "`jEk@4|i[#Fk?(8x)AV.-my variable"]}, "shadow": False, "topLevel": True,
626
- "x": 415, "y": 473
627
- },
628
- "data_hidevariable": {
629
- "opcode": "data_hidevariable", "next": None, "parent": None,
630
- "inputs": {}, "fields": {"VARIABLE": ["my variable", "`jEk@4|i[#Fk?(8x)AV.-my variable"]}, "shadow": False, "topLevel": True,
631
- "x": 319, "y": 587
632
- },
633
- "data_addtolist": {
634
- "opcode": "data_addtolist", "next": None, "parent": None,
635
- "inputs": {"ITEM": [1, [10, "thing"]]}, "fields": {"LIST": ["MY_LIST", "o6`kIhtT{xWH+rX(5d,A"]}, "shadow": False, "topLevel": True,
636
- "x": 385, "y": 109
637
- },
638
- "data_deleteoflist": {
639
- "opcode": "data_deleteoflist", "next": None, "parent": None,
640
- "inputs": {"INDEX": [1, [7, "1"]]}, "fields": {"LIST": ["MY_LIST", "o6`kIhtT{xWH+rX(5d,A"]}, "shadow": False, "topLevel": True,
641
- "x": 384, "y": 244
642
- },
643
- "data_deletealloflist": {
644
- "opcode": "data_deletealloflist", "next": None, "parent": None,
645
- "inputs": {}, "fields": {"LIST": ["MY_LIST", "o6`kIhtT{xWH+rX(5d,A"]}, "shadow": False, "topLevel": True,
646
- "x": 387, "y": 374
647
- },
648
- "data_insertatlist": {
649
- "opcode": "data_insertatlist", "next": None, "parent": None,
650
- "inputs": {"ITEM": [1, [10, "thing"]], "INDEX": [1, [7, "1"]]}, "fields": {"LIST": ["MY_LIST", "o6`kIhtT{xWH+rX(5d,A"]}, "shadow": False, "topLevel": True,
651
- "x": 366, "y": 527
652
- },
653
- "data_replaceitemoflist": {
654
- "opcode": "data_replaceitemoflist", "next": None, "parent": None,
655
- "inputs": {"INDEX": [1, [7, "1"]], "ITEM": [1, [10, "thing"]]}, "fields": {"LIST": ["MY_LIST", "o6`kIhtT{xWH+rX(5d,A"]}, "shadow": False, "topLevel": True,
656
- "x": 365, "y": 657
657
- },
658
- "data_itemoflist": {
659
- "opcode": "data_itemoflist", "next": None, "parent": None,
660
- "inputs": {"INDEX": [1, [7, "1"]]}, "fields": {"LIST": ["MY_LIST", "o6`kIhtT{xWH+rX(5d,A"]}, "shadow": False, "topLevel": True,
661
- "x": 862, "y": 117
662
- },
663
- "data_itemnumoflist": {
664
- "opcode": "data_itemnumoflist", "next": None, "parent": None,
665
- "inputs": {"ITEM": [1, [10, "thing"]]}, "fields": {"LIST": ["MY_LIST", "o6`kIhtT{xWH+rX(5d,A"]}, "shadow": False, "topLevel": True,
666
- "x": 883, "y": 238
667
- },
668
- "data_lengthoflist": {
669
- "opcode": "data_lengthoflist", "next": None, "parent": None,
670
- "inputs": {}, "fields": {"LIST": ["MY_LIST", "o6`kIhtT{xWH+rX(5d,A"]}, "shadow": False, "topLevel": True,
671
- "x": 876, "y": 342
672
- },
673
- "data_listcontainsitem": {
674
- "opcode": "data_listcontainsitem", "next": None, "parent": None,
675
- "inputs": {"ITEM": [1, [10, "thing"]]}, "fields": {"LIST": ["MY_LIST", "o6`kIhtT{xWH+rX(5d,A"]}, "shadow": False, "topLevel": True,
676
- "x": 871, "y": 463
677
- },
678
- "data_showlist": {
679
- "opcode": "data_showlist", "next": None, "parent": None,
680
- "inputs": {}, "fields": {"LIST": ["MY_LIST", "o6`kIhtT{xWH+rX(5d,A"]}, "shadow": False, "topLevel": True,
681
- "x": 931, "y": 563
682
- },
683
- "data_hidelist": {
684
- "opcode": "data_hidelist", "next": None, "parent": None,
685
- "inputs": {}, "fields": {"LIST": ["MY_LIST", "o6`kIhtT{xWH+rX(5d,A"]}, "shadow": False, "topLevel": True,
686
- "x": 962, "y": 716
687
- },
688
-
689
- # event_block.json
690
- "event_whenflagclicked": {
691
- "opcode": "event_whenflagclicked", "next": None, "parent": None,
692
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
693
- "x": 166, "y": -422
694
- },
695
- "event_whenkeypressed": {
696
- "opcode": "event_whenkeypressed", "next": None, "parent": None,
697
- "inputs": {}, "fields": {"KEY_OPTION": ["space", None]}, "shadow": False, "topLevel": True,
698
- "x": 151, "y": -329
699
- },
700
- "event_whenthisspriteclicked": {
701
- "opcode": "event_whenthisspriteclicked", "next": None, "parent": None,
702
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
703
- "x": 156, "y": -223
704
- },
705
- "event_whenbackdropswitchesto": {
706
- "opcode": "event_whenbackdropswitchesto", "next": None, "parent": None,
707
- "inputs": {}, "fields": {"BACKDROP": ["backdrop1", None]}, "shadow": False, "topLevel": True,
708
- "x": 148, "y": -101
709
- },
710
- "event_whengreaterthan": {
711
- "opcode": "event_whengreaterthan", "next": None, "parent": None,
712
- "inputs": {"VALUE": [1, [4, "10"]]}, "fields": {"WHENGREATERTHANMENU": ["LOUDNESS", None]}, "shadow": False, "topLevel": True,
713
- "x": 150, "y": 10
714
- },
715
- "event_whenbroadcastreceived": {
716
- "opcode": "event_whenbroadcastreceived", "next": None, "parent": None,
717
- "inputs": {}, "fields": {"BROADCAST_OPTION": ["message1", "5O!nei;S$!c!=hCT}0:a"]}, "shadow": False, "topLevel": True,
718
- "x": 141, "y": 118
719
- },
720
- "event_broadcast": {
721
- "opcode": "event_broadcast", "next": None, "parent": None,
722
- "inputs": {"BROADCAST_INPUT": [1, [11, "message1", "5O!nei;S$!c!=hCT}0:a"]]}, "fields": {}, "shadow": False, "topLevel": True,
723
- "x": 151, "y": 229
724
- },
725
- "event_broadcastandwait": {
726
- "opcode": "event_broadcastandwait", "next": None, "parent": None,
727
- "inputs": {"BROADCAST_INPUT": [1, [11, "message1", "5O!nei;S$!c!=hCT}0:a"]]}, "fields": {}, "shadow": False, "topLevel": True,
728
- "x": 157, "y": 340
729
- },
730
-
731
- # look_block.json
732
- "looks_sayforsecs": {
733
- "opcode": "looks_sayforsecs", "next": None, "parent": None,
734
- "inputs": {"MESSAGE": [1, [10, "Hello!"]], "SECS": [1, [4, "2"]]}, "fields": {}, "shadow": False, "topLevel": True,
735
- "x": 408, "y": 91
736
- },
737
- "looks_say": {
738
- "opcode": "looks_say", "next": None, "parent": None,
739
- "inputs": {"MESSAGE": [1, [10, "Hello!"]]}, "fields": {}, "shadow": False, "topLevel": True,
740
- "x": 413, "y": 213
741
- },
742
- "looks_thinkforsecs": {
743
- "opcode": "looks_thinkforsecs", "next": None, "parent": None,
744
- "inputs": {"MESSAGE": [1, [10, "Hmm..."]], "SECS": [1, [4, "2"]]}, "fields": {}, "shadow": False, "topLevel": True,
745
- "x": 413, "y": 317
746
- },
747
- "looks_think": {
748
- "opcode": "looks_think", "next": None, "parent": None,
749
- "inputs": {"MESSAGE": [1, [10, "Hmm..."]]}, "fields": {}, "shadow": False, "topLevel": True,
750
- "x": 412, "y": 432
751
- },
752
- "looks_switchcostumeto": {
753
- "opcode": "looks_switchcostumeto", "next": None, "parent": None,
754
- "inputs": {"COSTUME": [1, "8;bti4wv(iH9nkOacCJ|"]}, "fields": {}, "shadow": False, "topLevel": True,
755
- "x": 411, "y": 555
756
- },
757
- "looks_costume": {
758
- "opcode": "looks_costume", "next": None, "parent": "Q#a,6LPWHqo9-0Nu*[SV",
759
- "inputs": {}, "fields": {"COSTUME": ["costume2", None]}, "shadow": True, "topLevel": False
760
- },
761
- "looks_nextcostume": {
762
- "opcode": "looks_nextcostume", "next": None, "parent": None,
763
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
764
- "x": 419, "y": 687
765
- },
766
- "looks_switchbackdropto": {
767
- "opcode": "looks_switchbackdropto", "next": None, "parent": None,
768
- "inputs": {"BACKDROP": [1, "-?yeX}29V*wd6W:unW0i"]}, "fields": {}, "shadow": False, "topLevel": True,
769
- "x": 901, "y": 91
770
- },
771
- "looks_backdrops": {
772
- "opcode": "looks_backdrops", "next": None, "parent": "`Wm^p~l[(IWzc1|wNv*.",
773
- "inputs": {}, "fields": {"BACKDROP": ["backdrop1", None]}, "shadow": True, "topLevel": False
774
- },
775
- "looks_changesizeby": {
776
- "opcode": "looks_changesizeby", "next": None, "parent": None,
777
- "inputs": {"CHANGE": [1, [4, "10"]]}, "fields": {}, "shadow": False, "topLevel": True,
778
- "x": 895, "y": 192
779
- },
780
- "looks_setsizeto": {
781
- "opcode": "looks_setsizeto", "next": None, "parent": None,
782
- "inputs": {"SIZE": [1, [4, "100"]]}, "fields": {}, "shadow": False, "topLevel": True,
783
- "x": 896, "y": 303
784
- },
785
- "looks_changeeffectby": {
786
- "opcode": "looks_changeeffectby", "next": None, "parent": None,
787
- "inputs": {"CHANGE": [1, [4, "25"]]}, "fields": {"EFFECT": ["COLOR", None]}, "shadow": False, "topLevel": True,
788
- "x": 892, "y": 416
789
- },
790
- "looks_seteffectto": {
791
- "opcode": "looks_seteffectto", "next": None, "parent": None,
792
- "inputs": {"VALUE": [1, [4, "0"]]}, "fields": {"EFFECT": ["COLOR", None]}, "shadow": False, "topLevel": True,
793
- "x": 902, "y": 527
794
- },
795
- "looks_cleargraphiceffects": {
796
- "opcode": "looks_cleargraphiceffects", "next": None, "parent": None,
797
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
798
- "x": 902, "y": 638
799
- },
800
- "looks_show": {
801
- "opcode": "looks_show", "next": None, "parent": None,
802
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
803
- "x": 908, "y": 758
804
- },
805
- "looks_hide": {
806
- "opcode": "looks_hide", "next": None, "parent": None,
807
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
808
- "x": 455, "y": 861
809
- },
810
- "looks_gotofrontback": {
811
- "opcode": "looks_gotofrontback", "next": None, "parent": None,
812
- "inputs": {}, "fields": {"FRONT_BACK": ["front", None]}, "shadow": False, "topLevel": True,
813
- "x": 853, "y": 878
814
- },
815
- "looks_goforwardbackwardlayers": {
816
- "opcode": "looks_goforwardbackwardlayers", "next": None, "parent": None,
817
- "inputs": {"NUM": [1, [7, "1"]]}, "fields": {"FORWARD_BACKWARD": ["forward", None]}, "shadow": False, "topLevel": True,
818
- "x": 851, "y": 999
819
- },
820
- "looks_costumenumbername": {
821
- "opcode": "looks_costumenumbername", "next": None, "parent": None,
822
- "inputs": {}, "fields": {"NUMBER_NAME": ["number", None]}, "shadow": False, "topLevel": True,
823
- "x": 458, "y": 1007
824
- },
825
- "looks_backdropnumbername": {
826
- "opcode": "looks_backdropnumbername", "next": None, "parent": None,
827
- "inputs": {}, "fields": {"NUMBER_NAME": ["number", None]}, "shadow": False, "topLevel": True,
828
- "x": 1242, "y": 753
829
- },
830
- "looks_size": {
831
- "opcode": "looks_size", "next": None, "parent": None,
832
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
833
- "x": 1249, "y": 876
834
- },
835
-
836
- # operator_block.json
837
- "operator_add": {
838
- "opcode": "operator_add", "next": None, "parent": None,
839
- "inputs": {"NUM1": [1, [4, ""]], "NUM2": [1, [4, ""]]}, "fields": {}, "shadow": False, "topLevel": True,
840
- "x": 128, "y": 153
841
- },
842
- "operator_subtract": {
843
- "opcode": "operator_subtract", "next": None, "parent": None,
844
- "inputs": {"NUM1": [1, [4, ""]], "NUM2": [1, [4, ""]]}, "fields": {}, "shadow": False, "topLevel": True,
845
- "x": 134, "y": 214
846
- },
847
- "operator_multiply": {
848
- "opcode": "operator_multiply", "next": None, "parent": None,
849
- "inputs": {"NUM1": [1, [4, ""]], "NUM2": [1, [4, ""]]}, "fields": {}, "shadow": False, "topLevel": True,
850
- "x": 134, "y": 278
851
- },
852
- "operator_divide": {
853
- "opcode": "operator_divide", "next": None, "parent": None,
854
- "inputs": {"NUM1": [1, [4, ""]], "NUM2": [1, [4, ""]]}, "fields": {}, "shadow": False, "topLevel": True,
855
- "x": 138, "y": 359
856
- },
857
- "operator_random": {
858
- "opcode": "operator_random", "next": None, "parent": None,
859
- "inputs": {"FROM": [1, [4, "1"]], "TO": [1, [4, "10"]]}, "fields": {}, "shadow": False, "topLevel": True,
860
- "x": 311, "y": 157
861
- },
862
- "operator_gt": {
863
- "opcode": "operator_gt", "next": None, "parent": None,
864
- "inputs": {"OPERAND1": [1, [10, ""]], "OPERAND2": [1, [10, "50"]]}, "fields": {}, "shadow": False, "topLevel": True,
865
- "x": 348, "y": 217
866
- },
867
- "operator_lt": {
868
- "opcode": "operator_lt", "next": None, "parent": None,
869
- "inputs": {"OPERAND1": [1, [10, ""]], "OPERAND2": [1, [10, "50"]]}, "fields": {}, "shadow": False, "topLevel": True,
870
- "x": 345, "y": 286
871
- },
872
- "operator_equals": {
873
- "opcode": "operator_equals", "next": None, "parent": None,
874
- "inputs": {"OPERAND1": [1, [10, ""]], "OPERAND2": [1, [10, "50"]]}, "fields": {}, "shadow": False, "topLevel": True,
875
- "x": 345, "y": 372
876
- },
877
- "operator_and": {
878
- "opcode": "operator_and", "next": None, "parent": None,
879
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
880
- "x": 701, "y": 158
881
- },
882
- "operator_or": {
883
- "opcode": "operator_or", "next": None, "parent": None,
884
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
885
- "x": 705, "y": 222
886
- },
887
- "operator_not": {
888
- "opcode": "operator_not", "next": None, "parent": None,
889
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
890
- "x": 734, "y": 283
891
- },
892
- "operator_join": {
893
- "opcode": "operator_join", "next": None, "parent": None,
894
- "inputs": {"STRING1": [1, [10, "apple "]], "STRING2": [1, [10, "banana"]]}, "fields": {}, "shadow": False, "topLevel": True,
895
- "x": 663, "y": 378
896
- },
897
- "operator_letter_of": {
898
- "opcode": "operator_letter_of", "next": None, "parent": None,
899
- "inputs": {"LETTER": [1, [6, "1"]], "STRING": [1, [10, "apple"]]}, "fields": {}, "shadow": False, "topLevel": True,
900
- "x": 664, "y": 445
901
- },
902
- "operator_length": {
903
- "opcode": "operator_length", "next": None, "parent": None,
904
- "inputs": {"STRING": [1, [10, "apple"]]}, "fields": {}, "shadow": False, "topLevel": True,
905
- "x": 664, "y": 521
906
- },
907
- "operator_contains": {
908
- "opcode": "operator_contains", "next": None, "parent": None,
909
- "inputs": {"STRING1": [1, [10, "apple"]], "STRING2": [1, [10, "a"]]}, "fields": {}, "shadow": False, "topLevel": True,
910
- "x": 634, "y": 599
911
- },
912
- "operator_mod": {
913
- "opcode": "operator_mod", "next": None, "parent": None,
914
- "inputs": {"NUM1": [1, [4, ""]], "NUM2": [1, [4, ""]]}, "fields": {}, "shadow": False, "topLevel": True,
915
- "x": 295, "y": 594
916
- },
917
- "operator_round": {
918
- "opcode": "operator_round", "next": None, "parent": None,
919
- "inputs": {"NUM": [1, [4, ""]]}, "fields": {}, "shadow": False, "topLevel": True,
920
- "x": 307, "y": 674
921
- },
922
- "operator_mathop": {
923
- "opcode": "operator_mathop", "next": None, "parent": None,
924
- "inputs": {"NUM": [1, [4, ""]]}, "fields": {"OPERATOR": ["abs", None]}, "shadow": False, "topLevel": True,
925
- "x": 280, "y": 754
926
- },
927
-
928
- # sensing_block.json
929
- "sensing_touchingobject": {
930
- "opcode": "sensing_touchingobject", "next": None, "parent": None,
931
- "inputs": {"TOUCHINGOBJECTMENU": [1, "sensing_touchingobjectmenu"]}, "fields": {}, "shadow": False, "topLevel": True,
932
- "x": 359, "y": 116
933
- },
934
- "sensing_touchingobjectmenu": {
935
- "opcode": "sensing_touchingobjectmenu", "next": None, "parent": "sensing_touchingobject",
936
- "inputs": {}, "fields": {"TOUCHINGOBJECTMENU": ["_mouse_", None]}, "shadow": True, "topLevel": False
937
- },
938
- "sensing_touchingcolor": {
939
- "opcode": "sensing_touchingcolor", "next": None, "parent": None,
940
- "inputs": {"COLOR": [1, [9, "#55b888"]]}, "fields": {}, "shadow": False, "topLevel": True,
941
- "x": 360, "y": 188
942
- },
943
- "sensing_coloristouchingcolor": {
944
- "opcode": "sensing_coloristouchingcolor", "next": None, "parent": None,
945
- "inputs": {"COLOR": [1, [9, "#d019f2"]], "COLOR2": [1, [9, "#2b0de3"]]}, "fields": {}, "shadow": False, "topLevel": True,
946
- "x": 348, "y": 277
947
- },
948
- "sensing_askandwait": {
949
- "opcode": "sensing_askandwait", "next": None, "parent": None,
950
- "inputs": {"QUESTION": [1, [10, "What's your name?"]]}, "fields": {}, "shadow": False, "topLevel": True,
951
- "x": 338, "y": 354
952
- },
953
- "sensing_answer": {
954
- "opcode": "sensing_answer", "next": None, "parent": None,
955
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
956
- "x": 782, "y": 111
957
- },
958
- "sensing_keypressed": {
959
- "opcode": "sensing_keypressed", "next": None, "parent": None,
960
- "inputs": {"KEY_OPTION": [1, "sensing_keyoptions"]}, "fields": {}, "shadow": False, "topLevel": True,
961
- "x": 762, "y": 207
962
- },
963
- "sensing_keyoptions": {
964
- "opcode": "sensing_keyoptions", "next": None, "parent": "sensing_keypressed",
965
- "inputs": {}, "fields": {"KEY_OPTION": ["space", None]}, "shadow": True, "topLevel": False
966
- },
967
- "sensing_mousedown": {
968
- "opcode": "sensing_mousedown", "next": None, "parent": None,
969
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
970
- "x": 822, "y": 422
971
- },
972
- "sensing_mousex": {
973
- "opcode": "sensing_mousex", "next": None, "parent": None,
974
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
975
- "x": 302, "y": 528
976
- },
977
- "sensing_mousey": {
978
- "opcode": "sensing_mousey", "next": None, "parent": None,
979
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
980
- "x": 668, "y": 547
981
- },
982
- "sensing_setdragmode": {
983
- "opcode": "sensing_setdragmode", "next": None, "parent": None,
984
- "inputs": {}, "fields": {"DRAG_MODE": ["draggable", None]}, "shadow": False, "topLevel": True,
985
- "x": 950, "y": 574
986
- },
987
- "sensing_loudness": {
988
- "opcode": "sensing_loudness", "next": None, "parent": None,
989
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
990
- "x": 658, "y": 703
991
- },
992
- "sensing_timer": {
993
- "opcode": "sensing_timer", "next": None, "parent": None,
994
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
995
- "x": 459, "y": 671
996
- },
997
- "sensing_resettimer": {
998
- "opcode": "sensing_resettimer", "next": None, "parent": None,
999
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
1000
- "x": 462, "y": 781
1001
- },
1002
- "sensing_of": {
1003
- "opcode": "sensing_of", "next": None, "parent": None,
1004
- "inputs": {"OBJECT": [1, "sensing_of_object_menu"]}, "fields": {"PROPERTY": ["backdrop #", None]}, "shadow": False, "topLevel": True,
1005
- "x": 997, "y": 754
1006
- },
1007
- "sensing_of_object_menu": {
1008
- "opcode": "sensing_of_object_menu", "next": None, "parent": "sensing_of",
1009
- "inputs": {}, "fields": {"OBJECT": ["_stage_", None]}, "shadow": True, "topLevel": False
1010
- },
1011
- "sensing_current": {
1012
- "opcode": "sensing_current", "next": None, "parent": None,
1013
- "inputs": {}, "fields": {"CURRENTMENU": ["YEAR", None]}, "shadow": False, "topLevel": True,
1014
- "x": 627, "y": 884
1015
- },
1016
- "sensing_dayssince2000": {
1017
- "opcode": "sensing_dayssince2000", "next": None, "parent": None,
1018
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
1019
- "x": 959, "y": 903
1020
- },
1021
- "sensing_username": {
1022
- "opcode": "sensing_username", "next": None, "parent": None,
1023
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
1024
- "x": 833, "y": 757
1025
- },
1026
-
1027
- # sound_block.json
1028
- "sound_playuntildone": {
1029
- "opcode": "sound_playuntildone", "next": None, "parent": None,
1030
- "inputs": {"SOUND_MENU": [1, "sound_sounds_menu"]}, "fields": {}, "shadow": False, "topLevel": True,
1031
- "x": 253, "y": 17
1032
- },
1033
- "sound_sounds_menu": {
1034
- "opcode": "sound_sounds_menu", "next": None, "parent": "sound_playuntildone and sound_play",
1035
- "inputs": {}, "fields": {"SOUND_MENU": ["Meow", None]}, "shadow": True, "topLevel": False
1036
- },
1037
- "sound_play": {
1038
- "opcode": "sound_play", "next": None, "parent": None,
1039
- "inputs": {"SOUND_MENU": [1, "sound_sounds_menu"]}, "fields": {}, "shadow": False, "topLevel": True,
1040
- "x": 245, "y": 122
1041
- },
1042
- "sound_stopallsounds": {
1043
- "opcode": "sound_stopallsounds", "next": None, "parent": None,
1044
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
1045
- "x": 253, "y": 245
1046
- },
1047
- "sound_changeeffectby": {
1048
- "opcode": "sound_changeeffectby", "next": None, "parent": None,
1049
- "inputs": {"VALUE": [1, [4, "10"]]}, "fields": {"EFFECT": ["PITCH", None]}, "shadow": False, "topLevel": True,
1050
- "x": 653, "y": 14
1051
- },
1052
- "sound_seteffectto": {
1053
- "opcode": "sound_seteffectto", "next": None, "parent": None,
1054
- "inputs": {"VALUE": [1, [4, "100"]]}, "fields": {"EFFECT": ["PITCH", None]}, "shadow": False, "topLevel": True,
1055
- "x": 653, "y": 139
1056
- },
1057
- "sound_cleareffects": {
1058
- "opcode": "sound_cleareffects", "next": None, "parent": None,
1059
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
1060
- "x": 651, "y": 242
1061
- },
1062
- "sound_changevolumeby": {
1063
- "opcode": "sound_changevolumeby", "next": None, "parent": None,
1064
- "inputs": {"VOLUME": [1, [4, "-10"]]}, "fields": {}, "shadow": False, "topLevel": True,
1065
- "x": 645, "y": 353
1066
- },
1067
- "sound_setvolumeto": {
1068
- "opcode": "sound_setvolumeto", "next": None, "parent": None,
1069
- "inputs": {"VOLUME": [1, [4, "100"]]}, "fields": {}, "shadow": False, "topLevel": True,
1070
- "x": 1108, "y": 5
1071
- },
1072
- "sound_volume": {
1073
- "opcode": "sound_volume", "next": None, "parent": None,
1074
- "inputs": {}, "fields": {}, "shadow": False, "topLevel": True,
1075
- "x": 1136, "y": 123
1076
- },
1077
- }
1078
-
1079
- # #Example input with opcodes from various categories
1080
- # input_opcodes = [
1081
- # {"opcode": "sound_play", "count": 2}, # New: Sound block with menu
1082
- # {"opcode": "sound_playuntildone", "count": 2}, # New: Sound block with menu
1083
- # ]
1084
-
1085
- # Example input with opcodes from various categories
1086
- # input_opcodes = [
1087
- # {"opcode": "sound_play", "count": 2},
1088
- # {"opcode": "sound_playuntildone", "count": 2},
1089
- # {"opcode":"motion_goto","count":2},
1090
- # {"opcode":"motion_glideto","count":2},
1091
- # {"opcode":"looks_switchbackdropto","count":2},
1092
- # {"opcode":"looks_switchcostumeto","count":2},
1093
- # {"opcode":"control_create_clone_of","count":2},
1094
- # {"opcode":"sensing_touchingobject","count":2},
1095
- # {"opcode":"sensing_of","count":2},
1096
- # {"opcode":"sensing_keypressed","count":2},
1097
- # {"opcode":"motion_pointtowards","count":2},
1098
- # ]
1099
-
1100
- # generated_output = generate_blocks_from_opcodes(input_opcodes, all_block_definitions)
1101
- # print(json.dumps(generated_output, indent=2))
1102
-
1103
- initial_opcode_counts = [
1104
- {"opcode":"event_whenflagclicked","count":1},
1105
- {"opcode":"motion_gotoxy","count":1},
1106
- {"opcode":"motion_glidesecstoxy","count":1},
1107
- {"opcode":"motion_xposition","count":1},
1108
- {"opcode":"motion_setx","count":1},
1109
- {"opcode":"control_forever","count":1},
1110
- {"opcode":"control_if","count":1},
1111
- {"opcode":"control_stop","count":1},
1112
- {"opcode":"operator_lt","count":1},
1113
- {"opcode":"sensing_istouching","count":1},
1114
- {"opcode":"sensing_touchingobjectmenu","count":1}, # This will now be generated as a child of sensing_touchingobject
1115
- {"opcode":"event_broadcast","count":1},
1116
- {"opcode":"data_setvariableto","count":2},
1117
- {"opcode":"data_showvariable","count":2},
1118
- ]
1119
-
1120
- # Generate the initial blocks and get the opcode_occurrences
1121
- generated_output_json, initial_opcode_occurrences = generate_blocks_from_opcodes(initial_opcode_counts, all_block_definitions)
1122
-
1123
- # Pseudo-code to interpret
1124
- pseudo_code_input = """
1125
- when green flag clicked
1126
- go to x: (240) y: (-135)
1127
- set [score v] to +1
1128
- set [speed v] to +1
1129
- show variable [score v]
1130
- show variable [speed v]
1131
- forever
1132
- glide (2) seconds to x: (-240) y: (-135)
1133
- if <((x position)) < (-235)> then
1134
- set x to (240)
1135
- end
1136
- if <touching [Sprite1 v]?> then
1137
- broadcast [Game Over v]
1138
- stop [all v]
1139
- end
1140
- end
1141
- end
1142
- """
1143
-
1144
- # Interpret the pseudo-code and update the blocks, passing opcode_occurrences
1145
- final_generated_blocks = interpret_pseudo_code_and_update_blocks(generated_output_json, pseudo_code_input, all_block_definitions, initial_opcode_occurrences)
1146
-
1147
- print(json.dumps(final_generated_blocks, indent=2))