use wgpu::SurfaceError;
use super::{SettingsWindow, SettingsWindowAction};
use crate::settings_ui::UpdateCheckResult;
impl SettingsWindow {
pub(super) fn render(&mut self) -> SettingsWindowAction {
if !self.ready {
return SettingsWindowAction::None;
}
let output = match self.surface.get_current_texture() {
Ok(output) => output,
Err(SurfaceError::Lost | SurfaceError::Outdated) => {
self.surface.configure(&self.device, &self.surface_config);
return SettingsWindowAction::None;
}
Err(SurfaceError::Timeout) => {
log::warn!("Settings window surface timeout");
return SettingsWindowAction::None;
}
Err(e) => {
log::error!("Settings window surface error: {:?}", e);
return SettingsWindowAction::None;
}
};
let view = output
.texture
.create_view(&wgpu::TextureViewDescriptor::default());
let mut config_to_save = None;
let mut config_for_live = None;
let mut shader_apply = None;
let mut cursor_shader_apply = None;
let mut raw_input = self.egui_state.take_egui_input(&self.window);
if let Some(text) = self.pending_paste.take() {
raw_input.events.push(egui::Event::Paste(text));
}
raw_input.events.append(&mut self.pending_events);
let egui_output = self.egui_ctx.run(raw_input, |ctx| {
let (save, live, shader, cursor_shader) = self.settings_ui.show_as_panel(ctx);
config_to_save = save;
config_for_live = live;
shader_apply = shader;
cursor_shader_apply = cursor_shader;
});
if self.settings_ui.test_detection_requested {
self.settings_ui.test_detection_requested = false;
let preceding_cmd = if self.settings_ui.test_detection_command.is_empty() {
None
} else {
Some(self.settings_ui.test_detection_command.as_str())
};
let result = crate::prettifier::config_bridge::test_detection(
&self.settings_ui.config,
&self.settings_ui.test_detection_content,
preceding_cmd,
);
self.settings_ui.test_detection_result = Some((
result.format_id,
result.confidence,
result.matched_rules,
result.threshold,
));
}
for cmd in &egui_output.platform_output.commands {
match cmd {
egui::OutputCommand::CopyText(text) => {
if let Ok(mut clipboard) = arboard::Clipboard::new()
&& let Err(e) = clipboard.set_text(text)
{
log::warn!("Settings window: failed to copy to clipboard: {}", e);
}
}
egui::OutputCommand::CopyImage(_) => {}
_ => {}
}
}
self.egui_state
.handle_platform_output(&self.window, egui_output.platform_output.clone());
let paint_jobs = self
.egui_ctx
.tessellate(egui_output.shapes, self.egui_ctx.pixels_per_point());
for (id, delta) in &egui_output.textures_delta.set {
self.egui_renderer
.update_texture(&self.device, &self.queue, *id, delta);
}
let mut encoder = self
.device
.create_command_encoder(&wgpu::CommandEncoderDescriptor {
label: Some("Settings Window Encoder"),
});
let screen_descriptor = egui_wgpu::ScreenDescriptor {
size_in_pixels: [self.surface_config.width, self.surface_config.height],
pixels_per_point: self.window.scale_factor() as f32,
};
self.egui_renderer.update_buffers(
&self.device,
&self.queue,
&mut encoder,
&paint_jobs,
&screen_descriptor,
);
{
let render_pass = encoder.begin_render_pass(&wgpu::RenderPassDescriptor {
label: Some("Settings Window Render Pass"),
color_attachments: &[Some(wgpu::RenderPassColorAttachment {
view: &view,
resolve_target: None,
ops: wgpu::Operations {
load: wgpu::LoadOp::Clear(wgpu::Color {
r: 0.094,
g: 0.094,
b: 0.094,
a: 1.0,
}),
store: wgpu::StoreOp::Store,
},
depth_slice: None,
})],
depth_stencil_attachment: None,
timestamp_writes: None,
occlusion_query_set: None,
});
let mut render_pass = render_pass.forget_lifetime();
self.egui_renderer
.render(&mut render_pass, &paint_jobs, &screen_descriptor);
}
self.queue.submit(std::iter::once(encoder.finish()));
output.present();
for id in &egui_output.textures_delta.free {
self.egui_renderer.free_texture(id);
}
if self.settings_ui.take_test_notification_request() {
return SettingsWindowAction::TestNotification;
}
if let Some(profiles) = self.settings_ui.take_profile_save_request() {
self.window.request_redraw();
return SettingsWindowAction::SaveProfiles(profiles);
}
if let Some(id) = self.settings_ui.take_profile_open_request() {
self.window.request_redraw();
return SettingsWindowAction::OpenProfile(id);
}
if self.settings_ui.open_log_requested {
self.settings_ui.open_log_requested = false;
return SettingsWindowAction::OpenLogFile;
}
if self.settings_ui.check_now_requested {
self.settings_ui.check_now_requested = false;
self.window.request_redraw();
return SettingsWindowAction::ForceUpdateCheck;
}
if self.settings_ui.update_install_requested {
self.settings_ui.update_install_requested = false;
if let Some(UpdateCheckResult::UpdateAvailable(ref info)) =
self.settings_ui.last_update_result
{
let version = info
.version
.strip_prefix('v')
.unwrap_or(&info.version)
.to_string();
self.settings_ui
.start_self_update_with(version.clone(), |v| {
crate::self_updater::perform_update(v, crate::VERSION).map(|r| {
crate::settings_ui::UpdateResult {
old_version: r.old_version,
new_version: r.new_version,
install_path: r.install_path.display().to_string(),
needs_restart: r.needs_restart,
}
})
});
self.window.request_redraw();
return SettingsWindowAction::InstallUpdate(version);
}
}
self.settings_ui.poll_update_install_status();
if let Some((index, start)) = self.settings_ui.pending_coprocess_actions.pop() {
log::info!(
"Settings window: popped coprocess action index={} start={}",
index,
start
);
self.window.request_redraw();
return if start {
SettingsWindowAction::StartCoprocess(index)
} else {
SettingsWindowAction::StopCoprocess(index)
};
}
if let Some((index, start)) = self.settings_ui.pending_script_actions.pop() {
crate::debug_info!(
"SCRIPT",
"Settings window: popped script action index={} start={}",
index,
start
);
self.window.request_redraw();
return if start {
SettingsWindowAction::StartScript(index)
} else {
SettingsWindowAction::StopScript(index)
};
}
if let Some(action) = self.settings_ui.pending_arrangement_actions.pop() {
self.window.request_redraw();
return action;
}
if self.settings_ui.identify_panes_requested {
self.settings_ui.identify_panes_requested = false;
self.window.request_redraw();
return SettingsWindowAction::IdentifyPanes;
}
if let Some(action) = self.settings_ui.shell_integration_action.take() {
self.window.request_redraw();
return match action {
crate::settings_ui::integrations_tab::ShellIntegrationAction::Install => {
SettingsWindowAction::InstallShellIntegration
}
crate::settings_ui::integrations_tab::ShellIntegrationAction::Uninstall => {
SettingsWindowAction::UninstallShellIntegration
}
};
}
if let Some(config) = config_to_save {
return SettingsWindowAction::SaveConfig(config);
}
if let Some(shader_result) = shader_apply {
return SettingsWindowAction::ApplyShader(shader_result);
}
if let Some(cursor_shader_result) = cursor_shader_apply {
return SettingsWindowAction::ApplyCursorShader(cursor_shader_result);
}
if let Some(config) = config_for_live {
return SettingsWindowAction::ApplyConfig(config);
}
SettingsWindowAction::None
}
}