1
0

MathUtil.cpp 7.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278
  1. /**
  2. Copyright 2013 BlackBerry Inc.
  3. Licensed under the Apache License, Version 2.0 (the "License");
  4. you may not use this file except in compliance with the License.
  5. You may obtain a copy of the License at
  6. http://www.apache.org/licenses/LICENSE-2.0
  7. Unless required by applicable law or agreed to in writing, software
  8. distributed under the License is distributed on an "AS IS" BASIS,
  9. WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  10. See the License for the specific language governing permissions and
  11. limitations under the License.
  12. Original file from GamePlay3D: http://gameplay3d.org
  13. This file was modified to fit the cocos2d-x project
  14. */
  15. #include "math/MathUtil.h"
  16. #include "base/ccMacros.h"
  17. #if (CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID)
  18. #include <cpu-features.h>
  19. #endif
  20. //#define USE_NEON32 : neon 32 code will be used
  21. //#define USE_NEON64 : neon 64 code will be used
  22. //#define INCLUDE_NEON32 : neon 32 code included
  23. //#define INCLUDE_NEON64 : neon 64 code included
  24. //#define USE_SSE : SSE code used
  25. //#define INCLUDE_SSE : SSE code included
  26. #if (CC_TARGET_PLATFORM == CC_PLATFORM_IOS)
  27. #if defined (__arm64__)
  28. #define USE_NEON64
  29. #define INCLUDE_NEON64
  30. #elif defined (__ARM_NEON__)
  31. #define USE_NEON32
  32. #define INCLUDE_NEON32
  33. #else
  34. #endif
  35. #elif (CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID)
  36. #if defined (__arm64__) || defined (__aarch64__)
  37. #define USE_NEON64
  38. #define INCLUDE_NEON64
  39. #elif defined (__ARM_NEON__)
  40. #define INCLUDE_NEON32
  41. #else
  42. #endif
  43. #else
  44. #endif
  45. #if defined (__SSE__)
  46. #define USE_SSE
  47. #define INCLUDE_SSE
  48. #endif
  49. #ifdef INCLUDE_NEON32
  50. #include "math/MathUtilNeon.inl"
  51. #endif
  52. #ifdef INCLUDE_NEON64
  53. #include "math/MathUtilNeon64.inl"
  54. #endif
  55. #ifdef INCLUDE_SSE
  56. #include "math/MathUtilSSE.inl"
  57. #endif
  58. #include "math/MathUtil.inl"
  59. NS_CC_MATH_BEGIN
  60. void MathUtil::smooth(float* x, float target, float elapsedTime, float responseTime)
  61. {
  62. GP_ASSERT(x);
  63. if (elapsedTime > 0)
  64. {
  65. *x += (target - *x) * elapsedTime / (elapsedTime + responseTime);
  66. }
  67. }
  68. void MathUtil::smooth(float* x, float target, float elapsedTime, float riseTime, float fallTime)
  69. {
  70. GP_ASSERT(x);
  71. if (elapsedTime > 0)
  72. {
  73. float delta = target - *x;
  74. *x += delta * elapsedTime / (elapsedTime + (delta > 0 ? riseTime : fallTime));
  75. }
  76. }
  77. float MathUtil::lerp(float from, float to, float alpha)
  78. {
  79. return from * (1.0f - alpha) + to * alpha;
  80. }
  81. bool MathUtil::isNeon32Enabled()
  82. {
  83. #ifdef USE_NEON32
  84. return true;
  85. #elif (defined (INCLUDE_NEON32) && (CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID) )
  86. class AnrdoidNeonChecker
  87. {
  88. public:
  89. AnrdoidNeonChecker()
  90. {
  91. if (android_getCpuFamily() == ANDROID_CPU_FAMILY_ARM && (android_getCpuFeatures() & ANDROID_CPU_ARM_FEATURE_NEON) != 0)
  92. _isNeonEnabled = true;
  93. else
  94. _isNeonEnabled = false;
  95. }
  96. bool isNeonEnabled() const { return _isNeonEnabled; }
  97. private:
  98. bool _isNeonEnabled;
  99. };
  100. static AnrdoidNeonChecker checker;
  101. return checker.isNeonEnabled();
  102. #else
  103. return false;
  104. #endif
  105. }
  106. bool MathUtil::isNeon64Enabled()
  107. {
  108. #ifdef USE_NEON64
  109. return true;
  110. #else
  111. return false;
  112. #endif
  113. }
  114. void MathUtil::addMatrix(const float* m, float scalar, float* dst)
  115. {
  116. #ifdef USE_NEON32
  117. MathUtilNeon::addMatrix(m, scalar, dst);
  118. #elif defined (USE_NEON64)
  119. MathUtilNeon64::addMatrix(m, scalar, dst);
  120. #elif defined (INCLUDE_NEON32)
  121. if(isNeon32Enabled()) MathUtilNeon::addMatrix(m, scalar, dst);
  122. else MathUtilC::addMatrix(m, scalar, dst);
  123. #else
  124. MathUtilC::addMatrix(m, scalar, dst);
  125. #endif
  126. }
  127. void MathUtil::addMatrix(const float* m1, const float* m2, float* dst)
  128. {
  129. #ifdef USE_NEON32
  130. MathUtilNeon::addMatrix(m1, m2, dst);
  131. #elif defined (USE_NEON64)
  132. MathUtilNeon64::addMatrix(m1, m2, dst);
  133. #elif defined (INCLUDE_NEON32)
  134. if(isNeon32Enabled()) MathUtilNeon::addMatrix(m1, m2, dst);
  135. else MathUtilC::addMatrix(m1, m2, dst);
  136. #else
  137. MathUtilC::addMatrix(m1, m2, dst);
  138. #endif
  139. }
  140. void MathUtil::subtractMatrix(const float* m1, const float* m2, float* dst)
  141. {
  142. #ifdef USE_NEON32
  143. MathUtilNeon::subtractMatrix(m1, m2, dst);
  144. #elif defined (USE_NEON64)
  145. MathUtilNeon64::subtractMatrix(m1, m2, dst);
  146. #elif defined (INCLUDE_NEON32)
  147. if(isNeon32Enabled()) MathUtilNeon::subtractMatrix(m1, m2, dst);
  148. else MathUtilC::subtractMatrix(m1, m2, dst);
  149. #else
  150. MathUtilC::subtractMatrix(m1, m2, dst);
  151. #endif
  152. }
  153. void MathUtil::multiplyMatrix(const float* m, float scalar, float* dst)
  154. {
  155. #ifdef USE_NEON32
  156. MathUtilNeon::multiplyMatrix(m, scalar, dst);
  157. #elif defined (USE_NEON64)
  158. MathUtilNeon64::multiplyMatrix(m, scalar, dst);
  159. #elif defined (INCLUDE_NEON32)
  160. if(isNeon32Enabled()) MathUtilNeon::multiplyMatrix(m, scalar, dst);
  161. else MathUtilC::multiplyMatrix(m, scalar, dst);
  162. #else
  163. MathUtilC::multiplyMatrix(m, scalar, dst);
  164. #endif
  165. }
  166. void MathUtil::multiplyMatrix(const float* m1, const float* m2, float* dst)
  167. {
  168. #ifdef USE_NEON32
  169. MathUtilNeon::multiplyMatrix(m1, m2, dst);
  170. #elif defined (USE_NEON64)
  171. MathUtilNeon64::multiplyMatrix(m1, m2, dst);
  172. #elif defined (INCLUDE_NEON32)
  173. if(isNeon32Enabled()) MathUtilNeon::multiplyMatrix(m1, m2, dst);
  174. else MathUtilC::multiplyMatrix(m1, m2, dst);
  175. #else
  176. MathUtilC::multiplyMatrix(m1, m2, dst);
  177. #endif
  178. }
  179. void MathUtil::negateMatrix(const float* m, float* dst)
  180. {
  181. #ifdef USE_NEON32
  182. MathUtilNeon::negateMatrix(m, dst);
  183. #elif defined (USE_NEON64)
  184. MathUtilNeon64::negateMatrix(m, dst);
  185. #elif defined (INCLUDE_NEON32)
  186. if(isNeon32Enabled()) MathUtilNeon::negateMatrix(m, dst);
  187. else MathUtilC::negateMatrix(m, dst);
  188. #else
  189. MathUtilC::negateMatrix(m, dst);
  190. #endif
  191. }
  192. void MathUtil::transposeMatrix(const float* m, float* dst)
  193. {
  194. #ifdef USE_NEON32
  195. MathUtilNeon::transposeMatrix(m, dst);
  196. #elif defined (USE_NEON64)
  197. MathUtilNeon64::transposeMatrix(m, dst);
  198. #elif defined (INCLUDE_NEON32)
  199. if(isNeon32Enabled()) MathUtilNeon::transposeMatrix(m, dst);
  200. else MathUtilC::transposeMatrix(m, dst);
  201. #else
  202. MathUtilC::transposeMatrix(m, dst);
  203. #endif
  204. }
  205. void MathUtil::transformVec4(const float* m, float x, float y, float z, float w, float* dst)
  206. {
  207. #ifdef USE_NEON32
  208. MathUtilNeon::transformVec4(m, x, y, z, w, dst);
  209. #elif defined (USE_NEON64)
  210. MathUtilNeon64::transformVec4(m, x, y, z, w, dst);
  211. #elif defined (INCLUDE_NEON32)
  212. if(isNeon32Enabled()) MathUtilNeon::transformVec4(m, x, y, z, w, dst);
  213. else MathUtilC::transformVec4(m, x, y, z, w, dst);
  214. #else
  215. MathUtilC::transformVec4(m, x, y, z, w, dst);
  216. #endif
  217. }
  218. void MathUtil::transformVec4(const float* m, const float* v, float* dst)
  219. {
  220. #ifdef USE_NEON32
  221. MathUtilNeon::transformVec4(m, v, dst);
  222. #elif defined (USE_NEON64)
  223. MathUtilNeon64::transformVec4(m, v, dst);
  224. #elif defined (INCLUDE_NEON32)
  225. if(isNeon32Enabled()) MathUtilNeon::transformVec4(m, v, dst);
  226. else MathUtilC::transformVec4(m, v, dst);
  227. #else
  228. MathUtilC::transformVec4(m, v, dst);
  229. #endif
  230. }
  231. void MathUtil::crossVec3(const float* v1, const float* v2, float* dst)
  232. {
  233. #ifdef USE_NEON32
  234. MathUtilNeon::crossVec3(v1, v2, dst);
  235. #elif defined (USE_NEON64)
  236. MathUtilNeon64::crossVec3(v1, v2, dst);
  237. #elif defined (INCLUDE_NEON32)
  238. if(isNeon32Enabled()) MathUtilNeon::crossVec3(v1, v2, dst);
  239. else MathUtilC::crossVec3(v1, v2, dst);
  240. #else
  241. MathUtilC::crossVec3(v1, v2, dst);
  242. #endif
  243. }
  244. NS_CC_MATH_END