Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependents: UsbHostMAX3421E_Hello
Wii.h
00001 /* Copyright (C) 2012 Kristian Lauszus, TKJ Electronics. All rights reserved. 00002 00003 This software may be distributed and modified under the terms of the GNU 00004 General Public License version 2 (GPL2) as published by the Free Software 00005 Foundation and appearing in the file GPL2.TXT included in the packaging of 00006 this file. Please note that GPL2 Section 2[b] requires that all works based 00007 on this software must also be made publicly available under the terms of 00008 the GPL2 ("Copyleft"). 00009 00010 Contact information 00011 ------------------- 00012 00013 Kristian Lauszus, TKJ Electronics 00014 Web : http://www.tkjelectronics.com 00015 e-mail : kristianl@tkjelectronics.com 00016 00017 IR camera support added by Allan Glover (adglover9.81@gmail.com) and Kristian Lauszus 00018 */ 00019 00020 #ifndef _wii_h_ 00021 #define _wii_h_ 00022 00023 #include "BTD.h" 00024 #include "controllerEnums.h" 00025 00026 /* Wii event flags */ 00027 #define WII_FLAG_MOTION_PLUS_CONNECTED (1 << 0) 00028 #define WII_FLAG_NUNCHUCK_CONNECTED (1 << 1) 00029 #define WII_FLAG_CALIBRATE_BALANCE_BOARD (1 << 2) 00030 00031 #define wii_check_flag(flag) (wii_event_flag & (flag)) 00032 #define wii_set_flag(flag) (wii_event_flag |= (flag)) 00033 #define wii_clear_flag(flag) (wii_event_flag &= ~(flag)) 00034 00035 /** Enum used to read the joystick on the Nunchuck. */ 00036 enum HatEnum { 00037 /** Read the x-axis on the Nunchuck joystick. */ 00038 HatX = 0, 00039 /** Read the y-axis on the Nunchuck joystick. */ 00040 HatY = 1, 00041 }; 00042 00043 /** Enum used to read the weight on Wii Balance Board. */ 00044 enum BalanceBoardEnum { 00045 TopRight = 0, 00046 BotRight = 1, 00047 TopLeft = 2, 00048 BotLeft = 3, 00049 }; 00050 00051 /** 00052 * This BluetoothService class implements support for the Wiimote including the Nunchuck and Motion Plus extension. 00053 * 00054 * It also support the Wii U Pro Controller. 00055 */ 00056 class WII : public BluetoothService { 00057 public: 00058 /** 00059 * Constructor for the WII class. 00060 * @param p Pointer to BTD class instance. 00061 * @param pair Set this to true in order to pair with the Wiimote. If the argument is omitted then it won't pair with it. 00062 * One can use ::PAIR to set it to true. 00063 */ 00064 WII(BTD *p, bool pair = false); 00065 00066 /** @name BluetoothService implementation */ 00067 /** Used this to disconnect any of the controllers. */ 00068 void disconnect(); 00069 /**@}*/ 00070 00071 /** @name Wii Controller functions */ 00072 /** 00073 * getButtonPress(Button b) will return true as long as the button is held down. 00074 * 00075 * While getButtonClick(Button b) will only return it once. 00076 * 00077 * So you instance if you need to increase a variable once you would use getButtonClick(Button b), 00078 * but if you need to drive a robot forward you would use getButtonPress(Button b). 00079 * @param b ::ButtonEnum to read. 00080 * @return getButtonPress(ButtonEnum b) will return a true as long as a button is held down, while getButtonClick(ButtonEnum b) will return true once for each button press. 00081 */ 00082 bool getButtonPress(ButtonEnum b); 00083 bool getButtonClick(ButtonEnum b); 00084 /**@}*/ 00085 00086 /** @name Wii Controller functions */ 00087 00088 /** Call this to start the pairing sequence with a controller */ 00089 void pair(void) { 00090 if(pBtd) 00091 pBtd->pairWithWiimote(); 00092 }; 00093 /** 00094 * Used to read the joystick of the Nunchuck. 00095 * @param a Either ::HatX or ::HatY. 00096 * @return Return the analog value in the range from approximately 25-230. 00097 */ 00098 uint8_t getAnalogHat(HatEnum a); 00099 /** 00100 * Used to read the joystick of the Wii U Pro Controller. 00101 * @param a Either ::LeftHatX, ::LeftHatY, ::RightHatX or ::RightHatY. 00102 * @return Return the analog value in the range from approximately 800-3200. 00103 */ 00104 uint16_t getAnalogHat(AnalogHatEnum a); 00105 00106 /** 00107 * Pitch calculated from the Wiimote. A complimentary filter is used if the Motion Plus is connected. 00108 * @return Pitch in the range from 0-360. 00109 */ 00110 float getPitch() { 00111 if(motionPlusConnected) 00112 return compPitch; 00113 return getWiimotePitch(); 00114 }; 00115 00116 /** 00117 * Roll calculated from the Wiimote. A complimentary filter is used if the Motion Plus is connected. 00118 * @return Roll in the range from 0-360. 00119 */ 00120 float getRoll() { 00121 if(motionPlusConnected) 00122 return compRoll; 00123 return getWiimoteRoll(); 00124 }; 00125 00126 /** 00127 * This is the yaw calculated by the gyro. 00128 * 00129 * <B>NOTE:</B> This angle will drift a lot and is only available if the Motion Plus extension is connected. 00130 * @return The angle calculated using the gyro. 00131 */ 00132 float getYaw() { 00133 return gyroYaw; 00134 }; 00135 00136 /** Used to set all LEDs and rumble off. */ 00137 void setAllOff(); 00138 /** Turn off rumble. */ 00139 void setRumbleOff(); 00140 /** Turn on rumble. */ 00141 void setRumbleOn(); 00142 /** Toggle rumble. */ 00143 void setRumbleToggle(); 00144 00145 /** 00146 * Set LED value without using the ::LEDEnum. 00147 * @param value See: ::LEDEnum. 00148 */ 00149 void setLedRaw(uint8_t value); 00150 00151 /** Turn all LEDs off. */ 00152 void setLedOff() { 00153 setLedRaw(0); 00154 }; 00155 /** 00156 * Turn the specific ::LEDEnum off. 00157 * @param a The ::LEDEnum to turn off. 00158 */ 00159 void setLedOff(LEDEnum a); 00160 /** 00161 * Turn the specific ::LEDEnum on. 00162 * @param a The ::LEDEnum to turn on. 00163 */ 00164 void setLedOn(LEDEnum a); 00165 /** 00166 * Toggle the specific ::LEDEnum. 00167 * @param a The ::LEDEnum to toggle. 00168 */ 00169 void setLedToggle(LEDEnum a); 00170 /** 00171 * This will set the LEDs, so the user can see which connections are active. 00172 * 00173 * The first ::LEDEnum indicate that the Wiimote is connected, 00174 * the second ::LEDEnum indicate indicate that a Motion Plus is also connected 00175 * the third ::LEDEnum will indicate that a Nunchuck controller is also connected. 00176 */ 00177 void setLedStatus(); 00178 00179 /** 00180 * Return the battery level of the Wiimote. 00181 * @return The battery level in the range 0-255. 00182 */ 00183 uint8_t getBatteryLevel(); 00184 00185 /** 00186 * Return the Wiimote state. 00187 * @return See: http://wiibrew.org/wiki/Wiimote#0x20:_Status. 00188 */ 00189 uint8_t getWiiState() { 00190 return wiiState; 00191 }; 00192 /**@}*/ 00193 00194 /**@{*/ 00195 /** Variable used to indicate if a Wiimote is connected. */ 00196 bool wiimoteConnected; 00197 /** Variable used to indicate if a Nunchuck controller is connected. */ 00198 bool nunchuckConnected; 00199 /** Variable used to indicate if a Nunchuck controller is connected. */ 00200 bool motionPlusConnected; 00201 /** Variable used to indicate if a Wii U Pro controller is connected. */ 00202 bool wiiUProControllerConnected; 00203 /** Variable used to indicate if a Wii Balance Board is connected. */ 00204 bool wiiBalanceBoardConnected; 00205 /**@}*/ 00206 00207 /* IMU Data, might be usefull if you need to do something more advanced than just calculating the angle */ 00208 00209 /**@{*/ 00210 00211 /** Pitch and roll calculated from the accelerometer inside the Wiimote. */ 00212 float getWiimotePitch() { 00213 return (atan2f(accYwiimote, accZwiimote) + M_PI) * RAD_TO_DEG; 00214 }; 00215 00216 float getWiimoteRoll() { 00217 return (atan2f(accXwiimote, accZwiimote) + M_PI) * RAD_TO_DEG; 00218 }; 00219 /**@}*/ 00220 00221 /**@{*/ 00222 00223 /** Pitch and roll calculated from the accelerometer inside the Nunchuck. */ 00224 float getNunchuckPitch() { 00225 return (atan2f(accYnunchuck, accZnunchuck) + M_PI) * RAD_TO_DEG; 00226 }; 00227 00228 float getNunchuckRoll() { 00229 return (atan2f(accXnunchuck, accZnunchuck) + M_PI) * RAD_TO_DEG; 00230 }; 00231 /**@}*/ 00232 00233 /**@{*/ 00234 /** Accelerometer values used to calculate pitch and roll. */ 00235 int16_t accXwiimote, accYwiimote, accZwiimote; 00236 int16_t accXnunchuck, accYnunchuck, accZnunchuck; 00237 /**@}*/ 00238 00239 /* Variables for the gyro inside the Motion Plus */ 00240 /** This is the pitch calculated by the gyro - use this to tune WII#pitchGyroScale. */ 00241 float gyroPitch; 00242 /** This is the roll calculated by the gyro - use this to tune WII#rollGyroScale. */ 00243 float gyroRoll; 00244 /** This is the yaw calculated by the gyro - use this to tune WII#yawGyroScale. */ 00245 float gyroYaw; 00246 00247 /**@{*/ 00248 /** The speed in deg/s from the gyro. */ 00249 float pitchGyroSpeed; 00250 float rollGyroSpeed; 00251 float yawGyroSpeed; 00252 /**@}*/ 00253 00254 /**@{*/ 00255 /** You might need to fine-tune these values. */ 00256 uint16_t pitchGyroScale; 00257 uint16_t rollGyroScale; 00258 uint16_t yawGyroScale; 00259 /**@}*/ 00260 00261 /**@{*/ 00262 /** Raw value read directly from the Motion Plus. */ 00263 int16_t gyroYawRaw; 00264 int16_t gyroRollRaw; 00265 int16_t gyroPitchRaw; 00266 /**@}*/ 00267 00268 /**@{*/ 00269 /** These values are set when the controller is first initialized. */ 00270 int16_t gyroYawZero; 00271 int16_t gyroRollZero; 00272 int16_t gyroPitchZero; 00273 /**@}*/ 00274 00275 /** @name Wii Balance Board functions */ 00276 00277 /** 00278 * Used to get the weight at the specific position on the Wii Balance Board. 00279 * @param pos ::BalanceBoardEnum to read from. 00280 * @return Returns the weight in kg. 00281 */ 00282 float getWeight(BalanceBoardEnum pos); 00283 00284 /** 00285 * Used to get total weight on the Wii Balance Board. 00286 * @return Returns the weight in kg. 00287 */ 00288 float getTotalWeight(); 00289 00290 /** 00291 * Used to get the raw reading at the specific position on the Wii Balance Board. 00292 * @param pos ::BalanceBoardEnum to read from. 00293 * @return Returns the raw reading. 00294 */ 00295 uint16_t getWeightRaw(BalanceBoardEnum pos) { 00296 return wiiBalanceBoardRaw[pos]; 00297 }; 00298 /**@}*/ 00299 00300 #ifdef WIICAMERA 00301 /** @name Wiimote IR camera functions 00302 * You will have to set ::ENABLE_WII_IR_CAMERA in settings.h to 1 in order use the IR camera. 00303 */ 00304 /** Initialises the camera as per the steps from: http://wiibrew.org/wiki/Wiimote#IR_Camera */ 00305 void IRinitialize(); 00306 00307 /** 00308 * IR object 1 x-position read from the Wii IR camera. 00309 * @return The x-position of the object in the range 0-1023. 00310 */ 00311 uint16_t getIRx1() { 00312 return IR_object_x1; 00313 }; 00314 00315 /** 00316 * IR object 1 y-position read from the Wii IR camera. 00317 * @return The y-position of the object in the range 0-767. 00318 */ 00319 uint16_t getIRy1() { 00320 return IR_object_y1; 00321 }; 00322 00323 /** 00324 * IR object 1 size read from the Wii IR camera. 00325 * @return The size of the object in the range 0-15. 00326 */ 00327 uint8_t getIRs1() { 00328 return IR_object_s1; 00329 }; 00330 00331 /** 00332 * IR object 2 x-position read from the Wii IR camera. 00333 * @return The x-position of the object in the range 0-1023. 00334 */ 00335 uint16_t getIRx2() { 00336 return IR_object_x2; 00337 }; 00338 00339 /** 00340 * IR object 2 y-position read from the Wii IR camera. 00341 * @return The y-position of the object in the range 0-767. 00342 */ 00343 uint16_t getIRy2() { 00344 return IR_object_y2; 00345 }; 00346 00347 /** 00348 * IR object 2 size read from the Wii IR camera. 00349 * @return The size of the object in the range 0-15. 00350 */ 00351 uint8_t getIRs2() { 00352 return IR_object_s2; 00353 }; 00354 00355 /** 00356 * IR object 3 x-position read from the Wii IR camera. 00357 * @return The x-position of the object in the range 0-1023. 00358 */ 00359 uint16_t getIRx3() { 00360 return IR_object_x3; 00361 }; 00362 00363 /** 00364 * IR object 3 y-position read from the Wii IR camera. 00365 * @return The y-position of the object in the range 0-767. 00366 */ 00367 uint16_t getIRy3() { 00368 return IR_object_y3; 00369 }; 00370 00371 /** 00372 * IR object 3 size read from the Wii IR camera. 00373 * @return The size of the object in the range 0-15. 00374 */ 00375 uint8_t getIRs3() { 00376 return IR_object_s3; 00377 }; 00378 00379 /** 00380 * IR object 4 x-position read from the Wii IR camera. 00381 * @return The x-position of the object in the range 0-1023. 00382 */ 00383 uint16_t getIRx4() { 00384 return IR_object_x4; 00385 }; 00386 00387 /** 00388 * IR object 4 y-position read from the Wii IR camera. 00389 * @return The y-position of the object in the range 0-767. 00390 */ 00391 uint16_t getIRy4() { 00392 return IR_object_y4; 00393 }; 00394 00395 /** 00396 * IR object 4 size read from the Wii IR camera. 00397 * @return The size of the object in the range 0-15. 00398 */ 00399 uint8_t getIRs4() { 00400 return IR_object_s4; 00401 }; 00402 00403 /** 00404 * Use this to check if the camera is enabled or not. 00405 * If not call WII#IRinitialize to initialize the IR camera. 00406 * @return True if it's enabled, false if not. 00407 */ 00408 bool isIRCameraEnabled() { 00409 return (wiiState & 0x08); 00410 }; 00411 /**@}*/ 00412 #endif 00413 00414 protected: 00415 /** @name BluetoothService implementation */ 00416 /** 00417 * Used to pass acldata to the services. 00418 * @param ACLData Incoming acldata. 00419 */ 00420 void ACLData(uint8_t* ACLData); 00421 /** Used to run part of the state machine. */ 00422 void Run(); 00423 /** Use this to reset the service. */ 00424 void Reset(); 00425 /** 00426 * Called when the controller is successfully initialized. 00427 * Use attachOnInit(void (*funcOnInit)(void)) to call your own function. 00428 * This is useful for instance if you want to set the LEDs in a specific way. 00429 */ 00430 void onInit(); 00431 /**@}*/ 00432 00433 private: 00434 00435 void L2CAP_task(); // L2CAP state machine 00436 00437 /* Variables filled from HCI event management */ 00438 bool activeConnection; // Used to indicate if it's already has established a connection 00439 00440 /* Variables used by high level L2CAP task */ 00441 uint8_t l2cap_state; 00442 uint8_t wii_event_flag; // Used for Wii flags 00443 00444 uint32_t ButtonState; 00445 uint32_t OldButtonState; 00446 uint32_t ButtonClickState; 00447 uint16_t hatValues[4]; 00448 00449 uint8_t HIDBuffer[3]; // Used to store HID commands 00450 00451 uint16_t stateCounter; 00452 bool unknownExtensionConnected; 00453 bool extensionConnected; 00454 bool checkBatteryLevel; // Set to true when getBatteryLevel() is called otherwise if should be false 00455 bool motionPlusInside; // True if it's a new Wiimote with the Motion Plus extension build into it 00456 00457 /* L2CAP Channels */ 00458 uint8_t control_scid[2]; // L2CAP source CID for HID_Control 00459 uint8_t control_dcid[2]; // 0x0060 00460 uint8_t interrupt_scid[2]; // L2CAP source CID for HID_Interrupt 00461 uint8_t interrupt_dcid[2]; // 0x0061 00462 00463 /* HID Commands */ 00464 void HID_Command(uint8_t* data, uint8_t nbytes); 00465 void setReportMode(bool continuous, uint8_t mode); 00466 00467 void writeData(uint32_t offset, uint8_t size, uint8_t* data); 00468 void initExtension1(); 00469 void initExtension2(); 00470 00471 void statusRequest(); // Used to update the Wiimote state and battery level 00472 00473 void readData(uint32_t offset, uint16_t size, bool EEPROM); 00474 void readExtensionType(); 00475 void readCalData(); 00476 void readWiiBalanceBoardCalibration(); // Used by the library to read the Wii Balance Board calibration values 00477 00478 void checkMotionPresent(); // Used to see if a Motion Plus is connected to the Wiimote 00479 void initMotionPlus(); 00480 void activateMotionPlus(); 00481 00482 uint16_t wiiBalanceBoardRaw[4]; // Wii Balance Board raw values 00483 uint16_t wiiBalanceBoardCal[3][4]; // Wii Balance Board calibration values 00484 00485 float compPitch; // Fusioned angle using a complimentary filter if the Motion Plus is connected 00486 float compRoll; // Fusioned angle using a complimentary filter if the Motion Plus is connected 00487 00488 bool activateNunchuck; 00489 bool motionValuesReset; // This bool is true when the gyro values has been reset 00490 uint32_t timer; 00491 00492 uint8_t wiiState; // Stores the value in l2capinbuf[12] - (0x01: Battery is nearly empty), (0x02: An Extension Controller is connected), (0x04: Speaker enabled), (0x08: IR enabled), (0x10: LED1, 0x20: LED2, 0x40: LED3, 0x80: LED4) 00493 uint8_t batteryLevel; 00494 00495 #ifdef WIICAMERA 00496 /* Private function and variables for the readings from the IR Camera */ 00497 void enableIRCamera1(); // Sets bit 2 of output report 13 00498 void enableIRCamera2(); // Sets bit 2 of output report 1A 00499 void writeSensitivityBlock1(); 00500 void writeSensitivityBlock2(); 00501 void write0x08Value(); 00502 void setWiiModeNumber(uint8_t mode_number); 00503 00504 uint16_t IR_object_x1; // IR x position 10 bits 00505 uint16_t IR_object_y1; // IR y position 10 bits 00506 uint8_t IR_object_s1; // IR size value 00507 uint16_t IR_object_x2; 00508 uint16_t IR_object_y2; 00509 uint8_t IR_object_s2; 00510 uint16_t IR_object_x3; // IR x position 10 bits 00511 uint16_t IR_object_y3; // IR y position 10 bits 00512 uint8_t IR_object_s3; // IR size value 00513 uint16_t IR_object_x4; 00514 uint16_t IR_object_y4; 00515 uint8_t IR_object_s4; 00516 #endif 00517 }; 00518 #endif
Generated on Tue Jul 12 2022 18:12:05 by
1.7.2