mirror of
https://github.com/kolbytn/mindcraft.git
synced 2025-08-09 00:35:33 +02:00
Merge branch 'main' of https://github.com/icwhite/mindcraft
This commit is contained in:
commit
c43dc879d2
11 changed files with 13285 additions and 137 deletions
|
@ -53,16 +53,19 @@ def analyze_json_file(file_path):
|
||||||
try:
|
try:
|
||||||
with open(file_path, 'r') as f:
|
with open(file_path, 'r') as f:
|
||||||
data = json.load(f)
|
data = json.load(f)
|
||||||
if 'turns' in data and isinstance(data['turns'], list):
|
if "turns" in data:
|
||||||
for turn in reversed(data['turns']): # Check turns from the end
|
for turn in data["turns"]:
|
||||||
if turn.get('role') == 'system' and isinstance(turn.get('content'), str):
|
if turn.get("role") == "system" and "content" in turn:
|
||||||
code = turn["content"].split(":")[-1].strip()
|
if isinstance(turn["content"], str) and "Task ended with score : " in turn["content"]:
|
||||||
if code in ["2", "1"]: # Check for success codes
|
score_found = True
|
||||||
return True
|
if "Task ended with score : 1" in turn["content"]:
|
||||||
elif 0 < float(code) < 1: # Check for other success indicators
|
return 1
|
||||||
return code
|
elif "Task ended with score : 0" in turn["content"]:
|
||||||
else:
|
return 0
|
||||||
return False
|
else:
|
||||||
|
score = float(turn["content"].split(":")[-1].strip())
|
||||||
|
return score
|
||||||
|
|
||||||
return False
|
return False
|
||||||
except FileNotFoundError:
|
except FileNotFoundError:
|
||||||
print(f"Error: File not found: {file_path}")
|
print(f"Error: File not found: {file_path}")
|
||||||
|
@ -82,12 +85,12 @@ def extract_result(folder_path):
|
||||||
if not json_files:
|
if not json_files:
|
||||||
return None
|
return None
|
||||||
else:
|
else:
|
||||||
outcome = False
|
score = None
|
||||||
for json_file in json_files:
|
for json_file in json_files:
|
||||||
outcome = analyze_json_file(json_file)
|
score = analyze_json_file(json_file)
|
||||||
if outcome:
|
if score is not None:
|
||||||
return True
|
return score
|
||||||
return False
|
return 0
|
||||||
|
|
||||||
def aggregate_results(local_folders):
|
def aggregate_results(local_folders):
|
||||||
"""
|
"""
|
||||||
|
@ -110,7 +113,7 @@ def aggregate_results(local_folders):
|
||||||
result = extract_result(folder_path)
|
result = extract_result(folder_path)
|
||||||
if result is not None:
|
if result is not None:
|
||||||
total += 1
|
total += 1
|
||||||
successful += float(result)
|
successful += result
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f"Error processing {folder_name}: {e}")
|
print(f"Error processing {folder_name}: {e}")
|
||||||
|
|
||||||
|
@ -161,28 +164,6 @@ def update_keys_json():
|
||||||
with open("keys.json", 'w', encoding='utf-8') as file:
|
with open("keys.json", 'w', encoding='utf-8') as file:
|
||||||
json.dump(data, file, indent=4)
|
json.dump(data, file, indent=4)
|
||||||
|
|
||||||
def check_task_completion(agents):
|
|
||||||
"""Check memory.json files of all agents to determine task success/failure."""
|
|
||||||
for agent in agents:
|
|
||||||
memory_path = f"bots/{agent}/memory.json"
|
|
||||||
try:
|
|
||||||
with open(memory_path, 'r') as f:
|
|
||||||
memory = json.load(f)
|
|
||||||
|
|
||||||
# Check the last system message in turns
|
|
||||||
for turn in reversed(memory['turns']):
|
|
||||||
if turn['role'] == 'system' and 'code' in turn['content']:
|
|
||||||
# Extract completion code
|
|
||||||
if 'code : 2' in turn['content']:
|
|
||||||
return True # Task successful
|
|
||||||
elif 'code : 4' in turn['content']:
|
|
||||||
return False # Task failed
|
|
||||||
|
|
||||||
except (FileNotFoundError, json.JSONDecodeError) as e:
|
|
||||||
print(f"Error reading memory for agent {agent}: {e}")
|
|
||||||
continue
|
|
||||||
return False # Default to failure if no conclusive result found
|
|
||||||
|
|
||||||
def set_environment_variable_tmux_session(session_name, key, value):
|
def set_environment_variable_tmux_session(session_name, key, value):
|
||||||
"""Set an environment variable for the current process."""
|
"""Set an environment variable for the current process."""
|
||||||
subprocess.run(["tmux", "send-keys", "-t", session_name, f"export {key}={value}", "C-m"])
|
subprocess.run(["tmux", "send-keys", "-t", session_name, f"export {key}={value}", "C-m"])
|
||||||
|
@ -202,7 +183,8 @@ def launch_parallel_experiments(task_path,
|
||||||
max_messages=15,
|
max_messages=15,
|
||||||
num_examples=2,
|
num_examples=2,
|
||||||
no_pruning=False,
|
no_pruning=False,
|
||||||
block_conversation=False):
|
block_conversation=False,
|
||||||
|
run_in_tmux=True):
|
||||||
|
|
||||||
with open(task_path, 'r', encoding='utf-8') as file:
|
with open(task_path, 'r', encoding='utf-8') as file:
|
||||||
content = file.read()
|
content = file.read()
|
||||||
|
@ -211,8 +193,6 @@ def launch_parallel_experiments(task_path,
|
||||||
task_ids = json_data.keys()
|
task_ids = json_data.keys()
|
||||||
|
|
||||||
task_type = json_data[list(task_ids)[0]]["type"]
|
task_type = json_data[list(task_ids)[0]]["type"]
|
||||||
|
|
||||||
|
|
||||||
# split the task_ids into num_parallel groups
|
# split the task_ids into num_parallel groups
|
||||||
task_ids = list(task_ids)
|
task_ids = list(task_ids)
|
||||||
task_ids_split = [task_ids[i::num_parallel] for i in range(num_parallel)]
|
task_ids_split = [task_ids[i::num_parallel] for i in range(num_parallel)]
|
||||||
|
@ -224,7 +204,10 @@ def launch_parallel_experiments(task_path,
|
||||||
elif task_type == "construction":
|
elif task_type == "construction":
|
||||||
world_name = "Superflat"
|
world_name = "Superflat"
|
||||||
|
|
||||||
servers = create_server_files("./server_data/", num_parallel, world_name=world_name)
|
if run_in_tmux:
|
||||||
|
servers = create_server_files("./server_data/", num_parallel, world_name=world_name)
|
||||||
|
else:
|
||||||
|
servers = [(f"./server_data_{i}/", 55916 + i) for i in range(num_parallel)]
|
||||||
date_time = datetime.now().strftime("%m-%d_%H-%M")
|
date_time = datetime.now().strftime("%m-%d_%H-%M")
|
||||||
experiments_folder = f"experiments/{exp_name}_{date_time}"
|
experiments_folder = f"experiments/{exp_name}_{date_time}"
|
||||||
exp_name = f"{exp_name}_{date_time}"
|
exp_name = f"{exp_name}_{date_time}"
|
||||||
|
@ -259,7 +242,8 @@ def launch_parallel_experiments(task_path,
|
||||||
max_messages=max_messages,
|
max_messages=max_messages,
|
||||||
num_examples=num_examples,
|
num_examples=num_examples,
|
||||||
no_pruning=no_pruning,
|
no_pruning=no_pruning,
|
||||||
block_conversation=block_conversation)
|
block_conversation=block_conversation,
|
||||||
|
run_in_tmux=run_in_tmux)
|
||||||
time.sleep(5)
|
time.sleep(5)
|
||||||
|
|
||||||
total_num_tasks = len(task_ids)
|
total_num_tasks = len(task_ids)
|
||||||
|
@ -307,7 +291,8 @@ def launch_server_experiment(task_path,
|
||||||
max_messages=15,
|
max_messages=15,
|
||||||
num_examples=2,
|
num_examples=2,
|
||||||
no_pruning=False,
|
no_pruning=False,
|
||||||
block_conversation=False):
|
block_conversation=False,
|
||||||
|
run_in_tmux=True):
|
||||||
|
|
||||||
"""
|
"""
|
||||||
Launch a Minecraft server and run experiments on it.
|
Launch a Minecraft server and run experiments on it.
|
||||||
|
@ -360,39 +345,107 @@ def launch_server_experiment(task_path,
|
||||||
agent_profiles_str += f'\"{agent}\", '
|
agent_profiles_str += f'\"{agent}\", '
|
||||||
agent_profiles_str += f"\"{agent_profiles[-1]}\"]'"
|
agent_profiles_str += f"\"{agent_profiles[-1]}\"]'"
|
||||||
print(agent_profiles_str)
|
print(agent_profiles_str)
|
||||||
launch_world(server_path, session_name="server_" + session_name, agent_names=agent_names, port=server_port)
|
if run_in_tmux:
|
||||||
|
print("run in tmux is true")
|
||||||
subprocess.run(['tmux', 'new-session', '-d', '-s', session_name], check=True)
|
launch_world(server_path, session_name="server_" + session_name, agent_names=agent_names, port=server_port)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
subprocess.run(['tmux', 'new-session', '-d', '-s', session_name], check=True)
|
||||||
# set environment variables
|
# set environment variables
|
||||||
set_environment_variable_tmux_session(session_name, "MINECRAFT_PORT", server_port)
|
if run_in_tmux:
|
||||||
set_environment_variable_tmux_session(session_name, "MINDSERVER_PORT", mindserver_port)
|
set_environment_variable_tmux_session(session_name, "MINECRAFT_PORT", server_port)
|
||||||
set_environment_variable_tmux_session(session_name, "PROFILES", agent_profiles_str)
|
set_environment_variable_tmux_session(session_name, "MINDSERVER_PORT", mindserver_port)
|
||||||
set_environment_variable_tmux_session(session_name, "MAX_MESSAGES", str(max_messages))
|
set_environment_variable_tmux_session(session_name, "PROFILES", agent_profiles_str)
|
||||||
set_environment_variable_tmux_session(session_name, "NUM_EXAMPLES", str(num_examples))
|
set_environment_variable_tmux_session(session_name, "MAX_MESSAGES", str(max_messages))
|
||||||
set_environment_variable_tmux_session(session_name, "LOG_ALL", "true")
|
set_environment_variable_tmux_session(session_name, "NUM_EXAMPLES", str(num_examples))
|
||||||
if insecure_coding:
|
set_environment_variable_tmux_session(session_name, "LOG_ALL", "true")
|
||||||
set_environment_variable_tmux_session(session_name, "INSECURE_CODING", "true")
|
if insecure_coding:
|
||||||
make_ops(agent_names, session_name)
|
set_environment_variable_tmux_session(session_name, "INSECURE_CODING", "true")
|
||||||
|
make_ops(agent_names, session_name)
|
||||||
|
else:
|
||||||
|
agent_profiles_str = "["
|
||||||
|
for agent in agent_profiles[:-1]:
|
||||||
|
agent_profiles_str += f"\"{agent}\", "
|
||||||
|
agent_profiles_str += f"\"{agent_profiles[-1]}\"]"
|
||||||
|
# print(agent_profiles_str)
|
||||||
|
os.environ["PROFILES"] = agent_profiles_str
|
||||||
|
os.environ["MAX_MESSAGES"] = str(max_messages)
|
||||||
|
os.environ["NUM_EXAMPLES"] = str(num_examples)
|
||||||
|
os.environ["LOG_ALL"] = "true"
|
||||||
|
|
||||||
|
run_script(task_path,
|
||||||
|
task_ids,
|
||||||
|
num_exp,
|
||||||
|
experiments_folder,
|
||||||
|
agent_names,
|
||||||
|
server_path,
|
||||||
|
s3=s3,
|
||||||
|
s3_path=s3_path,
|
||||||
|
session_name=session_name,
|
||||||
|
run_in_tmux=run_in_tmux)
|
||||||
|
|
||||||
# add the bots as op
|
# add the bots as op
|
||||||
# op_script_content = "sleep 5\n\op @p" * 20
|
# op_script_content = "sleep 5\n\op @p" * 20
|
||||||
# op_script_file = f"./tmp/op_script_{session_name}.sh"
|
# op_script_file = f"./tmp/op_script_{session_name}.sh"
|
||||||
# make_script_file_and_run(op_script_content, "server_" + session_name, op_script_file)
|
# make_script_file_and_run(op_script_content, "server_" + session_name, op_script_file)
|
||||||
blocked_actions = []
|
# blocked_actions = []
|
||||||
if not no_pruning:
|
# if not no_pruning:
|
||||||
if task_type == "cooking":
|
# if task_type == "cooking":
|
||||||
blocked_actions = BLOCKED_ACTIONS_COOKING
|
# blocked_actions = BLOCKED_ACTIONS_COOKING
|
||||||
elif task_type == "techtree":
|
# elif task_type == "techtree":
|
||||||
blocked_actions = BLOCKED_ACTIONS_CRAFTING
|
# blocked_actions = BLOCKED_ACTIONS_CRAFTING
|
||||||
elif task_type == "construction":
|
# elif task_type == "construction":
|
||||||
blocked_actions = BLOCKED_ACTIONS_CONSTRUCTION
|
# blocked_actions = BLOCKED_ACTIONS_CONSTRUCTION
|
||||||
if block_conversation:
|
# if block_conversation:
|
||||||
blocked_actions += ["!endConversation", "!startConversation"]
|
# blocked_actions += ["!endConversation", "!startConversation"]
|
||||||
set_environment_variable_tmux_session(session_name, "BLOCKED_ACTIONS", blocked_actions)
|
# set_environment_variable_tmux_session(session_name, "BLOCKED_ACTIONS", blocked_actions)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# script_content = ""
|
||||||
|
# for task_id in task_ids:
|
||||||
|
# # Create a separate folder for each task_id
|
||||||
|
# task_folder = os.path.join(experiments_folder, str(task_id))
|
||||||
|
# os.makedirs(task_folder, exist_ok=True)
|
||||||
|
# assert os.path.exists(task_folder), f"Directory {task_folder} was not created"
|
||||||
|
# print(f"Created directory: {task_folder}")
|
||||||
|
|
||||||
|
# cmd = f"node main.js --task_path \'{task_path}\' --task_id {task_id}"
|
||||||
|
# cp_cmd = f"cp {agent_names[0]}.json {server_path}bots/{agent_names[0]}/profile.json"
|
||||||
|
# for _ in range(num_exp):
|
||||||
|
# script_content += f"{cmd}\n"
|
||||||
|
# script_content += "sleep 2\n"
|
||||||
|
# for agent in agent_names:
|
||||||
|
# agent_file_path = os.path.join(task_folder, f"{agent}_{_}.json")
|
||||||
|
# script_content += f"echo 'Saving to {agent_file_path}'\n"
|
||||||
|
# cp_cmd = f"cp bots/{agent}/memory.json {agent_file_path}"
|
||||||
|
# script_content += f"echo '{cp_cmd}'\n"
|
||||||
|
# script_content += f"{cp_cmd}\n"
|
||||||
|
# script_content += "sleep 1\n"
|
||||||
|
# if s3:
|
||||||
|
# s3_cmd = f"aws s3 cp {agent_file_path} s3://{s3_path}/{task_id}/{agent}_{_}.json"
|
||||||
|
# script_content += f"echo 'Uploading {agent_file_path} to S3'\n"
|
||||||
|
# script_content += f"echo '{s3_cmd}'\n"
|
||||||
|
# script_content += f"{s3_cmd}\n"
|
||||||
|
# script_content += "sleep 1\n"
|
||||||
|
# script_content += f"sleep 10\n"
|
||||||
|
# if s3:
|
||||||
|
# for agent in agent_names:
|
||||||
|
# script_content += f"aws s3 cp bots/{agent} s3://{s3_path}/bots/{agent} --recursive\n"
|
||||||
|
|
||||||
|
# # Create a temporary shell script file
|
||||||
|
# script_file = f"./tmp/experiment_script_{session_name}.sh"
|
||||||
|
# make_script_file_and_run(script_content, script_file, session_name=session_name, run_in_tmux=True)
|
||||||
|
|
||||||
|
def run_script(task_path,
|
||||||
|
task_ids,
|
||||||
|
num_exp,
|
||||||
|
experiments_folder,
|
||||||
|
agent_names,
|
||||||
|
server_path,
|
||||||
|
s3=False,
|
||||||
|
s3_path="mindcraft-experiments",
|
||||||
|
session_name="0",
|
||||||
|
run_in_tmux=True,):
|
||||||
script_content = ""
|
script_content = ""
|
||||||
for task_id in task_ids:
|
for task_id in task_ids:
|
||||||
# Create a separate folder for each task_id
|
# Create a separate folder for each task_id
|
||||||
|
@ -426,7 +479,8 @@ def launch_server_experiment(task_path,
|
||||||
|
|
||||||
# Create a temporary shell script file
|
# Create a temporary shell script file
|
||||||
script_file = f"./tmp/experiment_script_{session_name}.sh"
|
script_file = f"./tmp/experiment_script_{session_name}.sh"
|
||||||
make_script_file_and_run(script_content, session_name, script_file)
|
make_script_file_and_run(script_content, script_file, session_name=session_name, run_in_tmux=run_in_tmux)
|
||||||
|
|
||||||
|
|
||||||
def make_ops(agent_names, session_name):
|
def make_ops(agent_names, session_name):
|
||||||
"""Make the agents operators in the Minecraft world."""
|
"""Make the agents operators in the Minecraft world."""
|
||||||
|
@ -458,7 +512,10 @@ def check_agent_ops(agent_names, ops_file="ops.json"):
|
||||||
return False
|
return False
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def make_script_file_and_run(script_content, session_name, file_name):
|
def make_script_file_and_run(script_content,
|
||||||
|
file_name,
|
||||||
|
session_name="0",
|
||||||
|
run_in_tmux=True):
|
||||||
script_dir = os.path.dirname(file_name)
|
script_dir = os.path.dirname(file_name)
|
||||||
os.makedirs(script_dir, exist_ok=True)
|
os.makedirs(script_dir, exist_ok=True)
|
||||||
assert os.path.exists(script_dir), f"Script directory {script_dir} was not created"
|
assert os.path.exists(script_dir), f"Script directory {script_dir} was not created"
|
||||||
|
@ -472,9 +529,10 @@ def make_script_file_and_run(script_content, session_name, file_name):
|
||||||
script_file_run = "bash " + file_name
|
script_file_run = "bash " + file_name
|
||||||
|
|
||||||
# Execute the shell script using subprocess
|
# Execute the shell script using subprocess
|
||||||
subprocess.run(["tmux", "send-keys", "-t", session_name, script_file_run, "C-m"])
|
if run_in_tmux:
|
||||||
|
subprocess.run(["tmux", "send-keys", "-t", session_name, script_file_run, "C-m"])
|
||||||
# subprocess.run(["tmux", "send-keys", "-t", session_name, f"/op {agent_names[0]}", "C-m"])
|
else:
|
||||||
|
subprocess.run(script_file_run.split())
|
||||||
|
|
||||||
def make_profiles(agent_names, models, apis, template_profile="profiles/collab_profile.json", url="http://127.0.0.1:8000/v1"):
|
def make_profiles(agent_names, models, apis, template_profile="profiles/collab_profile.json", url="http://127.0.0.1:8000/v1"):
|
||||||
assert len(agent_names) == len(models)
|
assert len(agent_names) == len(models)
|
||||||
|
@ -645,6 +703,7 @@ def main():
|
||||||
# edit_server_properties_file("../server_data/", 55917)
|
# edit_server_properties_file("../server_data/", 55917)
|
||||||
|
|
||||||
parser = argparse.ArgumentParser(description='Run Minecraft AI agent experiments')
|
parser = argparse.ArgumentParser(description='Run Minecraft AI agent experiments')
|
||||||
|
parser.add_argument('--no_launch_world', action='store_true', help='Do not launch the Minecraft world')
|
||||||
parser.add_argument('--task_path', default="multiagent_crafting_tasks.json", help='Path to the task file')
|
parser.add_argument('--task_path', default="multiagent_crafting_tasks.json", help='Path to the task file')
|
||||||
parser.add_argument('--num_agents', default=2, type=int, help='Number of agents to run')
|
parser.add_argument('--num_agents', default=2, type=int, help='Number of agents to run')
|
||||||
parser.add_argument('--num_exp', default=1, type=int, help='Number of experiments to run')
|
parser.add_argument('--num_exp', default=1, type=int, help='Number of experiments to run')
|
||||||
|
@ -666,14 +725,15 @@ def main():
|
||||||
|
|
||||||
args = parser.parse_args()
|
args = parser.parse_args()
|
||||||
print(args)
|
print(args)
|
||||||
|
if not args.no_launch_world:
|
||||||
try:
|
try:
|
||||||
subprocess.run(['tmux', 'kill-server'], check=True)
|
subprocess.run(['tmux', 'kill-server'], check=True)
|
||||||
except:
|
except:
|
||||||
print("No tmux session to kill")
|
print("No tmux session to kill")
|
||||||
|
|
||||||
# delete all server files
|
# delete all server files
|
||||||
clean_up_server_files(args.num_parallel)
|
if not args.no_launch_world:
|
||||||
|
clean_up_server_files(args.num_parallel)
|
||||||
if args.add_keys:
|
if args.add_keys:
|
||||||
update_keys_json()
|
update_keys_json()
|
||||||
|
|
||||||
|
@ -692,7 +752,8 @@ def main():
|
||||||
max_messages=args.max_messages,
|
max_messages=args.max_messages,
|
||||||
num_examples=args.num_examples,
|
num_examples=args.num_examples,
|
||||||
no_pruning=args.no_pruning,
|
no_pruning=args.no_pruning,
|
||||||
block_conversation=args.block_conversation)
|
block_conversation=args.block_conversation,
|
||||||
|
run_in_tmux=not args.no_launch_world)
|
||||||
|
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
main()
|
main()
|
|
@ -12,14 +12,12 @@ export class ConstructionTaskValidator {
|
||||||
let valid = false;
|
let valid = false;
|
||||||
let score = 0;
|
let score = 0;
|
||||||
let result = this.blueprint.check(this.agent.bot);
|
let result = this.blueprint.check(this.agent.bot);
|
||||||
if (result.mismatches.length === 0) {
|
if (result.mismatches.y_amount === 0) {
|
||||||
valid = true;
|
valid = true;
|
||||||
console.log('Task is complete');
|
console.log('Task is complete');
|
||||||
}
|
}
|
||||||
let total_blocks = result.mismatches.length + result.matches.length;
|
let total_blocks = result.mismatches.y_amount + result.matches.y_amount;
|
||||||
score = (result.matches.length / total_blocks) * 100;
|
score = (result.matches.y_amount / total_blocks) * 100;
|
||||||
console.log(`Agent name is ${this.agent.name}`);
|
|
||||||
console.log(`Task is ${score}% complete \n\n`);
|
|
||||||
return {
|
return {
|
||||||
"valid": valid,
|
"valid": valid,
|
||||||
"score": score
|
"score": score
|
||||||
|
@ -37,10 +35,10 @@ export class ConstructionTaskValidator {
|
||||||
export function resetConstructionWorld(bot, blueprint) {
|
export function resetConstructionWorld(bot, blueprint) {
|
||||||
console.log('Resetting world...');
|
console.log('Resetting world...');
|
||||||
const starting_position = blueprint.levels[0].coordinates;
|
const starting_position = blueprint.levels[0].coordinates;
|
||||||
const length = blueprint.levels[0].placement.length + 5;
|
const y_amount = blueprint.levels[0].placement.y_amount + 5;
|
||||||
const height = blueprint.levels.length + 5;
|
const height = blueprint.levels.y_amount + 5;
|
||||||
const width = blueprint.levels[0].placement[0].length + 5;
|
const width = blueprint.levels[0].placement[0].y_amount + 5;
|
||||||
const command = `/fill ${starting_position[0]} ${starting_position[1]} ${starting_position[2]} ${starting_position[0] + width} ${starting_position[1] + height} ${starting_position[2] + length} air`;
|
const command = `/fill ${starting_position[0]} ${starting_position[1]} ${starting_position[2]} ${starting_position[0] + width} ${starting_position[1] + height} ${starting_position[2] + y_amount} air`;
|
||||||
bot.chat(command);
|
bot.chat(command);
|
||||||
console.log('World reset');
|
console.log('World reset');
|
||||||
}
|
}
|
||||||
|
@ -50,7 +48,7 @@ export function checkLevelBlueprint(agent, levelNum) {
|
||||||
const bot = agent.bot;
|
const bot = agent.bot;
|
||||||
try {
|
try {
|
||||||
const result = blueprint.checkLevel(bot, levelNum);
|
const result = blueprint.checkLevel(bot, levelNum);
|
||||||
if (result.mismatches.length === 0) {
|
if (result.mismatches.y_amount === 0) {
|
||||||
return `Level ${levelNum} is correct`;
|
return `Level ${levelNum} is correct`;
|
||||||
} else {
|
} else {
|
||||||
let explanation = blueprint.explainLevelDifference(bot, levelNum);
|
let explanation = blueprint.explainLevelDifference(bot, levelNum);
|
||||||
|
@ -69,7 +67,7 @@ export function checkBlueprint(agent) {
|
||||||
const blueprint = agent.task.blueprint;
|
const blueprint = agent.task.blueprint;
|
||||||
const bot = agent.bot;
|
const bot = agent.bot;
|
||||||
const result = blueprint.check(bot);
|
const result = blueprint.check(bot);
|
||||||
if (result.mismatches.length === 0) {
|
if (result.mismatches.y_amount === 0) {
|
||||||
return "Blueprint is correct";
|
return "Blueprint is correct";
|
||||||
} else {
|
} else {
|
||||||
let explanation = blueprint.explainBlueprintDifference(bot);
|
let explanation = blueprint.explainBlueprintDifference(bot);
|
||||||
|
@ -97,11 +95,11 @@ export class Blueprint {
|
||||||
var placement_string = "[\n";
|
var placement_string = "[\n";
|
||||||
for (let row of placement) {
|
for (let row of placement) {
|
||||||
placement_string += "[";
|
placement_string += "[";
|
||||||
for (let i = 0; i < row.length - 1; i++) {
|
for (let i = 0; i < row.y_amount - 1; i++) {
|
||||||
let item = row[i];
|
let item = row[i];
|
||||||
placement_string += `${item}, `;
|
placement_string += `${item}, `;
|
||||||
}
|
}
|
||||||
let final_item = row[row.length - 1];
|
let final_item = row[row.y_amount - 1];
|
||||||
placement_string += `${final_item}],\n`;
|
placement_string += `${final_item}],\n`;
|
||||||
}
|
}
|
||||||
placement_string += "]";
|
placement_string += "]";
|
||||||
|
@ -118,7 +116,7 @@ export class Blueprint {
|
||||||
explainBlueprintDifference(bot) {
|
explainBlueprintDifference(bot) {
|
||||||
var explanation = "";
|
var explanation = "";
|
||||||
const levels = this.data.levels;
|
const levels = this.data.levels;
|
||||||
for (let i = 0; i < levels.length; i++) {
|
for (let i = 0; i < levels.y_amount; i++) {
|
||||||
let level_explanation = this.explainLevelDifference(bot, i);
|
let level_explanation = this.explainLevelDifference(bot, i);
|
||||||
explanation += level_explanation + "\n";
|
explanation += level_explanation + "\n";
|
||||||
}
|
}
|
||||||
|
@ -129,7 +127,7 @@ export class Blueprint {
|
||||||
const mismatches = results.mismatches;
|
const mismatches = results.mismatches;
|
||||||
const levelData = this.data.levels[levelNum];
|
const levelData = this.data.levels[levelNum];
|
||||||
|
|
||||||
if (mismatches.length === 0) {
|
if (mismatches.y_amount === 0) {
|
||||||
return `Level ${levelData.level} is complete`;
|
return `Level ${levelData.level} is complete`;
|
||||||
}
|
}
|
||||||
var explanation = `Level ${levelData.level} `;
|
var explanation = `Level ${levelData.level} `;
|
||||||
|
@ -153,7 +151,7 @@ export class Blueprint {
|
||||||
const levels = this.data.levels;
|
const levels = this.data.levels;
|
||||||
const mismatches = [];
|
const mismatches = [];
|
||||||
const matches = [];
|
const matches = [];
|
||||||
for (let i = 0; i < levels.length; i++) {
|
for (let i = 0; i < levels.y_amount; i++) {
|
||||||
const result = this.checkLevel(bot, i);
|
const result = this.checkLevel(bot, i);
|
||||||
mismatches.push(...result.mismatches);
|
mismatches.push(...result.mismatches);
|
||||||
matches.push(...result.matches);
|
matches.push(...result.matches);
|
||||||
|
@ -173,9 +171,9 @@ export class Blueprint {
|
||||||
const mismatches = [];
|
const mismatches = [];
|
||||||
const matches = [];
|
const matches = [];
|
||||||
|
|
||||||
for (let zOffset = 0; zOffset < placement.length; zOffset++) {
|
for (let zOffset = 0; zOffset < placement.y_amount; zOffset++) {
|
||||||
const row = placement[zOffset];
|
const row = placement[zOffset];
|
||||||
for (let xOffset = 0; xOffset < row.length; xOffset++) {
|
for (let xOffset = 0; xOffset < row.y_amount; xOffset++) {
|
||||||
const blockName = row[xOffset];
|
const blockName = row[xOffset];
|
||||||
|
|
||||||
const x = startCoords[0] + xOffset;
|
const x = startCoords[0] + xOffset;
|
||||||
|
@ -240,15 +238,15 @@ export class Blueprint {
|
||||||
|
|
||||||
// Update bounds
|
// Update bounds
|
||||||
minX = Math.min(minX, baseX);
|
minX = Math.min(minX, baseX);
|
||||||
maxX = Math.max(maxX, baseX + placement[0].length - 1);
|
maxX = Math.max(maxX, baseX + placement[0].y_amount - 1);
|
||||||
minY = Math.min(minY, baseY);
|
minY = Math.min(minY, baseY);
|
||||||
maxY = Math.max(maxY, baseY);
|
maxY = Math.max(maxY, baseY);
|
||||||
minZ = Math.min(minZ, baseZ);
|
minZ = Math.min(minZ, baseZ);
|
||||||
maxZ = Math.max(maxZ, baseZ + placement.length - 1);
|
maxZ = Math.max(maxZ, baseZ + placement.y_amount - 1);
|
||||||
|
|
||||||
// Loop through the 2D placement array
|
// Loop through the 2D placement array
|
||||||
for (let z = 0; z < placement.length; z++) {
|
for (let z = 0; z < placement.y_amount; z++) {
|
||||||
for (let x = 0; x < placement[z].length; x++) {
|
for (let x = 0; x < placement[z].y_amount; x++) {
|
||||||
const blockType = placement[z][x];
|
const blockType = placement[z][x];
|
||||||
if (blockType) {
|
if (blockType) {
|
||||||
const setblockCommand = `/setblock ${baseX + x} ${baseY} ${baseZ + z} ${blockType}`;
|
const setblockCommand = `/setblock ${baseX + x} ${baseY} ${baseZ + z} ${blockType}`;
|
||||||
|
@ -289,15 +287,15 @@ export class Blueprint {
|
||||||
|
|
||||||
// Update bounds
|
// Update bounds
|
||||||
minX = Math.min(minX, baseX) - 30;
|
minX = Math.min(minX, baseX) - 30;
|
||||||
maxX = Math.max(maxX, baseX + placement[0].length - 1) + 30;
|
maxX = Math.max(maxX, baseX + placement[0].y_amount - 1) + 30;
|
||||||
minY = Math.min(minY, baseY);
|
minY = Math.min(minY, baseY);
|
||||||
maxY = Math.max(maxY, baseY);
|
maxY = Math.max(maxY, baseY);
|
||||||
minZ = Math.min(minZ, baseZ) - 30;
|
minZ = Math.min(minZ, baseZ) - 30;
|
||||||
maxZ = Math.max(maxZ, baseZ + placement.length - 1) + 30;
|
maxZ = Math.max(maxZ, baseZ + placement.y_amount - 1) + 30;
|
||||||
|
|
||||||
// Loop through the 2D placement array
|
// Loop through the 2D placement array
|
||||||
for (let z = 0; z < placement.length; z++) {
|
for (let z = 0; z < placement.y_amount; z++) {
|
||||||
for (let x = 0; x < placement[z].length; x++) {
|
for (let x = 0; x < placement[z].y_amount; x++) {
|
||||||
const blockType = placement[z][x];
|
const blockType = placement[z][x];
|
||||||
if (blockType) {
|
if (blockType) {
|
||||||
const setblockCommand = `/setblock ${baseX + x} ${baseY} ${baseZ + z} air`;
|
const setblockCommand = `/setblock ${baseX + x} ${baseY} ${baseZ + z} air`;
|
||||||
|
@ -350,8 +348,8 @@ export function proceduralGeneration(m = 20,
|
||||||
complexity = 4,
|
complexity = 4,
|
||||||
startCoord = [148,-60,-170]) {
|
startCoord = [148,-60,-170]) {
|
||||||
// Build 3D space
|
// Build 3D space
|
||||||
const matrix = Array.from({length: p}, () =>
|
const matrix = Array.from({y_amount: p}, () =>
|
||||||
Array.from({length: m}, () =>
|
Array.from({y_amount: m}, () =>
|
||||||
Array(n).fill('air')
|
Array(n).fill('air')
|
||||||
)
|
)
|
||||||
);
|
);
|
||||||
|
@ -359,7 +357,7 @@ export function proceduralGeneration(m = 20,
|
||||||
// todo: extrapolate into another param? then have set materials be dynamic?
|
// todo: extrapolate into another param? then have set materials be dynamic?
|
||||||
let roomMaterials = ["stone", "terracotta", "quartz_block", "copper_block", "purpur_block"]
|
let roomMaterials = ["stone", "terracotta", "quartz_block", "copper_block", "purpur_block"]
|
||||||
|
|
||||||
if (complexity < roomMaterials.length) {
|
if (complexity < roomMaterials.y_amount) {
|
||||||
roomMaterials = roomMaterials.slice(0, complexity + 1);
|
roomMaterials = roomMaterials.slice(0, complexity + 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -510,9 +508,9 @@ export function proceduralGeneration(m = 20,
|
||||||
// Takes in a room and randomly converts some faces to be windows
|
// Takes in a room and randomly converts some faces to be windows
|
||||||
function addWindowsAsSquares(matrix, x, y, z, newLength, newWidth, newDepth, material) {
|
function addWindowsAsSquares(matrix, x, y, z, newLength, newWidth, newDepth, material) {
|
||||||
// Matrix dimensions
|
// Matrix dimensions
|
||||||
const matrixDepth = matrix.length;
|
const matrixDepth = matrix.y_amount;
|
||||||
const matrixLength = matrix[0].length;
|
const matrixLength = matrix[0].y_amount;
|
||||||
const matrixWidth = matrix[0][0].length;
|
const matrixWidth = matrix[0][0].y_amount;
|
||||||
const windowX = Math.ceil(minRoomWidth / 2)
|
const windowX = Math.ceil(minRoomWidth / 2)
|
||||||
const windowY = Math.ceil(minRoomLength / 2)
|
const windowY = Math.ceil(minRoomLength / 2)
|
||||||
const windowZ = Math.ceil(minRoomDepth / 2)
|
const windowZ = Math.ceil(minRoomDepth / 2)
|
||||||
|
@ -593,9 +591,9 @@ export function proceduralGeneration(m = 20,
|
||||||
|
|
||||||
function addWindowsAsPlane(matrix, x, y, z, newLength, newWidth, newDepth, material) {
|
function addWindowsAsPlane(matrix, x, y, z, newLength, newWidth, newDepth, material) {
|
||||||
// Ensure the new dimensions are within bounds
|
// Ensure the new dimensions are within bounds
|
||||||
const maxX = matrix[0].length;
|
const maxX = matrix[0].y_amount;
|
||||||
const maxY = matrix[0][0].length;
|
const maxY = matrix[0][0].y_amount;
|
||||||
const maxZ = matrix.length;
|
const maxZ = matrix.y_amount;
|
||||||
|
|
||||||
// Each face has a 30% chance of becoming a window
|
// Each face has a 30% chance of becoming a window
|
||||||
if (Math.random() < 0.8) {
|
if (Math.random() < 0.8) {
|
||||||
|
@ -643,21 +641,21 @@ export function proceduralGeneration(m = 20,
|
||||||
|
|
||||||
|
|
||||||
//still a little buggy
|
//still a little buggy
|
||||||
function addStairs(matrix, x, y, z, length, width, material) {
|
function addStairs(matrix, x, y, z, y_amount, width, material) {
|
||||||
let currentZ = z;
|
let currentZ = z;
|
||||||
let currentX = x + 1;
|
let currentX = x + 1;
|
||||||
let currentY = y + 1;
|
let currentY = y + 1;
|
||||||
let direction = 0;
|
let direction = 0;
|
||||||
let stepCount = 0;
|
let stepCount = 0;
|
||||||
const maxSteps = length * width; // Safety limit
|
const maxSteps = y_amount * width; // Safety limit
|
||||||
|
|
||||||
while (currentZ >= 0 && currentX < x + length - 1 && currentY < y + width - 1 && stepCount < maxSteps) {
|
while (currentZ >= 0 && currentX < x + y_amount - 1 && currentY < y + width - 1 && stepCount < maxSteps) {
|
||||||
// Place stair block
|
// Place stair block
|
||||||
matrix[currentZ][currentX][currentY] = material || 'stone';
|
matrix[currentZ][currentX][currentY] = material || 'stone';
|
||||||
|
|
||||||
// Clear 3 blocks above for headroom
|
// Clear 3 blocks above for headroom
|
||||||
for (let i = 1; i <= 3; i++) {
|
for (let i = 1; i <= 3; i++) {
|
||||||
if (currentZ + i < matrix.length) {
|
if (currentZ + i < matrix.y_amount) {
|
||||||
matrix[currentZ + i][currentX][currentY] = 'air';
|
matrix[currentZ + i][currentX][currentY] = 'air';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -665,8 +663,8 @@ export function proceduralGeneration(m = 20,
|
||||||
// Move to next position based on direction
|
// Move to next position based on direction
|
||||||
if (direction === 0) {
|
if (direction === 0) {
|
||||||
currentX++;
|
currentX++;
|
||||||
if (currentX >= x + length - 1) {
|
if (currentX >= x + y_amount - 1) {
|
||||||
currentX = x + length - 2;
|
currentX = x + y_amount - 2;
|
||||||
direction = 1;
|
direction = 1;
|
||||||
} else {
|
} else {
|
||||||
currentZ--;
|
currentZ--;
|
||||||
|
@ -700,7 +698,7 @@ export function proceduralGeneration(m = 20,
|
||||||
// Consider a random probability of adding a carpet
|
// Consider a random probability of adding a carpet
|
||||||
if (Math.random() < probability) {
|
if (Math.random() < probability) {
|
||||||
// Choose a random color for the carpet
|
// Choose a random color for the carpet
|
||||||
let randomColor = colors[Math.floor(Math.random() * colors.length)];
|
let randomColor = colors[Math.floor(Math.random() * colors.y_amount)];
|
||||||
// Add carpet one z position above the floor with a random color
|
// Add carpet one z position above the floor with a random color
|
||||||
matrix[z + 1][x][y] = `${randomColor}_carpet`;
|
matrix[z + 1][x][y] = `${randomColor}_carpet`;
|
||||||
}
|
}
|
||||||
|
@ -773,7 +771,7 @@ export function proceduralGeneration(m = 20,
|
||||||
|
|
||||||
for (let attempt = 0; attempt < 150; attempt++) {
|
for (let attempt = 0; attempt < 150; attempt++) {
|
||||||
|
|
||||||
const material = roomMaterials[Math.floor(Math.random() * roomMaterials.length)];
|
const material = roomMaterials[Math.floor(Math.random() * roomMaterials.y_amount)];
|
||||||
|
|
||||||
|
|
||||||
// dimensions of room
|
// dimensions of room
|
||||||
|
@ -790,7 +788,7 @@ export function proceduralGeneration(m = 20,
|
||||||
newZ = 0; // Ground floor
|
newZ = 0; // Ground floor
|
||||||
|
|
||||||
if (validateAndBuildBorder(matrix, newX, newY, newZ, newLength, newWidth, newDepth, m, n, p, material)) {
|
if (validateAndBuildBorder(matrix, newX, newY, newZ, newLength, newWidth, newDepth, m, n, p, material)) {
|
||||||
lastRoom = {x: newX, y: newY, z: newZ, length: newLength, width: newWidth, depth: newDepth};
|
lastRoom = {x: newX, y: newY, z: newZ, y_amount: newLength, width: newWidth, depth: newDepth};
|
||||||
roomPlaced = true;
|
roomPlaced = true;
|
||||||
placedRooms++;
|
placedRooms++;
|
||||||
|
|
||||||
|
@ -820,14 +818,14 @@ export function proceduralGeneration(m = 20,
|
||||||
|
|
||||||
embellishments(carpetStyle, windowStyle, matrix, newX, newY, newZ, newLength, newWidth, newDepth, material)
|
embellishments(carpetStyle, windowStyle, matrix, newX, newY, newZ, newLength, newWidth, newDepth, material)
|
||||||
|
|
||||||
// addLadder(matrix, lastRoom.x + Math.floor(lastRoom.length / 2),
|
// addLadder(matrix, lastRoom.x + Math.floor(lastRoom.y_amount / 2),
|
||||||
// lastRoom.y + Math.floor(lastRoom.width / 2),
|
// lastRoom.y + Math.floor(lastRoom.width / 2),
|
||||||
// newZ); // Adding the ladder
|
// newZ); // Adding the ladder
|
||||||
|
|
||||||
addStairs(matrix, newX, newY, newZ, newLength, newWidth, material)
|
addStairs(matrix, newX, newY, newZ, newLength, newWidth, material)
|
||||||
|
|
||||||
|
|
||||||
lastRoom = {x: newX, y: newY, z: newZ, length: newLength, width: newWidth, depth: newDepth};
|
lastRoom = {x: newX, y: newY, z: newZ, y_amount: newLength, width: newWidth, depth: newDepth};
|
||||||
roomPlaced = true;
|
roomPlaced = true;
|
||||||
placedRooms++;
|
placedRooms++;
|
||||||
break;
|
break;
|
||||||
|
@ -847,7 +845,7 @@ export function proceduralGeneration(m = 20,
|
||||||
addDoor(matrix, lastRoom.x, lastRoom.y + Math.floor(lastRoom.width / 2), lastRoom.z, material);
|
addDoor(matrix, lastRoom.x, lastRoom.y + Math.floor(lastRoom.width / 2), lastRoom.z, material);
|
||||||
|
|
||||||
|
|
||||||
lastRoom = {x: newX, y: newY, z: newZ, length: newLength, width: newWidth, depth: newDepth};
|
lastRoom = {x: newX, y: newY, z: newZ, y_amount: newLength, width: newWidth, depth: newDepth};
|
||||||
roomPlaced = true;
|
roomPlaced = true;
|
||||||
placedRooms++;
|
placedRooms++;
|
||||||
break;
|
break;
|
||||||
|
@ -855,7 +853,7 @@ export function proceduralGeneration(m = 20,
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 'right':
|
case 'right':
|
||||||
newX = lastRoom.x + lastRoom.length - 1;
|
newX = lastRoom.x + lastRoom.y_amount - 1;
|
||||||
newY = lastRoom.y;
|
newY = lastRoom.y;
|
||||||
newZ = lastRoom.z;
|
newZ = lastRoom.z;
|
||||||
if (validateAndBuildBorder(matrix, newX, newY, newZ, newLength, newWidth, newDepth, m, n, p, material)) {
|
if (validateAndBuildBorder(matrix, newX, newY, newZ, newLength, newWidth, newDepth, m, n, p, material)) {
|
||||||
|
@ -863,12 +861,12 @@ export function proceduralGeneration(m = 20,
|
||||||
embellishments(carpetStyle, windowStyle, matrix, newX, newY, newZ, newLength, newWidth, newDepth, material)
|
embellishments(carpetStyle, windowStyle, matrix, newX, newY, newZ, newLength, newWidth, newDepth, material)
|
||||||
|
|
||||||
|
|
||||||
addDoor(matrix, lastRoom.x + lastRoom.length - 1,
|
addDoor(matrix, lastRoom.x + lastRoom.y_amount - 1,
|
||||||
lastRoom.y + Math.floor(lastRoom.width / 2),
|
lastRoom.y + Math.floor(lastRoom.width / 2),
|
||||||
lastRoom.z, material);
|
lastRoom.z, material);
|
||||||
|
|
||||||
|
|
||||||
lastRoom = {x: newX, y: newY, z: newZ, length: newLength, width: newWidth, depth: newDepth};
|
lastRoom = {x: newX, y: newY, z: newZ, y_amount: newLength, width: newWidth, depth: newDepth};
|
||||||
roomPlaced = true;
|
roomPlaced = true;
|
||||||
placedRooms++;
|
placedRooms++;
|
||||||
break;
|
break;
|
||||||
|
@ -884,12 +882,12 @@ export function proceduralGeneration(m = 20,
|
||||||
embellishments(carpetStyle, windowStyle, matrix, newX, newY, newZ, newLength, newWidth, newDepth, material)
|
embellishments(carpetStyle, windowStyle, matrix, newX, newY, newZ, newLength, newWidth, newDepth, material)
|
||||||
|
|
||||||
|
|
||||||
addDoor(matrix, lastRoom.x + Math.floor(lastRoom.length / 2),
|
addDoor(matrix, lastRoom.x + Math.floor(lastRoom.y_amount / 2),
|
||||||
lastRoom.y + lastRoom.width - 1,
|
lastRoom.y + lastRoom.width - 1,
|
||||||
lastRoom.z, material);
|
lastRoom.z, material);
|
||||||
|
|
||||||
|
|
||||||
lastRoom = {x: newX, y: newY, z: newZ, length: newLength, width: newWidth, depth: newDepth};
|
lastRoom = {x: newX, y: newY, z: newZ, y_amount: newLength, width: newWidth, depth: newDepth};
|
||||||
roomPlaced = true;
|
roomPlaced = true;
|
||||||
placedRooms++;
|
placedRooms++;
|
||||||
break;
|
break;
|
||||||
|
@ -905,12 +903,12 @@ export function proceduralGeneration(m = 20,
|
||||||
embellishments(carpetStyle, windowStyle, matrix, newX, newY, newZ, newLength, newWidth, newDepth, material)
|
embellishments(carpetStyle, windowStyle, matrix, newX, newY, newZ, newLength, newWidth, newDepth, material)
|
||||||
|
|
||||||
|
|
||||||
addDoor(matrix, lastRoom.x + Math.floor(lastRoom.length / 2),
|
addDoor(matrix, lastRoom.x + Math.floor(lastRoom.y_amount / 2),
|
||||||
lastRoom.y,
|
lastRoom.y,
|
||||||
lastRoom.z, material);
|
lastRoom.z, material);
|
||||||
|
|
||||||
|
|
||||||
lastRoom = {x: newX, y: newY, z: newZ, length: newLength, width: newWidth, depth: newDepth};
|
lastRoom = {x: newX, y: newY, z: newZ, y_amount: newLength, width: newWidth, depth: newDepth};
|
||||||
roomPlaced = true;
|
roomPlaced = true;
|
||||||
placedRooms++;
|
placedRooms++;
|
||||||
break;
|
break;
|
||||||
|
@ -978,7 +976,7 @@ function printMatrix(matrix) {
|
||||||
*/
|
*/
|
||||||
function matrixToBlueprint(matrix, startCoord) {
|
function matrixToBlueprint(matrix, startCoord) {
|
||||||
// Validate inputs
|
// Validate inputs
|
||||||
if (!Array.isArray(matrix) || !Array.isArray(startCoord) || startCoord.length !== 3) {
|
if (!Array.isArray(matrix) || !Array.isArray(startCoord) || startCoord.y_amount !== 3) {
|
||||||
console.log(matrix)
|
console.log(matrix)
|
||||||
throw new Error('Invalid input format');
|
throw new Error('Invalid input format');
|
||||||
}
|
}
|
||||||
|
@ -1003,6 +1001,85 @@ function matrixToBlueprint(matrix, startCoord) {
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async function getBlockName(bot, coordinate) {
|
||||||
|
const blockAtLocation = bot.blockAt(new Vec3(coordinate.x, coordinate.y, coordinate.z));
|
||||||
|
const blockName = blockAtLocation ? bot.registry.blocks[blockAtLocation.type].name : "air";
|
||||||
|
return blockName;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Converts a world location to a blueprint. takes some time to ensure that the chunks are loaded before conversion.
|
||||||
|
* @param startCoord - [x,y,z] that signifies the start of the blueprint
|
||||||
|
* @param y_amount - how many spaces you want to register from the start coordinate in the y dimension
|
||||||
|
* @param x_amount - how many spaces in the x direction on minecraft
|
||||||
|
* @param z_amount - how many spaces from the start coordinate in the z direction in minecraft
|
||||||
|
* @param bot - the mineflayer agent (ex. andy)
|
||||||
|
* @returns - a Blueprint object of the converted blueprint
|
||||||
|
*/
|
||||||
|
export async function worldToBlueprint(startCoord, y_amount, x_amount, z_amount, bot) {
|
||||||
|
await bot.waitForChunksToLoad();
|
||||||
|
|
||||||
|
const materials = {};
|
||||||
|
|
||||||
|
const levels = [];
|
||||||
|
for (let y = 0; y < y_amount; y++) {
|
||||||
|
const placement = [];
|
||||||
|
const coordinates = [startCoord.x, startCoord.y + y, startCoord.z];
|
||||||
|
for (let z = 0; z < z_amount; z++) {
|
||||||
|
const row = [];
|
||||||
|
for (let x = 0; x < x_amount; x++) {
|
||||||
|
const worldCoord = {
|
||||||
|
x: startCoord.x + x,
|
||||||
|
y: startCoord.y + y,
|
||||||
|
z: startCoord.z + z
|
||||||
|
};
|
||||||
|
await bot.waitForChunksToLoad(worldCoord);
|
||||||
|
const blockName = await getBlockName(bot, worldCoord);
|
||||||
|
row.push(blockName);
|
||||||
|
if (blockName !== 'air') {
|
||||||
|
materials[blockName] = (materials[blockName] || 0) + 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
placement.push(row);
|
||||||
|
}
|
||||||
|
levels.push({
|
||||||
|
level: y,
|
||||||
|
coordinates: coordinates,
|
||||||
|
placement: placement
|
||||||
|
})
|
||||||
|
}
|
||||||
|
console.log(levels);
|
||||||
|
const blueprint_data = {
|
||||||
|
materials: materials,
|
||||||
|
levels: levels
|
||||||
|
}
|
||||||
|
return blueprint_data
|
||||||
|
}
|
||||||
|
|
||||||
|
export function blueprintToTask(blueprint_data, num_agents) {
|
||||||
|
let initialInventory = {}
|
||||||
|
for (let j = 0; j < num_agents; j++) {
|
||||||
|
initialInventory[JSON.stringify(j)] = {};
|
||||||
|
}
|
||||||
|
|
||||||
|
let give_agent = 0;
|
||||||
|
for (const key of Object.keys(blueprint_data.materials)) {
|
||||||
|
initialInventory[JSON.stringify(give_agent)][key] = blueprint_data.materials[key];
|
||||||
|
give_agent = (give_agent + 1) % num_agents;
|
||||||
|
}
|
||||||
|
|
||||||
|
const task = {
|
||||||
|
type: "construction",
|
||||||
|
goal: "Make a structure with the blueprint below",
|
||||||
|
conversation: "Let's share materials and make a structure with the blueprint",
|
||||||
|
agent_count: 2,
|
||||||
|
blueprint: blueprint_data,
|
||||||
|
initial_inventory: initialInventory,
|
||||||
|
};
|
||||||
|
return task;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
// testing code
|
// testing code
|
||||||
|
|
|
@ -379,7 +379,7 @@ export class Prompter {
|
||||||
let prompt = this.profile.saving_memory;
|
let prompt = this.profile.saving_memory;
|
||||||
prompt = await this.replaceStrings(prompt, null, null, to_summarize);
|
prompt = await this.replaceStrings(prompt, null, null, to_summarize);
|
||||||
let resp = await this.chat_model.sendRequest([], prompt);
|
let resp = await this.chat_model.sendRequest([], prompt);
|
||||||
await this._saveLog(prompt, null, resp, 'memSaving');
|
await this._saveLog(prompt, to_summarize, resp, 'memSaving');
|
||||||
if (resp?.includes('</think>')) {
|
if (resp?.includes('</think>')) {
|
||||||
const [_, afterThink] = resp.split('</think>')
|
const [_, afterThink] = resp.split('</think>')
|
||||||
resp = afterThink
|
resp = afterThink
|
||||||
|
|
BIN
tasks/.DS_Store
vendored
BIN
tasks/.DS_Store
vendored
Binary file not shown.
688
tasks/construction_tasks/custom/pyramid.json
Normal file
688
tasks/construction_tasks/custom/pyramid.json
Normal file
|
@ -0,0 +1,688 @@
|
||||||
|
{
|
||||||
|
"pyramid": {
|
||||||
|
"type": "construction",
|
||||||
|
"goal": "Make a structure with the blueprint below",
|
||||||
|
"conversation": "Let's share materials and make a structure with the blueprint",
|
||||||
|
"agent_count": 2,
|
||||||
|
"blueprint": {
|
||||||
|
"materials": {
|
||||||
|
"polished_granite": 1,
|
||||||
|
"gold_block": 27,
|
||||||
|
"stone_bricks": 41,
|
||||||
|
"polished_andesite": 34,
|
||||||
|
"quartz_block": 16,
|
||||||
|
"stone": 23,
|
||||||
|
"polished_diorite": 21,
|
||||||
|
"quartz_pillar": 2,
|
||||||
|
"glowstone": 3
|
||||||
|
},
|
||||||
|
"levels": [
|
||||||
|
{
|
||||||
|
"level": 0,
|
||||||
|
"coordinates": [
|
||||||
|
-60,
|
||||||
|
-60,
|
||||||
|
6
|
||||||
|
],
|
||||||
|
"placement": [
|
||||||
|
[
|
||||||
|
"polished_granite",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"gold_block",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite",
|
||||||
|
"gold_block",
|
||||||
|
"quartz_block",
|
||||||
|
"polished_andesite",
|
||||||
|
"gold_block",
|
||||||
|
"stone_bricks",
|
||||||
|
"gold_block"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite",
|
||||||
|
"stone",
|
||||||
|
"polished_diorite",
|
||||||
|
"polished_andesite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_diorite",
|
||||||
|
"gold_block"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"polished_andesite",
|
||||||
|
"stone",
|
||||||
|
"polished_diorite",
|
||||||
|
"polished_andesite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_diorite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"gold_block",
|
||||||
|
"polished_diorite",
|
||||||
|
"polished_andesite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_diorite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"quartz_block",
|
||||||
|
"polished_andesite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_diorite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite",
|
||||||
|
"quartz_block"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"polished_andesite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_diorite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite",
|
||||||
|
"polished_diorite",
|
||||||
|
"stone_bricks"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"gold_block",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_diorite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite",
|
||||||
|
"polished_diorite",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_diorite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite",
|
||||||
|
"polished_diorite",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite",
|
||||||
|
"gold_block"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"gold_block",
|
||||||
|
"gold_block",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite",
|
||||||
|
"quartz_block",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite",
|
||||||
|
"gold_block",
|
||||||
|
"gold_block"
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"level": 1,
|
||||||
|
"coordinates": [
|
||||||
|
-60,
|
||||||
|
-60,
|
||||||
|
6
|
||||||
|
],
|
||||||
|
"placement": [
|
||||||
|
[
|
||||||
|
"quartz_pillar",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"gold_block",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite",
|
||||||
|
"quartz_block",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite",
|
||||||
|
"gold_block",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"stone_bricks",
|
||||||
|
"stone",
|
||||||
|
"polished_diorite",
|
||||||
|
"polished_andesite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"stone_bricks",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"polished_andesite",
|
||||||
|
"polished_diorite",
|
||||||
|
"polished_andesite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_diorite",
|
||||||
|
"polished_andesite",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"quartz_block",
|
||||||
|
"polished_andesite",
|
||||||
|
"stone",
|
||||||
|
"glowstone",
|
||||||
|
"polished_diorite",
|
||||||
|
"stone",
|
||||||
|
"quartz_block",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"stone_bricks",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_diorite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"stone_bricks",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"polished_andesite",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_diorite",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite",
|
||||||
|
"polished_andesite",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"gold_block",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite",
|
||||||
|
"quartz_block",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_andesite",
|
||||||
|
"gold_block",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"level": 2,
|
||||||
|
"coordinates": [
|
||||||
|
-60,
|
||||||
|
-60,
|
||||||
|
6
|
||||||
|
],
|
||||||
|
"placement": [
|
||||||
|
[
|
||||||
|
"quartz_pillar",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"gold_block",
|
||||||
|
"stone_bricks",
|
||||||
|
"quartz_block",
|
||||||
|
"gold_block",
|
||||||
|
"gold_block",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_diorite",
|
||||||
|
"polished_andesite",
|
||||||
|
"stone",
|
||||||
|
"polished_andesite",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"quartz_block",
|
||||||
|
"polished_andesite",
|
||||||
|
"glowstone",
|
||||||
|
"stone_bricks",
|
||||||
|
"quartz_block",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"gold_block",
|
||||||
|
"stone",
|
||||||
|
"stone_bricks",
|
||||||
|
"polished_diorite",
|
||||||
|
"stone_bricks",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"gold_block",
|
||||||
|
"polished_andesite",
|
||||||
|
"quartz_block",
|
||||||
|
"stone_bricks",
|
||||||
|
"gold_block",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"level": 3,
|
||||||
|
"coordinates": [
|
||||||
|
-60,
|
||||||
|
-60,
|
||||||
|
6
|
||||||
|
],
|
||||||
|
"placement": [
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"gold_block",
|
||||||
|
"quartz_block",
|
||||||
|
"gold_block",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"quartz_block",
|
||||||
|
"glowstone",
|
||||||
|
"quartz_block",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"gold_block",
|
||||||
|
"quartz_block",
|
||||||
|
"gold_block",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
]
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"level": 4,
|
||||||
|
"coordinates": [
|
||||||
|
-60,
|
||||||
|
-60,
|
||||||
|
6
|
||||||
|
],
|
||||||
|
"placement": [
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"gold_block",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air",
|
||||||
|
"air"
|
||||||
|
]
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"initial_inventory": {
|
||||||
|
"0": {
|
||||||
|
"polished_granite": 1,
|
||||||
|
"stone_bricks": 41,
|
||||||
|
"quartz_block": 16,
|
||||||
|
"polished_diorite": 21,
|
||||||
|
"glowstone": 3
|
||||||
|
},
|
||||||
|
"1": {
|
||||||
|
"gold_block": 27,
|
||||||
|
"polished_andesite": 34,
|
||||||
|
"stone": 23,
|
||||||
|
"quartz_pillar": 2
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
1034
tasks/construction_tasks/custom/tasks.json
Normal file
1034
tasks/construction_tasks/custom/tasks.json
Normal file
File diff suppressed because it is too large
Load diff
54
tasks/construction_tasks/get_blueprint.js
Normal file
54
tasks/construction_tasks/get_blueprint.js
Normal file
|
@ -0,0 +1,54 @@
|
||||||
|
import mineflayer from 'mineflayer';
|
||||||
|
import { worldToBlueprint, blueprintToTask } from '../../src/agent/task_types/construction_tasks.js';
|
||||||
|
import fs from 'fs';
|
||||||
|
import { start } from 'repl';
|
||||||
|
|
||||||
|
const bot = mineflayer.createBot({
|
||||||
|
host: 'localhost', // Replace with your server IP or hostname
|
||||||
|
port: 55916, // Replace with your server port
|
||||||
|
username: 'andy', // Replace with your bot's username
|
||||||
|
// password: 'your_bot_password' // Only if the server has online-mode=true
|
||||||
|
});
|
||||||
|
|
||||||
|
bot.on('spawn', async () => {
|
||||||
|
console.log("Bot spawned. Starting blueprint check...");
|
||||||
|
// set this to be minX, minY, minZ
|
||||||
|
const startCoord = {
|
||||||
|
x: -60,
|
||||||
|
y: 1,
|
||||||
|
z: 6,
|
||||||
|
}
|
||||||
|
bot.chat(`/tp andy ${startCoord.x} ${startCoord.y} ${startCoord.z}`);
|
||||||
|
const yOffset = 5;
|
||||||
|
const xOffset = 10;
|
||||||
|
const zOffset = 10;
|
||||||
|
|
||||||
|
const taskFilePath = '/Users/isadorawhite/izzy_mindcraft/mindcraft/tasks/construction_tasks/custom/pyramid.json';
|
||||||
|
const task_name = "pyramid";
|
||||||
|
|
||||||
|
|
||||||
|
setTimeout(async () => {
|
||||||
|
let task_blueprint = await worldToBlueprint(startCoord, yOffset, xOffset, zOffset, bot);
|
||||||
|
|
||||||
|
for (const level of task_blueprint.levels) {
|
||||||
|
// Perform operations on each level
|
||||||
|
console.log("Level coordinates:", level.coordinates);
|
||||||
|
const new_coordinates = [level.coordinates[0], -60, level.coordinates[2]];
|
||||||
|
level.coordinates = new_coordinates;
|
||||||
|
console.log("New coordinates:", level.coordinates);
|
||||||
|
}
|
||||||
|
console.log("Blueprint generated:", task_blueprint.levels[0].coordinates);
|
||||||
|
|
||||||
|
const task = blueprintToTask(task_blueprint, 2);
|
||||||
|
const task_collection = {}
|
||||||
|
task_collection[task_name] = task;
|
||||||
|
|
||||||
|
fs.writeFileSync(taskFilePath, JSON.stringify(task_collection, null, 2), (err) => {
|
||||||
|
if (err) {
|
||||||
|
console.error('Error writing task to file:', err);
|
||||||
|
} else {
|
||||||
|
console.log('Task dumped to file successfully.');
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}, 5000); // Delay of 5 seconds (5000 milliseconds)
|
||||||
|
});
|
BIN
tasks/construction_tasks/test.zip
Normal file
BIN
tasks/construction_tasks/test.zip
Normal file
Binary file not shown.
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
Loading…
Add table
Reference in a new issue