convex_hull.cpp 58 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724172517261727172817291730173117321733173417351736173717381739174017411742174317441745174617471748174917501751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784178517861787178817891790179117921793179417951796179717981799180018011802180318041805180618071808180918101811181218131814181518161817181818191820182118221823182418251826182718281829183018311832183318341835183618371838183918401841184218431844184518461847184818491850185118521853185418551856185718581859186018611862186318641865186618671868186918701871187218731874187518761877187818791880188118821883188418851886188718881889189018911892189318941895189618971898189919001901190219031904190519061907190819091910191119121913191419151916191719181919192019211922192319241925192619271928192919301931193219331934193519361937193819391940194119421943194419451946194719481949195019511952195319541955195619571958195919601961196219631964196519661967196819691970197119721973197419751976197719781979198019811982198319841985198619871988198919901991199219931994199519961997199819992000200120022003200420052006200720082009201020112012201320142015201620172018201920202021202220232024202520262027202820292030203120322033203420352036203720382039204020412042204320442045204620472048204920502051205220532054205520562057205820592060206120622063206420652066206720682069207020712072207320742075207620772078207920802081208220832084208520862087208820892090209120922093209420952096209720982099210021012102210321042105210621072108210921102111211221132114211521162117211821192120212121222123212421252126212721282129213021312132213321342135213621372138213921402141214221432144214521462147214821492150215121522153215421552156215721582159216021612162216321642165216621672168216921702171217221732174217521762177217821792180218121822183218421852186218721882189219021912192219321942195219621972198219922002201220222032204220522062207220822092210221122122213221422152216221722182219222022212222222322242225222622272228222922302231223222332234223522362237223822392240224122422243224422452246224722482249225022512252225322542255225622572258225922602261226222632264226522662267226822692270227122722273227422752276227722782279228022812282228322842285228622872288228922902291229222932294229522962297229822992300230123022303230423052306230723082309
  1. /*************************************************************************/
  2. /* convex_hull.cpp */
  3. /*************************************************************************/
  4. /* This file is part of: */
  5. /* GODOT ENGINE */
  6. /* https://godotengine.org */
  7. /*************************************************************************/
  8. /* Copyright (c) 2007-2021 Juan Linietsky, Ariel Manzur. */
  9. /* Copyright (c) 2014-2021 Godot Engine contributors (cf. AUTHORS.md). */
  10. /* */
  11. /* Permission is hereby granted, free of charge, to any person obtaining */
  12. /* a copy of this software and associated documentation files (the */
  13. /* "Software"), to deal in the Software without restriction, including */
  14. /* without limitation the rights to use, copy, modify, merge, publish, */
  15. /* distribute, sublicense, and/or sell copies of the Software, and to */
  16. /* permit persons to whom the Software is furnished to do so, subject to */
  17. /* the following conditions: */
  18. /* */
  19. /* The above copyright notice and this permission notice shall be */
  20. /* included in all copies or substantial portions of the Software. */
  21. /* */
  22. /* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */
  23. /* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */
  24. /* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/
  25. /* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */
  26. /* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */
  27. /* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */
  28. /* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
  29. /*************************************************************************/
  30. /*
  31. * Based on Godot's patched VHACD-version of Bullet's btConvexHullComputer.
  32. * See /thirdparty/vhacd/btConvexHullComputer.cpp at 64403ddcab9f1dca2408f0a412a22d899708bbb1
  33. * In turn, based on /src/LinearMath/btConvexHullComputer.cpp in <https://github.com/bulletphysics/bullet3>
  34. * at 73b217fb07e7e3ce126caeb28ab3c9ddd0718467
  35. *
  36. * Changes:
  37. * - int32_t is consistently used instead of int in some cases
  38. * - integrated patch db0d6c92927f5a1358b887f2645c11f3014f0e8a from Bullet (CWE-190 integer overflow in btConvexHullComputer)
  39. * - adapted to Godot's code style
  40. * - replaced Bullet's types (e.g. vectors) with Godot's
  41. * - replaced custom Pool implementation with PagedAllocator
  42. */
  43. /*
  44. Copyright (c) 2011 Ole Kniemeyer, MAXON, www.maxon.net
  45. This software is provided 'as-is', without any express or implied warranty.
  46. In no event will the authors be held liable for any damages arising from the use of this software.
  47. Permission is granted to anyone to use this software for any purpose,
  48. including commercial applications, and to alter it and redistribute it freely,
  49. subject to the following restrictions:
  50. 1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
  51. 2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
  52. 3. This notice may not be removed or altered from any source distribution.
  53. */
  54. #include "convex_hull.h"
  55. #include "core/error_macros.h"
  56. #include "core/math/aabb.h"
  57. #include "core/math/math_defs.h"
  58. #include "core/os/memory.h"
  59. #include "core/paged_allocator.h"
  60. #include <string.h>
  61. //#define DEBUG_CONVEX_HULL
  62. //#define SHOW_ITERATIONS
  63. // -- GODOT start --
  64. // Assembly optimizations are not used at the moment.
  65. //#define USE_X86_64_ASM
  66. // -- GODOT end --
  67. #ifdef DEBUG_ENABLED
  68. #define CHULL_ASSERT(m_cond) \
  69. if (unlikely(!(m_cond))) { \
  70. ERR_PRINT("Assertion \"" _STR(m_cond) "\" failed."); \
  71. } else \
  72. ((void)0)
  73. #else
  74. #define CHULL_ASSERT(m_cond) \
  75. do { \
  76. } while (false)
  77. #endif
  78. #if defined(DEBUG_CONVEX_HULL) || defined(SHOW_ITERATIONS)
  79. #include <stdio.h>
  80. #endif
  81. // Convex hull implementation based on Preparata and Hong
  82. // Ole Kniemeyer, MAXON Computer GmbH
  83. class ConvexHullInternal {
  84. public:
  85. class Point64 {
  86. public:
  87. int64_t x;
  88. int64_t y;
  89. int64_t z;
  90. Point64(int64_t p_x, int64_t p_y, int64_t p_z) {
  91. x = p_x;
  92. y = p_y;
  93. z = p_z;
  94. }
  95. bool is_zero() {
  96. return (x == 0) && (y == 0) && (z == 0);
  97. }
  98. int64_t dot(const Point64 &b) const {
  99. return x * b.x + y * b.y + z * b.z;
  100. }
  101. };
  102. class Point32 {
  103. public:
  104. int32_t x = 0;
  105. int32_t y = 0;
  106. int32_t z = 0;
  107. int32_t index = -1;
  108. Point32() {
  109. }
  110. Point32(int32_t p_x, int32_t p_y, int32_t p_z) {
  111. x = p_x;
  112. y = p_y;
  113. z = p_z;
  114. }
  115. bool operator==(const Point32 &b) const {
  116. return (x == b.x) && (y == b.y) && (z == b.z);
  117. }
  118. bool operator!=(const Point32 &b) const {
  119. return (x != b.x) || (y != b.y) || (z != b.z);
  120. }
  121. bool is_zero() {
  122. return (x == 0) && (y == 0) && (z == 0);
  123. }
  124. Point64 cross(const Point32 &b) const {
  125. return Point64((int64_t)y * b.z - (int64_t)z * b.y, (int64_t)z * b.x - (int64_t)x * b.z, (int64_t)x * b.y - (int64_t)y * b.x);
  126. }
  127. Point64 cross(const Point64 &b) const {
  128. return Point64(y * b.z - z * b.y, z * b.x - x * b.z, x * b.y - y * b.x);
  129. }
  130. int64_t dot(const Point32 &b) const {
  131. return (int64_t)x * b.x + (int64_t)y * b.y + (int64_t)z * b.z;
  132. }
  133. int64_t dot(const Point64 &b) const {
  134. return x * b.x + y * b.y + z * b.z;
  135. }
  136. Point32 operator+(const Point32 &b) const {
  137. return Point32(x + b.x, y + b.y, z + b.z);
  138. }
  139. Point32 operator-(const Point32 &b) const {
  140. return Point32(x - b.x, y - b.y, z - b.z);
  141. }
  142. };
  143. class Int128 {
  144. public:
  145. uint64_t low = 0;
  146. uint64_t high = 0;
  147. Int128() {
  148. }
  149. Int128(uint64_t p_low, uint64_t p_high) {
  150. low = p_low;
  151. high = p_high;
  152. }
  153. Int128(uint64_t p_low) {
  154. low = p_low;
  155. high = 0;
  156. }
  157. Int128(int64_t p_value) {
  158. low = p_value;
  159. if (p_value >= 0) {
  160. high = 0;
  161. } else {
  162. high = (uint64_t)-1LL;
  163. }
  164. }
  165. static Int128 mul(int64_t a, int64_t b);
  166. static Int128 mul(uint64_t a, uint64_t b);
  167. Int128 operator-() const {
  168. return Int128((uint64_t) - (int64_t)low, ~high + (low == 0));
  169. }
  170. Int128 operator+(const Int128 &b) const {
  171. #ifdef USE_X86_64_ASM
  172. Int128 result;
  173. __asm__("addq %[bl], %[rl]\n\t"
  174. "adcq %[bh], %[rh]\n\t"
  175. : [rl] "=r"(result.low), [rh] "=r"(result.high)
  176. : "0"(low), "1"(high), [bl] "g"(b.low), [bh] "g"(b.high)
  177. : "cc");
  178. return result;
  179. #else
  180. uint64_t lo = low + b.low;
  181. return Int128(lo, high + b.high + (lo < low));
  182. #endif
  183. }
  184. Int128 operator-(const Int128 &b) const {
  185. #ifdef USE_X86_64_ASM
  186. Int128 result;
  187. __asm__("subq %[bl], %[rl]\n\t"
  188. "sbbq %[bh], %[rh]\n\t"
  189. : [rl] "=r"(result.low), [rh] "=r"(result.high)
  190. : "0"(low), "1"(high), [bl] "g"(b.low), [bh] "g"(b.high)
  191. : "cc");
  192. return result;
  193. #else
  194. return *this + -b;
  195. #endif
  196. }
  197. Int128 &operator+=(const Int128 &b) {
  198. #ifdef USE_X86_64_ASM
  199. __asm__("addq %[bl], %[rl]\n\t"
  200. "adcq %[bh], %[rh]\n\t"
  201. : [rl] "=r"(low), [rh] "=r"(high)
  202. : "0"(low), "1"(high), [bl] "g"(b.low), [bh] "g"(b.high)
  203. : "cc");
  204. #else
  205. uint64_t lo = low + b.low;
  206. if (lo < low) {
  207. ++high;
  208. }
  209. low = lo;
  210. high += b.high;
  211. #endif
  212. return *this;
  213. }
  214. Int128 &operator++() {
  215. if (++low == 0) {
  216. ++high;
  217. }
  218. return *this;
  219. }
  220. Int128 operator*(int64_t b) const;
  221. real_t to_scalar() const {
  222. return ((int64_t)high >= 0) ? real_t(high) * (real_t(0x100000000LL) * real_t(0x100000000LL)) + real_t(low) : -(-*this).to_scalar();
  223. }
  224. int32_t get_sign() const {
  225. return ((int64_t)high < 0) ? -1 : ((high || low) ? 1 : 0);
  226. }
  227. bool operator<(const Int128 &b) const {
  228. return (high < b.high) || ((high == b.high) && (low < b.low));
  229. }
  230. int32_t ucmp(const Int128 &b) const {
  231. if (high < b.high) {
  232. return -1;
  233. }
  234. if (high > b.high) {
  235. return 1;
  236. }
  237. if (low < b.low) {
  238. return -1;
  239. }
  240. if (low > b.low) {
  241. return 1;
  242. }
  243. return 0;
  244. }
  245. };
  246. class Rational64 {
  247. private:
  248. uint64_t numerator;
  249. uint64_t denominator;
  250. int32_t sign;
  251. public:
  252. Rational64(int64_t p_numerator, int64_t p_denominator) {
  253. if (p_numerator > 0) {
  254. sign = 1;
  255. numerator = (uint64_t)p_numerator;
  256. } else if (p_numerator < 0) {
  257. sign = -1;
  258. numerator = (uint64_t)-p_numerator;
  259. } else {
  260. sign = 0;
  261. numerator = 0;
  262. }
  263. if (p_denominator > 0) {
  264. denominator = (uint64_t)p_denominator;
  265. } else if (p_denominator < 0) {
  266. sign = -sign;
  267. denominator = (uint64_t)-p_denominator;
  268. } else {
  269. denominator = 0;
  270. }
  271. }
  272. bool is_negative_infinity() const {
  273. return (sign < 0) && (denominator == 0);
  274. }
  275. bool is_nan() const {
  276. return (sign == 0) && (denominator == 0);
  277. }
  278. int32_t compare(const Rational64 &b) const;
  279. real_t to_scalar() const {
  280. return sign * ((denominator == 0) ? FLT_MAX : (real_t)numerator / denominator);
  281. }
  282. };
  283. class Rational128 {
  284. private:
  285. Int128 numerator;
  286. Int128 denominator;
  287. int32_t sign;
  288. bool is_int_64;
  289. public:
  290. Rational128(int64_t p_value) {
  291. if (p_value > 0) {
  292. sign = 1;
  293. this->numerator = p_value;
  294. } else if (p_value < 0) {
  295. sign = -1;
  296. this->numerator = -p_value;
  297. } else {
  298. sign = 0;
  299. this->numerator = (uint64_t)0;
  300. }
  301. this->denominator = (uint64_t)1;
  302. is_int_64 = true;
  303. }
  304. Rational128(const Int128 &p_numerator, const Int128 &p_denominator) {
  305. sign = p_numerator.get_sign();
  306. if (sign >= 0) {
  307. this->numerator = p_numerator;
  308. } else {
  309. this->numerator = -p_numerator;
  310. }
  311. int32_t dsign = p_denominator.get_sign();
  312. if (dsign >= 0) {
  313. this->denominator = p_denominator;
  314. } else {
  315. sign = -sign;
  316. this->denominator = -p_denominator;
  317. }
  318. is_int_64 = false;
  319. }
  320. int32_t compare(const Rational128 &b) const;
  321. int32_t compare(int64_t b) const;
  322. real_t to_scalar() const {
  323. return sign * ((denominator.get_sign() == 0) ? FLT_MAX : numerator.to_scalar() / denominator.to_scalar());
  324. }
  325. };
  326. class PointR128 {
  327. public:
  328. Int128 x;
  329. Int128 y;
  330. Int128 z;
  331. Int128 denominator;
  332. PointR128() {
  333. }
  334. PointR128(Int128 p_x, Int128 p_y, Int128 p_z, Int128 p_denominator) {
  335. x = p_x;
  336. y = p_y;
  337. z = p_z;
  338. denominator = p_denominator;
  339. }
  340. real_t xvalue() const {
  341. return x.to_scalar() / denominator.to_scalar();
  342. }
  343. real_t yvalue() const {
  344. return y.to_scalar() / denominator.to_scalar();
  345. }
  346. real_t zvalue() const {
  347. return z.to_scalar() / denominator.to_scalar();
  348. }
  349. };
  350. class Edge;
  351. class Face;
  352. class Vertex {
  353. public:
  354. Vertex *next = nullptr;
  355. Vertex *prev = nullptr;
  356. Edge *edges = nullptr;
  357. Face *first_nearby_face = nullptr;
  358. Face *last_nearby_face = nullptr;
  359. PointR128 point128;
  360. Point32 point;
  361. int32_t copy = -1;
  362. Vertex() {
  363. }
  364. #ifdef DEBUG_CONVEX_HULL
  365. void print() {
  366. printf("V%d (%d, %d, %d)", point.index, point.x, point.y, point.z);
  367. }
  368. void print_graph();
  369. #endif
  370. Point32 operator-(const Vertex &b) const {
  371. return point - b.point;
  372. }
  373. Rational128 dot(const Point64 &b) const {
  374. return (point.index >= 0) ? Rational128(point.dot(b)) : Rational128(point128.x * b.x + point128.y * b.y + point128.z * b.z, point128.denominator);
  375. }
  376. real_t xvalue() const {
  377. return (point.index >= 0) ? real_t(point.x) : point128.xvalue();
  378. }
  379. real_t yvalue() const {
  380. return (point.index >= 0) ? real_t(point.y) : point128.yvalue();
  381. }
  382. real_t zvalue() const {
  383. return (point.index >= 0) ? real_t(point.z) : point128.zvalue();
  384. }
  385. void receive_nearby_faces(Vertex *p_src) {
  386. if (last_nearby_face) {
  387. last_nearby_face->next_with_same_nearby_vertex = p_src->first_nearby_face;
  388. } else {
  389. first_nearby_face = p_src->first_nearby_face;
  390. }
  391. if (p_src->last_nearby_face) {
  392. last_nearby_face = p_src->last_nearby_face;
  393. }
  394. for (Face *f = p_src->first_nearby_face; f; f = f->next_with_same_nearby_vertex) {
  395. CHULL_ASSERT(f->nearby_vertex == p_src);
  396. f->nearby_vertex = this;
  397. }
  398. p_src->first_nearby_face = nullptr;
  399. p_src->last_nearby_face = nullptr;
  400. }
  401. };
  402. class Edge {
  403. public:
  404. Edge *next = nullptr;
  405. Edge *prev = nullptr;
  406. Edge *reverse = nullptr;
  407. Vertex *target = nullptr;
  408. Face *face = nullptr;
  409. int32_t copy = -1;
  410. void link(Edge *n) {
  411. CHULL_ASSERT(reverse->target == n->reverse->target);
  412. next = n;
  413. n->prev = this;
  414. }
  415. #ifdef DEBUG_CONVEX_HULL
  416. void print() {
  417. printf("E%p : %d -> %d, n=%p p=%p (0 %d\t%d\t%d) -> (%d %d %d)", this, reverse->target->point.index, target->point.index, next, prev,
  418. reverse->target->point.x, reverse->target->point.y, reverse->target->point.z, target->point.x, target->point.y, target->point.z);
  419. }
  420. #endif
  421. };
  422. class Face {
  423. public:
  424. Face *next = nullptr;
  425. Vertex *nearby_vertex = nullptr;
  426. Face *next_with_same_nearby_vertex = nullptr;
  427. Point32 origin;
  428. Point32 dir0;
  429. Point32 dir1;
  430. Face() {
  431. }
  432. void init(Vertex *p_a, Vertex *p_b, Vertex *p_c) {
  433. nearby_vertex = p_a;
  434. origin = p_a->point;
  435. dir0 = *p_b - *p_a;
  436. dir1 = *p_c - *p_a;
  437. if (p_a->last_nearby_face) {
  438. p_a->last_nearby_face->next_with_same_nearby_vertex = this;
  439. } else {
  440. p_a->first_nearby_face = this;
  441. }
  442. p_a->last_nearby_face = this;
  443. }
  444. Point64 get_normal() {
  445. return dir0.cross(dir1);
  446. }
  447. };
  448. template <typename UWord, typename UHWord>
  449. class DMul {
  450. private:
  451. static uint32_t high(uint64_t p_value) {
  452. return (uint32_t)(p_value >> 32);
  453. }
  454. static uint32_t low(uint64_t p_value) {
  455. return (uint32_t)p_value;
  456. }
  457. static uint64_t mul(uint32_t a, uint32_t b) {
  458. return (uint64_t)a * (uint64_t)b;
  459. }
  460. static void shl_half(uint64_t &p_value) {
  461. p_value <<= 32;
  462. }
  463. static uint64_t high(Int128 p_value) {
  464. return p_value.high;
  465. }
  466. static uint64_t low(Int128 p_value) {
  467. return p_value.low;
  468. }
  469. static Int128 mul(uint64_t a, uint64_t b) {
  470. return Int128::mul(a, b);
  471. }
  472. static void shl_half(Int128 &p_value) {
  473. p_value.high = p_value.low;
  474. p_value.low = 0;
  475. }
  476. public:
  477. static void mul(UWord p_a, UWord p_b, UWord &r_low, UWord &r_high) {
  478. UWord p00 = mul(low(p_a), low(p_b));
  479. UWord p01 = mul(low(p_a), high(p_b));
  480. UWord p10 = mul(high(p_a), low(p_b));
  481. UWord p11 = mul(high(p_a), high(p_b));
  482. UWord p0110 = UWord(low(p01)) + UWord(low(p10));
  483. p11 += high(p01);
  484. p11 += high(p10);
  485. p11 += high(p0110);
  486. shl_half(p0110);
  487. p00 += p0110;
  488. if (p00 < p0110) {
  489. ++p11;
  490. }
  491. r_low = p00;
  492. r_high = p11;
  493. }
  494. };
  495. private:
  496. class IntermediateHull {
  497. public:
  498. Vertex *min_xy = nullptr;
  499. Vertex *max_xy = nullptr;
  500. Vertex *min_yx = nullptr;
  501. Vertex *max_yx = nullptr;
  502. IntermediateHull() {
  503. }
  504. };
  505. enum Orientation { NONE,
  506. CLOCKWISE,
  507. COUNTER_CLOCKWISE };
  508. Vector3 scaling;
  509. Vector3 center;
  510. PagedAllocator<Vertex> vertex_pool;
  511. PagedAllocator<Edge> edge_pool;
  512. PagedAllocator<Face> face_pool;
  513. LocalVector<Vertex *> original_vertices;
  514. int32_t merge_stamp = 0;
  515. int32_t min_axis = 0;
  516. int32_t med_axis = 0;
  517. int32_t max_axis = 0;
  518. int32_t used_edge_pairs = 0;
  519. int32_t max_used_edge_pairs = 0;
  520. static Orientation get_orientation(const Edge *p_prev, const Edge *p_next, const Point32 &p_s, const Point32 &p_t);
  521. Edge *find_max_angle(bool p_ccw, const Vertex *p_start, const Point32 &p_s, const Point64 &p_rxs, const Point64 &p_ssxrxs, Rational64 &p_min_cot);
  522. void find_edge_for_coplanar_faces(Vertex *p_c0, Vertex *p_c1, Edge *&p_e0, Edge *&p_e1, Vertex *p_stop0, Vertex *p_stop1);
  523. Edge *new_edge_pair(Vertex *p_from, Vertex *p_to);
  524. void remove_edge_pair(Edge *p_edge) {
  525. Edge *n = p_edge->next;
  526. Edge *r = p_edge->reverse;
  527. CHULL_ASSERT(p_edge->target && r->target);
  528. if (n != p_edge) {
  529. n->prev = p_edge->prev;
  530. p_edge->prev->next = n;
  531. r->target->edges = n;
  532. } else {
  533. r->target->edges = nullptr;
  534. }
  535. n = r->next;
  536. if (n != r) {
  537. n->prev = r->prev;
  538. r->prev->next = n;
  539. p_edge->target->edges = n;
  540. } else {
  541. p_edge->target->edges = nullptr;
  542. }
  543. edge_pool.free(p_edge);
  544. edge_pool.free(r);
  545. used_edge_pairs--;
  546. }
  547. void compute_internal(int32_t p_start, int32_t p_end, IntermediateHull &r_result);
  548. bool merge_projection(IntermediateHull &p_h0, IntermediateHull &p_h1, Vertex *&r_c0, Vertex *&r_c1);
  549. void merge(IntermediateHull &p_h0, IntermediateHull &p_h1);
  550. Vector3 to_gd_vector(const Point32 &p_v);
  551. Vector3 get_gd_normal(Face *p_face);
  552. bool shift_face(Face *p_face, real_t p_amount, LocalVector<Vertex *> p_stack);
  553. public:
  554. ~ConvexHullInternal() {
  555. vertex_pool.reset(true);
  556. edge_pool.reset(true);
  557. face_pool.reset(true);
  558. }
  559. Vertex *vertex_list;
  560. void compute(const Vector3 *p_coords, int32_t p_count);
  561. Vector3 get_coordinates(const Vertex *p_v);
  562. real_t shrink(real_t amount, real_t p_clamp_amount);
  563. };
  564. ConvexHullInternal::Int128 ConvexHullInternal::Int128::operator*(int64_t b) const {
  565. bool negative = (int64_t)high < 0;
  566. Int128 a = negative ? -*this : *this;
  567. if (b < 0) {
  568. negative = !negative;
  569. b = -b;
  570. }
  571. Int128 result = mul(a.low, (uint64_t)b);
  572. result.high += a.high * (uint64_t)b;
  573. return negative ? -result : result;
  574. }
  575. ConvexHullInternal::Int128 ConvexHullInternal::Int128::mul(int64_t a, int64_t b) {
  576. Int128 result;
  577. #ifdef USE_X86_64_ASM
  578. __asm__("imulq %[b]"
  579. : "=a"(result.low), "=d"(result.high)
  580. : "0"(a), [b] "r"(b)
  581. : "cc");
  582. return result;
  583. #else
  584. bool negative = a < 0;
  585. if (negative) {
  586. a = -a;
  587. }
  588. if (b < 0) {
  589. negative = !negative;
  590. b = -b;
  591. }
  592. DMul<uint64_t, uint32_t>::mul((uint64_t)a, (uint64_t)b, result.low, result.high);
  593. return negative ? -result : result;
  594. #endif
  595. }
  596. ConvexHullInternal::Int128 ConvexHullInternal::Int128::mul(uint64_t a, uint64_t b) {
  597. Int128 result;
  598. #ifdef USE_X86_64_ASM
  599. __asm__("mulq %[b]"
  600. : "=a"(result.low), "=d"(result.high)
  601. : "0"(a), [b] "r"(b)
  602. : "cc");
  603. #else
  604. DMul<uint64_t, uint32_t>::mul(a, b, result.low, result.high);
  605. #endif
  606. return result;
  607. }
  608. int32_t ConvexHullInternal::Rational64::compare(const Rational64 &b) const {
  609. if (sign != b.sign) {
  610. return sign - b.sign;
  611. } else if (sign == 0) {
  612. return 0;
  613. }
  614. #ifdef USE_X86_64_ASM
  615. int32_t result;
  616. int64_t tmp;
  617. int64_t dummy;
  618. __asm__("mulq %[bn]\n\t"
  619. "movq %%rax, %[tmp]\n\t"
  620. "movq %%rdx, %%rbx\n\t"
  621. "movq %[tn], %%rax\n\t"
  622. "mulq %[bd]\n\t"
  623. "subq %[tmp], %%rax\n\t"
  624. "sbbq %%rbx, %%rdx\n\t" // rdx:rax contains 128-bit-difference "numerator*b.denominator - b.numerator*denominator"
  625. "setnsb %%bh\n\t" // bh=1 if difference is non-negative, bh=0 otherwise
  626. "orq %%rdx, %%rax\n\t"
  627. "setnzb %%bl\n\t" // bl=1 if difference if non-zero, bl=0 if it is zero
  628. "decb %%bh\n\t" // now bx=0x0000 if difference is zero, 0xff01 if it is negative, 0x0001 if it is positive (i.e., same sign as difference)
  629. "shll $16, %%ebx\n\t" // ebx has same sign as difference
  630. : "=&b"(result), [tmp] "=&r"(tmp), "=a"(dummy)
  631. : "a"(denominator), [bn] "g"(b.numerator), [tn] "g"(numerator), [bd] "g"(b.denominator)
  632. : "%rdx", "cc");
  633. // if sign is +1, only bit 0 of result is inverted, which does not change the sign of result (and cannot result in zero)
  634. // if sign is -1, all bits of result are inverted, which changes the sign of result (and again cannot result in zero)
  635. return result ? result ^ sign : 0;
  636. #else
  637. return sign * Int128::mul(numerator, b.denominator).ucmp(Int128::mul(denominator, b.numerator));
  638. #endif
  639. }
  640. int32_t ConvexHullInternal::Rational128::compare(const Rational128 &b) const {
  641. if (sign != b.sign) {
  642. return sign - b.sign;
  643. } else if (sign == 0) {
  644. return 0;
  645. }
  646. if (is_int_64) {
  647. return -b.compare(sign * (int64_t)numerator.low);
  648. }
  649. Int128 nbd_low, nbd_high, dbn_low, dbn_high;
  650. DMul<Int128, uint64_t>::mul(numerator, b.denominator, nbd_low, nbd_high);
  651. DMul<Int128, uint64_t>::mul(denominator, b.numerator, dbn_low, dbn_high);
  652. int32_t cmp = nbd_high.ucmp(dbn_high);
  653. if (cmp) {
  654. return cmp * sign;
  655. }
  656. return nbd_low.ucmp(dbn_low) * sign;
  657. }
  658. int32_t ConvexHullInternal::Rational128::compare(int64_t b) const {
  659. if (is_int_64) {
  660. int64_t a = sign * (int64_t)numerator.low;
  661. return (a > b) ? 1 : ((a < b) ? -1 : 0);
  662. }
  663. if (b > 0) {
  664. if (sign <= 0) {
  665. return -1;
  666. }
  667. } else if (b < 0) {
  668. if (sign >= 0) {
  669. return 1;
  670. }
  671. b = -b;
  672. } else {
  673. return sign;
  674. }
  675. return numerator.ucmp(denominator * b) * sign;
  676. }
  677. ConvexHullInternal::Edge *ConvexHullInternal::new_edge_pair(Vertex *p_from, Vertex *p_to) {
  678. CHULL_ASSERT(p_from && p_to);
  679. Edge *e = edge_pool.alloc();
  680. Edge *r = edge_pool.alloc();
  681. e->reverse = r;
  682. r->reverse = e;
  683. e->copy = merge_stamp;
  684. r->copy = merge_stamp;
  685. e->target = p_to;
  686. r->target = p_from;
  687. e->face = nullptr;
  688. r->face = nullptr;
  689. used_edge_pairs++;
  690. if (used_edge_pairs > max_used_edge_pairs) {
  691. max_used_edge_pairs = used_edge_pairs;
  692. }
  693. return e;
  694. }
  695. bool ConvexHullInternal::merge_projection(IntermediateHull &r_h0, IntermediateHull &r_h1, Vertex *&r_c0, Vertex *&r_c1) {
  696. Vertex *v0 = r_h0.max_yx;
  697. Vertex *v1 = r_h1.min_yx;
  698. if ((v0->point.x == v1->point.x) && (v0->point.y == v1->point.y)) {
  699. CHULL_ASSERT(v0->point.z < v1->point.z);
  700. Vertex *v1p = v1->prev;
  701. if (v1p == v1) {
  702. r_c0 = v0;
  703. if (v1->edges) {
  704. CHULL_ASSERT(v1->edges->next == v1->edges);
  705. v1 = v1->edges->target;
  706. CHULL_ASSERT(v1->edges->next == v1->edges);
  707. }
  708. r_c1 = v1;
  709. return false;
  710. }
  711. Vertex *v1n = v1->next;
  712. v1p->next = v1n;
  713. v1n->prev = v1p;
  714. if (v1 == r_h1.min_xy) {
  715. if ((v1n->point.x < v1p->point.x) || ((v1n->point.x == v1p->point.x) && (v1n->point.y < v1p->point.y))) {
  716. r_h1.min_xy = v1n;
  717. } else {
  718. r_h1.min_xy = v1p;
  719. }
  720. }
  721. if (v1 == r_h1.max_xy) {
  722. if ((v1n->point.x > v1p->point.x) || ((v1n->point.x == v1p->point.x) && (v1n->point.y > v1p->point.y))) {
  723. r_h1.max_xy = v1n;
  724. } else {
  725. r_h1.max_xy = v1p;
  726. }
  727. }
  728. }
  729. v0 = r_h0.max_xy;
  730. v1 = r_h1.max_xy;
  731. Vertex *v00 = nullptr;
  732. Vertex *v10 = nullptr;
  733. int32_t sign = 1;
  734. for (int32_t side = 0; side <= 1; side++) {
  735. int32_t dx = (v1->point.x - v0->point.x) * sign;
  736. if (dx > 0) {
  737. while (true) {
  738. int32_t dy = v1->point.y - v0->point.y;
  739. Vertex *w0 = side ? v0->next : v0->prev;
  740. if (w0 != v0) {
  741. int32_t dx0 = (w0->point.x - v0->point.x) * sign;
  742. int32_t dy0 = w0->point.y - v0->point.y;
  743. if ((dy0 <= 0) && ((dx0 == 0) || ((dx0 < 0) && (dy0 * dx <= dy * dx0)))) {
  744. v0 = w0;
  745. dx = (v1->point.x - v0->point.x) * sign;
  746. continue;
  747. }
  748. }
  749. Vertex *w1 = side ? v1->next : v1->prev;
  750. if (w1 != v1) {
  751. int32_t dx1 = (w1->point.x - v1->point.x) * sign;
  752. int32_t dy1 = w1->point.y - v1->point.y;
  753. int32_t dxn = (w1->point.x - v0->point.x) * sign;
  754. if ((dxn > 0) && (dy1 < 0) && ((dx1 == 0) || ((dx1 < 0) && (dy1 * dx < dy * dx1)))) {
  755. v1 = w1;
  756. dx = dxn;
  757. continue;
  758. }
  759. }
  760. break;
  761. }
  762. } else if (dx < 0) {
  763. while (true) {
  764. int32_t dy = v1->point.y - v0->point.y;
  765. Vertex *w1 = side ? v1->prev : v1->next;
  766. if (w1 != v1) {
  767. int32_t dx1 = (w1->point.x - v1->point.x) * sign;
  768. int32_t dy1 = w1->point.y - v1->point.y;
  769. if ((dy1 >= 0) && ((dx1 == 0) || ((dx1 < 0) && (dy1 * dx <= dy * dx1)))) {
  770. v1 = w1;
  771. dx = (v1->point.x - v0->point.x) * sign;
  772. continue;
  773. }
  774. }
  775. Vertex *w0 = side ? v0->prev : v0->next;
  776. if (w0 != v0) {
  777. int32_t dx0 = (w0->point.x - v0->point.x) * sign;
  778. int32_t dy0 = w0->point.y - v0->point.y;
  779. int32_t dxn = (v1->point.x - w0->point.x) * sign;
  780. if ((dxn < 0) && (dy0 > 0) && ((dx0 == 0) || ((dx0 < 0) && (dy0 * dx < dy * dx0)))) {
  781. v0 = w0;
  782. dx = dxn;
  783. continue;
  784. }
  785. }
  786. break;
  787. }
  788. } else {
  789. int32_t x = v0->point.x;
  790. int32_t y0 = v0->point.y;
  791. Vertex *w0 = v0;
  792. Vertex *t;
  793. while (((t = side ? w0->next : w0->prev) != v0) && (t->point.x == x) && (t->point.y <= y0)) {
  794. w0 = t;
  795. y0 = t->point.y;
  796. }
  797. v0 = w0;
  798. int32_t y1 = v1->point.y;
  799. Vertex *w1 = v1;
  800. while (((t = side ? w1->prev : w1->next) != v1) && (t->point.x == x) && (t->point.y >= y1)) {
  801. w1 = t;
  802. y1 = t->point.y;
  803. }
  804. v1 = w1;
  805. }
  806. if (side == 0) {
  807. v00 = v0;
  808. v10 = v1;
  809. v0 = r_h0.min_xy;
  810. v1 = r_h1.min_xy;
  811. sign = -1;
  812. }
  813. }
  814. v0->prev = v1;
  815. v1->next = v0;
  816. v00->next = v10;
  817. v10->prev = v00;
  818. if (r_h1.min_xy->point.x < r_h0.min_xy->point.x) {
  819. r_h0.min_xy = r_h1.min_xy;
  820. }
  821. if (r_h1.max_xy->point.x >= r_h0.max_xy->point.x) {
  822. r_h0.max_xy = r_h1.max_xy;
  823. }
  824. r_h0.max_yx = r_h1.max_yx;
  825. r_c0 = v00;
  826. r_c1 = v10;
  827. return true;
  828. }
  829. void ConvexHullInternal::compute_internal(int32_t p_start, int32_t p_end, IntermediateHull &r_result) {
  830. int32_t n = p_end - p_start;
  831. switch (n) {
  832. case 0:
  833. r_result.min_xy = nullptr;
  834. r_result.max_xy = nullptr;
  835. r_result.min_yx = nullptr;
  836. r_result.max_yx = nullptr;
  837. return;
  838. case 2: {
  839. Vertex *v = original_vertices[p_start];
  840. Vertex *w = original_vertices[p_start + 1];
  841. if (v->point != w->point) {
  842. int32_t dx = v->point.x - w->point.x;
  843. int32_t dy = v->point.y - w->point.y;
  844. if ((dx == 0) && (dy == 0)) {
  845. if (v->point.z > w->point.z) {
  846. Vertex *t = w;
  847. w = v;
  848. v = t;
  849. }
  850. CHULL_ASSERT(v->point.z < w->point.z);
  851. v->next = v;
  852. v->prev = v;
  853. r_result.min_xy = v;
  854. r_result.max_xy = v;
  855. r_result.min_yx = v;
  856. r_result.max_yx = v;
  857. } else {
  858. v->next = w;
  859. v->prev = w;
  860. w->next = v;
  861. w->prev = v;
  862. if ((dx < 0) || ((dx == 0) && (dy < 0))) {
  863. r_result.min_xy = v;
  864. r_result.max_xy = w;
  865. } else {
  866. r_result.min_xy = w;
  867. r_result.max_xy = v;
  868. }
  869. if ((dy < 0) || ((dy == 0) && (dx < 0))) {
  870. r_result.min_yx = v;
  871. r_result.max_yx = w;
  872. } else {
  873. r_result.min_yx = w;
  874. r_result.max_yx = v;
  875. }
  876. }
  877. Edge *e = new_edge_pair(v, w);
  878. e->link(e);
  879. v->edges = e;
  880. e = e->reverse;
  881. e->link(e);
  882. w->edges = e;
  883. return;
  884. }
  885. FALLTHROUGH;
  886. }
  887. case 1: {
  888. Vertex *v = original_vertices[p_start];
  889. v->edges = nullptr;
  890. v->next = v;
  891. v->prev = v;
  892. r_result.min_xy = v;
  893. r_result.max_xy = v;
  894. r_result.min_yx = v;
  895. r_result.max_yx = v;
  896. return;
  897. }
  898. }
  899. int32_t split0 = p_start + n / 2;
  900. Point32 p = original_vertices[split0 - 1]->point;
  901. int32_t split1 = split0;
  902. while ((split1 < p_end) && (original_vertices[split1]->point == p)) {
  903. split1++;
  904. }
  905. compute_internal(p_start, split0, r_result);
  906. IntermediateHull hull1;
  907. compute_internal(split1, p_end, hull1);
  908. #ifdef DEBUG_CONVEX_HULL
  909. printf("\n\nMerge\n");
  910. r_result.print();
  911. hull1.print();
  912. #endif
  913. merge(r_result, hull1);
  914. #ifdef DEBUG_CONVEX_HULL
  915. printf("\n Result\n");
  916. r_result.print();
  917. #endif
  918. }
  919. #ifdef DEBUG_CONVEX_HULL
  920. void ConvexHullInternal::IntermediateHull::print() {
  921. printf(" Hull\n");
  922. for (Vertex *v = min_xy; v;) {
  923. printf(" ");
  924. v->print();
  925. if (v == max_xy) {
  926. printf(" max_xy");
  927. }
  928. if (v == min_yx) {
  929. printf(" min_yx");
  930. }
  931. if (v == max_yx) {
  932. printf(" max_yx");
  933. }
  934. if (v->next->prev != v) {
  935. printf(" Inconsistency");
  936. }
  937. printf("\n");
  938. v = v->next;
  939. if (v == min_xy) {
  940. break;
  941. }
  942. }
  943. if (min_xy) {
  944. min_xy->copy = (min_xy->copy == -1) ? -2 : -1;
  945. min_xy->print_graph();
  946. }
  947. }
  948. void ConvexHullInternal::Vertex::print_graph() {
  949. print();
  950. printf("\nEdges\n");
  951. Edge *e = edges;
  952. if (e) {
  953. do {
  954. e->print();
  955. printf("\n");
  956. e = e->next;
  957. } while (e != edges);
  958. do {
  959. Vertex *v = e->target;
  960. if (v->copy != copy) {
  961. v->copy = copy;
  962. v->print_graph();
  963. }
  964. e = e->next;
  965. } while (e != edges);
  966. }
  967. }
  968. #endif
  969. ConvexHullInternal::Orientation ConvexHullInternal::get_orientation(const Edge *p_prev, const Edge *p_next, const Point32 &p_s, const Point32 &p_t) {
  970. CHULL_ASSERT(p_prev->reverse->target == p_next->reverse->target);
  971. if (p_prev->next == p_next) {
  972. if (p_prev->prev == p_next) {
  973. Point64 n = p_t.cross(p_s);
  974. Point64 m = (*p_prev->target - *p_next->reverse->target).cross(*p_next->target - *p_next->reverse->target);
  975. CHULL_ASSERT(!m.is_zero());
  976. int64_t dot = n.dot(m);
  977. CHULL_ASSERT(dot != 0);
  978. return (dot > 0) ? COUNTER_CLOCKWISE : CLOCKWISE;
  979. }
  980. return COUNTER_CLOCKWISE;
  981. } else if (p_prev->prev == p_next) {
  982. return CLOCKWISE;
  983. } else {
  984. return NONE;
  985. }
  986. }
  987. ConvexHullInternal::Edge *ConvexHullInternal::find_max_angle(bool p_ccw, const Vertex *p_start, const Point32 &p_s, const Point64 &p_rxs, const Point64 &p_sxrxs, Rational64 &p_min_cot) {
  988. Edge *min_edge = nullptr;
  989. #ifdef DEBUG_CONVEX_HULL
  990. printf("find max edge for %d\n", p_start->point.index);
  991. #endif
  992. Edge *e = p_start->edges;
  993. if (e) {
  994. do {
  995. if (e->copy > merge_stamp) {
  996. Point32 t = *e->target - *p_start;
  997. Rational64 cot(t.dot(p_sxrxs), t.dot(p_rxs));
  998. #ifdef DEBUG_CONVEX_HULL
  999. printf(" Angle is %f (%d) for ", Math::atan(cot.to_scalar()), (int32_t)cot.is_nan());
  1000. e->print();
  1001. #endif
  1002. if (cot.is_nan()) {
  1003. CHULL_ASSERT(p_ccw ? (t.dot(p_s) < 0) : (t.dot(p_s) > 0));
  1004. } else {
  1005. int32_t cmp;
  1006. if (min_edge == nullptr) {
  1007. p_min_cot = cot;
  1008. min_edge = e;
  1009. } else if ((cmp = cot.compare(p_min_cot)) < 0) {
  1010. p_min_cot = cot;
  1011. min_edge = e;
  1012. } else if ((cmp == 0) && (p_ccw == (get_orientation(min_edge, e, p_s, t) == COUNTER_CLOCKWISE))) {
  1013. min_edge = e;
  1014. }
  1015. }
  1016. #ifdef DEBUG_CONVEX_HULL
  1017. printf("\n");
  1018. #endif
  1019. }
  1020. e = e->next;
  1021. } while (e != p_start->edges);
  1022. }
  1023. return min_edge;
  1024. }
  1025. void ConvexHullInternal::find_edge_for_coplanar_faces(Vertex *p_c0, Vertex *p_c1, Edge *&p_e0, Edge *&p_e1, Vertex *p_stop0, Vertex *p_stop1) {
  1026. Edge *start0 = p_e0;
  1027. Edge *start1 = p_e1;
  1028. Point32 et0 = start0 ? start0->target->point : p_c0->point;
  1029. Point32 et1 = start1 ? start1->target->point : p_c1->point;
  1030. Point32 s = p_c1->point - p_c0->point;
  1031. Point64 normal = ((start0 ? start0 : start1)->target->point - p_c0->point).cross(s);
  1032. int64_t dist = p_c0->point.dot(normal);
  1033. CHULL_ASSERT(!start1 || (start1->target->point.dot(normal) == dist));
  1034. Point64 perp = s.cross(normal);
  1035. CHULL_ASSERT(!perp.is_zero());
  1036. #ifdef DEBUG_CONVEX_HULL
  1037. printf(" Advancing %d %d (%p %p, %d %d)\n", p_c0->point.index, p_c1->point.index, start0, start1, start0 ? start0->target->point.index : -1, start1 ? start1->target->point.index : -1);
  1038. #endif
  1039. int64_t max_dot0 = et0.dot(perp);
  1040. if (p_e0) {
  1041. while (p_e0->target != p_stop0) {
  1042. Edge *e = p_e0->reverse->prev;
  1043. if (e->target->point.dot(normal) < dist) {
  1044. break;
  1045. }
  1046. CHULL_ASSERT(e->target->point.dot(normal) == dist);
  1047. if (e->copy == merge_stamp) {
  1048. break;
  1049. }
  1050. int64_t dot = e->target->point.dot(perp);
  1051. if (dot <= max_dot0) {
  1052. break;
  1053. }
  1054. max_dot0 = dot;
  1055. p_e0 = e;
  1056. et0 = e->target->point;
  1057. }
  1058. }
  1059. int64_t max_dot1 = et1.dot(perp);
  1060. if (p_e1) {
  1061. while (p_e1->target != p_stop1) {
  1062. Edge *e = p_e1->reverse->next;
  1063. if (e->target->point.dot(normal) < dist) {
  1064. break;
  1065. }
  1066. CHULL_ASSERT(e->target->point.dot(normal) == dist);
  1067. if (e->copy == merge_stamp) {
  1068. break;
  1069. }
  1070. int64_t dot = e->target->point.dot(perp);
  1071. if (dot <= max_dot1) {
  1072. break;
  1073. }
  1074. max_dot1 = dot;
  1075. p_e1 = e;
  1076. et1 = e->target->point;
  1077. }
  1078. }
  1079. #ifdef DEBUG_CONVEX_HULL
  1080. printf(" Starting at %d %d\n", et0.index, et1.index);
  1081. #endif
  1082. int64_t dx = max_dot1 - max_dot0;
  1083. if (dx > 0) {
  1084. while (true) {
  1085. int64_t dy = (et1 - et0).dot(s);
  1086. if (p_e0 && (p_e0->target != p_stop0)) {
  1087. Edge *f0 = p_e0->next->reverse;
  1088. if (f0->copy > merge_stamp) {
  1089. int64_t dx0 = (f0->target->point - et0).dot(perp);
  1090. int64_t dy0 = (f0->target->point - et0).dot(s);
  1091. if ((dx0 == 0) ? (dy0 < 0) : ((dx0 < 0) && (Rational64(dy0, dx0).compare(Rational64(dy, dx)) >= 0))) {
  1092. et0 = f0->target->point;
  1093. dx = (et1 - et0).dot(perp);
  1094. p_e0 = (p_e0 == start0) ? nullptr : f0;
  1095. continue;
  1096. }
  1097. }
  1098. }
  1099. if (p_e1 && (p_e1->target != p_stop1)) {
  1100. Edge *f1 = p_e1->reverse->next;
  1101. if (f1->copy > merge_stamp) {
  1102. Point32 d1 = f1->target->point - et1;
  1103. if (d1.dot(normal) == 0) {
  1104. int64_t dx1 = d1.dot(perp);
  1105. int64_t dy1 = d1.dot(s);
  1106. int64_t dxn = (f1->target->point - et0).dot(perp);
  1107. if ((dxn > 0) && ((dx1 == 0) ? (dy1 < 0) : ((dx1 < 0) && (Rational64(dy1, dx1).compare(Rational64(dy, dx)) > 0)))) {
  1108. p_e1 = f1;
  1109. et1 = p_e1->target->point;
  1110. dx = dxn;
  1111. continue;
  1112. }
  1113. } else {
  1114. CHULL_ASSERT((p_e1 == start1) && (d1.dot(normal) < 0));
  1115. }
  1116. }
  1117. }
  1118. break;
  1119. }
  1120. } else if (dx < 0) {
  1121. while (true) {
  1122. int64_t dy = (et1 - et0).dot(s);
  1123. if (p_e1 && (p_e1->target != p_stop1)) {
  1124. Edge *f1 = p_e1->prev->reverse;
  1125. if (f1->copy > merge_stamp) {
  1126. int64_t dx1 = (f1->target->point - et1).dot(perp);
  1127. int64_t dy1 = (f1->target->point - et1).dot(s);
  1128. if ((dx1 == 0) ? (dy1 > 0) : ((dx1 < 0) && (Rational64(dy1, dx1).compare(Rational64(dy, dx)) <= 0))) {
  1129. et1 = f1->target->point;
  1130. dx = (et1 - et0).dot(perp);
  1131. p_e1 = (p_e1 == start1) ? nullptr : f1;
  1132. continue;
  1133. }
  1134. }
  1135. }
  1136. if (p_e0 && (p_e0->target != p_stop0)) {
  1137. Edge *f0 = p_e0->reverse->prev;
  1138. if (f0->copy > merge_stamp) {
  1139. Point32 d0 = f0->target->point - et0;
  1140. if (d0.dot(normal) == 0) {
  1141. int64_t dx0 = d0.dot(perp);
  1142. int64_t dy0 = d0.dot(s);
  1143. int64_t dxn = (et1 - f0->target->point).dot(perp);
  1144. if ((dxn < 0) && ((dx0 == 0) ? (dy0 > 0) : ((dx0 < 0) && (Rational64(dy0, dx0).compare(Rational64(dy, dx)) < 0)))) {
  1145. p_e0 = f0;
  1146. et0 = p_e0->target->point;
  1147. dx = dxn;
  1148. continue;
  1149. }
  1150. } else {
  1151. CHULL_ASSERT((p_e0 == start0) && (d0.dot(normal) < 0));
  1152. }
  1153. }
  1154. }
  1155. break;
  1156. }
  1157. }
  1158. #ifdef DEBUG_CONVEX_HULL
  1159. printf(" Advanced edges to %d %d\n", et0.index, et1.index);
  1160. #endif
  1161. }
  1162. void ConvexHullInternal::merge(IntermediateHull &p_h0, IntermediateHull &p_h1) {
  1163. if (!p_h1.max_xy) {
  1164. return;
  1165. }
  1166. if (!p_h0.max_xy) {
  1167. p_h0 = p_h1;
  1168. return;
  1169. }
  1170. merge_stamp--;
  1171. Vertex *c0 = nullptr;
  1172. Edge *to_prev0 = nullptr;
  1173. Edge *first_new0 = nullptr;
  1174. Edge *pending_head0 = nullptr;
  1175. Edge *pending_tail0 = nullptr;
  1176. Vertex *c1 = nullptr;
  1177. Edge *to_prev1 = nullptr;
  1178. Edge *first_new1 = nullptr;
  1179. Edge *pending_head1 = nullptr;
  1180. Edge *pending_tail1 = nullptr;
  1181. Point32 prev_point;
  1182. if (merge_projection(p_h0, p_h1, c0, c1)) {
  1183. Point32 s = *c1 - *c0;
  1184. Point64 normal = Point32(0, 0, -1).cross(s);
  1185. Point64 t = s.cross(normal);
  1186. CHULL_ASSERT(!t.is_zero());
  1187. Edge *e = c0->edges;
  1188. Edge *start0 = nullptr;
  1189. if (e) {
  1190. do {
  1191. int64_t dot = (*e->target - *c0).dot(normal);
  1192. CHULL_ASSERT(dot <= 0);
  1193. if ((dot == 0) && ((*e->target - *c0).dot(t) > 0)) {
  1194. if (!start0 || (get_orientation(start0, e, s, Point32(0, 0, -1)) == CLOCKWISE)) {
  1195. start0 = e;
  1196. }
  1197. }
  1198. e = e->next;
  1199. } while (e != c0->edges);
  1200. }
  1201. e = c1->edges;
  1202. Edge *start1 = nullptr;
  1203. if (e) {
  1204. do {
  1205. int64_t dot = (*e->target - *c1).dot(normal);
  1206. CHULL_ASSERT(dot <= 0);
  1207. if ((dot == 0) && ((*e->target - *c1).dot(t) > 0)) {
  1208. if (!start1 || (get_orientation(start1, e, s, Point32(0, 0, -1)) == COUNTER_CLOCKWISE)) {
  1209. start1 = e;
  1210. }
  1211. }
  1212. e = e->next;
  1213. } while (e != c1->edges);
  1214. }
  1215. if (start0 || start1) {
  1216. find_edge_for_coplanar_faces(c0, c1, start0, start1, nullptr, nullptr);
  1217. if (start0) {
  1218. c0 = start0->target;
  1219. }
  1220. if (start1) {
  1221. c1 = start1->target;
  1222. }
  1223. }
  1224. prev_point = c1->point;
  1225. prev_point.z++;
  1226. } else {
  1227. prev_point = c1->point;
  1228. prev_point.x++;
  1229. }
  1230. Vertex *first0 = c0;
  1231. Vertex *first1 = c1;
  1232. bool first_run = true;
  1233. while (true) {
  1234. Point32 s = *c1 - *c0;
  1235. Point32 r = prev_point - c0->point;
  1236. Point64 rxs = r.cross(s);
  1237. Point64 sxrxs = s.cross(rxs);
  1238. #ifdef DEBUG_CONVEX_HULL
  1239. printf("\n Checking %d %d\n", c0->point.index, c1->point.index);
  1240. #endif
  1241. Rational64 min_cot0(0, 0);
  1242. Edge *min0 = find_max_angle(false, c0, s, rxs, sxrxs, min_cot0);
  1243. Rational64 min_cot1(0, 0);
  1244. Edge *min1 = find_max_angle(true, c1, s, rxs, sxrxs, min_cot1);
  1245. if (!min0 && !min1) {
  1246. Edge *e = new_edge_pair(c0, c1);
  1247. e->link(e);
  1248. c0->edges = e;
  1249. e = e->reverse;
  1250. e->link(e);
  1251. c1->edges = e;
  1252. return;
  1253. } else {
  1254. int32_t cmp = !min0 ? 1 : (!min1 ? -1 : min_cot0.compare(min_cot1));
  1255. #ifdef DEBUG_CONVEX_HULL
  1256. printf(" -> Result %d\n", cmp);
  1257. #endif
  1258. if (first_run || ((cmp >= 0) ? !min_cot1.is_negative_infinity() : !min_cot0.is_negative_infinity())) {
  1259. Edge *e = new_edge_pair(c0, c1);
  1260. if (pending_tail0) {
  1261. pending_tail0->prev = e;
  1262. } else {
  1263. pending_head0 = e;
  1264. }
  1265. e->next = pending_tail0;
  1266. pending_tail0 = e;
  1267. e = e->reverse;
  1268. if (pending_tail1) {
  1269. pending_tail1->next = e;
  1270. } else {
  1271. pending_head1 = e;
  1272. }
  1273. e->prev = pending_tail1;
  1274. pending_tail1 = e;
  1275. }
  1276. Edge *e0 = min0;
  1277. Edge *e1 = min1;
  1278. #ifdef DEBUG_CONVEX_HULL
  1279. printf(" Found min edges to %d %d\n", e0 ? e0->target->point.index : -1, e1 ? e1->target->point.index : -1);
  1280. #endif
  1281. if (cmp == 0) {
  1282. find_edge_for_coplanar_faces(c0, c1, e0, e1, nullptr, nullptr);
  1283. }
  1284. if ((cmp >= 0) && e1) {
  1285. if (to_prev1) {
  1286. for (Edge *e = to_prev1->next, *n = nullptr; e != min1; e = n) {
  1287. n = e->next;
  1288. remove_edge_pair(e);
  1289. }
  1290. }
  1291. if (pending_tail1) {
  1292. if (to_prev1) {
  1293. to_prev1->link(pending_head1);
  1294. } else {
  1295. min1->prev->link(pending_head1);
  1296. first_new1 = pending_head1;
  1297. }
  1298. pending_tail1->link(min1);
  1299. pending_head1 = nullptr;
  1300. pending_tail1 = nullptr;
  1301. } else if (!to_prev1) {
  1302. first_new1 = min1;
  1303. }
  1304. prev_point = c1->point;
  1305. c1 = e1->target;
  1306. to_prev1 = e1->reverse;
  1307. }
  1308. if ((cmp <= 0) && e0) {
  1309. if (to_prev0) {
  1310. for (Edge *e = to_prev0->prev, *n = nullptr; e != min0; e = n) {
  1311. n = e->prev;
  1312. remove_edge_pair(e);
  1313. }
  1314. }
  1315. if (pending_tail0) {
  1316. if (to_prev0) {
  1317. pending_head0->link(to_prev0);
  1318. } else {
  1319. pending_head0->link(min0->next);
  1320. first_new0 = pending_head0;
  1321. }
  1322. min0->link(pending_tail0);
  1323. pending_head0 = nullptr;
  1324. pending_tail0 = nullptr;
  1325. } else if (!to_prev0) {
  1326. first_new0 = min0;
  1327. }
  1328. prev_point = c0->point;
  1329. c0 = e0->target;
  1330. to_prev0 = e0->reverse;
  1331. }
  1332. }
  1333. if ((c0 == first0) && (c1 == first1)) {
  1334. if (to_prev0 == nullptr) {
  1335. pending_head0->link(pending_tail0);
  1336. c0->edges = pending_tail0;
  1337. } else {
  1338. for (Edge *e = to_prev0->prev, *n = nullptr; e != first_new0; e = n) {
  1339. n = e->prev;
  1340. remove_edge_pair(e);
  1341. }
  1342. if (pending_tail0) {
  1343. pending_head0->link(to_prev0);
  1344. first_new0->link(pending_tail0);
  1345. }
  1346. }
  1347. if (to_prev1 == nullptr) {
  1348. pending_tail1->link(pending_head1);
  1349. c1->edges = pending_tail1;
  1350. } else {
  1351. for (Edge *e = to_prev1->next, *n = nullptr; e != first_new1; e = n) {
  1352. n = e->next;
  1353. remove_edge_pair(e);
  1354. }
  1355. if (pending_tail1) {
  1356. to_prev1->link(pending_head1);
  1357. pending_tail1->link(first_new1);
  1358. }
  1359. }
  1360. return;
  1361. }
  1362. first_run = false;
  1363. }
  1364. }
  1365. struct PointComparator {
  1366. _FORCE_INLINE_ bool operator()(const ConvexHullInternal::Point32 &p, const ConvexHullInternal::Point32 &q) const {
  1367. return (p.y < q.y) || ((p.y == q.y) && ((p.x < q.x) || ((p.x == q.x) && (p.z < q.z))));
  1368. }
  1369. };
  1370. void ConvexHullInternal::compute(const Vector3 *p_coords, int32_t p_count) {
  1371. AABB aabb;
  1372. for (int32_t i = 0; i < p_count; i++) {
  1373. Vector3 p = p_coords[i];
  1374. if (i == 0) {
  1375. aabb.position = p;
  1376. } else {
  1377. aabb.expand_to(p);
  1378. }
  1379. }
  1380. Vector3 s = aabb.size;
  1381. max_axis = s.max_axis();
  1382. min_axis = s.min_axis();
  1383. if (min_axis == max_axis) {
  1384. min_axis = (max_axis + 1) % 3;
  1385. }
  1386. med_axis = 3 - max_axis - min_axis;
  1387. s /= real_t(10216);
  1388. if (((med_axis + 1) % 3) != max_axis) {
  1389. s *= -1;
  1390. }
  1391. scaling = s;
  1392. if (s[0] != 0) {
  1393. s[0] = real_t(1) / s[0];
  1394. }
  1395. if (s[1] != 0) {
  1396. s[1] = real_t(1) / s[1];
  1397. }
  1398. if (s[2] != 0) {
  1399. s[2] = real_t(1) / s[2];
  1400. }
  1401. center = aabb.position;
  1402. LocalVector<Point32> points;
  1403. points.resize(p_count);
  1404. for (int32_t i = 0; i < p_count; i++) {
  1405. Vector3 p = p_coords[i];
  1406. p = (p - center) * s;
  1407. points[i].x = (int32_t)p[med_axis];
  1408. points[i].y = (int32_t)p[max_axis];
  1409. points[i].z = (int32_t)p[min_axis];
  1410. points[i].index = i;
  1411. }
  1412. points.sort_custom<PointComparator>();
  1413. vertex_pool.reset(true);
  1414. original_vertices.resize(p_count);
  1415. for (int32_t i = 0; i < p_count; i++) {
  1416. Vertex *v = vertex_pool.alloc();
  1417. v->edges = nullptr;
  1418. v->point = points[i];
  1419. v->copy = -1;
  1420. original_vertices[i] = v;
  1421. }
  1422. points.clear();
  1423. edge_pool.reset(true);
  1424. used_edge_pairs = 0;
  1425. max_used_edge_pairs = 0;
  1426. merge_stamp = -3;
  1427. IntermediateHull hull;
  1428. compute_internal(0, p_count, hull);
  1429. vertex_list = hull.min_xy;
  1430. #ifdef DEBUG_CONVEX_HULL
  1431. printf("max. edges %d (3v = %d)", max_used_edge_pairs, 3 * p_count);
  1432. #endif
  1433. }
  1434. Vector3 ConvexHullInternal::to_gd_vector(const Point32 &p_v) {
  1435. Vector3 p;
  1436. p[med_axis] = real_t(p_v.x);
  1437. p[max_axis] = real_t(p_v.y);
  1438. p[min_axis] = real_t(p_v.z);
  1439. return p * scaling;
  1440. }
  1441. Vector3 ConvexHullInternal::get_gd_normal(Face *p_face) {
  1442. return to_gd_vector(p_face->dir0).cross(to_gd_vector(p_face->dir1)).normalized();
  1443. }
  1444. Vector3 ConvexHullInternal::get_coordinates(const Vertex *p_v) {
  1445. Vector3 p;
  1446. p[med_axis] = p_v->xvalue();
  1447. p[max_axis] = p_v->yvalue();
  1448. p[min_axis] = p_v->zvalue();
  1449. return p * scaling + center;
  1450. }
  1451. real_t ConvexHullInternal::shrink(real_t p_amount, real_t p_clamp_amount) {
  1452. if (!vertex_list) {
  1453. return 0;
  1454. }
  1455. int32_t stamp = --merge_stamp;
  1456. LocalVector<Vertex *> stack;
  1457. vertex_list->copy = stamp;
  1458. stack.push_back(vertex_list);
  1459. LocalVector<Face *> faces;
  1460. Point32 ref = vertex_list->point;
  1461. Int128 hull_center_x(0, 0);
  1462. Int128 hull_center_y(0, 0);
  1463. Int128 hull_center_z(0, 0);
  1464. Int128 volume(0, 0);
  1465. while (stack.size() > 0) {
  1466. Vertex *v = stack[stack.size() - 1];
  1467. stack.remove(stack.size() - 1);
  1468. Edge *e = v->edges;
  1469. if (e) {
  1470. do {
  1471. if (e->target->copy != stamp) {
  1472. e->target->copy = stamp;
  1473. stack.push_back(e->target);
  1474. }
  1475. if (e->copy != stamp) {
  1476. Face *face = face_pool.alloc();
  1477. face->init(e->target, e->reverse->prev->target, v);
  1478. faces.push_back(face);
  1479. Edge *f = e;
  1480. Vertex *a = nullptr;
  1481. Vertex *b = nullptr;
  1482. do {
  1483. if (a && b) {
  1484. int64_t vol = (v->point - ref).dot((a->point - ref).cross(b->point - ref));
  1485. CHULL_ASSERT(vol >= 0);
  1486. Point32 c = v->point + a->point + b->point + ref;
  1487. hull_center_x += vol * c.x;
  1488. hull_center_y += vol * c.y;
  1489. hull_center_z += vol * c.z;
  1490. volume += vol;
  1491. }
  1492. CHULL_ASSERT(f->copy != stamp);
  1493. f->copy = stamp;
  1494. f->face = face;
  1495. a = b;
  1496. b = f->target;
  1497. f = f->reverse->prev;
  1498. } while (f != e);
  1499. }
  1500. e = e->next;
  1501. } while (e != v->edges);
  1502. }
  1503. }
  1504. if (volume.get_sign() <= 0) {
  1505. return 0;
  1506. }
  1507. Vector3 hull_center;
  1508. hull_center[med_axis] = hull_center_x.to_scalar();
  1509. hull_center[max_axis] = hull_center_y.to_scalar();
  1510. hull_center[min_axis] = hull_center_z.to_scalar();
  1511. hull_center /= 4 * volume.to_scalar();
  1512. hull_center *= scaling;
  1513. int32_t face_count = faces.size();
  1514. if (p_clamp_amount > 0) {
  1515. real_t min_dist = FLT_MAX;
  1516. for (int32_t i = 0; i < face_count; i++) {
  1517. Vector3 normal = get_gd_normal(faces[i]);
  1518. real_t dist = normal.dot(to_gd_vector(faces[i]->origin) - hull_center);
  1519. if (dist < min_dist) {
  1520. min_dist = dist;
  1521. }
  1522. }
  1523. if (min_dist <= 0) {
  1524. return 0;
  1525. }
  1526. p_amount = MIN(p_amount, min_dist * p_clamp_amount);
  1527. }
  1528. uint32_t seed = 243703;
  1529. for (int32_t i = 0; i < face_count; i++, seed = 1664525 * seed + 1013904223) {
  1530. SWAP(faces[i], faces[seed % face_count]);
  1531. }
  1532. for (int32_t i = 0; i < face_count; i++) {
  1533. if (!shift_face(faces[i], p_amount, stack)) {
  1534. return -p_amount;
  1535. }
  1536. }
  1537. return p_amount;
  1538. }
  1539. bool ConvexHullInternal::shift_face(Face *p_face, real_t p_amount, LocalVector<Vertex *> p_stack) {
  1540. Vector3 orig_shift = get_gd_normal(p_face) * -p_amount;
  1541. if (scaling[0] != 0) {
  1542. orig_shift[0] /= scaling[0];
  1543. }
  1544. if (scaling[1] != 0) {
  1545. orig_shift[1] /= scaling[1];
  1546. }
  1547. if (scaling[2] != 0) {
  1548. orig_shift[2] /= scaling[2];
  1549. }
  1550. Point32 shift((int32_t)orig_shift[med_axis], (int32_t)orig_shift[max_axis], (int32_t)orig_shift[min_axis]);
  1551. if (shift.is_zero()) {
  1552. return true;
  1553. }
  1554. Point64 normal = p_face->get_normal();
  1555. #ifdef DEBUG_CONVEX_HULL
  1556. printf("\nShrinking p_face (%d %d %d) (%d %d %d) (%d %d %d) by (%d %d %d)\n",
  1557. p_face->origin.x, p_face->origin.y, p_face->origin.z, p_face->dir0.x, p_face->dir0.y, p_face->dir0.z, p_face->dir1.x, p_face->dir1.y, p_face->dir1.z, shift.x, shift.y, shift.z);
  1558. #endif
  1559. int64_t orig_dot = p_face->origin.dot(normal);
  1560. Point32 shifted_origin = p_face->origin + shift;
  1561. int64_t shifted_dot = shifted_origin.dot(normal);
  1562. CHULL_ASSERT(shifted_dot <= orig_dot);
  1563. if (shifted_dot >= orig_dot) {
  1564. return false;
  1565. }
  1566. Edge *intersection = nullptr;
  1567. Edge *start_edge = p_face->nearby_vertex->edges;
  1568. #ifdef DEBUG_CONVEX_HULL
  1569. printf("Start edge is ");
  1570. start_edge->print();
  1571. printf(", normal is (%lld %lld %lld), shifted dot is %lld\n", normal.x, normal.y, normal.z, shifted_dot);
  1572. #endif
  1573. Rational128 opt_dot = p_face->nearby_vertex->dot(normal);
  1574. int32_t cmp = opt_dot.compare(shifted_dot);
  1575. #ifdef SHOW_ITERATIONS
  1576. int32_t n = 0;
  1577. #endif
  1578. if (cmp >= 0) {
  1579. Edge *e = start_edge;
  1580. do {
  1581. #ifdef SHOW_ITERATIONS
  1582. n++;
  1583. #endif
  1584. Rational128 dot = e->target->dot(normal);
  1585. CHULL_ASSERT(dot.compare(orig_dot) <= 0);
  1586. #ifdef DEBUG_CONVEX_HULL
  1587. printf("Moving downwards, edge is ");
  1588. e->print();
  1589. printf(", dot is %f (%f %lld)\n", (float)dot.to_scalar(), (float)opt_dot.to_scalar(), shifted_dot);
  1590. #endif
  1591. if (dot.compare(opt_dot) < 0) {
  1592. int32_t c = dot.compare(shifted_dot);
  1593. opt_dot = dot;
  1594. e = e->reverse;
  1595. start_edge = e;
  1596. if (c < 0) {
  1597. intersection = e;
  1598. break;
  1599. }
  1600. cmp = c;
  1601. }
  1602. e = e->prev;
  1603. } while (e != start_edge);
  1604. if (!intersection) {
  1605. return false;
  1606. }
  1607. } else {
  1608. Edge *e = start_edge;
  1609. do {
  1610. #ifdef SHOW_ITERATIONS
  1611. n++;
  1612. #endif
  1613. Rational128 dot = e->target->dot(normal);
  1614. CHULL_ASSERT(dot.compare(orig_dot) <= 0);
  1615. #ifdef DEBUG_CONVEX_HULL
  1616. printf("Moving upwards, edge is ");
  1617. e->print();
  1618. printf(", dot is %f (%f %lld)\n", (float)dot.to_scalar(), (float)opt_dot.to_scalar(), shifted_dot);
  1619. #endif
  1620. if (dot.compare(opt_dot) > 0) {
  1621. cmp = dot.compare(shifted_dot);
  1622. if (cmp >= 0) {
  1623. intersection = e;
  1624. break;
  1625. }
  1626. opt_dot = dot;
  1627. e = e->reverse;
  1628. start_edge = e;
  1629. }
  1630. e = e->prev;
  1631. } while (e != start_edge);
  1632. if (!intersection) {
  1633. return true;
  1634. }
  1635. }
  1636. #ifdef SHOW_ITERATIONS
  1637. printf("Needed %d iterations to find initial intersection\n", n);
  1638. #endif
  1639. if (cmp == 0) {
  1640. Edge *e = intersection->reverse->next;
  1641. #ifdef SHOW_ITERATIONS
  1642. n = 0;
  1643. #endif
  1644. while (e->target->dot(normal).compare(shifted_dot) <= 0) {
  1645. #ifdef SHOW_ITERATIONS
  1646. n++;
  1647. #endif
  1648. e = e->next;
  1649. if (e == intersection->reverse) {
  1650. return true;
  1651. }
  1652. #ifdef DEBUG_CONVEX_HULL
  1653. printf("Checking for outwards edge, current edge is ");
  1654. e->print();
  1655. printf("\n");
  1656. #endif
  1657. }
  1658. #ifdef SHOW_ITERATIONS
  1659. printf("Needed %d iterations to check for complete containment\n", n);
  1660. #endif
  1661. }
  1662. Edge *first_intersection = nullptr;
  1663. Edge *face_edge = nullptr;
  1664. Edge *first_face_edge = nullptr;
  1665. #ifdef SHOW_ITERATIONS
  1666. int32_t m = 0;
  1667. #endif
  1668. while (true) {
  1669. #ifdef SHOW_ITERATIONS
  1670. m++;
  1671. #endif
  1672. #ifdef DEBUG_CONVEX_HULL
  1673. printf("Intersecting edge is ");
  1674. intersection->print();
  1675. printf("\n");
  1676. #endif
  1677. if (cmp == 0) {
  1678. Edge *e = intersection->reverse->next;
  1679. start_edge = e;
  1680. #ifdef SHOW_ITERATIONS
  1681. n = 0;
  1682. #endif
  1683. while (true) {
  1684. #ifdef SHOW_ITERATIONS
  1685. n++;
  1686. #endif
  1687. if (e->target->dot(normal).compare(shifted_dot) >= 0) {
  1688. break;
  1689. }
  1690. intersection = e->reverse;
  1691. e = e->next;
  1692. if (e == start_edge) {
  1693. return true;
  1694. }
  1695. }
  1696. #ifdef SHOW_ITERATIONS
  1697. printf("Needed %d iterations to advance intersection\n", n);
  1698. #endif
  1699. }
  1700. #ifdef DEBUG_CONVEX_HULL
  1701. printf("Advanced intersecting edge to ");
  1702. intersection->print();
  1703. printf(", cmp = %d\n", cmp);
  1704. #endif
  1705. if (!first_intersection) {
  1706. first_intersection = intersection;
  1707. } else if (intersection == first_intersection) {
  1708. break;
  1709. }
  1710. int32_t prev_cmp = cmp;
  1711. Edge *prev_intersection = intersection;
  1712. Edge *prev_face_edge = face_edge;
  1713. Edge *e = intersection->reverse;
  1714. #ifdef SHOW_ITERATIONS
  1715. n = 0;
  1716. #endif
  1717. while (true) {
  1718. #ifdef SHOW_ITERATIONS
  1719. n++;
  1720. #endif
  1721. e = e->reverse->prev;
  1722. CHULL_ASSERT(e != intersection->reverse);
  1723. cmp = e->target->dot(normal).compare(shifted_dot);
  1724. #ifdef DEBUG_CONVEX_HULL
  1725. printf("Testing edge ");
  1726. e->print();
  1727. printf(" -> cmp = %d\n", cmp);
  1728. #endif
  1729. if (cmp >= 0) {
  1730. intersection = e;
  1731. break;
  1732. }
  1733. }
  1734. #ifdef SHOW_ITERATIONS
  1735. printf("Needed %d iterations to find other intersection of p_face\n", n);
  1736. #endif
  1737. if (cmp > 0) {
  1738. Vertex *removed = intersection->target;
  1739. e = intersection->reverse;
  1740. if (e->prev == e) {
  1741. removed->edges = nullptr;
  1742. } else {
  1743. removed->edges = e->prev;
  1744. e->prev->link(e->next);
  1745. e->link(e);
  1746. }
  1747. #ifdef DEBUG_CONVEX_HULL
  1748. printf("1: Removed part contains (%d %d %d)\n", removed->point.x, removed->point.y, removed->point.z);
  1749. #endif
  1750. Point64 n0 = intersection->face->get_normal();
  1751. Point64 n1 = intersection->reverse->face->get_normal();
  1752. int64_t m00 = p_face->dir0.dot(n0);
  1753. int64_t m01 = p_face->dir1.dot(n0);
  1754. int64_t m10 = p_face->dir0.dot(n1);
  1755. int64_t m11 = p_face->dir1.dot(n1);
  1756. int64_t r0 = (intersection->face->origin - shifted_origin).dot(n0);
  1757. int64_t r1 = (intersection->reverse->face->origin - shifted_origin).dot(n1);
  1758. Int128 det = Int128::mul(m00, m11) - Int128::mul(m01, m10);
  1759. CHULL_ASSERT(det.get_sign() != 0);
  1760. Vertex *v = vertex_pool.alloc();
  1761. v->point.index = -1;
  1762. v->copy = -1;
  1763. v->point128 = PointR128(Int128::mul(p_face->dir0.x * r0, m11) - Int128::mul(p_face->dir0.x * r1, m01) + Int128::mul(p_face->dir1.x * r1, m00) - Int128::mul(p_face->dir1.x * r0, m10) + det * shifted_origin.x,
  1764. Int128::mul(p_face->dir0.y * r0, m11) - Int128::mul(p_face->dir0.y * r1, m01) + Int128::mul(p_face->dir1.y * r1, m00) - Int128::mul(p_face->dir1.y * r0, m10) + det * shifted_origin.y,
  1765. Int128::mul(p_face->dir0.z * r0, m11) - Int128::mul(p_face->dir0.z * r1, m01) + Int128::mul(p_face->dir1.z * r1, m00) - Int128::mul(p_face->dir1.z * r0, m10) + det * shifted_origin.z,
  1766. det);
  1767. v->point.x = (int32_t)v->point128.xvalue();
  1768. v->point.y = (int32_t)v->point128.yvalue();
  1769. v->point.z = (int32_t)v->point128.zvalue();
  1770. intersection->target = v;
  1771. v->edges = e;
  1772. p_stack.push_back(v);
  1773. p_stack.push_back(removed);
  1774. p_stack.push_back(nullptr);
  1775. }
  1776. if (cmp || prev_cmp || (prev_intersection->reverse->next->target != intersection->target)) {
  1777. face_edge = new_edge_pair(prev_intersection->target, intersection->target);
  1778. if (prev_cmp == 0) {
  1779. face_edge->link(prev_intersection->reverse->next);
  1780. }
  1781. if ((prev_cmp == 0) || prev_face_edge) {
  1782. prev_intersection->reverse->link(face_edge);
  1783. }
  1784. if (cmp == 0) {
  1785. intersection->reverse->prev->link(face_edge->reverse);
  1786. }
  1787. face_edge->reverse->link(intersection->reverse);
  1788. } else {
  1789. face_edge = prev_intersection->reverse->next;
  1790. }
  1791. if (prev_face_edge) {
  1792. if (prev_cmp > 0) {
  1793. face_edge->link(prev_face_edge->reverse);
  1794. } else if (face_edge != prev_face_edge->reverse) {
  1795. p_stack.push_back(prev_face_edge->target);
  1796. while (face_edge->next != prev_face_edge->reverse) {
  1797. Vertex *removed = face_edge->next->target;
  1798. remove_edge_pair(face_edge->next);
  1799. p_stack.push_back(removed);
  1800. #ifdef DEBUG_CONVEX_HULL
  1801. printf("2: Removed part contains (%d %d %d)\n", removed->point.x, removed->point.y, removed->point.z);
  1802. #endif
  1803. }
  1804. p_stack.push_back(nullptr);
  1805. }
  1806. }
  1807. face_edge->face = p_face;
  1808. face_edge->reverse->face = intersection->face;
  1809. if (!first_face_edge) {
  1810. first_face_edge = face_edge;
  1811. }
  1812. }
  1813. #ifdef SHOW_ITERATIONS
  1814. printf("Needed %d iterations to process all intersections\n", m);
  1815. #endif
  1816. if (cmp > 0) {
  1817. first_face_edge->reverse->target = face_edge->target;
  1818. first_intersection->reverse->link(first_face_edge);
  1819. first_face_edge->link(face_edge->reverse);
  1820. } else if (first_face_edge != face_edge->reverse) {
  1821. p_stack.push_back(face_edge->target);
  1822. while (first_face_edge->next != face_edge->reverse) {
  1823. Vertex *removed = first_face_edge->next->target;
  1824. remove_edge_pair(first_face_edge->next);
  1825. p_stack.push_back(removed);
  1826. #ifdef DEBUG_CONVEX_HULL
  1827. printf("3: Removed part contains (%d %d %d)\n", removed->point.x, removed->point.y, removed->point.z);
  1828. #endif
  1829. }
  1830. p_stack.push_back(nullptr);
  1831. }
  1832. CHULL_ASSERT(p_stack.size() > 0);
  1833. vertex_list = p_stack[0];
  1834. #ifdef DEBUG_CONVEX_HULL
  1835. printf("Removing part\n");
  1836. #endif
  1837. #ifdef SHOW_ITERATIONS
  1838. n = 0;
  1839. #endif
  1840. uint32_t pos = 0;
  1841. while (pos < p_stack.size()) {
  1842. uint32_t end = p_stack.size();
  1843. while (pos < end) {
  1844. Vertex *kept = p_stack[pos++];
  1845. #ifdef DEBUG_CONVEX_HULL
  1846. kept->print();
  1847. #endif
  1848. bool deeper = false;
  1849. Vertex *removed;
  1850. while ((removed = p_stack[pos++]) != nullptr) {
  1851. #ifdef SHOW_ITERATIONS
  1852. n++;
  1853. #endif
  1854. kept->receive_nearby_faces(removed);
  1855. while (removed->edges) {
  1856. if (!deeper) {
  1857. deeper = true;
  1858. p_stack.push_back(kept);
  1859. }
  1860. p_stack.push_back(removed->edges->target);
  1861. remove_edge_pair(removed->edges);
  1862. }
  1863. }
  1864. if (deeper) {
  1865. p_stack.push_back(nullptr);
  1866. }
  1867. }
  1868. }
  1869. #ifdef SHOW_ITERATIONS
  1870. printf("Needed %d iterations to remove part\n", n);
  1871. #endif
  1872. p_stack.resize(0);
  1873. p_face->origin = shifted_origin;
  1874. return true;
  1875. }
  1876. static int32_t get_vertex_copy(ConvexHullInternal::Vertex *p_vertex, LocalVector<ConvexHullInternal::Vertex *> &p_vertices) {
  1877. int32_t index = p_vertex->copy;
  1878. if (index < 0) {
  1879. index = p_vertices.size();
  1880. p_vertex->copy = index;
  1881. p_vertices.push_back(p_vertex);
  1882. #ifdef DEBUG_CONVEX_HULL
  1883. printf("Vertex %d gets index *%d\n", p_vertex->point.index, index);
  1884. #endif
  1885. }
  1886. return index;
  1887. }
  1888. real_t ConvexHullComputer::compute(const Vector3 *p_coords, int32_t p_count, real_t p_shrink, real_t p_shrink_clamp) {
  1889. if (p_count <= 0) {
  1890. vertices.clear();
  1891. edges.clear();
  1892. faces.clear();
  1893. return 0;
  1894. }
  1895. ConvexHullInternal hull;
  1896. hull.compute(p_coords, p_count);
  1897. real_t shift = 0;
  1898. if ((p_shrink > 0) && ((shift = hull.shrink(p_shrink, p_shrink_clamp)) < 0)) {
  1899. vertices.clear();
  1900. edges.clear();
  1901. faces.clear();
  1902. return shift;
  1903. }
  1904. vertices.resize(0);
  1905. edges.resize(0);
  1906. faces.resize(0);
  1907. LocalVector<ConvexHullInternal::Vertex *> old_vertices;
  1908. get_vertex_copy(hull.vertex_list, old_vertices);
  1909. int32_t copied = 0;
  1910. while (copied < (int32_t)old_vertices.size()) {
  1911. ConvexHullInternal::Vertex *v = old_vertices[copied];
  1912. vertices.push_back(hull.get_coordinates(v));
  1913. ConvexHullInternal::Edge *first_edge = v->edges;
  1914. if (first_edge) {
  1915. int32_t first_copy = -1;
  1916. int32_t prev_copy = -1;
  1917. ConvexHullInternal::Edge *e = first_edge;
  1918. do {
  1919. if (e->copy < 0) {
  1920. int32_t s = edges.size();
  1921. edges.push_back(Edge());
  1922. edges.push_back(Edge());
  1923. Edge *c = &edges[s];
  1924. Edge *r = &edges[s + 1];
  1925. e->copy = s;
  1926. e->reverse->copy = s + 1;
  1927. c->reverse = 1;
  1928. r->reverse = -1;
  1929. c->target_vertex = get_vertex_copy(e->target, old_vertices);
  1930. r->target_vertex = copied;
  1931. #ifdef DEBUG_CONVEX_HULL
  1932. printf(" CREATE: Vertex *%d has edge to *%d\n", copied, c->get_target_vertex());
  1933. #endif
  1934. }
  1935. if (prev_copy >= 0) {
  1936. edges[e->copy].next = prev_copy - e->copy;
  1937. } else {
  1938. first_copy = e->copy;
  1939. }
  1940. prev_copy = e->copy;
  1941. e = e->next;
  1942. } while (e != first_edge);
  1943. edges[first_copy].next = prev_copy - first_copy;
  1944. }
  1945. copied++;
  1946. }
  1947. for (int32_t i = 0; i < copied; i++) {
  1948. ConvexHullInternal::Vertex *v = old_vertices[i];
  1949. ConvexHullInternal::Edge *first_edge = v->edges;
  1950. if (first_edge) {
  1951. ConvexHullInternal::Edge *e = first_edge;
  1952. do {
  1953. if (e->copy >= 0) {
  1954. #ifdef DEBUG_CONVEX_HULL
  1955. printf("Vertex *%d has edge to *%d\n", i, edges[e->copy].get_target_vertex());
  1956. #endif
  1957. faces.push_back(e->copy);
  1958. ConvexHullInternal::Edge *f = e;
  1959. do {
  1960. #ifdef DEBUG_CONVEX_HULL
  1961. printf(" Face *%d\n", edges[f->copy].get_target_vertex());
  1962. #endif
  1963. f->copy = -1;
  1964. f = f->reverse->prev;
  1965. } while (f != e);
  1966. }
  1967. e = e->next;
  1968. } while (e != first_edge);
  1969. }
  1970. }
  1971. return shift;
  1972. }
  1973. Error ConvexHullComputer::convex_hull(const Vector<Vector3> &p_points, Geometry::MeshData &r_mesh) {
  1974. return convex_hull(p_points.ptr(), p_points.size(), r_mesh);
  1975. }
  1976. Error ConvexHullComputer::convex_hull(const PoolVector<Vector3> &p_points, Geometry::MeshData &r_mesh) {
  1977. return convex_hull(p_points.read().ptr(), p_points.size(), r_mesh);
  1978. }
  1979. Error ConvexHullComputer::convex_hull(const Vector3 *p_points, int32_t p_point_count, Geometry::MeshData &r_mesh) {
  1980. r_mesh = Geometry::MeshData(); // clear
  1981. if (p_point_count == 0) {
  1982. return FAILED; // matches QuickHull
  1983. }
  1984. ConvexHullComputer ch;
  1985. ch.compute(p_points, p_point_count, -1.0, -1.0);
  1986. r_mesh.vertices = ch.vertices;
  1987. // Copy the edges over. There's two "half-edges" for every edge, so we pick only one of them.
  1988. r_mesh.edges.resize(ch.edges.size() / 2);
  1989. uint32_t edges_copied = 0;
  1990. for (uint32_t i = 0; i < ch.edges.size(); i++) {
  1991. uint32_t a = (&ch.edges[i])->get_source_vertex();
  1992. uint32_t b = (&ch.edges[i])->get_target_vertex();
  1993. if (a < b) { // Copy only the "canonical" edge. For the reverse edge, this will be false.
  1994. ERR_BREAK(edges_copied >= (uint32_t)r_mesh.edges.size());
  1995. r_mesh.edges.write[edges_copied].a = a;
  1996. r_mesh.edges.write[edges_copied].b = b;
  1997. edges_copied++;
  1998. }
  1999. }
  2000. if (edges_copied != (uint32_t)r_mesh.edges.size()) {
  2001. ERR_PRINT("Invalid edge count.");
  2002. }
  2003. r_mesh.faces.resize(ch.faces.size());
  2004. for (uint32_t i = 0; i < ch.faces.size(); i++) {
  2005. const Edge *e_start = &ch.edges[ch.faces[i]];
  2006. const Edge *e = e_start;
  2007. Geometry::MeshData::Face &face = r_mesh.faces.write[i];
  2008. do {
  2009. face.indices.push_back(e->get_target_vertex());
  2010. e = e->get_next_edge_of_face();
  2011. } while (e != e_start);
  2012. // reverse indices: Godot wants clockwise, but this is counter-clockwise
  2013. if (face.indices.size() > 2) {
  2014. // reverse all but the first index.
  2015. int *indices = face.indices.ptrw();
  2016. for (int c = 0; c < (face.indices.size() - 1) / 2; c++) {
  2017. SWAP(indices[c + 1], indices[face.indices.size() - 1 - c]);
  2018. }
  2019. }
  2020. // compute normal
  2021. if (face.indices.size() >= 3) {
  2022. face.plane = Plane(r_mesh.vertices[face.indices[0]], r_mesh.vertices[face.indices[1]], r_mesh.vertices[face.indices[2]]);
  2023. } else {
  2024. WARN_PRINT("Too few vertices per face.");
  2025. }
  2026. }
  2027. return OK;
  2028. }