MyHamburgerMenu

index.html

<!DOCTYPE html>
<html lang="ja">

<head>
  <meta charset="utf-8">
  <title>FAQ</title>
  <link rel="stylesheet" href="css/styles.css">
</head>

<body>
  <h1>FAQ</h1>
  <dl>
    <div>
      <dt>質問です</dt>
      <dd>回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。</dd>
    </div>
    <div>
      <dt>質問です</dt>
      <dd>回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。</dd>
    </div>
    <div>
      <dt>質問です</dt>
      <dd>回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。回答です。</dd>
    </div>
  </dl>

  <script src="js/main.js"></script>
</body>

</html>

style.css

h1 {
    font-size: 18px;
    border-bottom: 1px solid;
    padding: 8px 16px;
    margin-bottom: 16px;
}

dl {
    margin: 0;
}

dl>div {
    margin-bottom: 8px;
}

dt {
    padding: 8px;
    cursor: pointer;
    user-select: none;
    position: relative;
}

dt::before {
    content: 'Q. ';
}

dt::after {
    content: '+';
    position: absolute;
    top: 8px;
    right: 16px;
    transition: transform .3s;
}

dl>div.appear dt::after {
    transform: rotate(45deg);
}

dd {
    padding: 8px;
    margin: 0;
    display: none;
}

dd::before {
    content: 'A .';
}

dl>div.appear dd {
    display: block;
    animation: .3s fadeIn;
}

@keyframes fadeIn {
    0% {
        opacity: 0;
        transform: translateY(-10px);
    }

    100% {
        opacity: 1;
        transform: none;
    }
}

main.js

'use strict';

{
  const dts = document.querySelectorAll('dt');

  dts.forEach(dt => {
    dt.addEventListener('click', () => {
      dt.parentNode.classList.toggle('appear');
    });
  });
}

ゼロから始めるC++:初心者が知っておきたい基礎と応用

C++とは?その基礎と特徴

C++の概要と歴史

 C++は1983年にビャーネ・ストロヴストルップ氏によって開発された汎用プログラミング言語です。この言語は、C言語を基盤にしつつ、オブジェクト指向プログラミングやジェネリックプログラミングなどの高度な手法を導入しています。C++はその後の改良を重ね、1998年に初めて標準化(C++98)されました。その後、C++11、C++17、C++20といった形で規格が定期的に更新され、最新バージョンが登場しています。この言語は、システムレベルのプログラミングからアプリケーション開発まで幅広い分野で使用され、高い性能と柔軟性を持つ言語として知られています。

C言語との比較:どんな点が異なるのか?

 C++はC言語をベースにしているものの、オブジェクト指向プログラミングや高水準の抽象化をサポートしている点が大きな違いです。具体的には、C++では「クラス」や「オブジェクト」といった構造を通じて、コードの再利用性やメンテナンス性を向上させることができます。また、C++はテンプレートや例外処理といったジェネリックプログラミングのための機能も提供しています。一方で、C言語はシンプルで低水準な操作に向いており、高度な制御が可能なため、システムプログラミングに最適化されています。このため、C++はC言語の柔軟性を引き継ぎつつ、プログラムの設計と管理を容易にするための多くの機能を追加した言語といえます。

C++の主な用途と強み

 C++は、その高いパフォーマンスと柔軟性から、さまざまな分野で利用されています。具体的には、オペレーティングシステム、デバイスドライバ、ゲーム開発、グラフィックス処理、科学技術計算、金融市場向けアプリケーションなどに使用されます。C++の強みとしては、ネイティブコードでコンパイルされるためパフォーマンスが非常に高いこと、またシステムに密接に近いプログラムが可能である点が挙げられます。さらに、最新の標準規格により、より安全かつ効率的なコーディングが可能となっています。このように、C++は初心者からベテランプログラマーまで幅広く支持される言語です。

基本的なプログラム構造

 C++の基本的なプログラム構造はわかりやすい設計になっています。たとえば、以下は典型的なC++プログラムの例です。

  #include <iostream> using namespace std; int main() { cout << "Hello, World!" << endl; return 0; }

 このコードでは、#include <iostream>で標準ライブラリをインクルードし、coutを利用して画面に文字列を出力しています。main関数がプログラムのエントリーポイントです。基本的な構造がシンプルである反面、強力なカスタマイズ機能や拡張性も備えています。

C++でよく使うツールと環境

 C++開発を始めるためには、適切なツールと環境を整えることが重要です。一般的によく使用されるC++のコンパイラとしては、GCC(GNU Compiler Collection)やClang、Microsoft Visual C++、Intel C++ Compilerなどがあります。また、開発環境(IDE)としては、Visual Studio、CLion、Code::Blocks、Dev-C++などが利用されています。これらのツールは豊富なデバッグ機能や補完機能を提供し、開発の効率を向上させます。また、クロスプラットフォーム対応の性質を活かし、Windows、Linux、macOSなどのさまざまな環境でC++プログラムの開発が可能です。

C++プログラミングの基礎を学ぶ

変数と基本データ型

 変数とは、データを格納するための箱のようなもので、C++ではプログラム中のデータの管理に重要な役割を果たします。変数を利用するためには型を指定する必要があり、これをデータ型と呼びます。C++にはいくつかの基本データ型があり、代表的なものとして整数型(int)、浮動小数点型(float, double)、文字型(char)、ブール型(bool)があります。

 例えば、整数を格納するにはint number = 10;のように記述します。また、C++は強い静的型付けの特徴を持つため、変数を宣言する際に型を明示しなければなりません。ただし、autoというキーワードを使用することで、コンパイラに型を推測させることも可能です。

演算子と制御文の使い方

 C++にはさまざまな演算子が用意されており、足し算や引き算などの基本的な算術演算子(+、-、*、/、%)に加え、比較演算子(==、!=、<、>など)や論理演算子(&&、||、!)が一般的に使用されます。これらの演算子を活用することで、より柔軟な処理を実現できます。

 制御文は、プログラムの実行フローを制御するために用いられます。例えば、条件分岐に使用されるif、繰り返し処理を行うforやwhileループがあります。

 以下はif文とfor文の簡単な例です:

if (x > 0) {
    cout << "xは正の値です。" << endl;
}

for (int i = 0; i < 5; i++) {
    cout << "現在のiの値: " << i << endl;
}

関数とスコープ

 関数は特定の処理をまとめるために使用されるもので、プログラムの再利用性や可読性を高めます。C++では、関数を定義する際に戻り値の型、関数名、引数リストを指定します。例えば、以下のような簡単な関数を作成できます:

int add(int a, int b) {
    return a + b;
}

 関数のスコープとは、変数や関数がアクセス可能な範囲を指します。スコープには、ローカルスコープとグローバルスコープがあります。ローカルスコープは関数内で定義された変数に適用され、グローバルスコープはプログラム全体でアクセスできる変数に適用されます。

入出力操作: cinとcout

 C++のプログラムにおける基本的な入出力操作には、cinとcoutが使用されます。coutを使用するとコンソール画面にデータを出力することができ、cinを使用するとユーザーからの入力を受け取ることができます。以下はその例です:

#include <iostream>
using namespace std;

int main() {
    int age;
    cout << "年齢を入力してください: ";
    cin >> age;
    cout << "あなたの年齢は " << age << " 歳です。" << endl;
    return 0;
}

 上記例では、cinでユーザーから入力を受け取り、それをcoutで表示しています。このようにしてデータを動的に扱うことが可能です。

メモリ管理とポインタの概念

 C++の特徴の一つとして、メモリ管理をプログラマーが詳細に制御できる点が挙げられます。これにはポインタが密接に関わっています。ポインタとは、他の変数のメモリアドレスを格納する特殊な変数のことです。以下はポインタの基本的な使用例です:

int x = 10;
int* ptr = &x; // xのアドレスを取得してptrに格納
cout << "xの値: " << x << endl;
cout << "ptrが指す値: " << *ptr << endl; // ポインタ経由でxの値を取得

 C++では、newキーワードで動的にメモリを割り当て、deleteキーワードでそのメモリを解放する必要があります。ただし、モダンC++(C++11以降)ではsmart pointersの導入により、手動でのメモリ管理の必要性が大幅に減少しています。

オブジェクト指向プログラミングとC++

クラスとオブジェクトの基本

 クラスとオブジェクトは、C++のオブジェクト指向プログラミングの基盤となる重要な概念です。クラスはデータ構造や操作(メソッド)を定義する設計図のような役割を果たします。一方、オブジェクトはそのクラスをもとに生成された実際のインスタンスで、クラスで定義されたプロパティやメソッドを持っています。

 例えば、「車」というクラスを作成すると、それをもとに「自動車A」や「自動車B」といった具体的なオブジェクトを生成することができます。このようなモデリングを行うことで、コードの再利用性と構造の明確化が実現できます。C++を使用すると、これらのクラスやオブジェクトを効率的に扱うことが可能です。

コンストラクタとデストラクタ

 コンストラクタとデストラクタは、クラスの初期化と解放を行う特別なメソッドです。コンストラクタはオブジェクトが生成される際に自動的に呼び出され、初期化処理を行います。たとえば、クラス内のメンバ変数の設定や必要なリソースの確保などが含まれます。一方、デストラクタはオブジェクトが破棄される際に自動的に呼び出され、リソースの解放や終了処理を行います。

 これにより、C++では手動でメモリ管理を行う必要がある場面でも、効率的かつ安全にリソースを管理することが可能です。特に動的メモリを扱う場合、これらの仕組みを活用することで、メモリリークを防ぐことができます。

継承と多態性(ポリモーフィズム)

 継承は既存のクラスの機能を引き継ぎつつ、新しい機能を追加できる仕組みです。C++では、子クラスは親クラスからプロパティやメソッドを受け継ぐことができるため、コードの再利用性と拡張性が向上します。一例として、「動物」という親クラスを作成し、その動物クラスを継承した「犬」や「猫」という子クラスを作ることが挙げられます。

 多態性(ポリモーフィズム)は、同じインターフェースを使用して、異なる動作をするメソッドを実現する仕組みです。これにより、動的バインディングを使用して、派生クラスで定義されたメソッドが実行されるようになります。C++では、仮想関数(virtual関数)を利用することでポリモーフィズムを実装できます。

テンプレートとSTL(標準テンプレートライブラリ)の活用

 C++にはジェネリックプログラミングをサポートするテンプレート機能があります。テンプレートを使用すると、型に依存しない汎用的なクラスや関数を作成でき、異なるデータ型にも対応できる柔軟なプログラム開発が可能です。例えば、整数や文字列といった異なる型を扱う配列クラスをテンプレートで効率的に構築できます。

 また、標準テンプレートライブラリ(STL)は、C++の強力なツールセットの1つで、効率的なデータ構造(例えば、ベクターやリスト)やアルゴリズム(ソートや検索など)が含まれています。テンプレートとSTLを活用することで、開発の効率を大幅に向上させることができます。

実践的なC++プログラミング

例外処理とエラーハンドリング

 C++では、プログラムの実行中に発生するエラーを適切に処理するための仕組みとして例外処理が用意されています。try、catch、throwを使うことで、発生したエラーを捕捉し、対処を簡潔に記述できます。これにより、異常時の挙動を明確にし、プログラムが途中で異常終了することを防ぐことが可能です。

 例えば、ファイルが存在しない場合や、メモリ不足が発生した場合など、意図しない状況への対応を容易にします。また、C++の標準ライブラリには多くの例外クラスが用意されており、適切なエラーハンドリングが求められる場面において活用されます。

モダンC++の新機能(C++11以降)

 C++11以降、言語仕様に多くの改良が加えられ、より簡潔で効率的なプログラムが記述できるようになりました。新しい機能として、ラムダ式、スマートポインタ(std::shared_ptrやstd::unique_ptr)、constexpr、auto型推論、範囲ベースforループなどがあります。

 特にスマートポインタは、プログラマが手動でメモリを管理する手間を減らし、メモリリークのリスクを軽減します。また、C++17ではstd::optionalや構造化束縛、C++20ではコルーチンやコンセプト(Concepts)などが追加され、より直感的かつ表現力豊かな記述が可能になっています。

 これらのモダンC++の機能を活用することで、保守性やパフォーマンスが向上した高品質なコードを記述することができます。

デバッグと最適化の基礎

 C++は高性能なプログラムを記述できる一方で、バグの発見や解消が他の言語に比べて難しい場合があります。そのため、デバッグの基本的な手法を身に着けることが重要です。主な方法として、デバッガを活用してブレークポイントを設定したり、変数の状態を監視したりすることが挙げられます。主に使用されるツールとして、GDBやVisual Studioのデバッグ機能などがあります。

 デバッグだけでなく、最適化も重要なポイントです。コードの性能を向上させるためには、計算量や必要なメモリの削減を意識した設計が求められます。C++はコンパイル時の最適化が強力であり、その特性を活かして無駄のないネイティブコードを生成することが可能です。また、プロファイリングツールを使えばボトルネックの特定や性能改善のヒントを得ることができます。

プロジェクト設計とコードの再利用性

 C++で大規模なプロジェクトを設計する際には、オブジェクト指向プログラミング(OOP)の概念が強力なツールとなります。クラスや継承を活用することで、機能の拡張やメンテナンスが容易になり、コードの再利用性を高めることが可能です。また、ジェネリックプログラミングを用いてテンプレートを活用することで、汎用性の高いコードを実現できます。

 さらに、モジュール化を通じてコードを分割し、他のプロジェクトでも再利用できるライブラリとして活用することも可能です。例えば、C++の標準テンプレートライブラリ(STL)は再利用性の高い優れた例であり、開発者が効率よく開発を進めるための良い参考となります。

 効率的なプロジェクト設計は、ソフトウェアの保守性を向上させ、複雑なシステムをシンプルに管理する鍵となります。設計段階で再利用性に配慮することで、完成後のコスト削減にも繋がります。

地震情報サイト

<!DOCTYPE html>
<html lang="ja">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>地震情報 - 完全版</title>
    <style>
        body {
            font-family: Arial, sans-serif;
            margin: 0;
            padding: 0;
            background-color: var(--bg-color, #ffffff);
            color: var(--text-color, #000000);
            transition: background-color 0.3s, color 0.3s;
        }
        .container {
            max-width: 1200px;
            margin: 20px auto;
            padding: 20px;
            background: var(--card-bg, #ffffff);
            border-radius: 8px;
            box-shadow: 0 2px 10px rgba(0, 0, 0, 0.1);
        }
        h1 {
            text-align: center;
        }
        #map {
            height: 400px;
            margin-top: 20px;
        }
        .toggle-dark-mode {
            position: fixed;
            top: 10px;
            right: 10px;
            padding: 10px;
            background: #007BFF;
            color: white;
            border: none;
            border-radius: 5px;
            cursor: pointer;
        }
        @media (max-width: 768px) {
            .container {
                padding: 10px;
            }
        }
    </style>
    <link rel="stylesheet" href="https://unpkg.com/leaflet@1.7.1/dist/leaflet.css" />
    <script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
</head>
<body>
    <button class="toggle-dark-mode" onclick="toggleDarkMode()">ダークモード切り替え</button>
    <div class="container">
        <h1>地震情報</h1>
        <div id="quakeStats">
            <canvas id="intensityChart" width="400" height="200"></canvas>
        </div>
        <div id="map"></div>
        <div id="regionData"></div>
    </div>

    <script src="https://unpkg.com/leaflet@1.7.1/dist/leaflet.js"></script>
    <script>
        const rssUrl = 'https://www.jma.go.jp/bosai/quake/data/list.xml';
        let quakeData = [];
        const regions = {};

        const map = L.map('map').setView([35.6895, 139.6917], 5);
        L.tileLayer('https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', {
            attribution: '© OpenStreetMap contributors'
        }).addTo(map);

        async function fetchEarthquakeData() {
            try {
                const response = await fetch(`https://api.allorigins.win/get?url=${encodeURIComponent(rssUrl)}`);
                const data = await response.json();
                const parser = new DOMParser();
                const xmlDoc = parser.parseFromString(data.contents, "text/xml");

                const items = xmlDoc.getElementsByTagName('item');
                quakeData = [];

                for (let i = 0; i < items.length; i++) {
                    const title = items[i].getElementsByTagName('title')[0].textContent;
                    const description = items[i].getElementsByTagName('description')[0].textContent;
                    const pubDate = items[i].getElementsByTagName('pubDate')[0].textContent;

                    const match = description.match(/震源地:(.+?)、緯度:(.+?)、経度:(.+?)、震度:(.+?)、/);
                    if (match) {
                        const location = match[1];
                        const lat = parseFloat(match[2]);
                        const lng = parseFloat(match[3]);
                        const intensity = parseFloat(match[4]);

                        quakeData.push({ title, location, lat, lng, intensity, pubDate });
                        if (!regions[location]) {
                            regions[location] = [];
                        }
                        regions[location].push({ intensity, pubDate });
                    }
                }

                displayQuakeData();
                updateChart();
            } catch (error) {
                console.error('地震情報の取得に失敗しました:', error);
            }
        }

        function displayQuakeData() {
            map.eachLayer(layer => {
                if (layer.options && layer.options.pane === "markerPane") {
                    map.removeLayer(layer);
                }
            });

            quakeData.forEach(quake => {
                L.circle([quake.lat, quake.lng], {
                    color: 'red',
                    fillColor: '#f03',
                    fillOpacity: 0.5,
                    radius: quake.intensity * 10000
                }).addTo(map)
                .bindPopup(`<strong>${quake.title}</strong><br>震源地: ${quake.location}<br>震度: ${quake.intensity}`);
            });
        }

        function updateChart() {
            const ctx = document.getElementById('intensityChart').getContext('2d');
            const labels = quakeData.map(q => q.pubDate);
            const intensities = quakeData.map(q => q.intensity);

            new Chart(ctx, {
                type: 'line',
                data: {
                    labels: labels,
                    datasets: [{
                        label: '震度',
                        data: intensities,
                        borderColor: 'rgba(255, 99, 132, 1)',
                        borderWidth: 2,
                        fill: false
                    }]
                }
            });
        }

        function toggleDarkMode() {
            const isDarkMode = document.body.style.getPropertyValue('--bg-color') === '#ffffff';
            document.body.style.setProperty('--bg-color', isDarkMode ? '#333333' : '#ffffff');
            document.body.style.setProperty('--text-color', isDarkMode ? '#ffffff' : '#000000');
            document.body.style.setProperty('--card-bg', isDarkMode ? '#444444' : '#ffffff');
        }

        fetchEarthquakeData();
        setInterval(fetchEarthquakeData, 60000); // 1分ごとに更新
    </script>
</body>
</html>

Javascript RPG


<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Epic RPG</title>
  <style>
    body {
      font-family: Arial, sans-serif;
      margin: 20px;
    }
    #game-log {
      background: #f4f4f4;
      padding: 10px;
      margin-bottom: 20px;
      height: 200px;
      overflow-y: auto;
      border: 1px solid #ddd;
    }
    button {
      margin: 5px;
      padding: 10px;
    }
    #player-stats {
      margin-bottom: 20px;
    }
  </style>
</head>
<body>
  <h1>Epic RPG</h1>
  <div id="player-stats">
    <p><strong>Name:</strong> <span id="player-name">Hero</span></p>
    <p><strong>HP:</strong> <span id="player-hp">100</span>/<span id="player-max-hp">100</span></p>
    <p><strong>MP:</strong> <span id="player-mp">50</span>/<span id="player-max-mp">50</span></p>
    <p><strong>Level:</strong> <span id="player-level">1</span></p>
    <p><strong>EXP:</strong> <span id="player-exp">0</span>/100</p>
    <p><strong>Gold:</strong> <span id="player-gold">0</span></p>
    <p><strong>Inventory:</strong> <span id="player-inventory">Potion x1</span></p>
    <p><strong>Skills:</strong> <span id="player-skills">Fireball</span></p>
    <p><strong>Equipped Weapon:</strong> <span id="player-weapon">None</span></p>
    <p><strong>Equipped Armor:</strong> <span id="player-armor">None</span></p>
    <p><strong>Current Quest:</strong> <span id="player-quest">None</span></p>
    <p><strong>Stage:</strong> <span id="current-stage">1</span></p>
  </div>
  <div id="game-log"></div>
  <button onclick="attack()">Attack</button>
  <button onclick="useSkill()">Use Skill</button>
  <button onclick="heal()">Heal</button>
  <button onclick="openShop()">Shop</button>
  <button onclick="acceptQuest()">Quest</button>
  <button onclick="craftItem()">Craft Item</button>
  <button onclick="nextStage()">Next Stage</button>
  <button onclick="restart()">Restart</button>
  <script>
    // プレイヤーと敵のデータ
    let player = {
      name: "Hero",
      hp: 100,
      maxHp: 100,
      mp: 50,
      maxMp: 50,
      attackPower: 10,
      defense: 5,
      exp: 0,
      level: 1,
      gold: 50,
      inventory: ["Potion", "Iron Ore"],
      skills: ["Fireball"],
      weapon: null,
      armor: null,
      quest: null,
      stage: 1,
    };

    let enemy = {
      name: "Goblin",
      hp: 50,
      maxHp: 50,
      attackPower: 8,
      defense: 3,
    };

    const quests = [
      { name: "Defeat 3 Goblins", progress: 0, goal: 3, reward: 100 },
      { name: "Collect 2 Potions", progress: 0, goal: 2, reward: 50 },
    ];

    const stages = [
      { stage: 1, description: "The Forest of Beginnings", enemies: ["Goblin", "Orc"] },
      { stage: 2, description: "The Cursed Mines", enemies: ["Dark Bat", "Skeleton"] },
      { stage: 3, description: "The Dragon's Lair", enemies: ["Fire Dragon"] },
    ];

    // ゲームログ表示関数
    function log(message) {
      const logDiv = document.getElementById("game-log");
      logDiv.innerHTML += `<p>${message}</p>`;
      logDiv.scrollTop = logDiv.scrollHeight;
    }

    // プレイヤーの攻撃
    function attack() {
      const damage = Math.max(Math.floor(Math.random() * player.attackPower) - enemy.defense, 1);
      enemy.hp -= damage;
      log(`You attack the ${enemy.name} for ${damage} damage!`);
      if (enemy.hp <= 0) {
        log(`You defeated the ${enemy.name}!`);
        gainExp(20);
        gainGold(Math.floor(Math.random() * 20) + 10);
        updateQuestProgress("Defeat 3 Goblins");
        spawnNewEnemy();
        return;
      }
      enemyAttack();
    }

    // 敵の攻撃
    function enemyAttack() {
      const damage = Math.max(Math.floor(Math.random() * enemy.attackPower) - player.defense, 0);
      player.hp -= damage;
      log(`The ${enemy.name} attacks you for ${damage} damage! Current HP: ${player.hp}`);
      if (player.hp <= 0) {
        log("You have been defeated...");
        log("Press 'Restart' to try again.");
      }
      updateStats();
    }

    // ステージ移動
    function nextStage() {
      player.stage++;
      const currentStage = stages.find(stage => stage.stage === player.stage);
      if (!currentStage) {
        log("Congratulations! You have completed the game!");
        return;
      }
      log(`You enter the ${currentStage.description}.`);
      spawnNewEnemy();
      updateStats();
    }

    // 新しい敵を生成
    function spawnNewEnemy() {
      const currentStage = stages.find(stage => stage.stage === player.stage);
      const randomEnemyName = currentStage.enemies[Math.floor(Math.random() * currentStage.enemies.length)];
      enemy = {
        name: randomEnemyName,
        hp: Math.floor(Math.random() * 30 + 50),
        maxHp: Math.floor(Math.random() * 30 + 50),
        attackPower: Math.floor(Math.random() * 5 + 10),
        defense: Math.floor(Math.random() * 5),
      };
      log(`A wild ${enemy.name} appears with ${enemy.hp} HP!`);
    }

    // アイテムクラフト
    function craftItem() {
      if (player.inventory.includes("Iron Ore")) {
        player.inventory.splice(player.inventory.indexOf("Iron Ore"), 1);
        player.weapon = "Iron Sword";
        player.attackPower += 5;
        log("You crafted an Iron Sword! Attack power increased by 5.");
      } else {
        log("You don't have the required materials to craft an item.");
      }
      updateStats();
    }

    // ステータス更新
    function updateStats() {
      document.getElementById("player-name").innerText = player.name;
      document.getElementById("player-hp").innerText = player.hp;
      document.getElementById("player-max-hp").innerText = player.maxHp;
      document.getElementById("player-mp").innerText = player.mp;
      document.getElementById("player-max-mp").innerText = player.maxMp;
      document.getElementById("player-level").innerText = player.level;
      document.getElementById("player-exp").innerText = player.exp;
      document.getElementById("player-gold").innerText = player.gold;
      document.getElementById("player-inventory").innerText = player.inventory.join(", ") || "Empty";
      document.getElementById("player-skills").innerText = player.skills.join(", ") || "None";
      document.getElementById("player-weapon").innerText = player.weapon || "None";
      document.getElementById("player-armor").innerText = player.armor || "None";
      document.getElementById("player-quest").innerText = player.quest ? player.quest.name : "None";
      document.getElementById("current-stage").innerText = player.stage;
    }

    // 初期化
    log("Welcome to the RPG! A Goblin appears!");
    updateStats();
    spawnNewEnemy();
  </script>
</body>
</html>

VR機器の作り方

VR機器の作り方について詳しく説明します。VR(バーチャルリアリティ)機器は、実際に体験する感覚を提供するために、さまざまなステップや技術が必要です。以下はその基本的なプロセスです:

  1. コンセプトと企画
    目的の設定: VR体験を通じて何を達成したいのか(エンターテイメント、教育、トレーニングなど)を明確にします。
    ユーザーストーリーの作成: 利用者の視点からVR体験の流れを設計します。
  2. ハードウェアの選択
    VRヘッドセット: Oculus Quest、HTC Vive、PlayStation VRなど、目的に合ったヘッドセットを選びます。
    コントローラー: 手の動きや操作を反映するために、コントローラーや手振れ追跡デバイスが必要です。
    センサー: 位置追跡や動きを検知するためのセンサーが重要です。
  3. ソフトウェアの開発
    VRエンジンの選択: UnityやUnreal Engineが一般的に使用されます。これらのプラットフォームはVR開発に適したツールを提供します。
    3Dモデリング: モデリングソフト(Blender、Mayaなど)を使ってVR環境やキャラクターを制作します。
    プログラミング: C#(Unity)やC++(Unreal Engine)を使ってインタラクションやゲームロジックを実装します。
  4. VRコンテンツの制作
    360度ビデオ撮影: 実写のVR体験には、360度カメラを用いた撮影が必要です。
    VRアプリケーションの開発: ゲーム、教育ツール、シミュレーションなどのアプリケーションを開発します。
  5. テストと最適化
    ユーザーテスト: 目標とする体験が提供されているかを確認するためのテスト。
    パフォーマンスの最適化: VRは高いフレームレートが必要なため、動作が滑らかになるよう調整します。
  6. デプロイとマーケティング
    プラットフォームへの配信: SteamVR、Oculus Store、PSNなどにアプリを公開します。
    マーケティング: VR体験のユニークさを伝えるためのプロモーション活動。

追加リソース
VR動画の作り方についての詳細は、様々なウェブサイトやブログで見つけることができます。具体的な技術や手順については、例えばVR動画の制作方法からアップロードまでを解説した記事などが参考になります。
また、VRコンテンツの基本的な制作方法についての情報も豊富にあります。

これらのステップを踏むことで、独自のVR体験を生み出すことができます。ただし、技術やリソースの違いにより、各プロジェクトの具体的な工程は異なる場合があります。

VR機器を作ることは非常に高度なプロジェクトで、ハードウェア、ソフトウェア、センサー技術、そして光学技術が必要です。以下はVR機器を自作するための基本的なステップを説明しますが、全てを個人で実現するには多大な知識とリソースが必要であることを理解してください。


1. 設計と目標の定義

  • 目的を決める: ゲーム向け、3D建築シミュレーション、医療トレーニングなど、VR機器の用途を明確にする。
  • 仕様を設定する:
    • 解像度 (例: 1920×1080や4K)
    • リフレッシュレート (例: 60Hz、90Hz以上)
    • トラッキング方式 (例: インサイドアウト、外部センサー使用)
    • 対応プラットフォーム (PC、モバイル、独立型)

2. 必要なコンポーネント

ハードウェア

  1. ディスプレイパネル:
    • 高解像度のOLEDやLCDパネルを選択。
    • 両目用に2枚のディスプレイが必要か、1枚のディスプレイで分割表示するかを決定。
  2. レンズ:
    • フレネルレンズや非球面レンズを使用し、視野角(FOV)を広げる。
    • 視差補正を行うための設計が必要。
  3. センサー:
    • ジャイロセンサー加速度センサーで頭の動きを検出。
    • 高精度なトラッキングには、カメラやLIDARなども利用。
  4. マイクロコントローラー:
    • ArduinoやRaspberry Piでセンサーやディスプレイを制御。
  5. 外部トラッキングデバイス(必要に応じて):
    • Lighthouse(HTC Vive方式)や独自の赤外線カメラを使用。
  6. ハウジング:
    • 3Dプリンターでフレームを作成したり、市販のVRゴーグルを改造。
  7. コントローラー:
    • 物理ボタンやトリガー付きのハンドコントローラー。
    • ジェスチャー認識にはLeap Motionなどを使用。

ソフトウェア

  1. ソフトウェア開発キット (SDK):
    • OpenVR (SteamVR対応)
    • OpenXR(汎用VRフレームワーク)
    • UnityやUnreal Engineでの開発用プラグイン。
  2. ドライバとファームウェア:
    • センサーやディスプレイを正しく動作させるためのソフトウェアを作成。
  3. VR環境の作成:
    • UnityやUnreal EngineでVRアプリケーションを設計。
    • トラッキングデータとディスプレイ出力の同期が重要。
  4. オペレーティングシステムとの連携:
    • Windows、Linux、Androidでの動作確認。

3. 実装とプロトタイピング

  • 試作品の作成:
    • 必要な部品を集めて組み立てる。
    • 配線を行い、センサーとディスプレイの動作を確認。
  • テストと調整:
    • レンズの焦点距離調整。
    • トラッキング精度の調整。
    • センサーのキャリブレーション。

4. 製品化

  • デザインの改良:
    • 小型化、軽量化、快適性向上を図る。
    • ヘッドストラップやパッドの追加。
  • 量産可能性の評価:
    • 部品調達とコスト評価。
    • 製造ラインの設計。

5. 参考資料とリソース

  • DIY VRコミュニティ:
    • DIY VR Projects (RedditやHackaday)
    • OpenHMD(オープンソースのVRフレームワーク)
  • 必要なツール:
    • 3Dプリンター、はんだごて、マイクロコントローラー用プログラミング環境。
  • 参考キット:
    • Google Cardboard(簡易型VR機器の仕組みを理解するのに最適)
    • Oculus DK1/DK2の分解例を調査。

注意点

  • 高い安全性を確保: 長時間使用時の目や首への負担を考慮する。
  • 法律と規制: 無線通信を使用する場合、適切な規制に準拠する必要がある。

VR機器の開発は多くの試行錯誤を伴いますが、小規模なプロトタイプから始めて技術を学びながら進めることをお勧めします。興味のある具体的なポイントがあればさらに詳細をお伝えします!」

宇宙ロケットの作り方

宇宙ロケットを作る方法については、以下のようなステップやポイントがあります:

基本的な理解:
ロケットは、燃料を燃やし、生成された高温のガスを後方に噴出させることで推進力を得ます。ジェットエンジンと違い、ロケットは酸素を自ら持っているため、空気がない宇宙でも飛行可能です。

設計と材料:
モデルロケットの場合、教育や趣味で作ることが可能で、火薬を使用する簡易なロケットから始めることが一般的です。必要な材料は、紙製の胴体、ロケットエンジン、フィン、ノーズコーンなどです。

本格的なロケットについては、大規模な工場や施設がなくても、民間企業や大学で開発が進んでいます。軽量化素材やロケット部品の設計、燃料の選定が重要となります。

製作手順:
モデルロケット:
胴体を作り、フィンを取り付け、ノーズコーンを装着します。その後、ロケットエンジンを胴体に組み込みます。飛ばす際には安全な場所で行い、風向きや周囲の環境に注意が必要です。

大型ロケット:
設計段階で多段構造(例:1段目、2段目)を考慮する必要があります。これは各段で燃料を効率的に使い、重量を減らすためです。

燃料タンクの設計、推進システムの開発、制御システムの組み立てなど、専門的な技術と知識が求められます。

教育とリソース:
日本では、JAXAやその他教育機関がロケット製作を学ぶ機会を提供しています。また、書籍やオンラインリソースも豊富に存在し、基本的な理論から実際の製作方法までカバーしています。

注意点:
特に大型のロケットや教育以外の目的での製作は、法規制や安全性の問題が関わるため、専門家や関連機関との連携が必要です。

この概要は、一般的な情報を元にしています。実際の製作には、より具体的なガイドラインや安全規則に従う必要があります。

ゲーム機の作り方

ゲーム機の作り方

ChatGPT:
ChatGPT
ゲーム機を作るには、ハードウェアとソフトウェアの両方を設計・開発する必要があります。以下は、ゲーム機を作るための基本的なプロセスです。

  1. コンセプトの決定
    目的と仕様を決める
    ゲーム機のターゲット:子供向け、カジュアルゲーマー向け、ハードコアゲーマー向けなど。
    プラットフォームのタイプ:据え置き型、携帯型、VR/AR対応型。
    必要な機能:
    解像度(720p、1080p、4K)
    コントローラー(ワイヤレス/有線)
    ネット接続(Wi-Fi、Bluetooth)
    ストレージ容量
  2. ハードウェアの設計
    ゲーム機のコア部分は、以下の主要コンポーネントから構成されます。

(1) プロセッサ (CPU/GPU)
CPU: ゲームのロジックやシステム処理を担当。
GPU: ゲームグラフィックを描画。
選択肢:
Raspberry Pi(初期プロトタイプ向け)
NVIDIA Jetson Nano(AIや高性能グラフィック用)
(2) メモリ (RAM)
速度と容量を考慮する必要がある。
4GB以上が一般的。
(3) ストレージ
ゲームデータを保存。
SDカードやSSDが一般的。
(4) 入出力デバイス
ディスプレイ出力: HDMIポートなどを搭載。
コントローラー接続: BluetoothやUSBポート。
センサー(必要ならVRやモーションセンサーを追加)。
(5) 電源
ポータブルゲーム機ならリチウムイオン電池。
据え置き型ならACアダプター。

  1. ソフトウェアの開発
    ゲーム機のソフトウェアは、主に以下の部分から構成されます。

(1) オペレーティングシステム
OSがゲーム機の基本機能を制御。
選択肢:
Linux(カスタマイズ可能で無料)
独自の軽量OSを構築(組み込み用RTOSなど)
(2) ゲームエンジンの統合
UnityやUnreal Engineなどのエンジンをサポート可能にする。
(3) インターフェースの開発
ゲームメニュー、設定画面、ストア機能。
UI/UXツールを使用して設計。
(4) ゲームの実行環境
開発者がゲームを作成・実行できるSDKを提供。

  1. プロトタイプの作成
    (1) ハードウェアのプロトタイプ
    3Dプリンターで筐体を作成。
    市販のコンポーネント(Raspberry PiやArduinoなど)を使ってテスト。
    (2) ソフトウェアの実装
    OSとゲームの基本動作を確認。
    システム起動時の動作やゲーム起動プロセスを構築。
  2. 製造と量産
    回路基板 (PCB) 設計: ハードウェアの統合を1枚のPCBで行う。
    量産用工場との提携: ハードウェア部品の量産。
    品質テスト: 全体の動作テストとバグ修正。
  3. 販売戦略とマーケティング
    オンライン販売: 自社サイトやクラウドファンディング(Kickstarterなど)。
    店舗販売: パートナーシップを構築。
    ゲームエコシステム: 独自のゲームストアを構築して収益を拡大。
    参考リソース
    Raspberry Pi Projects(プロトタイプに最適)
    公式サイト
    Arduino(ハードウェア制御用)
    公式サイト
    Unity(ゲームエンジン)
    公式サイト
    Unreal Engine(高性能ゲームエンジン)
    公式サイト
    興味のあるステップについて詳細を知りたい場合は教えてください!

文章生成AIデモ

<!DOCTYPE html>
<html lang="ja">
<head>
    <meta charset="UTF-8"/>
    <meta name="viewport" content="width=device-width, initial-scale=1.0"/>
    <title>文章生成AIデモ(擬似生成強化版)</title>
    <style>
        body {
            margin: 0;
            font-family: 'Helvetica Neue', Arial, sans-serif;
            background: #f5f5f5;
            color: #333;
        }
        header, footer {
            background: #222;
            color: #fff;
            padding: 1.5em;
            text-align: center;
        }
        header h1 {
            margin: 0;
            font-weight: normal;
        }
        main {
            max-width: 1000px;
            margin: 2em auto;
            background: #fff;
            border-radius: 8px;
            padding: 2em;
            box-shadow: 0 2px 10px rgba(0,0,0,0.1);
        }
        h2 {
            margin-top: 0;
        }

        .intro-text {
            font-size: 0.95em;
            line-height: 1.6;
            margin-bottom: 2em;
            color: #555;
        }

        .form-group {
            margin-bottom: 1.5em;
        }
        label {
            display: block;
            margin-bottom: 0.5em;
            font-weight: bold;
        }
        textarea {
            width: 100%;
            height: 150px;
            box-sizing: border-box;
            padding: 1em;
            font-size: 1em;
            border: 1px solid #ccc;
            border-radius: 4px;
            resize: vertical;
        }
        select, input[type=range] {
            width: 100%;
            box-sizing: border-box;
            padding: 0.5em;
            font-size: 1em;
            margin-top: 0.5em;
            border: 1px solid #ccc;
            border-radius: 4px;
            background: #fff;
        }
        .range-value {
            text-align: right;
            font-size: 0.9em;
            color: #666;
        }
        button {
            background: #007bff;
            color: #fff;
            border: none;
            padding: 0.75em 1.5em;
            font-size: 1em;
            border-radius: 4px;
            cursor: pointer;
            display: inline-block;
        }
        button:hover {
            background: #0056b3;
        }
        .output-section {
            margin-top: 2em;
        }
        #output-area {
            border: 1px solid #ccc;
            min-height: 150px;
            padding: 1em;
            border-radius: 4px;
            background: #fafafa;
            white-space: pre-wrap;
        }

        /* ローディングアニメーション */
        .loading-overlay {
            display: none;
            position: fixed;
            top:0; left:0; right:0; bottom:0;
            background: rgba(0,0,0,0.3);
            z-index: 9999;
            justify-content: center;
            align-items: center;
        }
        .loading-container {
            background: #fff;
            padding: 2em;
            border-radius: 8px;
            text-align: center;
            box-shadow: 0 0 15px rgba(0,0,0,0.2);
        }
        .loading-spinner {
            margin: 0 auto 1em;
            width: 50px;
            height: 50px;
            border: 6px solid #eee;
            border-top-color: #007bff;
            border-radius: 50%;
            animation: spin 1s linear infinite;
        }
        @keyframes spin {
          100% { transform: rotate(360deg); }
        }
        .error-message {
            color: #d00;
            font-weight: bold;
            margin-top: 1em;
        }

        footer p {
            margin: 0;
            font-size: 0.9em;
        }

        /* レスポンシブ対応 */
        @media (max-width: 600px) {
            main {
                margin: 1em;
                padding: 1em;
            }
        }
    </style>
</head>
<body>
    <header>
        <h1>文章生成AIデモ(擬似)</h1>
    </header>
    <main>
        <div class="intro-text">
            <p>このデモは擬似的な文章生成を行います。入力されたプロンプト、モデル選択、Temperatureに基づいてあたかもAIが文章を生成したかのような結果を返します。</p>
            <p>実際のAIモデルはこのページ単体では動作しておらず、<b>キーワードに応じた例示的なテキスト</b>を返すだけです。後にサーバーサイドでバックエンドを用意すれば、本物のAI生成が可能になります。</p>
            <p>試しに、以下のようなキーワードを含めてみてください:<br>
            ・「猫」:猫に関する創作文章<br>
            ・「エネルギー問題」:環境やエネルギーについての説明文<br>
            ・「小説の冒頭」:文学的な書き出し<br>
            ・「ビジネス戦略」:ビジネス、マーケティングに関連するテキスト
            </p>
        </div>

        <section class="input-section">
            <h2>プロンプト入力</h2>
            <div class="form-group">
                <label for="prompt-input">プロンプト (アイデアやキーワード等)</label>
                <textarea id="prompt-input" placeholder="ここに文章生成のためのヒントとなるプロンプトを入力してください"></textarea>
            </div>

            <div class="form-group">
                <label for="model-select">モデル選択</label>
                <select id="model-select">
                    <option value="model-1">model-1 (標準モデル)</option>
                    <option value="model-2">model-2 (創造性強化モデル)</option>
                    <option value="model-3">model-3 (高精度モデル)</option>
                </select>
            </div>

            <div class="form-group">
                <label>創造性(Temperature)</label>
                <div class="range-value">値: <span id="temperature-value">0.7</span></div>
                <input type="range" id="temperature-range" min="0" max="1" step="0.1" value="0.7">
            </div>

            <div class="form-group" style="text-align: right;">
                <button id="generate-btn">生成</button>
            </div>
        </section>

        <section class="output-section">
            <h2>生成結果</h2>
            <div id="output-area"></div>
        </section>

        <div class="error-message" id="error-message" style="display:none;"></div>
    </main>

    <div class="loading-overlay" id="loading-overlay">
        <div class="loading-container">
            <div class="loading-spinner"></div>
            <p>文章生成中です。しばらくお待ちください...</p>
        </div>
    </div>

    <footer>
        <p>© 2024 AI Text Generation Demo (Mocked)</p>
    </footer>

    <script>
        const promptInput = document.getElementById('prompt-input');
        const modelSelect = document.getElementById('model-select');
        const temperatureRange = document.getElementById('temperature-range');
        const temperatureValue = document.getElementById('temperature-value');
        const generateBtn = document.getElementById('generate-btn');
        const outputArea = document.getElementById('output-area');
        const errorMessage = document.getElementById('error-message');
        const loadingOverlay = document.getElementById('loading-overlay');

        temperatureRange.addEventListener('input', () => {
            temperatureValue.textContent = temperatureRange.value;
        });

        // キーワードに応じて返す擬似的な生成テキストを用意
        function getMockResponse(prompt, model, temperature) {
            // 全角・半角を区別しないために小文字で判定
            const lowerPrompt = prompt.toLowerCase();

            let baseText = "【擬似的なAI生成結果】\n";
            baseText += "プロンプト: \"" + prompt + "\"\n";
            baseText += "モデル: " + model + "\n";
            baseText += "Temperature: " + temperature + "\n\n";

            if (lowerPrompt.includes("猫")) {
                baseText += "ふわふわした毛皮に包まれた小さな猫は、朝日が差し込む窓辺で静かに丸くなっている。その瞳は琥珀色に輝き、しなやかな尾は優雅な曲線を描く。\n" +
                            "この猫は人間に対して警戒心を持ちながらも、一度心を開いた相手には無限の甘えを見せる。";
            } else if (lowerPrompt.includes("エネルギー問題") || lowerPrompt.includes("環境")) {
                baseText += "世界的なエネルギー問題は、化石燃料の枯渇と気候変動への懸念を背景に深刻化している。再生可能エネルギーの導入は、ただ単に環境負荷を低減するだけでなく、地域経済の活性化や新たな技術開発の契機となる。\n" +
                            "太陽光や風力エネルギーなどのクリーンな資源を活用することで、持続可能な未来を築くことが可能だ。";
            } else if (lowerPrompt.includes("小説の冒頭") || lowerPrompt.includes("物語の始まり")) {
                baseText += "薄暗い路地裏に、一人の少年が立っていた。その少年の瞳には、不思議な光が宿っている。遠くで犬が吠える音、古い街灯が淡い橙色の光を投げかける。\n" +
                            "少年は一枚の古めかしい地図を握りしめ、見知らぬ世界への第一歩を踏み出そうとしていた。";
            } else if (lowerPrompt.includes("ビジネス戦略") || lowerPrompt.includes("マーケティング")) {
                baseText += "成功するビジネス戦略は、顧客ニーズの正確な把握から始まる。市場調査をもとに、ターゲット層に響く価値提案を明確化し、差別化された製品・サービスを提供することが重要だ。\n" +
                            "さらに、マーケティング戦略を通じてブランド認知度を高め、持続的な成長のために柔軟な計画修正とPDCAサイクルを回し続ける必要がある。";
            } else {
                // 特定のキーワードがない場合は、汎用的な擬似生成テキストを返す
                baseText += "あなたのプロンプトに基づくテキストを生成します。\n" +
                            "このテキストはあくまでサンプルであり、実際のAIモデルによる生成結果を模したものです。\n\n" +
                            "ここに様々なアイディア、説明、物語、または議論が展開されることでしょう。\n" +
                            "モデルやTemperatureを変更することで、文体やアイデアの広がり、独創性のレベルが変化すると考えられます。";
            }

            return baseText;
        }

        generateBtn.addEventListener('click', async () => {
            const prompt = promptInput.value.trim();
            const model = modelSelect.value;
            const temperature = parseFloat(temperatureRange.value);

            if (!prompt) {
                alert("プロンプトを入力してください。");
                return;
            }

            // 前回の結果やエラーメッセージをクリア
            outputArea.textContent = '';
            errorMessage.style.display = 'none';
            errorMessage.textContent = '';

            // ローディング表示
            loadingOverlay.style.display = 'flex';

            try {
                // 実際のfetchを行わず、擬似生成結果を生成
                const generatedText = getMockResponse(prompt, model, temperature);
                // 模擬的に処理時間を設ける(待ち時間を演出)
                await new Promise(resolve => setTimeout(resolve, 1000));

                outputArea.textContent = generatedText;
            } catch (err) {
                console.error(err);
                errorMessage.textContent = "エラーが発生しました。詳細はコンソールをご確認ください。";
                errorMessage.style.display = 'block';
            } finally {
                // ローディング非表示
                loadingOverlay.style.display = 'none';
            }
        });
    </script>
</body>
</html>

<!DOCTYPE html>
<html lang="ja">
<head>
    <meta charset="UTF-8"/>
    <meta name="viewport" content="width=device-width, initial-scale=1.0"/>
    <title>文章生成AIデモ(擬似生成強化版)</title>
    <style>
        body {
            margin: 0;
            font-family: 'Helvetica Neue', Arial, sans-serif;
            background: #f5f5f5;
            color: #333;
        }
        header, footer {
            background: #222;
            color: #fff;
            padding: 1.5em;
            text-align: center;
        }
        header h1 {
            margin: 0;
            font-weight: normal;
        }
        main {
            max-width: 1000px;
            margin: 2em auto;
            background: #fff;
            border-radius: 8px;
            padding: 2em;
            box-shadow: 0 2px 10px rgba(0,0,0,0.1);
        }
        h2 {
            margin-top: 0;
        }

        .intro-text {
            font-size: 0.95em;
            line-height: 1.6;
            margin-bottom: 2em;
            color: #555;
        }

        .form-group {
            margin-bottom: 1.5em;
        }
        label {
            display: block;
            margin-bottom: 0.5em;
            font-weight: bold;
        }
        textarea {
            width: 100%;
            height: 150px;
            box-sizing: border-box;
            padding: 1em;
            font-size: 1em;
            border: 1px solid #ccc;
            border-radius: 4px;
            resize: vertical;
        }
        select, input[type=range] {
            width: 100%;
            box-sizing: border-box;
            padding: 0.5em;
            font-size: 1em;
            margin-top: 0.5em;
            border: 1px solid #ccc;
            border-radius: 4px;
            background: #fff;
        }
        .range-value {
            text-align: right;
            font-size: 0.9em;
            color: #666;
        }
        button {
            background: #007bff;
            color: #fff;
            border: none;
            padding: 0.75em 1.5em;
            font-size: 1em;
            border-radius: 4px;
            cursor: pointer;
            display: inline-block;
        }
        button:hover {
            background: #0056b3;
        }
        .output-section {
            margin-top: 2em;
        }
        #output-area {
            border: 1px solid #ccc;
            min-height: 150px;
            padding: 1em;
            border-radius: 4px;
            background: #fafafa;
            white-space: pre-wrap;
        }

        /* ローディングアニメーション */
        .loading-overlay {
            display: none;
            position: fixed;
            top:0; left:0; right:0; bottom:0;
            background: rgba(0,0,0,0.3);
            z-index: 9999;
            justify-content: center;
            align-items: center;
        }
        .loading-container {
            background: #fff;
            padding: 2em;
            border-radius: 8px;
            text-align: center;
            box-shadow: 0 0 15px rgba(0,0,0,0.2);
        }
        .loading-spinner {
            margin: 0 auto 1em;
            width: 50px;
            height: 50px;
            border: 6px solid #eee;
            border-top-color: #007bff;
            border-radius: 50%;
            animation: spin 1s linear infinite;
        }
        @keyframes spin {
          100% { transform: rotate(360deg); }
        }
        .error-message {
            color: #d00;
            font-weight: bold;
            margin-top: 1em;
        }

        footer p {
            margin: 0;
            font-size: 0.9em;
        }

        /* レスポンシブ対応 */
        @media (max-width: 600px) {
            main {
                margin: 1em;
                padding: 1em;
            }
        }
    </style>
</head>
<body>
    <header>
        <h1>文章生成AIデモ(擬似)</h1>
    </header>
    <main>
        <div class="intro-text">
            <p>このデモは擬似的な文章生成を行います。入力されたプロンプト、モデル選択、Temperatureに基づいてあたかもAIが文章を生成したかのような結果を返します。</p>
            <p>実際のAIモデルはこのページ単体では動作しておらず、<b>キーワードに応じた例示的なテキスト</b>を返すだけです。後にサーバーサイドでバックエンドを用意すれば、本物のAI生成が可能になります。</p>
            <p>試しに、以下のようなキーワードを含めてみてください:<br>
            ・「猫」:猫に関する創作文章<br>
            ・「エネルギー問題」:環境やエネルギーについての説明文<br>
            ・「小説の冒頭」:文学的な書き出し<br>
            ・「ビジネス戦略」:ビジネス、マーケティングに関連するテキスト
            </p>
        </div>

        <section class="input-section">
            <h2>プロンプト入力</h2>
            <div class="form-group">
                <label for="prompt-input">プロンプト (アイデアやキーワード等)</label>
                <textarea id="prompt-input" placeholder="ここに文章生成のためのヒントとなるプロンプトを入力してください"></textarea>
            </div>

            <div class="form-group">
                <label for="model-select">モデル選択</label>
                <select id="model-select">
                    <option value="model-1">model-1 (標準モデル)</option>
                    <option value="model-2">model-2 (創造性強化モデル)</option>
                    <option value="model-3">model-3 (高精度モデル)</option>
                </select>
            </div>

            <div class="form-group">
                <label>創造性(Temperature)</label>
                <div class="range-value">値: <span id="temperature-value">0.7</span></div>
                <input type="range" id="temperature-range" min="0" max="1" step="0.1" value="0.7">
            </div>

            <div class="form-group" style="text-align: right;">
                <button id="generate-btn">生成</button>
            </div>
        </section>

        <section class="output-section">
            <h2>生成結果</h2>
            <div id="output-area"></div>
        </section>

        <div class="error-message" id="error-message" style="display:none;"></div>
    </main>

    <div class="loading-overlay" id="loading-overlay">
        <div class="loading-container">
            <div class="loading-spinner"></div>
            <p>文章生成中です。しばらくお待ちください...</p>
        </div>
    </div>

    <footer>
        <p>© 2024 AI Text Generation Demo (Mocked)</p>
    </footer>

    <script>
        const promptInput = document.getElementById('prompt-input');
        const modelSelect = document.getElementById('model-select');
        const temperatureRange = document.getElementById('temperature-range');
        const temperatureValue = document.getElementById('temperature-value');
        const generateBtn = document.getElementById('generate-btn');
        const outputArea = document.getElementById('output-area');
        const errorMessage = document.getElementById('error-message');
        const loadingOverlay = document.getElementById('loading-overlay');

        temperatureRange.addEventListener('input', () => {
            temperatureValue.textContent = temperatureRange.value;
        });

        // キーワードに応じて返す擬似的な生成テキストを用意
        function getMockResponse(prompt, model, temperature) {
            // 全角・半角を区別しないために小文字で判定
            const lowerPrompt = prompt.toLowerCase();

            let baseText = "【擬似的なAI生成結果】\n";
            baseText += "プロンプト: \"" + prompt + "\"\n";
            baseText += "モデル: " + model + "\n";
            baseText += "Temperature: " + temperature + "\n\n";

            if (lowerPrompt.includes("猫")) {
                baseText += "ふわふわした毛皮に包まれた小さな猫は、朝日が差し込む窓辺で静かに丸くなっている。その瞳は琥珀色に輝き、しなやかな尾は優雅な曲線を描く。\n" +
                            "この猫は人間に対して警戒心を持ちながらも、一度心を開いた相手には無限の甘えを見せる。";
            } else if (lowerPrompt.includes("エネルギー問題") || lowerPrompt.includes("環境")) {
                baseText += "世界的なエネルギー問題は、化石燃料の枯渇と気候変動への懸念を背景に深刻化している。再生可能エネルギーの導入は、ただ単に環境負荷を低減するだけでなく、地域経済の活性化や新たな技術開発の契機となる。\n" +
                            "太陽光や風力エネルギーなどのクリーンな資源を活用することで、持続可能な未来を築くことが可能だ。";
            } else if (lowerPrompt.includes("小説の冒頭") || lowerPrompt.includes("物語の始まり")) {
                baseText += "薄暗い路地裏に、一人の少年が立っていた。その少年の瞳には、不思議な光が宿っている。遠くで犬が吠える音、古い街灯が淡い橙色の光を投げかける。\n" +
                            "少年は一枚の古めかしい地図を握りしめ、見知らぬ世界への第一歩を踏み出そうとしていた。";
            } else if (lowerPrompt.includes("ビジネス戦略") || lowerPrompt.includes("マーケティング")) {
                baseText += "成功するビジネス戦略は、顧客ニーズの正確な把握から始まる。市場調査をもとに、ターゲット層に響く価値提案を明確化し、差別化された製品・サービスを提供することが重要だ。\n" +
                            "さらに、マーケティング戦略を通じてブランド認知度を高め、持続的な成長のために柔軟な計画修正とPDCAサイクルを回し続ける必要がある。";
            } else {
                // 特定のキーワードがない場合は、汎用的な擬似生成テキストを返す
                baseText += "あなたのプロンプトに基づくテキストを生成します。\n" +
                            "このテキストはあくまでサンプルであり、実際のAIモデルによる生成結果を模したものです。\n\n" +
                            "ここに様々なアイディア、説明、物語、または議論が展開されることでしょう。\n" +
                            "モデルやTemperatureを変更することで、文体やアイデアの広がり、独創性のレベルが変化すると考えられます。";
            }

            return baseText;
        }

        generateBtn.addEventListener('click', async () => {
            const prompt = promptInput.value.trim();
            const model = modelSelect.value;
            const temperature = parseFloat(temperatureRange.value);

            if (!prompt) {
                alert("プロンプトを入力してください。");
                return;
            }

            // 前回の結果やエラーメッセージをクリア
            outputArea.textContent = '';
            errorMessage.style.display = 'none';
            errorMessage.textContent = '';

            // ローディング表示
            loadingOverlay.style.display = 'flex';

            try {
                // 実際のfetchを行わず、擬似生成結果を生成
                const generatedText = getMockResponse(prompt, model, temperature);
                // 模擬的に処理時間を設ける(待ち時間を演出)
                await new Promise(resolve => setTimeout(resolve, 1000));

                outputArea.textContent = generatedText;
            } catch (err) {
                console.error(err);
                errorMessage.textContent = "エラーが発生しました。詳細はコンソールをご確認ください。";
                errorMessage.style.display = 'block';
            } finally {
                // ローディング非表示
                loadingOverlay.style.display = 'none';
            }
        });
    </script>
</body>
</html>

高度なコード比較サイト

<!DOCTYPE html>
<html lang="ja">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>高度なコード比較サイト</title>
  <style>
    body {
      font-family: Arial, sans-serif;
      background-color: #f4f4f4;
      margin: 0;
      padding: 0;
    }

    .container {
      width: 90%;
      max-width: 900px;
      margin: 20px auto;
      background: #fff;
      box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
      padding: 20px;
      border-radius: 5px;
    }

    h1 {
      text-align: center;
      margin-bottom: 20px;
      color: #333;
    }

    .code-input {
      display: flex;
      justify-content: space-between;
      margin-bottom: 20px;
      gap: 10px;
    }

    textarea {
      width: 48%;
      height: 300px;
      font-family: monospace;
      font-size: 14px;
      padding: 10px;
      border: 1px solid #ddd;
      border-radius: 5px;
      resize: none;
      background-color: #f9f9f9;
    }

    .buttons {
      display: flex;
      justify-content: center;
      gap: 10px;
    }

    button {
      padding: 10px 20px;
      background: #007BFF;
      color: #fff;
      border: none;
      border-radius: 5px;
      cursor: pointer;
      font-size: 16px;
    }

    button:hover {
      background: #0056b3;
    }

    #result {
      white-space: pre-wrap;
      font-family: monospace;
      background-color: #f8f9fa;
      padding: 10px;
      border: 1px solid #ddd;
      border-radius: 5px;
      max-height: 300px;
      overflow-y: auto;
    }

    .highlight {
      background-color: #ffcccc;
      font-weight: bold;
      color: #d9534f;
    }

    .line {
      border-left: 4px solid #ccc;
      padding-left: 10px;
      margin: 5px 0;
    }
  </style>
</head>
<body>
  <div class="container">
    <h1>高度なコード比較ツール</h1>
    <div class="code-input">
      <textarea id="code1" placeholder="コード1を入力..."></textarea>
      <textarea id="code2" placeholder="コード2を入力..."></textarea>
    </div>
    <div class="buttons">
      <button onclick="compareCodes()">比較する</button>
      <button onclick="clearFields()">クリア</button>
    </div>
    <h3>比較結果</h3>
    <div id="result">
      <!-- 結果表示エリア -->
    </div>
  </div>
  <script>
    function compareCodes() {
      const code1 = document.getElementById('code1').value.split('\n');
      const code2 = document.getElementById('code2').value.split('\n');
      const resultContainer = document.getElementById('result');
      resultContainer.innerHTML = '';

      const maxLength = Math.max(code1.length, code2.length);

      for (let i = 0; i < maxLength; i++) {
        const line1 = code1[i] || '';
        const line2 = code2[i] || '';
        const lineClass = line1 !== line2 ? 'highlight' : '';

        resultContainer.innerHTML += `
          <div class="line">
            <strong>行 ${i + 1}:</strong>
            <span class="${lineClass}">コード1: "${line1}"</span> |
            <span class="${lineClass}">コード2: "${line2}"</span>
          </div>`;
      }

      if (!resultContainer.innerHTML.trim()) {
        resultContainer.innerHTML = '<div>コードに違いはありません。</div>';
      }
    }

    function clearFields() {
      document.getElementById('code1').value = '';
      document.getElementById('code2').value = '';
      document.getElementById('result').innerHTML = '';
    }
  </script>
</body>
</html>
<!DOCTYPE html>
<html lang="ja">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>高度なコード比較サイト</title>
  <style>
    body {
      font-family: Arial, sans-serif;
      background-color: #f4f4f4;
      margin: 0;
      padding: 0;
    }

    .container {
      width: 90%;
      max-width: 900px;
      margin: 20px auto;
      background: #fff;
      box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
      padding: 20px;
      border-radius: 5px;
    }

    h1 {
      text-align: center;
      margin-bottom: 20px;
      color: #333;
    }

    .code-input {
      display: flex;
      justify-content: space-between;
      margin-bottom: 20px;
      gap: 10px;
    }

    textarea {
      width: 48%;
      height: 300px;
      font-family: monospace;
      font-size: 14px;
      padding: 10px;
      border: 1px solid #ddd;
      border-radius: 5px;
      resize: none;
      background-color: #f9f9f9;
    }

    .buttons {
      display: flex;
      justify-content: center;
      gap: 10px;
    }

    button {
      padding: 10px 20px;
      background: #007BFF;
      color: #fff;
      border: none;
      border-radius: 5px;
      cursor: pointer;
      font-size: 16px;
    }

    button:hover {
      background: #0056b3;
    }

    #result {
      white-space: pre-wrap;
      font-family: monospace;
      background-color: #f8f9fa;
      padding: 10px;
      border: 1px solid #ddd;
      border-radius: 5px;
      max-height: 300px;
      overflow-y: auto;
    }

    .highlight {
      background-color: #ffcccc;
      font-weight: bold;
      color: #d9534f;
    }

    .line {
      border-left: 4px solid #ccc;
      padding-left: 10px;
      margin: 5px 0;
    }
  </style>
</head>
<body>
  <div class="container">
    <h1>高度なコード比較ツール</h1>
    <div class="code-input">
      <textarea id="code1" placeholder="コード1を入力..."></textarea>
      <textarea id="code2" placeholder="コード2を入力..."></textarea>
    </div>
    <div class="buttons">
      <button onclick="compareCodes()">比較する</button>
      <button onclick="clearFields()">クリア</button>
    </div>
    <h3>比較結果</h3>
    <div id="result">
      <!-- 結果表示エリア -->
    </div>
  </div>
  <script>
    function compareCodes() {
      const code1 = document.getElementById('code1').value.split('\n');
      const code2 = document.getElementById('code2').value.split('\n');
      const resultContainer = document.getElementById('result');
      resultContainer.innerHTML = '';

      const maxLength = Math.max(code1.length, code2.length);

      for (let i = 0; i < maxLength; i++) {
        const line1 = code1[i] || '';
        const line2 = code2[i] || '';
        const lineClass = line1 !== line2 ? 'highlight' : '';

        resultContainer.innerHTML += `
          <div class="line">
            <strong>行 ${i + 1}:</strong>
            <span class="${lineClass}">コード1: "${line1}"</span> |
            <span class="${lineClass}">コード2: "${line2}"</span>
          </div>`;
      }

      if (!resultContainer.innerHTML.trim()) {
        resultContainer.innerHTML = '<div>コードに違いはありません。</div>';
      }
    }

    function clearFields() {
      document.getElementById('code1').value = '';
      document.getElementById('code2').value = '';
      document.getElementById('result').innerHTML = '';
    }
  </script>
</body>
</html>

CSS ヘッダーのスタイルの変更

body {
    margin: 0;
    font-family: Verdana, sans-serif;
}

header {
    display: flex;
    padding: 0 16px;
}

header h1 {
    margin: 0;
    font-size: 22px;
    line-height: 64px;
}

.sp-menu {
    margin-left: auto;
}

.sp-menu #open {
    font-size: 32px;
    line-height: 64px;
    cursor: pointer;
}

main {
    padding: 0 16px;
}
body {
    margin: 0;
    font-family: Verdana, sans-serif;
}

header {
    display: flex;
    padding: 0 16px;
}

header h1 {
    margin: 0;
    font-size: 22px;
    line-height: 64px;
}

.sp-menu {
    margin-left: auto;
}

.sp-menu #open {
    font-size: 32px;
    line-height: 64px;
    cursor: pointer;
}

main {
    padding: 0 16px;
}