/src/FreeImage/Source/OpenEXR/Imath/ImathVec.cpp

https://bitbucket.org/cabalistic/ogredeps/ · C++ · 540 lines · 414 code · 81 blank · 45 comment · 89 complexity · 447fbf5ebceb25691b2450ba43782830 MD5 · raw file

  1. ///////////////////////////////////////////////////////////////////////////
  2. //
  3. // Copyright (c) 2002, Industrial Light & Magic, a division of Lucas
  4. // Digital Ltd. LLC
  5. //
  6. // All rights reserved.
  7. //
  8. // Redistribution and use in source and binary forms, with or without
  9. // modification, are permitted provided that the following conditions are
  10. // met:
  11. // * Redistributions of source code must retain the above copyright
  12. // notice, this list of conditions and the following disclaimer.
  13. // * Redistributions in binary form must reproduce the above
  14. // copyright notice, this list of conditions and the following disclaimer
  15. // in the documentation and/or other materials provided with the
  16. // distribution.
  17. // * Neither the name of Industrial Light & Magic nor the names of
  18. // its contributors may be used to endorse or promote products derived
  19. // from this software without specific prior written permission.
  20. //
  21. // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  22. // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  23. // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
  24. // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
  25. // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
  26. // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
  27. // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
  28. // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
  29. // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  30. // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
  31. // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  32. //
  33. ///////////////////////////////////////////////////////////////////////////
  34. //----------------------------------------------------------------------------
  35. //
  36. // Specializations of the Vec2<T> and Vec3<T> templates.
  37. //
  38. //----------------------------------------------------------------------------
  39. #include "ImathVec.h"
  40. #if (defined _WIN32 || defined _WIN64) && defined _MSC_VER
  41. // suppress exception specification warnings
  42. #pragma warning(disable:4290)
  43. #endif
  44. namespace Imath {
  45. namespace
  46. {
  47. template<class T>
  48. bool
  49. normalizeOrThrow(Vec2<T> &v)
  50. {
  51. int axis = -1;
  52. for (int i = 0; i < 2; i ++)
  53. {
  54. if (v[i] != 0)
  55. {
  56. if (axis != -1)
  57. {
  58. throw IntVecNormalizeExc ("Cannot normalize an integer "
  59. "vector unless it is parallel "
  60. "to a principal axis");
  61. }
  62. axis = i;
  63. }
  64. }
  65. v[axis] = (v[axis] > 0) ? 1 : -1;
  66. return true;
  67. }
  68. template<class T>
  69. bool
  70. normalizeOrThrow(Vec3<T> &v)
  71. {
  72. int axis = -1;
  73. for (int i = 0; i < 3; i ++)
  74. {
  75. if (v[i] != 0)
  76. {
  77. if (axis != -1)
  78. {
  79. throw IntVecNormalizeExc ("Cannot normalize an integer "
  80. "vector unless it is parallel "
  81. "to a principal axis");
  82. }
  83. axis = i;
  84. }
  85. }
  86. v[axis] = (v[axis] > 0) ? 1 : -1;
  87. return true;
  88. }
  89. template<class T>
  90. bool
  91. normalizeOrThrow(Vec4<T> &v)
  92. {
  93. int axis = -1;
  94. for (int i = 0; i < 4; i ++)
  95. {
  96. if (v[i] != 0)
  97. {
  98. if (axis != -1)
  99. {
  100. throw IntVecNormalizeExc ("Cannot normalize an integer "
  101. "vector unless it is parallel "
  102. "to a principal axis");
  103. }
  104. axis = i;
  105. }
  106. }
  107. v[axis] = (v[axis] > 0) ? 1 : -1;
  108. return true;
  109. }
  110. }
  111. // Vec2<short>
  112. template <>
  113. short
  114. Vec2<short>::length () const
  115. {
  116. float lenF = Math<float>::sqrt ((float)dot (*this));
  117. short lenS = (short) (lenF + 0.5f);
  118. return lenS;
  119. }
  120. template <>
  121. const Vec2<short> &
  122. Vec2<short>::normalize ()
  123. {
  124. normalizeOrThrow<short>(*this);
  125. return *this;
  126. }
  127. template <>
  128. const Vec2<short> &
  129. Vec2<short>::normalizeExc () throw (Iex::MathExc)
  130. {
  131. if ((x == 0) && (y == 0))
  132. throw NullVecExc ("Cannot normalize null vector.");
  133. normalizeOrThrow<short>(*this);
  134. return *this;
  135. }
  136. template <>
  137. const Vec2<short> &
  138. Vec2<short>::normalizeNonNull ()
  139. {
  140. normalizeOrThrow<short>(*this);
  141. return *this;
  142. }
  143. template <>
  144. Vec2<short>
  145. Vec2<short>::normalized () const
  146. {
  147. Vec2<short> v(*this);
  148. normalizeOrThrow<short>(v);
  149. return v;
  150. }
  151. template <>
  152. Vec2<short>
  153. Vec2<short>::normalizedExc () const throw (Iex::MathExc)
  154. {
  155. if ((x == 0) && (y == 0))
  156. throw NullVecExc ("Cannot normalize null vector.");
  157. Vec2<short> v(*this);
  158. normalizeOrThrow<short>(v);
  159. return v;
  160. }
  161. template <>
  162. Vec2<short>
  163. Vec2<short>::normalizedNonNull () const
  164. {
  165. Vec2<short> v(*this);
  166. normalizeOrThrow<short>(v);
  167. return v;
  168. }
  169. // Vec2<int>
  170. template <>
  171. int
  172. Vec2<int>::length () const
  173. {
  174. float lenF = Math<float>::sqrt ((float)dot (*this));
  175. int lenI = (int) (lenF + 0.5f);
  176. return lenI;
  177. }
  178. template <>
  179. const Vec2<int> &
  180. Vec2<int>::normalize ()
  181. {
  182. normalizeOrThrow<int>(*this);
  183. return *this;
  184. }
  185. template <>
  186. const Vec2<int> &
  187. Vec2<int>::normalizeExc () throw (Iex::MathExc)
  188. {
  189. if ((x == 0) && (y == 0))
  190. throw NullVecExc ("Cannot normalize null vector.");
  191. normalizeOrThrow<int>(*this);
  192. return *this;
  193. }
  194. template <>
  195. const Vec2<int> &
  196. Vec2<int>::normalizeNonNull ()
  197. {
  198. normalizeOrThrow<int>(*this);
  199. return *this;
  200. }
  201. template <>
  202. Vec2<int>
  203. Vec2<int>::normalized () const
  204. {
  205. Vec2<int> v(*this);
  206. normalizeOrThrow<int>(v);
  207. return v;
  208. }
  209. template <>
  210. Vec2<int>
  211. Vec2<int>::normalizedExc () const throw (Iex::MathExc)
  212. {
  213. if ((x == 0) && (y == 0))
  214. throw NullVecExc ("Cannot normalize null vector.");
  215. Vec2<int> v(*this);
  216. normalizeOrThrow<int>(v);
  217. return v;
  218. }
  219. template <>
  220. Vec2<int>
  221. Vec2<int>::normalizedNonNull () const
  222. {
  223. Vec2<int> v(*this);
  224. normalizeOrThrow<int>(v);
  225. return v;
  226. }
  227. // Vec3<short>
  228. template <>
  229. short
  230. Vec3<short>::length () const
  231. {
  232. float lenF = Math<float>::sqrt ((float)dot (*this));
  233. short lenS = (short) (lenF + 0.5f);
  234. return lenS;
  235. }
  236. template <>
  237. const Vec3<short> &
  238. Vec3<short>::normalize ()
  239. {
  240. normalizeOrThrow<short>(*this);
  241. return *this;
  242. }
  243. template <>
  244. const Vec3<short> &
  245. Vec3<short>::normalizeExc () throw (Iex::MathExc)
  246. {
  247. if ((x == 0) && (y == 0) && (z == 0))
  248. throw NullVecExc ("Cannot normalize null vector.");
  249. normalizeOrThrow<short>(*this);
  250. return *this;
  251. }
  252. template <>
  253. const Vec3<short> &
  254. Vec3<short>::normalizeNonNull ()
  255. {
  256. normalizeOrThrow<short>(*this);
  257. return *this;
  258. }
  259. template <>
  260. Vec3<short>
  261. Vec3<short>::normalized () const
  262. {
  263. Vec3<short> v(*this);
  264. normalizeOrThrow<short>(v);
  265. return v;
  266. }
  267. template <>
  268. Vec3<short>
  269. Vec3<short>::normalizedExc () const throw (Iex::MathExc)
  270. {
  271. if ((x == 0) && (y == 0) && (z == 0))
  272. throw NullVecExc ("Cannot normalize null vector.");
  273. Vec3<short> v(*this);
  274. normalizeOrThrow<short>(v);
  275. return v;
  276. }
  277. template <>
  278. Vec3<short>
  279. Vec3<short>::normalizedNonNull () const
  280. {
  281. Vec3<short> v(*this);
  282. normalizeOrThrow<short>(v);
  283. return v;
  284. }
  285. // Vec3<int>
  286. template <>
  287. int
  288. Vec3<int>::length () const
  289. {
  290. float lenF = Math<float>::sqrt ((float)dot (*this));
  291. int lenI = (int) (lenF + 0.5f);
  292. return lenI;
  293. }
  294. template <>
  295. const Vec3<int> &
  296. Vec3<int>::normalize ()
  297. {
  298. normalizeOrThrow<int>(*this);
  299. return *this;
  300. }
  301. template <>
  302. const Vec3<int> &
  303. Vec3<int>::normalizeExc () throw (Iex::MathExc)
  304. {
  305. if ((x == 0) && (y == 0) && (z == 0))
  306. throw NullVecExc ("Cannot normalize null vector.");
  307. normalizeOrThrow<int>(*this);
  308. return *this;
  309. }
  310. template <>
  311. const Vec3<int> &
  312. Vec3<int>::normalizeNonNull ()
  313. {
  314. normalizeOrThrow<int>(*this);
  315. return *this;
  316. }
  317. template <>
  318. Vec3<int>
  319. Vec3<int>::normalized () const
  320. {
  321. Vec3<int> v(*this);
  322. normalizeOrThrow<int>(v);
  323. return v;
  324. }
  325. template <>
  326. Vec3<int>
  327. Vec3<int>::normalizedExc () const throw (Iex::MathExc)
  328. {
  329. if ((x == 0) && (y == 0) && (z == 0))
  330. throw NullVecExc ("Cannot normalize null vector.");
  331. Vec3<int> v(*this);
  332. normalizeOrThrow<int>(v);
  333. return v;
  334. }
  335. template <>
  336. Vec3<int>
  337. Vec3<int>::normalizedNonNull () const
  338. {
  339. Vec3<int> v(*this);
  340. normalizeOrThrow<int>(v);
  341. return v;
  342. }
  343. // Vec4<short>
  344. template <>
  345. short
  346. Vec4<short>::length () const
  347. {
  348. float lenF = Math<float>::sqrt ((float)dot (*this));
  349. short lenS = (short) (lenF + 0.5f);
  350. return lenS;
  351. }
  352. template <>
  353. const Vec4<short> &
  354. Vec4<short>::normalize ()
  355. {
  356. normalizeOrThrow<short>(*this);
  357. return *this;
  358. }
  359. template <>
  360. const Vec4<short> &
  361. Vec4<short>::normalizeExc () throw (Iex::MathExc)
  362. {
  363. if ((x == 0) && (y == 0) && (z == 0) && (w == 0))
  364. throw NullVecExc ("Cannot normalize null vector.");
  365. normalizeOrThrow<short>(*this);
  366. return *this;
  367. }
  368. template <>
  369. const Vec4<short> &
  370. Vec4<short>::normalizeNonNull ()
  371. {
  372. normalizeOrThrow<short>(*this);
  373. return *this;
  374. }
  375. template <>
  376. Vec4<short>
  377. Vec4<short>::normalized () const
  378. {
  379. Vec4<short> v(*this);
  380. normalizeOrThrow<short>(v);
  381. return v;
  382. }
  383. template <>
  384. Vec4<short>
  385. Vec4<short>::normalizedExc () const throw (Iex::MathExc)
  386. {
  387. if ((x == 0) && (y == 0) && (z == 0) && (w == 0))
  388. throw NullVecExc ("Cannot normalize null vector.");
  389. Vec4<short> v(*this);
  390. normalizeOrThrow<short>(v);
  391. return v;
  392. }
  393. template <>
  394. Vec4<short>
  395. Vec4<short>::normalizedNonNull () const
  396. {
  397. Vec4<short> v(*this);
  398. normalizeOrThrow<short>(v);
  399. return v;
  400. }
  401. // Vec4<int>
  402. template <>
  403. int
  404. Vec4<int>::length () const
  405. {
  406. float lenF = Math<float>::sqrt ((float)dot (*this));
  407. int lenI = (int) (lenF + 0.5f);
  408. return lenI;
  409. }
  410. template <>
  411. const Vec4<int> &
  412. Vec4<int>::normalize ()
  413. {
  414. normalizeOrThrow<int>(*this);
  415. return *this;
  416. }
  417. template <>
  418. const Vec4<int> &
  419. Vec4<int>::normalizeExc () throw (Iex::MathExc)
  420. {
  421. if ((x == 0) && (y == 0) && (z == 0) && (w == 0))
  422. throw NullVecExc ("Cannot normalize null vector.");
  423. normalizeOrThrow<int>(*this);
  424. return *this;
  425. }
  426. template <>
  427. const Vec4<int> &
  428. Vec4<int>::normalizeNonNull ()
  429. {
  430. normalizeOrThrow<int>(*this);
  431. return *this;
  432. }
  433. template <>
  434. Vec4<int>
  435. Vec4<int>::normalized () const
  436. {
  437. Vec4<int> v(*this);
  438. normalizeOrThrow<int>(v);
  439. return v;
  440. }
  441. template <>
  442. Vec4<int>
  443. Vec4<int>::normalizedExc () const throw (Iex::MathExc)
  444. {
  445. if ((x == 0) && (y == 0) && (z == 0) && (w == 0))
  446. throw NullVecExc ("Cannot normalize null vector.");
  447. Vec4<int> v(*this);
  448. normalizeOrThrow<int>(v);
  449. return v;
  450. }
  451. template <>
  452. Vec4<int>
  453. Vec4<int>::normalizedNonNull () const
  454. {
  455. Vec4<int> v(*this);
  456. normalizeOrThrow<int>(v);
  457. return v;
  458. }
  459. } // namespace Imath