hcwiid 0.0.4 → 0.0.5
raw patch · 5 files changed
+102/−7 lines, 5 filesPVP: major bump suggested
API removals or changes: PVP suggests a major version bump
API changes (from Hackage documentation)
+ System.CWiid: CWiidIRSrc :: Bool -> Int -> Int -> Int -> CWiidIRSrc
+ System.CWiid: cwiidGetIR :: CWiidWiimote -> IO [CWiidIRSrc]
+ System.CWiid: cwiidIRSrcPosX :: CWiidIRSrc -> Int
+ System.CWiid: cwiidIRSrcPosY :: CWiidIRSrc -> Int
+ System.CWiid: cwiidIRSrcSize :: CWiidIRSrc -> Int
+ System.CWiid: cwiidIRSrcValid :: CWiidIRSrc -> Bool
+ System.CWiid: data CWiidIRSrc
+ System.CWiid: instance Show CWiidIRSrc
+ System.CWiid: instance Storable CWiidIRSrc
+ System.CWiid: irSrc :: CWiidState -> [CWiidIRSrc]
- System.CWiid: CWiidState :: Int -> Int -> Int -> Int -> Int -> [Int] -> CWiidState
+ System.CWiid: CWiidState :: Int -> Int -> Int -> Int -> Int -> [Int] -> [CWiidIRSrc] -> CWiidState
Files
- CHANGELOG +5/−0
- README +0/−1
- System/CWiid.hsc +68/−4
- hcwiid.cabal +1/−1
- test/Test.hs +28/−1
CHANGELOG view
@@ -1,3 +1,8 @@+2014-05-20 Ivan Perez <ivan.perez@keera.co.uk>++ * API: adds infrared tracking support+ * Tests: adapts test to report IR data+ 2014-05-17 Ivan Perez <ivan.perez@keera.co.uk> * API: adds accelerometer sensing.
README view
@@ -18,7 +18,6 @@ TODO ========-* Enable IR. Create an example that uses it. * Locate projects using this. (I am personally working on some games that will be published.) * Write a decent example that uses more than just testing a button thing.
System/CWiid.hsc view
@@ -23,8 +23,8 @@ -- then exported properly. -- -- * Not all functions/wiimote fields are accessible. In particular,--- acceleromoter info is in testing stage and no IR information--- is exported.+-- acceleromoter and IR is in testing stage. Nunchuck, calibration,+-- wiimote plus are not handled at all (but will be in the future). -- -- All in all, the code works quite well and is currently being used -- to implement several real games.@@ -57,7 +57,10 @@ CWiidBtnFlag(..), -- * Accelerometers cwiidGetAcc,- CWiidAcc(..)+ CWiidAcc(..),+ -- * Infra-red+ CWiidIRSrc(..),+ cwiidGetIR ) where -- import Foreign.C.Error@@ -148,13 +151,14 @@ data CWiidState = CWiidState { rptMode :: Int, led :: Int, rumble :: Int, battery :: Int, buttons :: Int, acc :: [Int]+ , irSrc :: [CWiidIRSrc] } deriving Show instance Storable CWiidState where sizeOf = const #size struct cwiid_state alignment = sizeOf- poke cwst (CWiidState rp l ru ba bu [ac0,ac1,ac2]) = do+ poke cwst (CWiidState rp l ru ba bu [ac0,ac1,ac2] irs) = do (#poke struct cwiid_state, rpt_mode) cwst rp (#poke struct cwiid_state, led) cwst l (#poke struct cwiid_state, rumble) cwst ru@@ -163,6 +167,7 @@ (#poke struct cwiid_state, acc[0]) cwst (fromIntegral ac0 :: CUChar) (#poke struct cwiid_state, acc[1]) cwst (fromIntegral ac1 :: CUChar) (#poke struct cwiid_state, acc[2]) cwst (fromIntegral ac2 :: CUChar)+ pokeArray ((#ptr struct cwiid_state, ir_src) cwst) irs peek cwst = do rp <- (#peek struct cwiid_state, rpt_mode) cwst l <- (#peek struct cwiid_state, led) cwst@@ -172,10 +177,66 @@ ac0 <- (#peek struct cwiid_state, acc[0]) cwst ac1 <- (#peek struct cwiid_state, acc[1]) cwst ac2 <- (#peek struct cwiid_state, acc[2]) cwst+ irs <- peekArray cwiidIrSrcCount ((#ptr struct cwiid_state, ir_src) cwst) return $ CWiidState rp l ru ba bu [ fromIntegral (ac0 :: CUChar) , fromIntegral (ac1 :: CUChar) , fromIntegral (ac2 :: CUChar)]+ irs +-- * Infrared++-- | Maximum number of infrared points detected.+-- By default (according to cwiid) it should be 4.+cwiidIrSrcCount :: Int+cwiidIrSrcCount = (#const CWIID_IR_SRC_COUNT)++-- struct cwiid_ir_src {+-- char valid;+-- uint16_t pos[2];+-- int8_t size;+-- };+--+-- The following model is weaker than the counterpart in C (see above). We do+-- so in order to provide something more "natural" in Haskell, but it might+-- be better to use a more precise datatype.++-- | Internal representation of an infrared point. You should no use it+-- unless you know what you are doing; use 'CWiidIR' instead.+data CWiidIRSrc = CWiidIRSrc+ { cwiidIRSrcValid :: Bool+ , cwiidIRSrcPosX :: Int+ , cwiidIRSrcPosY :: Int+ , cwiidIRSrcSize :: Int+ }+ deriving Show++instance Storable CWiidIRSrc where+ sizeOf = const #size struct cwiid_ir_src+ alignment = sizeOf+ poke cwst (CWiidIRSrc valid posX posY sz) = do+ (#poke struct cwiid_ir_src, valid) cwst ((if valid then (-1) else 0) :: CChar)+ (#poke struct cwiid_ir_src, pos[0]) cwst (fromIntegral posX :: CUShort)+ (#poke struct cwiid_ir_src, pos[1]) cwst (fromIntegral posY :: CUShort)+ (#poke struct cwiid_ir_src, size) cwst (fromIntegral sz :: CChar)+ peek cwst = do+ valid <- (#peek struct cwiid_ir_src, valid) cwst+ posX <- (#peek struct cwiid_ir_src, pos[0]) cwst+ posY <- (#peek struct cwiid_ir_src, pos[1]) cwst+ sz <- (#peek struct cwiid_ir_src, size) cwst+ return $ CWiidIRSrc (not ((valid :: CChar) == 0))+ (fromIntegral (posX :: CUShort))+ (fromIntegral (posY :: CUShort))+ (fromIntegral (sz :: CChar))++cwiidGetIR :: CWiidWiimote -> IO [CWiidIRSrc]+cwiidGetIR wm = + alloca $ \wiState -> do+ _ <- c_cwiid_get_state handle wiState+ ws <- peek wiState+ return (irSrc ws)+ where handle = unCWiidWiimote wm++-- * Leds newtype CWiidLedFlag = CWiidLedFlag { unCWiidLedFlag :: Int } deriving (Eq, Show) @@ -298,6 +359,9 @@ deriving (Eq, Show) -- | Obtain accelerometer information.+-- FIXME: read wmgui/main.c:cwiid_acc(1119) to understand how to use+-- this information, what else might need to be exported, and how+-- to calibrate the accelerometers. cwiidGetAcc :: CWiidWiimote -> IO CWiidAcc cwiidGetAcc wm = alloca $ \wiState -> do
hcwiid.cabal view
@@ -1,5 +1,5 @@ Name: hcwiid-Version: 0.0.4+Version: 0.0.5 Author: Kiwamu Okabe <kiwamu@debian.or.jp>, Ivan Perez <ivan.perez@keera.co.uk> Maintainer: Ivan Perez <ivan.perez@keera.co.uk> License: GPL-2
test/Test.hs view
@@ -4,6 +4,8 @@ import Control.Monad import System.CWiid import System.Posix.Unistd+-- Uncomment if you want to move the mouse with the wiimote+-- import System.Process main :: IO () main = do@@ -11,8 +13,33 @@ (Just wm) <- cwiidOpen putStrLn "found!" _ <- cwiidSetLed wm (combineCwiidLedFlag [cwiidLed1, cwiidLed3])- _ <- cwiidSetRptMode wm 7+ _ <- cwiidSetRptMode wm 15 -- Buttons + Acc + IR _ <- forever $ do _ <- usleep 300000 cwiidGetBtnState wm >>= print cwiidGetAcc wm >>= print+ cwiidGetIR wm >>= print++ -- The following code shows how to use the IR camera+ -- to control the mouse. Adjust your monitor resolution+ -- and displacement using the constants below.+ --+ -- irs <- cwiidGetIR wm+ -- let numLeds = filter cwiidIRSrcValid rs+ -- let led1 = irs!!0+ -- led2 = irs!!1+ -- let posX = ((cwiidIRSrcPosX led1) + (cwiidIRSrcPosX led2)) `div` 2+ -- let posY = ((cwiidIRSrcPosY led1) + (cwiidIRSrcPosY led2)) `div` 2+ -- propX = (fromIntegral (1024 - posX)) / 1024.0+ -- propY = (fromIntegral (max 0 (posY - 384))) / 384.0 + -- finX = monitorDispX + round (monitorResX * propX)+ -- finY = monitorDispY + round (monitorResY * propY)++ -- system $ "xdotool mousemove " ++ show finX ++ " " ++ show finY+ return () -- not reach++-- monitorResX = 1280+-- monitorResY = 1024+-- +-- monitorDispX = 1920+-- monitorDispY = 0