やった結果
ArduinoとLIS3DHの接続
Arduino | LIS3DH |
---|---|
3.3V | pin1 |
GND | pin2 |
pin13 | pin3 |
pin11 | pin4 |
pin12 | pin5 |
pin10 | pin6 |
Arduinoで使ったコード
LIS3DH.ino
#include <SPI.h>
const byte R_BIT = 0x80; // 0b10000000
const byte R_MASK = 0xBF; // 0b10111111
const byte W_MASK = 0x3F; // 0b00111111
const byte CS = 10; // pin10
const int CTRL_REG1 = 0x20;
const int OUT_X_L = 0x28;
const int OUT_X_H = 0x29;
const int OUT_Y_L = 0x2A;
const int OUT_Y_H = 0x2B;
const int OUT_Z_L = 0x2C;
const int OUT_Z_H = 0x2D;
int x_axis = 1;
int y_axis = 2;
int z_axis = 3;
unsigned int readRegister(byte reg) {
unsigned int result;
reg |= R_BIT;
reg &= R_MASK;
digitalWrite(CS, LOW);
SPI.transfer(reg);
result = SPI.transfer(0x00);
digitalWrite(CS, HIGH);
return result;
}
void writeRegister(byte reg, byte data) {
reg &= W_MASK;
digitalWrite(CS, LOW);
SPI.transfer(reg);
SPI.transfer(data);
digitalWrite(CS, HIGH);
}
void setup() {
unsigned int res = 0;
pinMode(CS, OUTPUT);
SPI.begin();
SPI.setBitOrder(MSBFIRST);
SPI.setDataMode(SPI_MODE3);
SPI.setClockDivider(SPI_CLOCK_DIV2);
writeRegister(CTRL_REG1, 0x27);
res = readRegister(0x0F);
Serial.begin(115200);
delay(1);
}
int getValue(int axis) {
int Val = 0;
int h, l;
if (axis == x_axis) {
l = readRegister(OUT_X_L);
h = readRegister(OUT_X_H);
} else if (axis == y_axis) {
l = readRegister(OUT_Y_L);
h = readRegister(OUT_Y_H);
} else if (axis == z_axis) {
l = readRegister(OUT_Z_L);
h = readRegister(OUT_Z_H);
}
Val = h << 8 | l;
return Val;
}
void loop() {
int x, y, z;
writeRegister(CTRL_REG1, 0x27);
x = getValue(x_axis);
y = getValue(y_axis);
z = getValue(z_axis);
const int angleX = atan2(x, z) / PI * 180;
const int angleY = atan2(y, z) / PI * 180;
Serial.print(angleX);
Serial.print("\t");
Serial.println(angleY);
Serial.flush();
delay(100);
}
Unityで使うC#コード
LIS3DH.cs
using System;
using System.IO.Ports;
using System.Threading;
using UnityEngine;
using System.Collections.Generic;
public class LIS3DH : MonoBehaviour {
public const string SERIAL_PORT = "COM8";
public const int SERIAL_BAUD_RATE = 115200;
private const int SERIAL_TIMEOUT = 100;
private Thread _readThread;
private static SerialPort _serialPort;
private static bool _continue;
private static Quaternion _handQuaternion = new Quaternion();
private List<Vector3> angleCache = new List<Vector3>();
public int angleCacheNum = 10;
public Vector3 angle {
private set {
angleCache.Add(value);
if (angleCache.Count > angleCacheNum) {
angleCache.RemoveAt(0);
}
}
get {
if (angleCache.Count > 0) {
var sum = Vector3.zero;
angleCache.ForEach(angle => { sum += angle; });
return sum / angleCache.Count;
} else {
return Vector3.zero;
}
}
}
void Start() {
_readThread = new Thread(Read);
_serialPort = new SerialPort(SERIAL_PORT, SERIAL_BAUD_RATE);
_serialPort.ReadTimeout = SERIAL_TIMEOUT;
_serialPort.Open();
_continue = true;
_readThread.Start();
}
void Update() {
//Debug.Log (angle);
transform.rotation = Quaternion.Euler(angle);
}
void OnApplicationQuit() {
_continue = false;
_readThread.Join();
_serialPort.Close();
}
private void Read() {
string[] values;
while (_continue) {
if (_serialPort.IsOpen) {
try {
values = _serialPort.ReadLine().Split('\t');
var angleX = float.Parse(values[0]) * -1;
var angleY = float.Parse(values[1]) * -1;
angle = new Vector3(angleX, 0, angleY);
//_handQuaternion.eulerAngles.Set(angleX, 0, angleY);
//Debug.Log (angleX + "," + angleY);
} catch (TimeoutException) {
}
}
Thread.Sleep(1);
}
}
}
参考
http://makers-with-myson.blog.so-net.ne.jp/2014-03-08
http://tips.hecomi.com/entry/2014/07/28/023525