stat2025 commited on
Commit
1ac9943
·
verified ·
1 Parent(s): be0199f

Upload 2 files

Browse files
Files changed (2) hide show
  1. index.html +415 -0
  2. script.js +177 -0
index.html ADDED
@@ -0,0 +1,415 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <!doctype html>
2
+ <html lang="ar" dir="rtl">
3
+ <head>
4
+ <meta charset="utf-8" />
5
+ <meta name="viewport" content="width=device-width, initial-scale=1" />
6
+ <title>بحث الخرائط</title>
7
+ <style>
8
+ :root{
9
+ /* Palette */
10
+ --primary:#4137A8;
11
+ --secondary:#1CADE4;
12
+ --success:#00B050;
13
+ --warn:#FFC000;
14
+ --muted:#5C6E88;
15
+
16
+ --bg:#F6F8FC;
17
+ --card:#FFFFFF;
18
+ --text:#0B1324;
19
+ --line:#E7ECF5;
20
+
21
+ --radius:22px;
22
+ --shadow: 0 18px 55px rgba(51,91,116,.12);
23
+ --shadow2: 0 10px 26px rgba(51,91,116,.10);
24
+ --focus: 0 0 0 6px rgba(28,173,228,.18);
25
+
26
+ --maxw: 980px;
27
+ }
28
+
29
+ *{box-sizing:border-box}
30
+ html,body{height:100%}
31
+ body{
32
+ margin:0;
33
+ font-family: system-ui, -apple-system, "Segoe UI", Tahoma, Arial, sans-serif;
34
+ color:var(--text);
35
+ background:
36
+ radial-gradient(900px 520px at 18% 10%, rgba(65,55,168,.12), rgba(65,55,168,0) 60%),
37
+ radial-gradient(900px 520px at 82% 12%, rgba(28,173,228,.14), rgba(28,173,228,0) 60%),
38
+ radial-gradient(900px 520px at 50% 110%, rgba(0,176,80,.10), rgba(0,176,80,0) 55%),
39
+ linear-gradient(180deg, #ffffff, var(--bg));
40
+ display:flex;
41
+ flex-direction:column;
42
+ overflow-x:hidden;
43
+ }
44
+
45
+ .wrap{
46
+ width:min(var(--maxw), 92vw);
47
+ margin: 0 auto;
48
+ padding: 26px 0 92px;
49
+ flex:1;
50
+ display:flex;
51
+ flex-direction:column;
52
+ gap: 14px;
53
+ }
54
+
55
+ /* Header */
56
+ header{
57
+ display:flex;
58
+ align-items:center;
59
+ justify-content:space-between;
60
+ gap:12px;
61
+ flex-wrap:wrap;
62
+ padding-top: 4px;
63
+ }
64
+ .title{
65
+ display:flex;
66
+ align-items:center;
67
+ gap:12px;
68
+ }
69
+ .logo{
70
+ width:44px;height:44px;border-radius:16px;
71
+ background:
72
+ radial-gradient(16px 16px at 28% 26%, rgba(255,255,255,.9), rgba(255,255,255,0) 60%),
73
+ linear-gradient(135deg, var(--primary), var(--secondary));
74
+ box-shadow: var(--shadow2);
75
+ flex: 0 0 auto;
76
+ }
77
+ h1{
78
+ margin:0;
79
+ font-size: 18px;
80
+ letter-spacing:.2px;
81
+ color: var(--primary);
82
+ font-weight: 850;
83
+ line-height:1;
84
+ }
85
+ .chip{
86
+ display:inline-flex;
87
+ align-items:center;
88
+ gap:8px;
89
+ padding: 10px 12px;
90
+ border-radius:999px;
91
+ border:1px solid rgba(28,173,228,.22);
92
+ background: linear-gradient(180deg, #ffffff, rgba(28,173,228,.08));
93
+ color: var(--muted);
94
+ font-size: 12.5px;
95
+ box-shadow: 0 10px 24px rgba(51,91,116,.10);
96
+ white-space:nowrap;
97
+ }
98
+ .chip b{ color: var(--primary); font-weight: 900; }
99
+
100
+ /* Main card */
101
+ .card{
102
+ border-radius: var(--radius);
103
+ background: rgba(255,255,255,.92);
104
+ border: 1px solid var(--line);
105
+ box-shadow: var(--shadow);
106
+ overflow:hidden;
107
+ position:relative;
108
+ }
109
+ .card::before{
110
+ content:"";
111
+ position:absolute; inset:-2px;
112
+ background:
113
+ radial-gradient(420px 260px at 15% 0%, rgba(65,55,168,.10), rgba(65,55,168,0) 60%),
114
+ radial-gradient(460px 280px at 85% 8%, rgba(28,173,228,.10), rgba(28,173,228,0) 62%);
115
+ pointer-events:none;
116
+ }
117
+ .inner{
118
+ position:relative;
119
+ padding: 18px;
120
+ }
121
+
122
+ /* Centered panel */
123
+ .panel{
124
+ width:min(860px, 100%);
125
+ margin: 0 auto;
126
+ display:grid;
127
+ gap: 12px;
128
+ padding: 6px 0 2px;
129
+ }
130
+
131
+ /* Field + button group */
132
+ .row{
133
+ display:grid;
134
+ grid-template-columns: 1fr auto;
135
+ gap: 12px;
136
+ align-items:stretch;
137
+ justify-items:center;
138
+ }
139
+ @media(max-width: 720px){
140
+ .row{ grid-template-columns: 1fr; }
141
+ .chip{ display:none; }
142
+ }
143
+
144
+ .field{
145
+ width:100%;
146
+ background:#fff;
147
+ border:1px solid var(--line);
148
+ border-radius: 18px;
149
+ box-shadow: 0 10px 26px rgba(51,91,116,.10);
150
+ padding: 14px;
151
+ display:flex;
152
+ align-items:center;
153
+ gap: 10px;
154
+ justify-content:center;
155
+ }
156
+ .fieldIcon{
157
+ width:38px;height:38px;border-radius:14px;
158
+ display:grid;place-items:center;
159
+ background: linear-gradient(135deg, rgba(65,55,168,.10), rgba(28,173,228,.10));
160
+ border: 1px solid rgba(65,55,168,.12);
161
+ color: var(--primary);
162
+ font-size: 18px;
163
+ flex:0 0 auto;
164
+ }
165
+ input{
166
+ width:100%;
167
+ border:none;
168
+ outline:none;
169
+ font-size: 16px;
170
+ padding: 0;
171
+ background:transparent;
172
+ text-align:center;
173
+ color: var(--text);
174
+ }
175
+ input::placeholder{ color: rgba(92,110,136,.55); }
176
+
177
+ .btnGroup{
178
+ display:grid;
179
+ grid-template-columns: 1fr 1fr;
180
+ gap: 10px;
181
+ width: 320px;
182
+ justify-self:stretch;
183
+ }
184
+ @media(max-width: 720px){
185
+ .btnGroup{ width:100%; }
186
+ }
187
+
188
+ .btn{
189
+ height: 66px;
190
+ border-radius: 18px;
191
+ border:1px solid transparent;
192
+ cursor:pointer;
193
+ font-size: 15px;
194
+ font-weight: 900;
195
+ display:flex;
196
+ align-items:center;
197
+ justify-content:center;
198
+ gap:10px;
199
+ box-shadow: 0 10px 26px rgba(51,91,116,.10);
200
+ transition: transform .06s ease, opacity .2s ease, box-shadow .2s ease;
201
+ user-select:none;
202
+ }
203
+ .btn:active{ transform: translateY(1px); }
204
+ .btn.primary{
205
+ color:#fff;
206
+ background: linear-gradient(135deg, var(--primary), var(--secondary));
207
+ }
208
+ .btn.secondary{
209
+ background:#fff;
210
+ border-color: var(--line);
211
+ color: var(--muted);
212
+ }
213
+ .btn:hover{ opacity:.94; }
214
+
215
+ .meta{
216
+ display:flex;
217
+ align-items:center;
218
+ justify-content:space-between;
219
+ gap: 10px;
220
+ flex-wrap:wrap;
221
+ color: var(--muted);
222
+ font-size: 13px;
223
+ padding: 0 4px;
224
+ }
225
+ .pill{
226
+ display:inline-flex;
227
+ align-items:center;
228
+ gap:8px;
229
+ padding: 8px 10px;
230
+ border-radius: 999px;
231
+ border: 1px solid rgba(0,176,80,.18);
232
+ background: linear-gradient(180deg, #ffffff, rgba(0,176,80,.08));
233
+ color: #0a5a32;
234
+ font-weight: 900;
235
+ }
236
+
237
+ /* Results */
238
+ .results{
239
+ margin-top: 8px;
240
+ display:grid;
241
+ gap: 10px;
242
+ }
243
+
244
+ .result{
245
+ background:#fff;
246
+ border:1px solid var(--line);
247
+ border-radius: 18px;
248
+ padding: 14px;
249
+ box-shadow: 0 10px 26px rgba(51,91,116,.10);
250
+ display:flex;
251
+ align-items:center;
252
+ justify-content:space-between;
253
+ gap: 12px;
254
+ }
255
+ .name{
256
+ font-weight: 950;
257
+ font-size: 15.5px;
258
+ line-height:1.7;
259
+ white-space:nowrap;
260
+ overflow:hidden;
261
+ text-overflow:ellipsis;
262
+ max-width: 64ch;
263
+ }
264
+ @media(max-width: 720px){
265
+ .name{ max-width: 42ch; }
266
+ .result{ flex-direction: column; align-items: stretch; }
267
+ .actions{ justify-content: stretch; }
268
+ .openBtn,.copyBtn{ width: 100%; justify-content:center; }
269
+ }
270
+
271
+ .actions{
272
+ display:flex;
273
+ gap: 8px;
274
+ flex-wrap:wrap;
275
+ justify-content:flex-end;
276
+ }
277
+
278
+ .openBtn, .copyBtn{
279
+ border-radius: 14px;
280
+ padding: 10px 12px;
281
+ border: 1px solid transparent;
282
+ font-size: 13.5px;
283
+ font-weight: 950;
284
+ cursor:pointer;
285
+ display:inline-flex;
286
+ align-items:center;
287
+ gap: 8px;
288
+ white-space:nowrap;
289
+ transition: transform .06s ease, opacity .2s ease;
290
+ user-select:none;
291
+ text-decoration:none;
292
+ }
293
+ .openBtn{
294
+ color:#fff;
295
+ background: linear-gradient(135deg, var(--primary), var(--secondary));
296
+ box-shadow: 0 10px 22px rgba(65,55,168,.18);
297
+ }
298
+ .copyBtn{
299
+ color:#0b1324;
300
+ background: linear-gradient(135deg, #ffffff, rgba(0,176,80,.12));
301
+ border-color: rgba(0,176,80,.22);
302
+ }
303
+ .openBtn:active,.copyBtn:active{ transform: translateY(1px); }
304
+ .openBtn:hover,.copyBtn:hover{ opacity:.93; }
305
+
306
+ .empty{
307
+ text-align:center;
308
+ color: var(--muted);
309
+ background:#fff;
310
+ border: 1px dashed rgba(92,110,136,.35);
311
+ border-radius: 18px;
312
+ padding: 18px 12px;
313
+ }
314
+
315
+ mark{
316
+ background: rgba(28,173,228,.12);
317
+ border: 1px solid rgba(28,173,228,.16);
318
+ color: var(--primary);
319
+ padding: 1px 6px;
320
+ border-radius: 999px;
321
+ }
322
+
323
+ /* Focus ring on the field wrapper when input focused */
324
+ .field:focus-within{
325
+ border-color: rgba(28,173,228,.45);
326
+ box-shadow: var(--focus), 0 10px 26px rgba(51,91,116,.10);
327
+ }
328
+
329
+ /* Toast */
330
+ .toast{
331
+ position:fixed;
332
+ left:50%;
333
+ bottom: 78px;
334
+ transform: translateX(-50%) translateY(14px);
335
+ background: rgba(51,91,116,.92);
336
+ color:#fff;
337
+ padding: 10px 14px;
338
+ border-radius: 999px;
339
+ box-shadow: 0 18px 45px rgba(0,0,0,.14);
340
+ opacity:0;
341
+ pointer-events:none;
342
+ transition: opacity .22s ease, transform .22s ease;
343
+ font-size: 13px;
344
+ display:flex;
345
+ align-items:center;
346
+ gap:8px;
347
+ z-index: 50;
348
+ }
349
+ .toast.show{
350
+ opacity:1;
351
+ transform: translateX(-50%) translateY(0);
352
+ }
353
+ .toast .dot{
354
+ width:9px;height:9px;border-radius:50%;
355
+ background: var(--warn);
356
+ box-shadow: 0 0 0 3px rgba(255,192,0,.22);
357
+ }
358
+
359
+ footer{
360
+ position:fixed;
361
+ left:0; right:0; bottom:0;
362
+ text-align:center;
363
+ padding: 10px 14px;
364
+ background: rgba(255,255,255,.82);
365
+ border-top: 1px solid rgba(231,236,245,.95);
366
+ backdrop-filter: blur(10px);
367
+ color: var(--muted);
368
+ font-size: 12.5px;
369
+ z-index: 40;
370
+ }
371
+ footer b{ color: var(--primary); font-weight: 900; }
372
+ </style>
373
+ </head>
374
+ <body>
375
+ <div class="wrap">
376
+ <header>
377
+ <div class="title">
378
+ <div class="logo" aria-hidden="true"></div>
379
+ <h1>بحث الخرائط</h1>
380
+ </div>
381
+ <div class="chip" id="totalChip">إجمالي: <b>—</b></div>
382
+ </header>
383
+
384
+ <section class="card" aria-label="search">
385
+ <div class="inner">
386
+ <div class="panel">
387
+ <div class="row">
388
+ <div class="field" aria-label="search field">
389
+ <div class="fieldIcon" aria-hidden="true">🔎</div>
390
+ <input id="q" type="text" inputmode="search" autocomplete="off" placeholder="اكتب الاسم" />
391
+ </div>
392
+
393
+ <div class="btnGroup" aria-label="button group">
394
+ <button id="btnSearch" class="btn primary" type="button">بحث</button>
395
+ <button id="btnClear" class="btn secondary" type="button">مسح</button>
396
+ </div>
397
+ </div>
398
+
399
+ <div class="meta">
400
+ <div class="pill" id="countPill">النتائج: 0</div>
401
+ <div></div>
402
+ </div>
403
+
404
+ <div class="results" id="results" aria-live="polite"></div>
405
+ </div>
406
+ </div>
407
+ </section>
408
+ </div>
409
+
410
+ <div class="toast" id="toast"><span class="dot" aria-hidden="true"></span><span id="toastText">تم نسخ الرابط</span></div>
411
+ <footer>تصميم وإعداد الدعم الفني <b>نوف الناصر</b></footer>
412
+
413
+ <script src="./script.js"></script>
414
+ </body>
415
+ </html>
script.js ADDED
@@ -0,0 +1,177 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const DATA = [{"name": "أروى سعيد بن عبدالله القحطاني", "url": "https://stat2025-map.static.hf.space/BCS/37.html"}, {"name": "أسماء درويش سالم الدوسري", "url": "https://stat2025-map.static.hf.space/BCS/15.html"}, {"name": "أمل احمد محمد مجرشي", "url": "https://stat2025-map.static.hf.space/BCS/28.html"}, {"name": "أمل بنت علي بن علي السماعيل", "url": "https://stat2025-map.static.hf.space/BCS/07.html"}, {"name": "أمل جعفر بن علي آل حماد", "url": "https://stat2025-map.static.hf.space/BCS/30.html"}, {"name": "أمل صالح بن احمد آل مزعل", "url": "https://stat2025-map.static.hf.space/BCS/47.html"}, {"name": "ابرار بنت يوسف بن علي آل حماد", "url": "https://stat2025-map.static.hf.space/BCS/44.html"}, {"name": "احلام صالح معيوض العصيمي", "url": "https://stat2025-map.static.hf.space/BCS/16.html"}, {"name": "اسعد بن ماجد بن احمد الهاشم", "url": "https://stat2025-map.static.hf.space/BCS/46.html"}, {"name": "اسماء بنت محمد بن حسين العدساني", "url": "https://stat2025-map.static.hf.space/BCS/09.html"}, {"name": "ايمان عبدالعزيز بن صالح الصالح", "url": "https://stat2025-map.static.hf.space/BCS/40.html"}, {"name": "باسمه احمد بن محمد القرني", "url": "https://stat2025-map.static.hf.space/BCS/21.html"}, {"name": "باقر عبدالله بن هاشم الهاشم", "url": "https://stat2025-map.static.hf.space/BCS/11.html"}, {"name": "تركي وحيد بن عيسى المحيفيظ", "url": "https://stat2025-map.static.hf.space/BCS/01.html"}, {"name": "حسن عادل بن حسين الوصيبعي", "url": "https://stat2025-map.static.hf.space/BCS/03.html"}, {"name": "زكي بن عيسى بن عبدالله القفاص", "url": "https://stat2025-map.static.hf.space/BCS/51.html"}, {"name": "زهراء بنت عايش بن علي الصاهود", "url": "https://stat2025-map.static.hf.space/BCS/33.html"}, {"name": "ساره خالد سليمان المحيسن", "url": "https://stat2025-map.static.hf.space/BCS/35.html"}, {"name": "ساره راشد عبدالله المديني", "url": "https://stat2025-map.static.hf.space/BCS/34.html"}, {"name": "ساره عبدالحميد بن حسين البوحمد", "url": "https://stat2025-map.static.hf.space/BCS/12.html"}, {"name": "سميه رياض بن عبدالله البراك", "url": "https://stat2025-map.static.hf.space/BCS/39.html"}, {"name": "سميه سامى بن احمد النعيم", "url": "https://stat2025-map.static.hf.space/BCS/05.html"}, {"name": "شريفه ابراهيم بن عبدالله العقيل", "url": "https://stat2025-map.static.hf.space/BCS/41.html"}, {"name": "شيماء عبدالرحمن بن دحباش سودي", "url": "https://stat2025-map.static.hf.space/BCS/19.html"}, {"name": "صالح دلي الشمري", "url": "https://stat2025-map.static.hf.space/BCS/48.html"}, {"name": "طيبه فالح بن عبدالله الرويشد", "url": "https://stat2025-map.static.hf.space/BCS/31.html"}, {"name": "عائشه سليمان بن نايف الحربي", "url": "https://stat2025-map.static.hf.space/BCS/13.html"}, {"name": "عبدالله خلف الجدعان", "url": "https://stat2025-map.static.hf.space/BCS/49.html"}, {"name": "عقيله محمدحسين بن علي الجباره", "url": "https://stat2025-map.static.hf.space/BCS/06.html"}, {"name": "علياء فيصل بن محمد الكثيري", "url": "https://stat2025-map.static.hf.space/BCS/36.html"}, {"name": "غدير عبدالعزيز بن سعد القاسم", "url": "https://stat2025-map.static.hf.space/BCS/38.html"}, {"name": "فارس ثاني الشمري", "url": "https://stat2025-map.static.hf.space/BCS/50.html"}, {"name": "فاطمه حسين بن ابراهيم القرقوش", "url": "https://stat2025-map.static.hf.space/BCS/45.html"}, {"name": "فايزه محمد مسعود الحازمي", "url": "https://stat2025-map.static.hf.space/BCS/32.html"}, {"name": "فيصل تركي فيصل القحطاني", "url": "https://stat2025-map.static.hf.space/BCS/18.html"}, {"name": "لطيفه صالح بن عبدالرحمن العبد القادر", "url": "https://stat2025-map.static.hf.space/BCS/25.html"}, {"name": "لطيفه علي بن حسين النعيم", "url": "https://stat2025-map.static.hf.space/BCS/29.html"}, {"name": "لين أحمد بن عبدالعزيز القصير", "url": "https://stat2025-map.static.hf.space/BCS/22.html"}, {"name": "محمد دبيان بن مفرج الشمري", "url": "https://stat2025-map.static.hf.space/BCS/27.html"}, {"name": "مرتضى عبدالجليل بن عيسى الحكيم", "url": "https://stat2025-map.static.hf.space/BCS/43.html"}, {"name": "مصطفى احمد بن جمعه الرمضان", "url": "https://stat2025-map.static.hf.space/BCS/10.html"}, {"name": "ممدوح مشعل ضيف الله الصخري", "url": "https://stat2025-map.static.hf.space/BCS/26.html"}, {"name": "منيره سعد بن احمد الجديدي", "url": "https://stat2025-map.static.hf.space/BCS/04.html"}, {"name": "منيره سعود بن عبدالعزيز القوز", "url": "https://stat2025-map.static.hf.space/BCS/42.html"}, {"name": "نبأ عادل بن عبدالكريم آل رضوان", "url": "https://stat2025-map.static.hf.space/BCS/23.html"}, {"name": "نجود عبدالعزيز بن عقيل العمري", "url": "https://stat2025-map.static.hf.space/BCS/20.html"}, {"name": "نوره عبدالله بن زهير الرزقي", "url": "https://stat2025-map.static.hf.space/BCS/24.html"}, {"name": "نوره عبدالله بن مانع الخالدي", "url": "https://stat2025-map.static.hf.space/BCS/02.html"}, {"name": "نوف صالح بن محمد السميح", "url": "https://stat2025-map.static.hf.space/BCS/08.html"}, {"name": "نيللي حسين عبدالله الجعص", "url": "https://stat2025-map.static.hf.space/BCS/17.html"}, {"name": "وضحه خالد بن مشرف الخالدي", "url": "https://stat2025-map.static.hf.space/BCS/14.html"}];
2
+
3
+ function normalizeArabic(s) {
4
+ if (!s) return "";
5
+ return String(s)
6
+ .trim()
7
+ .toLowerCase()
8
+ .replace(/[\u064B-\u065F\u0670\u06D6-\u06ED]/g, "")
9
+ .replace(/\u0640/g, "")
10
+ .replace(/[إأآٱ]/g, "ا")
11
+ .replace(/ى/g, "ي")
12
+ .replace(/ة/g, "ه")
13
+ .replace(/^ال\s+/g, "")
14
+ .replace(/\s+/g, " ");
15
+ }
16
+
17
+ function escapeHtml(str) {
18
+ return String(str)
19
+ .replaceAll("&", "&amp;")
20
+ .replaceAll("<", "&lt;")
21
+ .replaceAll(">", "&gt;")
22
+ .replaceAll('"', "&quot;")
23
+ .replaceAll("'", "&#039;");
24
+ }
25
+
26
+ function highlightMatch(name, rawQuery) {
27
+ if (!rawQuery) return escapeHtml(name);
28
+ const tokens = rawQuery.trim().split(/\s+/).filter(Boolean);
29
+ if (!tokens.length) return escapeHtml(name);
30
+
31
+ const t = tokens[0];
32
+ const idx = name.indexOf(t);
33
+ if (idx === -1) return escapeHtml(name);
34
+
35
+ const before = escapeHtml(name.slice(0, idx));
36
+ const mid = escapeHtml(name.slice(idx, idx + t.length));
37
+ const after = escapeHtml(name.slice(idx + t.length));
38
+ return `${before}<mark>${mid}</mark>${after}`;
39
+ }
40
+
41
+ const elQ = document.getElementById("q");
42
+ const elResults = document.getElementById("results");
43
+ const elCount = document.getElementById("countPill");
44
+ const elTotal = document.getElementById("totalChip");
45
+ const toast = document.getElementById("toast");
46
+ const toastText = document.getElementById("toastText");
47
+
48
+ elTotal.innerHTML = `إجمالي: <b>${DATA.length}</b>`;
49
+
50
+ function showToast(msg = "تم نسخ الرابط") {
51
+ toastText.textContent = msg;
52
+ toast.classList.add("show");
53
+ clearTimeout(window.__toastT);
54
+ window.__toastT = setTimeout(() => toast.classList.remove("show"), 1200);
55
+ }
56
+
57
+ async function copyLink(url) {
58
+ try {
59
+ await navigator.clipboard.writeText(url);
60
+ showToast();
61
+ } catch (e) {
62
+ const ta = document.createElement("textarea");
63
+ ta.value = url;
64
+ document.body.appendChild(ta);
65
+ ta.select();
66
+ document.execCommand("copy");
67
+ document.body.removeChild(ta);
68
+ showToast();
69
+ }
70
+ }
71
+
72
+ function renderResults(list, rawQuery) {
73
+ elResults.innerHTML = "";
74
+
75
+ if (!list.length) {
76
+ elCount.textContent = "النتائج: 0";
77
+ elResults.innerHTML = `<div class="empty">لا توجد نتائج</div>`;
78
+ return;
79
+ }
80
+
81
+ elCount.textContent = `النتائج: ${list.length}`;
82
+ const frag = document.createDocumentFragment();
83
+
84
+ list.forEach(item => {
85
+ const row = document.createElement("div");
86
+ row.className = "result";
87
+
88
+ const nm = document.createElement("div");
89
+ nm.className = "name";
90
+ nm.innerHTML = highlightMatch(item.name, rawQuery);
91
+
92
+ const actions = document.createElement("div");
93
+ actions.className = "actions";
94
+
95
+ const open = document.createElement("a");
96
+ open.className = "openBtn";
97
+ open.href = item.url;
98
+ open.target = "_blank";
99
+ open.rel = "noopener";
100
+ open.innerHTML = `فتح <span aria-hidden="true">↗</span>`;
101
+
102
+ const copy = document.createElement("button");
103
+ copy.className = "copyBtn";
104
+ copy.type = "button";
105
+ copy.innerHTML = `نسخ <span aria-hidden="true">⧉</span>`;
106
+ copy.addEventListener("click", () => copyLink(item.url));
107
+
108
+ actions.appendChild(open);
109
+ actions.appendChild(copy);
110
+
111
+ row.appendChild(nm);
112
+ row.appendChild(actions);
113
+
114
+ frag.appendChild(row);
115
+ });
116
+
117
+ elResults.appendChild(frag);
118
+ }
119
+
120
+ function doSearch() {
121
+ const raw = (elQ.value || "").trim();
122
+ const q = normalizeArabic(raw);
123
+
124
+ if (!q) {
125
+ elCount.textContent = "النتائج: 0";
126
+ elResults.innerHTML = "";
127
+ return;
128
+ }
129
+
130
+ const tokens = q.split(" ").filter(Boolean);
131
+
132
+ const matched = DATA.filter(d => {
133
+ const nameNorm = normalizeArabic(d.name);
134
+ return tokens.every(t => nameNorm.includes(t));
135
+ });
136
+
137
+ matched.sort((a, b) => {
138
+ const al = (a.name || "").length;
139
+ const bl = (b.name || "").length;
140
+ if (al !== bl) return al - bl;
141
+ return (a.name || "").localeCompare(b.name || "", "ar");
142
+ });
143
+
144
+ renderResults(matched, raw);
145
+ }
146
+
147
+ document.getElementById("btnSearch").addEventListener("click", doSearch);
148
+ document.getElementById("btnClear").addEventListener("click", () => {
149
+ elQ.value = "";
150
+ elQ.focus();
151
+ elResults.innerHTML = "";
152
+ elCount.textContent = "النتائج: 0";
153
+ });
154
+
155
+ let t = null;
156
+ elQ.addEventListener("input", () => {
157
+ clearTimeout(t);
158
+ t = setTimeout(doSearch, 140);
159
+ });
160
+
161
+ elQ.addEventListener("keydown", (e) => {
162
+ if (e.key === "Enter") doSearch();
163
+ });
164
+
165
+ // Persist last query (invisible)
166
+ try {
167
+ const last = localStorage.getItem("maps_last_query");
168
+ if (last) {
169
+ elQ.value = last;
170
+ doSearch();
171
+ }
172
+ elQ.addEventListener("input", () => {
173
+ localStorage.setItem("maps_last_query", elQ.value || "");
174
+ });
175
+ } catch(_){}
176
+
177
+ elCount.textContent = "النتائج: 0";