<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<title>画像生成プロンプト作成機(完全版)</title>
<style>
body { font-family: sans-serif; padding: 1em; background-color: #f4f4f9; }
.container { display: flex; flex-direction: column; gap: 15px; max-width: 600px; margin: 0 auto; background: #fff; padding: 20px; border-radius: 12px; box-shadow: 0 4px 8px rgba(0,0,0,0.1); }
h1 { text-align: center; color: #333; font-size: 1.5em; }
/* セクションごとの枠 */
.section-box {
border: 1px solid #ddd;
padding: 15px;
border-radius: 8px;
background-color: #fafafa;
}
.section-label {
font-weight: bold;
color: #555;
display: block;
margin-bottom: 8px;
}
/* 1. 指示入力エリア(履歴付き) */
.prompt-input {
width: 100%;
padding: 10px;
font-size: 1em;
border: 2px solid #007bff;
border-radius: 6px;
box-sizing: border-box;
margin-bottom: 8px;
}
.history-controls { display: flex; gap: 8px; align-items: center; }
select.history-select { flex-grow: 1; padding: 6px; border: 1px solid #ccc; border-radius: 4px; }
.clear-btn { font-size: 0.8em; cursor: pointer; color: #d9534f; background: none; border: 1px solid #d9534f; border-radius: 4px; padding: 4px 8px; }
/* 2. ランダムボタン */
.random-btn {
width: 100%;
padding: 10px;
font-size: 1em;
font-weight: bold;
color: #fff;
background: linear-gradient(45deg, #ff6b6b, #f06595, #845ef7);
border: none;
border-radius: 6px;
cursor: pointer;
margin-bottom: 10px;
transition: transform 0.1s;
}
.random-btn:active { transform: scale(0.98); }
/* 詳細テキストエリア */
textarea {
width: 100%;
height: 100px;
padding: 10px;
box-sizing: border-box;
border: 1px solid #ccc;
border-radius: 6px;
font-size: 1em;
line-height: 1.5;
}
/* 3. 送信エリア */
.controls { display: flex; gap: 10px; align-items: center; margin-top: 5px; }
select#aiSelector { padding: 10px; border: 1px solid #ccc; border-radius: 6px; flex-grow: 1; }
button.send-btn { padding: 10px 20px; cursor: pointer; font-size: 1em; background-color: #007bff; color: white; border: none; border-radius: 6px; font-weight: bold; }
button.send-btn:hover { background-color: #0056b3; }
</style>
</head>
<body>
<h1>🎨 画像生成プロンプト作成機</h1>
<div class="container">
<div class="section-box">
<label class="section-label">1. 何を作りますか?(指示)</label>
<input type="text" id="instructionInput" class="prompt-input"
value="360度パノラマ画像を作って。">
<div class="history-controls">
<select id="instructionHistory" class="history-select" onchange="selectHistory()">
<option value="" disabled selected>履歴から選択...</option>
</select>
<button type="button" class="clear-btn" onclick="clearHistory()">履歴削除</button>
</div>
</div>
<div class="section-box">
<label class="section-label">2. どんな情景ですか?(詳細)</label>
<button class="random-btn" onclick="generateRandomPrompt()">
🎲 ランダムな情景を生成する
</button>
<textarea id="detailArea" placeholder="ボタンを押すか、ここに入力してください..."></textarea>
</div>
<div class="controls">
<select id="aiSelector">
<option value="gemini">Google Gemini</option>
<option value="chatgpt">ChatGPT</option>
<option value="claude">Claude</option>
<option value="perplexity">Perplexity</option>
</select>
<button class="send-btn" onclick="askAI()">🚀 AIに送信</button>
</div>
</div>
<script>
// ---------------------------------------------------------
// ■ 設定:ランダムワードリスト
// ---------------------------------------------------------
const promptData = {
locations: [
"近未来都市の摩天楼", "静かな湖畔の森", "魔法使いの書斎", "荒廃した砂漠の廃墟",
"桜が舞い散る日本の神社", "深海のクリスタル宮殿", "中世ヨーロッパの城下町",
"宇宙ステーションの内部", "ネオン輝くサイバーパンクな路地裏", "幻想的な浮遊大陸"
],
times: [
"夕暮れ時、黄金色の光", "満天の星空が広がる深夜", "朝霧に包まれた早朝",
"雷雨の激しい夜", "雪が降り積もる静寂な冬", "太陽が照りつける真昼"
],
styles: [
"油絵のようなタッチ", "高精細な写真のようなリアルさ", "水彩画風の柔らかい雰囲気",
"アニメ映画のようなドラマチックな照明", "80年代レトロフューチャー調"
],
details: [
"巨大な猫が寝ている", "空飛ぶ車が行き交っている", "謎の古代文字が光っている",
"色とりどりの花が咲き乱れている", "誰もいない静寂な空間"
]
};
// ---------------------------------------------------------
// ■ 履歴管理機能 (localStorage)
// ---------------------------------------------------------
const STORAGE_KEY = 'ai_image_instruction_history_v1';
window.onload = function() {
loadHistory();
};
function saveToHistory(text) {
if (!text) return;
let history = JSON.parse(localStorage.getItem(STORAGE_KEY)) || [];
// 重複削除して先頭に追加
history = history.filter(item => item !== text);
history.unshift(text);
if (history.length > 20) history.pop();
localStorage.setItem(STORAGE_KEY, JSON.stringify(history));
loadHistory();
}
function loadHistory() {
const historySelect = document.getElementById('instructionHistory');
const history = JSON.parse(localStorage.getItem(STORAGE_KEY)) || [];
historySelect.innerHTML = '<option value="" disabled selected>履歴から選択...</option>';
// デフォルトの選択肢(履歴がない場合や追加用)
const defaults = [
"360度パノラマ画像を作って。",
"PCのデスクトップ壁紙を作って。",
"ファンタジー小説の挿絵風ポートレートを作って。",
"スマホ用の縦長壁紙を作って。",
"RPGのアイテムアイコン画像を作って。"
];
// 履歴とデフォルトをマージ
const allItems = [...new Set([...history, ...defaults])];
allItems.forEach(text => {
const option = document.createElement('option');
option.value = text;
option.text = text.length > 30 ? text.substring(0, 30) + "..." : text;
historySelect.appendChild(option);
});
}
function selectHistory() {
const historySelect = document.getElementById('instructionHistory');
const instructionInput = document.getElementById('instructionInput');
instructionInput.value = historySelect.value;
}
function clearHistory() {
if(confirm("指示の履歴を削除しますか?")) {
localStorage.removeItem(STORAGE_KEY);
loadHistory();
}
}
// ---------------------------------------------------------
// ■ ランダム生成機能
// ---------------------------------------------------------
function generateRandomPrompt() {
const detailArea = document.getElementById('detailArea');
const pick = (arr) => arr[Math.floor(Math.random() * arr.length)];
const parts = [
pick(promptData.locations),
pick(promptData.times),
pick(promptData.styles)
];
if (Math.random() > 0.5) parts.push(pick(promptData.details));
detailArea.value = parts.join("。\n") + "。";
detailArea.focus(); // 編集しやすくフォーカス
}
// ---------------------------------------------------------
// ■ 送信機能 (Instruction + Detail)
// ---------------------------------------------------------
function askAI() {
const instruction = document.getElementById('instructionInput').value.trim();
const details = document.getElementById('detailArea').value.trim();
if (!instruction || !details) {
alert("指示と詳細の両方が必要です。");
return;
}
// 履歴に保存
saveToHistory(instruction);
// 合体させてプロンプト作成
const finalPrompt = instruction + "\n\n【情景の詳細】\n" + details;
const aiService = document.getElementById('aiSelector').value;
const encodedPrompt = encodeURIComponent(finalPrompt);
let url = "";
switch (aiService) {
case "gemini": url = "https://gemini.google.com/app"; break;
case "chatgpt": url = "https://chatgpt.com/"; break;
case "claude": url = "https://claude.ai/new"; break;
case "perplexity": url = `https://www.perplexity.ai/search?q=${encodedPrompt}`; break;
}
if (aiService === 'perplexity') {
window.open(url, '_blank');
} else {
if (navigator.clipboard) {
navigator.clipboard.writeText(finalPrompt).then(() => {
if(confirm("プロンプトをコピーしました!\n\n" + aiService + "へ移動して貼り付けますか?")) {
window.open(url, '_blank');
}
});
} else {
alert("コピー機能が使えません。");
window.open(url, '_blank');
}
}
}
</script>
</body>
</html>
使用変数
| aiService | |
| allItems | |
| askAI -------( Function ) | |
| charset | |
| class | |
| clearHistory -------( Function ) | |
| defaults | |
| detailArea | |
| details | |
| encodedPrompt | |
| finalPrompt | |
| generateRandomPrompt -------( Function ) | |
| history | |
| historySelect | |
| id | |
| innerHTML | |
| instruction | |
| instructionInput | |
| item | |
| lang | |
| loadHistory -------( Function ) | |
| onchange | |
| onclick | |
| onload | |
| option | |
| parts | |
| pick | |
| placeholder | |
| promptData | |
| q | |
| saveToHistory -------( Function ) | |
| selectHistory -------( Function ) | |
| STORAGE_KEY | |
| text | |
| type | |
| url | |
| value |