183 lines
19 KiB
HTML
183 lines
19 KiB
HTML
<!doctype html>
|
||
<html lang="ko">
|
||
<head>
|
||
<meta charset="UTF-8" />
|
||
<meta name="viewport" content="width=device-width, initial-scale=1.0, viewport-fit=cover" />
|
||
<meta name="theme-color" content="#101823" />
|
||
<meta name="description" content="함께 떠나는 온라인 해돋이, 해보러가기" />
|
||
<title>해보러가기</title>
|
||
<meta property="og:type" content="website" />
|
||
<meta property="og:url" content="https://sunrise.horoli.kr/" />
|
||
<meta property="og:title" content="해보러가기 · 관악산 일출" />
|
||
<meta property="og:description" content="함께 떠나는 온라인 해돋이. 관악산의 일출을 3D 풍경으로 만나보세요." />
|
||
<meta property="og:image" content="https://sunrise.horoli.kr/og-sunrise.jpg" />
|
||
<meta property="og:image:width" content="1200" />
|
||
<meta property="og:image:height" content="630" />
|
||
<meta property="og:image:alt" content="능선 위로 해가 떠오르기 시작하는 해보러가기 메인 화면" />
|
||
<link rel="preload" href="/fonts/GowunDodum-Title.ttf" as="font" type="font/ttf" crossorigin />
|
||
</head>
|
||
<body class="in-lobby">
|
||
<section id="lobby" aria-label="해보러가기 시작 화면">
|
||
<canvas id="lobby-sunrise" aria-hidden="true"></canvas>
|
||
<div class="lobby-content">
|
||
<h1 class="lobby-brand" aria-label="해 보러가기"><img src="/sunrise-mark.svg" alt="" />보러가기</h1>
|
||
<div class="lobby-panel">
|
||
<h2 id="lobby-title" tabindex="-1" hidden></h2>
|
||
<p id="lobby-status" role="status" aria-live="polite" hidden></p>
|
||
<div id="lobby-options"></div>
|
||
<button id="lobby-back" type="button" hidden>뒤로</button>
|
||
<button id="lobby-retry" type="button" hidden>다시 시도</button>
|
||
</div>
|
||
</div>
|
||
</section>
|
||
<svg class="icon-definitions" aria-hidden="true" xmlns="http://www.w3.org/2000/svg">
|
||
<symbol id="icon-place" viewBox="0 0 24 24"><path d="M20 10c0 6-8 12-8 12S4 16 4 10a8 8 0 1 1 16 0Z"/><circle cx="12" cy="10" r="2.5"/></symbol>
|
||
<symbol id="icon-clock" viewBox="0 0 24 24"><circle cx="12" cy="12" r="9"/><path d="M12 7v5l3 2"/></symbol>
|
||
<symbol id="icon-menu" viewBox="0 0 24 24"><path d="M4 6h16M4 12h16M4 18h16"/></symbol>
|
||
<symbol id="icon-wave" viewBox="0 0 24 24"><path d="M8 12V5a1.5 1.5 0 0 1 3 0v6-8a1.5 1.5 0 0 1 3 0v8-6a1.5 1.5 0 0 1 3 0v7-3a1.5 1.5 0 0 1 3 0v6a7 7 0 0 1-12 5l-5-6a1.5 1.5 0 0 1 2-2l3 3M3 4 1 2M2 8H0"/></symbol>
|
||
<symbol id="icon-sunrise" viewBox="0 0 24 24"><path d="M2 18h20M4 22h16M7 18a5 5 0 0 1 10 0M12 3v6M9 6l3-3 3 3M3 11l2 2M21 11l-2 2"/></symbol>
|
||
<symbol id="icon-umbrella" viewBox="0 0 24 24"><path d="M2 12a10 10 0 0 1 20 0H2Zm10 0v7a2 2 0 0 0 4 0M12 2V1"/></symbol>
|
||
<symbol id="icon-raincoat" viewBox="0 0 24 24"><path d="m8 3 4 3 4-3 5 5-3 4-2-2v11H8V10l-2 2-3-4 5-5ZM12 6v15M9 16h1M14 16h1"/></symbol>
|
||
<symbol id="icon-hood" viewBox="0 0 24 24"><path d="M4 15V10a8 8 0 0 1 16 0v5l-3 6H7l-3-6Z"/><path d="M8 15V10a4 4 0 0 1 8 0v5l-4 3-4-3ZM10 18v4M14 18v4"/></symbol>
|
||
<symbol id="icon-flashlight" viewBox="0 0 24 24"><path d="M8 10h8l-1 11H9L8 10ZM6 5h12v5H6V5ZM9 14h6M8 1l-1 2M12 0v3M16 1l1 2"/></symbol>
|
||
</svg>
|
||
<canvas id="world" aria-label="태양 관측 3D 풍경"></canvas>
|
||
<main class="hud" aria-label="관측 조작">
|
||
<div id="compass" role="img" aria-label="현재 시선 방위">
|
||
<div class="compass-scale" aria-hidden="true"></div>
|
||
<span class="compass-pointer" aria-hidden="true"></span>
|
||
<span class="compass-bearing" aria-hidden="true"></span>
|
||
</div>
|
||
<nav class="scene-toolbar" aria-label="화면 메뉴">
|
||
<div class="location-menu">
|
||
<button type="button" id="location-toggle" aria-expanded="false" aria-controls="location-options"><svg class="icon" aria-hidden="true"><use href="#icon-place"/></svg><span id="current-location">관악산 정상</span></button>
|
||
<div id="location-options" hidden>
|
||
<span class="sr-only" id="site-label">GWANAKSAN</span><span class="sr-only" id="observer-name">관악산 정상</span>
|
||
<nav class="site-navigation menu-list" aria-label="관측 장소">
|
||
<a data-site="gwanaksan" href="?site=gwanaksan">관악산</a><a data-site="hajodae" href="?site=hajodae">하조대</a><a data-site="gisamun" href="?site=gisamun">기사문 해변</a>
|
||
</nav>
|
||
</div>
|
||
</div>
|
||
<div class="toolbar-end">
|
||
<button type="button" id="screenshot-open" data-panel="screenshot" aria-label="촬영" title="화면 촬영" aria-haspopup="dialog" aria-controls="ui-dialog" disabled><svg class="icon" aria-hidden="true" viewBox="0 0 24 24"><path d="M3 6h4l2-3h6l2 3h4v15H3Z"/><circle cx="12" cy="13" r="4"/></svg></button>
|
||
<button type="button" data-panel="menu" aria-label="메뉴" aria-haspopup="dialog" aria-controls="ui-dialog"><svg class="icon" aria-hidden="true"><use href="#icon-menu"/></svg></button>
|
||
</div>
|
||
</nav>
|
||
<aside id="minimap-overlay" hidden>
|
||
<section id="terrain-minimap" class="minimap" aria-label="등고선 미니맵" hidden>
|
||
<button id="minimap-close" type="button" aria-label="미니맵 숨기기">×</button>
|
||
<div class="minimap-map">
|
||
<canvas aria-label="DSM 등고선 지도 · 화살표는 현재 위치와 방향" role="img"></canvas>
|
||
<span class="minimap-direction north">N</span><span class="minimap-direction east">E</span><span class="minimap-direction south">S</span><span class="minimap-direction west">W</span>
|
||
<div class="minimap-zoom"><button type="button" data-zoom="out" aria-label="미니맵 축소">−</button><button type="button" data-zoom="in" aria-label="미니맵 확대">+</button></div>
|
||
</div>
|
||
</section>
|
||
</aside>
|
||
<div id="solo-time-controls" aria-label="관측 시간">
|
||
<button id="time-toggle" type="button" aria-expanded="false" aria-controls="time-settings" aria-label="관측 시간 설정"><svg class="icon" aria-hidden="true"><use href="#icon-clock"/></svg><span id="compact-time" aria-hidden="true">00:00</span><span class="time-toggle-label">설정</span></button>
|
||
<div id="time-settings">
|
||
<div class="date-row"><span id="mode" class="mode">LIVE</span><time id="selected-time"></time><span class="unit">KST</span></div>
|
||
<fieldset id="time-controls" class="time-panel" aria-label="관측 시각 조절" disabled>
|
||
<label class="date-field"><span class="date-label">관측 날짜 · KST</span><span class="date-picker"><svg class="icon" aria-hidden="true" viewBox="0 0 24 24"><rect x="3" y="5" width="18" height="16" rx="3"/><path d="M7 3v4M17 3v4M3 11h18"/></svg><span id="date-display" aria-hidden="true"></span><input id="date" type="date" min="1901-01-01" max="2099-12-31" aria-label="관측 날짜 · KST" /></span></label>
|
||
<div class="slider-field"><div class="slider-label"><label for="time-slider">관측 시각</label><output id="time-output" for="time-slider">00:00:00</output></div>
|
||
<input id="time-slider" type="range" min="0" max="86390" step="10" value="0" title="방향키로 10초씩 조절" />
|
||
<div class="ticks" aria-hidden="true"><span>00:00</span><span>06:00</span><span>12:00</span><span>18:00</span><span>23:59</span></div>
|
||
</div>
|
||
<button id="live-button" type="button" aria-pressed="true" title="현재 시각으로 돌아가기"><span class="live-dot" aria-hidden="true"></span>LIVE</button>
|
||
</fieldset>
|
||
</div>
|
||
</div>
|
||
<div id="companion-selection" role="group" aria-label="선택한 캐릭터" hidden>
|
||
<span id="companion-name"></span>
|
||
<button type="button" id="stand-beside">옆에 서기</button>
|
||
<button type="button" id="companion-close" aria-label="선택 닫기">×</button>
|
||
<p id="companion-status" role="status"></p>
|
||
</div>
|
||
<div class="movement-controls" aria-label="위치와 방향 조절">
|
||
<p id="direction-hint" role="status" hidden>좌우로 드래그하면 내 캐릭터만 돌아갑니다</p>
|
||
<button type="button" id="direction-toggle" aria-pressed="false" aria-describedby="direction-hint" disabled>방향 맞추기</button>
|
||
</div>
|
||
<div class="emote-controls" aria-label="캐릭터 액션">
|
||
<button type="button" id="emote-wave" disabled aria-pressed="false" aria-describedby="emote-status" title="손 흔들기 · 단축키 1"><svg class="icon" aria-hidden="true"><use href="#icon-wave"/></svg><span id="primary-action-label">인사</span></button>
|
||
<button type="button" id="emote-pray" disabled aria-pressed="false" aria-describedby="emote-status" title="소원빌기 · 일출 전후 5분 · 단축키 2"><svg class="icon" aria-hidden="true"><use href="#icon-sunrise"/></svg>소원빌기</button>
|
||
<div class="equipment-menu">
|
||
<button type="button" id="equipment-toggle" aria-expanded="false" aria-controls="equipment-options"><svg class="icon" aria-hidden="true"><use href="#icon-umbrella"/></svg>장비</button>
|
||
<div id="equipment-options" hidden>
|
||
<div class="equipment-controls" role="group" aria-label="장비">
|
||
<button type="button" id="gear-flashlight" disabled aria-pressed="false" aria-label="손전등 켜기" title="손전등 · 단축키 6"><svg class="icon" aria-hidden="true"><use href="#icon-flashlight"/></svg><span id="flashlight-lumens"></span></button>
|
||
<button type="button" id="gear-umbrella" disabled aria-pressed="false" aria-label="우산 쓰기" title="우산 쓰기 · 단축키 3" aria-describedby="gear-status"><svg class="icon" aria-hidden="true"><use href="#icon-umbrella"/></svg></button>
|
||
<button type="button" id="gear-raincoat" disabled aria-pressed="false" aria-label="우비 입기" title="우비 입기 · 단축키 4" aria-describedby="gear-status"><svg class="icon" aria-hidden="true"><use href="#icon-raincoat"/></svg></button>
|
||
<button type="button" id="gear-hood" disabled aria-pressed="false" aria-label="모자 쓰기" title="모자 쓰기 · 단축키 5" aria-describedby="gear-status"><svg class="icon" aria-hidden="true"><use href="#icon-hood"/></svg></button>
|
||
</div>
|
||
<p id="gear-status" class="sr-only" role="status">기상악화시 사용할 수 있습니다</p>
|
||
</div>
|
||
</div>
|
||
<span id="emote-status" class="sr-only" role="status">양 캐릭터 불러오는 중…</span>
|
||
</div>
|
||
</main>
|
||
|
||
<div id="equipment-notice" role="status" aria-live="polite" hidden><svg class="icon" aria-hidden="true"><use href="#icon-umbrella"/></svg><span></span></div>
|
||
<dialog id="ui-dialog" aria-labelledby="dialog-title">
|
||
<header class="dialog-header"><button type="button" id="dialog-back" aria-label="뒤로" hidden>←</button><h1 id="dialog-title">메뉴</h1><button type="button" data-close aria-label="닫기" autofocus>×</button></header>
|
||
<div class="dialog-body">
|
||
<section data-dialog-panel="screenshot" hidden>
|
||
<p class="muted">현재 보고 있는 장면을 PNG 이미지로 저장합니다.</p>
|
||
<div class="menu-list">
|
||
<button type="button" data-screenshot="ui">UI 포함 · 화면 그대로</button>
|
||
<button type="button" data-screenshot="scene">UI 제외 · 풍경만</button>
|
||
</div>
|
||
</section>
|
||
<section data-dialog-panel="menu" hidden>
|
||
<p id="menu-current-mode" class="muted menu-current-mode">현재 함께 보기 중</p>
|
||
<nav class="menu-list menu-primary" aria-label="주요 메뉴">
|
||
<a href="./">메인으로 나가기 <span aria-hidden="true">↗</span></a>
|
||
<button id="session-mode" type="button" data-scene-action>혼자 보기로 전환</button>
|
||
</nav>
|
||
<details class="menu-secondary"><summary>설정 및 정보</summary>
|
||
<nav class="menu-list" aria-label="상세 메뉴">
|
||
<button type="button" data-panel="information">관측 정보 <span aria-hidden="true">›</span></button>
|
||
<button type="button" data-panel="view">지도·시점 <span aria-hidden="true">›</span></button>
|
||
<button type="button" data-panel="session">닉네임·접속 상태 <span aria-hidden="true">›</span></button>
|
||
<button type="button" data-panel="settings">설정·조작 방법 <span aria-hidden="true">›</span></button>
|
||
<button type="button" data-panel="sources">출처·오픈소스 <span aria-hidden="true">›</span></button>
|
||
</nav>
|
||
</details>
|
||
</section>
|
||
|
||
<section class="information" data-dialog-panel="information" hidden>
|
||
<div class="angles"><div><span class="label">방위각</span><strong id="azimuth">—</strong><span class="unit">북쪽 기준</span></div><div><span class="label">겉보기 고도각</span><strong id="altitude">—</strong><span id="sun-status" class="unit"></span></div></div>
|
||
<div class="events"><span>일출 <b id="sunrise">—</b></span><span>일몰 <b id="sunset">—</b></span></div>
|
||
<p class="muted">DSM 고도 보정 · 천문 시각 (능선 통과 시각 아님)<span id="standard-times"></span></p>
|
||
<div class="weather-information"><h2>기상</h2><p id="weather-status" class="muted" role="status">선택 시각의 기상자료 불러오는 중</p><p class="muted">관측지점 대표값 · 구름·시정·비·눈은 시각적 근사</p><p class="muted"><a href="https://open-meteo.com/" target="_blank" rel="noopener">Weather data by Open-Meteo</a> · <a href="https://creativecommons.org/licenses/by/4.0/" target="_blank" rel="noopener">CC BY 4.0</a></p><p class="muted">운량·시정은 시간 보간하고, 강우량은 제공되는 비·소나기 강수량을 합산합니다. 하늘·강수 효과는 이 자료를 가공한 시각적 표현입니다.</p></div>
|
||
<details><summary>관측점·지형 상태</summary><p id="observer-details" class="muted"></p><p id="terrain-status" class="muted" role="status">지형 불러오는 중…</p><p id="movement-status" class="muted">시작점에서 0m · 지형 따라 이동 · 구조물 충돌 미적용</p><p id="view-note" class="muted" role="status"></p></details>
|
||
</section>
|
||
<section data-dialog-panel="view" hidden>
|
||
<label class="switch-row"><input id="minimap-toggle" type="checkbox" />미니맵을 화면에 계속 표시</label>
|
||
<div class="structure-controls menu-list" aria-label="시점 선택">
|
||
<button type="button" id="look-east" data-scene-action>동쪽 하늘</button><button type="button" id="look-city" data-scene-action>과천 방향</button><button type="button" id="reset-position" data-scene-action>시작점 복귀</button><button type="button" id="city-overview" data-scene-action>과천 건물 조감</button>
|
||
<button type="button" data-look="summit-mast" data-scene-action>정상 통신탑</button><button type="button" data-look="summit-marker" data-scene-action>정상 표지석</button><button type="button" data-look="weather-radar" data-scene-action>레이돔</button><button type="button" data-look="north-deck" data-scene-action>북쪽 데크</button>
|
||
</div>
|
||
</section>
|
||
<section data-dialog-panel="session" hidden>
|
||
<div class="session-controls" aria-label="공동 관측 접속"><label for="nickname">닉네임</label><input id="nickname" type="text" maxlength="20" autocomplete="off" /><div class="button-row"><button id="retry-connection" type="button" hidden>다시 입장</button></div><p id="connection-status" class="muted" role="status" aria-live="polite">관악산 공동 방 준비 중…</p></div>
|
||
</section>
|
||
<section data-dialog-panel="settings" hidden>
|
||
<div class="height-field"><div class="slider-label"><label for="eye-height">관측 기준 높이</label><output id="eye-height-output" for="eye-height"></output></div><input id="eye-height" type="range" aria-describedby="eye-height-note" /><p id="eye-height-note" class="muted">태양 계산 기준 · 카메라는 3인칭</p></div>
|
||
<details open><summary>조작 방법</summary><p id="control-hint">바닥 탭 또는 우클릭으로 이동 · 캐릭터 탭 또는 클릭으로 선택 · 드래그로 시점만 회전 · 두 손가락 핀치 또는 마우스 휠로 확대·축소 · 방향 맞추기를 누른 뒤 좌우 드래그로 내 캐릭터 회전, 완료로 종료</p><p class="muted">1 인사 · 2 소원빌기 · 3 우산 · 4 우비 · 5 모자</p><p class="muted">소원빌기는 선택 시각이 일출 전후 5분일 때 사용할 수 있습니다. 이동하면 감정표현이 종료됩니다.</p></details>
|
||
<a id="terrain-comparison" class="terrain-source" href="?terrain=original">원본 지형 비교</a>
|
||
</section>
|
||
<section data-dialog-panel="sources" hidden>
|
||
<details open><summary>데이터 출처</summary><a class="terrain-source" href="/data-sources.html" target="_blank" rel="noopener">자료별 출처·라이선스·가공 데이터 다운로드</a><a class="terrain-source" href="https://open-meteo.com/" target="_blank" rel="noopener">Weather data by Open-Meteo</a><a class="terrain-source" href="https://creativecommons.org/licenses/by/4.0/" target="_blank" rel="noopener">기상 데이터 이용조건 · CC BY 4.0</a><p class="muted">기상 자료의 시간 보간·강우량 합산 및 시각 효과 변환을 적용했습니다.</p><a id="osm-source" class="terrain-source" href="/buildings/source.html" target="_blank" rel="noopener">건물: 국토교통부/VWorld · CC BY 2.0 KR</a><a id="terrain-source" class="terrain-source" href="/terrain/source.html" target="_blank" rel="noopener">DSM: 수목·구조물 포함 · 데이터 출처/제한</a><a id="building-status" class="terrain-source" href="/buildings/source.html" target="_blank" rel="noopener">건물 자료 불러오는 중…</a></details>
|
||
<details><summary>모델·참고 자료</summary><a id="structure-source" class="terrain-source" href="/structures.html" target="_blank" rel="noopener">구조물 모델 · 위치·치수 추정 · 근거 보기</a></details>
|
||
<details><summary>오픈소스 라이브러리</summary><p class="muted">Three.js · SunCalc · Socket.IO Client 및 포함된 의존성</p><a class="terrain-source" href="/licenses.txt" target="_blank" rel="noopener">버전·저작권·라이선스 원문</a></details>
|
||
<details><summary>글꼴</summary><p class="muted">고운돋움 · Pretendard — SIL Open Font License 1.1</p><a class="terrain-source" href="/fonts/GowunDodum-OFL.txt" target="_blank" rel="noopener">고운돋움 저작권·라이선스</a><a class="terrain-source" href="/fonts/Pretendard-LICENSE.txt" target="_blank" rel="noopener">Pretendard 저작권·라이선스</a></details>
|
||
<p class="muted">자료별 원본·이용 조건과 보정 내역은 각 출처 페이지에서 확인할 수 있습니다.</p>
|
||
</section>
|
||
</div>
|
||
</dialog>
|
||
<p id="screenshot-status" role="status" aria-live="polite" hidden></p>
|
||
<p id="render-error" role="alert" hidden></p>
|
||
<script type="module" src="/src/entry.ts"></script>
|
||
</body>
|
||
</html>
|