mirror of
https://github.com/YGGverse/Yoda.git
synced 2026-03-31 16:45:27 +00:00
implement Common identity as trait for AlertDialog
This commit is contained in:
parent
a6d84908cc
commit
fc8c967891
22 changed files with 131 additions and 175 deletions
|
|
@ -14,8 +14,8 @@ pub fn common(
|
|||
profile: &Rc<Profile>,
|
||||
request: &Uri,
|
||||
callback: &Rc<impl Fn(bool) + 'static>,
|
||||
) -> Common {
|
||||
Common::build(profile, request, callback)
|
||||
) -> AlertDialog {
|
||||
AlertDialog::common(profile, request, callback)
|
||||
}
|
||||
|
||||
/// Create new identity widget for unknown request
|
||||
|
|
|
|||
|
|
@ -1,38 +1,144 @@
|
|||
mod widget;
|
||||
use widget::Widget;
|
||||
mod action;
|
||||
pub mod form;
|
||||
|
||||
use super::Profile;
|
||||
use gtk::{glib::Uri, prelude::IsA};
|
||||
use action::Action as WidgetAction;
|
||||
use form::{list::item::value::Value, Form};
|
||||
|
||||
use crate::Profile;
|
||||
use adw::{
|
||||
prelude::{AlertDialogExt, AlertDialogExtManual},
|
||||
AlertDialog, ResponseAppearance,
|
||||
};
|
||||
use gtk::glib::Uri;
|
||||
use std::rc::Rc;
|
||||
|
||||
pub struct Common {
|
||||
// profile: Rc<Profile>,
|
||||
widget: Rc<Widget>,
|
||||
// Defaults
|
||||
const HEADING: &str = "Identity";
|
||||
const BODY: &str = "Select identity certificate";
|
||||
|
||||
// Response variants
|
||||
const RESPONSE_APPLY: (&str, &str) = ("apply", "Apply");
|
||||
const RESPONSE_CANCEL: (&str, &str) = ("cancel", "Cancel");
|
||||
// const RESPONSE_MANAGE: (&str, &str) = ("manage", "Manage");
|
||||
|
||||
// Select options
|
||||
|
||||
pub trait Common {
|
||||
fn common(profile: &Rc<Profile>, request: &Uri, callback: &Rc<impl Fn(bool) + 'static>)
|
||||
-> Self;
|
||||
}
|
||||
|
||||
impl Common {
|
||||
// Construct
|
||||
impl Common for AlertDialog {
|
||||
// Constructors
|
||||
|
||||
/// Create new `Self` for given `Profile`
|
||||
pub fn build(
|
||||
/// Create new `Self`
|
||||
fn common(
|
||||
profile: &Rc<Profile>,
|
||||
request: &Uri,
|
||||
callback: &Rc<impl Fn(bool) + 'static>,
|
||||
) -> Self {
|
||||
// Init widget
|
||||
let widget = Rc::new(Widget::build(profile, request, callback));
|
||||
// Init actions
|
||||
let action = Rc::new(WidgetAction::new());
|
||||
|
||||
// Return activated `Self`
|
||||
Self {
|
||||
// profile,
|
||||
widget,
|
||||
}
|
||||
}
|
||||
// Init child container
|
||||
let form = Rc::new(Form::build(&action, profile, request));
|
||||
|
||||
// Actions
|
||||
// Init main widget
|
||||
let alert_dialog = AlertDialog::builder()
|
||||
.heading(HEADING)
|
||||
.body(BODY)
|
||||
.close_response(RESPONSE_CANCEL.0)
|
||||
.default_response(RESPONSE_APPLY.0)
|
||||
.extra_child(&form.g_box)
|
||||
.build();
|
||||
|
||||
/// Show dialog for parent [Widget](https://docs.gtk.org/gtk4/class.Widget.html)
|
||||
pub fn present(&self, parent: Option<&impl IsA<gtk::Widget>>) {
|
||||
self.widget.present(parent);
|
||||
alert_dialog.add_responses(&[
|
||||
RESPONSE_CANCEL,
|
||||
// RESPONSE_MANAGE,
|
||||
RESPONSE_APPLY,
|
||||
]);
|
||||
|
||||
alert_dialog.connect_response(Some(RESPONSE_APPLY.0), {
|
||||
let callback = callback.clone();
|
||||
let form = form.clone();
|
||||
let profile = profile.clone();
|
||||
let request = request.clone();
|
||||
move |this, response| {
|
||||
// Prevent double-click action
|
||||
this.set_response_enabled(response, false);
|
||||
|
||||
// Get option match user choice
|
||||
let option = match form.list.selected().value_enum() {
|
||||
Value::ProfileIdentityId(value) => Some(value),
|
||||
Value::GuestSession => None,
|
||||
Value::GeneratePem => Some(
|
||||
profile
|
||||
.identity
|
||||
.make(None, &form.name.value().unwrap())
|
||||
.unwrap(), // @TODO handle
|
||||
),
|
||||
Value::ImportPem => Some(
|
||||
profile
|
||||
.identity
|
||||
.add(&form.file.pem.take().unwrap())
|
||||
.unwrap(), // @TODO handle
|
||||
),
|
||||
};
|
||||
|
||||
// Apply auth
|
||||
match option {
|
||||
// Activate identity for `scope`
|
||||
Some(profile_identity_id) => {
|
||||
if profile
|
||||
.identity
|
||||
.auth
|
||||
.apply(profile_identity_id, &request.to_string())
|
||||
.is_err()
|
||||
{
|
||||
panic!() // unexpected @TODO
|
||||
}
|
||||
}
|
||||
// Remove all identity auths for `scope`
|
||||
None => {
|
||||
if profile.identity.auth.remove(&request.to_string()).is_err() {
|
||||
panic!() // unexpected @TODO
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Run callback function
|
||||
callback(true)
|
||||
}
|
||||
});
|
||||
|
||||
// Deactivate not implemented feature @TODO
|
||||
// alert_dialog.set_response_enabled(RESPONSE_MANAGE.0, false);
|
||||
|
||||
// Decorate default response preset
|
||||
alert_dialog.set_response_appearance(RESPONSE_APPLY.0, ResponseAppearance::Suggested);
|
||||
/* contrast issue with Ubuntu orange accents
|
||||
alert_dialog.set_response_appearance(RESPONSE_CANCEL.0, ResponseAppearance::Destructive); */
|
||||
|
||||
// Init events
|
||||
action.update.connect_activate({
|
||||
let form = form.clone();
|
||||
let callback = callback.clone();
|
||||
let alert_dialog = alert_dialog.clone();
|
||||
move || {
|
||||
// Update child components
|
||||
form.update();
|
||||
|
||||
// Deactivate apply button if the form values could not be processed
|
||||
alert_dialog.set_response_enabled(RESPONSE_APPLY.0, form.is_applicable());
|
||||
|
||||
callback(false);
|
||||
}
|
||||
});
|
||||
|
||||
// Make initial update
|
||||
action.update.activate();
|
||||
|
||||
// Return new activated `Self`
|
||||
alert_dialog
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,150 +0,0 @@
|
|||
mod action;
|
||||
pub mod form;
|
||||
|
||||
use action::Action as WidgetAction;
|
||||
use form::{list::item::value::Value, Form};
|
||||
|
||||
use crate::Profile;
|
||||
use adw::{
|
||||
prelude::{AdwDialogExt, AlertDialogExt, AlertDialogExtManual},
|
||||
AlertDialog, ResponseAppearance,
|
||||
};
|
||||
use gtk::{glib::Uri, prelude::IsA};
|
||||
use std::rc::Rc;
|
||||
|
||||
// Defaults
|
||||
const HEADING: &str = "Identity";
|
||||
const BODY: &str = "Select identity certificate";
|
||||
|
||||
// Response variants
|
||||
const RESPONSE_APPLY: (&str, &str) = ("apply", "Apply");
|
||||
const RESPONSE_CANCEL: (&str, &str) = ("cancel", "Cancel");
|
||||
// const RESPONSE_MANAGE: (&str, &str) = ("manage", "Manage");
|
||||
|
||||
// Select options
|
||||
|
||||
pub struct Widget {
|
||||
alert_dialog: AlertDialog,
|
||||
}
|
||||
|
||||
impl Widget {
|
||||
// Constructors
|
||||
|
||||
/// Create new `Self`
|
||||
pub fn build(
|
||||
profile: &Rc<Profile>,
|
||||
request: &Uri,
|
||||
callback: &Rc<impl Fn(bool) + 'static>,
|
||||
) -> Self {
|
||||
// Init actions
|
||||
let action = Rc::new(WidgetAction::new());
|
||||
|
||||
// Init child container
|
||||
let form = Rc::new(Form::build(&action, profile, request));
|
||||
|
||||
// Init main widget
|
||||
let alert_dialog = AlertDialog::builder()
|
||||
.heading(HEADING)
|
||||
.body(BODY)
|
||||
.close_response(RESPONSE_CANCEL.0)
|
||||
.default_response(RESPONSE_APPLY.0)
|
||||
.extra_child(&form.g_box)
|
||||
.build();
|
||||
|
||||
alert_dialog.add_responses(&[
|
||||
RESPONSE_CANCEL,
|
||||
// RESPONSE_MANAGE,
|
||||
RESPONSE_APPLY,
|
||||
]);
|
||||
|
||||
alert_dialog.connect_response(Some(RESPONSE_APPLY.0), {
|
||||
let callback = callback.clone();
|
||||
let form = form.clone();
|
||||
let profile = profile.clone();
|
||||
let request = request.clone();
|
||||
move |this, response| {
|
||||
// Prevent double-click action
|
||||
this.set_response_enabled(response, false);
|
||||
|
||||
// Get option match user choice
|
||||
let option = match form.list.selected().value_enum() {
|
||||
Value::ProfileIdentityId(value) => Some(value),
|
||||
Value::GuestSession => None,
|
||||
Value::GeneratePem => Some(
|
||||
profile
|
||||
.identity
|
||||
.make(None, &form.name.value().unwrap())
|
||||
.unwrap(), // @TODO handle
|
||||
),
|
||||
Value::ImportPem => Some(
|
||||
profile
|
||||
.identity
|
||||
.add(&form.file.pem.take().unwrap())
|
||||
.unwrap(), // @TODO handle
|
||||
),
|
||||
};
|
||||
|
||||
// Apply auth
|
||||
match option {
|
||||
// Activate identity for `scope`
|
||||
Some(profile_identity_id) => {
|
||||
if profile
|
||||
.identity
|
||||
.auth
|
||||
.apply(profile_identity_id, &request.to_string())
|
||||
.is_err()
|
||||
{
|
||||
panic!() // unexpected @TODO
|
||||
}
|
||||
}
|
||||
// Remove all identity auths for `scope`
|
||||
None => {
|
||||
if profile.identity.auth.remove(&request.to_string()).is_err() {
|
||||
panic!() // unexpected @TODO
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Run callback function
|
||||
callback(true)
|
||||
}
|
||||
});
|
||||
|
||||
// Deactivate not implemented feature @TODO
|
||||
// alert_dialog.set_response_enabled(RESPONSE_MANAGE.0, false);
|
||||
|
||||
// Decorate default response preset
|
||||
alert_dialog.set_response_appearance(RESPONSE_APPLY.0, ResponseAppearance::Suggested);
|
||||
/* contrast issue with Ubuntu orange accents
|
||||
alert_dialog.set_response_appearance(RESPONSE_CANCEL.0, ResponseAppearance::Destructive); */
|
||||
|
||||
// Init events
|
||||
action.update.connect_activate({
|
||||
let form = form.clone();
|
||||
let callback = callback.clone();
|
||||
let alert_dialog = alert_dialog.clone();
|
||||
move || {
|
||||
// Update child components
|
||||
form.update();
|
||||
|
||||
// Deactivate apply button if the form values could not be processed
|
||||
alert_dialog.set_response_enabled(RESPONSE_APPLY.0, form.is_applicable());
|
||||
|
||||
callback(false);
|
||||
}
|
||||
});
|
||||
|
||||
// Make initial update
|
||||
action.update.activate();
|
||||
|
||||
// Return new activated `Self`
|
||||
Self { alert_dialog }
|
||||
}
|
||||
|
||||
// Actions
|
||||
|
||||
/// Show dialog with new preset
|
||||
pub fn present(&self, parent: Option<&impl IsA<gtk::Widget>>) {
|
||||
self.alert_dialog.present(parent)
|
||||
}
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue