Merge pull request #429 from taroj1205/fix/video

Implement lazy loading of videos
This commit is contained in:
mr. m 2025-01-27 15:33:06 +01:00 committed by GitHub
commit d32077cf6d
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
9 changed files with 359 additions and 250 deletions

View file

@ -18,5 +18,5 @@ export default defineConfig({
site: 'https://zen-browser.app', site: 'https://zen-browser.app',
redirects: { redirects: {
'/themes/[...slug]': '/mods/[...slug]', '/themes/[...slug]': '/mods/[...slug]',
}, }
}) })

View file

@ -1,7 +1,5 @@
--- ---
import Title from '../components/Title.astro'
import Description from '../components/Description.astro' import Description from '../components/Description.astro'
import { Image } from 'astro:assets'
import browserSidebar from '../assets/browser-sidebar.webm' import browserSidebar from '../assets/browser-sidebar.webm'
import browserWorkspaces from '../assets/browser-workspaces.webm' import browserWorkspaces from '../assets/browser-workspaces.webm'
@ -10,7 +8,8 @@ import browserGlance from '../assets/browser-glance.webm'
import browserSplitViews from '../assets/browser-splitview.webm' import browserSplitViews from '../assets/browser-splitview.webm'
import { motion } from 'motion/react' import { motion } from 'motion/react'
import { getTitleAnimation, getZoomInAnimation } from '../animations' import { getTitleAnimation } from '../animations'
import Video from './Video.astro'
--- ---
<section <section
@ -47,14 +46,15 @@ import { getTitleAnimation, getZoomInAnimation } from '../animations'
organized. organized.
</p> </p>
</div> </div>
<video <Video
src={browserWorkspaces} src={browserWorkspaces}
autoplay autoplay
loop loop
muted muted
playsinline playsinline
preload="none" preload="none"
class="rounded-xl border-4 border-white object-cover shadow"></video> class="rounded-xl border-4 border-white object-cover shadow"
/>
</div> </div>
<div class="long-feature xl:!flex-row-reverse"> <div class="long-feature xl:!flex-row-reverse">
<div class="lg:p-24"> <div class="lg:p-24">
@ -66,14 +66,15 @@ import { getTitleAnimation, getZoomInAnimation } from '../animations'
distractions. distractions.
</p> </p>
</div> </div>
<video <Video
src={browserCompactMode} src={browserCompactMode}
autoplay autoplay
loop loop
muted muted
playsinline playsinline
preload="none" preload="none"
class="rounded-xl border-4 border-white object-cover shadow"></video> class="rounded-xl border-4 border-white object-cover shadow"
/>
</div> </div>
<div class="long-feature"> <div class="long-feature">
<div class="lg:p-24"> <div class="lg:p-24">
@ -87,14 +88,15 @@ import { getTitleAnimation, getZoomInAnimation } from '../animations'
opening them. opening them.
</p> </p>
</div> </div>
<video <Video
src={browserGlance} src={browserGlance}
autoplay autoplay
loop loop
muted muted
playsinline playsinline
preload="none" preload="none"
class="rounded-xl border-4 border-white object-cover shadow"></video> class="rounded-xl border-4 border-white object-cover shadow"
/>
</div> </div>
<div class="long-feature xl:!flex-row-reverse"> <div class="long-feature xl:!flex-row-reverse">
<div class="lg:p-24"> <div class="lg:p-24">
@ -107,14 +109,15 @@ import { getTitleAnimation, getZoomInAnimation } from '../animations'
Zen's split view feature allows you to view multiple tabs at once. Zen's split view feature allows you to view multiple tabs at once.
</p> </p>
</div> </div>
<video <Video
src={browserSplitViews} src={browserSplitViews}
autoplay autoplay
loop loop
muted muted
playsinline playsinline
preload="none" preload="none"
class="rounded-xl border-4 border-white object-cover shadow"></video> class="rounded-xl border-4 border-white object-cover shadow"
/>
</div> </div>
<div class="long-feature"> <div class="long-feature">
<div class="lg:p-24"> <div class="lg:p-24">
@ -125,14 +128,15 @@ import { getTitleAnimation, getZoomInAnimation } from '../animations'
Zen's sidebar feature allows you to view all your tabs in one place. Zen's sidebar feature allows you to view all your tabs in one place.
</p> </p>
</div> </div>
<video <Video
src={browserSidebar} src={browserSidebar}
autoplay autoplay
loop loop
muted muted
playsinline playsinline
preload="none" preload="none"
class="rounded-xl border-4 border-white object-cover shadow"></video> class="rounded-xl border-4 border-white object-cover shadow"
/>
</div> </div>
</div> </div>
</section> </section>

View file

@ -12,7 +12,7 @@ import {
} from 'astro-navbar' } from 'astro-navbar'
import { ArrowRight, ChevronDown, Download, DownloadCloud } from 'lucide-astro' import { ArrowRight, ChevronDown, Download, DownloadCloud } from 'lucide-astro'
import Logo from './Logo.astro' import Logo from './Logo.astro'
import { ThemeSwitch } from 'free-astro-components' import ThemeSwitch from './ThemeSwitch.astro'
--- ---
<nav <nav
@ -112,7 +112,7 @@ import { ThemeSwitch } from 'free-astro-components'
</div> </div>
<div class="ml-auto flex gap-2"> <div class="ml-auto flex gap-2">
<div id="theme-switcher" class="ml-auto md:mr-2"> <div id="theme-switcher" class="ml-auto md:mr-2">
<ThemeSwitch label="" class="px-1 py-2" /> <ThemeSwitch />
</div> </div>
<Button href="/download" class="ml-auto" isPrimary> <Button href="/download" class="ml-auto" isPrimary>
<span class="hidden items-center gap-2 md:flex"> <span class="hidden items-center gap-2 md:flex">

View file

@ -0,0 +1,33 @@
---
interface Props {
label?: string
class?: string
}
const { label = 'Toggle theme', class: className, ...rest } = Astro.props
import SunIcon from '../icons/SunIcon.astro'
import MoonIcon from '../icons/MoonIcon.astro'
---
<button
id="theme-toggle"
type="button"
class:list={['rounded-lg p-2.5 outline-none', className]}
aria-label={label}
{...rest}
>
<SunIcon class="hidden size-5 dark:block" />
<MoonIcon class="size-5 dark:hidden" />
</button>
<script>
document.addEventListener('astro:page-load', () => {
const themeToggleBtn = document.getElementById('theme-toggle')
themeToggleBtn?.addEventListener('click', () => {
const currentTheme = document.documentElement.dataset.theme
const newTheme = currentTheme === 'dark' ? 'light' : 'dark'
localStorage.theme = newTheme
document.documentElement.dataset.theme = newTheme
})
})
</script>

View file

@ -0,0 +1,42 @@
---
const { src, class: className, ...rest } = Astro.props
const type = src.split('.').pop() || 'webm'
---
<video
class:list={['w-full', className]}
data-src={src}
preload="none"
{...rest}
>
<source src="" type={`video/${type}`} />
</video>
<script>
document.addEventListener('astro:page-load', () => {
const videos = document.querySelectorAll('video[data-src]')
const loadVideo = (video: HTMLVideoElement) => {
const source = video.querySelector('source')
const dataSrc = video.getAttribute('data-src')
if (dataSrc && source) {
source.src = dataSrc
video.load()
video.removeAttribute('data-src')
}
}
const observer = new IntersectionObserver((entries) => {
entries.forEach((entry) => {
if (entry.isIntersecting) {
loadVideo(entry.target as HTMLVideoElement)
observer.unobserve(entry.target)
}
})
})
videos.forEach((video) => {
observer.observe(video)
})
})
</script>

9
src/icons/MoonIcon.astro Normal file
View file

@ -0,0 +1,9 @@
---
const { class: className, ...rest } = Astro.props
---
<svg class={className} viewBox="0 0 24 24" {...rest}>
<path
d="M10.719 2.082c-2.572 2.028-4.719 5.212-4.719 9.918 0 4.569 1.938 7.798 4.548 9.895-4.829-.705-8.548-4.874-8.548-9.895 0-5.08 3.808-9.288 8.719-9.918zm1.281-2.082c-6.617 0-12 5.383-12 12s5.383 12 12 12c1.894 0 3.87-.333 5.37-1.179-3.453-.613-9.37-3.367-9.37-10.821 0-7.555 6.422-10.317 9.37-10.821-1.74-.682-3.476-1.179-5.37-1.179zm0 10.999c1.437.438 2.562 1.564 2.999 3.001.44-1.437 1.565-2.562 3.001-3-1.436-.439-2.561-1.563-3.001-3-.437 1.436-1.562 2.561-2.999 2.999zm8.001.001c.958.293 1.707 1.042 2 2.001.291-.959 1.042-1.709 1.999-2.001-.957-.292-1.707-1.042-2-2-.293.958-1.042 1.708-1.999 2zm-1-9c-.437 1.437-1.563 2.562-2.998 3.001 1.438.44 2.561 1.564 3.001 3.002.437-1.438 1.563-2.563 2.996-3.002-1.433-.437-2.559-1.564-2.999-3.001z"
fill="currentColor"></path>
</svg>

9
src/icons/SunIcon.astro Normal file
View file

@ -0,0 +1,9 @@
---
const { class: className, ...rest } = Astro.props
---
<svg class={className} viewBox="0 0 24 24" {...rest}>
<path
d="M12 9c1.654 0 3 1.346 3 3s-1.346 3-3 3-3-1.346-3-3 1.346-3 3-3zm0-2c-2.762 0-5 2.238-5 5s2.238 5 5 5 5-2.238 5-5-2.238-5-5-5zm-4.184-.599l-3.593-3.594-1.415 1.414 3.595 3.595c.401-.537.876-1.013 1.413-1.415zm4.184-1.401c.34 0 .672.033 1 .08v-5.08h-2v5.08c.328-.047.66-.08 1-.08zm5.598 2.815l3.595-3.595-1.414-1.414-3.595 3.595c.537.402 1.012.878 1.414 1.414zm-12.598 4.185c0-.34.033-.672.08-1h-5.08v2h5.08c-.047-.328-.08-.66-.08-1zm11.185 5.598l3.594 3.593 1.415-1.414-3.594-3.593c-.403.536-.879 1.012-1.415 1.414zm-9.784-1.414l-3.593 3.593 1.414 1.414 3.593-3.593c-.536-.402-1.011-.877-1.414-1.414zm12.519-5.184c.047.328.08.66.08 1s-.033.672-.08 1h5.08v-2h-5.08zm-6.92 8c-.34 0-.672-.033-1-.08v5.08h2v-5.08c-.328.047-.66.08-1 .08z"
fill="currentColor"></path>
</svg>

View file

@ -7,29 +7,32 @@ const { title } = Astro.props
import '@fontsource/bricolage-grotesque/400.css' import '@fontsource/bricolage-grotesque/400.css'
import NavBar from '../components/NavBar.astro' import NavBar from '../components/NavBar.astro'
import Footer from '../components/Footer.astro' import Footer from '../components/Footer.astro'
import { ClientRouter } from 'astro:transitions'
--- ---
<script is:inline> <script is:inline>
const theme = (() => { function setDarkMode(document) {
if (typeof localStorage !== 'undefined' && localStorage.getItem('theme')) { let theme = localStorage.theme
return localStorage.getItem('theme') ?? 'light'
}
if (window.matchMedia('(prefers-color-scheme: dark)').matches) {
return 'dark'
}
return 'light'
})()
if (theme === 'light') { if (theme === undefined) {
document.documentElement.setAttribute('data-theme', 'light') theme = window.matchMedia('(prefers-color-scheme: dark)').matches
} else { ? 'dark'
document.documentElement.setAttribute('data-theme', 'dark') : 'light'
}
localStorage.theme = theme
document.documentElement.dataset.theme = theme
} }
window.localStorage.setItem('theme', theme) setDarkMode(document)
document.addEventListener('astro:before-swap', (event) => {
setDarkMode(event.newDocument)
})
</script> </script>
<html lang="en"> <html lang="en" transition:name="root" transition:animate="none">
<head> <head>
<meta charset="UTF-8" /> <meta charset="UTF-8" />
<meta <meta
@ -69,6 +72,7 @@ import Footer from '../components/Footer.astro'
title="Zen Browser Release Notes" title="Zen Browser Release Notes"
href={`${Astro.url.origin}/feed.xml`} href={`${Astro.url.origin}/feed.xml`}
/> />
<ClientRouter />
</head> </head>
<body <body
class="overflow-x-hidden bg-paper font-['bricolage-grotesque'] text-dark" class="overflow-x-hidden bg-paper font-['bricolage-grotesque'] text-dark"

View file

@ -261,257 +261,265 @@ const appleIcon = icon({ prefix: 'fab', iconName: 'apple' })
</main> </main>
</Layout> </Layout>
<script> <script>
const releases = { document.addEventListener('astro:page-load', () => {
macos: { const releases = {
intel: 'zen.macos-x86_64.dmg', macos: {
arm: 'zen.macos-aarch64.dmg', intel: 'zen.macos-x86_64.dmg',
}, arm: 'zen.macos-aarch64.dmg',
linux: {
x86_64: {
tar: 'zen.linux-x86_64.tar.bz2',
appImage: 'zen-x86_64.AppImage',
}, },
aarch64: { linux: {
tar: 'zen.linux-aarch64.tar.bz2', x86_64: {
appImage: 'zen-aarch64.AppImage', tar: 'zen.linux-x86_64.tar.bz2',
appImage: 'zen-x86_64.AppImage',
},
aarch64: {
tar: 'zen.linux-aarch64.tar.bz2',
appImage: 'zen-aarch64.AppImage',
},
}, },
}, windows: {
windows: { x86_64: {
x86_64: { installer: 'zen.installer.exe',
installer: 'zen.installer.exe', zip: 'zen.win-x86_64.zip',
zip: 'zen.win-x86_64.zip', },
arm64: {
installer: 'zen.installer-arm64.exe',
zip: 'zen.win-arm64.zip',
},
}, },
arm64: { } as any
installer: 'zen.installer-arm64.exe',
zip: 'zen.win-arm64.zip',
},
},
} as any
const BASE_URL = const BASE_URL =
'https://github.com/zen-browser/desktop/releases/latest/download' 'https://github.com/zen-browser/desktop/releases/latest/download'
const TWILIGHT_BASE_URL = const TWILIGHT_BASE_URL =
'https://github.com/zen-browser/desktop/releases/download/twilight' 'https://github.com/zen-browser/desktop/releases/download/twilight'
var selectedOS: string | null = null var selectedOS: string | null = null
var isTwilight: boolean = false var isTwilight: boolean = false
var selectedArch: string | null = null var selectedArch: string | null = null
function showButton(buttonId: string, show: boolean) { function showButton(buttonId: string, show: boolean) {
const button = document.getElementById(buttonId) as HTMLButtonElement const button = document.getElementById(buttonId) as HTMLButtonElement
if (show) { if (show) {
button?.classList.remove('hidden') button?.classList.remove('hidden')
} else { } else {
button?.classList.add('hidden') button?.classList.add('hidden')
}
} }
}
function downloadRelease(os: string, arch: string, format: string = '') { function downloadRelease(os: string, arch: string, format: string = '') {
console.log('Downloading release', os, arch, format) console.log('Downloading release', os, arch, format)
let releaseName = releases[os][arch] let releaseName = releases[os][arch]
if (os !== 'macos') { if (os !== 'macos') {
releaseName = releases[os][arch][format] releaseName = releases[os][arch][format]
}
const url = `${isTwilight ? TWILIGHT_BASE_URL : BASE_URL}/${releaseName}`
console.log('Downloading from', url)
window.open(url, '_blank')
} }
const url = `${isTwilight ? TWILIGHT_BASE_URL : BASE_URL}/${releaseName}`
console.log('Downloading from', url)
window.open(url, '_blank')
}
function goNextForm() { function goNextForm() {
if (selectedOS === null) { if (selectedOS === null) {
const osSelect = document.getElementById('os-select') as HTMLFormElement const osSelect = document.getElementById('os-select') as HTMLFormElement
const selectedRadio = osSelect.querySelector( const selectedRadio = osSelect.querySelector(
"input[type='radio']:checked", "input[type='radio']:checked",
) as HTMLInputElement ) as HTMLInputElement
selectedOS = selectedRadio.value selectedOS = selectedRadio.value
document.getElementById('form-os-select')?.classList.add('hidden') document.getElementById('form-os-select')?.classList.add('hidden')
if (selectedOS === 'macos') { if (selectedOS === 'macos') {
const macosDownload = document.getElementById( const macosDownload = document.getElementById(
'form-macos-download', 'form-macos-download',
) as HTMLDivElement ) as HTMLDivElement
macosDownload.classList.remove('hidden') macosDownload.classList.remove('hidden')
showButton('next-button', false) showButton('next-button', false)
} else if (selectedOS === 'linux') { } else if (selectedOS === 'linux') {
const linuxDownload = document.getElementById( const linuxDownload = document.getElementById(
'linux-target-download',
) as HTMLDivElement
linuxDownload.classList.remove('hidden')
} else if (selectedOS === 'windows') {
const windowsDownload = document.getElementById(
'windows-target-download',
) as HTMLDivElement
windowsDownload.classList.remove('hidden')
}
showButton('back-button', true) // Show Back button after first step
} else if (selectedOS === 'linux' && selectedArch === null) {
const linuxTargetSelect = document.getElementById(
'linux-target-download', 'linux-target-download',
) as HTMLFormElement
const selectedRadio = linuxTargetSelect.querySelector(
"input[type='radio']:checked",
) as HTMLInputElement
selectedArch = selectedRadio.value
document
.getElementById('linux-target-download')
?.classList.add('hidden')
const linuxDownload = document.getElementById(
'form-linux-download',
) as HTMLDivElement ) as HTMLDivElement
linuxDownload.classList.remove('hidden') linuxDownload.classList.remove('hidden')
} else if (selectedOS === 'windows') {
const windowsDownload = document.getElementById( showButton('next-button', false)
} else if (selectedOS === 'windows' && selectedArch === null) {
const windowsTargetSelect = document.getElementById(
'windows-target-download', 'windows-target-download',
) as HTMLFormElement
const selectedRadio = windowsTargetSelect.querySelector(
"input[type='radio']:checked",
) as HTMLInputElement
selectedArch = selectedRadio.value
document
.getElementById('windows-target-download')
?.classList.add('hidden')
const windowsDownload = document.getElementById(
'windows-download',
) as HTMLDivElement ) as HTMLDivElement
windowsDownload.classList.remove('hidden') windowsDownload.classList.remove('hidden')
showButton('next-button', false)
} else {
throw new Error('Unknown state')
} }
showButton('back-button', true) // Show Back button after first step }
} else if (selectedOS === 'linux' && selectedArch === null) {
const linuxTargetSelect = document.getElementById( function goPreviousForm() {
'linux-target-download', if (selectedArch) {
) as HTMLFormElement // Go back to architecture selection
const selectedRadio = linuxTargetSelect.querySelector( if (selectedOS === 'linux') {
"input[type='radio']:checked", document
.getElementById('form-linux-download')
?.classList.add('hidden')
document
.getElementById('linux-target-download')
?.classList.remove('hidden')
} else if (selectedOS === 'windows') {
document.getElementById('windows-download')?.classList.add('hidden')
document
.getElementById('windows-target-download')
?.classList.remove('hidden')
}
selectedArch = null
showButton('back-button', true)
showButton('next-button', true)
} else if (selectedOS) {
// Go back to OS selection
if (selectedOS === 'macos') {
document
.getElementById('form-macos-download')
?.classList.add('hidden')
} else if (selectedOS === 'linux') {
document
.getElementById('linux-target-download')
?.classList.add('hidden')
} else if (selectedOS === 'windows') {
document
.getElementById('windows-target-download')
?.classList.add('hidden')
}
document.getElementById('form-os-select')?.classList.remove('hidden')
selectedOS = null
showButton('back-button', false)
showButton('next-button', true)
}
}
showButton('back-button', false) // Hide Back button on page load
showButton('next-button', true) // Ensure Next button is visible on load
function filloutDefaultOS() {
const osSelect = document.getElementById('os-select') as HTMLFormElement
const osSelectWindows = document.getElementById(
'os-select-windows',
) as HTMLInputElement ) as HTMLInputElement
selectedArch = selectedRadio.value const osSelectLinux = document.getElementById(
document.getElementById('linux-target-download')?.classList.add('hidden') 'os-select-linux',
) as HTMLInputElement
const linuxDownload = document.getElementById( const osSelectMacOS = document.getElementById(
'form-linux-download', 'os-select-macos',
) as HTMLDivElement
linuxDownload.classList.remove('hidden')
showButton('next-button', false)
} else if (selectedOS === 'windows' && selectedArch === null) {
const windowsTargetSelect = document.getElementById(
'windows-target-download',
) as HTMLFormElement
const selectedRadio = windowsTargetSelect.querySelector(
"input[type='radio']:checked",
) as HTMLInputElement ) as HTMLInputElement
selectedArch = selectedRadio.value
document
.getElementById('windows-target-download')
?.classList.add('hidden')
const windowsDownload = document.getElementById( if (navigator.platform.includes('Win')) {
'windows-download', osSelectWindows.checked = true
) as HTMLDivElement } else if (navigator.platform.includes('Linux')) {
windowsDownload.classList.remove('hidden') osSelectLinux.checked = true
} else if (navigator.platform.includes('Mac')) {
showButton('next-button', false) osSelectMacOS.checked = true
} else {
throw new Error('Unknown state')
}
}
function goPreviousForm() {
if (selectedArch) {
// Go back to architecture selection
if (selectedOS === 'linux') {
document.getElementById('form-linux-download')?.classList.add('hidden')
document
.getElementById('linux-target-download')
?.classList.remove('hidden')
} else if (selectedOS === 'windows') {
document.getElementById('windows-download')?.classList.add('hidden')
document
.getElementById('windows-target-download')
?.classList.remove('hidden')
} }
selectedArch = null }
showButton('back-button', true)
showButton('next-button', true) function getIfTwilight() {
} else if (selectedOS) { const urlParams = new URLSearchParams(window.location.search)
// Go back to OS selection isTwilight = urlParams.has('twilight')
if (selectedOS === 'macos') { if (isTwilight) {
document.getElementById('form-macos-download')?.classList.add('hidden') console.log('Twilight mode enabled')
} else if (selectedOS === 'linux') { const name = document.getElementById('zen-name')
document const twilightInfo = document.getElementById('twilight-info')
.getElementById('linux-target-download') if (name) name.innerHTML = 'Twilight'
?.classList.add('hidden') if (twilightInfo) twilightInfo.classList.remove('hidden')
} else if (selectedOS === 'windows') { } else {
document document.getElementById('windows-zip-download')?.classList.add('hidden')
.getElementById('windows-target-download')
?.classList.add('hidden')
} }
document.getElementById('form-os-select')?.classList.remove('hidden')
selectedOS = null
showButton('back-button', false)
showButton('next-button', true)
} }
}
showButton('back-button', false) // Hide Back button on page load getIfTwilight()
showButton('next-button', true) // Ensure Next button is visible on load
function filloutDefaultOS() { document.getElementById('next-button')?.addEventListener('click', () => {
const osSelect = document.getElementById('os-select') as HTMLFormElement goNextForm()
const osSelectWindows = document.getElementById( })
'os-select-windows',
) as HTMLInputElement
const osSelectLinux = document.getElementById(
'os-select-linux',
) as HTMLInputElement
const osSelectMacOS = document.getElementById(
'os-select-macos',
) as HTMLInputElement
if (navigator.platform.includes('Win')) { document.getElementById('back-button')?.addEventListener('click', () => {
osSelectWindows.checked = true goPreviousForm()
} else if (navigator.platform.includes('Linux')) { })
osSelectLinux.checked = true
} else if (navigator.platform.includes('Mac')) {
osSelectMacOS.checked = true
}
}
function getIfTwilight() { document
const urlParams = new URLSearchParams(window.location.search) .getElementById('macos-arm-download')
isTwilight = urlParams.has('twilight') ?.addEventListener('click', () => {
if (isTwilight) { downloadRelease('macos', 'arm')
console.log('Twilight mode enabled') })
const name = document.getElementById('zen-name')
const twilightInfo = document.getElementById('twilight-info')
if (name) name.innerHTML = 'Twilight'
if (twilightInfo) twilightInfo.classList.remove('hidden')
} else {
document.getElementById('windows-zip-download')?.classList.add('hidden')
}
}
getIfTwilight() document
.getElementById('macos-intel-download')
?.addEventListener('click', () => {
downloadRelease('macos', 'intel')
})
document.getElementById('next-button')?.addEventListener('click', () => { document
goNextForm() .getElementById('linux-tar-download')
?.addEventListener('click', () => {
downloadRelease('linux', selectedArch as string, 'tar')
})
document
.getElementById('linux-appimage-download')
?.addEventListener('click', () => {
downloadRelease('linux', selectedArch as string, 'appImage')
})
document
.getElementById('linux-flathub-download')
?.addEventListener('click', () => {
window.open('https://flathub.org/apps/app.zen_browser.zen')
})
document
.getElementById('windows-installer-download')
?.addEventListener('click', () => {
downloadRelease('windows', selectedArch as string, 'installer')
})
document
.getElementById('windows-zip-download')
?.addEventListener('click', () => {
//downloadRelease("windows", selectedArch as string, "zip");
})
filloutDefaultOS()
}) })
document.getElementById('back-button')?.addEventListener('click', () => {
goPreviousForm()
})
document
.getElementById('macos-arm-download')
?.addEventListener('click', () => {
downloadRelease('macos', 'arm')
})
document
.getElementById('macos-intel-download')
?.addEventListener('click', () => {
downloadRelease('macos', 'intel')
})
document
.getElementById('linux-tar-download')
?.addEventListener('click', () => {
downloadRelease('linux', selectedArch as string, 'tar')
})
document
.getElementById('linux-appimage-download')
?.addEventListener('click', () => {
downloadRelease('linux', selectedArch as string, 'appImage')
})
document
.getElementById('linux-flathub-download')
?.addEventListener('click', () => {
window.open('https://flathub.org/apps/app.zen_browser.zen')
})
document
.getElementById('windows-installer-download')
?.addEventListener('click', () => {
downloadRelease('windows', selectedArch as string, 'installer')
})
document
.getElementById('windows-zip-download')
?.addEventListener('click', () => {
//downloadRelease("windows", selectedArch as string, "zip");
})
filloutDefaultOS()
</script> </script>
<style is:global> <style is:global>
@keyframes fadeIn { @keyframes fadeIn {