Skip to content
Snippets Groups Projects
Verified Commit 4cf29e88 authored by Louis's avatar Louis :fire:
Browse files

Use mold linker; use latest web wrapper; adjust build commands

parent 1b5a4c32
No related branches found
No related tags found
No related merge requests found
...@@ -5,7 +5,7 @@ ...@@ -5,7 +5,7 @@
[target.x86_64-unknown-linux-gnu] [target.x86_64-unknown-linux-gnu]
linker = "clang" linker = "clang"
rustflags = ["-Clink-arg=-fuse-ld=lld", "-Zshare-generics=y"] rustflags = ["-Clink-arg=-fuse-ld=mold", "-Zshare-generics=y"]
# NOTE: you must manually install https://github.com/michaeleisel/zld on mac. you can easily do this with the "brew" package manager: # NOTE: you must manually install https://github.com/michaeleisel/zld on mac. you can easily do this with the "brew" package manager:
# `brew install michaeleisel/zld/zld` # `brew install michaeleisel/zld/zld`
......
...@@ -52,30 +52,30 @@ build-linux: ...@@ -52,30 +52,30 @@ build-linux:
only: only:
- trunk - trunk
build-arm64: #build-arm64:
image: "r.lcr.gr/microhacks/bevy-builder:arm64" # image: "r.lcr.gr/microhacks/bevy-builder:arm64"
tags: # tags:
- arm64 # - arm64
stage: build # stage: build
before_script: # before_script:
- export CARGO_HOME="${CI_PROJECT_DIR}/.cargo" # - export CARGO_HOME="${CI_PROJECT_DIR}/.cargo"
- export PATH="${CI_PROJECT_DIR}/.cargo/bin:$PATH" # - export PATH="${CI_PROJECT_DIR}/.cargo/bin:$PATH"
cache: # cache:
key: build-cache-arm64 # key: build-cache-arm64
paths: # paths:
- .cargo/registry/cache # - .cargo/registry/cache
- .cargo/registry/index # - .cargo/registry/index
- .cargo/git/db # - .cargo/git/db
- .cargo/bin/ # - .cargo/bin/
- target/ # - target/
script: # script:
- cargo build --release -p ${BINARY_FOLDER} --target aarch64-unknown-linux-gnu # - cargo build --release -p ${BINARY_FOLDER} --target aarch64-unknown-linux-gnu
artifacts: # artifacts:
expire_in: 1 day # expire_in: 1 day
paths: # paths:
- target/aarch64-unknown-linux-gnu/release/game_core # - target/aarch64-unknown-linux-gnu/release/game_core
only: # only:
- trunk # - trunk
build-web: build-web:
stage: build stage: build
...@@ -112,16 +112,16 @@ package-all: ...@@ -112,16 +112,16 @@ package-all:
- cp -r assets dist/assets - cp -r assets dist/assets
- cp target/x86_64-unknown-linux-gnu/release/${BINARY_NAME} "dist/${BINARY_NAME}" - cp target/x86_64-unknown-linux-gnu/release/${BINARY_NAME} "dist/${BINARY_NAME}"
- cp target/x86_64-pc-windows-gnu/release/${BINARY_NAME}.exe "dist/${BINARY_NAME}.exe" - cp target/x86_64-pc-windows-gnu/release/${BINARY_NAME}.exe "dist/${BINARY_NAME}.exe"
- cp target/aarch64-unknown-linux-gnu/release/${BINARY_NAME} "dist/${BINARY_NAME}.arm64" # - cp target/aarch64-unknown-linux-gnu/release/${BINARY_NAME} "dist/${BINARY_NAME}.arm64"
- cd "${CI_PROJECT_DIR}/dist" && zip -r "windows.zip" "./${BINARY_NAME}.exe" ./assets - cd "${CI_PROJECT_DIR}/dist" && zip -r "windows.zip" "./${BINARY_NAME}.exe" ./assets
- cd "${CI_PROJECT_DIR}/dist" && zip -r "linux.x86.zip" "./${BINARY_NAME}" ./assets - cd "${CI_PROJECT_DIR}/dist" && zip -r "linux.x86.zip" "./${BINARY_NAME}" ./assets
- cd "${CI_PROJECT_DIR}/dist" && zip -r "linux.arm64.zip" "./${BINARY_NAME}.arm64" ./assets # - cd "${CI_PROJECT_DIR}/dist" && zip -r "linux.arm64.zip" "./${BINARY_NAME}.arm64" ./assets
- cd "${CI_PROJECT_DIR}/${BINARY_FOLDER}/dist" && zip -r "web.zip" ./* - cd "${CI_PROJECT_DIR}/${BINARY_FOLDER}/dist" && zip -r "web.zip" ./*
- cd "${CI_PROJECT_DIR}" && mv "${CI_PROJECT_DIR}/game_core/dist/web.zip" "${CI_PROJECT_DIR}/dist/web.zip" - cd "${CI_PROJECT_DIR}" && mv "${CI_PROJECT_DIR}/game_core/dist/web.zip" "${CI_PROJECT_DIR}/dist/web.zip"
dependencies: dependencies:
- build-windows - build-windows
- build-linux - build-linux
- build-arm64 # - build-arm64
- build-web - build-web
artifacts: artifacts:
expire_in: 7 days expire_in: 7 days
...@@ -129,7 +129,7 @@ package-all: ...@@ -129,7 +129,7 @@ package-all:
- dist/web.zip - dist/web.zip
- dist/windows.zip - dist/windows.zip
- dist/linux.x86.zip - dist/linux.x86.zip
- dist/linux.arm64.zip # - dist/linux.arm64.zip
only: only:
- trunk - trunk
......
...@@ -6,6 +6,9 @@ members = [ ...@@ -6,6 +6,9 @@ members = [
"game_core", "game_core",
] ]
[profile.dev.package."*"]
opt-level = 3
[workspace.dependencies] [workspace.dependencies]
fastrand = "1.8.0" fastrand = "1.8.0"
anyhow = "1.0.66" anyhow = "1.0.66"
...@@ -19,7 +22,7 @@ micro_musicbox = { version = "0.5.0", features = ["mp3"] } ...@@ -19,7 +22,7 @@ micro_musicbox = { version = "0.5.0", features = ["mp3"] }
micro_banimate = "0.2.1" micro_banimate = "0.2.1"
[workspace.dependencies.bevy] [workspace.dependencies.bevy]
version = "0.9.0" version = "0.9.1"
default-features = false default-features = false
features = [ features = [
"bevy_asset", "bevy_asset",
...@@ -32,7 +35,3 @@ features = [ ...@@ -32,7 +35,3 @@ features = [
"serialize", "serialize",
"filesystem_watcher" "filesystem_watcher"
] ]
[profile.release]
debug = 0
opt-level = 3
...@@ -22,10 +22,10 @@ assets: ...@@ -22,10 +22,10 @@ assets:
run: run:
RUSTFLAGS="-Awarnings" \ RUSTFLAGS="-Awarnings" \
cargo run --release --features "bevy/dynamic" -p game_core cargo run -p game_core
run-web: run-web:
cd game_core && trunk serve --release cd game_core && trunk serve
check: check:
cargo check --release --features "bevy/dynamic" -p game_core cargo check --release --features "bevy/dynamic" -p game_core
......
...@@ -12,6 +12,11 @@ document.addEventListener('DOMContentLoaded', function() { ...@@ -12,6 +12,11 @@ document.addEventListener('DOMContentLoaded', function() {
if (mutation.addedNodes.length > 0) { if (mutation.addedNodes.length > 0) {
for (const node of mutation.addedNodes) { for (const node of mutation.addedNodes) {
if (node.nodeName.toLowerCase() === 'canvas') { if (node.nodeName.toLowerCase() === 'canvas') {
let viewport = document.querySelector(`meta[name="viewport"]`)
if (viewport) {
viewport.content = 'height=720, width=1280, initial-scale=1, user-scalable=no'
}
node.focus(); node.focus();
if (window.focusHandler) { if (window.focusHandler) {
window.focusHandler.disconnect() window.focusHandler.disconnect()
......
window.originalFetch = window.fetch
window.sessionFetchCache = {}
window.sessionProgressState = {}
function fetchAndReportProgress(url) {
const outbound = new XMLHttpRequest()
let defer = {}
let promise = new Promise((resolve, reject) => {
defer = { resolve, reject }
})
outbound.onprogress = function(event) {
window.sessionProgressState[url] = event.lengthComputable ? {
indeterminate: false,
loaded: event.loaded,
total: event.total,
complete: event.loaded === event.total,
error: null,
} : {
indeterminate: true,
loaded: 0,
total: 0,
complete: false,
error: null
}
}
outbound.onerror = function(event) {
window.sessionProgressState[url].error = true
defer.reject(new Error("Failed to get"))
}
outbound.onloadstart = function(event) {
window.sessionProgressState[url] = {
indeterminate: !event.lengthComputable,
loaded: event.loaded,
total: event.total,
complete: false,
error: null,
}
}
outbound.onload = function(event) {
window.sessionProgressState[url] = {
indeterminate: !event.lengthComputable,
loaded: event.loaded,
total: event.total,
complete: true,
error: null,
}
window.sessionFetchCache[url] = new Uint8Array(outbound.response)
defer.resolve(window.sessionFetchCache[url])
}
outbound.responseType = "arraybuffer"
outbound.open("GET", url, true)
outbound.send()
return promise
}
function checkLoop(url) {
let defer = {}
let promise = new Promise((resolve, reject) => {
defer = { resolve, reject }
})
function inner() {
if (window.sessionFetchCache[url]) {
defer.resolve(window.sessionFetchCache[url])
} else if (window.sessionProgressState[url]) {
const val = window.sessionProgressState[url]
if (val.error) {
defer.reject(new Error("Failed to get"))
} else {
requestAnimationFrame(inner)
}
} else {
defer.reject(new Error("Missing entry"))
}
}
requestAnimationFrame(inner)
return promise
}
window.fetch = async function interceptedFetch(...params) {
if (params.length === 1 && typeof params[0] === "string") {
const path = params[0]
if (path.endsWith("wasm")) {
try {
const value = await checkLoop(path)
return new Response(value, {
headers: {},
status: 200,
statusText: 'ok'
})
} catch(_) {
return window.originalFetch(...params)
}
}
}
return window.originalFetch(...params)
}
window.interceptPreloads = function() {
let elems = document.querySelectorAll('link[rel="preload"][as="fetch"]')
const checks = []
elems.forEach(item => {
checks.push(item.href)
fetchAndReportProgress(item.href)
})
const start_container = document.getElementById('start_container')
for (const child of Array.from(start_container.children)) {
start_container.removeChild(child)
}
start_container.innerHTML = `<div style="width: 85%; height: 2.5rem; margin: auto; background-color: lightgray">
<div id="progressbar" style="width: 0%; height: 2.5rem; background-color: cornflowerblue"></div>
</div>`
function check_progress() {
let total_progress = 0
let total_total = 0
let is_complete = checks.every(url => window.sessionFetchCache.hasOwnProperty(url))
if (is_complete) {
document.getElementById('progressbar').style.width = `100%`
start_container.innerHTML = document.getElementById('content_loaded').innerHTML
window.attachStartListener()
} else {
for (const url of checks) {
let value = window.sessionProgressState[url]
console.log(value)
if (value) {
total_progress += value.loaded
total_total += value.total
}
}
const percent = Math.floor((total_progress / total_total) * 100)
document.getElementById('progressbar').style.width = `${percent}%`
requestAnimationFrame(check_progress)
}
}
check_progress()
}
...@@ -2,7 +2,7 @@ ...@@ -2,7 +2,7 @@
action = "wrap" action = "wrap"
template =''' template ='''
<script> <script>
document.addEventListener('DOMContentLoaded', () => { window.attachStartListener = function() {
document.getElementById('start_button').addEventListener('click', function() { document.getElementById('start_button').addEventListener('click', function() {
let element = document.createElement('{{{TAG}}}'); let element = document.createElement('{{{TAG}}}');
let attr_string = `{{{ATTR}}}` let attr_string = `{{{ATTR}}}`
...@@ -12,11 +12,15 @@ document.addEventListener('DOMContentLoaded', () => { ...@@ -12,11 +12,15 @@ document.addEventListener('DOMContentLoaded', () => {
}); });
element.innerHTML = `{{{CONTENT}}}`; element.innerHTML = `{{{CONTENT}}}`;
document.body.appendChild(element); document.body.appendChild(element);
const remove = ['start_container', 'init-styles'] const remove = ['start_container', 'init-styles', 'content_loaded']
remove.forEach(function(id) { remove.forEach(function(id) {
let container = document.getElementById(id); let container = document.getElementById(id);
container.parentNode.removeChild(container); container.parentNode.removeChild(container);
}); });
}); });
}); };
document.addEventListener('DOMContentLoaded', () => {
window.interceptPreloads()
})
</script>''' </script>'''
\ No newline at end of file
...@@ -4,10 +4,21 @@ ...@@ -4,10 +4,21 @@
<meta charset="utf-8"/> <meta charset="utf-8"/>
<title>Bevy 2D Template</title> <!-- TODO: Set game name --> <title>Bevy 2D Template</title> <!-- TODO: Set game name -->
<link data-trunk rel="copy-dir" href="../assets"/> <link data-trunk rel="copy-dir" href="../assets"/>
<meta name="viewport" content="width=device-width, initial-scale=1" />
<style> <style>
html, body { body,
html {
margin: 0; margin: 0;
padding: 0; padding: 0;
width: 100vw;
height: 100vh;
}
canvas {
display: block;
}
body {
overflow: hidden;
} }
</style> </style>
<style id="init-styles"> <style id="init-styles">
...@@ -16,9 +27,8 @@ ...@@ -16,9 +27,8 @@
} }
#start_container { #start_container {
width: auto; width: 100vw;
height: 100vh; height: 100vh;
aspect-ratio: 1;
display: flex; display: flex;
justify-content: center; justify-content: center;
align-items: center; align-items: center;
...@@ -47,8 +57,9 @@ ...@@ -47,8 +57,9 @@
} }
#start_button { #start_button {
width: 25%; width: auto;
height: 25%; height: 25%;
aspect-ratio: 1;
background-color: black; background-color: black;
border-radius: 50%; border-radius: 50%;
cursor: pointer; cursor: pointer;
...@@ -83,26 +94,27 @@ ...@@ -83,26 +94,27 @@
<body> <body>
<main id="start_container"> <main id="start_container">
</main>
<div style="display: none" id="content_loaded">
<svg <svg
width="512" viewBox="0 0 512 512"
height="512" id="start_button"
viewBox="0 0 512 512" xmlns="http://www.w3.org/2000/svg">
id="start_button"
xmlns="http://www.w3.org/2000/svg">
<path <path
class="play-button-component swircle" class="play-button-component swircle"
d="M 482.86983,256 A 226.86983,226.86983 0 0 1 256,482.86983 226.86983,226.86983 0 0 1 29.130173,256 226.86983,226.86983 0 0 1 256,29.130173 226.86983,226.86983 0 0 1 482.86983,256 Z"/> d="M 482.86983,256 A 226.86983,226.86983 0 0 1 256,482.86983 226.86983,226.86983 0 0 1 29.130173,256 226.86983,226.86983 0 0 1 256,29.130173 226.86983,226.86983 0 0 1 482.86983,256 Z"/>
<path <path
class="play-button-component swircle" class="play-button-component swircle"
d="M 447.06812,256 A 191.06812,191.06812 0 0 1 256,447.06812 191.06812,191.06812 0 0 1 64.931885,256 191.06812,191.06812 0 0 1 256,64.931885 191.06812,191.06812 0 0 1 447.06812,256 Z"/> d="M 447.06812,256 A 191.06812,191.06812 0 0 1 256,447.06812 191.06812,191.06812 0 0 1 64.931885,256 191.06812,191.06812 0 0 1 256,64.931885 191.06812,191.06812 0 0 1 447.06812,256 Z"/>
<path <path
class="play-button-component" class="play-button-component"
d="M 194.45831,348.47991 V 163.5198 l 159.08378,91.84706 -126.14795,72.83155 V 232.4989" /> d="M 194.45831,348.47991 V 163.5198 l 159.08378,91.84706 -126.14795,72.83155 V 232.4989" />
</svg> </svg>
<h1>Press Start To Play</h1> <h1>Press Start To Play</h1>
</main> </div>
<link data-trunk rel="inline" href="../build/web/intercept.js"/>
<link data-trunk rel="inline" href="../build/web/audio.js"/> <link data-trunk rel="inline" href="../build/web/audio.js"/>
<link data-trunk rel="inline" href="../build/web/autofocus.js"/> <link data-trunk rel="inline" href="../build/web/autofocus.js"/>
......
...@@ -4,3 +4,4 @@ pub mod load_config; ...@@ -4,3 +4,4 @@ pub mod load_config;
pub mod resources; pub mod resources;
pub mod utilities; pub mod utilities;
pub mod window; pub mod window;
pub mod web;
\ No newline at end of file
...@@ -43,6 +43,6 @@ pub fn configure_default_plugins() -> PluginGroupBuilder { ...@@ -43,6 +43,6 @@ pub fn configure_default_plugins() -> PluginGroupBuilder {
pub struct InitAppPlugins; pub struct InitAppPlugins;
impl PluginGroup for InitAppPlugins { impl PluginGroup for InitAppPlugins {
fn build(self) -> PluginGroupBuilder { fn build(self) -> PluginGroupBuilder {
configure_default_plugins().add(DefaultResourcesPlugin) configure_default_plugins().add(DefaultResourcesPlugin).add(super::web::WebPlugin)
} }
} }
#[cfg(target_arch = "wasm32")]
mod __plugin {
use bevy::app::{App, Plugin, CoreStage};
pub fn handle_startup_fullscreen() {
if micro_bevy_web_utils::bindings::is_touch_device() {
micro_bevy_web_utils::bindings::make_selector_fullscreen("canvas".to_string());
micro_bevy_web_utils::bindings::bind_selector_touch_events("canvas".to_string());
micro_bevy_web_utils::bindings::orientation_lock("landscape".to_string());
}
}
pub struct WebPlugin;
impl Plugin for WebPlugin {
fn build(&self, app: &mut App) {
app.add_startup_system(inner::handle_startup_fullscreen)
.add_system_to_stage(
CoreStage::First,
micro_bevy_web_utils::bevy::emit_touch_events,
);
}
}
}
#[cfg(not(target_arch = "wasm32"))]
mod __plugin {
use bevy::app::{App, Plugin};
pub struct WebPlugin;
impl Plugin for WebPlugin {
fn build(&self, app: &mut App) {}
}
}
pub use __plugin::WebPlugin;
\ No newline at end of file
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment