[Unity] Claude3にローグライクを作らせようとした話。
最近話題のClaude3にunityというゲームエンジンでローグライクを作らせようとしてみました。
きっかけはたまたま視聴したYouTubeのこの動画で
Claude3がアンチスレやYouTubeのコメント欄とかを解像度高めで生成してたのをみて、
Claude3やばいな!めっちゃ賢いな!
これならローグライクも作れるんじゃね?
と思ったため、見切り発車でローグライクをClaude3に作らせてみることにしました。
この動画から、最初に長文の資料を入れてから質問をするとClaudeの性能が上がると分かったので
まずはローグライクの開発手順や設計を入れてから、作ってもらうことにします。
今回は、この記事を参考にして、Claude3にローグライクの開発手順や設計の資料を入れました。
さぁ早速ローグライクを作ってくれ!
おお!なんかすごい!
でももっとコードとかも書いて欲しい!
このプロンプトならコードを書いてくれるはず!
(なんか見返したら質問の日本語が変だな)
結構具体的になった!
あとは肝心のスクリプトを見せてくれ!
さぁどうなる?
はい、作成したスクリプトの具体的な内容を記述します。
**InputManager.cs**
```csharp
using UnityEngine;
using UnityEngine.InputSystem;
public class InputManager : MonoBehaviour
{
public delegate void OnInputAction(InputAction.CallbackContext context);
public static event OnInputAction onMove;
public static event OnInputAction onInteract;
private PlayerInput playerInput;
private void Awake()
{
playerInput = new PlayerInput();
playerInput.Player.Move.performed += HandleMoveInput;
playerInput.Player.Interact.performed += HandleInteractInput;
}
private void OnEnable()
{
playerInput.Player.Enable();
}
private void OnDisable()
{
playerInput.Player.Disable();
}
private void HandleMoveInput(InputAction.CallbackContext context)
{
onMove?.Invoke(context);
}
private void HandleInteractInput(InputAction.CallbackContext context)
{
onInteract?.Invoke(context);
}
}
```
**PlayerMovement.cs**
```csharp
using UnityEngine;
public class PlayerMovement : MonoBehaviour
{
public float moveSpeed = 5f;
private Vector2 moveDirection;
private void Awake()
{
InputManager.onMove += HandleMoveInput;
}
private void HandleMoveInput(InputAction.CallbackContext context)
{
moveDirection = context.ReadValue<Vector2>();
}
private void Update()
{
Move();
}
private void Move()
{
transform.Translate(moveDirection * moveSpeed * Time.deltaTime);
}
}
```
**MessageManager.cs**
```csharp
using UnityEngine;
using UnityEngine.UI;
public class MessageManager : MonoBehaviour
{
public Text messageText;
public Queue<string> messageQueue = new Queue<string>();
private void Update()
{
if (messageQueue.Count > 0 && string.IsNullOrEmpty(messageText.text))
{
messageText.text = messageQueue.Dequeue();
}
}
public void AddMessage(string message)
{
messageQueue.Enqueue(message);
}
}
```
**MapManager.cs**
```csharp
using UnityEngine;
using UnityEngine.Tilemaps;
public class MapManager : MonoBehaviour
{
public Tilemap dungeon;
public Tile wallTile;
public Tile floorTile;
private int[,] mapData;
private void Start()
{
LoadMapData();
RenderMap();
}
private void LoadMapData()
{
// Load map data from file or generate procedurally
mapData = new int[,]
{
{1, 1, 1, 1, 1},
{1, 0, 0, 0, 1},
{1, 0, 1, 0, 1},
{1, 0, 0, 0, 1},
{1, 1, 1, 1, 1}
};
}
private void RenderMap()
{
for (int y = 0; y < mapData.GetLength(1); y++)
{
for (int x = 0; x < mapData.GetLength(0); x++)
{
Tile tile = mapData[x, y] == 1 ? wallTile : floorTile;
dungeon.SetTile(new Vector3Int(x, y, 0), tile);
}
}
}
}
```
**WallCollision.cs**
```csharp
using UnityEngine;
public class WallCollision : MonoBehaviour
{
private void OnCollisionEnter2D(Collision2D collision)
{
if (collision.gameObject.CompareTag("Player"))
{
// Handle player collision with wall
Debug.Log("Player collided with wall");
}
}
}
```
**GameDataManager.cs**
```csharp
using UnityEngine;
public class GameDataManager : MonoBehaviour
{
private void Update()
{
if (Input.GetKeyDown(KeyCode.S))
{
SaveGame();
}
else if (Input.GetKeyDown(KeyCode.L))
{
LoadGame();
}
}
private void SaveGame()
{
// Save game data to file or PlayerPrefs
}
private void LoadGame()
{
// Load game data from file or PlayerPrefs
}
}
```
**MonsterAI.cs**
```csharp
using UnityEngine;
public class MonsterAI : MonoBehaviour
{
public float moveSpeed = 2f;
public Transform playerTransform;
private void Update()
{
MoveTowardsPlayer();
}
private void MoveTowardsPlayer()
{
Vector3 direction = (playerTransform.position - transform.position).normalized;
transform.Translate(direction * moveSpeed * Time.deltaTime);
}
}
```
**TurnManager.cs**
```csharp
using System.Collections.Generic;
using UnityEngine;
public class TurnManager : MonoBehaviour
{
public enum TurnState
{
PlayerTurn,
EnemyTurn
}
public TurnState currentTurnState;
public List<MonsterAI> enemies;
private void Update()
{
switch (currentTurnState)
{
case TurnState.PlayerTurn:
// Handle player turn
break;
case TurnState.EnemyTurn:
EnemyTurn();
break;
}
}
private void EnemyTurn()
{
foreach (MonsterAI enemy in enemies)
{
enemy.MoveTowardsPlayer();
}
// Switch to player turn after all enemies have moved
currentTurnState = TurnState.PlayerTurn;
}
}
```
**CharacterStats.cs**
```csharp
using UnityEngine;
public class CharacterStats : MonoBehaviour
{
public int maxHealth = 100;
public int currentHealth;
public int attack = 10;
public int defense = 5;
private void Start()
{
currentHealth = maxHealth;
}
}
```
**DamageCalculator.cs**
```csharp
public static class DamageCalculator
{
public static int CalculateDamage(int attackerAttack, int defenderDefense)
{
// Simple damage calculation formula: Attacker's attack - Defender's defense
return Mathf.Max(attackerAttack - defenderDefense, 1);
}
}
```
あれ?止まったな。
続きを書いてくれ!
using UnityEngine;
public static class DamageCalculator
{
public static int CalculateDamage(int attackerAttack, int defenderDefense)
{
// Simple damage calculation formula: Attacker's attack - Defender's defense
return Mathf.Max(attackerAttack - defenderDefense, 1);
}
public static void ApplyDamage(CharacterStats attacker, CharacterStats defender)
{
int damageAmount = CalculateDamage(attacker.attack, defender.defense);
defender.currentHealth -= damageAmount;
// Display damage message
string message = $"{attacker.name} dealt {damageAmount} damage to {defender.name}";
MessageManager.Instance.AddMessage(message);
// Check if defender is dead
if (defender.currentHealth <= 0)
{
HandleCharacterDeath(defender);
}
}
private static void HandleCharacterDeath(CharacterStats character)
{
// Handle character death logic (e.g., drop loot, gain experience, remove from game)
string message = $"{character.name} has died.";
MessageManager.Instance.AddMessage(message);
// Remove character from game
Destroy(character.gameObject);
}
}
おお!コードが完成した!
ところどころおかしなコードがあって
多分このコードをそのまま貼り付けてもちゃんと動くかどうかは分からないけど、プロトタイプとしては結構良さそうな感じがする。
これはここから質問してうまく調整していけば、
ちゃんとしたローグライクが作れそうなポテンシャルが
Claude3にある感じがする!
いやーなんかすごい時代になりましたね!
では今回はここまで!
続きはこちら
この記事を見た人におすすめの記事
この記事が気に入ったらサポートをしてみませんか?