Skip to content

Commit

Permalink
[bluetooth] heart rate monitor sample for iOS & Android
Browse files Browse the repository at this point in the history
  • Loading branch information
conceptdev committed Oct 24, 2014
1 parent 0c8935c commit 91ea735
Show file tree
Hide file tree
Showing 54 changed files with 1,450 additions and 1 deletion.
21 changes: 21 additions & 0 deletions BluetoothHeartRateMonitor/HeartRateMonitor.Core/App.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
using System;
using Xamarin.Forms;
using Robotics.Mobile.Core.Bluetooth.LE;

namespace HeartRateMonitor
{
public class App
{
static IAdapter Adapter;

public static Page GetMainPage ()
{
return new NavigationPage (new DeviceList (Adapter));
}

public static void SetAdapter (IAdapter adapter) {
Adapter = adapter;
}
}
}

Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
using System;
using System.Globalization;
using Xamarin.Forms;

namespace HeartRateMonitor
{
public class EmptyStringConverter : IValueConverter
{
public object Convert (
object value,
Type targetType,
object parameter,
CultureInfo culture)
{
String str = (String)value;
return String.IsNullOrWhiteSpace (str) ? "<un-named device>" : str;
}

public object ConvertBack (
object value,
Type targetType,
object parameter,
CultureInfo culture)
{
throw new NotImplementedException ("EmptyStringConverter is one-way");
}
}
}

Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
using System;
using Xamarin.Forms;
using System.Globalization;

namespace HeartRateMonitor
{
public class GuidConverter : IValueConverter
{
public object Convert (
object value,
Type targetType,
object parameter,
CultureInfo culture)
{
Guid guid = (Guid)value;
return guid.ToString ();
}

public object ConvertBack (
object value,
Type targetType,
object parameter,
CultureInfo culture)
{
throw new NotImplementedException ("GuidConverter is one-way");
}
}
}

Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
<?xml version="1.0" encoding="utf-8"?>
<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup>
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
<ProjectTypeGuids>{786C830F-07A1-408B-BD7F-6EE04809D6DB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}</ProjectTypeGuids>
<ProjectGuid>{A1E14BEA-A9D9-46C5-83AA-8891A13E4837}</ProjectGuid>
<OutputType>Library</OutputType>
<RootNamespace>HeartRateMonitor</RootNamespace>
<AssemblyName>HeartRateMonitor</AssemblyName>
<TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
<TargetFrameworkProfile>Profile78</TargetFrameworkProfile>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<DebugSymbols>true</DebugSymbols>
<DebugType>full</DebugType>
<Optimize>false</Optimize>
<OutputPath>bin\Debug</OutputPath>
<DefineConstants>DEBUG;</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
<ConsolePause>false</ConsolePause>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
<DebugType>full</DebugType>
<Optimize>true</Optimize>
<OutputPath>bin\Release</OutputPath>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
<ConsolePause>false</ConsolePause>
</PropertyGroup>
<ItemGroup>
<Compile Include="App.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
<Compile Include="Pages\DeviceList.xaml.cs">
<DependentUpon>DeviceList.xaml</DependentUpon>
</Compile>
<Compile Include="Pages\ServiceList.xaml.cs">
<DependentUpon>ServiceList.xaml</DependentUpon>
</Compile>
<Compile Include="Pages\CharacteristicList.xaml.cs">
<DependentUpon>CharacteristicList.xaml</DependentUpon>
</Compile>
<Compile Include="Pages\CharacteristicDetail.xaml.cs">
<DependentUpon>CharacteristicDetail.xaml</DependentUpon>
</Compile>
<Compile Include="Extensions\GuidConverter.cs" />
<Compile Include="Extensions\EmptyStringConverter.cs" />
<Compile Include="Pages\CharacteristicDetail_Hrm.xaml.cs">
<DependentUpon>CharacteristicDetail_Hrm.xaml</DependentUpon>
</Compile>
</ItemGroup>
<Import Project="$(MSBuildExtensionsPath32)\Microsoft\Portable\$(TargetFrameworkVersion)\Microsoft.Portable.CSharp.targets" />
<Import Project="..\packages\Xamarin.Forms.1.2.3.6257\build\portable-win+net45+wp80+MonoAndroid10+MonoTouch10\Xamarin.Forms.targets" Condition="Exists('..\packages\Xamarin.Forms.1.2.3.6257\build\portable-win+net45+wp80+MonoAndroid10+MonoTouch10\Xamarin.Forms.targets')" />
<ItemGroup>
<Folder Include="Pages\" />
<Folder Include="Extensions\" />
</ItemGroup>
<ItemGroup>
<EmbeddedResource Include="Pages\DeviceList.xaml">
<Generator>MSBuild:Compile</Generator>
</EmbeddedResource>
<EmbeddedResource Include="Pages\ServiceList.xaml">
<Generator>MSBuild:Compile</Generator>
</EmbeddedResource>
<EmbeddedResource Include="Pages\CharacteristicList.xaml">
<Generator>MSBuild:Compile</Generator>
</EmbeddedResource>
<EmbeddedResource Include="Pages\CharacteristicDetail.xaml">
<Generator>MSBuild:Compile</Generator>
</EmbeddedResource>
<EmbeddedResource Include="Pages\CharacteristicDetail_Hrm.xaml">
<Generator>MSBuild:Compile</Generator>
</EmbeddedResource>
</ItemGroup>
<ItemGroup>
<Reference Include="Xamarin.Forms.Core">
<HintPath>..\packages\Xamarin.Forms.1.2.3.6257\lib\portable-win+net45+wp80+MonoAndroid10+MonoTouch10\Xamarin.Forms.Core.dll</HintPath>
</Reference>
<Reference Include="Xamarin.Forms.Xaml">
<HintPath>..\packages\Xamarin.Forms.1.2.3.6257\lib\portable-win+net45+wp80+MonoAndroid10+MonoTouch10\Xamarin.Forms.Xaml.dll</HintPath>
</Reference>
<Reference Include="Robotics.Mobile.Core">
<HintPath>..\Components\Monkey.Robotics-0.5\lib\ios\Robotics.Mobile.Core.dll</HintPath>
</Reference>
</ItemGroup>
<ItemGroup>
<None Include="packages.config" />
</ItemGroup>
</Project>
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
<?xml version="1.0" encoding="UTF-8"?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
x:Class="HeartRateMonitor.CharacteristicDetail"
Title="Characteristic">

<StackLayout>
<StackLayout.Padding>10,10,10,10</StackLayout.Padding>
<Label Text="Generic display of information from Bluetooth characteristic." />
<BoxView HeightRequest="3" WidthRequest="600" Color="Red" HorizontalOptions="CenterAndExpand" />

<Label Text="Name" TextColor="Gray" />
<Label x:Name="Name" Text="-" />

<Label Text="ID" TextColor="Gray" />
<Label x:Name="ID" Text="-" />

<Label Text="Raw Value" TextColor="Gray" />
<Label x:Name="RawValue" Text="-" />

<Label Text="String Value" TextColor="Gray" />
<Label x:Name="StringValue" Text="-" />
</StackLayout>
</ContentPage>
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
using System;
using System.Collections.Generic;
using Xamarin.Forms;
using Robotics.Mobile.Core.Bluetooth.LE;
using System.Diagnostics;
using System.Linq;

namespace HeartRateMonitor
{
public partial class CharacteristicDetail : ContentPage
{
IAdapter adapter;
IDevice device;
IService service;
ICharacteristic characteristic;

public CharacteristicDetail (IAdapter adapter, IDevice device, IService service, ICharacteristic characteristic)
{
InitializeComponent ();
this.characteristic = characteristic;

if (characteristic.CanUpdate) {
characteristic.ValueUpdated += (s, e) => {
Debug.WriteLine("characteristic.ValueUpdated");
Device.BeginInvokeOnMainThread( () => {
IsBusy = false; // only spin until the first result is received
UpdateDisplay(characteristic);
});

};
IsBusy = true;
characteristic.StartUpdates();
}
}

protected override async void OnAppearing ()
{
base.OnAppearing ();

if (characteristic.CanRead) {
var c = await characteristic.ReadAsync();
UpdateDisplay(c);
}
}

protected override void OnDisappearing()
{
base.OnDisappearing();
if (characteristic.CanUpdate) {
characteristic.StopUpdates();
}
}
void UpdateDisplay (ICharacteristic c) {
Name.Text = c.Name;
//ID.Text = c.ID.ToString();
ID.Text = c.ID.PartialFromUuid ();

var s = (from i in c.Value
select i.ToString ("X").PadRight(2, '0')).ToArray ();
RawValue.Text = string.Join (":", s);

if (c.ID == 0x2A37.UuidFromPartial ()) {
// heart rate
StringValue.Text = DecodeHeartRateCharacteristicValue (c.Value);
StringValue.TextColor = Color.Red;
} else {
StringValue.Text = c.StringValue;
StringValue.TextColor = Color.Default;
}

}

string DecodeHeartRateCharacteristicValue(byte[] data) {
ushort bpm = 0;
if ((data [0] & 0x01) == 0) {
bpm = data [1];
} else {
bpm = (ushort)data [1];
bpm = (ushort)(((bpm >> 8) & 0xFF) | ((bpm << 8) & 0xFF00));
}
return bpm.ToString () + " bpm";
}
}
}

Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
<?xml version="1.0" encoding="UTF-8"?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
x:Class="HeartRateMonitor.CharacteristicDetail_Hrm"
Title="HeartRate Characteristic">

<StackLayout>
<StackLayout.Padding>10,10,10,10</StackLayout.Padding>
<Label Text="Heart rate info." />
<BoxView HeightRequest="3" WidthRequest="600" Color="Red" HorizontalOptions="CenterAndExpand" />

<Label Text="Name" TextColor="Gray" />
<Label x:Name="Name" Text="-" />

<Label Text="ID" TextColor="Gray" />
<Label x:Name="ID" Text="-" />

<Label Text="Raw Value" TextColor="Gray" />
<Label x:Name="RawValue" Text="-" />

<Label Text="String Value" TextColor="Gray" />
<Label x:Name="StringValue" Text="-" />
</StackLayout>
</ContentPage>
Loading

0 comments on commit 91ea735

Please sign in to comment.