RSS

Tag Archives: Netduino

Microsoft TechDays 2013 Paris: une grand merci!

The greatest Microsoft event of Europe has just been closed in Paris, France.
I am soooo honored to have been mentioned in the “Geek in da House” session of Laurent Ellerbach.

Image00001

He presented two very interesting projects, both of them involving Netduino and a little hardware around.
In the first part of his session, Laurent presents his remotely controlled gardening sprinkler system. Afterward, his Netduino is used in a totally different way: as transmitter for IR commands against a Lego train. My help was just on the latter project.
Here is the link of the video (French speaking).
Have fun!

 
Leave a comment

Posted by on February 17, 2013 in .Net, Electronics, Software

 

Tags: , , , , ,

A playable Invaders-like game with a Netduino Plus 2

Finally here is my last article of the series about the GDI library for Netduino and how to use it.
The post guides you on how to create your own game, such an Invaders-like playable game.

WP_000337

WP_000321
Enjoy!

 
Leave a comment

Posted by on February 17, 2013 in .Net, Electronics, Software

 

Tags: , , , , , , ,

The GDI library for Netduino targets a LCD module

This time the article will show you how to use the GDI library for Netduino for driving a very common LCD character module.

Enjoy!

 
Leave a comment

Posted by on February 16, 2013 in .Net, Electronics, Software

 

Tags: , , , , , , ,

Animation with the GDI library for Netduino

This is my third article about the GDI library for Netduino.
This time the discussion is on how to create a simple animation for the Sure Electronics led-matrix.
Enjoy!

 
Leave a comment

Posted by on February 14, 2013 in .Net, Electronics, Software

 

Tags: , , , , , , ,

A simple yet versatile GDI library for Netduino

Okay, here is another article of mine regarding the led-matrix. It is a step-by-step tutorial on how to create static drawings with the GDI library for Netduino.

WP_000293
Have fun!

 
Leave a comment

Posted by on February 10, 2013 in Electronics

 

Tags: , , , , , ,

Sure Electronics Led-matrix driver for Netduino

Finally I done it!
Here is a link to my article explaining how to drive a Sure Electronics led-matrix module with a Netduino (Plus) 2.


Enjoy!

 
Leave a comment

Posted by on February 10, 2013 in Electronics

 

Tags: , , , , ,

Modbus libraries version 2 beta are out!

Today I published the version 2 (beta) of the Modbus libraries suite.
The most noticeable news is about the ordinary desktop .Net 4.5 support. This comes along a stunning Windows Store-like demo app for bidirectional testing with any Modbus-enabled Netduino.

demo0

demo1

demo2

demo3

This demo has been styled upon the brand-new Windows 8 “Modern-UI” rules, so that the incoming Windows RT libraries will feature a similar demo running on a tablet instead.

I also added the Windows Phone 8 support, but it looks exactly as the previous Windows Phone 7.5 release. I tested it only with the emulator not having any WP8-enabled phone.

Stay tuned!

 
1 Comment

Posted by on January 17, 2013 in .Net, Electronics, Software

 

Tags: , , , , , ,

How to get our Netduino running faster

Before going on on my graphic library for led matrix, I think it’s time to optimize a bit the code in order to get the Netduino running faster.
My job is programming application using .Net for desktop, but a PC is very rich of resources such as RAM and processor speed. Instead, the Micro Framework offers a very small environment where every byte more might have an impact on the final result.
running_cheetah_320x240
Here is a brief bunch of tests for showing a comparison on different approaches against a same task. Sometime you don’t care about the best way to write the code, but the interesting thing is actually knowing how the things are working. You will be surprised, as I was.

The test bench.

The base program for the tests is very simple: it is an endless loop where the code under test runs interleaved by a short pause of 100ms. The comparison is mostly against different yet commonly-used types, such as Int32, Single, Double and Byte.
The timings are taken by using a scope, then watching at two output ports when they change their state.
Except for the very first, each test cycles 50 times over a 20-operations set: that for minimize the overhead due to the “for-loop”. By the way, the first test is targeted just for get the “for-loop” heaviness.
It follows the test program template:

namespace PerformanceTest
{
    public class Program
    {
        private const int Count = 50;

        private static OutputPort QTest = new OutputPort(Pins.GPIO_PIN_D0, false);
        private static OutputPort QPulse = new OutputPort(Pins.GPIO_PIN_D1, false);


        public static void Main()
        {
            byte b;
            byte bx = 50;
            byte by = 16;

            int i;
            int ix = 50;
            int iy = 16;

            float f;
            float fx = 50.0f;
            float fy = 16.0f;

            double d;
            double dx = 50.0;
            double dy = 16.0;

            while (true)
            {
                //start of the test
                QTest.Write(true);


                // ... operations to test ...


                //end of the test
                QTest.Write(false);
                Thread.Sleep(100);
            }
        }


        private static void Pulse()
        {
            QPulse.Write(true);
            QPulse.Write(false);
        }

    }
}

The basic for-loop.

Since every test will use the “for-loop”, we should measure how much overhead that introduces.
Here is the snippet…

                for (int n = 0; n < 1000; n++)
                {
                    //do nothing
                }

…and here is the timing:
UNIT0000

Roughly speaking, we could say that every for-loop cycle takes about 7 microseconds.

How does look the IL-opcodes generated by the compiler (restricted to the only for-loop)?
Well, it is pretty interesting digging a bit behind (or under?) the scenes. I will take advantage by the awesome ILSpy, which is a free, open-source decompiler, disassembler and much more provided by the SharpDevelop teams.

		IL_0042: ldc.i4.0
		IL_0043: stloc.s n
		IL_0045: br.s IL_004f
		// loop start (head: IL_004f)
			IL_0047: nop
			IL_0048: nop
			IL_0049: ldloc.s n
			IL_004b: ldc.i4.1
			IL_004c: add
			IL_004d: stloc.s n

			IL_004f: ldloc.s n
			IL_0051: ldc.i4 1000
			IL_0056: clt
			IL_0058: stloc.s CS$4$0000
			IL_005a: ldloc.s CS$4$0000
			IL_005c: brtrue.s IL_0047
		// end loop

Notice how the final branch-on-true jumps back to the first opcode, which implies a couple of “nop”s: why?
Anyway, we are not going to optimize the for-loop yet.

Addition.

The addition will be performed over three common types: Int32, Single and Double.
Here is the snippet…

                for (int n = 0; n < Count; n++)
                {
                    i = ix + iy; //repeated 20 times
                }

                Pulse();

                for (int n = 0; n < Count; n++)
                {
                    f = fx + fy; //repeated 20 times
                }

                Pulse();

                for (int n = 0; n < Count; n++)
                {
                    d = dx + dy; //repeated 20 times
                }

…and here is the timing:
UNIT0001

Again, an “average” addition takes about 2 microseconds.

Many users are blaming the poor speed of a board like Netduino, because its core can run at over 200Mips. Two microseconds for an addition (integer or floating-point) seems a waste of performance, but…please, bear in mind that a so small yet inexpensive board performs similar about the same as an old 1984 IBM PC-AT machine (estimated price US$5000).

The interesting thing is that there’s almost no difference between using Int32 or Single, whose are both 32-bit based. Surprisingly, even choosing Double as type, the calculation takes insignificantly longer than the other cases. However, a Double takes 8 bytes.
Below there are the parts of IL whose depict the operations:

                        // ...

			IL_004e: ldloc.s ix
			IL_0050: ldloc.s iy
			IL_0052: add
			IL_0053: stloc.3
                        
                        // ...

			IL_00eb: ldloc.s fx
			IL_00ed: ldloc.s fy
			IL_00ef: add
			IL_00f0: stloc.s f
                        
                        // ...

			IL_019c: ldloc.s dx
			IL_019e: ldloc.s dy
			IL_01a0: add
			IL_01a1: stloc.s d
                        
                        // ...

Multiplication.

Here is the snippet…

                for (int n = 0; n < Count; n++)
                {
                    i = ix * iy; //repeated 20 times
                }

                Pulse();

                for (int n = 0; n < Count; n++)
                {
                    i = ix << 4; //repeated 20 times
                }

                Pulse();

                for (int n = 0; n < Count; n++)
                {
                    f = fx * fy; //repeated 20 times
                }

                Pulse();

                for (int n = 0; n < Count; n++)
                {
                    d = dx * dy; //repeated 20 times
                }

…and here is the timing:
UNIT0002

As for the addition, the multiplication takes almost the same time to perform and it seems there’s no significant loss of performance over different data types.
There is an extra-special case, which calculates the multiplication leveraging the left-shift operator. It’s a very particular case, but it’s noticeable the better speed than an ordinary multiplication. Is it worthwhile choosing a shift over a real multiplication? I don’t believe…
Below there are the parts of IL whose depict the operations:

                        // ...

			IL_004e: ldloc.s ix
			IL_0050: ldloc.s iy
			IL_0052: mul
			IL_0053: stloc.3
                        
                        // ...

			IL_00e8: ldloc.s ix
			IL_00ea: ldc.i4.4
			IL_00eb: shl
			IL_00ec: stloc.3
                        
                        // ...

			IL_016e: ldloc.s fx
			IL_0170: ldloc.s fy
			IL_0172: mul
			IL_0173: stloc.s f
                        
                        // ...

			IL_021f: ldloc.s dx
			IL_0221: ldloc.s dy
			IL_0223: mul
			IL_0224: stloc.s d
                        
                        // ...

Logical AND.

Here is the snippet…

                for (int n = 0; n < Count; n++)
                {
                    i = ix & iy; //repeated 20 times
                }

                Pulse();

                for (int n = 0; n < Count; n++)
                {
                    b = (byte)(bx & by); //repeated 20 times
                }

…and here is the timing:
UNIT0003

It is clear that a logical operation like the AND takes almost the same as an ordinary addition between Int32-s. Instead, the interesting thing is seeing how different is working with Int32 and Byte.
Any .Net Framework operates at least on 32-bits operands (whereas possible it uses 64-bits). Thus, when you constrain your variables to a tiny byte, most operations will cast the values to Int32-s. That takes much more time to do and demonstrates why in the .Net world the speculation habits of small CPUs are wrong.
Below there are the parts of IL whose depict the operations:

                        // ...

			IL_004e: ldloc.s ix
			IL_0050: ldloc.s iy
			IL_0052: and
			IL_0053: stloc.3
                        
                        // ...

			IL_00e8: ldloc.1
			IL_00e9: ldloc.2
			IL_00ea: and
			IL_00eb: conv.u1
			IL_00ec: stloc.0
                        
                        // ...

Min/Max calculation.

Here is the snippet…

                for (int n = 0; n < Count; n++)
                {
                    i = System.Math.Min(ix, iy);
                    i = System.Math.Max(ix, iy);
                    // ... repeated 10 times
                }

                Pulse();

                for (int n = 0; n < Count; n++)
                {
                    i = ix < iy ? ix : iy;
                    i = ix > iy ? ix : iy;
                    // ... repeated 10 times
                }

                Pulse();

                for (int n = 0; n < Count; n++)
                {
                    i = ix; if (ix < iy) i = iy;
                    i = ix; if (ix > iy) i = iy;
                    // ... repeated 10 times
                }

…and here is the timing:
UNIT0005

Please, bear in mind that the time is 5x than the above charts.

Using a library function is preferable: we should avoid “reinventing the wheel” and most of the times a library function embeds native code and yields faster results. However, when that function is particularly simple, it could be better choosing another approach, such as in this example.
The timings clear shows that calling the framework’s Min/Max function takes about three-times than using a trivial ternary-if. Even using a third attempt for calculating the min/max yields no better results other than the most trivial way.
Let’s have a peek at the IL assembly:

                        // ...

			IL_004e: ldloc.s ix
			IL_0050: ldloc.s iy
			IL_0052: call int32 [mscorlib]System.Math::Min(int32, int32)
			IL_0057: stloc.3
                        
                        // ...

			IL_013b: ldloc.s ix
			IL_013d: ldloc.s iy
			IL_013f: blt.s IL_0145

			IL_0141: ldloc.s iy
			IL_0143: br.s IL_0147

			IL_0145: ldloc.s ix

			IL_0147: stloc.3
                        
                        // ...

			IL_0264: ldloc.s ix
			IL_0266: stloc.3
			IL_0267: ldloc.s ix
			IL_0269: ldloc.s iy
			IL_026b: clt
			IL_026d: ldc.i4.0
			IL_026e: ceq
			IL_0270: stloc.s CS$4$0000
			IL_0272: ldloc.s CS$4$0000
			IL_0274: brtrue.s IL_0279

			IL_0276: ldloc.s iy
			IL_0278: stloc.3
                        
                        // ...

Sample expression.

Here is the snippet…

                for (int n = 0; n < Count; n++)
                {
                    d = ix * (fx + dx) * (fy + dy); //repeated 20 times
                }

                Pulse();

                for (int n = 0; n < Count; n++)
                {
                    d = ix; 
                    d *= fx + dx; 
                    d *= (fy + dy);
                    // ... repeated 20 times
                }

…and here is the timing:
UNIT0004

The timings are showing that an inline-expression performs better than a compound operator. That’s normal, because the compiler actually does what the user wrote: store each intermediate operation in the variable. That forces the compiler to avoid optimizations such as in the inline syntax.
The IL opcodes demonstrate the longer task in the second case:

                        // ...

			IL_004e: ldloc.s ix
			IL_0050: conv.r8
			IL_0051: ldloc.s fx
			IL_0053: conv.r8
			IL_0054: ldloc.s dx
			IL_0056: add
			IL_0057: mul
			IL_0058: ldloc.s fy
			IL_005a: conv.r8
			IL_005b: ldloc.s dy
			IL_005d: add
			IL_005e: mul
			IL_005f: stloc.s d
                        
                        // ...

			IL_01ef: ldloc.s ix
			IL_01f1: conv.r8
			IL_01f2: stloc.s d
			IL_01f4: ldloc.s d
			IL_01f6: ldloc.s fx
			IL_01f8: conv.r8
			IL_01f9: ldloc.s dx
			IL_01fb: add
			IL_01fc: mul
			IL_01fd: stloc.s d
			IL_01ff: ldloc.s d
			IL_0201: ldloc.s fy
			IL_0203: conv.r8
			IL_0204: ldloc.s dy
			IL_0206: add
			IL_0207: mul
			IL_0208: stloc.s d
                        
                        // ...

Conclusion.

As a professional programmer, I ma obsessed by well-written source code, patterns, good-practices and so away. However, I also believe it’s useful to know when and how put your finger on a program to get the most from it.
That is also a good programming practice, IMHO.

 
13 Comments

Posted by on January 5, 2013 in .Net, Software

 

Tags: , , , ,

An example of an hardware problem and how to solve it

This post was not planned, in the sense that the main article is expected on the real working project (coming soon), not on the problems related. However, this is a typical case of hardware malfunction (due to a insufficient design redundancy), and it thought it was useful to show. I realized that most users not having a good practice in electronics, get discouraged when they try to replicate a circuit and that does not work as expected. They first wonder about the “logical equivalency” of the schematic/wiring, but that does not seem a good reason for make it working.
works-on-my-bb
Electronics is physics, I mean a small part of. So, the world is not working differently when we talk about electrons spinning or a logic chip connected to a micro-controller. However, the main task done for years by scientists is to simplify, to model, to minimize interaction between “electronic parts”, so that the design will become easier yet reliable.

Yesterday.

In this post I want to describe what happened to me yesterday, when I was trying to make the circuit working, but it did not wanted to. All my attention was payed on the software (written by me), on possible bugs in the new Netduino Plus 2, and even about some wrong wiring. None of these areas was the right one, but the most unsuspected component.

Image00003

The goal of the project is interfacing a Sure Electronics Led-matrix board to the Netduino Plus 2 with a minimal external hardware. By the way, the board can be SPI-driven with a couple more of signals. All I need is some pull-up resistor, just because the STM32 MCU used by the Netduino Plus 2 does not embed them as the Atmel does.
So far, so well.

Yesterday the C# software driver was completed and worked well…ehm, bad…or well?…Hard to say how…
According to the Sure Electronics datasheet, as well as the Holtek HT1632 datasheet, my driver running on the Netduino produced the waveform correctly. Every single pattern, command, and data have been checked on the scope, and looked fine. However, the leds on the board were not lighting at all, or -at most- randomly colorized.

Today.

I had a suspect on the board itself, but I refused it because I mumbled:

…these boards are sold worldwide in thousands units: how can be not working?

However, today I checked the board correctness against its schematic.
The first yet easy component to check was the mapper for enabling the HT1632 led-controllers. There are four controllers on my board, which is 16 rows by 32 columns, bi-color led-matrix. The mapper is a normal 74HC164 shift-register, similar but simpler than the famous 74HC595.
The software driver clocks the 74HC164 so that only one HT1632 is enabled at once. Basically the driver issues a logic “zero” to the shift-register input, then shifts once: this will move the zero to the first register output, while all the remaining are “one”. This enables only the first controller, and the driver feeds it with the matrix data. Every further clock should issue a logic “one”, so that the logic “zero” is “moving” forward on the register’s outputs, and the other controllers are enabled.

The 74HC164 used for enabling the led controllers.

The 74HC164 used for enabling the led controllers.


What made me shocking is the wrong output state of the register. Although the clocks were issued correctly, as well as the input data, the outputs were completely wrong, most of the times enabling more controllers at once. That was a very good reason for the leds lighting randomly!
So, my move was to inspect what made the shift-register shifting unexpectedly. To do that, I placed the first scope probe on the 74HC164 output activating badly, and the second probe on the same chip clock. At first glance there was no reason for the output getting low, because there was no clock edges. However, something must happen, because the 74HC164 actually shifts the data.
The 74HC164 clock (above) and its first output going low.

The 74HC164 clock (above) and the data input fed into.

The first output of the shift-register, which correctly goes low along a whole clock period.

The first output of the shift-register, which correctly goes low along a whole clock period.

The shifter's second output going low earlier than the second clock pulse.

The shifter’s second output going low earlier than the second clock pulse.

The clock generated by the Netduino is perfectly flat upon the output falling: that's suspect!

The clock generated by the Netduino is perfectly flat upon the output falling: that’s suspect!

The driver timings are around several milliseconds: even the new Netduino can’t reach microseconds pulses. By the way, the external logic does not care about milliseconds, and it works even on nanoseconds events.

The actual clock by the 74HC164 pin shows a small glitch shorter than 100nS.

The actual clock by the 74HC164 pin shows a small glitch shorter than 100nS.

I scaled the scope time-base up to sub-microseconds timings, and…GOTCHA!…a subtle pulse was causing the improper shifting.
Now, I didn’t know exactly where that pulse is originated, nor the very best way to avoid it. By the way, it had to cut off, otherwise the board won’t worked. Two guesses: stray capacitance (e.g. PCB tracking too tight), and/or bad grounding (e.g. leds’ current leads voltage drops).

The solution.

The easier way to cut a spike off is placing a small 1nF capacitor across the signal and ground (assuming the grounding is good).

The 1nF capacitor added to the board.

The 1nF capacitor added to the board.


The funny thing is that the capacitor was considered by design, but not mounted (at least on my board). I wonder why the Sure Electronics Engineers missed it.

The 74HC164 second output shows perfectly after the capacitor insertion.

The 74HC164 second output shows perfectly after the capacitor insertion.

Conclusions.

I know, it’s frustrating.
Most of the users having fun with Netduino are programmers, and they can’t accept that does not exist “copy-and-paste” for hardware. Well, it can be applied if the circuit model has enough redundancy so that most of the undesired effects and interactions can be ignored.
So, please, don’t trash your long awaited hardware project just because it does not work at first time. Dig, dig, and dig again. Also remember that a logic analyzer can’t replace a scope, but a scope most of the time can.

 
6 Comments

Posted by on December 28, 2012 in Electronics

 

Tags: , , , , ,

Infrared receiver driver for Netduino

Introduction.

Two Lego Power-Functions infrared remote commanders


This is the completion of my old article on how to create a simple infrared transmitter with your Netduino.

To tell the truth, I had no plans on creating such a receiver, but I needed a quick and easy way to send commands wirelessly to a Netduino installed over a toy. I’m having a lot of fun with mechanical toys, such as Lego or Eitech. That’s not a news for me, because these were my favorite playgrounds during my childhood. Now, with the *duino-revolution, the creativity really has no limit.

My very first attempt.

Here is my very first attempt of creating something hybrid with Lego/Eitech and Netduino. I can do all that only during my spare time (which is few), and I needed something easy, really easy. The easier way is infrared, because I already own a couple of Lego commanders, and I know that the Lego stuffs have already been used with success by Laurent Ellerbach. He’s much creative than me in the Lego-world, but my deal is create something to simple as the children can use.
So, I chose to start with a very simple model, such a small rover, built using an Eitech kit.

The top-view of the chassis.


The bottom-view with the two motors, and the two-series of cogs for an higher torque.


It’s very simple, because it has a couple of motors: each driving a belt. The direction can be modified adjusting the motors’ speed.

The hardware.

Everything is supposed to work upon the demodulated signal outputted by any common infrared-module. Vishay’s among the greatest manufacturers, but there are many models. I used the Vishay TSOP 31238, which is pretty old (I think obsolete), but still good. However, there’s a direct replacement.

Such a modules are very easy to find, yet cheap. It’s commonly used on several appliances, such as TVs, HiFi-sets, etc.
The real infrared light running from the commander is modulated using a carrier, normally ranging from 36 to 40 kHz. This frequency is too fast for a direct detection with the Netduino, but even using a faster MCU a good analog amplifier+filtering is needed. Thus, I strongly recommend to use an integrated module.
The connection of that module to the Netduino is literally trivial: just three wires.

The Vishay module is able to work either at +3.3V, and at +5V, so don’t mind what kind of supply you’ll choose. Also there’s no any difference in the final behavior, sensivity or else. In the picture I connected it at +3.3V.
As for the rover, I used two transistors (BC337) for the motors, which are driven by the PWMs. I also provided a couple of lights (green and red leds), directly driven by two Netduino’s outputs.

How the software works.

The infrared receiver driver is very simple: just a generic base class, which has to be derived to any specific-protocol decoder. At the moment of writing, there’s only the Lego protocol decoder, though.
The basic principle is sampling the falling edges of the module’s output, using a Netduino InterruptPort as sampler. On every interrupt there’s a timestamp indicating the absolute time: for higher resolution, I considered the “ticks”. One “tick” is the smallest time-unit defined by the .Net Framework (any flavor), and it equals to 100 nanoseconds. Also, I preferred the ticks over the whole “DateTime” structure, just because it’s an Int64, and its math is very simple compared to the DateTime complexity.
So, every interrupt there’s a new “interval” value, since the previous edge/interrupt. On the very first edge there’s no any “previous” reference, thus this event is useful for detecting the message start. On the same start, a timer is started.
Since the receiver is generic, it can’t know when the message is over. So the timer plays a crucial role for claiming the message termination. This is a trick, of course, but it doesn’t look so bad!
Once the timer expires, the collection of intervals is fed to the derivation (i.e. the concrete decoder), which analyzes the intervals’ values, and converts in logical bits. For that reason, the decoder may detect errors.
When everything goes well, the decoder can pack up a “message” object containing the useful data, and the type of that message is usually strictly dependent to the specific protocol. Anyway, the message is passed as argument for an event, which can notify the host application.
So far, the usage of the class is straightful:

    public class Program
    {
        private static PWM _wheelRight = new PWM(Pins.GPIO_PIN_D5);
        private static PWM _wheelLeft = new PWM(Pins.GPIO_PIN_D6);
        private static OutputPort _red = new OutputPort(Pins.GPIO_PIN_D0, false);
        private static OutputPort _green = new OutputPort(Pins.GPIO_PIN_D1, false);


        public static void Main()
        {
            //create the infrared receiver listening to the port 8
            var irrx = new InfraredLegoReceiver(Pins.GPIO_PIN_D8);
            irrx.InfraredMessageDecoded += irrx_InfraredMessageDecoded;
            irrx.IsEnabled = true;

            //do whatever

            Thread.Sleep(Timeout.Infinite);
        }


        static void irrx_InfraredMessageDecoded(
            object sender, 
            InfraredMessageDecodedEventArgs e)
        {
            var message = (LegoMessage)e.Message;
            //Debug.Print(message.Mode + " " + message.Func);

            switch (message.Func & 0x03)
            {
                case 0:
                    _wheelLeft.SetDutyCycle(0);
                    _red.Write(false);
                    break;

                case 1:
                    _wheelLeft.SetDutyCycle(100);
                    break;

                case 2:
                    _red.Write(true);
                    break;
            }

            switch (message.Func & 0x0C)
            {
                case 0:
                    _wheelRight.SetDutyCycle(0);
                    _green.Write(false);
                    break;

                case 4:
                    _wheelRight.SetDutyCycle(100);
                    break;

                case 8:
                    _green.Write(true);
                    break;
            }
        }

    }

Please, note that the receiver itself relies on few lines: the remaining is code for the handling the incoming commands.

            //create the infrared receiver listening to the port 8
            var irrx = new InfraredLegoReceiver(Pins.GPIO_PIN_D8);
            irrx.InfraredMessageDecoded += irrx_InfraredMessageDecoded;
            irrx.IsEnabled = true;

Furthermore, all the driver is working in a event-driven fashion. That yields a total freedom for the host application, as well a very-responsive environment.

The rover preview.

Here are some more pictures about the rover, this time with much more mechanical parts, and the electronics stuffs on the top.
It’s still in an early stage, although is working fine.

The source code is available as part of the Cet Open Toolbox on Codeplex.

 
Leave a comment

Posted by on November 1, 2012 in .Net, Electronics, Software

 

Tags: , , , ,

 
Follow

Get every new post delivered to your Inbox.

Join 53 other followers