33using System . Collections . Generic ;
44using System . Collections . ObjectModel ;
55using System . ComponentModel ;
6- using System . IO ;
76using System . Linq ;
87using System . Threading . Tasks ;
98using System . Windows . Data ;
109using System . Windows . Input ;
1110using System . Windows . Threading ;
1211using Windows . Devices . WiFi ;
12+ using Windows . Foundation . Metadata ;
1313using Windows . Security . Credentials ;
14+ using Windows . System ;
1415using LiveCharts ;
1516using LiveCharts . Wpf ;
17+ using log4net ;
1618using MahApps . Metro . Controls . Dialogs ;
1719using NETworkManager . Localization ;
1820using NETworkManager . Localization . Resources ;
@@ -28,24 +30,40 @@ namespace NETworkManager.ViewModels;
2830public class WiFiViewModel : ViewModelBase
2931{
3032 #region Variables
31-
3233 private readonly IDialogCoordinator _dialogCoordinator ;
3334
35+ private static readonly ILog Log = LogManager . GetLogger ( typeof ( WiFiViewModel ) ) ;
36+
3437 private readonly bool _isLoading ;
3538 private readonly DispatcherTimer _autoRefreshTimer = new ( ) ;
3639 private readonly DispatcherTimer _hideConnectionStatusMessageTimer = new ( ) ;
3740
38- private bool _sdkContractsFailedToLoad ;
41+ private bool _sdkContractAvailable ;
42+
43+ public bool SdkContractAvailable
44+ {
45+ get => _sdkContractAvailable ;
46+ set
47+ {
48+ if ( value == _sdkContractAvailable )
49+ return ;
50+
51+ _sdkContractAvailable = value ;
52+ OnPropertyChanged ( ) ;
53+ }
54+ }
55+
56+ private bool _wiFiAdapterAccessEnabled ;
3957
40- public bool SdkContractsFailedToLoad
58+ public bool WiFiAdapterAccessEnabled
4159 {
42- get => _sdkContractsFailedToLoad ;
60+ get => _wiFiAdapterAccessEnabled ;
4361 set
4462 {
45- if ( value == _sdkContractsFailedToLoad )
63+ if ( value == _wiFiAdapterAccessEnabled )
4664 return ;
4765
48- _sdkContractsFailedToLoad = value ;
66+ _wiFiAdapterAccessEnabled = value ;
4967 OnPropertyChanged ( ) ;
5068 }
5169 }
@@ -398,6 +416,26 @@ public WiFiViewModel(IDialogCoordinator instance)
398416
399417 _dialogCoordinator = instance ;
400418
419+ // Check if Microsoft.Windows.SDK.Contracts is available
420+ SdkContractAvailable = ApiInformation . IsTypePresent ( "Windows.Devices.WiFi.WiFiAdapter" ) ;
421+
422+ if ( ! SdkContractAvailable )
423+ {
424+ _isLoading = false ;
425+
426+ return ;
427+ }
428+
429+ // Check if the access is denied and show a message
430+ WiFiAdapterAccessEnabled = RequestAccess ( ) ;
431+
432+ if ( ! WiFiAdapterAccessEnabled )
433+ {
434+ _isLoading = false ;
435+
436+ return ;
437+ }
438+
401439 // Result view + search
402440 NetworksView = CollectionViewSource . GetDefaultView ( Networks ) ;
403441 NetworksView . SortDescriptions . Add ( new SortDescription (
@@ -504,33 +542,54 @@ private void ExportAction()
504542 Export ( ) . ConfigureAwait ( false ) ;
505543 }
506544
545+ public ICommand OpenSettingsCommand => new RelayCommand ( _ => OpenSettingsAction ( ) ) ;
546+
547+ private static void OpenSettingsAction ( )
548+ {
549+ Launcher . LaunchUriAsync ( new Uri ( "ms-settings:privacy-location" ) ) ;
550+ }
507551 #endregion
508552
509553 #region Methods
510554
555+ /// <summary>
556+ /// Request access to the WiFi adapter.
557+ /// </summary>
558+ /// <returns>Fails if the access is denied.</returns>
559+ private static bool RequestAccess ( )
560+ {
561+ var accessStatus = WiFiAdapter . RequestAccessAsync ( ) . GetAwaiter ( ) . GetResult ( ) ;
562+
563+ return accessStatus == WiFiAccessStatus . Allowed ;
564+ }
565+
511566 private async Task LoadAdapters ( string adapterId = null )
512567 {
513568 IsAdaptersLoading = true ;
514569
570+ // Show a loading animation for the user
571+ await Task . Delay ( 2500 ) ;
572+
515573 try
516574 {
517575 Adapters = await WiFi . GetAdapterAsync ( ) ;
518-
519- // Check if we found any adapters
520- if ( Adapters . Count > 0 )
521- {
522- // Check for existing adapter id or select the first one
523- if ( string . IsNullOrEmpty ( adapterId ) )
524- SelectedAdapter = Adapters . FirstOrDefault ( ) ;
525- else
526- SelectedAdapter = Adapters . FirstOrDefault ( s => s . NetworkInterfaceInfo . Id . ToString ( ) == adapterId ) ??
527- Adapters . FirstOrDefault ( ) ;
528- }
529576 }
530- catch
531- ( FileNotFoundException ) // This exception is thrown, when the Microsoft.Windows.SDK.Contracts is not available...
577+ catch ( Exception ex )
532578 {
533- SdkContractsFailedToLoad = true ;
579+ Log . Error ( "Error trying to get WiFi adapters." , ex ) ;
580+
581+ Adapters . Clear ( ) ;
582+ }
583+
584+ // Check if we found any adapters
585+ if ( Adapters . Count > 0 )
586+ {
587+ // Check for existing adapter id or select the first one
588+ if ( string . IsNullOrEmpty ( adapterId ) )
589+ SelectedAdapter = Adapters . FirstOrDefault ( ) ;
590+ else
591+ SelectedAdapter = Adapters . FirstOrDefault ( s => s . NetworkInterfaceInfo . Id . ToString ( ) == adapterId ) ??
592+ Adapters . FirstOrDefault ( ) ;
534593 }
535594
536595 IsAdaptersLoading = false ;
0 commit comments