5353 <!-- End Preloader-->
5454
5555 <!--Floating button-->
56- < div id ="floating-button " class ="float ">
57- < div class ="control-center open ">
58- < div class ="audio-play ">
56+ < div id ="floating-button " class ="float ">
57+ < div class ="control-center open ">
58+ < div class ="audio-play ">
5959 < audio id ="page-audio " src ="music/a_thousand_years.mp3 " preload ="auto " loop > </ audio >
6060 < img id ="youtube-icon1 " src ="images/audio/play.png " alt ="Play audio " style ="width:40px;cursor:pointer; " />
61- </ div >
62- < ul class ="right-sidebar ">
63- <!--gallery-->
64- < li onclick ="scrollToElement('fh5co-gallery') " style ="background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAADAAAAAwCAYAAABXAvmHAAAABmJLR0QA/wD/AP+gvaeTAAADe0lEQVRoge2YTWgVVxiG35Mr1n+qopYkik1dFKRiJGgWLmqrLsSFPy3Y1G6soFkJdulWcFHBgAFRQcGFLgRr1W6kLvz/SdpNQQqtfyXG+oMuaheamMfFzMXPw0zuzOTcG5H7bu7MOe/3fe878805M1eqo4463m8ADUAHcBroBwYJg8E43ylgA9BQDfEtwO+BBFfCb8DHeTW64cRLuiZpxkguQk48ktTunLuTNSDRQHw7eyW1BhKWB72SljjnhrKQ0/pug0ZHvCS1Sfo6KznNQEcYLYWRuX6agUWBhBRFW/kAmDscMc3AzKBy8mOWOb4YLyiJSDNQCqtH9yQtlzRJ0gpJ/1Tg2/rNko7k2ieqsMZ/6eVfUSkgQcv6JK3hd79kXPfOrxXI8V3SYK0MtFc4z4KFmZlVaKG7cdtMAlYC9wq00ECS1rSdmKTxWsI553wt5TGLIi10QNISRUttu6SDBTVWDyl39RXQmcLvBIZG0GJZWih7VyTkGwQ2VYj5Fhh4Fw0MAB3e/EagD9iYwcQzYAswG5gOrANu1crAC7wNBNhM1E7Ev997818BL+P52yR8pACTgfPVNvACWOONbzXiyxgCtnm8VcDNJPGGMwE4Wy0D/wMrvbEfSH9Qh4DtHr/BHI8HThB9Njaa8XHAL9Uw8Ll3viPtSnnYkZBrInDOcP4C5pj5sbG5cAY8ATszigfoAcab2CnAxQTeXeATwxsDHAtuIKf4G8A0E/shcHUY/gNgvuGXgENBDAAO6Moh/gIw2cRPjQ1VwkNggVd3bwgDB3KIPwtMMLGzgD9yxD8GWk28A/aM1MCDjMVPA+NMXBPwZw7xZTwFFifoKBnOYB4DZzIUPQV8YGLmEK0wRfEcWObpaDLzfXkMfFOh2FFgjOHPI8M7fkYTX5i89tPT/6ob1kAJ6E0pchgoGe6nwP0A4sv41eTuNuM/ZjYQBzcDd7zk+3h7h/0M+Deg+H6gOc79EfCfmVuay0CcpIU3L11dgDNzi4AnAcVfAZri3A44buZ6bO28JpzvHmgnek0eCQaAv4GfgNXEdzaut8vjLktW946BqG2Oe+J3j7auVBAtFo1Eq0030SpkcRKzYIQoOJvoRawW2I9ZqkOaaAEuVVF4Dzl6vtCTTfTArVX0d1+rpEZJRa7WK0kPJd2XdF7Sz5IuO+dG/X+pOuqoo0Z4DePtUHAz1eX1AAAAAElFTkSuQmCC) "> </ li >
65- <!--chat-->
66- < li onclick ="scrollToElement('fh5co-testimonial') " style ="background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABgAAAAYCAYAAADgdz34AAAABmJLR0QA/wD/AP+gvaeTAAABKklEQVRIidWVq04DQRhGv900QUFFCVWgUYQ6PAgeAUVwSDwplocoCamsqKlE4ICQECDlAfAYoAoDHEQ7SdnO7lw6CE6yYi45384/kxnpv5NVDQJ1SXuSdiVtSGpOhl4kDSVdSOplWTYKSgVqwAnwjps3oA3UfOVN4NpDXOQKWHHJ68BDhNxwDyxVBZzPITeclclbwHeCgC9g03jzqYwDOU6VJ7mkfVvAdgK5YccWsGqZ2JC0HNA2rNkCsEwslszVNizM9ABPCTbYMLSt4LLkb2K4sQV0ZS9TDD1rL9BJUJ670ljGV8XjHPJPYKtybUADuI0MOPUqIOPr+hgYBcgHQO62/w5aBA6BPvAMvE6+In1g9uzHUpB38X1sAgM+gKOk4qmANrD+J/JQfgANB//YYXlyuAAAAABJRU5ErkJggg==) "> </ li >
67- </ ul >
68- <!--calendar-->
69- < div onclick ="scrollToElement('fh5co-event') " class ="option-btn open "> </ div >
70- < ul class ="left-sidebar ">
71- <!--countdown-->
72- < li onclick ="scrollToElement('fh5co-header') " style ="background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABgAAAAYCAYAAADgdz34AAAABmJLR0QA/wD/AP+gvaeTAAABG0lEQVRIidXVTS4EQRjG8SZ2IrEnETEcQmYsjLkCiUu4g1P42FpxhmGG2IvEcAcfG9Z+FtOS1qaramZ6wZPUpqve5//2k36rs+wvCLd+6yaldjaR8TmKm95iDcIhzrA4bmEHp3jCR74ecYKdwrm7PLoBllOMN9AfkX1ZPaxjBff5s4OY+RbeEsy/9YoWFrCP+VjnVeabaAYgjZRoLqvaLJypUi9m3gnlkACAdtGzPAd70VeMazcEaNYA2AoBlmoA/JiBudJmcPzRzLJsJgKo9jCc1mk1KHqWI7qOdJeifghwXgPgIriL7hTxXEXxWMXzBOZpV0UOaeUFqXox/MLShYbAvVRQF2tjmZdAbRwb/kje8/WAI2xPbPxv9AUiVMwGoTr9YAAAAABJRU5ErkJggg==) "> </ li >
73- <!--couple-->
74- < li onclick ="scrollToElement('fh5co-couple') " style ="background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAB4AAAAeCAYAAAA7MK6iAAAABmJLR0QA/wD/AP+gvaeTAAAB7UlEQVRIie2VPUiVURjH/+eqSSJN4tDWRRAH5xD8QDCwgqAWhwwSaarBwUGaHFwcBAchGqNNdDaKoKAkBEvUURAVRInw82Jx0Z/De64+Xu5773nv0CD3P533eZ//+T3nW6qoomstwAEPgXfAKnAA7AE/gWGgJsbXAIwCi8ARkAF+AS+AqlLQJmCB4voMDAL1xvfUFxin98WgLX5kIdoHbnvfK+AswJMBvgGPLbQGWAmEAgx7XzuQTeDLaSgHfpLA9Bu45X0/yoAC/AXSKUn9AfvuTNIXSb3OuUOgQ9LdAJ8kfZDUJenYf9dKGqiW1JyXuCbpq6RlSRuStiStO+f2TM6DQOiSpOfOuV1gStKIj3eKyx2ZJdqxrlRvwHzMNP4DlomOYx/m+AEdJm9H5mM8cBQCNvKA00AbcKOIp9GuswW3JgBnjO9toKfWVmrBdQnAVkkKvlBKUsbHY6ephNbKMaUkffftj0C6jD5uhiRhrtlcoAXY9jPwJrATq+5AT+eVNfbBZqLjdAq0JwTPBOQ7YM54Nu3PMR/8A9wrYH4UAwZ4VgSaBmYtFOi1CSlgxiTMA5PAhG9jcrfywFngJQGXT1x1VcBrosc8X/sm734BOERPX9AdXrBCoh3YI+mOogdiXdIn59xJWSOqqKL/qXMXI9MKbss7gAAAAABJRU5ErkJggg==) "> </ li >
75- </ ul >
76- </ div >
77- </ div >
61+ </ div >
62+ < ul class ="right-sidebar ">
63+ <!--gallery-->
64+ < li onclick ="scrollToElement('data') "
65+ style ="background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAADAAAAAwCAYAAABXAvmHAAAABmJLR0QA/wD/AP+gvaeTAAADe0lEQVRoge2YTWgVVxiG35Mr1n+qopYkik1dFKRiJGgWLmqrLsSFPy3Y1G6soFkJdulWcFHBgAFRQcGFLgRr1W6kLvz/SdpNQQqtfyXG+oMuaheamMfFzMXPw0zuzOTcG5H7bu7MOe/3fe878805M1eqo4463m8ADUAHcBroBwYJg8E43ylgA9BQDfEtwO+BBFfCb8DHeTW64cRLuiZpxkguQk48ktTunLuTNSDRQHw7eyW1BhKWB72SljjnhrKQ0/pug0ZHvCS1Sfo6KznNQEcYLYWRuX6agUWBhBRFW/kAmDscMc3AzKBy8mOWOb4YLyiJSDNQCqtH9yQtlzRJ0gpJ/1Tg2/rNko7k2ieqsMZ/6eVfUSkgQcv6JK3hd79kXPfOrxXI8V3SYK0MtFc4z4KFmZlVaKG7cdtMAlYC9wq00ECS1rSdmKTxWsI553wt5TGLIi10QNISRUttu6SDBTVWDyl39RXQmcLvBIZG0GJZWih7VyTkGwQ2VYj5Fhh4Fw0MAB3e/EagD9iYwcQzYAswG5gOrANu1crAC7wNBNhM1E7Ev997818BL+P52yR8pACTgfPVNvACWOONbzXiyxgCtnm8VcDNJPGGMwE4Wy0D/wMrvbEfSH9Qh4DtHr/BHI8HThB9Njaa8XHAL9Uw8Ll3viPtSnnYkZBrInDOcP4C5pj5sbG5cAY8ATszigfoAcab2CnAxQTeXeATwxsDHAtuIKf4G8A0E/shcHUY/gNgvuGXgENBDAAO6Moh/gIw2cRPjQ1VwkNggVd3bwgDB3KIPwtMMLGzgD9yxD8GWk28A/aM1MCDjMVPA+NMXBPwZw7xZTwFFifoKBnOYB4DZzIUPQV8YGLmEK0wRfEcWObpaDLzfXkMfFOh2FFgjOHPI8M7fkYTX5i89tPT/6ob1kAJ6E0pchgoGe6nwP0A4sv41eTuNuM/ZjYQBzcDd7zk+3h7h/0M+Deg+H6gOc79EfCfmVuay0CcpIU3L11dgDNzi4AnAcVfAZri3A44buZ6bO28JpzvHmgnek0eCQaAv4GfgNXEdzaut8vjLktW946BqG2Oe+J3j7auVBAtFo1Eq0030SpkcRKzYIQoOJvoRawW2I9ZqkOaaAEuVVF4Dzl6vtCTTfTArVX0d1+rpEZJRa7WK0kPJd2XdF7Sz5IuO+dG/X+pOuqoo0Z4DePtUHAz1eX1AAAAAElFTkSuQmCC) ">
66+ </ li >
67+ <!--chat-->
68+ < li onclick ="scrollToElement('fh5co-testimonial') "
69+ style ="background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABgAAAAYCAYAAADgdz34AAAABmJLR0QA/wD/AP+gvaeTAAABKklEQVRIidWVq04DQRhGv900QUFFCVWgUYQ6PAgeAUVwSDwplocoCamsqKlE4ICQECDlAfAYoAoDHEQ7SdnO7lw6CE6yYi45384/kxnpv5NVDQJ1SXuSdiVtSGpOhl4kDSVdSOplWTYKSgVqwAnwjps3oA3UfOVN4NpDXOQKWHHJ68BDhNxwDyxVBZzPITeclclbwHeCgC9g03jzqYwDOU6VJ7mkfVvAdgK5YccWsGqZ2JC0HNA2rNkCsEwslszVNizM9ABPCTbYMLSt4LLkb2K4sQV0ZS9TDD1rL9BJUJ670ljGV8XjHPJPYKtybUADuI0MOPUqIOPr+hgYBcgHQO62/w5aBA6BPvAMvE6+In1g9uzHUpB38X1sAgM+gKOk4qmANrD+J/JQfgANB//YYXlyuAAAAABJRU5ErkJggg==) ">
70+ </ li >
71+ </ ul >
72+ <!--calendar-->
73+ < div onclick ="scrollToElement('data') " class ="option-btn open "> </ div >
74+ < ul class ="left-sidebar ">
75+ <!--countdown-->
76+ < li onclick ="scrollToElement('fh5co-header') "
77+ style ="background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABgAAAAYCAYAAADgdz34AAAABmJLR0QA/wD/AP+gvaeTAAABG0lEQVRIidXVTS4EQRjG8SZ2IrEnETEcQmYsjLkCiUu4g1P42FpxhmGG2IvEcAcfG9Z+FtOS1qaramZ6wZPUpqve5//2k36rs+wvCLd+6yaldjaR8TmKm95iDcIhzrA4bmEHp3jCR74ecYKdwrm7PLoBllOMN9AfkX1ZPaxjBff5s4OY+RbeEsy/9YoWFrCP+VjnVeabaAYgjZRoLqvaLJypUi9m3gnlkACAdtGzPAd70VeMazcEaNYA2AoBlmoA/JiBudJmcPzRzLJsJgKo9jCc1mk1KHqWI7qOdJeifghwXgPgIriL7hTxXEXxWMXzBOZpV0UOaeUFqXox/MLShYbAvVRQF2tjmZdAbRwb/kje8/WAI2xPbPxv9AUiVMwGoTr9YAAAAABJRU5ErkJggg==) ">
78+ </ li >
79+ <!--couple-->
80+ < li onclick ="scrollToElement('fh5co-couple') "
81+ style ="background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAB4AAAAeCAYAAAA7MK6iAAAABmJLR0QA/wD/AP+gvaeTAAAB7UlEQVRIie2VPUiVURjH/+eqSSJN4tDWRRAH5xD8QDCwgqAWhwwSaarBwUGaHFwcBAchGqNNdDaKoKAkBEvUURAVRInw82Jx0Z/De64+Xu5773nv0CD3P533eZ//+T3nW6qoomstwAEPgXfAKnAA7AE/gWGgJsbXAIwCi8ARkAF+AS+AqlLQJmCB4voMDAL1xvfUFxin98WgLX5kIdoHbnvfK+AswJMBvgGPLbQGWAmEAgx7XzuQTeDLaSgHfpLA9Bu45X0/yoAC/AXSKUn9AfvuTNIXSb3OuUOgQ9LdAJ8kfZDUJenYf9dKGqiW1JyXuCbpq6RlSRuStiStO+f2TM6DQOiSpOfOuV1gStKIj3eKyx2ZJdqxrlRvwHzMNP4DlomOYx/m+AEdJm9H5mM8cBQCNvKA00AbcKOIp9GuswW3JgBnjO9toKfWVmrBdQnAVkkKvlBKUsbHY6ephNbKMaUkffftj0C6jD5uhiRhrtlcoAXY9jPwJrATq+5AT+eVNfbBZqLjdAq0JwTPBOQ7YM54Nu3PMR/8A9wrYH4UAwZ4VgSaBmYtFOi1CSlgxiTMA5PAhG9jcrfywFngJQGXT1x1VcBrosc8X/sm734BOERPX9AdXrBCoh3YI+mOogdiXdIn59xJWSOqqKL/qXMXI9MKbss7gAAAAABJRU5ErkJggg==) ">
82+ </ li >
83+ </ ul >
84+ </ div >
85+ </ div >
7886
7987 <!-- Begin Header -->
8088 < div class ="header-wrapper " id ="home ">
@@ -245,7 +253,7 @@ <h4 class="subtitle tempatwaktu">
245253 <!-- End regular-section-->
246254
247255 <!-- Begin Waktu Section -->
248- < section class ="section-dark " id ="Waktu ">
256+ < section class ="section-dark " id ="data ">
249257 < div class ="container ">
250258
251259 < div class ="column is-12 regular-section " data-aos ="fade-up " data-aos-easing ="linear ">
@@ -326,7 +334,7 @@ <h1 class="title has-text-centered section-title">Local</h1>
326334 </ section >
327335 <!-- End Lokasi Content -->
328336
329-
337+
330338 <!-- Begin RSVP Content -->
331339
332340 <!-- RSVP FORM (Bulma-friendly) -->
@@ -519,10 +527,11 @@ <h1 class="title has-text-centered section-title" data-aos="fade-up" data-aos-ea
519527</ body >
520528< script >
521529
522- ( function ( ) {
530+ ( function ( ) {
523531 const audio = document . getElementById ( 'page-audio' ) ;
524532 const icon = document . getElementById ( 'youtube-icon1' ) ;
525533 let startedMutedAutoplay = false ;
534+ let canUnmute = false ; // whether unmuted playback is allowed by browser
526535
527536 function updateIcon ( ) {
528537 if ( ! icon || ! audio ) return ;
@@ -536,44 +545,99 @@ <h1 class="title has-text-centered section-title" data-aos="fade-up" data-aos-ea
536545 await audio . play ( ) ;
537546 startedMutedAutoplay = true ;
538547 updateIcon ( ) ;
539- const unmuteOnGesture = ( ) => {
540- audio . muted = false ;
541- audio . play ( ) . catch ( ( ) => { } ) ;
542- updateIcon ( ) ;
543- document . removeEventListener ( 'pointerdown' , unmuteOnGesture ) ;
544- } ;
545- document . addEventListener ( 'pointerdown' , unmuteOnGesture , { once : true } ) ;
546548 } catch ( e ) {
547- // autoplay failed (likely blocked). Leave muted = false so user can start playback.
549+ // autoplay muted failed; leave paused so user gesture can start audible playback
550+ startedMutedAutoplay = false ;
548551 audio . muted = false ;
549552 }
550553 }
551554
555+ // Attempt to unmute and play audibly from the start. Returns true if audible playback started.
556+ async function attemptUnmuteAndPlay ( ) {
557+ if ( ! audio ) return false ;
558+ audio . muted = false ;
559+ // Ensure we start from the beginning when audible playback begins
560+ const startFromBeginning = async ( ) => {
561+ if ( audio . readyState < 1 ) {
562+ await new Promise ( ( resolve ) => audio . addEventListener ( 'loadedmetadata' , resolve , { once : true } ) ) ;
563+ }
564+ try { audio . currentTime = 0 ; } catch ( e ) { /* ignore if not seekable yet */ }
565+ await audio . play ( ) ;
566+ } ;
567+
568+ try {
569+ await startFromBeginning ( ) ;
570+ canUnmute = true ;
571+ updateIcon ( ) ;
572+ return true ;
573+ } catch ( e ) {
574+ // Unmute was not allowed. Restore muted state (keep muted autoplay if running), don't start audible playback.
575+ audio . muted = true ;
576+ // If muted autoplay wasn't running, pause to avoid surprising behavior.
577+ if ( ! startedMutedAutoplay ) {
578+ try { audio . pause ( ) ; } catch { }
579+ }
580+ return false ;
581+ }
582+ }
583+
552584 if ( audio && icon ) {
553585 audio . loop = true ;
554- icon . addEventListener ( 'click' , ( ) => {
586+
587+ // Try muted autoplay on load (allowed by browsers). This keeps audio silent until unmute is allowed.
588+ tryAutoplayMuted ( ) ;
589+
590+ // On first user gesture anywhere, attempt to unmute audibly and restart from the beginning.
591+ const onFirstGesture = async ( ) => {
592+ await attemptUnmuteAndPlay ( ) ;
593+ } ;
594+ document . addEventListener ( 'pointerdown' , onFirstGesture , { once : true } ) ;
595+
596+ icon . addEventListener ( 'click' , async ( ) => {
555597 if ( audio . paused ) {
556- // if we started muted autoplay, unmute when user explicitly clicks the control
557- audio . muted = false ;
558- audio . play ( ) . then ( updateIcon ) . catch ( ( ) => { } ) ;
598+ // Try to start audible playback from the beginning (succeeds only if browser allows unmuting after a gesture)
599+ const ok = await attemptUnmuteAndPlay ( ) ;
600+ if ( ! ok ) {
601+ // fallback: if muted autoplay is available, ensure muted playback is running so icon state is correct
602+ if ( startedMutedAutoplay ) {
603+ await audio . play ( ) . catch ( ( ) => { } ) ;
604+ updateIcon ( ) ;
605+ }
606+ }
559607 } else {
560608 audio . pause ( ) ;
561609 updateIcon ( ) ;
562610 }
563611 } ) ;
564612
565- // attempt muted autoplay on load; will unmute on first user gesture
566- tryAutoplayMuted ( ) ;
567613 updateIcon ( ) ;
568614
569615 window . audioPlayer = {
570- play : async ( ) => { await audio . play ( ) . catch ( ( ) => { } ) ; updateIcon ( ) ; } ,
616+ play : async ( ) => { if ( ! canUnmute ) await attemptUnmuteAndPlay ( ) ; else await audio . play ( ) . catch ( ( ) => { } ) ; updateIcon ( ) ; } ,
571617 pause : ( ) => { audio . pause ( ) ; updateIcon ( ) ; } ,
572- toggle : ( ) => { if ( audio . paused ) return window . audioPlayer . play ( ) ; else window . audioPlayer . pause ( ) ; }
618+ toggle : async ( ) => { if ( audio . paused ) return window . audioPlayer . play ( ) ; else window . audioPlayer . pause ( ) ; }
573619 } ;
574620 }
575621 } ) ( ) ;
576622
623+ // Smooth scroll helper used by floating controls
624+ function scrollToElement ( id ) {
625+ const el = document . getElementById ( id ) ;
626+ if ( ! el ) return ;
627+ try {
628+ el . scrollIntoView ( { behavior : 'smooth' , block : 'start' } ) ;
629+ } catch ( e ) {
630+ // fallback
631+ const top = el . getBoundingClientRect ( ) . top + window . pageYOffset ;
632+ window . scrollTo ( { top, behavior : 'smooth' } ) ;
633+ }
634+ if ( history . replaceState ) {
635+ history . replaceState ( null , null , '#' + id ) ;
636+ } else {
637+ location . hash = '#' + id ;
638+ }
639+ }
640+
577641
578642 // Replace with your Worker endpoint
579643 const API_SUBMIT_URL = "https://wedding.tiagoalfredo-rocha.workers.dev/submit" ;
0 commit comments