Geminiに今日は、犬の絵をボックスアートに変換して、それを動かせるようにしてもらうよう依頼してみました。
まず、犬の絵をアップロードし、その後、
「この絵の犬のボクセルアートを作って操作ができるようにしてください。」
というプロンプトを入れてみました。
すぐに回答が来ました。それを示したのが以下の図です。
ただし、作成されたボクセルアートは、操作盤はあるのですが、操作盤で動いてくれません。
操作盤で動くように頼んでみたのですが、だめでした。
しかし、その代わりと言って、次のプログラムを作成してくれました。
下の点線から、点線までの間がプログラムです。
そして、使い方も提供してくれています。
使い方はこのプログラムの下に出ています。
---------------------------------
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<title>ボクセル犬 操作デモ</title>
<style>
body { margin: 0; overflow: hidden; background-color: #f0f0f0; font-family: sans-serif; }
#control-panel {
position: absolute;
bottom: 20px;
left: 20px;
width: 150px;
height: 150px;
background: rgba(0, 0, 0, 0.2);
border-radius: 20px;
display: grid;
grid-template-columns: 1fr 1fr 1fr;
grid-template-rows: 1fr 1fr 1fr;
padding: 10px;
gap: 5px;
}
.btn {
background: rgba(255, 255, 255, 0.5);
border: none;
border-radius: 5px;
font-size: 20px;
cursor: pointer;
display: flex;
align-items: center;
justify-content: center;
user-select: none;
}
.btn:active { background: rgba(255, 255, 255, 0.8); }
#btn-up { grid-column: 2; grid-row: 1; }
#btn-left { grid-column: 1; grid-row: 2; }
#btn-right { grid-column: 3; grid-row: 2; }
#btn-down { grid-column: 2; grid-row: 3; }
#instruction {
position: absolute;
top: 10px;
left: 10px;
background: rgba(255,255,255,0.8);
padding: 10px;
border-radius: 5px;
}
</style>
</head>
<body>
<div id="instruction">画面上のボタンまたはキーボードの矢印キーで犬を動かせます</div>
<div id="control-panel">
<div class="btn" id="btn-up">▲</div>
<div class="btn" id="btn-left">◀</div>
<div class="btn" id="btn-right">▶</div>
<div class="btn" id="btn-down">▼</div>
</div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/r128/three.min.js"></script>
<script>
// 1. シーン、カメラ、レンダラーのセットアップ
const scene = new THREE.Scene();
scene.background = new THREE.Color(0xa0d8ef); // 空の色
const camera = new THREE.PerspectiveCamera(60, window.innerWidth / window.innerHeight, 0.1, 1000);
camera.position.set(0, 5, 8);
camera.lookAt(0, 0, 0);
const renderer = new THREE.WebGLRenderer({ antialias: true });
renderer.setSize(window.innerWidth, window.innerHeight);
renderer.shadowMap.enabled = true;
document.body.appendChild(renderer.domElement);
// 2. ライトの設定
const ambientLight = new THREE.AmbientLight(0xffffff, 0.6);
scene.add(ambientLight);
const dirLight = new THREE.DirectionalLight(0xffffff, 0.8);
dirLight.position.set(5, 10, 7);
dirLight.castShadow = true;
scene.add(dirLight);
// 3. 地面(草地)
const groundGeometry = new THREE.BoxGeometry(10, 1, 10);
const groundMaterial = new THREE.MeshLambertMaterial({ color: 0x7cfc00 });
const ground = new THREE.Mesh(groundGeometry, groundMaterial);
ground.position.y = -0.5;
ground.receiveShadow = true;
scene.add(ground);
// 草の装飾(ランダム配置)
const grassGeo = new THREE.BoxGeometry(0.1, 0.4, 0.1);
const grassMat = new THREE.MeshBasicMaterial({ color: 0x228b22 });
for(let i=0; i<30; i++){
const grass = new THREE.Mesh(grassGeo, grassMat);
grass.position.set((Math.random()-0.5)*8, 0.2, (Math.random()-0.5)*8);
scene.add(grass);
}
// 4. ボクセル犬の作成(グループ化)
const dogGroup = new THREE.Group();
const orangeMat = new THREE.MeshLambertMaterial({ color: 0xe69b38 }); // 茶色
const whiteMat = new THREE.MeshLambertMaterial({ color: 0xffffff }); // 白
const blackMat = new THREE.MeshLambertMaterial({ color: 0x333333 }); // 黒
// 体
const bodyGeo = new THREE.BoxGeometry(1.2, 1, 1.8);
const body = new THREE.Mesh(bodyGeo, orangeMat);
body.position.y = 1;
body.castShadow = true;
dogGroup.add(body);
// 頭
const headGeo = new THREE.BoxGeometry(1, 1, 1);
const head = new THREE.Mesh(headGeo, orangeMat);
head.position.set(0, 1.8, 0.8);
head.castShadow = true;
dogGroup.add(head);
// 耳
const earGeo = new THREE.BoxGeometry(0.3, 0.4, 0.2);
const earL = new THREE.Mesh(earGeo, orangeMat);
earL.position.set(0.3, 2.4, 0.8);
dogGroup.add(earL);
const earR = new THREE.Mesh(earGeo, orangeMat);
earR.position.set(-0.3, 2.4, 0.8);
dogGroup.add(earR);
// 鼻
const noseGeo = new THREE.BoxGeometry(0.2, 0.2, 0.2);
const nose = new THREE.Mesh(noseGeo, blackMat);
nose.position.set(0, 1.7, 1.35);
dogGroup.add(nose);
// 目
const eyeGeo = new THREE.BoxGeometry(0.1, 0.1, 0.1);
const eyeL = new THREE.Mesh(eyeGeo, blackMat);
eyeL.position.set(0.25, 1.9, 1.3);
dogGroup.add(eyeL);
const eyeR = new THREE.Mesh(eyeGeo, blackMat);
eyeR.position.set(-0.25, 1.9, 1.3);
dogGroup.add(eyeR);
// しっぽ
const tailGeo = new THREE.BoxGeometry(0.3, 0.6, 0.3);
const tail = new THREE.Mesh(tailGeo, whiteMat);
tail.position.set(0, 1.5, -1);
tail.rotation.x = Math.PI / 4;
dogGroup.add(tail);
// 足(4本)
const legGeo = new THREE.BoxGeometry(0.3, 0.6, 0.3);
const legPositions = [
{x: 0.4, z: 0.6}, {x: -0.4, z: 0.6}, // 前足
{x: 0.4, z: -0.6}, {x: -0.4, z: -0.6} // 後ろ足
];
const legs = [];
legPositions.forEach(pos => {
const leg = new THREE.Mesh(legGeo, orangeMat);
leg.position.set(pos.x, 0.3, pos.z);
leg.castShadow = true;
dogGroup.add(leg);
legs.push(leg); // アニメーション用に保存
});
scene.add(dogGroup);
// 5. 操作ロジック
let moveForward = false;
let moveBackward = false;
let rotateLeft = false;
let rotateRight = false;
// キーボード操作
document.addEventListener('keydown', (e) => {
switch(e.key) {
case 'ArrowUp': moveForward = true; break;
case 'ArrowDown': moveBackward = true; break;
case 'ArrowLeft': rotateLeft = true; break;
case 'ArrowRight': rotateRight = true; break;
}
});
document.addEventListener('keyup', (e) => {
switch(e.key) {
case 'ArrowUp': moveForward = false; break;
case 'ArrowDown': moveBackward = false; break;
case 'ArrowLeft': rotateLeft = false; break;
case 'ArrowRight': rotateRight = false; break;
}
});
// 画面ボタン操作(マウス・タッチ)
const setupBtn = (id, stateName) => {
const btn = document.getElementById(id);
btn.addEventListener('mousedown', () => eval(stateName + ' = true'));
btn.addEventListener('mouseup', () => eval(stateName + ' = false'));
btn.addEventListener('touchstart', (e) => { e.preventDefault(); eval(stateName + ' = true'); });
btn.addEventListener('touchend', (e) => { e.preventDefault(); eval(stateName + ' = false'); });
};
setupBtn('btn-up', 'moveForward');
setupBtn('btn-down', 'moveBackward');
setupBtn('btn-left', 'rotateLeft');
setupBtn('btn-right', 'rotateRight');
// アニメーションループ
let walkCycle = 0;
function animate() {
requestAnimationFrame(animate);
// 移動処理
const speed = 0.05;
const rotSpeed = 0.05;
let isMoving = false;
if (rotateLeft) dogGroup.rotation.y += rotSpeed;
if (rotateRight) dogGroup.rotation.y -= rotSpeed;
if (moveForward) {
dogGroup.position.x += Math.sin(dogGroup.rotation.y) * speed;
dogGroup.position.z += Math.cos(dogGroup.rotation.y) * speed;
isMoving = true;
}
if (moveBackward) {
dogGroup.position.x -= Math.sin(dogGroup.rotation.y) * speed;
dogGroup.position.z -= Math.cos(dogGroup.rotation.y) * speed;
isMoving = true;
}
// 足のアニメーション
if (isMoving) {
walkCycle += 0.2;
legs[0].rotation.x = Math.sin(walkCycle) * 0.5;
legs[1].rotation.x = Math.sin(walkCycle + Math.PI) * 0.5;
legs[2].rotation.x = Math.sin(walkCycle + Math.PI) * 0.5;
legs[3].rotation.x = Math.sin(walkCycle) * 0.5;
} else {
// 止まったら足を戻す
legs.forEach(leg => leg.rotation.x = 0);
}
// 画面端でのループ(簡易的)
if (dogGroup.position.x > 5) dogGroup.position.x = -5;
if (dogGroup.position.x < -5) dogGroup.position.x = 5;
if (dogGroup.position.z > 5) dogGroup.position.z = -5;
if (dogGroup.position.z < -5) dogGroup.position.z = 5;
renderer.render(scene, camera);
}
animate();
// ウィンドウリサイズ対応
window.addEventListener('resize', () => {
camera.aspect = window.innerWidth / window.innerHeight;
camera.updateProjectionMatrix();
renderer.setSize(window.innerWidth, window.innerHeight);
});
</script>
</body>
</html>
-----------------------------------------
使い方
1. 上記のコードをコピーします。
2. パソコンの「メモ帳」などのテキストエディタを開きます。
3. コードを貼り付けます。
4. ファイルを保存する際、ファイル名を dog_game.html にします (拡張子を.html にしてください)。
5. 保存したファイルをダブルクリックすると、ブラウザが立ち上がり、画面左下のパネルでボクセル犬を操作できます。
この使い方通りに操作をして、、実際に犬が動くことを確かめてください。コードが問題になるという表示があるとにには、Unicode(UTF-16)を使用するといいようです。
たしかに、動きますね。

.png)
.png)






