Example #1
0
 /// <summary>
 /// This method wraps the traditional scan, but waits for the centralManager to be ready before initiating scan
 /// </summary>
 /// <param name="centralManager">The centralManager to scan with</param>
 /// <param name="restart">Stops any current scan running</param>
 /// <param name="config">ScanConfig parameters you would like to use</param>
 /// <returns></returns>
 public static IObservable <IScanResult> Scan(this ICentralManager centralManager, ScanConfig?config = null, bool restart = false)
 {
     if (restart && centralManager.IsScanning)
     {
         centralManager.StopScan(); // need a pause to wait for scan to end
     }
     return(centralManager.Scan(config));
 }
Example #2
0
        private void ScanToggleAsync()
        {
            if (this.IsScanning)
            {
                this.IsScanning = false;
                this._scan?.Dispose();
            }
            else
            {
                this.Peripherals.Clear();
                Debug.WriteLine("View" + Thread.CurrentThread.ManagedThreadId);

                this._scan = _centralManager
                             .Scan()
                             .Buffer(TimeSpan.FromSeconds(1))
                             .Synchronize()
                             .ObserveOn(XamarinDispatcherScheduler.Current)
                             .Subscribe(
                    results =>
                {
                    //Debug.WriteLine("within: " + Thread.CurrentThread.ManagedThreadId);

                    var list = new List <PeripheralItemViewModel>();
                    foreach (var result in results)
                    {
                        var peripheral = this.Peripherals.FirstOrDefault(x => x.Equals(result.Peripheral));
                        if (peripheral == null)
                        {
                            peripheral = list.FirstOrDefault(x => x.Equals(result.Peripheral));
                        }

                        if (peripheral != null)
                        {
                            peripheral.Update(result);
                        }
                        else
                        {
                            peripheral = new PeripheralItemViewModel(result.Peripheral);
                            peripheral.Update(result);
                            list.Add(peripheral);
                        }
                    }
                    foreach (var per in list)
                    {
                        this.Peripherals.Add(per);
                    }

                    RaisePropertyChanged(nameof(Peripherals));
                },
                    ex => Console.WriteLine("ERROR: " + ex.ToString())
                    )
                             .DisposeWith(this.DeactivateWith);

                this.IsScanning = true;
            }
            RaisePropertyChanged(nameof(Peripherals));
            RaisePropertyChanged(nameof(IsScanning));
        }
Example #3
0
 /// <summary>
 /// Scans only for distinct peripherals instead of repeating each peripheral scan response - this will only give you peripherals, not RSSI or ad packets
 /// </summary>
 /// <param name="centralManager"></param>
 /// <param name="config"></param>
 /// <returns></returns>
 public static IObservable <IPeripheral> ScanForUniquePeripherals(this ICentralManager centralManager, ScanConfig?config = null) => centralManager
 .Scan(config)
 .Distinct(x => x.Peripheral.Uuid)
 .Select(x => x.Peripheral);
Example #4
0
 /// <summary>
 /// This will scan until the peripheral a specific peripheral is found, then cancel the scan
 /// </summary>
 /// <param name="centralManager"></param>
 /// <param name="peripheralName"></param>
 /// <param name="includeLocalName"></param>
 /// <returns></returns>
 public static IObservable <IPeripheral> ScanUntilPeripheralFound(this ICentralManager centralManager, string peripheralName, bool includeLocalName = true) => centralManager
 .Scan()
 .Where(x =>
        x.Peripheral.Name?.Equals(peripheralName, StringComparison.OrdinalIgnoreCase) ?? false ||
        (includeLocalName && (x.AdvertisementData?.LocalName?.Equals(peripheralName, StringComparison.InvariantCultureIgnoreCase) ?? false))
        )
 .Take(1)
 .Select(x => x.Peripheral);
Example #5
0
 /// <summary>
 /// This will scan until the peripheral a specific peripheral is found, then cancel the scan
 /// </summary>
 /// <param name="centralManager"></param>
 /// <param name="peripheralUuid"></param>
 /// <returns></returns>
 public static IObservable <IPeripheral> ScanUntilPeripheralFound(this ICentralManager centralManager, Guid peripheralUuid) => centralManager
 .Scan()
 .Where(x => x.Peripheral.Uuid.Equals(peripheralUuid))
 .Take(1)
 .Select(x => x.Peripheral);
Example #6
0
        public AdapterViewModel(ICentralManager central,
                                INavigationService navigator,
                                IUserDialogs dialogs)
        {
            this.CanControlAdapterState = central.CanControlAdapterState();

            this.WhenAnyValue(x => x.SelectedPeripheral)
            .Skip(1)
            .Where(x => x != null)
            .SubOnMainThread(x => navigator.Navigate("Peripheral", ("Peripheral", x.Peripheral)));

            this.ToggleAdapterState = ReactiveCommand.Create(
                () =>
            {
                var poweredOn = central.Status == AccessState.Available;
                if (!central.TrySetAdapterState(!poweredOn))
                {
                    dialogs.Alert("Cannot change bluetooth adapter state");
                }
            }
                );

            this.ScanToggle = ReactiveCommand.Create(
                () =>
            {
                if (this.IsScanning)
                {
                    this.IsScanning = false;
                    this.scan?.Dispose();
                }
                else
                {
                    this.Peripherals.Clear();

                    this.scan = central
                                .Scan()
                                .Buffer(TimeSpan.FromSeconds(1))
                                .Synchronize()
                                .SubOnMainThread(
                        results =>
                    {
                        var list = new List <PeripheralItemViewModel>();
                        foreach (var result in results)
                        {
                            var peripheral = this.Peripherals.FirstOrDefault(x => x.Equals(result.Peripheral));
                            if (peripheral == null)
                            {
                                peripheral = list.FirstOrDefault(x => x.Equals(result.Peripheral));
                            }

                            if (peripheral != null)
                            {
                                peripheral.Update(result);
                            }
                            else
                            {
                                peripheral = new PeripheralItemViewModel(result.Peripheral);
                                peripheral.Update(result);
                                list.Add(peripheral);
                            }
                        }
                        if (list.Any())
                        {
                            this.Peripherals.AddRange(list);
                        }
                    },
                        ex => dialogs.Alert(ex.ToString(), "ERROR")
                        )
                                .DisposeWith(this.DeactivateWith);

                    this.IsScanning = true;
                }
            }
                );
        }
Example #7
0
 /// <summary>
 /// Scan for heart rate sensors.  Note that a lot of heart rate sensors do not advertise their service UUID
 /// </summary>
 /// <param name="adapter"></param>
 /// <returns></returns>
 public static IObservable <IScanResult> ScanForHeartRateSensors(this ICentralManager centralManager) => centralManager.Scan(new ScanConfig
 {
     ServiceUuids =
     {
         HeartRateServiceUuid
     }
 });
Example #8
0
        public AdapterViewModel(ICentralManager central,
                                INavigationService navigationService,
                                IUserDialogs dialogs)
        {
            this.SelectPeripheral = ReactiveCommand.CreateFromTask <ScanResultViewModel>(
                x => navigationService.Navigate(
                    "Peripheral",
                    ("Peripheral", x.Peripheral)
                    )
                );

            this.OpenSettings = ReactiveCommand.Create(() =>
            {
                if (central.Features.HasFlag(BleFeatures.OpenSettings))
                {
                    central.OpenSettings();
                }
                else
                {
                    dialogs.Alert("Cannot open bluetooth settings");
                }
            });

            this.ToggleAdapterState = ReactiveCommand.Create(
                () =>
            {
                if (central.CanControlAdapterState())
                {
                    var poweredOn = central.Status == AccessState.Available;
                    central.SetAdapterState(!poweredOn);
                }
                else
                {
                    dialogs.Alert("Cannot change bluetooth adapter state");
                }
            }
                );

            this.ScanToggle = ReactiveCommand.Create(
                () =>
            {
                if (this.IsScanning)
                {
                    this.scan?.Dispose();
                }
                else
                {
                    this.Peripherals.Clear();

                    this.scan = central
                                .Scan()
                                .Buffer(TimeSpan.FromSeconds(1))
                                .Synchronize()
                                .SubOnMainThread(
                        results =>
                    {
                        var list = new List <ScanResultViewModel>();
                        foreach (var result in results)
                        {
                            var dev = this.Peripherals.FirstOrDefault(x => x.Uuid.Equals(result.Peripheral.Uuid));

                            if (dev != null)
                            {
                                dev.TrySet(result);
                            }
                            else
                            {
                                dev = new ScanResultViewModel();
                                dev.TrySet(result);
                                list.Add(dev);
                            }
                        }
                        if (list.Any())
                        {
                            this.Peripherals.AddRange(list);
                        }
                    },
                        ex => dialogs.Alert(ex.ToString(), "ERROR")
                        )
                                .DisposeWith(this.DeactivateWith);
                }
            }
                );
        }
Example #9
0
 public static IObservable <Beacon> ScanForBeacons(this ICentralManager centralManager) => centralManager
 .Scan()
 .Where(x => x.IsBeacon())
 .Select(x => x.ToBeacon());
 /// <summary>
 /// This will scan until the peripheral a specific peripheral is found, then cancel the scan
 /// </summary>
 /// <param name="centralManager"></param>
 /// <param name="deviceName"></param>
 /// <returns></returns>
 public static IObservable <IPeripheral> ScanUntilPeripheralFound(this ICentralManager centralManager, string deviceName) => centralManager
 .Scan()
 .Where(x => x.Peripheral.Name?.Equals(deviceName, StringComparison.OrdinalIgnoreCase) ?? false)
 .Take(1)
 .Select(x => x.Peripheral);
Example #11
0
 public static IObservable <Beacon> ScanForBeacons(this ICentralManager centralManager, bool forMonitoring = false) => centralManager
 .Scan(new ScanConfig
 {
     //AndroidUseScanBatching = true,
     ScanType = forMonitoring
             ? BleScanType.LowPowered
             : BleScanType.Balanced
 })
 .Where(x => x.IsBeacon())
 .Select(x => x.AdvertisementData.ManufacturerData.Data.Parse(x.Rssi));