Skip to main content
Glama

Poker Task Management MCP

by Hirao-Y
interactive_guide_level2.html81.9 kB
<!DOCTYPE html> <html lang="ja"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>🏥 Poker MCP Interactive Guide - Level 2: 実用設計</title> <script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/r128/three.min.js"></script> <style> :root { --primary-blue: #1e3a8a; --primary-green: #059669; --warning-orange: #d97706; --danger-red: #dc2626; --accent-physics: #7c3aed; --accent-success: #10b981; --accent-medical: #ec4899; --accent-nuclear: #f59e0b; --accent-research: #06b6d4; } * { margin: 0; padding: 0; box-sizing: border-box; } body { font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif; background: linear-gradient(135deg, #f8fafc 0%, #e2e8f0 100%); color: #1f2937; overflow-x: hidden; } .main-header { background: linear-gradient(135deg, var(--primary-blue) 0%, var(--accent-physics) 100%); color: white; padding: 1rem 2rem; display: flex; justify-content: space-between; align-items: center; box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1); } .logo { font-size: 1.5rem; font-weight: bold; } .progress-container { flex: 1; max-width: 400px; margin: 0 2rem; } .progress-bar { width: 100%; height: 8px; background: rgba(255, 255, 255, 0.2); border-radius: 4px; overflow: hidden; } .progress { height: 100%; background: var(--accent-success); transition: width 0.5s ease; border-radius: 4px; } .level-indicator { font-size: 0.9rem; opacity: 0.9; margin-top: 0.25rem; } .scenario-selector { position: fixed; top: 0; left: 0; width: 100vw; height: 100vh; background: rgba(0, 0, 0, 0.9); display: flex; justify-content: center; align-items: center; z-index: 1000; } .scenario-modal { background: white; border-radius: 20px; padding: 2rem; max-width: 1000px; max-height: 90vh; overflow-y: auto; } .scenario-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(300px, 1fr)); gap: 1.5rem; margin-top: 1.5rem; } .scenario-card { border: 2px solid #e5e7eb; border-radius: 12px; padding: 1.5rem; cursor: pointer; transition: all 0.3s ease; text-align: center; } .scenario-card:hover { border-color: var(--primary-blue); transform: translateY(-5px); box-shadow: 0 10px 20px rgba(0, 0, 0, 0.1); } .scenario-card.medical { border-color: var(--accent-medical); } .scenario-card.nuclear { border-color: var(--accent-nuclear); } .scenario-card.research { border-color: var(--accent-research); } .scenario-preparation { margin-top: 1rem; padding-top: 1rem; border-top: 1px solid #e5e7eb; } .preparation-badge { background: linear-gradient(45deg, var(--accent-physics), var(--primary-blue)); color: white; padding: 0.25rem 0.75rem; border-radius: 12px; font-size: 0.8rem; font-weight: 600; display: inline-block; margin-bottom: 0.5rem; } .preparation-list { list-style: none; padding: 0; margin: 0; } .preparation-list li { font-size: 0.8rem; color: #6b7280; padding: 0.2rem 0; position: relative; padding-left: 1rem; } .preparation-list li:before { content: "•"; color: var(--primary-blue); font-weight: bold; position: absolute; left: 0; } .scenario-icon { font-size: 3rem; margin-bottom: 1rem; } .scenario-title { font-size: 1.3rem; font-weight: bold; margin-bottom: 0.5rem; } .scenario-description { font-size: 0.95rem; color: #6b7280; margin-bottom: 1rem; } .main-content { display: grid; grid-template-columns: 320px 1fr 350px; gap: 1rem; padding: 1rem; height: calc(100vh - 140px); } .instruction-panel, .design-panel, .visualization-panel { background: white; border-radius: 12px; padding: 1.5rem; box-shadow: 0 4px 6px rgba(0, 0, 0, 0.05); overflow-y: auto; } .visualization-panel { position: relative; overflow: hidden; padding: 0; } #threejs-container { width: 100%; height: 100%; } .view-controls { position: absolute; top: 1rem; right: 1rem; display: flex; flex-direction: column; gap: 0.5rem; } .view-btn { background: rgba(255, 255, 255, 0.9); border: none; padding: 0.5rem 1rem; border-radius: 8px; cursor: pointer; font-size: 0.8rem; font-weight: 600; } .view-btn.active { background: var(--primary-blue); color: white; } .design-tools { position: absolute; bottom: 1rem; left: 1rem; display: flex; gap: 0.5rem; } .tool-btn { background: var(--primary-green); color: white; border: none; padding: 0.5rem 1rem; border-radius: 20px; cursor: pointer; font-size: 0.8rem; font-weight: 600; } .step-indicator { background: linear-gradient(135deg, var(--accent-physics), #9333ea); color: white; padding: 0.5rem 1rem; border-radius: 20px; font-size: 0.85rem; margin-bottom: 1rem; text-align: center; } .design-section { margin-bottom: 2rem; padding-bottom: 1rem; border-bottom: 1px solid #e5e7eb; } .design-section h3 { color: var(--primary-blue); margin-bottom: 1rem; font-size: 1.1rem; } .parameter-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 1rem; margin-bottom: 1rem; } .parameter-input { width: 100%; padding: 0.75rem; border: 2px solid #e5e7eb; border-radius: 8px; font-size: 0.9rem; } .slider-group { margin: 1rem 0; } .slider-group label { display: block; font-weight: 600; margin-bottom: 0.5rem; } .slider { width: 100%; height: 6px; background: #e5e7eb; outline: none; -webkit-appearance: none; } .slider::-webkit-slider-thumb { appearance: none; width: 20px; height: 20px; border-radius: 50%; background: var(--primary-blue); cursor: pointer; } .slider-value { background: var(--primary-blue); color: white; padding: 0.25rem 0.75rem; border-radius: 12px; font-size: 0.8rem; font-weight: 600; margin-left: 0.5rem; } .calc-btn { background: linear-gradient(135deg, var(--primary-blue), var(--accent-physics)); color: white; border: none; padding: 1rem 2rem; border-radius: 10px; font-size: 1rem; font-weight: 600; cursor: pointer; width: 100%; margin: 1rem 0; } .results-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 1rem; margin-top: 1rem; } .result-card { background: rgba(255, 255, 255, 0.8); border-radius: 8px; padding: 1rem; text-align: center; } .result-value { font-size: 1.5rem; font-weight: bold; color: var(--primary-blue); margin: 0.5rem 0; } .result-label { font-size: 0.8rem; color: #6b7280; text-transform: uppercase; } .result-status { padding: 0.25rem 0.75rem; border-radius: 12px; font-size: 0.8rem; font-weight: 600; margin-top: 0.5rem; display: inline-block; } .result-status.ok { background: var(--primary-green); color: white; } .result-status.warning { background: var(--warning-orange); color: white; } .optimization-game { background: linear-gradient(135deg, #fef7cd, #fbbf24); border-radius: 12px; padding: 1.5rem; margin: 1rem 0; display: none; } .constraints-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(120px, 1fr)); gap: 0.5rem; margin: 1rem 0; } .constraint-item { background: rgba(255, 255, 255, 0.7); border-radius: 6px; padding: 0.75rem; text-align: center; font-size: 0.8rem; } .constraint-value { font-weight: bold; color: var(--primary-blue); display: block; margin-top: 0.25rem; } .score-display { background: rgba(255, 255, 255, 0.9); border-radius: 10px; padding: 1rem; text-align: center; margin-top: 1rem; } .score-value { font-size: 2rem; font-weight: bold; color: var(--primary-green); margin: 0.5rem 0; } .navigation-footer { background: white; padding: 1rem 2rem; display: flex; justify-content: space-between; align-items: center; } .nav-btn { padding: 0.75rem 1.5rem; border-radius: 8px; font-size: 0.9rem; font-weight: 600; cursor: pointer; border: none; } .nav-btn.primary { background: var(--primary-blue); color: white; } .nav-btn.secondary { background: #e5e7eb; color: #1f2937; } .nav-btn:disabled { opacity: 0.5; cursor: not-allowed; } @media (max-width: 768px) { .main-content { grid-template-columns: 1fr; height: auto; } .scenario-grid { grid-template-columns: 1fr; } } </style> </head> <body> <div class="scenario-selector" id="scenario-selector"> <div class="scenario-modal"> <h2 style="text-align: center; color: var(--primary-blue); margin-bottom: 1rem;"> 🏗️ 実用設計シナリオを選択してください </h2> <p style="text-align: center; color: #6b7280; margin-bottom: 1.5rem;"> 実際の施設設計を体験しながら、放射線遮蔽の実用スキルを習得しましょう </p> <div class="scenario-grid"> <div class="scenario-card medical" data-scenario="medical"> <div class="scenario-icon">🏥</div> <div class="scenario-title">医療施設遮蔽設計</div> <div class="scenario-description"> 18MV線形加速器治療室の遮蔽設計。医療法施行規則に基づく安全で効率的な設計を学習します。 </div> <div class="scenario-preparation"> <div class="preparation-badge">📋 Level 3A準備</div> <ul class="preparation-list"> <li>医療法施行規則の理解</li> <li>管理区域境界線量基準</li> <li>安全管理体制の基礎</li> </ul> </div> </div> <div class="scenario-card nuclear" data-scenario="nuclear"> <div class="scenario-icon">⚛️</div> <div class="scenario-title">原子力施設遮蔽設計</div> <div class="scenario-description"> 高レベル放射性廃棄物貯蔵施設の遮蔽設計。複合遮蔽と長期安全性を考慮した設計手法を習得します。 </div> <div class="scenario-preparation"> <div class="preparation-badge">📋 Level 3B準備</div> <ul class="preparation-list"> <li>原子炉等規制法の理解</li> <li>複合遮蔽材料の選択</li> <li>長期安全性評価</li> </ul> </div> </div> <div class="scenario-card research" data-scenario="research"> <div class="scenario-icon">🔬</div> <div class="scenario-title">研究施設遮蔽設計</div> <div class="scenario-description"> サイクロトロン加速器施設の中性子遮蔽設計。多様な放射線に対応する複合遮蔽システムを習得します。 </div> <div class="scenario-preparation"> <div class="preparation-badge">📋 Level 3C準備</div> <ul class="preparation-list"> <li>放射線障害防止法の理解</li> <li>中性子遮蔽の基礎</li> <li>複合放射線場の概念</li> </ul> </div> </div> </div> </div> </div> <header class="main-header"> <div class="logo">🏥 Poker MCP Interactive Guide - Level 2</div> <div class="progress-container"> <div class="progress-bar"> <div class="progress" id="main-progress" style="width: 0%"></div> </div> <div class="level-indicator">実用設計 - 完全版</div> </div> <div class="current-step" id="current-step-display">シナリオ選択</div> </header> <main class="main-content"> <div class="instruction-panel"> <div class="step-indicator" id="step-indicator">Step 0: 実用シナリオ選択</div> <div id="instruction-content"> <h2>🎯 Level 2: 実用設計へようこそ</h2> <p>このレベルでは、実際の施設で使用される遮蔽設計技術を習得します。</p> <div style="background: #ede9fe; border: 1px solid var(--accent-physics); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h3>🎓 学習目標</h3> <ul> <li>実際の施設設計プロセス体験</li> <li>制約条件下での最適化手法</li> <li>分野別専門知識の理解</li> <li>総合的な設計判断力</li> </ul> </div> <p>上から1つのシナリオを選択して、実用的な遮蔽設計を体験してください。</p> </div> </div> <div class="visualization-panel"> <div id="threejs-container"></div> <div class="view-controls"> <button class="view-btn active" id="view-structure">🏗️ 構造</button> <button class="view-btn" id="view-dose">☢️ 線量</button> <button class="view-btn" id="view-cost">💰 コスト</button> </div> <div class="design-tools"> <button class="tool-btn" id="optimize-auto">🤖 最適化</button> <button class="tool-btn" id="validate-design">✅ 検証</button> <button class="tool-btn" id="export-report">📄 報告書</button> </div> </div> <div class="design-panel"> <div class="design-section"> <h3>🏗️ 基本幾何設計</h3> <div class="parameter-grid"> <div> <label>室内長さ (m)</label> <input type="number" class="parameter-input" id="room-length" value="8" min="5" max="15" step="0.5"> </div> <div> <label>室内幅 (m)</label> <input type="number" class="parameter-input" id="room-width" value="6" min="4" max="12" step="0.5"> </div> <div> <label>室内高さ (m)</label> <input type="number" class="parameter-input" id="room-height" value="3" min="2.5" max="5" step="0.1"> </div> <div> <label>迷路長さ (m)</label> <input type="number" class="parameter-input" id="maze-length" value="4" min="2" max="8" step="0.5"> </div> </div> </div> <div class="design-section"> <h3>🧱 遮蔽材料設計</h3> <div class="slider-group"> <label>主壁厚さ (cm)</label> <input type="range" class="slider" id="main-wall-thickness" min="50" max="300" value="150" step="5"> <span class="slider-value" id="main-wall-value">150 cm</span> </div> <div class="slider-group"> <label>ドア遮蔽厚さ (cm)</label> <input type="range" class="slider" id="door-thickness" min="5" max="50" value="15" step="1"> <span class="slider-value" id="door-value">15 cm</span> </div> <div style="margin: 1rem 0;"> <label style="display: block; font-weight: 600; margin-bottom: 0.5rem;">主壁材料</label> <select class="parameter-input" id="wall-material"> <option value="concrete_normal">普通コンクリート</option> <option value="concrete_heavy" selected>重コンクリート</option> <option value="concrete_barite">バライトコンクリート</option> <option value="concrete_borated">ホウ素入りコンクリート</option> <option value="steel_concrete">鋼鉄+コンクリート複合</option> </select> </div> <div style="margin: 1rem 0;"> <label style="display: block; font-weight: 600; margin-bottom: 0.5rem;">ドア材料</label> <select class="parameter-input" id="door-material"> <option value="lead" selected>純鉛</option> <option value="steel_lead">鋼鉄+鉛複合</option> <option value="tungsten">タングステン</option> </select> </div> </div> <div style="background: #f0fdf4; border: 1px solid var(--primary-green); border-radius: 10px; padding: 1.5rem; margin: 1rem 0;"> <button class="calc-btn" id="calculate-design">⚡ 高精度遮蔽性能計算</button> <div class="results-grid" id="results-grid" style="display: none;"> <div class="result-card"> <div class="result-label">最大線量率</div> <div class="result-value" id="max-dose-rate">-- μSv/h</div> <div class="result-status" id="dose-status">--</div> </div> <div class="result-card"> <div class="result-label">総工事費</div> <div class="result-value" id="total-cost">-- 万円</div> <div class="result-status" id="cost-status">--</div> </div> <div class="result-card"> <div class="result-label">材料重量</div> <div class="result-value" id="total-weight">-- トン</div> <div class="result-status" id="weight-status">--</div> </div> <div class="result-card"> <div class="result-label">安全余裕</div> <div class="result-value" id="safety-margin">-- %</div> <div class="result-status" id="margin-status">--</div> </div> </div> </div> <div class="optimization-game" id="optimization-game"> <div style="text-align: center; margin-bottom: 1rem;"> <h4 style="color: var(--warning-orange); margin-bottom: 0.5rem;">🎯 設計最適化チャレンジ</h4> <p>制約条件内で最高効率の設計を達成しよう!</p> </div> <div class="constraints-grid"> <div class="constraint-item"> <div>線量率上限</div> <div class="constraint-value" id="dose-constraint">2.5 μSv/h</div> </div> <div class="constraint-item"> <div>予算上限</div> <div class="constraint-value" id="cost-constraint">5000 万円</div> </div> <div class="constraint-item"> <div>重量制限</div> <div class="constraint-value" id="weight-constraint">800 トン</div> </div> <div class="constraint-item"> <div>工期制限</div> <div class="constraint-value" id="schedule-constraint">6 ヶ月</div> </div> </div> <div class="score-display"> <div class="result-label">総合最適化スコア</div> <div class="score-value" id="optimization-score">0</div> <div style="font-size: 0.8rem; color: #6b7280;">100点満点</div> </div> </div> </div> </main> <footer class="navigation-footer"> <button class="nav-btn secondary" id="prev-step" disabled>← 前のステップ</button> <div style="display: flex; gap: 1rem;"> <button class="nav-btn secondary" id="hint-btn">💡 ヒント</button> <button class="nav-btn secondary" id="reset-design">🔄 リセット</button> <button class="nav-btn secondary" id="save-design">💾 保存</button> </div> <button class="nav-btn primary" id="next-step">次のステップ →</button> </footer> <script> const scenarioDatabase = { medical: { name: "医療施設遮蔽設計", icon: "🏥", description: "18MV線形加速器治療室", source: { type: "linac_18MV", energy: 18, nominalRate: 600 }, requirements: { doseLimit: 2.5, regulation: "医療法施行規則" }, constraints: { maxCost: 5000, maxWeight: 800, maxSchedule: 6 }, materials: ["concrete_heavy", "concrete_barite", "steel_concrete"], defaultDesign: { roomDimensions: [8, 6, 3], wallThickness: 150, doorThickness: 15, mazeLength: 4 } }, nuclear: { name: "原子力施設遮蔽設計", icon: "⚛️", description: "高レベル放射性廃棄物貯蔵施設", source: { type: "mixed_waste", activity: 1e15 }, requirements: { doseLimit: 250, regulation: "核燃料物質等の規制に関する法律" }, constraints: { maxCost: 15000, maxWeight: 2000, maxSchedule: 12 }, materials: ["steel_concrete", "concrete_heavy"], defaultDesign: { roomDimensions: [6, 6, 4], wallThickness: 200, doorThickness: 25, mazeLength: 6 } }, research: { name: "研究施設遮蔽設計", icon: "🔬", description: "サイクロトロン加速器施設", source: { type: "cyclotron", energy: 30, current: 100 }, requirements: { doseLimit: 5.0, regulation: "放射線障害防止法" }, constraints: { maxCost: 8000, maxWeight: 1200, maxSchedule: 9 }, materials: ["concrete_borated", "steel_concrete", "concrete_heavy"], defaultDesign: { roomDimensions: [10, 8, 4], wallThickness: 180, doorThickness: 20, mazeLength: 5 } } }; const materialDatabase = { concrete_normal: { name: "普通コンクリート", density: 2.3, muMass: 0.0636, cost: 25000, color: 0xd2b48c }, concrete_heavy: { name: "重コンクリート", density: 3.5, muMass: 0.0636, cost: 45000, color: 0x8b7355 }, concrete_barite: { name: "バライトコンクリート", density: 4.2, muMass: 0.0620, cost: 85000, color: 0x9d8964 }, concrete_borated: { name: "ホウ素入りコンクリート", density: 2.8, muMass: 0.0636, cost: 65000, color: 0xa0a0ff }, steel_concrete: { name: "鋼鉄+コンクリート複合", density: 4.2, muMass: 0.0580, cost: 85000, color: 0x708090 }, lead: { name: "純鉛", density: 11.34, muMass: 0.107, cost: 450000, color: 0x696969 }, steel_lead: { name: "鋼鉄+鉛複合", density: 9.5, muMass: 0.089, cost: 320000, color: 0x2f4f4f }, tungsten: { name: "タングステン", density: 19.25, muMass: 0.0947, cost: 2800000, color: 0x404040 } }; let scene, camera, renderer; let currentScenario = null; let designParameters = {}; let calculationResults = {}; let visualizer = null; let progressManager = null; class ProgressManager { constructor() { this.currentStep = 0; this.totalSteps = 6; this.scenario = null; } setScenario(scenarioKey) { this.scenario = scenarioKey; this.currentStep = 1; this.updateProgress(); this.updateStepContent(); } updateProgress() { const progress = Math.max(0, (this.currentStep - 1) / (this.totalSteps - 1) * 100); document.getElementById('main-progress').style.width = progress + '%'; const stepNames = ["シナリオ選択", "法規制・仕様理解", "基本幾何設計", "材料設計・申請基礎", "性能最適化", "品質保証・検証", "Level3準備完了"]; document.getElementById('current-step-display').textContent = stepNames[this.currentStep] || `Step ${this.currentStep}`; } nextStep() { if (this.currentStep < this.totalSteps) { this.currentStep++; this.updateStepContent(); this.updateProgress(); } else { alert('🎉 Level 2 完了!\n\n実用的な遮蔽設計スキルを習得しました!'); } } updateStepContent() { const scenario = scenarioDatabase[this.scenario]; if (!scenario) return; const stepContents = { 1: { title: `Step 1: ${scenario.name} - 施設仕様・法規制理解`, content: ` <div style="background: #ede9fe; border: 1px solid var(--accent-physics); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h3>${scenario.icon} ${scenario.name}</h3> <p><strong>${scenario.description}</strong></p> <h4>🎯 設計要求事項</h4> <ul> <li>線量率限度: <strong>${scenario.requirements.doseLimit} μSv/h</strong></li> <li>法的根拠: ${scenario.requirements.regulation}</li> </ul> </div> <div class="regulation-details" style="background: #fef7cd; border: 1px solid var(--warning-orange); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h4>📋 ${this.getRegulationTitle()}</h4> <div class="regulation-content"> ${this.getRegulationContent()} </div> </div> <div class="workflow-preview" style="background: #f0fdf4; border: 1px solid var(--primary-green); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h4>🔄 実務ワークフロー概要</h4> <div class="workflow-steps"> 企画 → 基本設計 → <strong>詳細設計(現在学習中)</strong> → 申請書類作成 → 施工 → 検査 → 運用 </div> <p style="font-size: 0.9rem; color: #6b7280; margin-top: 0.5rem;"> Level 3では、申請から運用まで全プロセスを詳細に学習します </p> </div> <p>💡 右側の3D表示で施設構造を確認し、設計パラメータを理解しましょう。</p> ` }, 2: { title: "Step 2: 基本幾何設計", content: ` <h3>🏗️ 施設幾何の詳細設計</h3> <p>治療室・貯蔵室・実験室の最適な空間配置を設計します。</p> <div style="background: #fef3c7; border: 1px solid var(--warning-orange); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h4>🎯 設計考慮事項</h4> <ul> <li><strong>室内寸法</strong>: 設備配置・作業空間・保守アクセス</li> <li><strong>迷路設計</strong>: 散乱線低減・入退室効率</li> <li><strong>構造強度</strong>: 自重・地震荷重・長期安定性</li> </ul> </div> <p>⚡ パラメータを調整して最適な施設レイアウトを設計してください。</p> ` }, 3: { title: "Step 3: 遮蔽材料設計・申請書類基礎", content: ` <h3>🧱 高度な遮蔽材料設計</h3> <p>材料選択と厚さ決定により、安全性と経済性を両立します。</p> <div style="background: #fef2f2; border: 1px solid var(--danger-red); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h4>⚖️ 遮蔽性能の定量評価</h4> <p><strong>Cs-137を1/100に減衰させる厚さ:</strong></p> <ul> <li>鉛: 約4cm(最高効率)</li> <li>コンクリート: 約80cm(大容量・低コスト)</li> <li>重コンクリート: 約50cm(中間解)</li> </ul> </div> <p>🧪 「高精度遮蔽性能計算」で実際の減衰を確認しながら最適化してください。</p> <div class="document-creation-preview" style="background: #fef7cd; border: 1px solid var(--warning-orange); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h4>📄 設計書作成の基礎体験</h4> <p>実務では、計算結果を申請書類にまとめる必要があります。</p> <div class="basic-document-template"> <div class="template-section"> <strong>1. 設計概要:</strong> <span class="auto-fill" style="color: var(--primary-blue); font-weight: 600;"> ${this.getBasicDesignSummary()} </span> </div> <div class="template-section"> <strong>2. 遮蔽計算結果:</strong> <span class="auto-fill" id="doc-calc-results" style="color: var(--primary-blue);"> 計算実行後に自動挿入 </span> </div> <div class="template-section"> <strong>3. 法規制遵守状況:</strong> <span class="auto-fill" id="doc-compliance" style="color: var(--primary-blue);"> 計算実行後に自動評価 </span> </div> </div> <p style="font-size: 0.9rem; color: #6b7280; margin-top: 0.75rem;"> ⚡ 計算実行後、上記テンプレートに結果が自動挿入されます<br> 📚 Level 3では、正式な申請書類の作成方法を詳しく学習します </p> </div> ` }, 4: { title: "Step 4: 性能最適化", content: ` <h3>🎮 設計最適化チャレンジ</h3> <p>全制約条件を満たしながら、最高効率の設計を目指します。</p> <div style="background: #ede9fe; border: 1px solid var(--accent-physics); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h4>🏆 最適化目標</h4> <ol> <li><strong>安全性確保</strong> (50点): 線量率基準の確実な遵守</li> <li><strong>経済性向上</strong> (30点): 総工事費の最小化</li> <li><strong>設計効率</strong> (20点): 重量・空間・工期の効率化</li> </ol> </div> <p>🎯 右下の最適化スコア100点達成を目指しましょう!</p> ` }, 5: { title: "Step 5: 高度品質保証・第三者検証", content: ` <h3>🔍 多段階品質保証システム</h3> <p>実務では、段階的な品質確認により設計の信頼性を確保します。</p> <div class="verification-levels" style="background: #f0fdf4; border: 1px solid var(--primary-green); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h4>📊 Level 1: 自己検証</h4> <div class="check-items"> <label><input type="checkbox" class="verification-check"> 計算結果の再確認・単位系の一貫性</label><br> <label><input type="checkbox" class="verification-check"> 入力パラメータの妥当性確認</label><br> <label><input type="checkbox" class="verification-check"> 保守的仮定の適用確認</label> </div> </div> <div class="internal-review" style="background: #fef7cd; border: 1px solid var(--warning-orange); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h4>🤝 Level 2: 内部査読</h4> <button class="simulate-review-btn" style="background: var(--warning-orange); color: white; border: none; padding: 0.5rem 1rem; border-radius: 6px; cursor: pointer;"> 📋 内部査読シミュレーション </button> <div class="review-feedback" style="display: none; margin-top: 1rem;"> <h5>👨‍🔬 上級研究者からの査読コメント例:</h5> <ul style="margin: 0.5rem 0;"> <li>"ビルドアップ係数の選択根拠を明確にしてください"</li> <li>"散乱線の寄与を考慮していますか?"</li> <li>"安全余裕の設定理由を記載してください"</li> </ul> </div> </div> <div class="external-audit-prep" style="background: #fef2f2; border: 1px solid var(--danger-red); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h4>🏛️ Level 3: 外部監査準備</h4> <ul> <li><strong>計算手法の透明性:</strong> 使用した公式・定数の明示</li> <li><strong>保守的仮定:</strong> 不確かさを考慮した安全側評価</li> <li><strong>代替案検討:</strong> 複数の設計案の比較検討</li> <li><strong>妥当性確認:</strong> ベンチマーク問題との比較</li> </ul> <p style="font-size: 0.9rem; color: #6b7280; margin-top: 0.5rem;"> 📚 Level 3では、実際の規制審査対応方法を詳しく学習します </p> </div> <div class="benchmark-test" style="background: #ede9fe; border: 1px solid var(--accent-physics); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h4>🎯 ベンチマーク検証</h4> <p><strong>NCRP Report 144 標準問題との比較:</strong></p> <div class="benchmark-comparison"> <div>あなたの計算結果: <span id="user-result-benchmark">未計算</span></div> <div>標準解: 2.4 μSv/h</div> <div>許容差異: ±20%以内</div> </div> <button class="run-benchmark-btn" style="background: var(--accent-physics); color: white; border: none; padding: 0.5rem 1rem; border-radius: 6px; cursor: pointer; margin-top: 0.5rem;"> 🔄 ベンチマーク実行 </button> </div> ` }, 6: { title: "Step 6: Level 3準備完了・進路選択", content: ` <h3>🎓 Level 3準備状況評価</h3> <p>Level 2での学習を基に、Level 3での専門学習の準備状況を確認します。</p> <div class="readiness-assessment" style="background: #ede9fe; border: 1px solid var(--accent-physics); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h4>📊 ${this.getCurrentScenarioReadiness().title}準備度</h4> <div class="progress-bar" style="background: #e5e7eb; height: 8px; border-radius: 4px; margin: 0.5rem 0;"> <div class="progress" style="background: var(--accent-success); height: 100%; border-radius: 4px; width: ${this.getCurrentScenarioReadiness().percentage}%; transition: width 0.5s ease;"></div> </div> <div class="readiness-items" style="margin: 1rem 0;"> ${this.getCurrentScenarioReadiness().items} </div> </div> <div class="level3-pathways" style="background: #f0fdf4; border: 1px solid var(--primary-green); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h4>🚀 推奨Level 3学習パス</h4> <div class="pathway-recommendation"> ${this.getLevel3Recommendation()} </div> </div> <div class="next-steps" style="background: #fef7cd; border: 1px solid var(--warning-orange); border-radius: 8px; padding: 1rem; margin: 1rem 0;"> <h4>📋 次のステップ</h4> <ul> <li><strong>実務適用:</strong> 学習した設計手法の実践活用</li> <li><strong>Level 3学習:</strong> 専門分野での高度技能習得</li> <li><strong>継続学習:</strong> 最新技術・規制動向の把握</li> <li><strong>知識共有:</strong> チーム・組織への技術展開</li> </ul> </div> <div class="completion-certificate" style="text-align: center; background: linear-gradient(135deg, var(--accent-success), var(--primary-green)); color: white; border-radius: 12px; padding: 2rem; margin: 1rem 0;"> <h3>🏆 Level 2 実用設計 完了証明</h3> <p style="margin: 1rem 0;">放射線遮蔽実用設計スキルを習得しました</p> <div style="font-size: 0.9rem; opacity: 0.9;"> 習得スキル: 実用設計・法規制理解・品質保証・Level 3準備 </div> </div> ` } }; const currentContent = stepContents[this.currentStep]; if (currentContent) { document.getElementById('step-indicator').textContent = currentContent.title; document.getElementById('instruction-content').innerHTML = currentContent.content; const optimizationGame = document.getElementById('optimization-game'); if (this.currentStep >= 4) { optimizationGame.style.display = 'block'; } document.getElementById('prev-step').disabled = this.currentStep <= 1; document.getElementById('next-step').textContent = this.currentStep >= this.totalSteps ? '🎉 Level完了' : '次のステップ →'; } } calculateFinalScore() { if (!calculationResults || !calculationResults.isValid) return 0; const scenario = scenarioDatabase[this.scenario]; let score = 0; if (calculationResults.maxDoseRate <= scenario.requirements.doseLimit) { const margin = (scenario.requirements.doseLimit - calculationResults.maxDoseRate) / scenario.requirements.doseLimit; score += Math.min(50, 30 + margin * 20); } if (calculationResults.totalCost <= scenario.constraints.maxCost) { const efficiency = 1 - (calculationResults.totalCost / scenario.constraints.maxCost); score += Math.min(30, efficiency * 30); } if (calculationResults.totalWeight <= scenario.constraints.maxWeight) { const lightness = 1 - (calculationResults.totalWeight / scenario.constraints.maxWeight); score += Math.min(20, lightness * 20); } return Math.round(score); } getRegulationTitle() { switch (this.scenario) { case 'medical': return '医療法施行規則の基礎理解'; case 'nuclear': return '原子炉等規制法の基礎理解'; case 'research': return '放射線障害防止法の基礎理解'; default: return '適用法令の理解'; } } getRegulationContent() { switch (this.scenario) { case 'medical': return ` <ul> <li><strong>管理区域境界:</strong> 1.3mSv/3ヶ月以下</li> <li><strong>一般病室:</strong> 1.3mSv/3ヶ月以下 (年間5.2mSv相当)</li> <li><strong>安全管理体制:</strong> 責任者配置、指針策定、研修実施が義務</li> <li><strong>線量管理:</strong> 装置毎の線量記録と保存</li> <li><strong>Level 3で学習:</strong> 詳細な申請手続きと審査対応</li> </ul> `; case 'nuclear': return ` <ul> <li><strong>線量限度:</strong> 管理区域境界で250μSv/3ヶ月以下</li> <li><strong>安全審査:</strong> 設計・建設・運転の各段階で審査</li> <li><strong>品質保証:</strong> QMSに基づく設計・施工管理</li> <li><strong>長期安全:</strong> 廃棄物の長期保管を考慮した設計</li> <li><strong>Level 3で学習:</strong> 安全解析書の作成と審査対応</li> </ul> `; case 'research': return ` <ul> <li><strong>管理区域:</strong> 週40時間で1.3mSv/3ヶ月以下</li> <li><strong>許可申請:</strong> 使用・貯蔵・廃棄の各段階で許可必要</li> <li><strong>定期検査:</strong> 年1回の施設点検と記録保存</li> <li><strong>中性子対策:</strong> 特殊な遮蔽材料と線量評価手法</li> <li><strong>Level 3で学習:</strong> 許可申請書の詳細作成手法</li> </ul> `; default: return '<p>適用法令に応じた規制内容を理解します。</p>'; } } getBasicDesignSummary() { const scenario = scenarioDatabase[this.scenario]; if (!scenario) return '設計概要を生成中...'; switch (this.scenario) { case 'medical': return '18MV線形加速器治療室の遮蔽設計、医療法施行規則に基づく管理区域境界線量率2.5μSv/h以下を目標'; case 'nuclear': return '高レベル放射性廃棄物貯蔵施設の遮蔽設計、原子炉等規制法に基づく境界線量率250μSv/3ヶ月以下を目標'; case 'research': return 'サイクロトロン加速器施設の中性子遮蔽設計、放射線障害防止法に基づく管理区域境界線量率5.0μSv/h以下を目標'; default: return '放射線遮蔽設計の概要'; } } getCurrentScenarioReadiness() { switch (this.scenario) { case 'medical': return { title: '医療施設遮蔽(Level 3A)', percentage: 75, items: ` ✅ 医療法施行規則の基本理解<br> ✅ 線形加速器遮蔽の基礎計算<br> ✅ 設計書作成の基礎体験<br> 📚 Level 3A: 詳細申請書類・複雑散乱計算・審査対応を学習予定 ` }; case 'nuclear': return { title: '原子力施設遮蔽(Level 3B)', percentage: 70, items: ` ✅ 原子炉等規制法の基本理解<br> ✅ 複合遮蔽材料選択の基礎<br> ✅ 品質保証システムの理解<br> 📚 Level 3B: 安全解析書・長期安全性評価・規制審査を学習予定 ` }; case 'research': return { title: '研究施設遮蔽(Level 3C)', percentage: 80, items: ` ✅ 放射線障害防止法の基本理解<br> ✅ 中性子遮蔽の基礎概念<br> ✅ 複合放射線場の理解<br> 📚 Level 3C: MCNP連携・詳細中性子計算・許可申請を学習予定 ` }; default: return { title: '放射線遮蔽設計', percentage: 75, items: '基本的な準備が完了しています。' }; } } getLevel3Recommendation() { switch (this.scenario) { case 'medical': return ` <div style="padding: 0.5rem 0;"> <strong>🏥 Level 3A: 医療施設遮蔽設計実践</strong><br> <span style="color: #6b7280; font-size: 0.9rem;"> • 詳細な申請書類作成(使用許可・変更届出)<br> • 複雑な散乱計算(一次・二次散乱の詳細評価)<br> • 規制審査対応(指摘事項・追加資料作成)<br> • 実際の施設設計プロジェクト体験 </span> </div> `; case 'nuclear': return ` <div style="padding: 0.5rem 0;"> <strong>⚛️ Level 3B: 原子力施設遮蔽設計実践</strong><br> <span style="color: #6b7280; font-size: 0.9rem;"> • 安全解析書の遮蔽設計章作成<br> • 長期安全性評価(腐食・劣化考慮)<br> • QMSに基づく設計管理<br> • 廃棄物処理施設設計プロジェクト </span> </div> `; case 'research': return ` <div style="padding: 0.5rem 0;"> <strong>🔬 Level 3C: 研究施設遮蔽設計実践</strong><br> <span style="color: #6b7280; font-size: 0.9rem;"> • MCNP連携による高精度計算<br> • 中性子遮蔽の詳細設計手法<br> • 使用許可申請書の完全作成<br> • 加速器施設設計プロジェクト </span> </div> `; default: return 'あなたの学習目標に応じたLevel 3コースを選択してください。'; } } } class FacilityVisualizer { constructor(container) { this.container = container; this.facilityObjects = {}; this.initializeScene(); this.animate(); } initializeScene() { scene = new THREE.Scene(); scene.background = new THREE.Color(0xf0f4f8); camera = new THREE.PerspectiveCamera(60, this.container.clientWidth / this.container.clientHeight, 0.1, 1000); camera.position.set(15, 10, 15); camera.lookAt(0, 0, 0); renderer = new THREE.WebGLRenderer({ antialias: true }); renderer.setSize(this.container.clientWidth, this.container.clientHeight); renderer.shadowMap.enabled = true; this.container.appendChild(renderer.domElement); const ambientLight = new THREE.AmbientLight(0xffffff, 0.4); scene.add(ambientLight); const directionalLight = new THREE.DirectionalLight(0xffffff, 0.6); directionalLight.position.set(10, 20, 10); directionalLight.castShadow = true; scene.add(directionalLight); this.createFloorAndGrid(); this.setupControls(); } createFloorAndGrid() { const floorGeometry = new THREE.PlaneGeometry(50, 50); const floorMaterial = new THREE.MeshLambertMaterial({ color: 0xffffff, transparent: true, opacity: 0.8 }); const floor = new THREE.Mesh(floorGeometry, floorMaterial); floor.rotation.x = -Math.PI / 2; floor.receiveShadow = true; scene.add(floor); const gridHelper = new THREE.GridHelper(50, 50, 0xcccccc, 0xeeeeee); scene.add(gridHelper); } setupControls() { let isMouseDown = false; let mouseX = 0, mouseY = 0; let targetRotationY = 0.8; let currentDistance = 25; this.container.addEventListener('mousedown', (event) => { isMouseDown = true; mouseX = event.clientX; mouseY = event.clientY; }); this.container.addEventListener('mousemove', (event) => { if (!isMouseDown) return; const deltaX = event.clientX - mouseX; targetRotationY += deltaX * 0.01; mouseX = event.clientX; mouseY = event.clientY; }); this.container.addEventListener('mouseup', () => { isMouseDown = false; }); this.container.addEventListener('wheel', (event) => { event.preventDefault(); currentDistance += event.deltaY * 0.01; currentDistance = Math.max(10, Math.min(60, currentDistance)); }); const updateCamera = () => { camera.position.x = currentDistance * Math.sin(targetRotationY); camera.position.y = currentDistance * 0.5; camera.position.z = currentDistance * Math.cos(targetRotationY); camera.lookAt(0, 2, 0); requestAnimationFrame(updateCamera); }; updateCamera(); } createFacilityStructure(scenario, parameters) { this.clearFacility(); const roomLength = parameters.roomLength || 8; const roomWidth = parameters.roomWidth || 6; const roomHeight = parameters.roomHeight || 3; const wallThickness = (parameters.wallThickness || 150) / 100; const wallMaterial = materialDatabase[parameters.wallMaterial] || materialDatabase.concrete_heavy; this.createWalls(roomLength, roomWidth, roomHeight, wallThickness, wallMaterial); this.createRadiationSource(scenario); this.createDetectors(roomLength, roomWidth, wallThickness); } createWalls(length, width, height, thickness, materialData) { const wallMaterial = new THREE.MeshPhongMaterial({ color: materialData.color, transparent: true, opacity: 0.8 }); const walls = [ { geometry: new THREE.BoxGeometry(length + 2*thickness, height, thickness), position: [0, height/2, -width/2 - thickness/2] }, { geometry: new THREE.BoxGeometry(length + 2*thickness, height, thickness), position: [0, height/2, width/2 + thickness/2] }, { geometry: new THREE.BoxGeometry(thickness, height, width), position: [-length/2 - thickness/2, height/2, 0] }, { geometry: new THREE.BoxGeometry(thickness, height, width), position: [length/2 + thickness/2, height/2, 0] }, { geometry: new THREE.BoxGeometry(length + 2*thickness, thickness, width + 2*thickness), position: [0, height + thickness/2, 0] } ]; walls.forEach((wallData, index) => { const wall = new THREE.Mesh(wallData.geometry, wallMaterial); wall.position.set(...wallData.position); wall.castShadow = true; wall.receiveShadow = true; this.facilityObjects[`wall_${index}`] = wall; scene.add(wall); }); } createRadiationSource(scenario) { let geometry, material; switch (scenario) { case 'medical': geometry = new THREE.BoxGeometry(3, 2, 1.5); material = new THREE.MeshPhongMaterial({ color: 0x4a90e2, emissive: 0x001133 }); break; case 'nuclear': geometry = new THREE.CylinderGeometry(1.0, 1.0, 3); material = new THREE.MeshPhongMaterial({ color: 0xff6b35, emissive: 0x331100 }); break; case 'research': geometry = new THREE.CylinderGeometry(2.5, 2.5, 1); material = new THREE.MeshPhongMaterial({ color: 0x50c878, emissive: 0x003311 }); break; default: geometry = new THREE.SphereGeometry(0.5); material = new THREE.MeshPhongMaterial({ color: 0xff4444, emissive: 0x220000 }); } const source = new THREE.Mesh(geometry, material); source.position.set(0, 1.5, 0); source.castShadow = true; this.facilityObjects.radiation_source = source; scene.add(source); } createDetectors(roomLength, roomWidth, wallThickness) { const detectorGeometry = new THREE.SphereGeometry(0.12); const detectorMaterial = new THREE.MeshPhongMaterial({ color: 0x44ff44, emissive: 0x002200, transparent: true, opacity: 0.8 }); const detectionPoints = [ [roomLength/2 + wallThickness + 0.3, 1, 0], [-roomLength/2 - wallThickness - 0.3, 1, 0], [0, 1, roomWidth/2 + wallThickness + 0.3], [0, 1, -roomWidth/2 - wallThickness - 0.3] ]; detectionPoints.forEach((pos, index) => { const detector = new THREE.Mesh(detectorGeometry, detectorMaterial.clone()); detector.position.set(...pos); this.facilityObjects[`detector_${index}`] = detector; scene.add(detector); }); } clearFacility() { Object.values(this.facilityObjects).forEach(obj => { scene.remove(obj); }); this.facilityObjects = {}; } animate() { const render = () => { requestAnimationFrame(render); if (this.facilityObjects.radiation_source) { this.facilityObjects.radiation_source.rotation.y += 0.01; } renderer.render(scene, camera); }; render(); } } class ShieldingCalculator { calculateShielding(scenario, parameters) { const scenarioData = scenarioDatabase[scenario]; const wallMaterial = materialDatabase[parameters.wallMaterial]; const wallThickness = parameters.wallThickness / 100; const distance = 1.5; const sourceActivity = scenarioData.source.nominalRate || scenarioData.source.activity || 1000; const geometricAttenuation = 1 / (distance * distance); const mu = wallMaterial.muMass * wallMaterial.density * 100; const shieldingAttenuation = Math.exp(-mu * wallThickness); const buildup = 1 + (mu * wallThickness) * 0.5; const baseDoseRate = sourceActivity * 0.001; const maxDoseRate = baseDoseRate * geometricAttenuation * shieldingAttenuation * buildup; const roomLength = parameters.roomLength || 8; const roomWidth = parameters.roomWidth || 6; const roomHeight = parameters.roomHeight || 3; const volume = this.calculateWallVolume(roomLength, roomWidth, roomHeight, wallThickness); const totalCost = volume * wallMaterial.cost / 10000; const totalWeight = volume * wallMaterial.density; const safetyMargin = Math.max(0, ((scenarioData.requirements.doseLimit - maxDoseRate) / scenarioData.requirements.doseLimit) * 100); return { maxDoseRate: Math.max(maxDoseRate, 0.01), avgDoseRate: maxDoseRate * 0.7, totalCost: totalCost, totalWeight: totalWeight, safetyMargin: safetyMargin, isValid: maxDoseRate <= scenarioData.requirements.doseLimit }; } calculateWallVolume(length, width, height, wallThickness) { const outerLength = length + 2 * wallThickness; const outerWidth = width + 2 * wallThickness; const outerHeight = height + wallThickness; const outerVolume = outerLength * outerWidth * outerHeight; const innerVolume = length * width * height; return outerVolume - innerVolume; } } document.addEventListener('DOMContentLoaded', () => { progressManager = new ProgressManager(); const calculator = new ShieldingCalculator(); const scenarioCards = document.querySelectorAll('.scenario-card'); scenarioCards.forEach(card => { card.addEventListener('click', () => { selectScenario(card.dataset.scenario); }); }); const parameterInputs = document.querySelectorAll('.parameter-input'); parameterInputs.forEach(input => { input.addEventListener('change', updateDesignParameters); }); const sliders = document.querySelectorAll('.slider'); sliders.forEach(slider => { slider.addEventListener('input', (e) => { updateSliderDisplay(slider); updateDesignParameters(); }); }); document.getElementById('next-step').addEventListener('click', () => { progressManager.nextStep(); }); document.getElementById('prev-step').addEventListener('click', () => { if (progressManager.currentStep > 1) { progressManager.currentStep--; progressManager.updateStepContent(); progressManager.updateProgress(); } }); document.getElementById('calculate-design').addEventListener('click', async () => { if (!currentScenario) return; const calculateBtn = document.getElementById('calculate-design'); const resultsGrid = document.getElementById('results-grid'); calculateBtn.disabled = true; calculateBtn.textContent = '🔄 高精度計算中...'; try { await new Promise(resolve => setTimeout(resolve, 1000)); calculationResults = calculator.calculateShielding(currentScenario, designParameters); document.getElementById('max-dose-rate').textContent = calculationResults.maxDoseRate.toFixed(2) + ' μSv/h'; document.getElementById('total-cost').textContent = calculationResults.totalCost.toFixed(0) + ' 万円'; document.getElementById('total-weight').textContent = calculationResults.totalWeight.toFixed(0) + ' トン'; document.getElementById('safety-margin').textContent = calculationResults.safetyMargin.toFixed(1) + ' %'; updateResultStatus('dose-status', calculationResults.isValid); updateResultStatus('cost-status', calculationResults.totalCost <= scenarioDatabase[currentScenario].constraints.maxCost); updateResultStatus('weight-status', calculationResults.totalWeight <= scenarioDatabase[currentScenario].constraints.maxWeight); updateResultStatus('margin-status', calculationResults.safetyMargin >= 20); if (progressManager.currentStep >= 4) { updateOptimizationScore(); } // Update document template if in step 3 or later if (progressManager.currentStep >= 3) { updateDocumentTemplate(); } } catch (error) { alert('計算中にエラーが発生しました。'); } finally { calculateBtn.disabled = false; calculateBtn.textContent = '⚡ 高精度遮蔽性能計算'; resultsGrid.style.display = 'grid'; } }); document.getElementById('hint-btn').addEventListener('click', () => { if (!currentScenario) return; const scenarioData = scenarioDatabase[currentScenario]; alert(`💡 ${scenarioData.name}のヒント:\n\n• 線量限度: ${scenarioData.requirements.doseLimit} μSv/h\n• 法的根拠: ${scenarioData.requirements.regulation}\n• 設計のポイント: 安全性を最優先に考慮しましょう!`); }); document.getElementById('reset-design').addEventListener('click', resetToDefaultDesign); document.getElementById('save-design').addEventListener('click', () => { alert('💾 設計が保存されました!'); }); // New interactive features document.addEventListener('click', (e) => { if (e.target.classList.contains('simulate-review-btn')) { const feedbackDiv = e.target.parentElement.querySelector('.review-feedback'); if (feedbackDiv) { feedbackDiv.style.display = feedbackDiv.style.display === 'none' ? 'block' : 'none'; } } if (e.target.classList.contains('run-benchmark-btn')) { runBenchmarkTest(); } }); function selectScenario(scenarioKey) { currentScenario = scenarioKey; const scenarioData = scenarioDatabase[scenarioKey]; document.getElementById('scenario-selector').style.display = 'none'; progressManager.setScenario(scenarioKey); const defaultDesign = scenarioData.defaultDesign; designParameters = { roomLength: defaultDesign.roomDimensions[0], roomWidth: defaultDesign.roomDimensions[1], roomHeight: defaultDesign.roomDimensions[2], wallThickness: defaultDesign.wallThickness, doorThickness: defaultDesign.doorThickness, mazeLength: defaultDesign.mazeLength, wallMaterial: scenarioData.materials[0] || 'concrete_heavy', doorMaterial: 'lead' }; updateUIFromParameters(); initializeVisualization(); updateConstraintDisplay(scenarioData); } function initializeVisualization() { const container = document.getElementById('threejs-container'); visualizer = new FacilityVisualizer(container); visualizer.createFacilityStructure(currentScenario, designParameters); } function updateDesignParameters() { if (!currentScenario) return; designParameters.roomLength = parseFloat(document.getElementById('room-length').value) || 8; designParameters.roomWidth = parseFloat(document.getElementById('room-width').value) || 6; designParameters.roomHeight = parseFloat(document.getElementById('room-height').value) || 3; designParameters.wallThickness = parseFloat(document.getElementById('main-wall-thickness').value) || 150; designParameters.doorThickness = parseFloat(document.getElementById('door-thickness').value) || 15; designParameters.mazeLength = parseFloat(document.getElementById('maze-length').value) || 4; designParameters.wallMaterial = document.getElementById('wall-material').value || 'concrete_heavy'; designParameters.doorMaterial = document.getElementById('door-material').value || 'lead'; if (visualizer && currentScenario) { visualizer.createFacilityStructure(currentScenario, designParameters); } } function updateSliderDisplay(slider) { const valueDisplay = document.getElementById(slider.id.replace('main-wall-thickness', 'main-wall-value').replace('door-thickness', 'door-value')); if (valueDisplay) { valueDisplay.textContent = slider.value + ' cm'; } } function updateResultStatus(elementId, isGood) { const element = document.getElementById(elementId); if (isGood) { element.textContent = '✓ 適合'; element.className = 'result-status ok'; } else { element.textContent = '⚠ 要改善'; element.className = 'result-status warning'; } } function updateOptimizationScore() { if (!calculationResults || !calculationResults.isValid) { document.getElementById('optimization-score').textContent = '0'; return; } const score = progressManager.calculateFinalScore(); document.getElementById('optimization-score').textContent = score; } function updateConstraintDisplay(scenarioData) { document.getElementById('dose-constraint').textContent = scenarioData.requirements.doseLimit + ' μSv/h'; document.getElementById('cost-constraint').textContent = scenarioData.constraints.maxCost + ' 万円'; document.getElementById('weight-constraint').textContent = scenarioData.constraints.maxWeight + ' トン'; document.getElementById('schedule-constraint').textContent = scenarioData.constraints.maxSchedule + ' ヶ月'; } function updateUIFromParameters() { document.getElementById('room-length').value = designParameters.roomLength; document.getElementById('room-width').value = designParameters.roomWidth; document.getElementById('room-height').value = designParameters.roomHeight; document.getElementById('main-wall-thickness').value = designParameters.wallThickness; document.getElementById('door-thickness').value = designParameters.doorThickness; document.getElementById('maze-length').value = designParameters.mazeLength; document.getElementById('wall-material').value = designParameters.wallMaterial; document.getElementById('door-material').value = designParameters.doorMaterial; document.getElementById('main-wall-value').textContent = designParameters.wallThickness + ' cm'; document.getElementById('door-value').textContent = designParameters.doorThickness + ' cm'; } function resetToDefaultDesign() { if (!currentScenario) return; const defaultDesign = scenarioDatabase[currentScenario].defaultDesign; designParameters = { roomLength: defaultDesign.roomDimensions[0], roomWidth: defaultDesign.roomDimensions[1], roomHeight: defaultDesign.roomDimensions[2], wallThickness: defaultDesign.wallThickness, doorThickness: defaultDesign.doorThickness, mazeLength: defaultDesign.mazeLength, wallMaterial: scenarioDatabase[currentScenario].materials[0], doorMaterial: 'lead' }; updateUIFromParameters(); if (visualizer) { visualizer.createFacilityStructure(currentScenario, designParameters); } alert('🔄 設計パラメータをデフォルト値にリセットしました。'); } function updateDocumentTemplate() { if (!calculationResults || !currentScenario) return; const docCalcResults = document.getElementById('doc-calc-results'); const docCompliance = document.getElementById('doc-compliance'); if (docCalcResults) { docCalcResults.textContent = `最大線量率 ${calculationResults.maxDoseRate.toFixed(2)} μSv/h, 遮蔽厚さ ${designParameters.wallThickness || 150} cm`; } if (docCompliance) { const scenario = scenarioDatabase[currentScenario]; const isCompliant = calculationResults.maxDoseRate <= scenario.requirements.doseLimit; docCompliance.textContent = isCompliant ? `✓ ${scenario.requirements.regulation}に適合` : `⚠ 基準値${scenario.requirements.doseLimit}μSv/hを超過、要改善`; docCompliance.style.color = isCompliant ? 'var(--primary-green)' : 'var(--danger-red)'; } } function runBenchmarkTest() { if (!calculationResults) { alert('⚠ まず遮蔽計算を実行してください'); return; } const userResult = calculationResults.maxDoseRate; const standardResult = 2.4; const difference = ((userResult - standardResult) / standardResult * 100); const userResultElement = document.getElementById('user-result-benchmark'); if (userResultElement) { userResultElement.textContent = userResult.toFixed(2) + ' μSv/h'; } const isAcceptable = Math.abs(difference) <= 20; const message = isAcceptable ? `✅ ベンチマーク検証合格!\n差異: ${difference.toFixed(1)}% (許容範囲内)` : `⚠ ベンチマーク検証要確認\n差異: ${difference.toFixed(1)}% (許容範囲±20%を超過)`; alert(message); } }); </script> </body> </html>

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/Hirao-Y/poker_mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server