1 /*---------------------------------------------------------------------------*
2 Project: Horizon
3 File: math_Triangular.h
4
5 Copyright (C)2009-2010 Nintendo Co., Ltd. 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 $Revision: 19123 $
14 *---------------------------------------------------------------------------*/
15
16 #ifndef NN_MATH_TRIANGULAR_H_
17 #define NN_MATH_TRIANGULAR_H_
18
19 #include <nn/math/math_Config.h>
20 #include <nn/math/math_Constant.h>
21 #include <nn/math/math_Arithmetic.h>
22
23 #include <cmath>
24
25
26 namespace nn {
27 namespace math {
28 namespace internal {
29
30 struct SinCosSample
31 {
32 f32 sin_val;
33 f32 cos_val;
34 f32 sin_delta; // Difference from next sin_val
35 f32 cos_delta; // Difference from next cos_val
36 };
37
38 extern const SinCosSample gSinCosTbl[256 + 1];
39
40 } // namespace internal
41 } // namespace math
42 } // namespace nn
43
44
45 namespace nn {
46 namespace math {
47
48
49 /* =======================================================================
50 sin/cos/tan
51 ======================================================================== */
52 /* Please see man pages for details
53
54
55 */
56
57 #define NN_MATH_RAD_TO_FIDX(rad) ((rad) * (256.f / (2.0f * ::nn::math::F_PI)))
58 #define NN_MATH_DEG_TO_FIDX(deg) ((deg) * (256.f / 360.f) )
59 #define NN_MATH_DEG_TO_RAD(deg) ((deg) * (::nn::math::F_PI / 180.0f) )
60 #define NN_MATH_RAD_TO_DEG(rad) ((rad) * (180.0f / ::nn::math::F_PI) )
61 #define NN_MATH_FIDX_TO_RAD(fidx) ((fidx) * ((2.0f * ::nn::math::F_PI) / 256.f))
62 #define NN_MATH_FIDX_TO_DEG(fidx) ((fidx) * (360.f / 256.f) )
63
64
65 /*
66
67
68
69
70
71 */
72 f32 SinFIdx(f32 fidx);
73
74 /*
75
76
77
78
79
80 */
81 f32 CosFIdx(f32 fidx);
82
83 /*
84
85
86
87
88
89
90
91 */
92 void SinCosFIdx(f32* pSin, f32* pCos, f32 fidx);
93
94 /*
95
96
97
98
99
100 */
101 inline f32
TanFIdx(f32 fidx)102 TanFIdx(f32 fidx)
103 {
104 return ::std::tanf(NN_MATH_FIDX_TO_RAD(fidx));
105 }
106
107
108 /*
109
110
111
112
113
114 */
SinRad(f32 rad)115 inline f32 SinRad(f32 rad) { return SinFIdx(NN_MATH_RAD_TO_FIDX(rad)); }
116
117 /*
118
119
120
121
122
123 */
CosRad(f32 rad)124 inline f32 CosRad(f32 rad) { return CosFIdx(NN_MATH_RAD_TO_FIDX(rad)); }
125
126 /*
127
128
129
130
131
132
133
134 */
SinCosRad(f32 * s,f32 * c,f32 rad)135 inline void SinCosRad(f32* s, f32* c, f32 rad) { SinCosFIdx(s, c, NN_MATH_RAD_TO_FIDX(rad)); }
136
137 /*
138
139
140
141
142
143 */
TanRad(f32 rad)144 inline f32 TanRad(f32 rad) { return TanFIdx(NN_MATH_RAD_TO_FIDX(rad)); }
145
146
147
148
149 /*
150
151
152
153
154
155 */
SinDeg(f32 deg)156 inline f32 SinDeg(f32 deg) { return SinFIdx(NN_MATH_DEG_TO_FIDX(deg)); }
157
158 /*
159
160
161
162
163
164 */
CosDeg(f32 deg)165 inline f32 CosDeg(f32 deg) { return CosFIdx(NN_MATH_DEG_TO_FIDX(deg)); }
166
167 /*
168
169
170
171
172
173
174
175 */
SinCosDeg(f32 * s,f32 * c,f32 deg)176 inline void SinCosDeg(f32* s, f32* c, f32 deg) { SinCosFIdx(s, c, NN_MATH_DEG_TO_FIDX(deg)); }
177
178 /*
179
180
181
182
183
184 */
TanDeg(f32 deg)185 inline f32 TanDeg(f32 deg) { return TanFIdx(NN_MATH_DEG_TO_FIDX(deg)); }
186
187 #if 1
188 /* Once we start using one with a 16-bit index, the implementation of this function will be replaced. */
189
190 /*
191
192
193
194
195
196 */
197 f32 SinIdx(u16 idx);
198
199 /*
200
201
202
203
204
205 */
206 f32 CosIdx(u16 idx);
207
208 /*
209
210
211
212
213
214
215
216 */
217 void SinCosIdx(f32* s, f32* c, u16 idx);
218
219 /*
220
221
222
223
224
225 */
TanIdx(u16 idx)226 inline f32 TanIdx(u16 idx) { return TanFIdx(U16ToF32(idx) * (1.f / 256.f)); }
227 #endif
228
NN_fAcos(f32 x)229 inline f32 NN_fAcos(f32 x) { return ::std::acosf(x); }
NN_fAsin(f32 x)230 inline f32 NN_fAsin(f32 x) { return ::std::asinf(x); }
NN_fAtan(f32 x)231 inline f32 NN_fAtan(f32 x) { return ::std::atanf(x); }
NN_fAtan2(f32 y,f32 x)232 inline f32 NN_fAtan2(f32 y, f32 x) { return ::std::atan2f(y, x); }
233
234
235 /*
236
237
238
239
240
241 */
242 inline f32
AsinFIdx(f32 x)243 AsinFIdx(f32 x)
244 {
245 NN_MATH_WARNING(x <= 1.f && x >= -1.f, "AsinFIdx: Input is out of the domain.");
246 return NN_MATH_RAD_TO_FIDX(::std::asin(x));
247 }
248
249 /*
250
251
252
253
254
255 */
256 inline f32
AcosFIdx(f32 x)257 AcosFIdx(f32 x)
258 {
259 NN_MATH_WARNING(x <= 1.f && x >= -1.f, "AcosFIdx: Input is out of the domain.");
260 return NN_MATH_RAD_TO_FIDX(::std::acosf(x));
261 }
262
263
264 f32 AtanFIdx(f32 x);
265 f32 Atan2FIdx(f32 y, f32 x);
266
267
268 /*
269
270
271
272
273
274 */
AsinRad(f32 x)275 inline f32 AsinRad(f32 x)
276 {
277 NN_MATH_WARNING(x <= 1.f && x >= -1.f, "AsinRad: Input is out of the domain.");
278 return ::std::asin(x);
279 }
280
281 /*
282
283
284
285
286
287 */
AcosRad(f32 x)288 inline f32 AcosRad(f32 x)
289 {
290 NN_MATH_WARNING(x <= 1.f && x >= -1.f, "AcosRad: Input is out of the domain.");
291 return ::std::acos(x);
292 }
293
294 /*
295
296
297
298
299
300 */
AtanRad(f32 x)301 inline f32 AtanRad(f32 x) { return NN_MATH_FIDX_TO_RAD(AtanFIdx(x)); }
302
303 /*
304
305
306
307
308
309
310 */
Atan2Rad(f32 y,f32 x)311 inline f32 Atan2Rad(f32 y, f32 x) { return NN_MATH_FIDX_TO_RAD(Atan2FIdx(y, x)); }
312
313
314
315
316
317
318 /*
319
320
321
322
323
324 */
AsinDeg(f32 x)325 inline f32 AsinDeg(f32 x)
326 {
327 NN_MATH_WARNING(x <= 1.f && x >= -1.f, "AsinDeg: Input is out of the domain.");
328 return NN_MATH_RAD_TO_DEG(::std::asin(x));
329 }
330
331 /*
332
333
334
335
336
337 */
AcosDeg(f32 x)338 inline f32 AcosDeg(f32 x)
339 {
340 NN_MATH_WARNING(x <= 1.f && x >= -1.f, "AcosDeg: Input is out of the domain.");
341 return NN_MATH_RAD_TO_DEG(::std::acos(x));
342 }
343
344 /*
345
346
347
348
349
350 */
AtanDeg(f32 x)351 inline f32 AtanDeg(f32 x) { return NN_MATH_FIDX_TO_DEG(AtanFIdx(x)); }
352
353 /*
354
355
356
357
358
359
360 */
Atan2Deg(f32 y,f32 x)361 inline f32 Atan2Deg(f32 y, f32 x) { return NN_MATH_FIDX_TO_DEG(Atan2FIdx(y, x)); }
362
363 #if 1
364 /* Once we start using one with a 16-bit index, the implementation of this function will be replaced. */
365
366
367 /*
368
369
370
371
372
373 */
374 // Returns an index in the range of 0 - 90 degrees and 270 - 360 degrees
AsinIdx(f32 x)375 inline u16 AsinIdx(f32 x) { f32 fidx = AsinFIdx(x); return F32ToU16((fidx < 0 ? fidx + 256.f : fidx) * 256.f); }
376
377 /*
378
379
380
381
382
383 */
384 // Returns index in the [0,PI] range
AcosIdx(f32 x)385 inline u16 AcosIdx(f32 x) { return F32ToU16(AcosFIdx(x) * 256.f); }
386
387 /*
388
389
390
391
392
393 */
394 // Returns an index in the range of 0 - 90 degrees and 270 - 360 degrees
395 u16 AtanIdx(f32 x);
396
397 /*
398
399
400
401
402
403
404 */
405 // Returns an index in the range of 0 - 360 degrees
406 u16 Atan2Idx(f32 y, f32 x);
407 #endif
408
409 /*
410
411 */
412
413 } // namespace math
414 } // namespace nn
415
416
417 /* NN_MATH_TRIANGULAR_H_ */
418 #endif
419