haepada commited on
Commit
a4c78d2
·
verified ·
1 Parent(s): 542130b

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +156 -3
app.py CHANGED
@@ -400,9 +400,13 @@ def create_pwa_files():
400
  "description": "현대 도시 속 디지털 의례 공간",
401
  "start_url": "/",
402
  "display": "standalone",
403
- "background_color": "#ffffff",
404
- "theme_color": "#000000",
405
  "orientation": "portrait",
 
 
 
 
406
  "icons": [
407
  {
408
  "src": "/static/icons/icon-72x72.png",
@@ -452,6 +456,14 @@ def create_pwa_files():
452
  "type": "image/png",
453
  "purpose": "any maskable"
454
  }
 
 
 
 
 
 
 
 
455
  ]
456
  }
457
  with open(manifest_path, 'w', encoding='utf-8') as f:
@@ -532,7 +544,21 @@ self.addEventListener('fetch', event => {
532
  <meta name="apple-mobile-web-app-capable" content="yes">
533
  <meta name="apple-mobile-web-app-status-bar-style" content="black-translucent">
534
  <meta name="apple-mobile-web-app-title" content="디지털 굿판">
535
- <link rel="apple-touch-icon" href="/static/icons/icon-152x152.png">
 
 
 
 
 
 
 
 
 
 
 
 
 
 
536
  <style>
537
  /* iOS 상태바 영역 보호 */
538
  body {
@@ -552,15 +578,142 @@ self.addEventListener('fetch', event => {
552
  #gradio-app {
553
  background: #0b0f19 !important;
554
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
555
  </style>
556
  <script>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
557
  // 페이지 로드 시 상단으로 스크롤
558
  window.addEventListener('load', function() {
559
  setTimeout(() => {
560
  window.scrollTo(0, 0);
561
  }, 100);
562
  });
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
563
 
 
 
 
 
 
 
 
 
 
 
 
 
564
  // 화면 꺼짐 방지
565
  async function preventSleep() {
566
  try {
 
400
  "description": "현대 도시 속 디지털 의례 공간",
401
  "start_url": "/",
402
  "display": "standalone",
403
+ "background_color": "#0b0f19",
404
+ "theme_color": "#0b0f19",
405
  "orientation": "portrait",
406
+ "categories": ["art", "entertainment"],
407
+ "lang": "ko",
408
+ "dir": "ltr",
409
+ "prefer_related_applications": false,
410
  "icons": [
411
  {
412
  "src": "/static/icons/icon-72x72.png",
 
456
  "type": "image/png",
457
  "purpose": "any maskable"
458
  }
459
+ ],
460
+ "screenshots": [
461
+ {
462
+ "src": "/static/screenshots/screenshot1.png",
463
+ "sizes": "1280x720",
464
+ "type": "image/png",
465
+ "label": "홈 화면"
466
+ }
467
  ]
468
  }
469
  with open(manifest_path, 'w', encoding='utf-8') as f:
 
544
  <meta name="apple-mobile-web-app-capable" content="yes">
545
  <meta name="apple-mobile-web-app-status-bar-style" content="black-translucent">
546
  <meta name="apple-mobile-web-app-title" content="디지털 굿판">
547
+ <meta name="description" content="현대 도시 속 디지털 의례 공간">
548
+
549
+ <!-- iOS에서의 앱 아이콘 -->
550
+ <link rel="apple-touch-icon" href="/static/icons/icon-192x192.png">
551
+ <link rel="apple-touch-icon" sizes="152x152" href="/static/icons/icon-152x152.png">
552
+ <link rel="apple-touch-icon" sizes="180x180" href="/static/icons/icon-180x180.png">
553
+ <link rel="apple-touch-icon" sizes="167x167" href="/static/icons/icon-167x167.png">
554
+
555
+ <!-- iOS 스플래시 스크린 -->
556
+ <link rel="apple-touch-startup-image" href="/static/splash/apple-splash-2048-2732.png" media="(device-width: 1024px) and (device-height: 1366px) and (-webkit-device-pixel-ratio: 2)">
557
+ <link rel="apple-touch-startup-image" href="/static/splash/apple-splash-1668-2388.png" media="(device-width: 834px) and (device-height: 1194px) and (-webkit-device-pixel-ratio: 2)">
558
+ <link rel="apple-touch-startup-image" href="/static/splash/apple-splash-1536-2048.png" media="(device-width: 768px) and (device-height: 1024px) and (-webkit-device-pixel-ratio: 2)">
559
+ <link rel="apple-touch-startup-image" href="/static/splash/apple-splash-1125-2436.png" media="(device-width: 375px) and (device-height: 812px) and (-webkit-device-pixel-ratio: 3)">
560
+ <link rel="apple-touch-startup-image" href="/static/splash/apple-splash-828-1792.png" media="(device-width: 414px) and (device-height: 896px) and (-webkit-device-pixel-ratio: 2)">
561
+
562
  <style>
563
  /* iOS 상태바 영역 보호 */
564
  body {
 
578
  #gradio-app {
579
  background: #0b0f19 !important;
580
  }
581
+ .install-prompt {
582
+ position: fixed;
583
+ bottom: 20px;
584
+ left: 50%;
585
+ transform: translateX(-50%);
586
+ background: #2a2f3e;
587
+ color: white;
588
+ padding: 15px 20px;
589
+ border-radius: 12px;
590
+ box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1);
591
+ display: none;
592
+ z-index: 1000;
593
+ width: 90%;
594
+ max-width: 400px;
595
+ text-align: center;
596
+ }
597
+
598
+ .install-button {
599
+ background: #4a90e2;
600
+ color: white;
601
+ border: none;
602
+ padding: 10px 20px;
603
+ border-radius: 6px;
604
+ margin-top: 10px;
605
+ cursor: pointer;
606
+ font-weight: bold;
607
+ }
608
+
609
+ .close-prompt {
610
+ position: absolute;
611
+ top: 5px;
612
+ right: 10px;
613
+ background: none;
614
+ border: none;
615
+ color: white;
616
+ font-size: 20px;
617
+ cursor: pointer;
618
+ }
619
  </style>
620
  <script>
621
+ let deferredPrompt;
622
+
623
+ window.addEventListener('beforeinstallprompt', (e) => {
624
+ e.preventDefault();
625
+ deferredPrompt = e;
626
+ showInstallPrompt();
627
+ });
628
+
629
+ function showInstallPrompt() {
630
+ const prompt = document.createElement('div');
631
+ prompt.className = 'install-prompt';
632
+ prompt.innerHTML = `
633
+ <button class="close-prompt">&times;</button>
634
+ <p>디지털 굿판을 앱으로 설치하여 더 나은 경험을 누려보세요!</p>
635
+ <button class="install-button">앱 설치하기</button>
636
+ `;
637
+ document.body.appendChild(prompt);
638
+
639
+ // 설치 프롬프트 표시
640
+ setTimeout(() => {
641
+ prompt.style.display = 'block';
642
+ }, 2000);
643
+
644
+ // 닫기 버튼
645
+ prompt.querySelector('.close-prompt').addEventListener('click', () => {
646
+ prompt.remove();
647
+ });
648
+
649
+ // 설치 버튼
650
+ prompt.querySelector('.install-button').addEventListener('click', async () => {
651
+ if (deferredPrompt) {
652
+ deferredPrompt.prompt();
653
+ const { outcome } = await deferredPrompt.userChoice;
654
+ if (outcome === 'accepted') {
655
+ console.log('사용자가 앱 설치를 수락했습니다');
656
+ }
657
+ deferredPrompt = null;
658
+ prompt.remove();
659
+ }
660
+ });
661
+ }
662
+
663
+ // iOS Safari에서 설치 안내
664
+ if (navigator.standalone === false && navigator.userAgent.match(/Safari/i)) {
665
+ setTimeout(() => {
666
+ const iosPrompt = document.createElement('div');
667
+ iosPrompt.className = 'install-prompt';
668
+ iosPrompt.innerHTML = `
669
+ <button class="close-prompt">&times;</button>
670
+ <p>iOS에서 설치하기:<br>
671
+ 1. 공유 버튼을 탭하세요 📤<br>
672
+ 2. "홈 화면에 추가"를 선택하세요 ➕</p>
673
+ `;
674
+ document.body.appendChild(iosPrompt);
675
+ iosPrompt.style.display = 'block';
676
+
677
+ iosPrompt.querySelector('.close-prompt').addEventListener('click', () => {
678
+ iosPrompt.remove();
679
+ });
680
+ }, 2000);
681
+ }
682
  // 페이지 로드 시 상단으로 스크롤
683
  window.addEventListener('load', function() {
684
  setTimeout(() => {
685
  window.scrollTo(0, 0);
686
  }, 100);
687
  });
688
+ async function preventSleep() {
689
+ try {
690
+ if ('wakeLock' in navigator) {
691
+ const wakeLock = await navigator.wakeLock.request('screen');
692
+ console.log('화면 켜짐 유지 활성화');
693
+
694
+ document.addEventListener('visibilitychange', async () => {
695
+ if (document.visibilityState === 'visible') {
696
+ await preventSleep();
697
+ }
698
+ });
699
+ }
700
+ } catch (err) {
701
+ console.log('화면 켜짐 유지 실패:', err);
702
+ }
703
+ }
704
 
705
+ if ('serviceWorker' in navigator) {
706
+ window.addEventListener('load', async () => {
707
+ try {
708
+ const registration = await navigator.serviceWorker.register('/static/service-worker.js');
709
+ console.log('ServiceWorker 등록 성공:', registration.scope);
710
+ await preventSleep();
711
+ } catch (err) {
712
+ console.log('ServiceWorker 등록 실패:', err);
713
+ }
714
+ });
715
+ }
716
+
717
  // 화면 꺼짐 방지
718
  async function preventSleep() {
719
  try {