Skip to content

Commit

Permalink
Bluetooth support
Browse files Browse the repository at this point in the history
EV3-Basic can access the EV3 over a Serial Port connection. Setup of the
connection must be done manually by the user, with the normal facilities
of the operating system (an explaination is available in he user manual)
  • Loading branch information
c0pperdragon committed Apr 6, 2015
1 parent 843352e commit 306a002
Show file tree
Hide file tree
Showing 14 changed files with 420 additions and 26 deletions.
30 changes: 29 additions & 1 deletion Documentation/Resources/Manual.txt
Original file line number Diff line number Diff line change
Expand Up @@ -182,7 +182,35 @@ but only the codes 1 - 255 (they are just plain C-style char strings).
The same holds for all elements of text arrays.
</P>


<H1 class="chapter">Bluetooth Support</H1>
<P>
Connecting the EV3 to your PC directly with an USB cable is the most easy and reliable
way to use it with EV3-Basic. Nevertheless, having to use the cable can be quite cumbersome
in many circumstances, especially when developing mobile robots.
</P>
<P>
When you have a working bluetooth faciliy on your PC (either with a bluetooth dongle or built-in),
you can configure the EV3 to communicate with the PC wirelessly. If not already done, you have
to "pair" the EV3 with your PC to allow communication. To do so, first activate the bluetooth
features on the EV3: In the settings menu, activate the "Visibility" and "Bluetooth" options.
Then on the PC, open the system dialog "Bluetooth Devices". There you can search for the device
and start to establish a connection to EV3. The process may be a bit lengthy and requires to
confirm the action on the
EV3 as well as on the PC, and you will even have to enter the correct coupling code in some place
(should be "1234").
</P>
<P>
Once the connection is set up and the automatic installation of the appropriate drivers is
finished, your PC can communicate with the EV3 over a so-called "Serial Port". Which will
be named "COM1", "COM3" or the like. You can check which name was actually assigned by looking
at the properties page of the EV3 bluetooth device.
</P>
<P>
To use the newly established connection with EV3-Basic, just start your program from
Small Basic or just start the EV3-Explorer. When no EV3 can be found directly connected via USB,
but there are possible "Serial Ports" available, the PC will prompt you to select one of
these ports. When this is indeed the port for the EV3, the connection will work.
</P>

<H1 class="chapter">Library Documentation</H1>
<P>
Expand Down
32 changes: 30 additions & 2 deletions Documentation/ev3basic_manual.html
Original file line number Diff line number Diff line change
Expand Up @@ -264,7 +264,35 @@ <H3 class="subchapter">Limitation for text</H3>
The same holds for all elements of text arrays.
</P>


<H1 class="chapter">Bluetooth Support</H1>
<P>
Connecting the EV3 to your PC directly with an USB cable is the most easy and reliable
way to use it with EV3-Basic. Nevertheless, having to use the cable can be quite cumbersome
in many circumstances, especially when developing mobile robots.
</P>
<P>
When you have a working bluetooth faciliy on your PC (either with a bluetooth dongle or built-in),
you can configure the EV3 to communicate with the PC wirelessly. If not already done, you have
to "pair" the EV3 with your PC to allow communication. To do so, first activate the bluetooth
features on the EV3: In the settings menu, activate the "Visibility" and "Bluetooth" options.
Then on the PC, open the system dialog "Bluetooth Devices". There you can search for the device
and start to establish a connection to EV3. The process may be a bit lengthy and requires to
confirm the action on the
EV3 as well as on the PC, and you will even have to enter the correct coupling code in some place
(should be "1234").
</P>
<P>
Once the connection is set up and the automatic installation of the appropriate drivers is
finished, your PC can communicate with the EV3 over a so-called "Serial Port". Which will
be named "COM1", "COM3" or the like. You can check which name was actually assigned by looking
at the properties page of the EV3 bluetooth device.
</P>
<P>
To use the newly established connection with EV3-Basic, just start your program from
Small Basic or just start the EV3-Explorer. When no EV3 can be found directly connected via USB,
but there are possible "Serial Ports" available, the PC will prompt you to select one of
these ports. When this is indeed the port for the EV3, the connection will work.
</P>

<H1 class="chapter">Library Documentation</H1>
<P>
Expand Down Expand Up @@ -838,7 +866,7 @@ <H4 class="parameter">index</H4>
<H4 class="returns">Returns</H4>
<P class="returnssummary">The command-line argument at the specified index.</P>
<H2 class="object">Sensor</H2>
<P class="objectsummary">Access sensors that are attached to the brick.<BR>To specify the sensor use the port number which is printed below the socket on the brick (for example 1).<BR>To access sensors of further bricks that are connected via daisy-chaining, use the next higher numbers instead (5 - 8 will access the sensors on the first daisy-chained brick, 9-13 the sensors on the next one and so on).</P>
<P class="objectsummary">Access sensors that are attached to the brick.<BR>To specify the sensor use the port number which is printed below the socket on the brick (for example 1).<BR>To access sensors of further bricks that are connected via daisy-chaining, use the next higher numbers instead (5 - 8 will access the sensors on the first daisy-chained brick, 9-12 the sensors on the next one and so on).</P>
<H3 class="operation">Sensor.CommunicateI2C (port, address, writebytes, readbytes, writedata)</H3>
<P class="operationsummary">Communicates with devices using the I2C protocol over one of the sensor ports.<BR>This command addresses one device on the I2C-bus and can send and receive multiple bytes. This feature could be used to attach a custom sensor or to communicate with any device that is capable to be connected to the I2C bus as a slave.</P>
<H4 class="parameter">port</H4>
Expand Down
125 changes: 125 additions & 0 deletions EV3Communication/ConnectionFinder.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,125 @@
/* EV3-Basic: A basic compiler to target the Lego EV3 brick
Copyright (C) 2015 Reinhard Grafl
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Threading;
using System.Threading;


namespace EV3Communication
{
public class ConnectionFinder
{
static EV3Connection reuse = null;

public static EV3Connection CreateConnection()
{
// check if can re-use connection
if (reuse!=null)
{
EV3Connection c = reuse;
reuse = null;
return c;
}

// first try to get an USB connection
try
{
return new EV3ConnectionUSB();
}
catch (Exception)
{ }


// when no USB connection available, check the serial ports
String[] ports = System.IO.Ports.SerialPort.GetPortNames();
for (int i = 0; i < ports.Length; i++)
{
// strange problem: Port names seem to end with an 'o'?
if (ports[i].EndsWith("o"))
{
ports[i] = ports[i].Substring(0, ports[i].Length - 1);
}
}
// when no serial ports are available at all, stop try
if (ports.Length<1)
{
throw new Exception("Found no brick and no serial ports");
}


// when there are serial ports, let user decide
Array.Sort(ports, StringComparer.InvariantCulture);
ConnectionTypeDialog dialog = null;
// Create an extra thread for the dialog window
Thread newWindowThread = new Thread(new ThreadStart(() =>
{
// Create and show the Window
var window = new ConnectionTypeDialog(ports);
// When the window closes, shut down the dispatcher
window.Closed += (s, e) =>
Dispatcher.CurrentDispatcher.BeginInvokeShutdown(DispatcherPriority.Background);
window.Show();
// let other thread get hold the window to check for finish
dialog = window;
// Start the Dispatcher Processing
System.Windows.Threading.Dispatcher.Run();
}));
// Set the apartment state
newWindowThread.SetApartmentState(ApartmentState.STA);
// Make the thread a background thread
newWindowThread.IsBackground = true;
// Start the thread
newWindowThread.Start();

// wait here until the window actually was created and user has answered the prompt or closed the window...
while (dialog==null || dialog.IsVisible)
{
System.Threading.Thread.Sleep(100);
}

String port = dialog.GetSelectedPort();
if (port == null)
{
throw new Exception("User did not select serial port");
}

return new EV3ConnectionBluetooth(port);
}

public static void CloseConnection(EV3Connection c)
{
if (reuse!=null)
{
reuse.Close();
reuse = null;
}
// keep open bluetooth connections for further use
if (c is EV3ConnectionBluetooth && c.IsOpen())
{
reuse = c;
}
else
{
c.Close();
}
}
}
}
14 changes: 14 additions & 0 deletions EV3Communication/ConnectionTypeDialog.xaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
<Window
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" x:Name="window"
Title="No EV3 found" Height="220" Width="300"
x:Class="EV3Communication.ConnectionTypeDialog" ResizeMode="NoResize"
>
<Grid Margin="15" RenderTransformOrigin="0.75,0.6">
<TextBlock Margin="0" TextWrapping="Wrap" Text="Could not find an EV3 brick connected via USB. Do you want to try one of the following serial ports instead?" VerticalAlignment="Top" RenderTransformOrigin="0.513,-0.627" Height="51"/>
<ListBox x:Name="PortList" SelectionChanged="PortList_SelectionChanged" HorizontalAlignment="Left" Height="90" Margin="0" VerticalAlignment="Bottom" Width="140" VerticalContentAlignment="Bottom" Cursor="Arrow" BorderThickness="1" FontWeight="Bold"/>
<Button Click="CloseButton_clicked" Content="Close" HorizontalAlignment="Right" Margin="0" VerticalAlignment="Bottom" Width="75" IsCancel="True"/>

</Grid>
</Window>

76 changes: 76 additions & 0 deletions EV3Communication/ConnectionTypeDialog.xaml.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
/* EV3-Basic: A basic compiler to target the Lego EV3 brick
Copyright (C) 2015 Reinhard Grafl
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;

namespace EV3Communication
{
/// <summary>
/// Interaction logic for ConnectionTypeDialog.xaml
/// </summary>
public partial class ConnectionTypeDialog : Window
{
private String[] ports;
private String selected;

public ConnectionTypeDialog(String[] ports)
{
this.ports = ports;
this.selected = null;

InitializeComponent();

foreach (String p in ports)
{
PortList.Items.Add(p);
}
}

public String GetSelectedPort()
{
return selected;
}

private void CloseButton_clicked(object sender, System.Windows.RoutedEventArgs e)
{
selected = null;
Close();
}

private void PortList_SelectionChanged(Object sender, EventArgs e)
{
if (PortList.SelectedIndex>=0 && PortList.SelectedIndex<ports.Length)
{
selected = ports[PortList.SelectedIndex];
Close();
}
}


}
}
15 changes: 15 additions & 0 deletions EV3Communication/EV3Communication.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -30,17 +30,26 @@
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<ItemGroup>
<Reference Include="PresentationCore" />
<Reference Include="PresentationFramework" />
<Reference Include="System" />
<Reference Include="System.Core" />
<Reference Include="System.Management" />
<Reference Include="System.Xml.Linq" />
<Reference Include="System.Data.DataSetExtensions" />
<Reference Include="System.Data" />
<Reference Include="System.Xml" />
<Reference Include="WindowsBase" />
</ItemGroup>
<ItemGroup>
<Compile Include="BinaryBuffer.cs" />
<Compile Include="ByteCodeBuffer.cs" />
<Compile Include="ConnectionFinder.cs" />
<Compile Include="ConnectionTypeDialog.xaml.cs">
<DependentUpon>ConnectionTypeDialog.xaml</DependentUpon>
</Compile>
<Compile Include="EV3Connection.cs" />
<Compile Include="EV3ConnectionBluetooth.cs" />
<Compile Include="EV3ConnectionUSB.cs" />
<Compile Include="EV3RemoteControler.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
Expand All @@ -62,6 +71,12 @@
<ItemGroup>
<None Include="Resources\WatchDog.txt" />
</ItemGroup>
<ItemGroup>
<Page Include="ConnectionTypeDialog.xaml">
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>
</Page>
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
<!-- To modify your build process, add your task inside one of the targets below and uncomment it.
Other similar extension points exist, see Microsoft.Common.targets.
Expand Down
3 changes: 2 additions & 1 deletion EV3Communication/EV3Connection.cs
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,8 @@ public abstract class EV3Connection
// low-level data transmission (implemented in specialized object)
public abstract void SendPacket(byte[] data);
public abstract byte[] ReceivePacket();
public abstract void Close();
public abstract bool IsOpen();
internal abstract void Close();

// counter for each message to correctly pair it to its reply
private static ushort messagecounter = 0;
Expand Down
Loading

0 comments on commit 306a002

Please sign in to comment.