1 /*---------------------------------------------------------------------------*
2   Project:  Simple game pad API demo
3   File:     motordemo.c
4 
5   Copyright (C) 2000-2006 Nintendo.  All rights reserved.
6 
7   These coded instructions, statements, and computer programs contain
8   proprietary information of Nintendo of America Inc. and/or Nintendo
9   Company Ltd., and are protected by Federal copyright law.  They may
10   not be disclosed to third parties or copied or duplicated in any form,
11   in whole or in part, without the prior written consent of Nintendo.
12 
13   $Log: motordemo.c,v $
14   Revision 1.1  02/02/2006 06:11:49  yasuh-to
15   Initial import
16 
17 
18     4     01/03/06 17:18 Shiki
19     Modified InitCont() to support controller recalibration.
20 
21     3     01/03/05 11:00 Shiki
22     Revised.
23 
24     2     12/01/00 6:45p Shiki
25     Removed PADSetSpec().
26 
27     1     11/29/00 4:26p Shiki
28     Initial check-in.
29   $NoKeywords: $
30  *---------------------------------------------------------------------------*/
31 
32 #include <string.h>
33 #include <revolution.h>
34 #include "cont.h"
35 
36 u32 Motor[PAD_MAX_CONTROLLERS];
37 s32 Level[PAD_MAX_CONTROLLERS];
38 
39 #define MAX     (60*60)
40 #define MIN     (10*10)
41 
RambleCont(void)42 static void RambleCont(void)
43 {
44     int  chan;
45     BOOL controlMotor = FALSE;
46 
47     for (chan = 0; chan < PAD_MAX_CONTROLLERS; chan++)
48     {
49         Cont* cont;
50 
51         cont = &Conts[chan];
52         if (cont->err != PAD_ERR_NONE)
53         {
54             continue;
55         }
56 
57         if (cont->down & PAD_BUTTON_A)
58         {
59             Motor[chan] = (u32) ((Motor[chan] == PAD_MOTOR_RUMBLE) ?
60                                  PAD_MOTOR_STOP : PAD_MOTOR_RUMBLE);
61             controlMotor = TRUE;
62         }
63         else if ((cont->down & PAD_BUTTON_B) &&
64                  Motor[chan] == PAD_MOTOR_RUMBLE)
65         {
66             Motor[chan] = PAD_MOTOR_STOP_HARD;
67             controlMotor = TRUE;
68         }
69         else if (cont->button & PAD_BUTTON_X)
70         {
71             s32 level = (cont->stickX * cont->stickX + cont->stickY * cont->stickY);
72             if (MAX < level && Motor[chan] != PAD_MOTOR_RUMBLE)
73             {
74                 Motor[chan] = PAD_MOTOR_RUMBLE;
75                 controlMotor = TRUE;
76             }
77             else if (level < MIN && Motor[chan] != PAD_MOTOR_STOP)
78             {
79                 Motor[chan] = PAD_MOTOR_STOP;
80                 controlMotor = TRUE;
81             }
82             else
83             {
84                 // Adjust the frequency to start the motor.
85                 Level[chan] += level;
86                 if (MAX < Level[chan])
87                 {
88                     Level[chan] = 0;
89                     if (Motor[chan] != PAD_MOTOR_RUMBLE)
90                     {
91                         Motor[chan] = PAD_MOTOR_RUMBLE;
92                         controlMotor = TRUE;
93                     }
94                 }
95                 else if (Motor[chan] != PAD_MOTOR_STOP)
96                 {
97                     Motor[chan] = PAD_MOTOR_STOP;
98                     controlMotor = TRUE;
99                 }
100             }
101         }
102     }
103 
104     if (controlMotor)
105     {
106         PADControlAllMotors(Motor);
107     }
108 }
109 
PrintIntro(void)110 static void PrintIntro(void)
111 {
112     OSReport("\n\n");
113     OSReport("************************************************\n");
114     OSReport("motordemo: control ramble motor\n");
115     OSReport("************************************************\n");
116     OSReport("\n");
117     OSReport("Button A         : start/stop motor\n");
118     OSReport("Button B         : hard stop motor\n");
119     OSReport("Button X + stick : control motor strength\n");
120 }
121 
main(void)122 void main(void)
123 {
124     BOOL reset = FALSE;
125 
126     VIInit();
127     PADInit();
128 
129     PrintIntro();
130 
131     InitCont(PAD_CHAN0_BIT | PAD_CHAN1_BIT |
132              PAD_CHAN2_BIT | PAD_CHAN3_BIT, FALSE);
133 
134     for (;;)
135     {
136         ReadCont();
137         if (reset)
138         {
139             if (!OSGetResetSwitchState())
140             {
141                 reset = FALSE;
142             }
143             continue;
144         }
145 
146         RambleCont();
147         if (OSGetResetSwitchState())
148         {
149             reset = TRUE;
150 
151             // InitCont() stops all motors
152             memset(Motor, 0, sizeof Motor);
153             memset(Level, 0, sizeof Level);
154             InitCont(PAD_CHAN0_BIT | PAD_CHAN1_BIT |
155                      PAD_CHAN2_BIT | PAD_CHAN3_BIT, TRUE);
156         }
157         VIWaitForRetrace();
158     }
159 }
160