support custom resolution ui
Signed-off-by: fufesou <shuanglongchen@yeah.net>
This commit is contained in:
parent
bc5d8ad040
commit
5f10d1aae6
@ -995,10 +995,19 @@ class _ResolutionsMenu extends StatefulWidget {
|
|||||||
State<_ResolutionsMenu> createState() => _ResolutionsMenuState();
|
State<_ResolutionsMenu> createState() => _ResolutionsMenuState();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const double _kCustonResolutionEditingWidth = 42;
|
||||||
|
const _kCustomResolutionValue = 'custom';
|
||||||
|
String? _lastResolutionGroupValue;
|
||||||
|
|
||||||
class _ResolutionsMenuState extends State<_ResolutionsMenu> {
|
class _ResolutionsMenuState extends State<_ResolutionsMenu> {
|
||||||
String _groupValue = '';
|
String _groupValue = '';
|
||||||
Resolution? _localResolution;
|
Resolution? _localResolution;
|
||||||
|
|
||||||
|
late final TextEditingController _customWidth =
|
||||||
|
TextEditingController(text: display.width.toString());
|
||||||
|
late final TextEditingController _customHeight =
|
||||||
|
TextEditingController(text: display.height.toString());
|
||||||
|
|
||||||
PeerInfo get pi => widget.ffi.ffiModel.pi;
|
PeerInfo get pi => widget.ffi.ffiModel.pi;
|
||||||
FfiModel get ffiModel => widget.ffi.ffiModel;
|
FfiModel get ffiModel => widget.ffi.ffiModel;
|
||||||
Display get display => ffiModel.display;
|
Display get display => ffiModel.display;
|
||||||
@ -1012,22 +1021,20 @@ class _ResolutionsMenuState extends State<_ResolutionsMenu> {
|
|||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
final isVirtualDisplay = display.isVirtualDisplayResolution;
|
final isVirtualDisplay = display.isVirtualDisplayResolution;
|
||||||
// final visible =
|
final visible =
|
||||||
// ffiModel.keyboard && (isVirtualDisplay || resolutions.length > 1);
|
ffiModel.keyboard && (isVirtualDisplay || resolutions.length > 1);
|
||||||
final visible = ffiModel.keyboard && resolutions.length > 1;
|
|
||||||
if (!visible) return Offstage();
|
if (!visible) return Offstage();
|
||||||
_groupValue = '${display.width}x${display.height}';
|
|
||||||
_getLocalResolution();
|
_getLocalResolution();
|
||||||
final showOriginalBtn =
|
final showOriginalBtn =
|
||||||
display.isOriginalResolutionSet && !display.isOriginalResolution;
|
display.isOriginalResolutionSet && !display.isOriginalResolution;
|
||||||
final showFitLocalBtn = !_isRemoteResolutionFitLocal();
|
final showFitLocalBtn = !_isRemoteResolutionFitLocal();
|
||||||
|
_setGroupValue();
|
||||||
return _SubmenuButton(
|
return _SubmenuButton(
|
||||||
ffi: widget.ffi,
|
ffi: widget.ffi,
|
||||||
menuChildren: <Widget>[
|
menuChildren: <Widget>[
|
||||||
_OriginalResolutionMenuButton(showOriginalBtn),
|
_OriginalResolutionMenuButton(showOriginalBtn),
|
||||||
_FitLocalResolutionMenuButton(showFitLocalBtn),
|
_FitLocalResolutionMenuButton(showFitLocalBtn),
|
||||||
// _customResolutionMenuButton(isVirtualDisplay),
|
_customResolutionMenuButton(isVirtualDisplay),
|
||||||
_menuDivider(showOriginalBtn, showFitLocalBtn, isVirtualDisplay),
|
_menuDivider(showOriginalBtn, showFitLocalBtn, isVirtualDisplay),
|
||||||
] +
|
] +
|
||||||
_supportedResolutionMenuButtons(),
|
_supportedResolutionMenuButtons(),
|
||||||
@ -1035,6 +1042,14 @@ class _ResolutionsMenuState extends State<_ResolutionsMenu> {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
_setGroupValue() {
|
||||||
|
if (_lastResolutionGroupValue == _kCustomResolutionValue) {
|
||||||
|
_groupValue = _kCustomResolutionValue;
|
||||||
|
} else {
|
||||||
|
_groupValue = '${display.width}x${display.height}';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
_menuDivider(
|
_menuDivider(
|
||||||
bool showOriginalBtn, bool showFitLocalBtn, bool isVirtualDisplay) {
|
bool showOriginalBtn, bool showFitLocalBtn, bool isVirtualDisplay) {
|
||||||
return Offstage(
|
return Offstage(
|
||||||
@ -1060,12 +1075,24 @@ class _ResolutionsMenuState extends State<_ResolutionsMenu> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
_onChanged(String? value) async {
|
_onChanged(String? value) async {
|
||||||
|
_lastResolutionGroupValue = value;
|
||||||
if (value == null) return;
|
if (value == null) return;
|
||||||
final list = value.split('x');
|
|
||||||
if (list.length == 2) {
|
int? w;
|
||||||
final w = int.tryParse(list[0]);
|
int? h;
|
||||||
final h = int.tryParse(list[1]);
|
if (value == _kCustomResolutionValue) {
|
||||||
if (w != null && h != null) {
|
w = int.tryParse(_customWidth.text);
|
||||||
|
h = int.tryParse(_customHeight.text);
|
||||||
|
} else {
|
||||||
|
final list = value.split('x');
|
||||||
|
if (list.length == 2) {
|
||||||
|
w = int.tryParse(list[0]);
|
||||||
|
h = int.tryParse(list[1]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (w != null && h != null) {
|
||||||
|
if (w != display.width && h != display.height) {
|
||||||
await _changeResolution(w, h);
|
await _changeResolution(w, h);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1117,6 +1144,46 @@ class _ResolutionsMenuState extends State<_ResolutionsMenu> {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Widget _customResolutionMenuButton(isVirtualDisplay) {
|
||||||
|
return RdoMenuButton(
|
||||||
|
value: _kCustomResolutionValue,
|
||||||
|
groupValue: _groupValue,
|
||||||
|
onChanged: _onChanged,
|
||||||
|
ffi: widget.ffi,
|
||||||
|
child: Row(
|
||||||
|
children: [
|
||||||
|
Text('${translate('resolution_custom_tip')} '),
|
||||||
|
SizedBox(
|
||||||
|
width: _kCustonResolutionEditingWidth,
|
||||||
|
child: _resolutionInput(_customWidth),
|
||||||
|
),
|
||||||
|
Text(' x '),
|
||||||
|
SizedBox(
|
||||||
|
width: _kCustonResolutionEditingWidth,
|
||||||
|
child: _resolutionInput(_customHeight),
|
||||||
|
),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
TextField _resolutionInput(TextEditingController controller) {
|
||||||
|
return TextField(
|
||||||
|
decoration: InputDecoration(
|
||||||
|
border: InputBorder.none,
|
||||||
|
isDense: true,
|
||||||
|
contentPadding: EdgeInsets.fromLTRB(3, 3, 3, 3),
|
||||||
|
),
|
||||||
|
keyboardType: TextInputType.number,
|
||||||
|
inputFormatters: <TextInputFormatter>[
|
||||||
|
FilteringTextInputFormatter.digitsOnly,
|
||||||
|
LengthLimitingTextInputFormatter(4),
|
||||||
|
FilteringTextInputFormatter.allow(RegExp(r'[0-9]')),
|
||||||
|
],
|
||||||
|
controller: controller,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
List<Widget> _supportedResolutionMenuButtons() => resolutions
|
List<Widget> _supportedResolutionMenuButtons() => resolutions
|
||||||
.map((e) => RdoMenuButton(
|
.map((e) => RdoMenuButton(
|
||||||
value: '${e.width}x${e.height}',
|
value: '${e.width}x${e.height}',
|
||||||
@ -1655,14 +1722,14 @@ class RdoMenuButton<T> extends StatelessWidget {
|
|||||||
final ValueChanged<T?>? onChanged;
|
final ValueChanged<T?>? onChanged;
|
||||||
final Widget? child;
|
final Widget? child;
|
||||||
final FFI ffi;
|
final FFI ffi;
|
||||||
const RdoMenuButton(
|
const RdoMenuButton({
|
||||||
{Key? key,
|
Key? key,
|
||||||
required this.value,
|
required this.value,
|
||||||
required this.groupValue,
|
required this.groupValue,
|
||||||
required this.onChanged,
|
required this.child,
|
||||||
required this.child,
|
required this.ffi,
|
||||||
required this.ffi})
|
this.onChanged,
|
||||||
: super(key: key);
|
}) : super(key: key);
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user