| 
									
										
										
										
											2023-08-04 13:11:24 +08:00
										 |  |  | import 'dart:math'; | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-02-03 15:07:45 +08:00
										 |  |  | import 'package:flutter/material.dart'; | 
					
						
							| 
									
										
										
										
											2023-08-03 16:48:14 +08:00
										 |  |  | import 'package:flutter_hbb/models/peer_model.dart'; | 
					
						
							| 
									
										
										
										
											2023-02-03 15:07:45 +08:00
										 |  |  | import 'package:flutter_hbb/models/platform_model.dart'; | 
					
						
							| 
									
										
										
										
											2023-08-03 16:48:14 +08:00
										 |  |  | import 'package:get/get.dart'; | 
					
						
							| 
									
										
										
										
											2023-02-03 15:07:45 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  | import '../common.dart'; | 
					
						
							|  |  |  | import 'model.dart'; | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-08-03 16:48:14 +08:00
										 |  |  | enum PeerTabIndex { | 
					
						
							|  |  |  |   recent, | 
					
						
							|  |  |  |   fav, | 
					
						
							|  |  |  |   lan, | 
					
						
							|  |  |  |   ab, | 
					
						
							|  |  |  |   group, | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-02-03 15:07:45 +08:00
										 |  |  | const String defaultGroupTabname = 'Group'; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | class PeerTabModel with ChangeNotifier { | 
					
						
							|  |  |  |   WeakReference<FFI> parent; | 
					
						
							|  |  |  |   int get currentTab => _currentTab; | 
					
						
							|  |  |  |   int _currentTab = 0; // index in tabNames
 | 
					
						
							|  |  |  |   List<String> tabNames = [ | 
					
						
							|  |  |  |     'Recent Sessions', | 
					
						
							|  |  |  |     'Favorites', | 
					
						
							|  |  |  |     'Discovered', | 
					
						
							|  |  |  |     'Address Book', | 
					
						
							| 
									
										
										
										
											2023-06-23 17:05:48 +08:00
										 |  |  |     //defaultGroupTabname,
 | 
					
						
							| 
									
										
										
										
											2023-02-03 15:07:45 +08:00
										 |  |  |   ]; | 
					
						
							| 
									
										
										
										
											2023-06-21 16:04:52 +08:00
										 |  |  |   final List<IconData> icons = [ | 
					
						
							| 
									
										
										
										
											2023-06-23 12:58:27 +08:00
										 |  |  |     Icons.access_time_filled, | 
					
						
							| 
									
										
										
										
											2023-06-21 16:04:52 +08:00
										 |  |  |     Icons.star, | 
					
						
							|  |  |  |     Icons.explore, | 
					
						
							|  |  |  |     IconFont.addressBook, | 
					
						
							|  |  |  |     Icons.group, | 
					
						
							|  |  |  |   ]; | 
					
						
							|  |  |  |   List<int> get indexs => List.generate(tabNames.length, (index) => index); | 
					
						
							| 
									
										
										
										
											2023-08-03 16:48:14 +08:00
										 |  |  |   List<Peer> _selectedPeers = List.empty(growable: true); | 
					
						
							|  |  |  |   List<Peer> get selectedPeers => _selectedPeers; | 
					
						
							|  |  |  |   bool get multiSelectionMode => _selectedPeers.isNotEmpty; | 
					
						
							|  |  |  |   List<Peer> _currentTabCachedPeers = List.empty(growable: true); | 
					
						
							|  |  |  |   List<Peer> get currentTabCachedPeers => _currentTabCachedPeers; | 
					
						
							| 
									
										
										
										
											2023-08-04 13:11:24 +08:00
										 |  |  |   bool isShiftDown = false; | 
					
						
							|  |  |  |   String? _shiftAnchorId; | 
					
						
							| 
									
										
										
										
											2023-02-03 15:07:45 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   PeerTabModel(this.parent) { | 
					
						
							|  |  |  |     // init currentTab
 | 
					
						
							|  |  |  |     _currentTab = | 
					
						
							|  |  |  |         int.tryParse(bind.getLocalFlutterConfig(k: 'peer-tab-index')) ?? 0; | 
					
						
							| 
									
										
										
										
											2023-06-21 16:04:52 +08:00
										 |  |  |     if (_currentTab < 0 || _currentTab >= tabNames.length) { | 
					
						
							|  |  |  |       _currentTab = 0; | 
					
						
							| 
									
										
										
										
											2023-02-03 15:07:45 +08:00
										 |  |  |     } | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   setCurrentTab(int index) { | 
					
						
							|  |  |  |     if (_currentTab != index) { | 
					
						
							|  |  |  |       _currentTab = index; | 
					
						
							|  |  |  |       notifyListeners(); | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-06-21 16:04:52 +08:00
										 |  |  |   String tabTooltip(int index, String groupName) { | 
					
						
							| 
									
										
										
										
											2023-02-03 15:07:45 +08:00
										 |  |  |     if (index >= 0 && index < tabNames.length) { | 
					
						
							| 
									
										
										
										
											2023-08-03 16:48:14 +08:00
										 |  |  |       if (index == PeerTabIndex.group.index) { | 
					
						
							| 
									
										
										
										
											2023-06-21 16:04:52 +08:00
										 |  |  |         if (gFFI.userModel.isAdmin.value || groupName.isEmpty) { | 
					
						
							|  |  |  |           return translate(defaultGroupTabname); | 
					
						
							| 
									
										
										
										
											2023-02-03 15:07:45 +08:00
										 |  |  |         } else { | 
					
						
							| 
									
										
										
										
											2023-06-21 16:04:52 +08:00
										 |  |  |           return '${translate('Group')}: $groupName'; | 
					
						
							| 
									
										
										
										
											2023-02-03 15:07:45 +08:00
										 |  |  |         } | 
					
						
							|  |  |  |       } else { | 
					
						
							| 
									
										
										
										
											2023-06-21 16:04:52 +08:00
										 |  |  |         return translate(tabNames[index]); | 
					
						
							| 
									
										
										
										
											2023-02-03 15:07:45 +08:00
										 |  |  |       } | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |     assert(false); | 
					
						
							|  |  |  |     return index.toString(); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-06-21 16:04:52 +08:00
										 |  |  |   IconData tabIcon(int index) { | 
					
						
							|  |  |  |     if (index >= 0 && index < tabNames.length) { | 
					
						
							|  |  |  |       return icons[index]; | 
					
						
							| 
									
										
										
										
											2023-02-03 15:07:45 +08:00
										 |  |  |     } | 
					
						
							| 
									
										
										
										
											2023-06-21 16:04:52 +08:00
										 |  |  |     assert(false); | 
					
						
							|  |  |  |     return Icons.help; | 
					
						
							| 
									
										
										
										
											2023-02-03 15:07:45 +08:00
										 |  |  |   } | 
					
						
							| 
									
										
										
										
											2023-08-03 16:48:14 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   togglePeerSelect(Peer peer) { | 
					
						
							| 
									
										
										
										
											2023-08-04 13:11:24 +08:00
										 |  |  |     final cached = _currentTabCachedPeers.map((e) => e.id).toList(); | 
					
						
							|  |  |  |     int thisIndex = cached.indexOf(peer.id); | 
					
						
							|  |  |  |     int closestIndex = -1; | 
					
						
							|  |  |  |     String? closestId; | 
					
						
							|  |  |  |     int smallestDiff = -1; | 
					
						
							|  |  |  |     for (var i = 0; i < cached.length; i++) { | 
					
						
							|  |  |  |       if (isPeerSelected(cached[i])) { | 
					
						
							|  |  |  |         int diff = (i - thisIndex).abs(); | 
					
						
							|  |  |  |         if (smallestDiff == -1 || diff < smallestDiff) { | 
					
						
							|  |  |  |           closestIndex = i; | 
					
						
							|  |  |  |           closestId = cached[i]; | 
					
						
							|  |  |  |           smallestDiff = diff; | 
					
						
							|  |  |  |         } | 
					
						
							|  |  |  |       } | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |     if (isShiftDown && | 
					
						
							|  |  |  |         thisIndex >= 0 && | 
					
						
							|  |  |  |         closestIndex >= 0 && | 
					
						
							|  |  |  |         closestId != null) { | 
					
						
							|  |  |  |       int shiftAnchorIndex = cached.indexOf(_shiftAnchorId ?? ''); | 
					
						
							|  |  |  |       if (shiftAnchorIndex < 0) { | 
					
						
							|  |  |  |         // use closest as shift anchor, rather than focused which we don't have
 | 
					
						
							|  |  |  |         shiftAnchorIndex = closestIndex; | 
					
						
							|  |  |  |         _shiftAnchorId = closestId; | 
					
						
							|  |  |  |       } | 
					
						
							|  |  |  |       int start = min(shiftAnchorIndex, thisIndex); | 
					
						
							|  |  |  |       int end = max(shiftAnchorIndex, thisIndex); | 
					
						
							|  |  |  |       _selectedPeers.clear(); | 
					
						
							|  |  |  |       for (var i = start; i <= end; i++) { | 
					
						
							|  |  |  |         if (!isPeerSelected(cached[i])) { | 
					
						
							|  |  |  |           _selectedPeers.add(_currentTabCachedPeers[i]); | 
					
						
							|  |  |  |         } | 
					
						
							|  |  |  |       } | 
					
						
							| 
									
										
										
										
											2023-08-03 16:48:14 +08:00
										 |  |  |     } else { | 
					
						
							| 
									
										
										
										
											2023-08-04 13:11:24 +08:00
										 |  |  |       if (isPeerSelected(peer.id)) { | 
					
						
							|  |  |  |         _selectedPeers.removeWhere((p) => p.id == peer.id); | 
					
						
							|  |  |  |       } else { | 
					
						
							|  |  |  |         _selectedPeers.add(peer); | 
					
						
							|  |  |  |       } | 
					
						
							|  |  |  |       _shiftAnchorId = null; | 
					
						
							| 
									
										
										
										
											2023-08-03 16:48:14 +08:00
										 |  |  |     } | 
					
						
							|  |  |  |     notifyListeners(); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   closeSelection() { | 
					
						
							|  |  |  |     _selectedPeers.clear(); | 
					
						
							| 
									
										
										
										
											2023-08-04 13:11:24 +08:00
										 |  |  |     _shiftAnchorId = null; | 
					
						
							| 
									
										
										
										
											2023-08-03 16:48:14 +08:00
										 |  |  |     notifyListeners(); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   setCurrentTabCachedPeers(List<Peer> peers) { | 
					
						
							|  |  |  |     Future.delayed(Duration.zero, () { | 
					
						
							|  |  |  |       _currentTabCachedPeers = peers; | 
					
						
							|  |  |  |       notifyListeners(); | 
					
						
							|  |  |  |     }); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   selectAll() { | 
					
						
							|  |  |  |     _selectedPeers = _currentTabCachedPeers.toList(); | 
					
						
							|  |  |  |     notifyListeners(); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   bool isPeerSelected(String id) { | 
					
						
							|  |  |  |     return selectedPeers.firstWhereOrNull((p) => p.id == id) != null; | 
					
						
							|  |  |  |   } | 
					
						
							| 
									
										
										
										
											2023-02-03 15:07:45 +08:00
										 |  |  | } |