mirror of
https://github.com/weyne85/rustdesk.git
synced 2025-10-29 17:00:05 +00:00
Merge pull request #1220 from fufesou/flutter_desktop_remote_menus
Flutter desktop remote menus
This commit is contained in:
commit
e197c8a264
@ -194,14 +194,20 @@ void msgBox(String type, String title, String text, {bool? hasCancel}) {
|
|||||||
style: TextStyle(color: MyTheme.accent))));
|
style: TextStyle(color: MyTheme.accent))));
|
||||||
|
|
||||||
SmartDialog.dismiss();
|
SmartDialog.dismiss();
|
||||||
final buttons = [
|
List<Widget> buttons = [];
|
||||||
|
if (type != "connecting" && type != "success" && type.indexOf("nook") < 0) {
|
||||||
|
buttons.insert(
|
||||||
|
0,
|
||||||
wrap(Translator.call('OK'), () {
|
wrap(Translator.call('OK'), () {
|
||||||
SmartDialog.dismiss();
|
SmartDialog.dismiss();
|
||||||
backToHome();
|
backToHome();
|
||||||
})
|
}));
|
||||||
];
|
}
|
||||||
if (hasCancel == null) {
|
if (hasCancel == null) {
|
||||||
hasCancel = type != 'error';
|
// hasCancel = type != 'error';
|
||||||
|
hasCancel = type.indexOf("error") < 0 &&
|
||||||
|
type.indexOf("nocancel") < 0 &&
|
||||||
|
type != "restarting";
|
||||||
}
|
}
|
||||||
if (hasCancel) {
|
if (hasCancel) {
|
||||||
buttons.insert(
|
buttons.insert(
|
||||||
@ -210,6 +216,14 @@ void msgBox(String type, String title, String text, {bool? hasCancel}) {
|
|||||||
SmartDialog.dismiss();
|
SmartDialog.dismiss();
|
||||||
}));
|
}));
|
||||||
}
|
}
|
||||||
|
// TODO: test this button
|
||||||
|
if (type.indexOf("hasclose") >= 0) {
|
||||||
|
buttons.insert(
|
||||||
|
0,
|
||||||
|
wrap(Translator.call('Close'), () {
|
||||||
|
SmartDialog.dismiss();
|
||||||
|
}));
|
||||||
|
}
|
||||||
DialogManager.show((setState, close) => CustomAlertDialog(
|
DialogManager.show((setState, close) => CustomAlertDialog(
|
||||||
title: Text(translate(title), style: TextStyle(fontSize: 21)),
|
title: Text(translate(title), style: TextStyle(fontSize: 21)),
|
||||||
content: Text(Translator.call(text), style: TextStyle(fontSize: 15)),
|
content: Text(Translator.call(text), style: TextStyle(fontSize: 15)),
|
||||||
|
|||||||
@ -277,8 +277,7 @@ class _RemotePageState extends State<RemotePage>
|
|||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
super.build(context);
|
super.build(context);
|
||||||
Provider.of<CanvasModel>(context, listen: false).tabBarHeight =
|
_ffi.canvasModel.tabBarHeight = super.widget.tabBarHeight;
|
||||||
super.widget.tabBarHeight;
|
|
||||||
return WillPopScope(
|
return WillPopScope(
|
||||||
onWillPop: () async {
|
onWillPop: () async {
|
||||||
clientClose();
|
clientClose();
|
||||||
@ -605,8 +604,12 @@ class _RemotePageState extends State<RemotePage>
|
|||||||
await bind.getSessionToggleOption(id: id, arg: 'privacy-mode') !=
|
await bind.getSessionToggleOption(id: id, arg: 'privacy-mode') !=
|
||||||
true) {
|
true) {
|
||||||
more.add(PopupMenuItem<String>(
|
more.add(PopupMenuItem<String>(
|
||||||
child: Text(translate((_ffi.ffiModel.inputBlocked ? 'Unb' : 'B') +
|
child: Consumer<FfiModel>(
|
||||||
'lock user input')),
|
builder: (_context, ffiModel, _child) => () {
|
||||||
|
return Text(translate(
|
||||||
|
(ffiModel.inputBlocked ? 'Unb' : 'B') +
|
||||||
|
'lock user input'));
|
||||||
|
}()),
|
||||||
value: 'block-input'));
|
value: 'block-input'));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -882,11 +885,11 @@ class ImagePainter extends CustomPainter {
|
|||||||
if (image == null) return;
|
if (image == null) return;
|
||||||
canvas.scale(scale, scale);
|
canvas.scale(scale, scale);
|
||||||
// https://github.com/flutter/flutter/issues/76187#issuecomment-784628161
|
// https://github.com/flutter/flutter/issues/76187#issuecomment-784628161
|
||||||
|
// https://api.flutter-io.cn/flutter/dart-ui/FilterQuality.html
|
||||||
var paint = new Paint();
|
var paint = new Paint();
|
||||||
if (scale > 1.00001) {
|
|
||||||
paint.filterQuality = FilterQuality.high;
|
|
||||||
} else if (scale < 0.99999) {
|
|
||||||
paint.filterQuality = FilterQuality.medium;
|
paint.filterQuality = FilterQuality.medium;
|
||||||
|
if (scale > 10.00000) {
|
||||||
|
paint.filterQuality = FilterQuality.high;
|
||||||
}
|
}
|
||||||
canvas.drawImage(image!, new Offset(x, y), paint);
|
canvas.drawImage(image!, new Offset(x, y), paint);
|
||||||
}
|
}
|
||||||
@ -952,7 +955,11 @@ void showOptions(String id) async {
|
|||||||
more.add(getToggle(
|
more.add(getToggle(
|
||||||
id, setState, 'lock-after-session-end', 'Lock after session end'));
|
id, setState, 'lock-after-session-end', 'Lock after session end'));
|
||||||
if (pi.platform == 'Windows') {
|
if (pi.platform == 'Windows') {
|
||||||
more.add(getToggle(id, setState, 'privacy-mode', 'Privacy mode'));
|
more.add(Consumer<FfiModel>(
|
||||||
|
builder: (_context, _ffiModel, _child) => () {
|
||||||
|
return getToggle(
|
||||||
|
id, setState, 'privacy-mode', 'Privacy mode');
|
||||||
|
}()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
var setQuality = (String? value) {
|
var setQuality = (String? value) {
|
||||||
|
|||||||
@ -173,6 +173,10 @@ class FfiModel with ChangeNotifier {
|
|||||||
parent.target?.serverModel.onClientRemove(evt);
|
parent.target?.serverModel.onClientRemove(evt);
|
||||||
} else if (name == 'update_quality_status') {
|
} else if (name == 'update_quality_status') {
|
||||||
parent.target?.qualityMonitorModel.updateQualityStatus(evt);
|
parent.target?.qualityMonitorModel.updateQualityStatus(evt);
|
||||||
|
} else if (name == 'update_block_input_state') {
|
||||||
|
updateBlockInputState(evt);
|
||||||
|
} else if (name == 'update_privacy_mode') {
|
||||||
|
updatePrivacyMode(evt);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@ -228,6 +232,10 @@ class FfiModel with ChangeNotifier {
|
|||||||
parent.target?.serverModel.onClientRemove(evt);
|
parent.target?.serverModel.onClientRemove(evt);
|
||||||
} else if (name == 'update_quality_status') {
|
} else if (name == 'update_quality_status') {
|
||||||
parent.target?.qualityMonitorModel.updateQualityStatus(evt);
|
parent.target?.qualityMonitorModel.updateQualityStatus(evt);
|
||||||
|
} else if (name == 'update_block_input_state') {
|
||||||
|
updateBlockInputState(evt);
|
||||||
|
} else if (name == 'update_privacy_mode') {
|
||||||
|
updatePrivacyMode(evt);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
platformFFI.setEventCallback(cb);
|
platformFFI.setEventCallback(cb);
|
||||||
@ -331,6 +339,15 @@ class FfiModel with ChangeNotifier {
|
|||||||
}
|
}
|
||||||
notifyListeners();
|
notifyListeners();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
updateBlockInputState(Map<String, dynamic> evt) {
|
||||||
|
_inputBlocked = evt['input_state'] == 'on';
|
||||||
|
notifyListeners();
|
||||||
|
}
|
||||||
|
|
||||||
|
updatePrivacyMode(Map<String, dynamic> evt) {
|
||||||
|
notifyListeners();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class ImageModel with ChangeNotifier {
|
class ImageModel with ChangeNotifier {
|
||||||
|
|||||||
@ -1,4 +1,5 @@
|
|||||||
import 'dart:convert';
|
import 'dart:convert';
|
||||||
|
import 'dart:ui';
|
||||||
|
|
||||||
import 'package:desktop_multi_window/desktop_multi_window.dart';
|
import 'package:desktop_multi_window/desktop_multi_window.dart';
|
||||||
import 'package:flutter/services.dart';
|
import 'package:flutter/services.dart';
|
||||||
|
|||||||
@ -1004,6 +1004,13 @@ impl LoginConfigHandler {
|
|||||||
Some(msg_out)
|
Some(msg_out)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Get [`PeerConfig`] of the current [`LoginConfigHandler`].
|
||||||
|
///
|
||||||
|
/// # Arguments
|
||||||
|
pub fn get_config(&mut self) -> &mut PeerConfig {
|
||||||
|
&mut self.config
|
||||||
|
}
|
||||||
|
|
||||||
/// Get [`OptionMessage`] of the current [`LoginConfigHandler`].
|
/// Get [`OptionMessage`] of the current [`LoginConfigHandler`].
|
||||||
/// Return `None` if there's no option, for example, when the session is only for file transfer.
|
/// Return `None` if there's no option, for example, when the session is only for file transfer.
|
||||||
///
|
///
|
||||||
|
|||||||
@ -104,6 +104,19 @@ pub fn update_clipboard(clipboard: Clipboard, old: Option<&Arc<Mutex<String>>>)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub async fn send_opts_after_login(
|
||||||
|
config: &crate::client::LoginConfigHandler,
|
||||||
|
peer: &mut hbb_common::tcp::FramedStream,
|
||||||
|
) {
|
||||||
|
if let Some(opts) = config.get_option_message_after_login() {
|
||||||
|
let mut misc = Misc::new();
|
||||||
|
misc.set_option(opts);
|
||||||
|
let mut msg_out = Message::new();
|
||||||
|
msg_out.set_misc(misc);
|
||||||
|
allow_err!(peer.send(&msg_out).await);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#[cfg(feature = "use_rubato")]
|
#[cfg(feature = "use_rubato")]
|
||||||
pub fn resample_channels(
|
pub fn resample_channels(
|
||||||
data: &[f32],
|
data: &[f32],
|
||||||
|
|||||||
194
src/flutter.rs
194
src/flutter.rs
@ -1,7 +1,7 @@
|
|||||||
use std::{
|
use std::{
|
||||||
collections::{HashMap, VecDeque},
|
collections::{HashMap, VecDeque},
|
||||||
sync::{
|
sync::{
|
||||||
atomic::{AtomicUsize, Ordering},
|
atomic::{AtomicBool, AtomicUsize, Ordering},
|
||||||
Arc, Mutex, RwLock,
|
Arc, Mutex, RwLock,
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
@ -31,7 +31,10 @@ use hbb_common::{
|
|||||||
Stream,
|
Stream,
|
||||||
};
|
};
|
||||||
|
|
||||||
use crate::common::make_fd_to_json;
|
use crate::common::{
|
||||||
|
self, check_clipboard, make_fd_to_json, update_clipboard, ClipboardContext, CLIPBOARD_INTERVAL,
|
||||||
|
};
|
||||||
|
|
||||||
use crate::{client::*, flutter_ffi::EventToUI, make_fd_flutter};
|
use crate::{client::*, flutter_ffi::EventToUI, make_fd_flutter};
|
||||||
|
|
||||||
pub(super) const APP_TYPE_MAIN: &str = "main";
|
pub(super) const APP_TYPE_MAIN: &str = "main";
|
||||||
@ -44,6 +47,9 @@ lazy_static::lazy_static! {
|
|||||||
pub static ref GLOBAL_EVENT_STREAM: RwLock<HashMap<String, StreamSink<String>>> = Default::default(); // rust to dart event channel
|
pub static ref GLOBAL_EVENT_STREAM: RwLock<HashMap<String, StreamSink<String>>> = Default::default(); // rust to dart event channel
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static SERVER_CLIPBOARD_ENABLED: AtomicBool = AtomicBool::new(true);
|
||||||
|
static SERVER_KEYBOARD_ENABLED: AtomicBool = AtomicBool::new(true);
|
||||||
|
|
||||||
// pub fn get_session<'a>(id: &str) -> Option<&'a Session> {
|
// pub fn get_session<'a>(id: &str) -> Option<&'a Session> {
|
||||||
// SESSIONS.read().unwrap().get(id)
|
// SESSIONS.read().unwrap().get(id)
|
||||||
// }
|
// }
|
||||||
@ -70,7 +76,7 @@ impl Session {
|
|||||||
// TODO close
|
// TODO close
|
||||||
// Self::close();
|
// Self::close();
|
||||||
let events2ui = Arc::new(RwLock::new(events2ui));
|
let events2ui = Arc::new(RwLock::new(events2ui));
|
||||||
let mut session = Session {
|
let session = Session {
|
||||||
id: session_id.clone(),
|
id: session_id.clone(),
|
||||||
sender: Default::default(),
|
sender: Default::default(),
|
||||||
lc: Default::default(),
|
lc: Default::default(),
|
||||||
@ -657,6 +663,45 @@ struct Connection {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl Connection {
|
impl Connection {
|
||||||
|
// TODO: Similar to remote::start_clipboard
|
||||||
|
// merge the code
|
||||||
|
fn start_clipboard(
|
||||||
|
tx_protobuf: mpsc::UnboundedSender<Data>,
|
||||||
|
lc: Arc<RwLock<LoginConfigHandler>>,
|
||||||
|
) -> Option<std::sync::mpsc::Sender<()>> {
|
||||||
|
let (tx, rx) = std::sync::mpsc::channel();
|
||||||
|
match ClipboardContext::new() {
|
||||||
|
Ok(mut ctx) => {
|
||||||
|
let old_clipboard: Arc<Mutex<String>> = Default::default();
|
||||||
|
// ignore clipboard update before service start
|
||||||
|
check_clipboard(&mut ctx, Some(&old_clipboard));
|
||||||
|
std::thread::spawn(move || loop {
|
||||||
|
std::thread::sleep(Duration::from_millis(CLIPBOARD_INTERVAL));
|
||||||
|
match rx.try_recv() {
|
||||||
|
Ok(_) | Err(std::sync::mpsc::TryRecvError::Disconnected) => {
|
||||||
|
log::debug!("Exit clipboard service of client");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
_ => {}
|
||||||
|
}
|
||||||
|
if !SERVER_CLIPBOARD_ENABLED.load(Ordering::SeqCst)
|
||||||
|
|| !SERVER_KEYBOARD_ENABLED.load(Ordering::SeqCst)
|
||||||
|
|| lc.read().unwrap().disable_clipboard
|
||||||
|
{
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if let Some(msg) = check_clipboard(&mut ctx, Some(&old_clipboard)) {
|
||||||
|
tx_protobuf.send(Data::Message(msg)).ok();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
Err(err) => {
|
||||||
|
log::error!("Failed to start clipboard service of client: {}", err);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Some(tx)
|
||||||
|
}
|
||||||
|
|
||||||
/// Create a new connection.
|
/// Create a new connection.
|
||||||
///
|
///
|
||||||
/// # Arguments
|
/// # Arguments
|
||||||
@ -667,6 +712,10 @@ impl Connection {
|
|||||||
async fn start(session: Session, is_file_transfer: bool) {
|
async fn start(session: Session, is_file_transfer: bool) {
|
||||||
let mut last_recv_time = Instant::now();
|
let mut last_recv_time = Instant::now();
|
||||||
let (sender, mut receiver) = mpsc::unbounded_channel::<Data>();
|
let (sender, mut receiver) = mpsc::unbounded_channel::<Data>();
|
||||||
|
let mut stop_clipboard = None;
|
||||||
|
if !is_file_transfer {
|
||||||
|
stop_clipboard = Self::start_clipboard(sender.clone(), session.lc.clone());
|
||||||
|
}
|
||||||
*session.sender.write().unwrap() = Some(sender);
|
*session.sender.write().unwrap() = Some(sender);
|
||||||
let conn_type = if is_file_transfer {
|
let conn_type = if is_file_transfer {
|
||||||
session.lc.write().unwrap().is_file_transfer = true;
|
session.lc.write().unwrap().is_file_transfer = true;
|
||||||
@ -695,6 +744,9 @@ impl Connection {
|
|||||||
|
|
||||||
match Client::start(&session.id, &key, &token, conn_type).await {
|
match Client::start(&session.id, &key, &token, conn_type).await {
|
||||||
Ok((mut peer, direct)) => {
|
Ok((mut peer, direct)) => {
|
||||||
|
SERVER_KEYBOARD_ENABLED.store(true, Ordering::SeqCst);
|
||||||
|
SERVER_CLIPBOARD_ENABLED.store(true, Ordering::SeqCst);
|
||||||
|
|
||||||
session.push_event(
|
session.push_event(
|
||||||
"connection_ready",
|
"connection_ready",
|
||||||
vec![
|
vec![
|
||||||
@ -774,6 +826,12 @@ impl Connection {
|
|||||||
session.msgbox("error", "Connection Error", &err.to_string());
|
session.msgbox("error", "Connection Error", &err.to_string());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if let Some(stop) = stop_clipboard {
|
||||||
|
stop.send(()).ok();
|
||||||
|
}
|
||||||
|
SERVER_KEYBOARD_ENABLED.store(false, Ordering::SeqCst);
|
||||||
|
SERVER_CLIPBOARD_ENABLED.store(false, Ordering::SeqCst);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Handle message from peer.
|
/// Handle message from peer.
|
||||||
@ -786,6 +844,7 @@ impl Connection {
|
|||||||
Some(message::Union::VideoFrame(vf)) => {
|
Some(message::Union::VideoFrame(vf)) => {
|
||||||
if !self.first_frame {
|
if !self.first_frame {
|
||||||
self.first_frame = true;
|
self.first_frame = true;
|
||||||
|
common::send_opts_after_login(&self.session.lc.read().unwrap(), peer).await;
|
||||||
}
|
}
|
||||||
let incomming_format = CodecFormat::from(&vf);
|
let incomming_format = CodecFormat::from(&vf);
|
||||||
if self.video_format != incomming_format {
|
if self.video_format != incomming_format {
|
||||||
@ -1027,6 +1086,11 @@ impl Connection {
|
|||||||
self.session.msgbox("error", "Connection Error", &c);
|
self.session.msgbox("error", "Connection Error", &c);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
Some(misc::Union::BackNotification(notification)) => {
|
||||||
|
if !self.handle_back_notification(notification).await {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
_ => {}
|
_ => {}
|
||||||
},
|
},
|
||||||
Some(message::Union::TestDelay(t)) => {
|
Some(message::Union::TestDelay(t)) => {
|
||||||
@ -1051,6 +1115,130 @@ impl Connection {
|
|||||||
true
|
true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async fn handle_back_notification(&mut self, notification: BackNotification) -> bool {
|
||||||
|
match notification.union {
|
||||||
|
Some(back_notification::Union::BlockInputState(state)) => {
|
||||||
|
self.handle_back_msg_block_input(
|
||||||
|
state.enum_value_or(back_notification::BlockInputState::BlkStateUnknown),
|
||||||
|
)
|
||||||
|
.await;
|
||||||
|
}
|
||||||
|
Some(back_notification::Union::PrivacyModeState(state)) => {
|
||||||
|
if !self
|
||||||
|
.handle_back_msg_privacy_mode(
|
||||||
|
state.enum_value_or(back_notification::PrivacyModeState::PrvStateUnknown),
|
||||||
|
)
|
||||||
|
.await
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
_ => {}
|
||||||
|
}
|
||||||
|
true
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline(always)]
|
||||||
|
fn update_block_input_state(&mut self, on: bool) {
|
||||||
|
self.session.push_event(
|
||||||
|
"update_block_input_state",
|
||||||
|
[("input_state", if on { "on" } else { "off" })].into(),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
async fn handle_back_msg_block_input(&mut self, state: back_notification::BlockInputState) {
|
||||||
|
match state {
|
||||||
|
back_notification::BlockInputState::BlkOnSucceeded => {
|
||||||
|
self.update_block_input_state(true);
|
||||||
|
}
|
||||||
|
back_notification::BlockInputState::BlkOnFailed => {
|
||||||
|
self.session
|
||||||
|
.msgbox("custom-error", "Block user input", "Failed");
|
||||||
|
self.update_block_input_state(false);
|
||||||
|
}
|
||||||
|
back_notification::BlockInputState::BlkOffSucceeded => {
|
||||||
|
self.update_block_input_state(false);
|
||||||
|
}
|
||||||
|
back_notification::BlockInputState::BlkOffFailed => {
|
||||||
|
self.session
|
||||||
|
.msgbox("custom-error", "Unblock user input", "Failed");
|
||||||
|
}
|
||||||
|
_ => {}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline(always)]
|
||||||
|
fn update_privacy_mode(&mut self, on: bool) {
|
||||||
|
let mut config = self.session.load_config();
|
||||||
|
config.privacy_mode = on;
|
||||||
|
self.session.save_config(&config);
|
||||||
|
self.session.lc.write().unwrap().get_config().privacy_mode = on;
|
||||||
|
self.session.push_event("update_privacy_mode", [].into());
|
||||||
|
}
|
||||||
|
|
||||||
|
async fn handle_back_msg_privacy_mode(
|
||||||
|
&mut self,
|
||||||
|
state: back_notification::PrivacyModeState,
|
||||||
|
) -> bool {
|
||||||
|
match state {
|
||||||
|
back_notification::PrivacyModeState::PrvOnByOther => {
|
||||||
|
self.session.msgbox(
|
||||||
|
"error",
|
||||||
|
"Connecting...",
|
||||||
|
"Someone turns on privacy mode, exit",
|
||||||
|
);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
back_notification::PrivacyModeState::PrvNotSupported => {
|
||||||
|
self.session
|
||||||
|
.msgbox("custom-error", "Privacy mode", "Unsupported");
|
||||||
|
self.update_privacy_mode(false);
|
||||||
|
}
|
||||||
|
back_notification::PrivacyModeState::PrvOnSucceeded => {
|
||||||
|
self.session
|
||||||
|
.msgbox("custom-nocancel", "Privacy mode", "In privacy mode");
|
||||||
|
self.update_privacy_mode(true);
|
||||||
|
}
|
||||||
|
back_notification::PrivacyModeState::PrvOnFailedDenied => {
|
||||||
|
self.session
|
||||||
|
.msgbox("custom-error", "Privacy mode", "Peer denied");
|
||||||
|
self.update_privacy_mode(false);
|
||||||
|
}
|
||||||
|
back_notification::PrivacyModeState::PrvOnFailedPlugin => {
|
||||||
|
self.session
|
||||||
|
.msgbox("custom-error", "Privacy mode", "Please install plugins");
|
||||||
|
self.update_privacy_mode(false);
|
||||||
|
}
|
||||||
|
back_notification::PrivacyModeState::PrvOnFailed => {
|
||||||
|
self.session
|
||||||
|
.msgbox("custom-error", "Privacy mode", "Failed");
|
||||||
|
self.update_privacy_mode(false);
|
||||||
|
}
|
||||||
|
back_notification::PrivacyModeState::PrvOffSucceeded => {
|
||||||
|
self.session
|
||||||
|
.msgbox("custom-nocancel", "Privacy mode", "Out privacy mode");
|
||||||
|
self.update_privacy_mode(false);
|
||||||
|
}
|
||||||
|
back_notification::PrivacyModeState::PrvOffByPeer => {
|
||||||
|
self.session
|
||||||
|
.msgbox("custom-error", "Privacy mode", "Peer exit");
|
||||||
|
self.update_privacy_mode(false);
|
||||||
|
}
|
||||||
|
back_notification::PrivacyModeState::PrvOffFailed => {
|
||||||
|
self.session
|
||||||
|
.msgbox("custom-error", "Privacy mode", "Failed to turn off");
|
||||||
|
}
|
||||||
|
back_notification::PrivacyModeState::PrvOffUnknown => {
|
||||||
|
self.session
|
||||||
|
.msgbox("custom-error", "Privacy mode", "Turned off");
|
||||||
|
// log::error!("Privacy mode is turned off with unknown reason");
|
||||||
|
self.update_privacy_mode(false);
|
||||||
|
}
|
||||||
|
_ => {}
|
||||||
|
}
|
||||||
|
true
|
||||||
|
}
|
||||||
|
|
||||||
async fn handle_msg_from_ui(&mut self, data: Data, peer: &mut Stream) -> bool {
|
async fn handle_msg_from_ui(&mut self, data: Data, peer: &mut Stream) -> bool {
|
||||||
match data {
|
match data {
|
||||||
Data::Close => {
|
Data::Close => {
|
||||||
|
|||||||
@ -25,8 +25,12 @@ use clipboard::{
|
|||||||
use enigo::{self, Enigo, KeyboardControllable};
|
use enigo::{self, Enigo, KeyboardControllable};
|
||||||
use hbb_common::{
|
use hbb_common::{
|
||||||
allow_err,
|
allow_err,
|
||||||
config::{Config, LocalConfig, PeerConfig},
|
config::{Config, LocalConfig, PeerConfig, TransferSerde},
|
||||||
fs, log,
|
fs::{
|
||||||
|
self, can_enable_overwrite_detection, get_job, get_string, new_send_confirm,
|
||||||
|
DigestCheckResult, RemoveJobMeta, TransferJobMeta,
|
||||||
|
},
|
||||||
|
get_version_number, log,
|
||||||
message_proto::{permission_info::Permission, *},
|
message_proto::{permission_info::Permission, *},
|
||||||
protobuf::Message as _,
|
protobuf::Message as _,
|
||||||
rendezvous_proto::ConnType,
|
rendezvous_proto::ConnType,
|
||||||
@ -38,14 +42,6 @@ use hbb_common::{
|
|||||||
},
|
},
|
||||||
Stream,
|
Stream,
|
||||||
};
|
};
|
||||||
use hbb_common::{config::TransferSerde, fs::TransferJobMeta};
|
|
||||||
use hbb_common::{
|
|
||||||
fs::{
|
|
||||||
can_enable_overwrite_detection, get_job, get_string, new_send_confirm, DigestCheckResult,
|
|
||||||
RemoveJobMeta,
|
|
||||||
},
|
|
||||||
get_version_number,
|
|
||||||
};
|
|
||||||
|
|
||||||
#[cfg(windows)]
|
#[cfg(windows)]
|
||||||
use crate::clipboard_file::*;
|
use crate::clipboard_file::*;
|
||||||
@ -2071,22 +2067,6 @@ impl Remote {
|
|||||||
true
|
true
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn send_opts_after_login(&self, peer: &mut Stream) {
|
|
||||||
if let Some(opts) = self
|
|
||||||
.handler
|
|
||||||
.lc
|
|
||||||
.read()
|
|
||||||
.unwrap()
|
|
||||||
.get_option_message_after_login()
|
|
||||||
{
|
|
||||||
let mut misc = Misc::new();
|
|
||||||
misc.set_option(opts);
|
|
||||||
let mut msg_out = Message::new();
|
|
||||||
msg_out.set_misc(misc);
|
|
||||||
allow_err!(peer.send(&msg_out).await);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
async fn handle_msg_from_peer(&mut self, data: &[u8], peer: &mut Stream) -> bool {
|
async fn handle_msg_from_peer(&mut self, data: &[u8], peer: &mut Stream) -> bool {
|
||||||
if let Ok(msg_in) = Message::parse_from_bytes(&data) {
|
if let Ok(msg_in) = Message::parse_from_bytes(&data) {
|
||||||
match msg_in.union {
|
match msg_in.union {
|
||||||
@ -2095,7 +2075,7 @@ impl Remote {
|
|||||||
self.first_frame = true;
|
self.first_frame = true;
|
||||||
self.handler.call2("closeSuccess", &make_args!());
|
self.handler.call2("closeSuccess", &make_args!());
|
||||||
self.handler.call("adaptSize", &make_args!());
|
self.handler.call("adaptSize", &make_args!());
|
||||||
self.send_opts_after_login(peer).await;
|
common::send_opts_after_login(&self.handler.lc.read().unwrap(), peer).await;
|
||||||
}
|
}
|
||||||
let incomming_format = CodecFormat::from(&vf);
|
let incomming_format = CodecFormat::from(&vf);
|
||||||
if self.video_format != incomming_format {
|
if self.video_format != incomming_format {
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user