feat: Add wifi and bluetooth device switching

This commit is contained in:
Fabio Lenherr / DashieTM 2023-12-03 19:08:07 +01:00
parent b2b4ae0661
commit 959d1e735f
8 changed files with 281 additions and 101 deletions

View file

@ -6,7 +6,7 @@ description = "A wip universal Linux settings application."
[dependencies] [dependencies]
reset_daemon = "0.3.3" reset_daemon = "0.3.3"
ReSet-Lib = "0.5.5" ReSet-Lib = "0.6.1"
adw = { version = "0.5.3", package = "libadwaita", features = ["v1_4"] } adw = { version = "0.5.3", package = "libadwaita", features = ["v1_4"] }
dbus = "0.9.7" dbus = "0.9.7"
gtk = { version = "0.7.3", package = "gtk4", features = ["v4_12"] } gtk = { version = "0.7.3", package = "gtk4", features = ["v4_12"] }

View file

@ -5,14 +5,16 @@ use std::time::{Duration, SystemTime};
use adw::glib; use adw::glib;
use adw::glib::Object; use adw::glib::Object;
use adw::prelude::ComboRowExt;
use adw::subclass::prelude::ObjectSubclassIsExt; use adw::subclass::prelude::ObjectSubclassIsExt;
use dbus::blocking::Connection; use dbus::blocking::Connection;
use dbus::message::SignalArgs; use dbus::message::SignalArgs;
use dbus::{Error, Path}; use dbus::{Error, Path};
use gtk::gio; use glib::{clone, Cast};
use gtk::glib::Variant; use gtk::glib::Variant;
use gtk::prelude::{ActionableExt, ListBoxRowExt, WidgetExt}; use gtk::prelude::{ActionableExt, ListBoxRowExt, WidgetExt};
use ReSet_Lib::bluetooth::bluetooth::BluetoothDevice; use gtk::{gio, StringObject};
use ReSet_Lib::bluetooth::bluetooth::{BluetoothAdapter, BluetoothDevice};
use ReSet_Lib::signals::{BluetoothDeviceAdded, BluetoothDeviceChanged, BluetoothDeviceRemoved}; use ReSet_Lib::signals::{BluetoothDeviceAdded, BluetoothDeviceChanged, BluetoothDeviceRemoved};
use crate::components::base::listEntry::ListEntry; use crate::components::base::listEntry::ListEntry;
@ -68,10 +70,50 @@ pub fn populate_conntected_bluetooth_devices(bluetooth_box: Arc<BluetoothBox>) {
gio::spawn_blocking(move || { gio::spawn_blocking(move || {
let ref_box = bluetooth_box.clone(); let ref_box = bluetooth_box.clone();
let devices = get_connected_devices(); let devices = get_connected_devices();
let adapters = get_bluetooth_adapters();
{
let imp = bluetooth_box.imp();
let list = imp.resetModelList.write().unwrap();
let mut model_index = imp.resetModelIndex.write().unwrap();
let mut map = imp.resetBluetoothAdapters.write().unwrap();
imp.resetCurrentBluetoothAdapter
.replace(adapters.last().unwrap().clone());
for (index, adapter) in adapters.into_iter().enumerate() {
list.append(&adapter.alias);
map.insert(adapter.alias.clone(), (adapter, index as u32));
*model_index += 1;
}
}
glib::spawn_future(async move { glib::spawn_future(async move {
glib::idle_add_once(move || { glib::idle_add_once(move || {
let imp = ref_box.imp(); let imp = ref_box.imp();
let list = imp.resetModelList.read().unwrap();
imp.resetBluetoothAdapter.set_model(Some(&*list));
let map = imp.resetBluetoothAdapters.read().unwrap();
let device = imp.resetCurrentBluetoothAdapter.borrow();
if let Some(index) = map.get(&device.alias) {
imp.resetBluetoothAdapter.set_selected(index.1);
}
imp.resetBluetoothAdapter.connect_selected_notify(
clone!(@weak imp => move |dropdown| {
let selected = dropdown.selected_item();
if selected.is_none() {
return;
}
let selected = selected.unwrap();
let selected = selected.downcast_ref::<StringObject>().unwrap();
let selected = selected.string().to_string();
let device = imp.resetBluetoothAdapters.read().unwrap();
let device = device.get(&selected);
if device.is_none() {
return;
}
set_bluetooth_adapter(device.unwrap().0.path.clone());
}),
);
for device in devices { for device in devices {
let path = device.path.clone(); let path = device.path.clone();
let connected = device.connected; let connected = device.connected;
@ -252,3 +294,29 @@ fn get_connected_devices() -> Vec<BluetoothDevice> {
} }
res.unwrap().0 res.unwrap().0
} }
fn get_bluetooth_adapters() -> Vec<BluetoothAdapter> {
let conn = Connection::new_session().unwrap();
let proxy = conn.with_proxy(
"org.Xetibo.ReSetDaemon",
"/org/Xetibo/ReSetDaemon",
Duration::from_millis(1000),
);
let res: Result<(Vec<BluetoothAdapter>,), Error> =
proxy.method_call("org.Xetibo.ReSetBluetooth", "GetBluetoothAdapters", ());
if res.is_err() {
return Vec::new();
}
res.unwrap().0
}
fn set_bluetooth_adapter(path: Path<'static>) {
let conn = Connection::new_session().unwrap();
let proxy = conn.with_proxy(
"org.Xetibo.ReSetDaemon",
"/org/Xetibo/ReSetDaemon",
Duration::from_millis(1000),
);
let _: Result<(Vec<BluetoothAdapter>,), Error> =
proxy.method_call("org.Xetibo.ReSetBluetooth", "SetBluetoothAdapter", (path,));
}

View file

@ -1,12 +1,12 @@
use adw::ActionRow; use adw::{ActionRow, ComboRow};
use dbus::Path; use dbus::Path;
use gtk::prelude::*;
use gtk::subclass::prelude::*; use gtk::subclass::prelude::*;
use gtk::{glib, CompositeTemplate, ListBox, Switch}; use gtk::{glib, CompositeTemplate, ListBox, Switch};
use gtk::{prelude::*, StringList};
use std::cell::RefCell; use std::cell::RefCell;
use std::collections::HashMap; use std::collections::HashMap;
use std::sync::Arc; use std::sync::{Arc, RwLock};
use ReSet_Lib::bluetooth::bluetooth::BluetoothDevice; use ReSet_Lib::bluetooth::bluetooth::{BluetoothAdapter, BluetoothDevice};
use crate::components::base::listEntry::ListEntry; use crate::components::base::listEntry::ListEntry;
use crate::components::bluetooth::bluetoothBox; use crate::components::bluetooth::bluetoothBox;
@ -24,6 +24,8 @@ pub struct BluetoothBox {
#[template_child] #[template_child]
pub resetBluetoothAvailableDevices: TemplateChild<ListBox>, pub resetBluetoothAvailableDevices: TemplateChild<ListBox>,
#[template_child] #[template_child]
pub resetBluetoothAdapter: TemplateChild<ComboRow>,
#[template_child]
pub resetBluetoothConnectedDevices: TemplateChild<ListBox>, pub resetBluetoothConnectedDevices: TemplateChild<ListBox>,
#[template_child] #[template_child]
pub resetVisibility: TemplateChild<ActionRow>, pub resetVisibility: TemplateChild<ActionRow>,
@ -31,6 +33,10 @@ pub struct BluetoothBox {
pub resetBluetoothMainTab: TemplateChild<ListEntry>, pub resetBluetoothMainTab: TemplateChild<ListEntry>,
pub availableDevices: BluetoothMap, pub availableDevices: BluetoothMap,
pub connectedDevices: BluetoothMap, pub connectedDevices: BluetoothMap,
pub resetBluetoothAdapters: Arc<RwLock<HashMap<String, (BluetoothAdapter, u32)>>>,
pub resetCurrentBluetoothAdapter: Arc<RefCell<BluetoothAdapter>>,
pub resetModelList: Arc<RwLock<StringList>>,
pub resetModelIndex: Arc<RwLock<u32>>,
} }
#[glib::object_subclass] #[glib::object_subclass]

View file

@ -8,18 +8,18 @@ use crate::components::base::utils::Listeners;
use crate::components::utils::setComboRowEllipsis; use crate::components::utils::setComboRowEllipsis;
use adw::glib; use adw::glib;
use adw::glib::Object; use adw::glib::Object;
use adw::prelude::{ListBoxRowExt, PreferencesGroupExt}; use adw::prelude::{ComboRowExt, ListBoxRowExt, PreferencesGroupExt};
use adw::subclass::prelude::ObjectSubclassIsExt; use adw::subclass::prelude::ObjectSubclassIsExt;
use dbus::blocking::Connection; use dbus::blocking::Connection;
use dbus::message::SignalArgs; use dbus::message::SignalArgs;
use dbus::Error; use dbus::Error;
use dbus::Path; use dbus::Path;
use glib::{clone, PropertySet}; use glib::{clone, Cast, PropertySet};
use gtk::gio;
use gtk::glib::Variant; use gtk::glib::Variant;
use gtk::prelude::{ActionableExt, WidgetExt}; use gtk::prelude::{ActionableExt, WidgetExt};
use ReSet_Lib::network::network::{AccessPoint, WifiStrength}; use gtk::{gio, StringObject};
use ReSet_Lib::signals::AccessPointAdded; use ReSet_Lib::network::network::{AccessPoint, WifiDevice, WifiStrength};
use ReSet_Lib::signals::{AccessPointAdded, WifiDeviceChanged};
use ReSet_Lib::signals::{AccessPointChanged, AccessPointRemoved}; use ReSet_Lib::signals::{AccessPointChanged, AccessPointRemoved};
use crate::components::wifi::wifiBoxImpl; use crate::components::wifi::wifiBoxImpl;
@ -90,6 +90,20 @@ pub fn scanForWifi(wifiBox: Arc<WifiBox>) {
gio::spawn_blocking(move || { gio::spawn_blocking(move || {
let accessPoints = get_access_points(); let accessPoints = get_access_points();
let devices = get_wifi_devices();
{
let imp = wifibox_ref.imp();
let list = imp.resetModelList.write().unwrap();
let mut model_index = imp.resetModelIndex.write().unwrap();
let mut map = imp.resetWifiDevices.write().unwrap();
imp.resetCurrentWifiDevice
.replace(devices.last().unwrap().clone());
for (index, device) in devices.into_iter().enumerate() {
list.append(&device.name);
map.insert(device.name.clone(), (device, index as u32));
*model_index += 1;
}
}
let wifiEntries = wifiEntries.clone(); let wifiEntries = wifiEntries.clone();
let wifiEntriesPath = wifiEntriesPath.clone(); let wifiEntriesPath = wifiEntriesPath.clone();
dbus_start_network_events(); dbus_start_network_events();
@ -97,14 +111,40 @@ pub fn scanForWifi(wifiBox: Arc<WifiBox>) {
glib::idle_add_once(move || { glib::idle_add_once(move || {
let mut wifiEntries = wifiEntries.lock().unwrap(); let mut wifiEntries = wifiEntries.lock().unwrap();
let mut wifiEntriesPath = wifiEntriesPath.lock().unwrap(); let mut wifiEntriesPath = wifiEntriesPath.lock().unwrap();
let selfImp = wifibox_ref.imp(); let imp = wifibox_ref.imp();
let list = imp.resetModelList.read().unwrap();
imp.resetWiFiDevice.set_model(Some(&*list));
let map = imp.resetWifiDevices.read().unwrap();
let device = imp.resetCurrentWifiDevice.borrow();
if let Some(index) = map.get(&device.name) {
imp.resetWiFiDevice.set_selected(index.1);
}
imp.resetWiFiDevice
.connect_selected_notify(clone!(@weak imp => move |dropdown| {
let selected = dropdown.selected_item();
if selected.is_none() {
return;
}
let selected = selected.unwrap();
let selected = selected.downcast_ref::<StringObject>().unwrap();
let selected = selected.string().to_string();
let device = imp.resetWifiDevices.read().unwrap();
let device = device.get(&selected);
if device.is_none() {
return;
}
set_wifi_device(device.unwrap().0.path.clone());
}));
for accessPoint in accessPoints { for accessPoint in accessPoints {
let ssid = accessPoint.ssid.clone(); let ssid = accessPoint.ssid.clone();
let path = accessPoint.dbus_path.clone(); let path = accessPoint.dbus_path.clone();
let entry = WifiEntry::new(accessPoint, selfImp); let connected = imp.resetCurrentWifiDevice.borrow().active_access_point == path;
let entry = WifiEntry::new(connected, accessPoint, imp);
wifiEntries.insert(ssid, entry.clone()); wifiEntries.insert(ssid, entry.clone());
wifiEntriesPath.insert(path, entry.clone()); wifiEntriesPath.insert(path, entry.clone());
selfImp.resetWifiList.add(&*entry); imp.resetWifiList.add(&*entry);
} }
}); });
}); });
@ -157,6 +197,33 @@ pub fn get_access_points() -> Vec<AccessPoint> {
accessPoints accessPoints
} }
pub fn set_wifi_device(path: Path<'static>) {
let conn = Connection::new_session().unwrap();
let proxy = conn.with_proxy(
"org.Xetibo.ReSetDaemon",
"/org/Xetibo/ReSetDaemon",
Duration::from_millis(1000),
);
let _: Result<(bool,), Error> =
proxy.method_call("org.Xetibo.ReSetWireless", "SetWifiDevice", (path,));
}
pub fn get_wifi_devices() -> Vec<WifiDevice> {
let conn = Connection::new_session().unwrap();
let proxy = conn.with_proxy(
"org.Xetibo.ReSetDaemon",
"/org/Xetibo/ReSetDaemon",
Duration::from_millis(1000),
);
let res: Result<(Vec<WifiDevice>,), Error> =
proxy.method_call("org.Xetibo.ReSetWireless", "GetAllWifiDevices", ());
if res.is_err() {
return Vec::new();
}
let (devices,) = res.unwrap();
devices
}
pub fn get_stored_connections() -> Vec<(Path<'static>, Vec<u8>)> { pub fn get_stored_connections() -> Vec<(Path<'static>, Vec<u8>)> {
let conn = Connection::new_session().unwrap(); let conn = Connection::new_session().unwrap();
let proxy = conn.with_proxy( let proxy = conn.with_proxy(
@ -195,6 +262,7 @@ pub fn start_event_listener(listeners: Arc<Listeners>, wifi_box: Arc<WifiBox>) {
let added_ref = wifi_box.clone(); let added_ref = wifi_box.clone();
let removed_ref = wifi_box.clone(); let removed_ref = wifi_box.clone();
let changed_ref = wifi_box.clone(); let changed_ref = wifi_box.clone();
let wifi_changed_ref = wifi_box.clone();
let access_point_added = AccessPointAdded::match_rule( let access_point_added = AccessPointAdded::match_rule(
Some(&"org.Xetibo.ReSetDaemon".into()), Some(&"org.Xetibo.ReSetDaemon".into()),
Some(&Path::from("/org/Xetibo/ReSetDaemon")), Some(&Path::from("/org/Xetibo/ReSetDaemon")),
@ -210,6 +278,11 @@ pub fn start_event_listener(listeners: Arc<Listeners>, wifi_box: Arc<WifiBox>) {
Some(&Path::from("/org/Xetibo/ReSetDaemon")), Some(&Path::from("/org/Xetibo/ReSetDaemon")),
) )
.static_clone(); .static_clone();
let device_changed = WifiDeviceChanged::match_rule(
Some(&"org.Xetibo.ReSetDaemon".into()),
Some(&Path::from("/org/Xetibo/ReSetDaemon")),
)
.static_clone();
let res = conn.add_match(access_point_added, move |ir: AccessPointAdded, _, _| { let res = conn.add_match(access_point_added, move |ir: AccessPointAdded, _, _| {
println!("received added event"); println!("received added event");
let wifi_box = added_ref.clone(); let wifi_box = added_ref.clone();
@ -223,7 +296,9 @@ pub fn start_event_listener(listeners: Arc<Listeners>, wifi_box: Arc<WifiBox>) {
if wifiEntries.get(&ssid).is_some() { if wifiEntries.get(&ssid).is_some() {
return; return;
} }
let entry = WifiEntry::new(ir.access_point, imp); let connected = imp.resetCurrentWifiDevice.borrow().active_access_point
== ir.access_point.dbus_path;
let entry = WifiEntry::new(connected, ir.access_point, imp);
wifiEntries.insert(ssid, entry.clone()); wifiEntries.insert(ssid, entry.clone());
wifiEntriesPath.insert(path, entry.clone()); wifiEntriesPath.insert(path, entry.clone());
imp.resetWifiList.add(&*entry); imp.resetWifiList.add(&*entry);
@ -295,7 +370,9 @@ pub fn start_event_listener(listeners: Arc<Listeners>, wifi_box: Arc<WifiBox>) {
if !ir.access_point.stored { if !ir.access_point.stored {
entryImp.resetWifiEditButton.set_sensitive(false); entryImp.resetWifiEditButton.set_sensitive(false);
} }
if ir.access_point.connected { if ir.access_point.dbus_path
== imp.resetCurrentWifiDevice.borrow().active_access_point
{
entryImp entryImp
.resetWifiConnected .resetWifiConnected
.get() .get()
@ -315,6 +392,32 @@ pub fn start_event_listener(listeners: Arc<Listeners>, wifi_box: Arc<WifiBox>) {
println!("fail on change"); println!("fail on change");
return; return;
} }
let res = conn.add_match(device_changed, move |ir: WifiDeviceChanged, _, _| {
println!("received wifidevice changed event");
let wifi_box = wifi_changed_ref.clone();
glib::spawn_future(async move {
glib::idle_add_once(move || {
let imp = wifi_box.imp();
let mut current_device = imp.resetCurrentWifiDevice.borrow_mut();
if current_device.path == ir.wifi_device.path {
current_device.active_access_point = ir.wifi_device.active_access_point;
} else {
*current_device = ir.wifi_device;
}
let mut wifiEntries = imp.wifiEntries.lock().unwrap();
for entry in wifiEntries.iter_mut() {
let imp = entry.1.imp();
let mut connected = imp.connected.borrow_mut();
*connected = imp.accessPoint.borrow().dbus_path == current_device.path;
}
});
});
true
});
if res.is_err() {
println!("fail on add");
return;
}
println!("starting thread listener"); println!("starting thread listener");
loop { loop {
let _ = conn.process(Duration::from_millis(1000)); let _ = conn.process(Duration::from_millis(1000));

View file

@ -1,11 +1,13 @@
use crate::components::wifi::wifiBox; use crate::components::wifi::wifiBox;
use ReSet_Lib::network::network::WifiDevice;
use adw::{ActionRow, ComboRow, NavigationView, PreferencesGroup}; use adw::{ActionRow, ComboRow, NavigationView, PreferencesGroup};
use dbus::Path; use dbus::Path;
use gtk::prelude::*; use gtk::{prelude::*, StringList};
use gtk::subclass::prelude::*; use gtk::subclass::prelude::*;
use gtk::{glib, CompositeTemplate, Switch}; use gtk::{glib, CompositeTemplate, Switch};
use std::cell::RefCell;
use std::collections::HashMap; use std::collections::HashMap;
use std::sync::{Arc, Mutex}; use std::sync::{Arc, Mutex, RwLock};
use crate::components::base::listEntry::ListEntry; use crate::components::base::listEntry::ListEntry;
use crate::components::wifi::wifiEntry::WifiEntry; use crate::components::wifi::wifiEntry::WifiEntry;
@ -33,6 +35,10 @@ pub struct WifiBox {
pub wifiEntries: Arc<Mutex<HashMap<Vec<u8>, Arc<WifiEntry>>>>, pub wifiEntries: Arc<Mutex<HashMap<Vec<u8>, Arc<WifiEntry>>>>,
pub wifiEntriesPath: Arc<Mutex<HashMap<Path<'static>, Arc<WifiEntry>>>>, pub wifiEntriesPath: Arc<Mutex<HashMap<Path<'static>, Arc<WifiEntry>>>>,
pub savedWifiEntries: Arc<Mutex<Vec<ListEntry>>>, pub savedWifiEntries: Arc<Mutex<Vec<ListEntry>>>,
pub resetWifiDevices: Arc<RwLock<HashMap<String, (WifiDevice,u32)>>>,
pub resetCurrentWifiDevice: Arc<RefCell<WifiDevice>>,
pub resetModelList: Arc<RwLock<StringList>>,
pub resetModelIndex: Arc<RwLock<u32>>,
} }
unsafe impl Send for WifiBox {} unsafe impl Send for WifiBox {}

View file

@ -28,7 +28,7 @@ unsafe impl Send for WifiEntry {}
unsafe impl Sync for WifiEntry {} unsafe impl Sync for WifiEntry {}
impl WifiEntry { impl WifiEntry {
pub fn new(access_point: AccessPoint, wifiBox: &WifiBox) -> Arc<Self> { pub fn new(connected: bool, access_point: AccessPoint, wifiBox: &WifiBox) -> Arc<Self> {
let entry: Arc<WifiEntry> = Arc::new(Object::builder().build()); let entry: Arc<WifiEntry> = Arc::new(Object::builder().build());
let stored_entry = entry.clone(); let stored_entry = entry.clone();
let new_entry = entry.clone(); let new_entry = entry.clone();
@ -40,6 +40,7 @@ impl WifiEntry {
entryImp.wifiStrength.set(strength); entryImp.wifiStrength.set(strength);
entryImp.resetWifiLabel.get().set_text(name); entryImp.resetWifiLabel.get().set_text(name);
entryImp.resetWifiEncrypted.set_visible(false); entryImp.resetWifiEncrypted.set_visible(false);
entryImp.connected.set(connected);
// TODO handle encryption thing // TODO handle encryption thing
entryImp entryImp
.resetWifiStrength .resetWifiStrength
@ -53,7 +54,7 @@ impl WifiEntry {
if !access_point.stored { if !access_point.stored {
entryImp.resetWifiEditButton.set_sensitive(false); entryImp.resetWifiEditButton.set_sensitive(false);
} }
if access_point.connected { if connected {
entryImp entryImp
.resetWifiConnected .resetWifiConnected
.get() .get()
@ -68,7 +69,7 @@ impl WifiEntry {
entry.set_activatable(true); entry.set_activatable(true);
entry.connect_activated(clone!(@weak entryImp => move |_| { entry.connect_activated(clone!(@weak entryImp => move |_| {
let access_point = entryImp.accessPoint.borrow(); let access_point = entryImp.accessPoint.borrow();
if access_point.connected { if *entryImp.connected.borrow() {
click_disconnect(stored_entry.clone()); click_disconnect(stored_entry.clone());
} else if access_point.stored { } else if access_point.stored {
click_stored_network(stored_entry.clone()); click_stored_network(stored_entry.clone());
@ -92,7 +93,9 @@ impl WifiEntry {
pub fn click_disconnect(entry: Arc<WifiEntry>) { pub fn click_disconnect(entry: Arc<WifiEntry>) {
println!("called disconnect"); println!("called disconnect");
let entry_ref = entry.clone(); let entry_ref = entry.clone();
entry.set_activatable(false);
gio::spawn_blocking(move || { gio::spawn_blocking(move || {
let imp = entry_ref.imp();
let conn = Connection::new_session().unwrap(); let conn = Connection::new_session().unwrap();
let proxy = conn.with_proxy( let proxy = conn.with_proxy(
"org.Xetibo.ReSetDaemon", "org.Xetibo.ReSetDaemon",
@ -105,21 +108,24 @@ pub fn click_disconnect(entry: Arc<WifiEntry>) {
(), (),
); );
if res.is_err() { if res.is_err() {
println!("res of disconnect was error bro"); imp.connected.replace(false);
return; return;
} }
let imp = entry_ref.imp();
imp.resetWifiConnected.get().set_from_icon_name(None); imp.resetWifiConnected.get().set_from_icon_name(None);
imp.accessPoint.borrow_mut().connected = false; imp.connected.replace(false);
println!("disconnect worked"); glib::spawn_future(async move {
glib::idle_add_once(move || {
entry.set_activatable(true);
});
});
}); });
} }
pub fn click_stored_network(entry: Arc<WifiEntry>) { pub fn click_stored_network(entry: Arc<WifiEntry>) {
let result = Arc::new(AtomicBool::new(false));
let entryImp = entry.imp(); let entryImp = entry.imp();
let access_point = entryImp.accessPoint.borrow().clone(); let access_point = entryImp.accessPoint.borrow().clone();
let entry_ref = entry.clone(); let entry_ref = entry.clone();
entry.set_activatable(false);
gio::spawn_blocking(move || { gio::spawn_blocking(move || {
let conn = Connection::new_session().unwrap(); let conn = Connection::new_session().unwrap();
let proxy = conn.with_proxy( let proxy = conn.with_proxy(
@ -134,24 +140,23 @@ pub fn click_stored_network(entry: Arc<WifiEntry>) {
); );
glib::spawn_future(async move { glib::spawn_future(async move {
glib::idle_add_once(move || { glib::idle_add_once(move || {
let _imp = entry_ref.imp(); entry.set_activatable(true);
let imp = entry_ref.imp();
if res.is_err() { if res.is_err() {
println!("wat bro?"); println!("wtf?");
result.store(false, std::sync::atomic::Ordering::SeqCst); imp.connected.replace(false);
return; return;
} }
if res.unwrap() == (false,) { if res.unwrap() == (false,) {
println!("error bro?"); println!("false on connecting");
result.store(false, std::sync::atomic::Ordering::SeqCst); imp.connected.replace(false);
return; return;
} }
let imp = entry_ref.imp(); let imp = entry_ref.imp();
println!("wateroni");
imp.resetWifiConnected imp.resetWifiConnected
.get() .get()
.set_from_icon_name(Some("network-wireless-connected-symbolic")); .set_from_icon_name(Some("network-wireless-connected-symbolic"));
imp.accessPoint.borrow_mut().connected = true; imp.connected.replace(true);
result.store(true, std::sync::atomic::Ordering::SeqCst);
}); });
}); });
}); });
@ -159,81 +164,72 @@ pub fn click_stored_network(entry: Arc<WifiEntry>) {
} }
pub fn click_new_network(entry: Arc<WifiEntry>) { pub fn click_new_network(entry: Arc<WifiEntry>) {
let connect_new_network = |result: Arc<AtomicBool>, let connect_new_network =
entry: Arc<WifiEntry>, |entry: Arc<WifiEntry>, access_point: AccessPoint, password: String| {
access_point: AccessPoint, let entry_ref = entry.clone();
password: String| { let popup = entry.imp().resetWifiPopup.imp();
let entry_ref = entry.clone(); popup.resetPopupLabel.set_text("Connecting...");
let popup = entry.imp().resetWifiPopup.imp(); popup.resetPopupLabel.set_visible(true);
popup.resetPopupLabel.set_text("Connecting..."); popup.resetPopupEntry.set_sensitive(false);
popup.resetPopupLabel.set_visible(true); popup.resetPopupButton.set_sensitive(false);
popup.resetPopupEntry.set_sensitive(false);
popup.resetPopupButton.set_sensitive(false);
gio::spawn_blocking(move || { gio::spawn_blocking(move || {
let conn = Connection::new_session().unwrap(); let conn = Connection::new_session().unwrap();
let proxy = conn.with_proxy( let proxy = conn.with_proxy(
"org.Xetibo.ReSetDaemon", "org.Xetibo.ReSetDaemon",
"/org/Xetibo/ReSetDaemon", "/org/Xetibo/ReSetDaemon",
Duration::from_millis(10000), Duration::from_millis(10000),
); );
let res: Result<(bool,), Error> = proxy.method_call( let res: Result<(bool,), Error> = proxy.method_call(
"org.Xetibo.ReSetWireless", "org.Xetibo.ReSetWireless",
"ConnectToNewAccessPoint", "ConnectToNewAccessPoint",
(access_point, password), (access_point, password),
); );
glib::spawn_future(async move { glib::spawn_future(async move {
glib::idle_add_once(move || { glib::idle_add_once(move || {
if res.is_err() { if res.is_err() {
println!("error bro"); let imp = entry_ref.imp();
entry_ref imp.resetWifiPopup
.imp() .imp()
.resetWifiPopup .resetPopupLabel
.imp() .set_text("Could not connect to dbus.");
.resetPopupLabel imp.connected.replace(false);
.set_text("Could not connect to dbus."); return;
result.store(false, std::sync::atomic::Ordering::SeqCst); }
return; if res.unwrap() == (false,) {
} let imp = entry_ref.imp();
if res.unwrap() == (false,) { imp.resetWifiPopup
println!("wrong pw"); .imp()
entry_ref .resetPopupLabel
.imp() .set_text("Could not connect to access point.");
.resetWifiPopup imp.connected.replace(false);
.imp() return;
.resetPopupLabel }
.set_text("Could not connect to access point."); println!("worked?");
result.store(false, std::sync::atomic::Ordering::SeqCst); let imp = entry_ref.imp();
return; imp.resetWifiPopup.popdown();
} imp.resetWifiEditButton.set_sensitive(true);
println!("worked?"); imp.resetWifiConnected
let imp = entry_ref.imp(); .get()
imp.resetWifiPopup.popdown(); .set_from_icon_name(Some("network-wireless-connected-symbolic"));
imp.resetWifiEditButton.set_sensitive(true); imp.connected.replace(true);
imp.resetWifiConnected });
.get()
.set_from_icon_name(Some("network-wireless-connected-symbolic"));
result.store(true, std::sync::atomic::Ordering::SeqCst);
}); });
}); });
}); // TODO crate spinner animation and block UI
// TODO crate spinner animation and block UI };
};
let result = Arc::new(AtomicBool::new(false));
let result_ref = result.clone();
let result_ref_button = result.clone();
let entryImp = entry.imp(); let entryImp = entry.imp();
let popupImp = entryImp.resetWifiPopup.imp(); let popupImp = entryImp.resetWifiPopup.imp();
popupImp popupImp
.resetPopupEntry .resetPopupEntry
.connect_activate(clone!(@weak entry as origEntry, @weak entryImp => move |entry| { .connect_activate(clone!(@weak entry as origEntry, @weak entryImp => move |entry| {
connect_new_network(result_ref.clone(), origEntry, entryImp.accessPoint.clone().take(), entry.text().to_string()); connect_new_network(origEntry, entryImp.accessPoint.clone().take(), entry.text().to_string());
})); }));
popupImp.resetPopupButton.connect_clicked( popupImp.resetPopupButton.connect_clicked(
clone!(@weak entry as origEntry,@weak entryImp, @weak popupImp => move |_| { clone!(@weak entry as origEntry,@weak entryImp, @weak popupImp => move |_| {
let entry = entryImp.resetWifiPopup.imp().resetPopupEntry.text().to_string(); let entry = entryImp.resetWifiPopup.imp().resetPopupEntry.text().to_string();
connect_new_network(result_ref_button.clone(), origEntry, entryImp.accessPoint.clone().take(), entry); connect_new_network(origEntry, entryImp.accessPoint.clone().take(), entry);
}), }),
); );
entryImp.resetWifiPopup.popup(); entryImp.resetWifiPopup.popup();

View file

@ -5,7 +5,7 @@ use adw::subclass::prelude::ActionRowImpl;
use adw::ActionRow; use adw::ActionRow;
use gtk::subclass::prelude::*; use gtk::subclass::prelude::*;
use gtk::{glib, Button, CompositeTemplate, Image, Label}; use gtk::{glib, Button, CompositeTemplate, Image, Label};
use std::cell::RefCell; use std::cell::{RefCell, Cell};
use ReSet_Lib::network::network::{AccessPoint, WifiStrength}; use ReSet_Lib::network::network::{AccessPoint, WifiStrength};
#[allow(non_snake_case)] #[allow(non_snake_case)]
@ -27,6 +27,7 @@ pub struct WifiEntry {
pub wifiName: RefCell<String>, pub wifiName: RefCell<String>,
pub wifiStrength: RefCell<WifiStrength>, pub wifiStrength: RefCell<WifiStrength>,
pub accessPoint: RefCell<AccessPoint>, pub accessPoint: RefCell<AccessPoint>,
pub connected: RefCell<bool>,
} }
unsafe impl Send for WifiEntry {} unsafe impl Send for WifiEntry {}

View file

@ -39,7 +39,7 @@
<child> <child>
<object class="AdwPreferencesGroup" id="resetBluetoothDetails"> <object class="AdwPreferencesGroup" id="resetBluetoothDetails">
<child> <child>
<object class="AdwComboRow" id="resetBluetoothDevice"> <object class="AdwComboRow" id="resetBluetoothAdapter">
<property name="title">Bluetooth Device</property> <property name="title">Bluetooth Device</property>
</object> </object>
</child> </child>