prthm11 commited on
Commit
f5f51ef
·
verified ·
1 Parent(s): 0ccd664

Update utils/block_relation_builder.py

Browse files
Files changed (1) hide show
  1. utils/block_relation_builder.py +93 -49
utils/block_relation_builder.py CHANGED
@@ -4,7 +4,7 @@ import re
4
  from collections import defaultdict
5
  import secrets
6
  import string
7
- from typing import Dict, Any, TypedDict
8
 
9
 
10
  #################################################################################################################################################################
@@ -1871,7 +1871,8 @@ def classify(line):
1871
  if l.startswith("if <"): return "control_if", "c_block"
1872
  if l.startswith("repeat until <"): return "control_repeat_until", "c_block"
1873
  # Updated regex for stop block to handle different options
1874
- if re.match(r"stop \[(all|this script|other scripts in sprite)\s*v\]", l): return "control_stop", "cap"
 
1875
  if l.startswith("create clone of"): return "control_create_clone_of", "stack"
1876
  if l == "delete this clone": return "control_delete_this_clone", "cap"
1877
 
@@ -2572,8 +2573,9 @@ def process_scratch_blocks(all_generated_blocks, generated_output_json):
2572
  for input_name, input_data in all_gen_block_data["inputs"].items():
2573
  if input_name == "BROADCAST_INPUT":
2574
  # Special handling for BROADCAST_INPUT (type 11)
2575
- if isinstance(input_data, dict) and input_data.get("kind") == "menu":
2576
- menu_option = input_data.get("option", "")
 
2577
  broadcast_id = broadcast_id_map[menu_option]
2578
  processed_block["inputs"][input_name] = [
2579
  1,
@@ -2794,12 +2796,66 @@ def process_scratch_blocks(all_generated_blocks, generated_output_json):
2794
 
2795
  processed_blocks[block_id] = processed_block
2796
  return processed_blocks
2797
-
2798
  #################################################################################################################################################################
2799
  #--------------------------------------------------[Unique secret key for skelton json to make sure it donot overwrite each other]-------------------------------
2800
  #################################################################################################################################################################
2801
 
2802
- def rename_blocks(block_json: dict, opcode_count: dict) -> tuple[dict, dict]:
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2803
  """
2804
  Replace each block key in block_json and each identifier in opcode_count
2805
  with a newly generated secure token.
@@ -2895,60 +2951,39 @@ def variable_intialization(project_data):
2895
  initial_value = ""
2896
  if value_input and isinstance(value_input, list) and len(value_input) > 1 and \
2897
  isinstance(value_input[1], list) and len(value_input[1]) > 1:
2898
- # Extract value from various formats, e.g., [1, [10, "0"]] or [3, [12, "score", "id"], [10, "0"]]
2899
- if value_input[1][0] == 10: # Direct value like [10, "0"]
2900
  initial_value = str(value_input[1][1])
2901
- elif value_input[1][0] == 12 and len(value_input) > 2 and isinstance(value_input[2], list) and value_input[2][0] == 10: # Variable reference with initial value block
2902
- initial_value = str(value_input[2][1])
2903
- elif isinstance(value_input[1], (str, int, float)): # For direct number/string inputs
2904
  initial_value = str(value_input[1])
2905
-
2906
-
2907
- # Add/update the variable in the Stage's 'variables' with its initial value
2908
  stage_target["variables"][var_id] = [var_name, initial_value]
2909
 
2910
-
2911
  for key, value in obj.items():
2912
- # Process variable definitions in 'fields' (for blocks that define variables like 'show variable')
2913
- if key == "VARIABLE" and isinstance(value, list) and len(value) == 2:
2914
- var_name = value[0]
2915
- var_id = value[1]
2916
- # Only add if not already defined with an initial value from set_variableto
2917
- if var_id not in stage_target["variables"]:
2918
- stage_target["variables"][var_id] = [var_name, ""] # Default to empty string if no initial value found yet
2919
- elif stage_target["variables"][var_id][0] != var_name: # Update name if ID exists but name is different
2920
- stage_target["variables"][var_id][0] = var_name
2921
-
2922
-
2923
  # Process broadcast definitions in 'inputs' (BROADCAST_INPUT)
2924
- elif key == "BROADCAST_INPUT" and isinstance(value, list) and len(value) == 2 and \
2925
- isinstance(value[1], list) and len(value[1]) == 3 and value[1][0] == 11:
2926
  broadcast_name = value[1][1]
2927
  broadcast_id = value[1][2]
2928
- # Add/update the broadcast in the Stage's 'broadcasts'
2929
  stage_target["broadcasts"][broadcast_id] = broadcast_name
2930
 
2931
  # Process broadcast definitions in 'fields' (BROADCAST_OPTION)
2932
  elif key == "BROADCAST_OPTION" and isinstance(value, list) and len(value) == 2:
2933
  broadcast_name = value[0]
2934
  broadcast_id = value[1]
2935
- # Add/update the broadcast in the Stage's 'broadcasts'
2936
  stage_target["broadcasts"][broadcast_id] = broadcast_name
2937
-
2938
  # Recursively call for nested dictionaries or lists
2939
  process_dict(value)
 
2940
  elif isinstance(obj, list):
2941
  for i, item in enumerate(obj):
2942
  # Process variable references in 'inputs' (like [12, "score", "id"])
2943
  if isinstance(item, list) and len(item) == 3 and item[0] == 12:
2944
  var_name = item[1]
2945
  var_id = item[2]
2946
- # Only add if not already defined with an initial value from set_variableto
2947
  if var_id not in stage_target["variables"]:
2948
- stage_target["variables"][var_id] = [var_name, ""] # Default to empty string if no initial value found yet
2949
- elif stage_target["variables"][var_id][0] != var_name: # Update name if ID exists but name is different
2950
- stage_target["variables"][var_id][0] = var_name
2951
-
2952
  process_dict(item)
2953
 
2954
  # Iterate through all targets to process their blocks
@@ -3030,14 +3065,15 @@ def deduplicate_variables(project_data):
3030
  def variable_adder_main(project_data):
3031
  try:
3032
  declare_variable_json= variable_intialization(project_data)
 
3033
  except Exception as e:
3034
  print(f"Error error in the variable initialization opcodes: {e}")
3035
  try:
3036
  processed_json= deduplicate_variables(declare_variable_json)
3037
- return
 
3038
  except Exception as e:
3039
  print(f"Error error in the variable initialization opcodes: {e}")
3040
-
3041
  #################################################################################################################################################################
3042
  #--------------------------------------------------[Helper main function]----------------------------------------------------------------------------------------
3043
  #################################################################################################################################################################
@@ -3066,18 +3102,24 @@ def block_builder(opcode_count,pseudo_code):
3066
  #################################################################################################################################################################
3067
 
3068
  initial_opcode_counts = [
3069
- {
3070
- "opcode": "event_whenbroadcastreceived",
3071
- "count": 1
3072
- },
3073
- {
3074
- "opcode": "looks_hide",
3075
- "count": 1
3076
- }
3077
  ]
3078
  pseudo_code="""
3079
- when I receive [Game Over v]
3080
- hide
 
 
 
 
 
 
3081
  end
3082
  """
3083
  # print(pseudo_code)
@@ -3085,8 +3127,10 @@ end
3085
  # all_generated_blocks = generate_plan(generated_output_json, initial_opcode_occurrences, pseudo_code)
3086
  # processed_blocks= process_scratch_blocks(all_generated_blocks, generated_output_json)
3087
  # renamed_blocks, renamed_counts = rename_blocks(processed_blocks, initial_opcode_occurrences)
3088
- # print(all_generated_blocks)
3089
  # print("--------------\n\n")
3090
  # print(processed_blocks)
3091
  # print("--------------\n\n")
 
 
3092
  # print(renamed_blocks)
 
4
  from collections import defaultdict
5
  import secrets
6
  import string
7
+ from typing import Dict, Any, TypedDict,Tuple
8
 
9
 
10
  #################################################################################################################################################################
 
1871
  if l.startswith("if <"): return "control_if", "c_block"
1872
  if l.startswith("repeat until <"): return "control_repeat_until", "c_block"
1873
  # Updated regex for stop block to handle different options
1874
+ #if re.match(r"stop \[(all|this script|other scripts in sprite)\s*v\]", l): return "control_stop", "cap"
1875
+ if re.match(r"stop\s*(?:[\[(]?\s*(all|this script|other scripts in sprite)\s*[\])]?$)", l, re.IGNORECASE): return "control_stop", "cap"
1876
  if l.startswith("create clone of"): return "control_create_clone_of", "stack"
1877
  if l == "delete this clone": return "control_delete_this_clone", "cap"
1878
 
 
2573
  for input_name, input_data in all_gen_block_data["inputs"].items():
2574
  if input_name == "BROADCAST_INPUT":
2575
  # Special handling for BROADCAST_INPUT (type 11)
2576
+ if isinstance(input_data, dict) and input_data.get("kind") == "value":
2577
+ # This is the new logic to handle a direct value for broadcast
2578
+ menu_option = input_data.get("value", "message1")
2579
  broadcast_id = broadcast_id_map[menu_option]
2580
  processed_block["inputs"][input_name] = [
2581
  1,
 
2796
 
2797
  processed_blocks[block_id] = processed_block
2798
  return processed_blocks
2799
+
2800
  #################################################################################################################################################################
2801
  #--------------------------------------------------[Unique secret key for skelton json to make sure it donot overwrite each other]-------------------------------
2802
  #################################################################################################################################################################
2803
 
2804
+ def rename_blocks(block_json: Dict[str, Any], opcode_count: Dict[str, list]) -> Tuple[Dict[str, Any], Dict[str, list]]:
2805
+ """
2806
+ Replace each block key in block_json and each identifier in opcode_count
2807
+ with a newly generated secure token, ensuring all references are updated.
2808
+
2809
+ Args:
2810
+ block_json: Mapping of block_key -> block_data.
2811
+ opcode_count: Mapping of opcode -> list of block_keys.
2812
+
2813
+ Returns:
2814
+ A tuple of (new_block_json, new_opcode_count) with updated keys.
2815
+ """
2816
+ token_map = {}
2817
+
2818
+ # Step 1: Generate a secure token mapping for every existing block key
2819
+ for old_key in block_json.keys():
2820
+ while True:
2821
+ new_key = generate_secure_token()
2822
+ if new_key not in token_map.values():
2823
+ break
2824
+ token_map[old_key] = new_key
2825
+
2826
+ new_block_json = {}
2827
+
2828
+ # Step 2: Rebuild block_json with new keys and update all references
2829
+ for old_key, block in block_json.items():
2830
+ new_key = token_map[old_key]
2831
+ new_block_json[new_key] = block.copy()
2832
+
2833
+ # Update parent and next references
2834
+ if 'parent' in block and block['parent'] in token_map:
2835
+ new_block_json[new_key]['parent'] = token_map[block['parent']]
2836
+ if 'next' in block and block['next'] in token_map:
2837
+ new_block_json[new_key]['next'] = token_map[block['next']]
2838
+
2839
+ # Update inputs that reference blocks
2840
+ if 'inputs' in block:
2841
+ for inp_key, inp_val in block['inputs'].items():
2842
+ # This handles references like [2, 'block_key']
2843
+ if isinstance(inp_val, list) and len(inp_val) == 2:
2844
+ idx, ref = inp_val
2845
+ if isinstance(ref, str) and ref in token_map:
2846
+ new_block_json[new_key]['inputs'][inp_key] = [idx, token_map[ref]]
2847
+ # This new block handles references like [3, 'block_key', [10, '']]
2848
+ elif isinstance(inp_val, list) and len(inp_val) == 3:
2849
+ idx, ref, rest = inp_val
2850
+ if isinstance(ref, str) and ref in token_map:
2851
+ new_block_json[new_key]['inputs'][inp_key] = [idx, token_map[ref], rest]
2852
+
2853
+ # Step 3: Update opcode count map
2854
+ new_opcode_count = {}
2855
+ for opcode, key_list in opcode_count.items():
2856
+ new_opcode_count[opcode] = [token_map.get(k, k) for k in key_list]
2857
+
2858
+ return new_block_json, new_opcode_count
2859
  """
2860
  Replace each block key in block_json and each identifier in opcode_count
2861
  with a newly generated secure token.
 
2951
  initial_value = ""
2952
  if value_input and isinstance(value_input, list) and len(value_input) > 1 and \
2953
  isinstance(value_input[1], list) and len(value_input[1]) > 1:
2954
+ if value_input[1][0] == 10:
 
2955
  initial_value = str(value_input[1][1])
2956
+ elif value_input[1][0] == 12 and len(value_input) > 2 and isinstance(value_input[2], list) and value_input[2][0] == 10:
2957
+ initial_value = str(value_input[2][1])
2958
+ elif isinstance(value_input[1], (str, int, float)):
2959
  initial_value = str(value_input[1])
 
 
 
2960
  stage_target["variables"][var_id] = [var_name, initial_value]
2961
 
 
2962
  for key, value in obj.items():
 
 
 
 
 
 
 
 
 
 
 
2963
  # Process broadcast definitions in 'inputs' (BROADCAST_INPUT)
2964
+ if key == "BROADCAST_INPUT" and isinstance(value, list) and len(value) == 2 and \
2965
+ isinstance(value[1], list) and len(value[1]) == 3 and value[1][0] == 11:
2966
  broadcast_name = value[1][1]
2967
  broadcast_id = value[1][2]
 
2968
  stage_target["broadcasts"][broadcast_id] = broadcast_name
2969
 
2970
  # Process broadcast definitions in 'fields' (BROADCAST_OPTION)
2971
  elif key == "BROADCAST_OPTION" and isinstance(value, list) and len(value) == 2:
2972
  broadcast_name = value[0]
2973
  broadcast_id = value[1]
 
2974
  stage_target["broadcasts"][broadcast_id] = broadcast_name
2975
+
2976
  # Recursively call for nested dictionaries or lists
2977
  process_dict(value)
2978
+
2979
  elif isinstance(obj, list):
2980
  for i, item in enumerate(obj):
2981
  # Process variable references in 'inputs' (like [12, "score", "id"])
2982
  if isinstance(item, list) and len(item) == 3 and item[0] == 12:
2983
  var_name = item[1]
2984
  var_id = item[2]
 
2985
  if var_id not in stage_target["variables"]:
2986
+ stage_target["variables"][var_id] = [var_name, ""]
 
 
 
2987
  process_dict(item)
2988
 
2989
  # Iterate through all targets to process their blocks
 
3065
  def variable_adder_main(project_data):
3066
  try:
3067
  declare_variable_json= variable_intialization(project_data)
3068
+ print("declare_variable_json------->",declare_variable_json)
3069
  except Exception as e:
3070
  print(f"Error error in the variable initialization opcodes: {e}")
3071
  try:
3072
  processed_json= deduplicate_variables(declare_variable_json)
3073
+ print("processed_json------->",processed_json)
3074
+ return processed_json
3075
  except Exception as e:
3076
  print(f"Error error in the variable initialization opcodes: {e}")
 
3077
  #################################################################################################################################################################
3078
  #--------------------------------------------------[Helper main function]----------------------------------------------------------------------------------------
3079
  #################################################################################################################################################################
 
3102
  #################################################################################################################################################################
3103
 
3104
  initial_opcode_counts = [
3105
+ {"opcode": "event_whenbroadcastreceived","count": 1},
3106
+ {"opcode": "control_forever","count": 1},
3107
+ {"opcode": "control_if","count": 1},
3108
+ {"opcode": "sensing_istouching","count": 1},
3109
+ {"opcode": "looks_hide","count": 1},
3110
+ {"opcode": "looks_switchbackdropto","count": 1},
3111
+ {"opcode": "event_broadcast","count": 1},
3112
+ {"opcode": "control_stop","count": 1}
3113
  ]
3114
  pseudo_code="""
3115
+ when I receive [Game Start v]
3116
+ forever
3117
+ if <touching [obstacle v]?> then
3118
+ hide
3119
+ switch backdrop to [loose v]
3120
+ broadcast [Game Over v]
3121
+ stop all
3122
+ end
3123
  end
3124
  """
3125
  # print(pseudo_code)
 
3127
  # all_generated_blocks = generate_plan(generated_output_json, initial_opcode_occurrences, pseudo_code)
3128
  # processed_blocks= process_scratch_blocks(all_generated_blocks, generated_output_json)
3129
  # renamed_blocks, renamed_counts = rename_blocks(processed_blocks, initial_opcode_occurrences)
3130
+ # #print(all_generated_blocks)
3131
  # print("--------------\n\n")
3132
  # print(processed_blocks)
3133
  # print("--------------\n\n")
3134
+ # print(initial_opcode_occurrences)
3135
+ # print("--------------\n\n")
3136
  # print(renamed_blocks)