generated from lks/eframe_template_android
Upgrade egui and eframe to 0.31 and update all other dependencies
This commit is contained in:
parent
a8340a3fb9
commit
ab8abd635b
2982
Cargo.lock
generated
2982
Cargo.lock
generated
File diff suppressed because it is too large
Load Diff
23
Cargo.toml
23
Cargo.toml
@ -7,38 +7,39 @@ edition = "2021"
|
|||||||
|
|
||||||
# Common dependencies
|
# Common dependencies
|
||||||
[dependencies]
|
[dependencies]
|
||||||
anyhow = "1.0.83"
|
anyhow = "1.0.98"
|
||||||
cpal = "0.15.3"
|
cpal = "0.15.3"
|
||||||
egui = "0.27.0"
|
egui = "0.31"
|
||||||
egui_plot = "0.27.2"
|
egui_plot = "0.32"
|
||||||
log = "0.4.21"
|
log = "0.4.27"
|
||||||
realfft = "3.3.0"
|
realfft = "3.4.0"
|
||||||
|
|
||||||
# eframe features for non android targets
|
# eframe features for non android targets
|
||||||
[target.'cfg(not(target_os = "android"))'.dependencies.eframe]
|
[target.'cfg(not(target_os = "android"))'.dependencies.eframe]
|
||||||
version = "0.27.0"
|
version = "0.31"
|
||||||
default-features = false
|
default-features = false
|
||||||
features = ["accesskit", "default_fonts", "glow"]
|
features = ["accesskit", "default_fonts", "glow", "wayland", "x11"]
|
||||||
|
|
||||||
# eframe features for android targets
|
# eframe features for android targets
|
||||||
[target.'cfg(target_os = "android")'.dependencies.eframe]
|
[target.'cfg(target_os = "android")'.dependencies.eframe]
|
||||||
version = "0.27.0"
|
version = "0.31"
|
||||||
default-features = false
|
default-features = false
|
||||||
features = ["accesskit", "default_fonts", "glow", "android-native-activity"]
|
features = ["accesskit", "default_fonts", "glow", "android-native-activity"]
|
||||||
|
|
||||||
# android only dependencies
|
# android only dependencies
|
||||||
[target.'cfg(target_os = "android")'.dependencies]
|
[target.'cfg(target_os = "android")'.dependencies]
|
||||||
android_logger = "0.13.3"
|
android_logger = "0.15.0"
|
||||||
#android-activity = { version = "0.5", features = ["native-activity"] }
|
#android-activity = { version = "0.5", features = ["native-activity"] }
|
||||||
winit = { version = "0.29.4", features = ["android-native-activity"] }
|
winit = { version = "0.30.11", features = ["android-native-activity"] }
|
||||||
|
|
||||||
# native only dependencies
|
# native only dependencies
|
||||||
[target.'cfg(all(not(target_arch = "wasm32"), not(target_os = "android")))'.dependencies]
|
[target.'cfg(all(not(target_arch = "wasm32"), not(target_os = "android")))'.dependencies]
|
||||||
env_logger = "0.10"
|
env_logger = "0.11"
|
||||||
|
|
||||||
# web only dependencies
|
# web only dependencies
|
||||||
[target.'cfg(target_arch = "wasm32")'.dependencies]
|
[target.'cfg(target_arch = "wasm32")'.dependencies]
|
||||||
wasm-bindgen-futures = "0.4"
|
wasm-bindgen-futures = "0.4"
|
||||||
|
web-sys = "0.3.70" # to access the DOM (to hide the loading text)
|
||||||
|
|
||||||
[profile.release]
|
[profile.release]
|
||||||
opt-level = 2
|
opt-level = 2
|
||||||
|
|||||||
@ -3,18 +3,18 @@
|
|||||||
"short_name": "egui-template-pwa",
|
"short_name": "egui-template-pwa",
|
||||||
"icons": [
|
"icons": [
|
||||||
{
|
{
|
||||||
"src": "./icon-256.png",
|
"src": "./assets/icon-256.png",
|
||||||
"sizes": "256x256",
|
"sizes": "256x256",
|
||||||
"type": "image/png"
|
"type": "image/png"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"src": "./maskable_icon_x512.png",
|
"src": "./assets/maskable_icon_x512.png",
|
||||||
"sizes": "512x512",
|
"sizes": "512x512",
|
||||||
"type": "image/png",
|
"type": "image/png",
|
||||||
"purpose": "any maskable"
|
"purpose": "any maskable"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"src": "./icon-1024.png",
|
"src": "./assets/icon-1024.png",
|
||||||
"sizes": "1024x1024",
|
"sizes": "1024x1024",
|
||||||
"type": "image/png"
|
"type": "image/png"
|
||||||
}
|
}
|
||||||
|
|||||||
32
index.html
32
index.html
@ -17,16 +17,16 @@
|
|||||||
<link data-trunk rel="icon" href="assets/favicon.ico">
|
<link data-trunk rel="icon" href="assets/favicon.ico">
|
||||||
|
|
||||||
|
|
||||||
<link data-trunk rel="copy-file" href="assets/sw.js" />
|
<link data-trunk rel="copy-file" href="assets/sw.js"/>
|
||||||
<link data-trunk rel="copy-file" href="assets/manifest.json" />
|
<link data-trunk rel="copy-file" href="assets/manifest.json"/>
|
||||||
<link data-trunk rel="copy-file" href="assets/icon-1024.png" />
|
<link data-trunk rel="copy-file" href="assets/icon-1024.png" data-target-path="assets"/>
|
||||||
<link data-trunk rel="copy-file" href="assets/icon-256.png" />
|
<link data-trunk rel="copy-file" href="assets/icon-256.png" data-target-path="assets"/>
|
||||||
<link data-trunk rel="copy-file" href="assets/icon_ios_touch_192.png" />
|
<link data-trunk rel="copy-file" href="assets/icon_ios_touch_192.png" data-target-path="assets"/>
|
||||||
<link data-trunk rel="copy-file" href="assets/maskable_icon_x512.png" />
|
<link data-trunk rel="copy-file" href="assets/maskable_icon_x512.png" data-target-path="assets"/>
|
||||||
|
|
||||||
|
|
||||||
<link rel="manifest" href="manifest.json">
|
<link rel="manifest" href="manifest.json">
|
||||||
<link rel="apple-touch-icon" href="icon_ios_touch_192.png">
|
<link rel="apple-touch-icon" href="assets/icon_ios_touch_192.png">
|
||||||
<meta name="theme-color" media="(prefers-color-scheme: light)" content="white">
|
<meta name="theme-color" media="(prefers-color-scheme: light)" content="white">
|
||||||
<meta name="theme-color" media="(prefers-color-scheme: dark)" content="#404040">
|
<meta name="theme-color" media="(prefers-color-scheme: dark)" content="#404040">
|
||||||
|
|
||||||
@ -60,15 +60,16 @@
|
|||||||
width: 100%;
|
width: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Position canvas in center-top: */
|
/* Make canvas fill entire document: */
|
||||||
canvas {
|
canvas {
|
||||||
margin-right: auto;
|
margin-right: auto;
|
||||||
margin-left: auto;
|
margin-left: auto;
|
||||||
display: block;
|
display: block;
|
||||||
position: absolute;
|
position: absolute;
|
||||||
top: 0%;
|
top: 0;
|
||||||
left: 50%;
|
left: 0;
|
||||||
transform: translate(-50%, 0%);
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
.centered {
|
.centered {
|
||||||
@ -114,7 +115,6 @@
|
|||||||
transform: rotate(360deg);
|
transform: rotate(360deg);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
</style>
|
</style>
|
||||||
</head>
|
</head>
|
||||||
|
|
||||||
@ -123,6 +123,14 @@
|
|||||||
<!-- the id is hardcoded in main.rs . so, make sure both match. -->
|
<!-- the id is hardcoded in main.rs . so, make sure both match. -->
|
||||||
<canvas id="the_canvas_id"></canvas>
|
<canvas id="the_canvas_id"></canvas>
|
||||||
|
|
||||||
|
<!-- the loading spinner will be removed in main.rs -->
|
||||||
|
<div class="centered" id="loading_text">
|
||||||
|
<p style="font-size:16px">
|
||||||
|
Loading…
|
||||||
|
</p>
|
||||||
|
<div class="lds-dual-ring"></div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<!--Register Service Worker. this will cache the wasm / js scripts for offline use (for PWA functionality). -->
|
<!--Register Service Worker. this will cache the wasm / js scripts for offline use (for PWA functionality). -->
|
||||||
<!-- Force refresh (Ctrl + F5) to load the latest files instead of cached files -->
|
<!-- Force refresh (Ctrl + F5) to load the latest files instead of cached files -->
|
||||||
<script>
|
<script>
|
||||||
|
|||||||
@ -5,6 +5,6 @@
|
|||||||
# to the user in the error, instead of "error: invalid channel name '[toolchain]'".
|
# to the user in the error, instead of "error: invalid channel name '[toolchain]'".
|
||||||
|
|
||||||
[toolchain]
|
[toolchain]
|
||||||
channel = "1.76.0"
|
channel = "1.87.0"
|
||||||
components = [ "rustfmt", "clippy" ]
|
components = [ "rustfmt", "clippy" ]
|
||||||
targets = [ "wasm32-unknown-unknown", "aarch64-linux-android" ]
|
targets = [ "wasm32-unknown-unknown", "aarch64-linux-android" ]
|
||||||
|
|||||||
@ -104,7 +104,7 @@ impl eframe::App for TemplateApp {
|
|||||||
self.plots.render_menu_buttons(ui);
|
self.plots.render_menu_buttons(ui);
|
||||||
ui.add_space(16.0);
|
ui.add_space(16.0);
|
||||||
|
|
||||||
egui::widgets::global_dark_light_mode_buttons(ui);
|
egui::widgets::global_theme_preference_buttons(ui);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@ -82,9 +82,12 @@ impl DebugPlots {
|
|||||||
match plot {
|
match plot {
|
||||||
PlotData::U8(v) => {
|
PlotData::U8(v) => {
|
||||||
ui.heading("u8 Plot");
|
ui.heading("u8 Plot");
|
||||||
let line = Line::new(PlotPoints::from_iter(
|
let line = Line::new(
|
||||||
v.iter().enumerate().map(|(i, y)| [i as f64, *y as f64]),
|
"Data",
|
||||||
));
|
PlotPoints::from_iter(
|
||||||
|
v.iter().enumerate().map(|(i, y)| [i as f64, *y as f64]),
|
||||||
|
),
|
||||||
|
);
|
||||||
let plot = Plot::new(title);
|
let plot = Plot::new(title);
|
||||||
plot.show(ui, |plot_ui| {
|
plot.show(ui, |plot_ui| {
|
||||||
plot_ui.line(line);
|
plot_ui.line(line);
|
||||||
@ -96,7 +99,7 @@ impl DebugPlots {
|
|||||||
}
|
}
|
||||||
PlotData::F32(v) => {
|
PlotData::F32(v) => {
|
||||||
ui.heading("f32 plot");
|
ui.heading("f32 plot");
|
||||||
let line = Line::new(PlotPoints::from_ys_f32(&v));
|
let line = Line::new("Data", PlotPoints::from_ys_f32(&v));
|
||||||
let plot = Plot::new(title);
|
let plot = Plot::new(title);
|
||||||
plot.show(ui, |plot_ui| {
|
plot.show(ui, |plot_ui| {
|
||||||
plot_ui.line(line);
|
plot_ui.line(line);
|
||||||
@ -108,18 +111,23 @@ impl DebugPlots {
|
|||||||
}
|
}
|
||||||
PlotData::Bode32(v) => {
|
PlotData::Bode32(v) => {
|
||||||
ui.heading("Bode Plot");
|
ui.heading("Bode Plot");
|
||||||
let mag_line =
|
let mag_line = Line::new(
|
||||||
Line::new(PlotPoints::from_iter(v.iter().enumerate().map(|(i, c)| {
|
"Magnitude",
|
||||||
|
PlotPoints::from_iter(v.iter().enumerate().map(|(i, c)| {
|
||||||
[
|
[
|
||||||
i as f64,
|
i as f64,
|
||||||
((c.re * c.re) + (c.im * c.im)).sqrt() as f64 / v.len() as f64,
|
((c.re * c.re) + (c.im * c.im)).sqrt() as f64 / v.len() as f64,
|
||||||
]
|
]
|
||||||
})));
|
})),
|
||||||
let phase_line = Line::new(PlotPoints::from_iter(
|
);
|
||||||
v.iter()
|
let phase_line = Line::new(
|
||||||
.enumerate()
|
"Phase",
|
||||||
.map(|(i, c)| [i as f64, c.arg() as f64 / core::f64::consts::PI]),
|
PlotPoints::from_iter(
|
||||||
));
|
v.iter()
|
||||||
|
.enumerate()
|
||||||
|
.map(|(i, c)| [i as f64, c.arg() as f64 / core::f64::consts::PI]),
|
||||||
|
),
|
||||||
|
);
|
||||||
let plot = Plot::new(title);
|
let plot = Plot::new(title);
|
||||||
plot.show(ui, |plot_ui| {
|
plot.show(ui, |plot_ui| {
|
||||||
plot_ui.line(mag_line);
|
plot_ui.line(mag_line);
|
||||||
|
|||||||
@ -30,7 +30,7 @@ unsafe fn clear_texture(gl: &glow::Context, bytes_per_row: usize, n_rows: usize)
|
|||||||
1,
|
1,
|
||||||
glow::RED,
|
glow::RED,
|
||||||
glow::UNSIGNED_BYTE,
|
glow::UNSIGNED_BYTE,
|
||||||
PixelUnpackData::Slice(&blank_line),
|
PixelUnpackData::Slice(Some(&blank_line)),
|
||||||
);
|
);
|
||||||
check_for_gl_errors(&gl, &format!("clear texture with offset {}", offset));
|
check_for_gl_errors(&gl, &format!("clear texture with offset {}", offset));
|
||||||
}
|
}
|
||||||
@ -100,7 +100,7 @@ impl Waterfall {
|
|||||||
1,
|
1,
|
||||||
glow::RED,
|
glow::RED,
|
||||||
glow::UNSIGNED_BYTE,
|
glow::UNSIGNED_BYTE,
|
||||||
PixelUnpackData::Slice(&fft),
|
PixelUnpackData::Slice(Some(&fft)),
|
||||||
);
|
);
|
||||||
check_for_gl_errors(&gl, &format!("update texture with offset {}", self.offset));
|
check_for_gl_errors(&gl, &format!("update texture with offset {}", self.offset));
|
||||||
self.offset = (self.offset + 1) % self.height;
|
self.offset = (self.offset + 1) % self.height;
|
||||||
@ -215,7 +215,7 @@ impl Waterfall {
|
|||||||
glow::RED,
|
glow::RED,
|
||||||
glow::UNSIGNED_BYTE,
|
glow::UNSIGNED_BYTE,
|
||||||
//Some(&buffer), // This segfaults with large buffers
|
//Some(&buffer), // This segfaults with large buffers
|
||||||
None,
|
PixelUnpackData::Slice(None),
|
||||||
);
|
);
|
||||||
check_for_gl_errors(&gl, "Initializing Texture");
|
check_for_gl_errors(&gl, "Initializing Texture");
|
||||||
|
|
||||||
@ -246,7 +246,7 @@ impl Waterfall {
|
|||||||
0,
|
0,
|
||||||
glow::RGB,
|
glow::RGB,
|
||||||
UNSIGNED_BYTE,
|
UNSIGNED_BYTE,
|
||||||
Some(&turbo_colormap::TURBO_SRGB_BYTES),
|
PixelUnpackData::Slice(Some(&turbo_colormap::TURBO_SRGB_BYTES)),
|
||||||
);
|
);
|
||||||
check_for_gl_errors(&gl, "Initializing LUT");
|
check_for_gl_errors(&gl, "Initializing LUT");
|
||||||
|
|
||||||
|
|||||||
18
src/lib.rs
18
src/lib.rs
@ -7,7 +7,10 @@ mod backend;
|
|||||||
#[no_mangle]
|
#[no_mangle]
|
||||||
fn android_main(app: winit::platform::android::activity::AndroidApp) {
|
fn android_main(app: winit::platform::android::activity::AndroidApp) {
|
||||||
use winit::platform::android::activity::WindowManagerFlags;
|
use winit::platform::android::activity::WindowManagerFlags;
|
||||||
use winit::platform::android::EventLoopBuilderExtAndroid;
|
|
||||||
|
android_logger::init_once(
|
||||||
|
android_logger::Config::default().with_max_level(log::LevelFilter::Debug),
|
||||||
|
);
|
||||||
|
|
||||||
// Disable LAYOUT_IN_SCREEN to keep app from drawing under the status bar
|
// Disable LAYOUT_IN_SCREEN to keep app from drawing under the status bar
|
||||||
// winit does not currently do anything with MainEvent::InsetsChanged events
|
// winit does not currently do anything with MainEvent::InsetsChanged events
|
||||||
@ -18,18 +21,15 @@ fn android_main(app: winit::platform::android::activity::AndroidApp) {
|
|||||||
// Alternatively we can hide the system bars by setting the app to fullscreen
|
// Alternatively we can hide the system bars by setting the app to fullscreen
|
||||||
//app.set_window_flags(WindowManagerFlags::FULLSCREEN, WindowManagerFlags::empty());
|
//app.set_window_flags(WindowManagerFlags::FULLSCREEN, WindowManagerFlags::empty());
|
||||||
|
|
||||||
android_logger::init_once(
|
let options = eframe::NativeOptions {
|
||||||
android_logger::Config::default().with_max_level(log::LevelFilter::Debug),
|
android_app: Some(app),
|
||||||
);
|
..Default::default()
|
||||||
let mut options = eframe::NativeOptions::default();
|
};
|
||||||
options.event_loop_builder = Some(Box::new(move |builder| {
|
|
||||||
builder.with_android_app(app);
|
|
||||||
}));
|
|
||||||
|
|
||||||
let res = eframe::run_native(
|
let res = eframe::run_native(
|
||||||
"eframe template",
|
"eframe template",
|
||||||
options,
|
options,
|
||||||
Box::new(|cc| Box::new(app::TemplateApp::new(cc))),
|
Box::new(|cc| Ok(Box::new(app::TemplateApp::new(cc)))),
|
||||||
);
|
);
|
||||||
if let Err(e) = res {
|
if let Err(e) = res {
|
||||||
log::error!("{e:?}");
|
log::error!("{e:?}");
|
||||||
|
|||||||
39
src/main.rs
39
src/main.rs
@ -23,26 +23,53 @@ fn main() -> eframe::Result<()> {
|
|||||||
eframe::run_native(
|
eframe::run_native(
|
||||||
"eframe template",
|
"eframe template",
|
||||||
native_options,
|
native_options,
|
||||||
Box::new(|cc| Box::new(TemplateApp::new(cc))),
|
Box::new(|cc| Ok(Box::new(TemplateApp::new(cc)))),
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
// When compiling to web using trunk:
|
// When compiling to web using trunk:
|
||||||
#[cfg(target_arch = "wasm32")]
|
#[cfg(target_arch = "wasm32")]
|
||||||
fn main() {
|
fn main() {
|
||||||
|
use eframe::wasm_bindgen::JsCast as _;
|
||||||
|
|
||||||
// Redirect `log` message to `console.log` and friends:
|
// Redirect `log` message to `console.log` and friends:
|
||||||
eframe::WebLogger::init(log::LevelFilter::Debug).ok();
|
eframe::WebLogger::init(log::LevelFilter::Debug).ok();
|
||||||
|
|
||||||
let web_options = eframe::WebOptions::default();
|
let web_options = eframe::WebOptions::default();
|
||||||
|
|
||||||
wasm_bindgen_futures::spawn_local(async {
|
wasm_bindgen_futures::spawn_local(async {
|
||||||
eframe::WebRunner::new()
|
let document = web_sys::window()
|
||||||
|
.expect("No window")
|
||||||
|
.document()
|
||||||
|
.expect("No document");
|
||||||
|
|
||||||
|
let canvas = document
|
||||||
|
.get_element_by_id("the_canvas_id")
|
||||||
|
.expect("Failed to find the_canvas_id")
|
||||||
|
.dyn_into::<web_sys::HtmlCanvasElement>()
|
||||||
|
.expect("the_canvas_id was not a HtmlCanvasElement");
|
||||||
|
|
||||||
|
let start_result = eframe::WebRunner::new()
|
||||||
.start(
|
.start(
|
||||||
"the_canvas_id", // hardcode it
|
canvas,
|
||||||
web_options,
|
web_options,
|
||||||
Box::new(|cc| Box::new(TemplateApp::new(cc))),
|
Box::new(|cc| Ok(Box::new(TemplateApp::new(cc)))),
|
||||||
)
|
)
|
||||||
.await
|
.await;
|
||||||
.expect("failed to start eframe");
|
|
||||||
|
// Remove the loading text and spinner:
|
||||||
|
if let Some(loading_text) = document.get_element_by_id("loading_text") {
|
||||||
|
match start_result {
|
||||||
|
Ok(_) => {
|
||||||
|
loading_text.remove();
|
||||||
|
}
|
||||||
|
Err(e) => {
|
||||||
|
loading_text.set_inner_html(
|
||||||
|
"<p> The app has crashed. See the developer console for details. </p>",
|
||||||
|
);
|
||||||
|
panic!("Failed to start eframe: {e:?}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user