Curve.cpp 37 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346
  1. // Purposely not including Base.h here, or any other gameplay dependencies
  2. // so this class can be reused between gameplay and gameplay-encoder.
  3. #include "Curve.h"
  4. #include "Quaternion.h"
  5. #include <cassert>
  6. #include <cmath>
  7. #include <memory>
  8. using std::memcpy;
  9. using std::fabs;
  10. using std::sqrt;
  11. using std::cos;
  12. using std::sin;
  13. using std::exp;
  14. using std::strcmp;
  15. #ifndef NULL
  16. #define NULL 0
  17. #endif
  18. #ifndef MATH_PI
  19. #define MATH_PI 3.14159265358979323846f
  20. #endif
  21. #ifndef MATH_PIOVER2
  22. #define MATH_PIOVER2 1.57079632679489661923f
  23. #endif
  24. #ifndef MATH_PIX2
  25. #define MATH_PIX2 6.28318530717958647693f
  26. #endif
  27. // Object deletion macro
  28. #ifndef SAFE_DELETE
  29. #define SAFE_DELETE(x) \
  30. if (x) \
  31. { \
  32. delete x; \
  33. x = NULL; \
  34. }
  35. #endif
  36. // Array deletion macro
  37. #ifndef SAFE_DELETE_ARRAY
  38. #define SAFE_DELETE_ARRAY(x) \
  39. if (x) \
  40. { \
  41. delete[] x; \
  42. x = NULL; \
  43. }
  44. #endif
  45. namespace gameplay
  46. {
  47. Curve::Curve(unsigned int pointCount, unsigned int componentCount)
  48. : _pointCount(pointCount), _componentCount(componentCount), _componentSize(sizeof(float)*componentCount), _quaternionOffset(NULL), _points(NULL)
  49. {
  50. _points = new Point[_pointCount];
  51. for (unsigned int i = 0; i < _pointCount; i++)
  52. {
  53. _points[i].time = 0.0f;
  54. _points[i].value = new float[_componentCount];
  55. _points[i].inValue = new float[_componentCount];
  56. _points[i].outValue = new float[_componentCount];
  57. _points[i].type = LINEAR;
  58. }
  59. _points[_pointCount - 1].time = 1.0f;
  60. }
  61. Curve::~Curve()
  62. {
  63. SAFE_DELETE_ARRAY(_points);
  64. SAFE_DELETE_ARRAY(_quaternionOffset);
  65. }
  66. Curve::Point::Point()
  67. : time(0.0f), value(NULL), inValue(NULL), outValue(NULL)
  68. {
  69. }
  70. Curve::Point::~Point()
  71. {
  72. SAFE_DELETE_ARRAY(value);
  73. SAFE_DELETE_ARRAY(inValue);
  74. SAFE_DELETE_ARRAY(outValue);
  75. }
  76. unsigned int Curve::getPointCount() const
  77. {
  78. return _pointCount;
  79. }
  80. unsigned int Curve::getComponentCount() const
  81. {
  82. return _componentCount;
  83. }
  84. float Curve::getStartTime() const
  85. {
  86. return _points[0].time;
  87. }
  88. float Curve::getEndTime() const
  89. {
  90. return _points[_pointCount-1].time;
  91. }
  92. void Curve::setPoint(unsigned int index, float time, float* value, InterpolationType type)
  93. {
  94. setPoint(index, time, value, type, NULL, NULL);
  95. }
  96. void Curve::setPoint(unsigned int index, float time, float* value, InterpolationType type, float* inValue, float* outValue)
  97. {
  98. assert(index < _pointCount && time >= 0.0f && time <= 1.0f && !(index == 0 && time != 0.0f) && !(index == _pointCount - 1 && time != 1.0f));
  99. _points[index].time = time;
  100. _points[index].type = type;
  101. if (value)
  102. memcpy(_points[index].value, value, _componentSize);
  103. if (inValue)
  104. memcpy(_points[index].inValue, inValue, _componentSize);
  105. if (outValue)
  106. memcpy(_points[index].outValue, outValue, _componentSize);
  107. }
  108. void Curve::setTangent(unsigned int index, InterpolationType type, float* inValue, float* outValue)
  109. {
  110. assert(index < _pointCount);
  111. _points[index].type = type;
  112. if (inValue)
  113. memcpy(_points[index].inValue, inValue, _componentSize);
  114. if (outValue)
  115. memcpy(_points[index].outValue, outValue, _componentSize);
  116. }
  117. void Curve::evaluate(float time, float* dst) const
  118. {
  119. assert(dst && time >= 0 && time <= 1.0f);
  120. // Check if we are at or beyond the bounds of the curve.
  121. if (time <= _points[0].time)
  122. {
  123. memcpy(dst, _points[0].value, _componentSize);
  124. return;
  125. }
  126. else if (time >= _points[_pointCount - 1].time)
  127. {
  128. memcpy(dst, _points[_pointCount - 1].value, _componentSize);
  129. return;
  130. }
  131. // Locate the points we are interpolating between using a binary search.
  132. unsigned int index = determineIndex(time);
  133. Point* from = _points + index;
  134. Point* to = _points + (index + 1);
  135. // Calculate the fractional time between the two points.
  136. float scale = (to->time - from->time);
  137. float t = (time - from->time) / scale;
  138. // Calculate the value of the curve discretely if appropriate.
  139. switch (from->type)
  140. {
  141. case BEZIER:
  142. {
  143. interpolateBezier(t, from, to, dst);
  144. return;
  145. }
  146. case BSPLINE:
  147. {
  148. Point* c0;
  149. Point* c1;
  150. if (index == 0)
  151. {
  152. c0 = from;
  153. }
  154. else
  155. {
  156. c0 = (_points + index - 1);
  157. }
  158. if (index == _pointCount - 2)
  159. {
  160. c1 = to;
  161. }
  162. else
  163. {
  164. c1 = (_points + index + 2);
  165. }
  166. interpolateBSpline(t, c0, from, to, c1, dst);
  167. return;
  168. }
  169. case FLAT:
  170. {
  171. interpolateHermiteFlat(t, from, to, dst);
  172. return;
  173. }
  174. case HERMITE:
  175. {
  176. interpolateHermite(t, from, to, dst);
  177. return;
  178. }
  179. case LINEAR:
  180. {
  181. // Can just break here because linear formula follows switch
  182. break;
  183. }
  184. case SMOOTH:
  185. {
  186. interpolateHermiteSmooth(t, index, from, to, dst);
  187. return;
  188. }
  189. case STEP:
  190. {
  191. memcpy(dst, from->value, _componentSize);
  192. return;
  193. }
  194. case QUADRATIC_IN:
  195. {
  196. t *= t;
  197. break;
  198. }
  199. case QUADRATIC_OUT:
  200. {
  201. t *= -(t - 2.0f);
  202. break;
  203. }
  204. case QUADRATIC_IN_OUT:
  205. {
  206. float tx2 = t * 2.0f;
  207. if (tx2 < 1.0f)
  208. t = 0.5f * (tx2 * tx2);
  209. else
  210. {
  211. float temp = tx2 - 1.0f;
  212. t = 0.5f * (-( temp * (temp - 2.0f)) + 1.0f);
  213. }
  214. break;
  215. }
  216. case QUADRATIC_OUT_IN:
  217. {
  218. if (t < 0.5f)
  219. {
  220. t = 2.0f * t * (1.0f - t);
  221. }
  222. else
  223. {
  224. t = 1.0f + 2.0f * t * (t - 1.0f);
  225. }
  226. break;
  227. }
  228. case CUBIC_IN:
  229. {
  230. t *= t * t;
  231. break;
  232. }
  233. case CUBIC_OUT:
  234. {
  235. t--;
  236. t = t * t * t + 1;
  237. break;
  238. }
  239. case CUBIC_IN_OUT:
  240. {
  241. if ((t *= 2.0f) < 1.0f)
  242. {
  243. t = t * t * t * 0.5f;
  244. }
  245. else
  246. {
  247. t -= 2.0f;
  248. t = (t * t * t + 2.0f) * 0.5f;
  249. }
  250. break;
  251. }
  252. case CUBIC_OUT_IN:
  253. {
  254. t = (2.0f * t - 1.0f);
  255. t = (t * t * t + 1) * 0.5f;
  256. break;
  257. }
  258. case QUARTIC_IN:
  259. {
  260. t *= t * t * t;
  261. break;
  262. }
  263. case QUARTIC_OUT:
  264. {
  265. t--;
  266. t = -(t * t * t * t) + 1.0f;
  267. break;
  268. }
  269. case QUARTIC_IN_OUT:
  270. {
  271. t *= 2.0f;
  272. if (t < 1.0f)
  273. {
  274. t = 0.5f * t * t * t * t;
  275. }
  276. else
  277. {
  278. t -= 2.0f;
  279. t = -0.5f * (t * t * t * t - 2.0f);
  280. }
  281. break;
  282. }
  283. case QUARTIC_OUT_IN:
  284. {
  285. t = 2.0f * t - 1.0f;
  286. if (t < 0.0f)
  287. {
  288. t = 0.5f * (-(t * t) * t * t + 1.0f);
  289. }
  290. else
  291. {
  292. t = 0.5f * (t * t * t * t + 1.0f);
  293. }
  294. break;
  295. }
  296. case QUINTIC_IN:
  297. {
  298. t *= t * t * t * t;
  299. break;
  300. }
  301. case QUINTIC_OUT:
  302. {
  303. t--;
  304. t = t * t * t * t * t + 1.0f;
  305. break;
  306. }
  307. case QUINTIC_IN_OUT:
  308. {
  309. t *= 2.0f;
  310. if (t < 1.0f)
  311. {
  312. t = 0.5f * t * t * t * t * t;
  313. }
  314. else
  315. {
  316. t -= 2.0f;
  317. t = 0.5f * (t * t * t * t * t + 2.0f);
  318. }
  319. break;
  320. }
  321. case QUINTIC_OUT_IN:
  322. {
  323. t = 2.0f * t - 1.0f;
  324. t = 0.5f * (t * t * t * t * t + 1.0f);
  325. break;
  326. }
  327. case SINE_IN:
  328. {
  329. t = -(cos(t * MATH_PIOVER2) - 1.0f);
  330. break;
  331. }
  332. case SINE_OUT:
  333. {
  334. t = sin(t * MATH_PIOVER2);
  335. break;
  336. }
  337. case SINE_IN_OUT:
  338. {
  339. t = -0.5f * (cos(MATH_PI * t) - 1.0f);
  340. break;
  341. }
  342. case SINE_OUT_IN:
  343. {
  344. if (t < 0.5f)
  345. {
  346. t = 0.5f * sin(MATH_PI * t);
  347. }
  348. else
  349. {
  350. t = -0.5f * cos(MATH_PIOVER2 * (2.0f * t - 1.0f)) + 1.0f;
  351. }
  352. break;
  353. }
  354. case EXPONENTIAL_IN:
  355. {
  356. if (t != 0.0f)
  357. {
  358. t = exp(10.0f * (t - 1.0f));
  359. }
  360. break;
  361. }
  362. case EXPONENTIAL_OUT:
  363. {
  364. if (t != 1.0f)
  365. {
  366. t = -exp(-10.0f * t) + 1.0f;
  367. }
  368. break;
  369. }
  370. case EXPONENTIAL_IN_OUT:
  371. {
  372. if (t != 0.0f && t != 1.0f)
  373. {
  374. if (t < 0.5f)
  375. {
  376. t = 0.5f * exp(10.0f * (2.0f * t - 1.0f));
  377. }
  378. else
  379. {
  380. t = -0.5f * exp(10.0f * (-2.0f * t + 1.0f)) + 1.0f;
  381. }
  382. }
  383. break;
  384. }
  385. case EXPONENTIAL_OUT_IN:
  386. {
  387. if (t != 0.0f && t != 1.0f)
  388. {
  389. if (t < 0.5f)
  390. {
  391. t = -0.5f * exp(-20.0f * t) + 0.5f;
  392. }
  393. else
  394. {
  395. t = 0.5f * exp(20.0f * (t - 1.0f)) + 0.5f;
  396. }
  397. }
  398. break;
  399. }
  400. case CIRCULAR_IN:
  401. {
  402. t = -(sqrt(1.0f - t * t) - 1.0f);
  403. break;
  404. }
  405. case CIRCULAR_OUT:
  406. {
  407. t--;
  408. t = sqrt(1.0f - t * t);
  409. break;
  410. }
  411. case CIRCULAR_IN_OUT:
  412. {
  413. t *= 2.0f;
  414. if (t < 1.0f)
  415. {
  416. t = 0.5f * (-sqrt((1.0f - t * t)) + 1.0f);
  417. }
  418. else
  419. {
  420. t -= 2.0f;
  421. t = 0.5f * (sqrt((1.0f - t * t)) + 1.0f);
  422. }
  423. break;
  424. }
  425. case CIRCULAR_OUT_IN:
  426. {
  427. t = 2.0f * t - 1.0f;
  428. if (t < 0.0f)
  429. {
  430. t = 0.5f * sqrt(1.0f - t * t);
  431. }
  432. else
  433. {
  434. t = 0.5f * (2.0f - sqrt(1.0f - t * t));
  435. }
  436. break;
  437. }
  438. case ELASTIC_IN:
  439. {
  440. if (t != 0.0f && t != 1.0f)
  441. {
  442. t = t - 1.0f;
  443. t = -1.0f * ( exp(10.0f * t) * sin( (t - 0.075f) * MATH_PIX2 / 0.3f ) );
  444. }
  445. break;
  446. }
  447. case ELASTIC_OUT:
  448. {
  449. if (t != 0.0f && t != 1.0f)
  450. {
  451. t = exp(-10.0f * t) * sin((t - 0.075f) * MATH_PIX2 / 0.3f) + 1.0f;
  452. }
  453. break;
  454. }
  455. case ELASTIC_IN_OUT:
  456. {
  457. if (t != 0.0f && t != 1.0f)
  458. {
  459. t = 2.0f * t - 1.0f;
  460. if (t < 0.0f)
  461. {
  462. t = -0.5f * (exp((10 * t)) * sin(((t - 0.1125f) * MATH_PIX2 / 0.45f)));
  463. }
  464. else
  465. {
  466. t = 0.5f * exp((-10 * t)) * sin(((t - 0.1125f) * MATH_PIX2 / 0.45f)) + 1.0f;
  467. }
  468. }
  469. break;
  470. }
  471. case ELASTIC_OUT_IN:
  472. {
  473. if (t != 0.0f && t != 1.0f)
  474. {
  475. t *= 2.0f;
  476. if (t < 1.0f)
  477. {
  478. t = 0.5f * (exp((-10 * t)) * sin(((t - 0.1125f) * (MATH_PIX2) / 0.45f))) + 0.5f;
  479. }
  480. else
  481. {
  482. t = 0.5f * (exp((10 *(t - 2))) * sin(((t - 0.1125f) * (MATH_PIX2) / 0.45f))) + 0.5f;
  483. }
  484. }
  485. break;
  486. }
  487. case OVERSHOOT_IN:
  488. {
  489. t = t * t * (2.70158f * t - 1.70158f);
  490. break;
  491. }
  492. case OVERSHOOT_OUT:
  493. {
  494. t--;
  495. t = t * t * (2.70158f * t + 1.70158f) + 1;
  496. break;
  497. }
  498. case OVERSHOOT_IN_OUT:
  499. {
  500. t *= 2.0f;
  501. if (t < 1.0f)
  502. {
  503. t = 0.5f * t * t * (3.5949095f * t - 2.5949095f);
  504. }
  505. else
  506. {
  507. t -= 2.0f;
  508. t = 0.5f * (t * t * (3.5949095f * t + 2.5949095f) + 2.0f);
  509. }
  510. break;
  511. }
  512. case OVERSHOOT_OUT_IN:
  513. {
  514. t = 2.0f * t - 1.0f;
  515. if (t < 0.0f)
  516. {
  517. t = 0.5f * (t * t * (3.5949095f * t + 2.5949095f) + 1.0f);
  518. }
  519. else
  520. {
  521. t = 0.5f * (t * t * (3.5949095f * t - 2.5949095f) + 1.0f);
  522. }
  523. break;
  524. }
  525. case BOUNCE_IN:
  526. {
  527. t = 1.0f - t;
  528. if (t < 0.36363636363636365f)
  529. {
  530. t = 7.5625f * t * t;
  531. }
  532. else if (t < 0.7272727272727273f)
  533. {
  534. t -= 0.5454545454545454f;
  535. t = 7.5625f * t * t + 0.75f;
  536. }
  537. else if (t < 0.9090909090909091f)
  538. {
  539. t -= 0.8181818181818182f;
  540. t = 7.5625f * t * t + 0.9375f;
  541. }
  542. else
  543. {
  544. t -= 0.9545454545454546f;
  545. t = 7.5625f * t * t + 0.984375f;
  546. }
  547. t = 1.0f - t;
  548. break;
  549. }
  550. case BOUNCE_OUT:
  551. {
  552. if (t < 0.36363636363636365f)
  553. {
  554. t = 7.5625f * t * t;
  555. }
  556. else if (t < 0.7272727272727273f)
  557. {
  558. t -= 0.5454545454545454f;
  559. t = 7.5625f * t * t + 0.75f;
  560. }
  561. else if (t < 0.9090909090909091f)
  562. {
  563. t -= 0.8181818181818182f;
  564. t = 7.5625f * t * t + 0.9375f;
  565. }
  566. else
  567. {
  568. t -= 0.9545454545454546f;
  569. t = 7.5625f * t * t + 0.984375f;
  570. }
  571. break;
  572. }
  573. case BOUNCE_IN_OUT:
  574. {
  575. if (t < 0.5f)
  576. {
  577. t = 1.0f - t * 2.0f;
  578. if (t < 0.36363636363636365f)
  579. {
  580. t = 7.5625f * t * t;
  581. }
  582. else if (t < 0.7272727272727273f)
  583. {
  584. t -= 0.5454545454545454f;
  585. t = 7.5625f * t * t + 0.75f;
  586. }
  587. else if (t < 0.9090909090909091f)
  588. {
  589. t -= 0.8181818181818182f;
  590. t = 7.5625f * t * t + 0.9375f;
  591. }
  592. else
  593. {
  594. t -= 0.9545454545454546f;
  595. t = 7.5625f * t * t + 0.984375f;
  596. }
  597. t = (1.0f - t) * 0.5f;
  598. }
  599. else
  600. {
  601. t = t * 2.0f - 1.0f;
  602. if (t < 0.36363636363636365f)
  603. {
  604. t = 7.5625f * t * t;
  605. }
  606. else if (t < 0.7272727272727273f)
  607. {
  608. t -= 0.5454545454545454f;
  609. t = 7.5625f * t * t + 0.75f;
  610. }
  611. else if (t < 0.9090909090909091f)
  612. {
  613. t -= 0.8181818181818182f;
  614. t = 7.5625f * t * t + 0.9375f;
  615. }
  616. else
  617. {
  618. t -= 0.9545454545454546f;
  619. t = 7.5625f * t * t + 0.984375f;
  620. }
  621. t = 0.5f * t + 0.5f;
  622. }
  623. break;
  624. }
  625. case BOUNCE_OUT_IN:
  626. {
  627. if (t < 0.1818181818f)
  628. {
  629. t = 15.125f * t * t;
  630. }
  631. else if (t < 0.3636363636f)
  632. {
  633. t = 1.5f + (-8.250000001f + 15.125f * t) * t;
  634. }
  635. else if (t < 0.4545454546f)
  636. {
  637. t = 3.0f + (-12.375f + 15.125f * t) * t;
  638. }
  639. else if (t < 0.5f)
  640. {
  641. t = 3.9375f + (-14.4375f + 15.125f * t) * t;
  642. }
  643. else if (t <= 0.5454545455f)
  644. {
  645. t = -3.625000004f + (15.81250001f - 15.125f * t) * t;
  646. }
  647. else if (t <= 0.6363636365f)
  648. {
  649. t = -4.75f + (17.875f - 15.125f * t) * t;
  650. }
  651. else if (t <= 0.8181818180f)
  652. {
  653. t = -7.374999995f + (21.99999999f - 15.125f * t) * t;
  654. }
  655. else
  656. {
  657. t = -14.125f + (30.25f - 15.125f * t) * t;
  658. }
  659. break;
  660. }
  661. }
  662. interpolateLinear(t, from, to, dst);
  663. }
  664. float Curve::lerp(float t, float from, float to)
  665. {
  666. return lerpInl(t, from, to);
  667. }
  668. void Curve::setQuaternionOffset(unsigned int offset)
  669. {
  670. assert(offset <= (_componentCount - 4));
  671. if (!_quaternionOffset)
  672. _quaternionOffset = new unsigned int[1];
  673. *_quaternionOffset = offset;
  674. }
  675. void Curve::interpolateBezier(float s, Point* from, Point* to, float* dst) const
  676. {
  677. float s_2 = s * s;
  678. float eq0 = 1 - s;
  679. float eq0_2 = eq0 * eq0;
  680. float eq1 = eq0_2 * eq0;
  681. float eq2 = 3 * s * eq0_2;
  682. float eq3 = 3 * s_2 * eq0;
  683. float eq4 = s_2 * s;
  684. float* fromValue = from->value;
  685. float* toValue = to->value;
  686. float* outValue = from->outValue;
  687. float* inValue = to->inValue;
  688. if (!_quaternionOffset)
  689. {
  690. for (unsigned int i = 0; i < _componentCount; i++)
  691. {
  692. if (fromValue[i] == toValue[i])
  693. dst[i] = fromValue[i];
  694. else
  695. dst[i] = bezier(eq1, eq2, eq3, eq4, fromValue[i], outValue[i], toValue[i], inValue[i]);
  696. }
  697. }
  698. else
  699. {
  700. // Interpolate any values up to the quaternion offset as scalars.
  701. unsigned int quaternionOffset = *_quaternionOffset;
  702. unsigned int i = 0;
  703. for (i = 0; i < quaternionOffset; i++)
  704. {
  705. if (fromValue[i] == toValue[i])
  706. dst[i] = fromValue[i];
  707. else
  708. dst[i] = bezier(eq1, eq2, eq3, eq4, fromValue[i], outValue[i], toValue[i], inValue[i]);
  709. }
  710. // Handle quaternion component.
  711. float interpTime = bezier(eq1, eq2, eq3, eq4, from->time, outValue[i], to->time, inValue[i]);
  712. interpolateQuaternion(interpTime, (fromValue + i), (toValue + i), (dst + i));
  713. // Handle remaining components (if any) as scalars
  714. for (i += 4; i < _componentCount; i++)
  715. {
  716. if (fromValue[i] == toValue[i])
  717. dst[i] = fromValue[i];
  718. else
  719. dst[i] = bezier(eq1, eq2, eq3, eq4, fromValue[i], outValue[i], toValue[i], inValue[i]);
  720. }
  721. }
  722. }
  723. void Curve::interpolateBSpline(float s, Point* c0, Point* c1, Point* c2, Point* c3, float* dst) const
  724. {
  725. float s_2 = s * s;
  726. float s_3 = s_2 * s;
  727. float eq0 = (-s_3 + 3 * s_2 - 3 * s + 1) / 6.0f;
  728. float eq1 = (3 * s_3 - 6 * s_2 + 4) / 6.0f;
  729. float eq2 = (-3 * s_3 + 3 * s_2 + 3 * s + 1) / 6.0f;
  730. float eq3 = s_3 / 6.0f;
  731. float* c0Value = c0->value;
  732. float* c1Value = c1->value;
  733. float* c2Value = c2->value;
  734. float* c3Value = c3->value;
  735. if (!_quaternionOffset)
  736. {
  737. for (unsigned int i = 0; i < _componentCount; i++)
  738. {
  739. if (c1Value[i] == c2Value[i])
  740. dst[i] = c1Value[i];
  741. else
  742. dst[i] = bspline(eq0, eq1, eq2, eq3, c0Value[i], c1Value[i], c2Value[i], c3Value[i]);
  743. }
  744. }
  745. else
  746. {
  747. // Interpolate any values up to the quaternion offset as scalars.
  748. unsigned int quaternionOffset = *_quaternionOffset;
  749. unsigned int i = 0;
  750. for (i = 0; i < quaternionOffset; i++)
  751. {
  752. if (c1Value[i] == c2Value[i])
  753. dst[i] = c1Value[i];
  754. else
  755. dst[i] = bspline(eq0, eq1, eq2, eq3, c0Value[i], c1Value[i], c2Value[i], c3Value[i]);
  756. }
  757. // Handle quaternion component.
  758. float interpTime;
  759. if (c0->time == c1->time)
  760. interpTime = bspline(eq0, eq1, eq2, eq3, -c0->time, c1->time, c2->time, c3->time);
  761. else if (c2->time == c3->time)
  762. interpTime = bspline(eq0, eq1, eq2, eq3, c0->time, c1->time, c2->time, -c3->time);
  763. else
  764. interpTime = bspline(eq0, eq1, eq2, eq3, c0->time, c1->time, c2->time, c3->time);
  765. interpolateQuaternion(s, (c1Value + i) , (c2Value + i), (dst + i));
  766. // Handle remaining components (if any) as scalars
  767. for (i += 4; i < _componentCount; i++)
  768. {
  769. if (c1Value[i] == c2Value[i])
  770. dst[i] = c1Value[i];
  771. else
  772. dst[i] = bspline(eq0, eq1, eq2, eq3, c0Value[i], c1Value[i], c2Value[i], c3Value[i]);
  773. }
  774. }
  775. }
  776. void Curve::interpolateHermite(float s, Point* from, Point* to, float* dst) const
  777. {
  778. // Calculate the hermite basis functions.
  779. float s_2 = s * s; // t^2
  780. float s_3 = s_2 * s; // t^3
  781. float h00 = 2 * s_3 - 3 * s_2 + 1; // basis function 0
  782. float h01 = -2 * s_3 + 3 * s_2; // basis function 1
  783. float h10 = s_3 - 2 * s_2 + s; // basis function 2
  784. float h11 = s_3 - s_2; // basis function 3
  785. float* fromValue = from->value;
  786. float* toValue = to->value;
  787. float* outValue = from->outValue;
  788. float* inValue = to->inValue;
  789. if (!_quaternionOffset)
  790. {
  791. for (unsigned int i = 0; i < _componentCount; i++)
  792. {
  793. if (fromValue[i] == toValue[i])
  794. dst[i] = fromValue[i];
  795. else
  796. dst[i] = hermite(h00, h01, h10, h11, fromValue[i], outValue[i], toValue[i], inValue[i]);
  797. }
  798. }
  799. else
  800. {
  801. // Interpolate any values up to the quaternion offset as scalars.
  802. unsigned int quaternionOffset = *_quaternionOffset;
  803. unsigned int i = 0;
  804. for (i = 0; i < quaternionOffset; i++)
  805. {
  806. if (fromValue[i] == toValue[i])
  807. dst[i] = fromValue[i];
  808. else
  809. dst[i] = hermite(h00, h01, h10, h11, fromValue[i], outValue[i], toValue[i], inValue[i]);
  810. }
  811. // Handle quaternion component.
  812. float interpTime = hermite(h00, h01, h10, h11, from->time, outValue[i], to->time, inValue[i]);
  813. interpolateQuaternion(interpTime, (fromValue + i), (toValue + i), (dst + i));
  814. // Handle remaining components (if any) as scalars
  815. for (i += 4; i < _componentCount; i++)
  816. {
  817. if (fromValue[i] == toValue[i])
  818. dst[i] = fromValue[i];
  819. else
  820. dst[i] = hermite(h00, h01, h10, h11, fromValue[i], outValue[i], toValue[i], inValue[i]);
  821. }
  822. }
  823. }
  824. void Curve::interpolateHermiteFlat(float s, Point* from, Point* to, float* dst) const
  825. {
  826. // Calculate the hermite basis functions.
  827. float s_2 = s * s; // t^2
  828. float s_3 = s_2 * s; // t^3
  829. float h00 = 2 * s_3 - 3 * s_2 + 1; // basis function 0
  830. float h01 = -2 * s_3 + 3 * s_2; // basis function 1
  831. float* fromValue = from->value;
  832. float* toValue = to->value;
  833. if (!_quaternionOffset)
  834. {
  835. for (unsigned int i = 0; i < _componentCount; i++)
  836. {
  837. if (fromValue[i] == toValue[i])
  838. dst[i] = fromValue[i];
  839. else
  840. dst[i] = hermiteFlat(h00, h01, fromValue[i], toValue[i]);
  841. }
  842. }
  843. else
  844. {
  845. // Interpolate any values up to the quaternion offset as scalars.
  846. unsigned int quaternionOffset = *_quaternionOffset;
  847. unsigned int i = 0;
  848. for (i = 0; i < quaternionOffset; i++)
  849. {
  850. if (fromValue[i] == toValue[i])
  851. dst[i] = fromValue[i];
  852. else
  853. dst[i] = hermiteFlat(h00, h01, fromValue[i], toValue[i]);
  854. }
  855. // Handle quaternion component.
  856. float interpTime = hermiteFlat(h00, h01, from->time, to->time);
  857. interpolateQuaternion(interpTime, (fromValue + i), (toValue + i), (dst + i));
  858. // Handle remaining components (if any) as scalars
  859. for (i += 4; i < _componentCount; i++)
  860. {
  861. if (fromValue[i] == toValue[i])
  862. dst[i] = fromValue[i];
  863. else
  864. dst[i] = hermiteFlat(h00, h01, fromValue[i], toValue[i]);
  865. }
  866. }
  867. }
  868. void Curve::interpolateHermiteSmooth(float s, unsigned int index, Point* from, Point* to, float* dst) const
  869. {
  870. // Calculate the hermite basis functions.
  871. float s_2 = s * s; // t^2
  872. float s_3 = s_2 * s; // t^3
  873. float h00 = 2 * s_3 - 3 * s_2 + 1; // basis function 0
  874. float h01 = -2 * s_3 + 3 * s_2; // basis function 1
  875. float h10 = s_3 - 2 * s_2 + s; // basis function 2
  876. float h11 = s_3 - s_2; // basis function 3
  877. float inValue;
  878. float outValue;
  879. float* fromValue = from->value;
  880. float* toValue = to->value;
  881. if (!_quaternionOffset)
  882. {
  883. for (unsigned int i = 0; i < _componentCount; i++)
  884. {
  885. if (fromValue[i] == toValue[i])
  886. {
  887. dst[i] = fromValue[i];
  888. }
  889. else
  890. {
  891. if (index == 0)
  892. {
  893. outValue = toValue[i] - fromValue[i];
  894. }
  895. else
  896. {
  897. outValue = (toValue[i] - (from - 1)->value[i]) * ((from->time - (from - 1)->time) / (to->time - (from - 1)->time));
  898. }
  899. if (index == _pointCount - 2)
  900. {
  901. inValue = toValue[i] - fromValue[i];
  902. }
  903. else
  904. {
  905. inValue = ((to + 1)->value[i] - fromValue[i]) * ((to->time - from->time) / ((to + 1)->time - from->time));
  906. }
  907. dst[i] = hermiteSmooth(h00, h01, h10, h11, fromValue[i], outValue, toValue[i], inValue);
  908. }
  909. }
  910. }
  911. else
  912. {
  913. // Interpolate any values up to the quaternion offset as scalars.
  914. unsigned int quaternionOffset = *_quaternionOffset;
  915. unsigned int i = 0;
  916. for (i = 0; i < quaternionOffset; i++)
  917. {
  918. if (fromValue[i] == toValue[i])
  919. {
  920. dst[i] = fromValue[i];
  921. }
  922. else
  923. {
  924. if (index == 0)
  925. {
  926. outValue = toValue[i] - fromValue[i];
  927. }
  928. else
  929. {
  930. outValue = (toValue[i] - (from - 1)->value[i]) * ((from->time - (from - 1)->time) / (to->time - (from - 1)->time));
  931. }
  932. if (index == _pointCount - 2)
  933. {
  934. inValue = toValue[i] - fromValue[i];
  935. }
  936. else
  937. {
  938. inValue = ((to + 1)->value[i] - fromValue[i]) * ((to->time - from->time) / ((to + 1)->time - from->time));
  939. }
  940. dst[i] = hermiteSmooth(h00, h01, h10, h11, fromValue[i], outValue, toValue[i], inValue);
  941. }
  942. }
  943. // Handle quaternion component.
  944. if (index == 0)
  945. {
  946. outValue = to->time - from->time;
  947. }
  948. else
  949. {
  950. outValue = (to->time - (from - 1)->time) * ((from->time - (from - 1)->time) / (to->time - (from - 1)->time));
  951. }
  952. if (index == _pointCount - 2)
  953. {
  954. inValue = to->time - from->time;
  955. }
  956. else
  957. {
  958. inValue = ((to + 1)->time - from->time) * ((to->time - from->time) / ((to + 1)->time - from->time));
  959. }
  960. float interpTime = hermiteSmooth(h00, h01, h10, h11, from->time, outValue, to->time, inValue);
  961. interpolateQuaternion(interpTime, (fromValue + i), (toValue + i), (dst + i));
  962. // Handle remaining components (if any) as scalars
  963. for (i += 4; i < _componentCount; i++)
  964. {
  965. if (fromValue[i] == toValue[i])
  966. {
  967. dst[i] = fromValue[i];
  968. }
  969. else
  970. {
  971. // Interpolate as scalar.
  972. if (index == 0)
  973. {
  974. outValue = toValue[i] - fromValue[i];
  975. }
  976. else
  977. {
  978. outValue = (toValue[i] - (from - 1)->value[i]) * ((from->time - (from - 1)->time) / (to->time - (from - 1)->time));
  979. }
  980. if (index == _pointCount - 2)
  981. {
  982. inValue = toValue[i] - fromValue[i];
  983. }
  984. else
  985. {
  986. inValue = ((to + 1)->value[i] - fromValue[i]) * ((to->time - from->time) / ((to + 1)->time - from->time));
  987. }
  988. dst[i] = hermiteSmooth(h00, h01, h10, h11, fromValue[i], outValue, toValue[i], inValue);
  989. }
  990. }
  991. }
  992. }
  993. void Curve::interpolateLinear(float s, Point* from, Point* to, float* dst) const
  994. {
  995. float* fromValue = from->value;
  996. float* toValue = to->value;
  997. if (!_quaternionOffset)
  998. {
  999. for (unsigned int i = 0; i < _componentCount; i++)
  1000. {
  1001. if (fromValue[i] == toValue[i])
  1002. dst[i] = fromValue[i];
  1003. else
  1004. dst[i] = lerpInl(s, fromValue[i], toValue[i]);
  1005. }
  1006. }
  1007. else
  1008. {
  1009. // Interpolate any values up to the quaternion offset as scalars.
  1010. unsigned int quaternionOffset = *_quaternionOffset;
  1011. unsigned int i = 0;
  1012. for (i = 0; i < quaternionOffset; i++)
  1013. {
  1014. if (fromValue[i] == toValue[i])
  1015. dst[i] = fromValue[i];
  1016. else
  1017. dst[i] = lerpInl(s, fromValue[i], toValue[i]);
  1018. }
  1019. // Handle quaternion component.
  1020. interpolateQuaternion(s, (fromValue + i), (toValue + i), (dst + i));
  1021. // handle any remaining components as scalars
  1022. for (i += 4; i < _componentCount; i++)
  1023. {
  1024. if (fromValue[i] == toValue[i])
  1025. dst[i] = fromValue[i];
  1026. else
  1027. dst[i] = lerpInl(s, fromValue[i], toValue[i]);
  1028. }
  1029. }
  1030. }
  1031. void Curve::interpolateQuaternion(float s, float* from, float* to, float* dst) const
  1032. {
  1033. // Evaluate.
  1034. if (s >= 0)
  1035. {
  1036. Quaternion::slerp(from[0], from[1], from[2], from[3], to[0], to[1], to[2], to[3], s, dst, dst + 1, dst + 2, dst + 3);
  1037. }
  1038. else
  1039. Quaternion::slerp(to[0], to[1], to[2], to[3], from[0], from[1], from[2], from[3], s, dst, dst + 1, dst + 2, dst + 3);
  1040. //((Quaternion*) dst)->normalize();
  1041. }
  1042. int Curve::determineIndex(float time) const
  1043. {
  1044. unsigned int min = 0;
  1045. unsigned int max = _pointCount - 1;
  1046. unsigned int mid = 0;
  1047. // Do a binary search to determine the index.
  1048. do
  1049. {
  1050. mid = (min + max) >> 1;
  1051. if (time >= _points[mid].time && time <= _points[mid + 1].time)
  1052. return mid;
  1053. else if (time < _points[mid].time)
  1054. max = mid - 1;
  1055. else
  1056. min = mid + 1;
  1057. } while (min <= max);
  1058. // We should never hit this!
  1059. return -1;
  1060. }
  1061. int Curve::getInterpolationType(const char* curveId)
  1062. {
  1063. if (strcmp(curveId, "BEZIER") == 0)
  1064. {
  1065. return Curve::BEZIER;
  1066. }
  1067. else if (strcmp(curveId, "BSPLINE") == 0)
  1068. {
  1069. return Curve::BSPLINE;
  1070. }
  1071. else if (strcmp(curveId, "FLAT") == 0)
  1072. {
  1073. return Curve::FLAT;
  1074. }
  1075. else if (strcmp(curveId, "HERMITE") == 0)
  1076. {
  1077. return Curve::HERMITE;
  1078. }
  1079. else if (strcmp(curveId, "LINEAR") == 0)
  1080. {
  1081. return Curve::LINEAR;
  1082. }
  1083. else if (strcmp(curveId, "SMOOTH") == 0)
  1084. {
  1085. return Curve::SMOOTH;
  1086. }
  1087. else if (strcmp(curveId, "STEP") == 0)
  1088. {
  1089. return Curve::STEP;
  1090. }
  1091. else if (strcmp(curveId, "QUADRATIC_IN") == 0)
  1092. {
  1093. return Curve::QUADRATIC_IN;
  1094. }
  1095. else if (strcmp(curveId, "QUADRATIC_OUT") == 0)
  1096. {
  1097. return Curve::QUADRATIC_OUT;
  1098. }
  1099. else if (strcmp(curveId, "QUADRATIC_IN_OUT") == 0)
  1100. {
  1101. return Curve::QUADRATIC_IN_OUT;
  1102. }
  1103. else if (strcmp(curveId, "QUADRATIC_OUT_IN") == 0)
  1104. {
  1105. return Curve::QUADRATIC_OUT_IN;
  1106. }
  1107. else if (strcmp(curveId, "CUBIC_IN") == 0)
  1108. {
  1109. return Curve::CUBIC_IN;
  1110. }
  1111. else if (strcmp(curveId, "CUBIC_OUT") == 0)
  1112. {
  1113. return Curve::CUBIC_OUT;
  1114. }
  1115. else if (strcmp(curveId, "CUBIC_IN_OUT") == 0)
  1116. {
  1117. return Curve::CUBIC_IN_OUT;
  1118. }
  1119. else if (strcmp(curveId, "CUBIC_OUT_IN") == 0)
  1120. {
  1121. return Curve::CUBIC_OUT_IN;
  1122. }
  1123. else if (strcmp(curveId, "QUARTIC_IN") == 0)
  1124. {
  1125. return Curve::QUARTIC_IN;
  1126. }
  1127. else if (strcmp(curveId, "QUARTIC_OUT") == 0)
  1128. {
  1129. return Curve::QUARTIC_OUT;
  1130. }
  1131. else if (strcmp(curveId, "QUARTIC_IN_OUT") == 0)
  1132. {
  1133. return Curve::QUARTIC_IN_OUT;
  1134. }
  1135. else if (strcmp(curveId, "QUARTIC_OUT_IN") == 0)
  1136. {
  1137. return Curve::QUARTIC_OUT_IN;
  1138. }
  1139. else if (strcmp(curveId, "QUINTIC_IN") == 0)
  1140. {
  1141. return Curve::QUINTIC_IN;
  1142. }
  1143. else if (strcmp(curveId, "QUINTIC_OUT") == 0)
  1144. {
  1145. return Curve::QUINTIC_OUT;
  1146. }
  1147. else if (strcmp(curveId, "QUINTIC_IN_OUT") == 0)
  1148. {
  1149. return Curve::QUINTIC_IN_OUT;
  1150. }
  1151. else if (strcmp(curveId, "QUINTIC_OUT_IN") == 0)
  1152. {
  1153. return Curve::QUINTIC_OUT_IN;
  1154. }
  1155. else if (strcmp(curveId, "SINE_IN") == 0)
  1156. {
  1157. return Curve::SINE_IN;
  1158. }
  1159. else if (strcmp(curveId, "SINE_OUT") == 0)
  1160. {
  1161. return Curve::SINE_OUT;
  1162. }
  1163. else if (strcmp(curveId, "SINE_IN_OUT") == 0)
  1164. {
  1165. return Curve::SINE_IN_OUT;
  1166. }
  1167. else if (strcmp(curveId, "SINE_OUT_IN") == 0)
  1168. {
  1169. return Curve::SINE_OUT_IN;
  1170. }
  1171. else if (strcmp(curveId, "EXPONENTIAL_IN") == 0)
  1172. {
  1173. return Curve::EXPONENTIAL_IN;
  1174. }
  1175. else if (strcmp(curveId, "EXPONENTIAL_OUT") == 0)
  1176. {
  1177. return Curve::EXPONENTIAL_OUT;
  1178. }
  1179. else if (strcmp(curveId, "EXPONENTIAL_IN_OUT") == 0)
  1180. {
  1181. return Curve::EXPONENTIAL_IN_OUT;
  1182. }
  1183. else if (strcmp(curveId, "EXPONENTIAL_OUT_IN") == 0)
  1184. {
  1185. return Curve::EXPONENTIAL_OUT_IN;
  1186. }
  1187. else if (strcmp(curveId, "CIRCULAR_IN") == 0)
  1188. {
  1189. return Curve::CIRCULAR_IN;
  1190. }
  1191. else if (strcmp(curveId, "CIRCULAR_OUT") == 0)
  1192. {
  1193. return Curve::CIRCULAR_OUT;
  1194. }
  1195. else if (strcmp(curveId, "CIRCULAR_IN_OUT") == 0)
  1196. {
  1197. return Curve::CIRCULAR_IN_OUT;
  1198. }
  1199. else if (strcmp(curveId, "CIRCULAR_OUT_IN") == 0)
  1200. {
  1201. return Curve::CIRCULAR_OUT_IN;
  1202. }
  1203. else if (strcmp(curveId, "ELASTIC_IN") == 0)
  1204. {
  1205. return Curve::ELASTIC_IN;
  1206. }
  1207. else if (strcmp(curveId, "ELASTIC_OUT") == 0)
  1208. {
  1209. return Curve::ELASTIC_OUT;
  1210. }
  1211. else if (strcmp(curveId, "ELASTIC_IN_OUT") == 0)
  1212. {
  1213. return Curve::ELASTIC_IN_OUT;
  1214. }
  1215. else if (strcmp(curveId, "ELASTIC_OUT_IN") == 0)
  1216. {
  1217. return Curve::ELASTIC_OUT_IN;
  1218. }
  1219. else if (strcmp(curveId, "OVERSHOOT_IN") == 0)
  1220. {
  1221. return Curve::OVERSHOOT_IN;
  1222. }
  1223. else if (strcmp(curveId, "OVERSHOOT_OUT") == 0)
  1224. {
  1225. return Curve::OVERSHOOT_OUT;
  1226. }
  1227. else if (strcmp(curveId, "OVERSHOOT_IN_OUT") == 0)
  1228. {
  1229. return Curve::OVERSHOOT_IN_OUT;
  1230. }
  1231. else if (strcmp(curveId, "OVERSHOOT_OUT_IN") == 0)
  1232. {
  1233. return Curve::OVERSHOOT_OUT_IN;
  1234. }
  1235. else if (strcmp(curveId, "BOUNCE_IN") == 0)
  1236. {
  1237. return Curve::BOUNCE_IN;
  1238. }
  1239. else if (strcmp(curveId, "BOUNCE_OUT") == 0)
  1240. {
  1241. return Curve::BOUNCE_OUT;
  1242. }
  1243. else if (strcmp(curveId, "BOUNCE_IN_OUT") == 0)
  1244. {
  1245. return Curve::BOUNCE_IN_OUT;
  1246. }
  1247. else if (strcmp(curveId, "BOUNCE_OUT_IN") == 0)
  1248. {
  1249. return Curve::BOUNCE_OUT_IN;
  1250. }
  1251. return -1;
  1252. }
  1253. }