00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017 #include "iatan2.h"
00018
00019 static short atan2_table[] = {
00020 0, 25, 50, 75, 101, 126, 151, 176, 201, 226,
00021 251, 277, 302, 327, 352, 377, 402, 428, 453, 478,
00022 503, 529, 554, 579, 604, 630, 655, 680, 705, 731,
00023 756, 781, 807, 832, 858, 883, 908, 934, 959, 985,
00024 1010, 1036, 1061, 1087, 1113, 1138, 1164, 1189, 1215, 1241,
00025 1267, 1292, 1318, 1344, 1370, 1396, 1421, 1447, 1473, 1499,
00026 1525, 1551, 1577, 1603, 1629, 1656, 1682, 1708, 1734, 1761,
00027 1787, 1813, 1840, 1866, 1892, 1919, 1945, 1972, 1999, 2025,
00028 2052, 2079, 2105, 2132, 2159, 2186, 2213, 2240, 2267, 2294,
00029 2321, 2348, 2376, 2403, 2430, 2458, 2485, 2512, 2540, 2568,
00030 2595, 2623, 2651, 2678, 2706, 2734, 2762, 2790, 2818, 2846,
00031 2875, 2903, 2931, 2960, 2988, 3016, 3045, 3074, 3102, 3131,
00032 3160, 3189, 3218, 3247, 3276, 3305, 3334, 3364, 3393, 3423,
00033 3452, 3482, 3512, 3541, 3571, 3601, 3631, 3661, 3692, 3722,
00034 3752, 3783, 3813, 3844, 3875, 3905, 3936, 3967, 3998, 4029,
00035 4061, 4092, 4124, 4155, 4187, 4218, 4250, 4282, 4314, 4346,
00036 4379, 4411, 4444, 4476, 4509, 4542, 4575, 4608, 4641, 4674,
00037 4707, 4741, 4774, 4808, 4842, 4876, 4910, 4944, 4979, 5013,
00038 5048, 5083, 5117, 5152, 5188, 5223, 5258, 5294, 5329, 5365,
00039 5401, 5437, 5474, 5510, 5547, 5583, 5620, 5657, 5695, 5732,
00040 5769, 5807, 5845, 5883, 5921, 5960, 5998, 6037, 6076, 6115,
00041 6154, 6193, 6233, 6273, 6313, 6353, 6393, 6434, 6474, 6515,
00042 6556, 6598, 6639, 6681, 6723, 6765, 6808, 6850, 6893, 6936,
00043 6979, 7023, 7066, 7110, 7155, 7199, 7244, 7289, 7334, 7379,
00044 7425, 7471, 7517, 7563, 7610, 7657, 7704, 7752, 7799, 7847,
00045 7896, 7944, 7993, 8043, 8092, 8142, 8192, 8193
00046 };
00047
00048 static int atanValue(int y, int x, int sign_offset) {
00049 short *p = atan2_table;
00050 short v;
00051 int ret;
00052 int offset;
00053
00054 short *first, *last, *pre;
00055
00056 offset = (sign_offset < 0) ? -sign_offset : sign_offset ;
00057
00058 if (x == 0) {
00059 ;
00060 } else {
00061 v = y * 8192 / x;
00062 v = (v < 0) ? -v : v;
00063 first = atan2_table;
00064 last = atan2_table + 256;
00065
00066 do {
00067 pre = p;
00068 p = atan2_table + ((first-atan2_table) + (last-atan2_table)) / 2;
00069 if (*p > v) {
00070 last = p;
00071 } else {
00072 first = p;
00073 }
00074 } while (p != pre);
00075 }
00076 ret = (int)((p - atan2_table) * 32);
00077
00078 if (sign_offset < 0) {
00079 ret = offset - ret;
00080 } else {
00081 ret += offset;
00082 }
00083
00084 return ret;
00085 }
00086
00087 #define DEG(X) (int)(1.0 * 65536 * X / 360.0)
00088
00099 int iatan2(int y, int x) {
00100 int ret;
00101
00102 if (y >= 0) {
00103 if (x >= 0) {
00104 if (x >= y) {
00105 ret = atanValue(y, x, DEG(0));
00106 } else {
00107 ret = atanValue(x, y, DEG(-90));
00108 }
00109 } else {
00110 if (-x <= y) {
00111 ret = atanValue(x, y, DEG(90));
00112 } else {
00113 ret = atanValue(y, x, DEG(-180));
00114 }
00115 }
00116 } else {
00117 if (x < 0) {
00118 if (-x >= -y) {
00119 ret = atanValue(y, x, DEG(180));
00120 } else {
00121 ret = atanValue(x, y, DEG(-270));
00122 }
00123 } else {
00124 if (x <= -y) {
00125 ret = atanValue(x, y, DEG(270));
00126 } else {
00127 ret = atanValue(y, x, -DEG(360));
00128 }
00129 }
00130 }
00131 return ret;
00132 }
00133