Building Connected Things with Windows 10 IoT and Microsoft Azure
Lab 03: ThingLabs Thingy™
Table of Contents
- Table of Contents
- Bill of Materials
- Overview
- Connecting the Sensors
- Build the App
- Run the App on a Device
- Conclusion & Next Steps
In this lab, you will expand on the Nightlight you created in the previous lab and build the ThingLabs Thingy™. In the following labs you will use the ThingLabs Thingy™ to connect to Azure IoT services and track all of this data.
Bill of Materials
What you will need:
- Raspberry Pi 2
- From the GrovePi+ Starter Kit for Raspberry Pi
- GrovePi shield
- Grove LED (red) × 1 + connector cable
- Grove LED (blue) × 1 + connector cable
- Grove Light Sensor × 1 + connector cable
- Grove Button Sensor x 1 + connector cable
- Grove Sound Sensor x 1 + connector cable
- Grove Buzzer x 1 + connector cable
- Grove RGB LCD Display x 1 + connector cable
- 5V (2A to 3A) Switching Power Supply w/ MicroUSB Cable
- A Wi-Fi Adapter (choose one from the list here)
- 8GB micro SD card - class 10 or better. Microsoft suggests one of the following:
If you haven’t already done so, complete the previous lab - ‘Nightlight’.
Overview
In this lab you will combine the Nightlight device you previously created with several other input sensors and output actuators. The device will:
- Capture the amount of ambient light
- Increase the brightness intensity of an LED inversely to the amount of ambient light measured.
- Display the ambient light measurment on an LCD display.
- The display will adjust its backlight brightness according to the amount of ambient light in the area.
- Enable a button to turn on and off an LED and trigger sound.
Connecting the Sensors
Connect the sensors and actuators to the GrovePi shield as illustrated here:
- Connect the red LED module to D6
- Connect the blue LED module to D5
- Connect the Button module to D4
- Connect the Buzzer module to D2
- Connect the Light Sensor to A2
- Connect the RGB LCD Display to one of the I2C ports.
Build the App
Like the apps in the ‘Hello, Windows IoT!’ and ‘Nightlight’ labs, the ThingLabs Thingy™ application is a Background Application (IoT) project in Visual Studio.
- Launch Visual Studio and start a new Background Application (IoT) (found in the Templates -> C# -> Windows -> Windows IoT Core node).
- Name the application Thingy.
- Add a reference to the GrovePi libraries the same way you did in the previous labs.
- To install GrovePi for Windows IoT, ensure thinglabs is the selected Package Source and run the following command from the Package Manager Console
Install-Package GrovePi
- Verify that GrovePi v1.0.7 was installed by reading the log in the Package Manager Console.
- Open the StartupTask.cs file. Add the following to the using statements at the top of the file.
Define the Class-level Variables for the Thingy
Sensor Variables
There are six class-level variables you will use to refer to the physical sensors and actuators:
- Digital Sensors and Actuators - Sensors and actuators that have on/off (i.e. 0 or 1) states.
- buzzer - An IBuzzer instance that derives from
GrovePi.Sensor
and exposes properties to get the current status of the buzzer and change its state. - button - An IButton instance that derives from
GrovePi.Sensor
and exposes properties to get the current status of the button and change its state. - redLed - An ILed instance that derives from
GrovePi.Sensor
and exposes properties to get the current status of the red LED and change its state. - blueLed - An ILed instance that derives from
GrovePi.Sensor
and exposes properties to get the current status of the blue LED and change its state.
- buzzer - An IBuzzer instance that derives from
- Analog Sensors - Sensors that expose a range of measurement from 0-1023.
- lightSensor - An ILightSensor instance that enables measuring ambient light and is connected on an analog pin.
- Inter-Integrated Circuit (I2C - pronounces Eye-Squared-See) - A multi-master, multi-slave, single-ended, serial computer bus.
- display - An _IRgbLcdDisplay__ instance that enables displaying text and background color on a screen.
You will define these as class-level variables to be used throughout the application.
- Add the following class-level variable definitions inside the
public sealed class StartupTask : IBackgroundTask
class definition:
State and Other Variables
There are six class-level variables you will use in this application:
- ambientLightThreshold - An int constant between 0 (dark) and 1023 (bright) that defines the measurement of ambient light at which the LED should be in a completely off state.
- brightness - An int variable to track the current LED brightness.
- actualAmbientLight - An int variable to track the current value of ambient light as measured by the light sensor.
- buttonState - A SensorStatus variable to track the state of the button.
- timer - A ThreadPoolTimer instance that will control the rate of sensor and actuator interactions.
- deferral - A BackgroundTaskDeferral instance that will allow the application to continue to run even after the
Run()
method has completed.
These are class-level variables that will be used primarily to track state of the sensors.
- Add the following class-level variable definitions immediately after the preceeding variables.
Instantiate the Objects and Start the Timer
Inside the Run(IBackgroundTaskInstance taskInstance)
method, you need to instantiate all of the objects you defined, including the timer. The time will begin ticking as soon as it is created. Within the timer’s TimePeriodElapsed callback, you will do all of the interaction with the sensors and actuators.
- Modify the
Run(IBackgroundTaskInstance taskInstance)
method as follows:
Handle the TimePeriodElapsed Event
As with the Nightlight lab, you will handle measuring light data and setting the LED brightness in the timer’s TimePeriodElapsed. You will also poll the Thingy for button state changes and handle them by doing the following:
- Evaluate the
button.CurrentState
against thebuttonState
state variable. If there is a state change you will:- Update the
buttonState
value to the new state. - Use the
ChangeState()
method to change the state of the blue LED and the buzzer.
- Update the
- Get the light value from the light sensor by calling
lightSensor.SensorValue()
. - Evaluate the light value against the
ambientLightThreshold
value. - If the light value is below the threshold (i.e. dark enough that the LED should be illuminated), map the difference between the light value and the threshold to an 8-bit range (0-255).
- Use the value derived above to set the intensity/brightness of the LED.
- Set the background color of the LCD display between blue (bright light) and white (no light).
- Set the text of the LCD display to show the current light measurement.
Interact with Sensors Using the Timer
Where you created the timer in the ThreadPoolTimer.CreatePeriodicTimer(Timer_Tick, TimeSpan.FromMilliseconds(200))
call do the following:
- Hover the mouse over the
Timer_Tick
reference until a light bulb appears. - Click the down arrow and select Generate method ‘StartupTask.Timer_Tick’.
- Add the following code for the Timer_Tick method.
Create a Range Mapping Method
In the preceding code, you determine the LED brightness by mapping the delta of the actual light and the threshold value to an 8-bit range. This is done using a custom method - Map()
. Using the Visual Studio light bulb feature, add the Map()
method.
Where you wrote brightness = Map(ambientLightThreshold - actualAmbientLight, 0, ambientLightThreshold, 0, 255);
, do the following:
- Hover the mouse over the
Map
reference until a light bulb appears. - Click the down arrow and select Generate method ‘StartupTask.Map’.
- Modify the
Map()
method as follows:
If you want to compare your code with the master lab code, you can find it in the ThingLabs - Thingy4Windows Github repo here.
Run the App on a Device
As in the previous lab, you will build the application locally and then deploy it to the Raspberry Pi 2 and open a remote debugging session using Visual Studio.
- Ensure ARM is selected in the Solution Platforms drop-down list in the toolbar
- Select Remote Machine from the Device list in the toolbar.
- You will be prompted with the Remote Connections dialog. You can select your device in one of two ways:
- Select your device from the list of Auto Detected devices, OR
- Type in the device name or IP address into the Manual Configuration text box (set the Authentication Mode to Universal (Unencrypted Protocol)) and click Select.
NOTE: You can verify or modify these values by navigating to the project properties. This can be accomplished by double-clicking the Properties node in Solution Explorer and clicking on the Debug tab on the left.
- Now press F5 to run the application and you should see (in the Output window) it building locally and then deploying on the Raspberry Pi 2.
Once the application is deployed and running, try changing the amount of light the light sensor is exposed to. As it gets darker, the LED should glow brighter (it will glow brightest in complete darkness). When there is enough light, the threshold will be surpassed and the LED will turn off completely.
Conclusion & Next Steps
Congratulations! You have created the ThingLabs Thingy™. In subsequent labs you will use the Thingy to connect to Azure IoT services and track all of this data. The concepts you learned in this lab are:
- Working with multiple sensors and actuators.
- Maintaining state while constantly polling sensors for state changes.
- Making annoying noises with buzzers.
In the next lab you will set up an Azure IoT Hub to use with the ThingLabs Thingy™.