Example #1
0
        protected override bool ParseReport(byte[] report)
        {
            if (report[0] < 0x20)
                throw new InvalidOperationException("Received an output report!");
            InputReport type = (InputReport)report[0];
            if (type >= InputReport.Buttons && type <= InputReport.ButtonsAccelerometer36IrB)
            {
                if (type == InputReport.ButtonsAccelerometer36IrB)
                    ReportingMode = ReportingMode.ButtonsAccelerometer36Ir;
                else
                    ReportingMode = (ReportingMode)type;

                IRMode irMode = GetIrMode(type);
                if (this._IrMode != irMode)
                {
                    for (int i = 0; i < _CachedIRBeacons.Length; i++)
                    {
                        BasicIRBeacon newBeacon = null;
                        switch (irMode)
                        {
                            case IRMode.Basic:
                                newBeacon = new BasicIRBeacon();
                                break;
                            case IRMode.Extended:
                                newBeacon = new ExtendedIRBeacon();
                                break;
                            case IRMode.Full:
                                newBeacon = new FullIRBeacon();
                                break;
                        }
                        _CachedIRBeacons[i] = newBeacon;
                        _IRBeacons[i] = null;
                    }
                    this._IrMode = irMode;
                }
            }
            switch (type)
            {
                case InputReport.Buttons:
                    ParseButtons(report, 1);
                    break;
                case InputReport.ButtonsAccelerometer:
                    ParseButtons(report, 1);
                    ParseAccelerometer(report, 3);
                    break;
                case InputReport.Buttons8Extension:
                    ParseButtons(report, 1);
                    ParseExtension(report, 3, 8);
                    break;
                case InputReport.ButtonsAccelerometer12Ir:
                    {
                        ParseButtons(report, 1);
                        ParseAccelerometer(report, 3);

                        ExtendedIRBeacon irBeacon;

                        // Parse beacon 0.
                        irBeacon = (ExtendedIRBeacon)_CachedIRBeacons[0];
                        _IRBeacons[0] = ParseExtendedBeacon(report, 6, irBeacon) ? irBeacon : null;

                        // Parse beacon 1.
                        irBeacon = (ExtendedIRBeacon)_CachedIRBeacons[1];
                        _IRBeacons[1] = ParseExtendedBeacon(report, 9, irBeacon) ? irBeacon : null;

                        // Parse beacon 2.
                        irBeacon = (ExtendedIRBeacon)_CachedIRBeacons[2];
                        _IRBeacons[2] = ParseExtendedBeacon(report, 12, irBeacon) ? irBeacon : null;

                        // Parse beacon 3.
                        irBeacon = (ExtendedIRBeacon)_CachedIRBeacons[3];
                        _IRBeacons[3] = ParseExtendedBeacon(report, 15, irBeacon) ? irBeacon : null;
                    }
                    break;
                case InputReport.Buttons19Extension:
                    ParseButtons(report, 1);
                    ParseExtension(report, 3, 19);
                    break;
                case InputReport.ButtonsAccelerometer16Extension:
                    ParseButtons(report, 1);
                    ParseAccelerometer(report, 3);
                    ParseExtension(report, 6, 16);
                    break;
                case InputReport.Buttons10Ir9Extension:
                case InputReport.ButtonsAccelerometer10Ir6Extension:
                    {
                        int offset = 1;
                        offset += ParseButtons(report, offset);
                        if (type == InputReport.ButtonsAccelerometer10Ir6Extension)
                            offset += ParseAccelerometer(report, offset);

                        BasicIRBeacon irBeacon;

                        // Parse beacon 0.
                        irBeacon = _CachedIRBeacons[0];
                        _IRBeacons[0] = ParseBasicBeacon(report, offset, 0, irBeacon) ? irBeacon : null;

                        // Parse beacon 1.
                        irBeacon = _CachedIRBeacons[1];
                        _IRBeacons[1] = ParseBasicBeacon(report, offset, 1, irBeacon) ? irBeacon : null;

                        // Parse beacon 2.
                        irBeacon = _CachedIRBeacons[2];
                        _IRBeacons[2] = ParseBasicBeacon(report, offset + 5, 0, irBeacon) ? irBeacon : null;

                        // Parse beacon 3.
                        irBeacon = _CachedIRBeacons[3];
                        _IRBeacons[3] = ParseBasicBeacon(report, offset + 5, 1, irBeacon) ? irBeacon : null;

                        offset += 10; // Each pair of IR-beacons is 5 bytes.

                        if (type == InputReport.ButtonsAccelerometer10Ir6Extension)
                            ParseExtension(report, offset, 6);
                        else
                            ParseExtension(report, offset, 9);
                    }
                    break;
                case InputReport.Extension:
                    ParseExtension(report, 1, 21);
                    break;
                case InputReport.ButtonsAccelerometer36IrA:
                    {
                        ParseButtons(report, 1); // since button information is complete on both the interlaced reports it needs no temporary storage

                        _PartialAccelerometerX = report[3];
                        _PartialAccelerometerZ = (ushort)(((report[2] & 0x60) << 1) | ((report[1] & 0x60) >> 1));

                        _PartialIRBeaconOneResult = ParseFullBeacon(report, 4, (FullIRBeacon)_CachedIRBeacons[0]);
                        _PartialIRBeaconTwoResult = ParseFullBeacon(report, 13, (FullIRBeacon)_CachedIRBeacons[1]);
                    }
                    break;
                case InputReport.ButtonsAccelerometer36IrB:
                    {
                        ParseButtons(report, 1);

                        // Complete the _PartialAccelerometerZ field
                        _PartialAccelerometerZ = (ushort)(_PartialAccelerometerZ | ((report[2] & 60) >> 3) | ((report[1] & 60) >> 5));

                        // Initialize the accelerometer if it was not yet initialized (should never happen).
                        if (Accelerometer == null)
                            ReadCalibrationData();

                        // Construct the new accelerometer-values from now completed data
                        Accelerometer.Raw.X = _PartialAccelerometerX;
                        Accelerometer.Raw.Y = report[3];
                        Accelerometer.Raw.Z = _PartialAccelerometerZ;

                        UpdateCalibratedAccelerometer();

                        FullIRBeacon irBeacon;

                        // Commit partial irbeacon from 'a' report
                        IRBeacons[0] = _PartialIRBeaconOneResult ? _CachedIRBeacons[0] : null;

                        // Commit partial irbeacon from 'a' report
                        IRBeacons[1] = _PartialIRBeaconTwoResult ? _CachedIRBeacons[1] : null;

                        // Parse beacon 2.
                        irBeacon = (FullIRBeacon)_CachedIRBeacons[2];
                        IRBeacons[2] = ParseFullBeacon(report, 4, irBeacon) ? irBeacon : null;

                        // Parse beacon 3.
                        irBeacon = (FullIRBeacon)_CachedIRBeacons[3];
                        IRBeacons[3] = ParseFullBeacon(report, 13, irBeacon) ? irBeacon : null;
                    }
                    break;

                case InputReport.GetStatusResult:
                    ParseButtons(report, 1);
                    ParseStatus(report);
                    break;
                case InputReport.ReadDataResult:
                    ParseButtons(report, 1);
                    // The rest is handled by the ReadData method (waiting for the report).
                    break;
                case InputReport.WriteDataResult:
                    // The rest is handled by the WriteData method (waiting for the report).
                    break;
                default:
                    Debug.WriteLine("Unknown report type: " + type.ToString("x"));
                    return false;
            }

            if ((type >= InputReport.Buttons || type == InputReport.GetStatusResult) && (type != InputReport.ButtonsAccelerometer36IrA))
                OnUpdated();
            return true;
        }
Example #2
0
 /// <summary>
 /// http://wiibrew.org/index.php?title=Wiimote#Basic_Mode
 /// </summary>
 protected static bool ParseBasicBeacon(byte[] buff, int offset, int beaconIndex, BasicIRBeacon irBeacon)
 {
     switch (beaconIndex)
     {
         case 0:
             irBeacon.X = buff[offset + 0] | ((buff[offset + 2] >> 4) & 0x03) << 8;
             irBeacon.Y = buff[offset + 1] | ((buff[offset + 2] >> 6) & 0x03) << 8;
             break;
         case 1:
             irBeacon.X = buff[offset + 3] | ((buff[offset + 2] >> 0) & 0x03) << 8;
             irBeacon.Y = buff[offset + 4] | ((buff[offset + 2] >> 2) & 0x03) << 8;
             break;
         case 2:
             irBeacon.X = buff[11] | ((buff[13] >> 4) & 0x03) << 8;
             irBeacon.Y = buff[12] | ((buff[13] >> 6) & 0x03) << 8;
             break;
         case 3:
             irBeacon.X = buff[14] | ((buff[13] >> 0) & 0x03) << 8;
             irBeacon.Y = buff[15] | ((buff[13] >> 2) & 0x03) << 8;
             break;
     }
     return !(irBeacon.X == 1023 && irBeacon.Y == 1023);
 }