Polymorphic Hardware

Applying polymorphism to hardware enables users to do more with their devices while avoiding IoT pitfalls.

Similar projects worth following
Polymorphism is traditionally defined as the ability of a piece of software to process objects differently depending on their data type or class. Effectively this allows a function to do different things depending on what is passed to it.

Polymorphic Hardware will apply the concept of polymorphism to traditional embedded hardware. This will enable a single electronic device to fulfill multiple functional roles by allowing the user to run multiple firmwares and applications with said device.

Polymorphic Hardware is an extension of open source hardware and is intended to be a more consumer ready derivative. Because of its open nature it will also avoid many of the pitfalls of traditional IoT devices that are dependent on a single host cloud service.

Connectivity is a beautiful thing. It allows us to use our time more efficiently and interact with people on the other side of the planet. Without a doubt connectivity makes our world a better place, but more and more we are seeing examples of connectivity frustrating users instead of assisting them.

The most recent example of this was Revolv. This company developed a killer smart home hub and sold thousands of units to very excited customers only to have a questionable business decision brick the devices a few years later. Phillips almost made a similar mistake when they announced their Hue LED lightbulbs would only be allowed to interoperate with other Phillips products. Ultimately, until consumers are allowed to have full ownership of the firmware running on their devices, we will continue to see problems like this.

But it doesn't have to be this way. Polymorphic hardware is a concept for a solution to these problems we see from the IoT.

Polymorphism is traditionally a software concept that is used to describe code that can do different things depending on the objects and data passed to it. We can apply this to hardware by allowing end users to reprogram their device's firmware which will unlock a realm of new possibilities.

Let's look at one example:

Motion tracking wearables are all the rage these days. People love getting feedback from these devices and some folks even have multiple specialized devices for different movement applications. The funny thing is, most of these wearables share the same hardware solution: a microcontroller, Bluetooth, and a 9 axis sensor suite. If we apply the concept of polymorphism to these motion trackers, the user can now have a single device they could use to count steps, record and analyze a golf swing, and track a tennis match.

Because all polymorphic hardware will be reprogrammable by the end user these devices can never be bricked. If an app's cloud service ceases to exist, the user can simply reprogram the device and use it with another app which will prevent problems like those we've seen with Revolv and Phillips.

In the coming months, I will be developing hardware and software for this motion tracking example:

Hardware will be based on the TI CC2650 Bluetooth microcontroller. The board will be roughly the size of a quarter and will include a 9 axis + barometer sensor suite as well as a coin cell battery. Hardware will be licensed CC-BY-NC-SA.

Software for this project consists of two different pieces: embedded firmware and app SDK. The embedded firmware will be based off the TI SensorTag and will be modified to work with the custom hardware as well as add motion tracking features. The app SDK will use Apache Cordova to enable users to write apps with HTML5/JS. With the exception of the TI Bluetooth stack, all software will be licensed CC-BY.


PDF Schematic for bluetooth widget v1 License CC-BY-NC-SA

Adobe Portable Document Format - 37.26 kB - 04/24/2016 at 22:22

Preview Download


EAGLE Schematic for bluetooth widget v1 License CC-BY-NC-SA

sch - 396.37 kB - 04/24/2016 at 22:01

See BOM Download


EAGLE Layout for bluetooth widget v1 License CC-BY-NC-SA

brd - 79.48 kB - 04/24/2016 at 22:01


View all 3 files

  • 1 × TI CC2650 48MHz Cortex-M3 micocontroller + Bluetooth Low Energy Radio
  • 1 × Invensense MPU-9250 9 Axis Motion Sensor Suite
  • 1 × Measurement Specialties MS5607 High Precision Barometer
  • 1 × TI TMP007 Non-contact IR Thermometer
  • 1 × Winbond W25X40CL 4Mb SPI Flash memory

  • Race Recap

    Trey German05/31/2016 at 02:13 0 comments

    All I can say is "WOW"! The past week has been one of the most difficult of my life, and if I had the chance I would do it again in a heartbeat. Last Wednesday I drove up to Oklahoma and competed in the Icarus X race and WON! The race is a cross country powered paraglider race where pilots must complete the course completely unassisted.

    After attending the race briefing on Wednesday, 6 other pilots and myself took off from Arkoma Oklahoma Thursday morning on a trip that what would become a defining moment in our lives. Before takeoff, I attached a Polymorphic Dot to my wing to provide me with flight instrumentation. As soon as I got in the air it was clear I had hit a home run. As I climbed the altimeter needle sprung to life and as I turned I could see my bank angle on the attitude indicator changing. It was incredible to see the hardware I had worked on so hard the past few months come together and have a real function.

    Shortly after takeoff, however, it became clear this race was no joke. I normally fly down in Texas where there is no terrain and the weather is typically good. Oklahoma was quite a bit different. Instead of flat open land, I was flying over ridges and thousand foot tall mountains. The weather was something else too. Ceilings were capped at about 2000 feet by a layer of clouds, winds were blowing extremely strong out of the south, and we were surrounded by thunderstorms. As I tried to go over the terrain, I encountered down drafts that caused near crashes on several occasions. When I was able to gain some altitude, I would be tossed around like a sack of potatoes due to the turbulence. It was on the first leg I realized I wouldn't be able to safely take video footage of the Dot in action. I had to devote all my attention to flying in order to not die. In the coming week, I plan to get up in the air again (in more calm conditions) and get some video of the device and app in action.

    The race itself was incredible. I flew from Akoma to Poteau where I landed at an airport to get fuel. It was pretty cool walking up to an aviation gas pump with my aircraft on my back. I even got to make friends with the airport's guard dog!

    After Poteau, I was supposed to cross the most dangerous terrain of the race in order to get to the town of Talihina. During this leg, I was getting thrown around much more than the last as well as having partial collapses of my wing due to the turbulence. Just before crossing the mountains, myself and two other pilots elected to land in order to check the weather and make a go/no go call. After landing and making friends with the locals, we decided the conditions were just too strong to make a safe cross and elected to skip that checkpoint.

    We took off from that random field, and headed to the town of Red Oak for gas. I circled overhead looking for the closest field to the gas station and landed in it. After stowing my wing and gear bag, I walked into town with my paramotor and got gas at the local station. I got lots of strange looks and questions as I sat on the curb eating a Lunchable I had purchased inside. I scarfed down some crackers with ham and cheese and sipped on my Capri Sun. Life was good.

    It was at this point I realized I actually had a chance of winning the race. 5 of the 6 other pilots had already dropped out and my only competition had just landed in the same field as I and was having engine trouble. He elected to get a ride back to Arkoma and I though he was out of the race.

    After eating lunch, I took off from Red Oak and pointed my glider towards Webber Falls. This leg was one of the longest in the race, but because I had a tailwind I made excellent time. I also had to cross some pretty tall hills without any good emergency landing areas. The views were spectacular though!

    Webber Falls was definitely the most hilarious stop of the race. I landed in a field next to a Love's truck stop and decided to refuel the motor and myself. After chugging some water and nomming...

    Read more »

  • Pre-Race Update

    Trey German05/24/2016 at 01:02 2 comments

    In case you haven't heard, my secret plan for the "Anything Goes" part of the Hackaday Prize is to use the hardware I'm developing to instrument a Powered Paraglider. To the best of my knowledge this has never been done before! I've made a lot of progress, and I'm exited to share the results with you.

    Flying my powered paraglider!


    Over the past week or two, I've been working hard to add an attitude/heading reference system (AHRS) to the Polymorphic Dot. If you're not familiar an AHRS provides a pilot (or autopilot) with yaw (heading), pitch (attitude), and roll (bank) angles which effectively tells you how a body is oriented in reference to the earth. AHRS algorithms are very complex, so instead of writing my own, I'm relying on one of the more popular open source algorithms which was written by Sebastian Madgwick as part of his Ph.D thesis. You can find it here:

    I started by finding a javascript implementation of this algorithm. This allowed me to easily test and make sure that the IMU data I was getting was solid. The code I borrowed for this can be found here:

    After a bit of tweaking to feed the bluetooth IMU data into the algorithm, I had a 3D model of a box moving around on my phone in the same way that I moved a Polymorphic Dot.

    This really blew my mind! It shouldn't have been that easy, but thanks to open source software, I was able to get this working in days instead of months!

    My next step was to try to move the AHRS processing from the smart phone app to the Polymorphic Dot. Why would I do this when I already had a working solution? Well, a responsive AHRS needs a lot (>= 100 samples/second) of IMU data. By processing the IMU data locally on the Polymorphic Dot there is less processing for the app to do (so it runs faster) and less data for the Dot to transmit (so it uses less power). To this end I added a service to the Dot that reports AHRS data when enabled.

    The current implementation of the AHRS service is (in the spirit of Hackaday!) very much a hack. In the future I plan to convert the algorithm from floating to fixed point as well as port it to run on the low power sensor CPU present on the CC2650.

    After I had the AHRS working, it was time to begin work on the app for the race. Once again time was a major limitation, so I looked for open source flight instruments and happened to get lucky! Another Sebastian (Sébastien Matton), developed some javascript flight instruments as part of his thesis:

    After dropping the code into my app, I had attitude and heading indicators as well as an altimeter.

    The final piece I wanted to add to the app was a map. This would prevent me from constantly having to switch between my paragliding app and Google Maps. While I could use the standard javascript Maps API, I found a better solution for Cordova apps: the Cordova Google Maps Plugin! What makes this plugin special is that instead of opening google maps from the web, it instead loads the native Android/iOS Maps and embeds the view in your app. After adding the plugin to my project and adding a few lines of code to my index.js, I was able to display a map of the race area. A few more tweaks and I had the race course drawn out and icons added for gas stations.

    I've committed and pushed both the updated firmware and this new paragliding app to the github repos listed on this project page.


    In one of my previous posts, you probably saw the magnetic mount cases I developed for the paraglider race this week. As you may have guessed, they won't work that great for this application because of the magnets!

    In my rush to get everything done in time, I neglected to think about how the magnets would effect the magnetometer on the board. After I did some testing, I found that the pitch and bank angles weren't affected but the heading...

    Read more »

  • Meet Trey!

    Trey German05/18/2016 at 17:00 0 comments

    While I've been around the electronics industry for a hot minute and know quite a few of you, there are even more of you I've never met! To fix that, I've made this video introduction where I reveal what my secret plan is for the "Anything Goes" part of the 2016 Hackaday Prize.

  • Hardware Development Pt. 2

    Trey German05/17/2016 at 17:08 0 comments

    After posting all that info on the enclosures, it occurred to me that I owe you an update on hardware. Previously, I've covered the development of the little green board, but since then I've posted a bunch of pictures of a red version without any explanation!

    I was able to successfully bring up the first version of the board (the green one) and retrieve data from each of the sensors over bluetooth using the SDK I've been developing. Everything was going great until I started trying to update the firmware over bluetooth. Clearly I didn't RTFM enough because as I quickly found out, firmware updates require an external memory in order to buffer the application image.

    It was this shortcoming that led to the redesign of the board. I added the SPI flash to enable over the air firmware download (OAD), as well as a TMP007 IR temperature sensor. Finally, the CC2650 module I'm using comes in two flavors: internal and external antenna. Because the range wasn't the best with the internal antenna, I decided to design the board such that it could be populated with either variant of this module. I've highlighted these changes in the following graphic:

    I've had these new boards for a few weeks now and they are working fabulously. Only minor changes were needed in order to get the firmware running on these new boards. I've also settled on a name for these. Meet the Polymorphic●Move (pol-e-morf-ic dot moov).

  • Enclosure Development Pt.1

    Trey German05/13/2016 at 23:42 0 comments

    In my last post, I hinted that I will be strapping these things to some kind of moving contraption. I'm still not quite ready to tell you what that contraption is (Why ruin the surprise?), but in any case I'll need a case to hold the PCB as well as some method of attachment.

    Thankfully we live in a world where there are open source 3D CAD tools and cheap 3D printing services. Previously, I've played around with FreeCAD so I started by building a 3D model of the board in this tool. While I don't explicitly need a 3D model of the board, it will help in the long run by ensuring that all of the enclosures I design fit the board before I ever send the enclosure out for printing. After playing around with FreeCAD for an hour or two I came up with this model.

    While it lacks color and exact models of the parts, the overall model is dimensionally accurate, which will allow me to make sure the enclosure and board fit together without any interference.

    Once I had the model of the board, I started designing the bottom half of the case. I begun by stripping down the model of the board until I had just the outline of the PCB sketched. I then increased the size of the board a bit (for tolerance reasons) and extruded the board outline so I had a ring that was shaped like the board. I then added a bottom as well as some cutouts for magnets. The final step was to add some taps to the top side such that this half of the case could snap together with the top half.

    The top of the case followed almost the exact same design flow, but instead of including holders for magnets I added some strategic cuts such that the board's pushbutton could be pressed by squeezing the side of the case.

    The final piece of the enclosure was the magnetic mount's back. This piece of the case will sit behind a piece of fabric and allow the case to clamp to the fabric using magnets. Design for this piece was straightforward. I started with the model of the bottom of the case and simply trimmed off everything but the bottom side that included the holders for the magnets.

    Now that I had a model of my case, I needed to get it printed. Many of the details on these models are finer than the resolution of most consumer FDM printers so I elected to use a professional service which would give me access to industry grade 3D printers. I've used Shapeways in the past with great success so I chose to use their frosted detail plastic service.

    Literally 3 days after uploading my models and placing my order, I have the finished parts in my hand! I have no association with Shapeways, but I've got to give them props on their quality and turnaround time!

    After inspecting the finished parts and doing some test fits, I tried to snap together a case with a board inside. To my surprise, I couldn't snap it together! What had happened?

    Remember that tall JTAG header in the model of the PCB (near the top of this log entry)? Well it turns out I had forgotten to cut a hole in the top of the case so these pins could stick out. Like any good hacker, I saw this as an opportunity to use power tools instead of a problem. A few seconds after the case met my drill, I had a hole big enough to squeeze the pins through.

    The moment of truth was upon me. Would the board fit in the case? Would the case snap together? Would the pushbutton be push-able?

    I snapped the case together and sure enough everything worked according to plan! The case snapped together and I was able to turn on the board by squeezing the case around the button.

    With that said, there is some definite room for improvement. I will of course be adding a cutout to the top of the case so that it works out of the box without any modification. The other big issue I noticed was the snapping mechanism. While the two halves of the case and snap tabs fit together perfectly, the snap tabs are extremely small and prone to breakage.

    In the coming week, I'll be revising the case to fix these two issues. It's critical...

    Read more »

  • App SDK Development Pt. 2

    Trey German05/09/2016 at 21:02 0 comments

      Over the past few weeks, I've brushed up on my HTML and Javascript and have begun to write a javascript library in order to make getting started with the Polymorphic Dot that much easier. I started this process mostly by experimenting around with Cordova as well as reading tutorials and articles on javascript software architecture.

      After going back and forth between brainstorming and testing, I came up with the following overall app software architecture:

      Just like any other piece of software, the SDK will be made up of a stack of other pieces of software:

      1. Cordova, the ble-central plug-in, as well as any additional Cordova plug-ins run directly on the host OS (Android/iOS) and expose Javascript APIs to higher layers.
      2. PML Manager is a Javascript library that manages connection to Bluetooth devices. Once a connection is established and a hardware match found, the manager loads the appropriate device library(pmlDotMove.js for instance) and exposes a user friendly API for accessing the hardware.
      3. App is the user application to be built with Cordova. This app will make calls to the PML Manager to interact with Polymorphic Hardware devices as well as any Cordova or plug-in APIs it may need.

      Since I'm actually writing the PML Manager and its associated device libraries, let's focus on that. As stated earlier, the goal is to make this hardware as easy to use as possible. Of course, nowadays this means making the software as easy to use as possible. Let's walk through a typical connection scenario:

      1) Application initiates BLE device scan:


        When devices are found, a callback function (app.onDiscoverDevice in this case) is called and passed a device object so the app can populate a "devices found" list for the user.

        2) User selects device(s) to connect to. App stops scanning and passes device(s) to the connect API:

        pmlManager.connect(app.selectedDevices, app.onDeviceConnect);

        Note: pmlManager supports simultaneous connections to 8 devices.

        As each device is connected to, pmlManager looks at its advertising data to figure out what kind of Polymorphic Hardware it is. If it finds a match in its hardware definitions library, pmlManager will load a software interface object that matches the device and pass it back to the application via a callback (app.onDeviceConnect in this case).

        3) Now that the application has access to the software interface for a given device, it can configure the services and start receiving data:

        var onMoveData = function(data){
                var a = new Int16Array(data);
        	        //a[0] - Gyro X   a[1] - Gyro Y    a[2] - Gyro Z
                        //a[3] - Accel X  a[4] - Accel Y  a[5] - Accel Z
                        //a[6] - Mag X    a[7] - Mag Y    a[8] - Mag Z

        In this example I:

        1. Create a movement callback function to receive data from the Polymorphic Hardware.
        2. Register the movement callback and enable it.
        3. Configure how often I want to receive movement data.
        4. Enable all movement sensors (gyro, accel, mag).

        The user application would then do something with the data received in the onMoveData function. I went ahead and put together a quick example app which shows how to connect to multiple sensors and graph the movement data from each sensor. You can find the example Cordova app here.

        First the user selects the devices to connect to (user may select more than one):

        After devices are selected the user clicks on connect and the movement data is graphed:

        As you can see, everything appears to be working well so far.

        Graphing movement data is great, but without a solid sensor fusion algorithm its of questionable use. My next hurdle is to implement an attitude/heading reference system (AHRS) using this sensor data. In about two weeks, I'll be doing my first major field test of Polymorphic Hardware and having solid AHRS data will be critical to this test. Stay tuned for details....

      Read more »

    • Firmware Development Pt.1

      Trey German04/30/2016 at 19:34 0 comments

      Designing and developing the complete ecosystem for a product in four months is no easy task. Hell, most people would struggle to get just the hardware to a production ready point in that time frame. This is why it is so important to make smart decisions about how you scope and design a product when you have very limited resources.

      To this end, I'm starting with a working reference design's firmware and adding my special sauce on top. As mentioned previously, I'm using the TI SensorTag as my foundation. This board has a really great firmware that allows users to read all of the sensors as well as control IOs over a BLE link. You can find the original firmware in the BLE Stack from TI.

      Since I'm using someone else's software, it's very important to understand how the software is licensed. Like much of TI's software, the BLE stack and it's examples are licensed under a "TI Commercial" license. Let's take a look at the meat and potatoes of it:

      "The License limits your use, and you acknowledge, that the Software may not be modified, copied or distributed unless embedded on a Texas Instruments microcontroller or used solely and exclusively in conjunction with a Texas Instruments radio frequency transceiver, which is integrated into your product. Other than for the foregoing purpose, you may not use, reproduce, copy, prepare derivative works of, modify, distribute, perform, display or sell this Software and/or its documentation for any purpose."

      If we boil this down to normal english, it basically says "as long as you're using this software on a TI device, you can do whatever you want with this code". Since, I'm building an ecosystem of software designed to run on a single device (which uses TI silicon), I should be OK. Additionally, any code I write myself on top of this code base I can license with a more standard open source license.

      To finish up this first post on firmware, I've renamed the project, configured the board.h file, trimmed down the BLE stack package, and thrown it on github for everyone's enjoyment. You can find it here.

      Please note that while this code was originally written for a TI SensorTag I have since modified it for the Polymorphic Dot. If compiled and flashed this code will not work with TI SensorTag EVM.

    • Hardware Development Pt. 1

      Trey German04/24/2016 at 23:10 0 comments

      Designing and building a bluetooth motion tracker will be no easy task, and to that end I've decided to stand on the shoulders of some giants instead of starting from nothing. TI has a great development platform that fits this projects needs almost completely. It's called the SensorTag and its a Bluetooth Low Energy reference design that includes several different sensors. Since I've already written some Cordova training material that works with this device, basing my hardware design off this device will make this training material reusable when my hardware is available.

      The SensorTag though isn't 100% perfect for this project. It's a little larger than I'd like, has more sensors than are needed for this application, and has a discrete radio layout. The discrete radio could be a big problem later down the road. If the design takes off, I'll need to comply with FCC and other countries' radio rules. A discrete layout means expensive intentional radiator tests and certifications. There are other options though...

      Because of the above mentioned problems, I'll be designing and refining my own hardware. In order to make the design as flexible as possible, I wanted the finished board to be as small as possible. To this end the board is round and I'm shooting to have the finished design an inch in diameter. Next, I need to find a pre-certified FCC compliant module that is as small as possible and uses the CC2640 device in the SensorTag. There are a few out there I found, but the Sable-x from LSR was the smallest, so I chose this device. Finally, I chose to keep the Invensense MPU-9250 while swapping the SensorTag's Bosch barometer for the MS5607 from Measurement Specialties.

      After I finished drawing up all the parts in EAGLE and wiring up the schematic, I came up with this schematic.

      As everyone knows the EAGLE auto-router leaves a lot to be desired, so I layout and route all my boards completely by hand. It's a time consuming process, but if you want a board that is beautiful and routed efficiently there is no better way. After several cups of coffee I came up with this layout:

      The board measure 1010 mils in diameter and includes:

      • Sable-x Bluetooth Module
      • MPU-9250 9 Axis IMU
      • MS5607 Barometer
      • 3x RGB LEDs
      • Power/User Pushbutton
      • JTAG connector

      Now that I had a design I needed to get it manufactured. Traditionally, I would send the gerber files off to a PCB manufacturer, place a Digikey order, and assemble the boards myself, but I've opted for another route with this project. Because the timeline for this project is so short and this board is crazy high component density, I opted to go with a professional assembler. Thankfully, I have one just down the street from me in Houston called MacroFab. MacroFab is really cool because you can upload your whole design, pick parts, get a quote, and order boards all without ever talking to anyone. That said, the guys there are always happy to talk if you need help or have special assembly needs.

      A few weeks after I placed my order, I went over to pick up the boards and I was blown away with how small they were in person. Check out this photo:

      After getting the boards manufactured, the guy's at MacroFab invited me to appear on their podcast and talk about these boards. You can listen to it here.

      In the coming weeks, I'll be testing the boards and starting firmware development. Stay tuned for updates and let me know what you think of the project this far!

    • App SDK Development Pt. 1

      Trey German04/24/2016 at 22:17 0 comments

      As mentioned in the details section, I'll be building a smartphone SDK using Apache Cordova. Cordova is a very easy to use tool that allows anyone to build an app using HTML5 and Javascript, the same languages that the web is built on.

      Before I can build my SDK, I'll need to be an expert on both Cordova and HTML5/JS...and in my experience one of the best ways to become more skilled in a subject is to teach it. To this end, I've developed some training material for Cordova. This guide walks user's through installation, creation of their first app, app debugging, as well as how to add bluetooth connectivity to the app. You can find the guide here:

      To make sure the training material didn't have any kinks in it, I took a little road trip to Texas A&M University to teach some students how to build their first app.

      Overall the workshop went smoothly and ~30 students were able to build apps that graphed accelerometer data coming in over a bluetooth link.

    View all 9 project logs

    Enjoy this project?



    michael wrote 11/06/2016 at 16:31 point


    i am trying to implement my custom board, SABLE-X using MPU9250 TI Drivers and movement sensor services,  with AHRS madgwick/mahony functions.

    My sample frequency is 10Hz and deltat is 0.1.

    The yaw, roll and pitch are not looking good at the moment. I could not find on your github the received BLE values MAG/ACC/GYRO. I would like to check them against mine.

    The sensortag app uses also the madgwick function and the sample rate is 10Hz there too.

    So here is i build the 8 Bit values to 16 bit and send to madgwick function:

    p, li { white-space: pre-wrap; }

    int16_t value_save_msb = data[1];
    int16_t value_save_lsb = data[0];
    GyroX=((float)((int16_t)((value_save_lsb & 0xff) | (((int16_t)value_save_msb << 8) & 0xff00)))/ (float) 32768) * 250 * 1;
    value_save_msb = data[3];
    value_save_lsb = data[2];
    GyroY=((float)((int16_t)((value_save_lsb & 0xff) | (((int16_t)value_save_msb << 8) & 0xff00)))/ (float) 32768) * 250 * 1;
    value_save_msb = data[5];
    value_save_lsb = data[4];
    GyroZ=((float)((int16_t)((value_save_lsb & 0xff) | (((int16_t)value_save_msb << 8) & 0xff00)))/ (float) 32768) * 250 * 1;

    value_save_msb = data[7];
    value_save_lsb = data[6];
    AccX=(((float)((int16_t)((value_save_lsb & 0xff) | (((int16_t)value_save_msb << 8) & 0xff00)))/ (float) 32768) * 2) * 1;
    value_save_msb = data[9];
    value_save_lsb = data[8];
    AccY=(((float)((int16_t)((value_save_lsb & 0xff) | (((int16_t)value_save_msb << 8) & 0xff00)))/ (float) 32768) * 2) * 1;
    value_save_msb = data[11];
    value_save_lsb = data[10];
    AccZ=(((float)((int16_t)((value_save_lsb & 0xff) | (((int16_t)value_save_msb << 8) & 0xff00)))/ (float) 32768) * 2) * 1;

    value_save_msb = data[13];
    value_save_lsb = data[12];
    MagX=(((float)((int16_t)((value_save_lsb & 0xff) | (((int16_t)value_save_msb << 8) & 0xff00))) *(float)(49120/32768)));
    value_save_msb = data[15];
    value_save_lsb = data[14];
    MagY=(((float)((int16_t)((value_save_lsb & 0xff) | (((int16_t)value_save_msb << 8) & 0xff00))) *(float)(49120/32768)));
    value_save_msb = data[17];
    value_save_lsb = data[16];
    MagZ=(((float)((int16_t)((value_save_lsb & 0xff) | (((int16_t)value_save_msb << 8) & 0xff00))) *(float)(49120/32768)));

    MadgwickAHRSupdate(GyroX*M_PI/180, GyroY*M_PI/180, GyroZ*M_PI/180, AccX, AccY, AccZ, MagX, MagY, MagZ);

    double R11 = 2.*q0*q0 -1 +2.*q1*q1;
    double R21 = 2.*(q1*q2 - q0*q3);
    double R31 = 2.*(q1*q3 + q0*q2);
    double R32 = 2.*(q2*q3 - q0*q1);
    double R33 = 2.*q0*q0 -1 +2.*q3*q3;

    double phi = qAtan2(R32, R33 );
    double theta = -qAtan(R31 / sqrt(1-R31*R31) );
    double psi = qAtan2(R21, R11);
    yaw = phi;
    pitch = theta;
    roll = psi;

      Are you sure? yes | no

    LJCIRCUITS.COM PCB wrote 05/11/2016 at 03:06 point

    Is this PCB for 4Layers?

      Are you sure? yes | no

    Trey German wrote 05/11/2016 at 03:08 point

    Yes, 4 layer and 6 mil trace/space.

      Are you sure? yes | no

    LJCIRCUITS.COM PCB wrote 05/11/2016 at 03:11 point

    Thanks for your reply. Trey

      Are you sure? yes | no

    sally wrote 04/24/2016 at 23:48 point

    You might benefit from our paper on Thing Theory, where we describe Thing Agents: pp. 3–4

      Are you sure? yes | no

    Similar Projects

    Does this project spark your interest?

    Become a member to follow this project and never miss any updates