first commit

This commit is contained in:
2026-06-10 22:46:10 +07:00
commit a7cb1f2de0
15 changed files with 4045 additions and 0 deletions
+305
View File
@@ -0,0 +1,305 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>WebGIS — Spatial Data Management System</title>
<!-- Leaflet CSS -->
<link rel="stylesheet" href="https://unpkg.com/leaflet@1.9.4/dist/leaflet.css">
<!-- Leaflet Draw CSS -->
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/leaflet.draw/1.0.4/leaflet.draw.css">
<!-- App CSS -->
<link rel="stylesheet" href="assets/css/style.css">
</head>
<body>
<!-- ═══════════════════════ HEADER ═══════════════════════ -->
<header id="header">
<div class="logo">WEB<span>GIS</span></div>
<div class="tagline">Spatial Data Management System · Soreang, West Java</div>
<div class="spacer"></div>
<div class="status-badge">● LIVE</div>
</header>
<!-- ═══════════════════════ MAIN APP ═══════════════════════ -->
<div id="app">
<!-- ───────── SIDEBAR ───────── -->
<aside id="sidebar">
<!-- Tab Navigation -->
<nav id="sidebar-tabs">
<button class="tab-btn active" data-tab="layers">
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2">
<path d="M12 2L2 7l10 5 10-5-10-5zM2 17l10 5 10-5M2 12l10 5 10-5"/>
</svg>
LAYERS
</button>
<button class="tab-btn" data-tab="points">
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2">
<circle cx="12" cy="12" r="4"/><circle cx="12" cy="12" r="10" stroke-dasharray="2 3"/>
</svg>
POINTS
</button>
<button class="tab-btn" data-tab="roads">
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2">
<path d="M5 3v18M19 3v18M5 12h14"/>
</svg>
ROADS
</button>
<button class="tab-btn" data-tab="parcels">
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2">
<rect x="3" y="3" width="18" height="18" rx="2"/>
<path d="M9 3v18M3 9h18"/>
</svg>
PARCELS
</button>
<button class="tab-btn" data-tab="laporan">
📢 LAPORAN
</button>
</nav>
<!-- Tab Content -->
<div id="sidebar-content">
<!-- ════ LAYERS PANEL ════ -->
<div class="panel active" id="panel-layers">
<div class="section-title">⛽ SPBU — Gas Stations</div>
<label class="layer-item">
<input type="checkbox" class="layer-cb" data-layer="spbu24" checked>
<div class="layer-swatch circle" style="background:#22c55e"></div>
<span class="layer-label">24 Hours SPBU</span>
<span class="layer-count" data-count-layer="spbu24">0</span>
</label>
<label class="layer-item">
<input type="checkbox" class="layer-cb" data-layer="spbuNot" checked>
<div class="layer-swatch circle" style="background:#eab308"></div>
<span class="layer-label">Not 24 Hours SPBU</span>
<span class="layer-count" data-count-layer="spbuNot">0</span>
</label>
<div class="section-title">🕌 Other Points</div>
<label class="layer-item">
<input type="checkbox" class="layer-cb" data-layer="mosque" checked>
<div class="layer-swatch circle" style="background:#a78bfa"></div>
<span class="layer-label">Mosques</span>
<span class="layer-count" data-count-layer="mosque">0</span>
</label>
<label class="layer-item">
<input type="checkbox" class="layer-cb" data-layer="poor" checked>
<div class="layer-swatch circle" style="background:#f43f5e"></div>
<span class="layer-label">Poor Population Zones</span>
<span class="layer-count" data-count-layer="poor">0</span>
</label>
<div class="section-title">🛣️ Roads</div>
<label class="layer-item">
<input type="checkbox" class="layer-cb" data-layer="national" checked>
<div class="layer-swatch" style="background:#ef4444"></div>
<span class="layer-label">National Road</span>
<span class="layer-count" data-count-layer="national">0</span>
</label>
<label class="layer-item">
<input type="checkbox" class="layer-cb" data-layer="provincial" checked>
<div class="layer-swatch" style="background:#f97316"></div>
<span class="layer-label">Provincial Road</span>
<span class="layer-count" data-count-layer="provincial">0</span>
</label>
<label class="layer-item">
<input type="checkbox" class="layer-cb" data-layer="district" checked>
<div class="layer-swatch" style="background:#3b82f6"></div>
<span class="layer-label">District Road</span>
<span class="layer-count" data-count-layer="district">0</span>
</label>
<div class="section-title">🗺️ Land Parcels</div>
<label class="layer-item">
<input type="checkbox" class="layer-cb" data-layer="shm" checked>
<div class="layer-swatch" style="background:#10b981"></div>
<span class="layer-label">SHM — Freehold</span>
<span class="layer-count" data-count-layer="shm">0</span>
</label>
<label class="layer-item">
<input type="checkbox" class="layer-cb" data-layer="hgb" checked>
<div class="layer-swatch" style="background:#6366f1"></div>
<span class="layer-label">HGB — Building Rights</span>
<span class="layer-count" data-count-layer="hgb">0</span>
</label>
<label class="layer-item">
<input type="checkbox" class="layer-cb" data-layer="hgu" checked>
<div class="layer-swatch" style="background:#f59e0b"></div>
<span class="layer-label">HGU — Business Rights</span>
<span class="layer-count" data-count-layer="hgu">0</span>
</label>
<label class="layer-item">
<input type="checkbox" class="layer-cb" data-layer="hp" checked>
<div class="layer-swatch" style="background:#ec4899"></div>
<span class="layer-label">HP — Usage Rights</span>
<span class="layer-count" data-count-layer="hp">0</span>
</label>
</div>
<!-- ════ POINTS PANEL ════ -->
<div class="panel" id="panel-points">
<div class="info-box accent">
Click the map to place a point, then fill in the form.
</div>
<div class="btn-row" style="margin-top:0;margin-bottom:12px">
<button class="btn btn-primary btn-full" data-mode="point" onclick="enablePointAdd()">
Add Point on Map
</button>
<button
class="btn btn-secondary btn-full"
onclick="enableLaporanAdd()"
style="margin-top:8px">
📢 Laporkan Warga Miskin
</button>
</div>
<div class="section-title">All Points</div>
<div class="feature-list" id="point-list">
<div class="info-box">Loading…</div>
</div>
</div>
<!-- ════ ROADS PANEL ════ -->
<div class="panel" id="panel-roads">
<div class="info-box accent">
Draw a polyline on the map. Length is calculated automatically.
</div>
<div class="btn-row" style="margin-top:0;margin-bottom:12px">
<button class="btn btn-primary btn-full" data-mode="road" onclick="startAddRoad()">
✏️ Draw Road on Map
</button>
</div>
<div class="section-title">All Roads</div>
<div class="feature-list" id="road-list">
<div class="info-box">Loading…</div>
</div>
</div>
<!-- ════ PARCELS PANEL ════ -->
<div class="panel" id="panel-parcels">
<div class="info-box accent">
Draw a polygon on the map. Area is calculated automatically.
</div>
<div class="btn-row" style="margin-top:0;margin-bottom:12px">
<button class="btn btn-primary btn-full" data-mode="parcel" onclick="startAddParcel()">
🗺️ Draw Parcel on Map
</button>
</div>
<div class="section-title">All Parcels</div>
<div class="feature-list" id="parcel-list">
<div class="info-box">Loading…</div>
</div>
</div>
<!-- ════ LAPORAN PANEL ════ -->
<div class="panel" id="panel-laporan">
<div class="info-box accent">
Daftar laporan masyarakat yang menunggu verifikasi.
</div>
<div class="section-title">
Laporan Masyarakat
</div>
<div class="feature-list" id="laporan-list">
<div class="info-box">
Loading...
</div>
</div>
</div>
</div><!-- /sidebar-content -->
</aside>
<!-- ───────── MAP CONTAINER ───────── -->
<div id="map-container">
<!-- 🔥 PINDAH KE SINI -->
<div style="
position:absolute;
top:10px;
left:50px;
z-index:1000;
background:white;
padding:10px;
border-radius:8px;
box-shadow:0 2px 6px rgba(0,0,0,0.2);
">
Radius: <span id="radiusValue">500</span> m<br>
<input type="range" id="radiusSlider" min="100" max="2000" value="500">
</div>
<div id="map"></div>
<!-- Coordinates display -->
<div id="coords-display">0.000000, 0.000000</div>
<!-- Cancel draw hint (shown only during draw mode) -->
<div id="draw-hint" style="
display:none;
position:absolute;
top:12px;
left:50%;
transform:translateX(-50%);
z-index:500;
background:rgba(15,17,23,0.9);
border:1px solid var(--accent2);
color:var(--accent2);
border-radius:8px;
padding:6px 16px;
font-size:12px;
font-family:'Space Mono',monospace;
pointer-events:none;
">Press <strong>ESC</strong> to cancel</div>
</div>
</div><!-- /app -->
<!-- ═══════════════════════ STATS BAR ═══════════════════════ -->
<footer id="stats-bar">
<div class="stat-item">
<span class="stat-label">POINTS</span>
<span class="stat-val" id="stat-points">0</span>
</div>
<div class="stat-item">
<span class="stat-label">ROADS</span>
<span class="stat-val" id="stat-roads">0</span>
</div>
<div class="stat-item">
<span class="stat-label">PARCELS</span>
<span class="stat-val" id="stat-parcels">0</span>
</div>
<span style="margin-left:auto;color:var(--text-muted)">© WebGIS · OpenStreetMap</span>
</footer>
<!-- ═══════════════════════ MODAL ═══════════════════════ -->
<div id="modal-overlay">
<div id="modal"><!-- dynamically filled --></div>
</div>
<!-- ═══════════════════════ TOAST ═══════════════════════ -->
<div id="toast-container"></div>
<!-- ─── Leaflet JS ─── -->
<script src="https://unpkg.com/leaflet@1.9.4/dist/leaflet.js"></script>
<!-- Leaflet Draw -->
<script src="https://cdnjs.cloudflare.com/ajax/libs/leaflet.draw/1.0.4/leaflet.draw.js"></script>
<!-- Leaflet Geometry Util (for geodesic area calculation) -->
<script src="https://cdn.jsdelivr.net/npm/leaflet-geometryutil@0.10.3/src/leaflet.geometryutil.js"></script>
<!-- App JS -->
<script src="assets/js/app.js"></script>
</body>
</html>