convex_hull.cpp 58 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272227322742275227622772278227922802281228222832284228522862287228822892290229122922293229422952296229722982299230023012302230323042305230623072308230923102311
  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. void print();
  505. };
  506. enum Orientation { NONE,
  507. CLOCKWISE,
  508. COUNTER_CLOCKWISE };
  509. Vector3 scaling;
  510. Vector3 center;
  511. PagedAllocator<Vertex> vertex_pool;
  512. PagedAllocator<Edge> edge_pool;
  513. PagedAllocator<Face> face_pool;
  514. LocalVector<Vertex *> original_vertices;
  515. int32_t merge_stamp = 0;
  516. int32_t min_axis = 0;
  517. int32_t med_axis = 0;
  518. int32_t max_axis = 0;
  519. int32_t used_edge_pairs = 0;
  520. int32_t max_used_edge_pairs = 0;
  521. static Orientation get_orientation(const Edge *p_prev, const Edge *p_next, const Point32 &p_s, const Point32 &p_t);
  522. 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);
  523. void find_edge_for_coplanar_faces(Vertex *p_c0, Vertex *p_c1, Edge *&p_e0, Edge *&p_e1, Vertex *p_stop0, Vertex *p_stop1);
  524. Edge *new_edge_pair(Vertex *p_from, Vertex *p_to);
  525. void remove_edge_pair(Edge *p_edge) {
  526. Edge *n = p_edge->next;
  527. Edge *r = p_edge->reverse;
  528. CHULL_ASSERT(p_edge->target && r->target);
  529. if (n != p_edge) {
  530. n->prev = p_edge->prev;
  531. p_edge->prev->next = n;
  532. r->target->edges = n;
  533. } else {
  534. r->target->edges = nullptr;
  535. }
  536. n = r->next;
  537. if (n != r) {
  538. n->prev = r->prev;
  539. r->prev->next = n;
  540. p_edge->target->edges = n;
  541. } else {
  542. p_edge->target->edges = nullptr;
  543. }
  544. edge_pool.free(p_edge);
  545. edge_pool.free(r);
  546. used_edge_pairs--;
  547. }
  548. void compute_internal(int32_t p_start, int32_t p_end, IntermediateHull &r_result);
  549. bool merge_projection(IntermediateHull &p_h0, IntermediateHull &p_h1, Vertex *&r_c0, Vertex *&r_c1);
  550. void merge(IntermediateHull &p_h0, IntermediateHull &p_h1);
  551. Vector3 to_gd_vector(const Point32 &p_v);
  552. Vector3 get_gd_normal(Face *p_face);
  553. bool shift_face(Face *p_face, real_t p_amount, LocalVector<Vertex *> p_stack);
  554. public:
  555. ~ConvexHullInternal() {
  556. vertex_pool.reset(true);
  557. edge_pool.reset(true);
  558. face_pool.reset(true);
  559. }
  560. Vertex *vertex_list;
  561. void compute(const Vector3 *p_coords, int32_t p_count);
  562. Vector3 get_coordinates(const Vertex *p_v);
  563. real_t shrink(real_t amount, real_t p_clamp_amount);
  564. };
  565. ConvexHullInternal::Int128 ConvexHullInternal::Int128::operator*(int64_t b) const {
  566. bool negative = (int64_t)high < 0;
  567. Int128 a = negative ? -*this : *this;
  568. if (b < 0) {
  569. negative = !negative;
  570. b = -b;
  571. }
  572. Int128 result = mul(a.low, (uint64_t)b);
  573. result.high += a.high * (uint64_t)b;
  574. return negative ? -result : result;
  575. }
  576. ConvexHullInternal::Int128 ConvexHullInternal::Int128::mul(int64_t a, int64_t b) {
  577. Int128 result;
  578. #ifdef USE_X86_64_ASM
  579. __asm__("imulq %[b]"
  580. : "=a"(result.low), "=d"(result.high)
  581. : "0"(a), [b] "r"(b)
  582. : "cc");
  583. return result;
  584. #else
  585. bool negative = a < 0;
  586. if (negative) {
  587. a = -a;
  588. }
  589. if (b < 0) {
  590. negative = !negative;
  591. b = -b;
  592. }
  593. DMul<uint64_t, uint32_t>::mul((uint64_t)a, (uint64_t)b, result.low, result.high);
  594. return negative ? -result : result;
  595. #endif
  596. }
  597. ConvexHullInternal::Int128 ConvexHullInternal::Int128::mul(uint64_t a, uint64_t b) {
  598. Int128 result;
  599. #ifdef USE_X86_64_ASM
  600. __asm__("mulq %[b]"
  601. : "=a"(result.low), "=d"(result.high)
  602. : "0"(a), [b] "r"(b)
  603. : "cc");
  604. #else
  605. DMul<uint64_t, uint32_t>::mul(a, b, result.low, result.high);
  606. #endif
  607. return result;
  608. }
  609. int32_t ConvexHullInternal::Rational64::compare(const Rational64 &b) const {
  610. if (sign != b.sign) {
  611. return sign - b.sign;
  612. } else if (sign == 0) {
  613. return 0;
  614. }
  615. #ifdef USE_X86_64_ASM
  616. int32_t result;
  617. int64_t tmp;
  618. int64_t dummy;
  619. __asm__("mulq %[bn]\n\t"
  620. "movq %%rax, %[tmp]\n\t"
  621. "movq %%rdx, %%rbx\n\t"
  622. "movq %[tn], %%rax\n\t"
  623. "mulq %[bd]\n\t"
  624. "subq %[tmp], %%rax\n\t"
  625. "sbbq %%rbx, %%rdx\n\t" // rdx:rax contains 128-bit-difference "numerator*b.denominator - b.numerator*denominator"
  626. "setnsb %%bh\n\t" // bh=1 if difference is non-negative, bh=0 otherwise
  627. "orq %%rdx, %%rax\n\t"
  628. "setnzb %%bl\n\t" // bl=1 if difference if non-zero, bl=0 if it is zero
  629. "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)
  630. "shll $16, %%ebx\n\t" // ebx has same sign as difference
  631. : "=&b"(result), [tmp] "=&r"(tmp), "=a"(dummy)
  632. : "a"(denominator), [bn] "g"(b.numerator), [tn] "g"(numerator), [bd] "g"(b.denominator)
  633. : "%rdx", "cc");
  634. // if sign is +1, only bit 0 of result is inverted, which does not change the sign of result (and cannot result in zero)
  635. // if sign is -1, all bits of result are inverted, which changes the sign of result (and again cannot result in zero)
  636. return result ? result ^ sign : 0;
  637. #else
  638. return sign * Int128::mul(numerator, b.denominator).ucmp(Int128::mul(denominator, b.numerator));
  639. #endif
  640. }
  641. int32_t ConvexHullInternal::Rational128::compare(const Rational128 &b) const {
  642. if (sign != b.sign) {
  643. return sign - b.sign;
  644. } else if (sign == 0) {
  645. return 0;
  646. }
  647. if (is_int_64) {
  648. return -b.compare(sign * (int64_t)numerator.low);
  649. }
  650. Int128 nbd_low, nbd_high, dbn_low, dbn_high;
  651. DMul<Int128, uint64_t>::mul(numerator, b.denominator, nbd_low, nbd_high);
  652. DMul<Int128, uint64_t>::mul(denominator, b.numerator, dbn_low, dbn_high);
  653. int32_t cmp = nbd_high.ucmp(dbn_high);
  654. if (cmp) {
  655. return cmp * sign;
  656. }
  657. return nbd_low.ucmp(dbn_low) * sign;
  658. }
  659. int32_t ConvexHullInternal::Rational128::compare(int64_t b) const {
  660. if (is_int_64) {
  661. int64_t a = sign * (int64_t)numerator.low;
  662. return (a > b) ? 1 : ((a < b) ? -1 : 0);
  663. }
  664. if (b > 0) {
  665. if (sign <= 0) {
  666. return -1;
  667. }
  668. } else if (b < 0) {
  669. if (sign >= 0) {
  670. return 1;
  671. }
  672. b = -b;
  673. } else {
  674. return sign;
  675. }
  676. return numerator.ucmp(denominator * b) * sign;
  677. }
  678. ConvexHullInternal::Edge *ConvexHullInternal::new_edge_pair(Vertex *p_from, Vertex *p_to) {
  679. CHULL_ASSERT(p_from && p_to);
  680. Edge *e = edge_pool.alloc();
  681. Edge *r = edge_pool.alloc();
  682. e->reverse = r;
  683. r->reverse = e;
  684. e->copy = merge_stamp;
  685. r->copy = merge_stamp;
  686. e->target = p_to;
  687. r->target = p_from;
  688. e->face = nullptr;
  689. r->face = nullptr;
  690. used_edge_pairs++;
  691. if (used_edge_pairs > max_used_edge_pairs) {
  692. max_used_edge_pairs = used_edge_pairs;
  693. }
  694. return e;
  695. }
  696. bool ConvexHullInternal::merge_projection(IntermediateHull &r_h0, IntermediateHull &r_h1, Vertex *&r_c0, Vertex *&r_c1) {
  697. Vertex *v0 = r_h0.max_yx;
  698. Vertex *v1 = r_h1.min_yx;
  699. if ((v0->point.x == v1->point.x) && (v0->point.y == v1->point.y)) {
  700. CHULL_ASSERT(v0->point.z < v1->point.z);
  701. Vertex *v1p = v1->prev;
  702. if (v1p == v1) {
  703. r_c0 = v0;
  704. if (v1->edges) {
  705. CHULL_ASSERT(v1->edges->next == v1->edges);
  706. v1 = v1->edges->target;
  707. CHULL_ASSERT(v1->edges->next == v1->edges);
  708. }
  709. r_c1 = v1;
  710. return false;
  711. }
  712. Vertex *v1n = v1->next;
  713. v1p->next = v1n;
  714. v1n->prev = v1p;
  715. if (v1 == r_h1.min_xy) {
  716. if ((v1n->point.x < v1p->point.x) || ((v1n->point.x == v1p->point.x) && (v1n->point.y < v1p->point.y))) {
  717. r_h1.min_xy = v1n;
  718. } else {
  719. r_h1.min_xy = v1p;
  720. }
  721. }
  722. if (v1 == r_h1.max_xy) {
  723. if ((v1n->point.x > v1p->point.x) || ((v1n->point.x == v1p->point.x) && (v1n->point.y > v1p->point.y))) {
  724. r_h1.max_xy = v1n;
  725. } else {
  726. r_h1.max_xy = v1p;
  727. }
  728. }
  729. }
  730. v0 = r_h0.max_xy;
  731. v1 = r_h1.max_xy;
  732. Vertex *v00 = nullptr;
  733. Vertex *v10 = nullptr;
  734. int32_t sign = 1;
  735. for (int32_t side = 0; side <= 1; side++) {
  736. int32_t dx = (v1->point.x - v0->point.x) * sign;
  737. if (dx > 0) {
  738. while (true) {
  739. int32_t dy = v1->point.y - v0->point.y;
  740. Vertex *w0 = side ? v0->next : v0->prev;
  741. if (w0 != v0) {
  742. int32_t dx0 = (w0->point.x - v0->point.x) * sign;
  743. int32_t dy0 = w0->point.y - v0->point.y;
  744. if ((dy0 <= 0) && ((dx0 == 0) || ((dx0 < 0) && (dy0 * dx <= dy * dx0)))) {
  745. v0 = w0;
  746. dx = (v1->point.x - v0->point.x) * sign;
  747. continue;
  748. }
  749. }
  750. Vertex *w1 = side ? v1->next : v1->prev;
  751. if (w1 != v1) {
  752. int32_t dx1 = (w1->point.x - v1->point.x) * sign;
  753. int32_t dy1 = w1->point.y - v1->point.y;
  754. int32_t dxn = (w1->point.x - v0->point.x) * sign;
  755. if ((dxn > 0) && (dy1 < 0) && ((dx1 == 0) || ((dx1 < 0) && (dy1 * dx < dy * dx1)))) {
  756. v1 = w1;
  757. dx = dxn;
  758. continue;
  759. }
  760. }
  761. break;
  762. }
  763. } else if (dx < 0) {
  764. while (true) {
  765. int32_t dy = v1->point.y - v0->point.y;
  766. Vertex *w1 = side ? v1->prev : v1->next;
  767. if (w1 != v1) {
  768. int32_t dx1 = (w1->point.x - v1->point.x) * sign;
  769. int32_t dy1 = w1->point.y - v1->point.y;
  770. if ((dy1 >= 0) && ((dx1 == 0) || ((dx1 < 0) && (dy1 * dx <= dy * dx1)))) {
  771. v1 = w1;
  772. dx = (v1->point.x - v0->point.x) * sign;
  773. continue;
  774. }
  775. }
  776. Vertex *w0 = side ? v0->prev : v0->next;
  777. if (w0 != v0) {
  778. int32_t dx0 = (w0->point.x - v0->point.x) * sign;
  779. int32_t dy0 = w0->point.y - v0->point.y;
  780. int32_t dxn = (v1->point.x - w0->point.x) * sign;
  781. if ((dxn < 0) && (dy0 > 0) && ((dx0 == 0) || ((dx0 < 0) && (dy0 * dx < dy * dx0)))) {
  782. v0 = w0;
  783. dx = dxn;
  784. continue;
  785. }
  786. }
  787. break;
  788. }
  789. } else {
  790. int32_t x = v0->point.x;
  791. int32_t y0 = v0->point.y;
  792. Vertex *w0 = v0;
  793. Vertex *t;
  794. while (((t = side ? w0->next : w0->prev) != v0) && (t->point.x == x) && (t->point.y <= y0)) {
  795. w0 = t;
  796. y0 = t->point.y;
  797. }
  798. v0 = w0;
  799. int32_t y1 = v1->point.y;
  800. Vertex *w1 = v1;
  801. while (((t = side ? w1->prev : w1->next) != v1) && (t->point.x == x) && (t->point.y >= y1)) {
  802. w1 = t;
  803. y1 = t->point.y;
  804. }
  805. v1 = w1;
  806. }
  807. if (side == 0) {
  808. v00 = v0;
  809. v10 = v1;
  810. v0 = r_h0.min_xy;
  811. v1 = r_h1.min_xy;
  812. sign = -1;
  813. }
  814. }
  815. v0->prev = v1;
  816. v1->next = v0;
  817. v00->next = v10;
  818. v10->prev = v00;
  819. if (r_h1.min_xy->point.x < r_h0.min_xy->point.x) {
  820. r_h0.min_xy = r_h1.min_xy;
  821. }
  822. if (r_h1.max_xy->point.x >= r_h0.max_xy->point.x) {
  823. r_h0.max_xy = r_h1.max_xy;
  824. }
  825. r_h0.max_yx = r_h1.max_yx;
  826. r_c0 = v00;
  827. r_c1 = v10;
  828. return true;
  829. }
  830. void ConvexHullInternal::compute_internal(int32_t p_start, int32_t p_end, IntermediateHull &r_result) {
  831. int32_t n = p_end - p_start;
  832. switch (n) {
  833. case 0:
  834. r_result.min_xy = nullptr;
  835. r_result.max_xy = nullptr;
  836. r_result.min_yx = nullptr;
  837. r_result.max_yx = nullptr;
  838. return;
  839. case 2: {
  840. Vertex *v = original_vertices[p_start];
  841. Vertex *w = original_vertices[p_start + 1];
  842. if (v->point != w->point) {
  843. int32_t dx = v->point.x - w->point.x;
  844. int32_t dy = v->point.y - w->point.y;
  845. if ((dx == 0) && (dy == 0)) {
  846. if (v->point.z > w->point.z) {
  847. Vertex *t = w;
  848. w = v;
  849. v = t;
  850. }
  851. CHULL_ASSERT(v->point.z < w->point.z);
  852. v->next = v;
  853. v->prev = v;
  854. r_result.min_xy = v;
  855. r_result.max_xy = v;
  856. r_result.min_yx = v;
  857. r_result.max_yx = v;
  858. } else {
  859. v->next = w;
  860. v->prev = w;
  861. w->next = v;
  862. w->prev = v;
  863. if ((dx < 0) || ((dx == 0) && (dy < 0))) {
  864. r_result.min_xy = v;
  865. r_result.max_xy = w;
  866. } else {
  867. r_result.min_xy = w;
  868. r_result.max_xy = v;
  869. }
  870. if ((dy < 0) || ((dy == 0) && (dx < 0))) {
  871. r_result.min_yx = v;
  872. r_result.max_yx = w;
  873. } else {
  874. r_result.min_yx = w;
  875. r_result.max_yx = v;
  876. }
  877. }
  878. Edge *e = new_edge_pair(v, w);
  879. e->link(e);
  880. v->edges = e;
  881. e = e->reverse;
  882. e->link(e);
  883. w->edges = e;
  884. return;
  885. }
  886. FALLTHROUGH;
  887. }
  888. case 1: {
  889. Vertex *v = original_vertices[p_start];
  890. v->edges = nullptr;
  891. v->next = v;
  892. v->prev = v;
  893. r_result.min_xy = v;
  894. r_result.max_xy = v;
  895. r_result.min_yx = v;
  896. r_result.max_yx = v;
  897. return;
  898. }
  899. }
  900. int32_t split0 = p_start + n / 2;
  901. Point32 p = original_vertices[split0 - 1]->point;
  902. int32_t split1 = split0;
  903. while ((split1 < p_end) && (original_vertices[split1]->point == p)) {
  904. split1++;
  905. }
  906. compute_internal(p_start, split0, r_result);
  907. IntermediateHull hull1;
  908. compute_internal(split1, p_end, hull1);
  909. #ifdef DEBUG_CONVEX_HULL
  910. printf("\n\nMerge\n");
  911. r_result.print();
  912. hull1.print();
  913. #endif
  914. merge(r_result, hull1);
  915. #ifdef DEBUG_CONVEX_HULL
  916. printf("\n Result\n");
  917. r_result.print();
  918. #endif
  919. }
  920. #ifdef DEBUG_CONVEX_HULL
  921. void ConvexHullInternal::IntermediateHull::print() {
  922. printf(" Hull\n");
  923. for (Vertex *v = min_xy; v;) {
  924. printf(" ");
  925. v->print();
  926. if (v == max_xy) {
  927. printf(" max_xy");
  928. }
  929. if (v == min_yx) {
  930. printf(" min_yx");
  931. }
  932. if (v == max_yx) {
  933. printf(" max_yx");
  934. }
  935. if (v->next->prev != v) {
  936. printf(" Inconsistency");
  937. }
  938. printf("\n");
  939. v = v->next;
  940. if (v == min_xy) {
  941. break;
  942. }
  943. }
  944. if (min_xy) {
  945. min_xy->copy = (min_xy->copy == -1) ? -2 : -1;
  946. min_xy->print_graph();
  947. }
  948. }
  949. void ConvexHullInternal::Vertex::print_graph() {
  950. print();
  951. printf("\nEdges\n");
  952. Edge *e = edges;
  953. if (e) {
  954. do {
  955. e->print();
  956. printf("\n");
  957. e = e->next;
  958. } while (e != edges);
  959. do {
  960. Vertex *v = e->target;
  961. if (v->copy != copy) {
  962. v->copy = copy;
  963. v->print_graph();
  964. }
  965. e = e->next;
  966. } while (e != edges);
  967. }
  968. }
  969. #endif
  970. ConvexHullInternal::Orientation ConvexHullInternal::get_orientation(const Edge *p_prev, const Edge *p_next, const Point32 &p_s, const Point32 &p_t) {
  971. CHULL_ASSERT(p_prev->reverse->target == p_next->reverse->target);
  972. if (p_prev->next == p_next) {
  973. if (p_prev->prev == p_next) {
  974. Point64 n = p_t.cross(p_s);
  975. Point64 m = (*p_prev->target - *p_next->reverse->target).cross(*p_next->target - *p_next->reverse->target);
  976. CHULL_ASSERT(!m.is_zero());
  977. int64_t dot = n.dot(m);
  978. CHULL_ASSERT(dot != 0);
  979. return (dot > 0) ? COUNTER_CLOCKWISE : CLOCKWISE;
  980. }
  981. return COUNTER_CLOCKWISE;
  982. } else if (p_prev->prev == p_next) {
  983. return CLOCKWISE;
  984. } else {
  985. return NONE;
  986. }
  987. }
  988. 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) {
  989. Edge *min_edge = nullptr;
  990. #ifdef DEBUG_CONVEX_HULL
  991. printf("find max edge for %d\n", p_start->point.index);
  992. #endif
  993. Edge *e = p_start->edges;
  994. if (e) {
  995. do {
  996. if (e->copy > merge_stamp) {
  997. Point32 t = *e->target - *p_start;
  998. Rational64 cot(t.dot(p_sxrxs), t.dot(p_rxs));
  999. #ifdef DEBUG_CONVEX_HULL
  1000. printf(" Angle is %f (%d) for ", Math::atan(cot.to_scalar()), (int32_t)cot.is_nan());
  1001. e->print();
  1002. #endif
  1003. if (cot.is_nan()) {
  1004. CHULL_ASSERT(p_ccw ? (t.dot(p_s) < 0) : (t.dot(p_s) > 0));
  1005. } else {
  1006. int32_t cmp;
  1007. if (min_edge == nullptr) {
  1008. p_min_cot = cot;
  1009. min_edge = e;
  1010. } else if ((cmp = cot.compare(p_min_cot)) < 0) {
  1011. p_min_cot = cot;
  1012. min_edge = e;
  1013. } else if ((cmp == 0) && (p_ccw == (get_orientation(min_edge, e, p_s, t) == COUNTER_CLOCKWISE))) {
  1014. min_edge = e;
  1015. }
  1016. }
  1017. #ifdef DEBUG_CONVEX_HULL
  1018. printf("\n");
  1019. #endif
  1020. }
  1021. e = e->next;
  1022. } while (e != p_start->edges);
  1023. }
  1024. return min_edge;
  1025. }
  1026. 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) {
  1027. Edge *start0 = p_e0;
  1028. Edge *start1 = p_e1;
  1029. Point32 et0 = start0 ? start0->target->point : p_c0->point;
  1030. Point32 et1 = start1 ? start1->target->point : p_c1->point;
  1031. Point32 s = p_c1->point - p_c0->point;
  1032. Point64 normal = ((start0 ? start0 : start1)->target->point - p_c0->point).cross(s);
  1033. int64_t dist = p_c0->point.dot(normal);
  1034. CHULL_ASSERT(!start1 || (start1->target->point.dot(normal) == dist));
  1035. Point64 perp = s.cross(normal);
  1036. CHULL_ASSERT(!perp.is_zero());
  1037. #ifdef DEBUG_CONVEX_HULL
  1038. 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);
  1039. #endif
  1040. int64_t max_dot0 = et0.dot(perp);
  1041. if (p_e0) {
  1042. while (p_e0->target != p_stop0) {
  1043. Edge *e = p_e0->reverse->prev;
  1044. if (e->target->point.dot(normal) < dist) {
  1045. break;
  1046. }
  1047. CHULL_ASSERT(e->target->point.dot(normal) == dist);
  1048. if (e->copy == merge_stamp) {
  1049. break;
  1050. }
  1051. int64_t dot = e->target->point.dot(perp);
  1052. if (dot <= max_dot0) {
  1053. break;
  1054. }
  1055. max_dot0 = dot;
  1056. p_e0 = e;
  1057. et0 = e->target->point;
  1058. }
  1059. }
  1060. int64_t max_dot1 = et1.dot(perp);
  1061. if (p_e1) {
  1062. while (p_e1->target != p_stop1) {
  1063. Edge *e = p_e1->reverse->next;
  1064. if (e->target->point.dot(normal) < dist) {
  1065. break;
  1066. }
  1067. CHULL_ASSERT(e->target->point.dot(normal) == dist);
  1068. if (e->copy == merge_stamp) {
  1069. break;
  1070. }
  1071. int64_t dot = e->target->point.dot(perp);
  1072. if (dot <= max_dot1) {
  1073. break;
  1074. }
  1075. max_dot1 = dot;
  1076. p_e1 = e;
  1077. et1 = e->target->point;
  1078. }
  1079. }
  1080. #ifdef DEBUG_CONVEX_HULL
  1081. printf(" Starting at %d %d\n", et0.index, et1.index);
  1082. #endif
  1083. int64_t dx = max_dot1 - max_dot0;
  1084. if (dx > 0) {
  1085. while (true) {
  1086. int64_t dy = (et1 - et0).dot(s);
  1087. if (p_e0 && (p_e0->target != p_stop0)) {
  1088. Edge *f0 = p_e0->next->reverse;
  1089. if (f0->copy > merge_stamp) {
  1090. int64_t dx0 = (f0->target->point - et0).dot(perp);
  1091. int64_t dy0 = (f0->target->point - et0).dot(s);
  1092. if ((dx0 == 0) ? (dy0 < 0) : ((dx0 < 0) && (Rational64(dy0, dx0).compare(Rational64(dy, dx)) >= 0))) {
  1093. et0 = f0->target->point;
  1094. dx = (et1 - et0).dot(perp);
  1095. p_e0 = (p_e0 == start0) ? nullptr : f0;
  1096. continue;
  1097. }
  1098. }
  1099. }
  1100. if (p_e1 && (p_e1->target != p_stop1)) {
  1101. Edge *f1 = p_e1->reverse->next;
  1102. if (f1->copy > merge_stamp) {
  1103. Point32 d1 = f1->target->point - et1;
  1104. if (d1.dot(normal) == 0) {
  1105. int64_t dx1 = d1.dot(perp);
  1106. int64_t dy1 = d1.dot(s);
  1107. int64_t dxn = (f1->target->point - et0).dot(perp);
  1108. if ((dxn > 0) && ((dx1 == 0) ? (dy1 < 0) : ((dx1 < 0) && (Rational64(dy1, dx1).compare(Rational64(dy, dx)) > 0)))) {
  1109. p_e1 = f1;
  1110. et1 = p_e1->target->point;
  1111. dx = dxn;
  1112. continue;
  1113. }
  1114. } else {
  1115. CHULL_ASSERT((p_e1 == start1) && (d1.dot(normal) < 0));
  1116. }
  1117. }
  1118. }
  1119. break;
  1120. }
  1121. } else if (dx < 0) {
  1122. while (true) {
  1123. int64_t dy = (et1 - et0).dot(s);
  1124. if (p_e1 && (p_e1->target != p_stop1)) {
  1125. Edge *f1 = p_e1->prev->reverse;
  1126. if (f1->copy > merge_stamp) {
  1127. int64_t dx1 = (f1->target->point - et1).dot(perp);
  1128. int64_t dy1 = (f1->target->point - et1).dot(s);
  1129. if ((dx1 == 0) ? (dy1 > 0) : ((dx1 < 0) && (Rational64(dy1, dx1).compare(Rational64(dy, dx)) <= 0))) {
  1130. et1 = f1->target->point;
  1131. dx = (et1 - et0).dot(perp);
  1132. p_e1 = (p_e1 == start1) ? nullptr : f1;
  1133. continue;
  1134. }
  1135. }
  1136. }
  1137. if (p_e0 && (p_e0->target != p_stop0)) {
  1138. Edge *f0 = p_e0->reverse->prev;
  1139. if (f0->copy > merge_stamp) {
  1140. Point32 d0 = f0->target->point - et0;
  1141. if (d0.dot(normal) == 0) {
  1142. int64_t dx0 = d0.dot(perp);
  1143. int64_t dy0 = d0.dot(s);
  1144. int64_t dxn = (et1 - f0->target->point).dot(perp);
  1145. if ((dxn < 0) && ((dx0 == 0) ? (dy0 > 0) : ((dx0 < 0) && (Rational64(dy0, dx0).compare(Rational64(dy, dx)) < 0)))) {
  1146. p_e0 = f0;
  1147. et0 = p_e0->target->point;
  1148. dx = dxn;
  1149. continue;
  1150. }
  1151. } else {
  1152. CHULL_ASSERT((p_e0 == start0) && (d0.dot(normal) < 0));
  1153. }
  1154. }
  1155. }
  1156. break;
  1157. }
  1158. }
  1159. #ifdef DEBUG_CONVEX_HULL
  1160. printf(" Advanced edges to %d %d\n", et0.index, et1.index);
  1161. #endif
  1162. }
  1163. void ConvexHullInternal::merge(IntermediateHull &p_h0, IntermediateHull &p_h1) {
  1164. if (!p_h1.max_xy) {
  1165. return;
  1166. }
  1167. if (!p_h0.max_xy) {
  1168. p_h0 = p_h1;
  1169. return;
  1170. }
  1171. merge_stamp--;
  1172. Vertex *c0 = nullptr;
  1173. Edge *to_prev0 = nullptr;
  1174. Edge *first_new0 = nullptr;
  1175. Edge *pending_head0 = nullptr;
  1176. Edge *pending_tail0 = nullptr;
  1177. Vertex *c1 = nullptr;
  1178. Edge *to_prev1 = nullptr;
  1179. Edge *first_new1 = nullptr;
  1180. Edge *pending_head1 = nullptr;
  1181. Edge *pending_tail1 = nullptr;
  1182. Point32 prev_point;
  1183. if (merge_projection(p_h0, p_h1, c0, c1)) {
  1184. Point32 s = *c1 - *c0;
  1185. Point64 normal = Point32(0, 0, -1).cross(s);
  1186. Point64 t = s.cross(normal);
  1187. CHULL_ASSERT(!t.is_zero());
  1188. Edge *e = c0->edges;
  1189. Edge *start0 = nullptr;
  1190. if (e) {
  1191. do {
  1192. int64_t dot = (*e->target - *c0).dot(normal);
  1193. CHULL_ASSERT(dot <= 0);
  1194. if ((dot == 0) && ((*e->target - *c0).dot(t) > 0)) {
  1195. if (!start0 || (get_orientation(start0, e, s, Point32(0, 0, -1)) == CLOCKWISE)) {
  1196. start0 = e;
  1197. }
  1198. }
  1199. e = e->next;
  1200. } while (e != c0->edges);
  1201. }
  1202. e = c1->edges;
  1203. Edge *start1 = nullptr;
  1204. if (e) {
  1205. do {
  1206. int64_t dot = (*e->target - *c1).dot(normal);
  1207. CHULL_ASSERT(dot <= 0);
  1208. if ((dot == 0) && ((*e->target - *c1).dot(t) > 0)) {
  1209. if (!start1 || (get_orientation(start1, e, s, Point32(0, 0, -1)) == COUNTER_CLOCKWISE)) {
  1210. start1 = e;
  1211. }
  1212. }
  1213. e = e->next;
  1214. } while (e != c1->edges);
  1215. }
  1216. if (start0 || start1) {
  1217. find_edge_for_coplanar_faces(c0, c1, start0, start1, nullptr, nullptr);
  1218. if (start0) {
  1219. c0 = start0->target;
  1220. }
  1221. if (start1) {
  1222. c1 = start1->target;
  1223. }
  1224. }
  1225. prev_point = c1->point;
  1226. prev_point.z++;
  1227. } else {
  1228. prev_point = c1->point;
  1229. prev_point.x++;
  1230. }
  1231. Vertex *first0 = c0;
  1232. Vertex *first1 = c1;
  1233. bool first_run = true;
  1234. while (true) {
  1235. Point32 s = *c1 - *c0;
  1236. Point32 r = prev_point - c0->point;
  1237. Point64 rxs = r.cross(s);
  1238. Point64 sxrxs = s.cross(rxs);
  1239. #ifdef DEBUG_CONVEX_HULL
  1240. printf("\n Checking %d %d\n", c0->point.index, c1->point.index);
  1241. #endif
  1242. Rational64 min_cot0(0, 0);
  1243. Edge *min0 = find_max_angle(false, c0, s, rxs, sxrxs, min_cot0);
  1244. Rational64 min_cot1(0, 0);
  1245. Edge *min1 = find_max_angle(true, c1, s, rxs, sxrxs, min_cot1);
  1246. if (!min0 && !min1) {
  1247. Edge *e = new_edge_pair(c0, c1);
  1248. e->link(e);
  1249. c0->edges = e;
  1250. e = e->reverse;
  1251. e->link(e);
  1252. c1->edges = e;
  1253. return;
  1254. } else {
  1255. int32_t cmp = !min0 ? 1 : (!min1 ? -1 : min_cot0.compare(min_cot1));
  1256. #ifdef DEBUG_CONVEX_HULL
  1257. printf(" -> Result %d\n", cmp);
  1258. #endif
  1259. if (first_run || ((cmp >= 0) ? !min_cot1.is_negative_infinity() : !min_cot0.is_negative_infinity())) {
  1260. Edge *e = new_edge_pair(c0, c1);
  1261. if (pending_tail0) {
  1262. pending_tail0->prev = e;
  1263. } else {
  1264. pending_head0 = e;
  1265. }
  1266. e->next = pending_tail0;
  1267. pending_tail0 = e;
  1268. e = e->reverse;
  1269. if (pending_tail1) {
  1270. pending_tail1->next = e;
  1271. } else {
  1272. pending_head1 = e;
  1273. }
  1274. e->prev = pending_tail1;
  1275. pending_tail1 = e;
  1276. }
  1277. Edge *e0 = min0;
  1278. Edge *e1 = min1;
  1279. #ifdef DEBUG_CONVEX_HULL
  1280. printf(" Found min edges to %d %d\n", e0 ? e0->target->point.index : -1, e1 ? e1->target->point.index : -1);
  1281. #endif
  1282. if (cmp == 0) {
  1283. find_edge_for_coplanar_faces(c0, c1, e0, e1, nullptr, nullptr);
  1284. }
  1285. if ((cmp >= 0) && e1) {
  1286. if (to_prev1) {
  1287. for (Edge *e = to_prev1->next, *n = nullptr; e != min1; e = n) {
  1288. n = e->next;
  1289. remove_edge_pair(e);
  1290. }
  1291. }
  1292. if (pending_tail1) {
  1293. if (to_prev1) {
  1294. to_prev1->link(pending_head1);
  1295. } else {
  1296. min1->prev->link(pending_head1);
  1297. first_new1 = pending_head1;
  1298. }
  1299. pending_tail1->link(min1);
  1300. pending_head1 = nullptr;
  1301. pending_tail1 = nullptr;
  1302. } else if (!to_prev1) {
  1303. first_new1 = min1;
  1304. }
  1305. prev_point = c1->point;
  1306. c1 = e1->target;
  1307. to_prev1 = e1->reverse;
  1308. }
  1309. if ((cmp <= 0) && e0) {
  1310. if (to_prev0) {
  1311. for (Edge *e = to_prev0->prev, *n = nullptr; e != min0; e = n) {
  1312. n = e->prev;
  1313. remove_edge_pair(e);
  1314. }
  1315. }
  1316. if (pending_tail0) {
  1317. if (to_prev0) {
  1318. pending_head0->link(to_prev0);
  1319. } else {
  1320. pending_head0->link(min0->next);
  1321. first_new0 = pending_head0;
  1322. }
  1323. min0->link(pending_tail0);
  1324. pending_head0 = nullptr;
  1325. pending_tail0 = nullptr;
  1326. } else if (!to_prev0) {
  1327. first_new0 = min0;
  1328. }
  1329. prev_point = c0->point;
  1330. c0 = e0->target;
  1331. to_prev0 = e0->reverse;
  1332. }
  1333. }
  1334. if ((c0 == first0) && (c1 == first1)) {
  1335. if (to_prev0 == nullptr) {
  1336. pending_head0->link(pending_tail0);
  1337. c0->edges = pending_tail0;
  1338. } else {
  1339. for (Edge *e = to_prev0->prev, *n = nullptr; e != first_new0; e = n) {
  1340. n = e->prev;
  1341. remove_edge_pair(e);
  1342. }
  1343. if (pending_tail0) {
  1344. pending_head0->link(to_prev0);
  1345. first_new0->link(pending_tail0);
  1346. }
  1347. }
  1348. if (to_prev1 == nullptr) {
  1349. pending_tail1->link(pending_head1);
  1350. c1->edges = pending_tail1;
  1351. } else {
  1352. for (Edge *e = to_prev1->next, *n = nullptr; e != first_new1; e = n) {
  1353. n = e->next;
  1354. remove_edge_pair(e);
  1355. }
  1356. if (pending_tail1) {
  1357. to_prev1->link(pending_head1);
  1358. pending_tail1->link(first_new1);
  1359. }
  1360. }
  1361. return;
  1362. }
  1363. first_run = false;
  1364. }
  1365. }
  1366. struct PointComparator {
  1367. _FORCE_INLINE_ bool operator()(const ConvexHullInternal::Point32 &p, const ConvexHullInternal::Point32 &q) const {
  1368. return (p.y < q.y) || ((p.y == q.y) && ((p.x < q.x) || ((p.x == q.x) && (p.z < q.z))));
  1369. }
  1370. };
  1371. void ConvexHullInternal::compute(const Vector3 *p_coords, int32_t p_count) {
  1372. AABB aabb;
  1373. for (int32_t i = 0; i < p_count; i++) {
  1374. Vector3 p = p_coords[i];
  1375. if (i == 0) {
  1376. aabb.position = p;
  1377. } else {
  1378. aabb.expand_to(p);
  1379. }
  1380. }
  1381. Vector3 s = aabb.size;
  1382. max_axis = s.max_axis();
  1383. min_axis = s.min_axis();
  1384. if (min_axis == max_axis) {
  1385. min_axis = (max_axis + 1) % 3;
  1386. }
  1387. med_axis = 3 - max_axis - min_axis;
  1388. s /= real_t(10216);
  1389. if (((med_axis + 1) % 3) != max_axis) {
  1390. s *= -1;
  1391. }
  1392. scaling = s;
  1393. if (s[0] != 0) {
  1394. s[0] = real_t(1) / s[0];
  1395. }
  1396. if (s[1] != 0) {
  1397. s[1] = real_t(1) / s[1];
  1398. }
  1399. if (s[2] != 0) {
  1400. s[2] = real_t(1) / s[2];
  1401. }
  1402. center = aabb.position;
  1403. LocalVector<Point32> points;
  1404. points.resize(p_count);
  1405. for (int32_t i = 0; i < p_count; i++) {
  1406. Vector3 p = p_coords[i];
  1407. p = (p - center) * s;
  1408. points[i].x = (int32_t)p[med_axis];
  1409. points[i].y = (int32_t)p[max_axis];
  1410. points[i].z = (int32_t)p[min_axis];
  1411. points[i].index = i;
  1412. }
  1413. points.sort_custom<PointComparator>();
  1414. vertex_pool.reset(true);
  1415. original_vertices.resize(p_count);
  1416. for (int32_t i = 0; i < p_count; i++) {
  1417. Vertex *v = vertex_pool.alloc();
  1418. v->edges = nullptr;
  1419. v->point = points[i];
  1420. v->copy = -1;
  1421. original_vertices[i] = v;
  1422. }
  1423. points.clear();
  1424. edge_pool.reset(true);
  1425. used_edge_pairs = 0;
  1426. max_used_edge_pairs = 0;
  1427. merge_stamp = -3;
  1428. IntermediateHull hull;
  1429. compute_internal(0, p_count, hull);
  1430. vertex_list = hull.min_xy;
  1431. #ifdef DEBUG_CONVEX_HULL
  1432. printf("max. edges %d (3v = %d)", max_used_edge_pairs, 3 * p_count);
  1433. #endif
  1434. }
  1435. Vector3 ConvexHullInternal::to_gd_vector(const Point32 &p_v) {
  1436. Vector3 p;
  1437. p[med_axis] = real_t(p_v.x);
  1438. p[max_axis] = real_t(p_v.y);
  1439. p[min_axis] = real_t(p_v.z);
  1440. return p * scaling;
  1441. }
  1442. Vector3 ConvexHullInternal::get_gd_normal(Face *p_face) {
  1443. return to_gd_vector(p_face->dir0).cross(to_gd_vector(p_face->dir1)).normalized();
  1444. }
  1445. Vector3 ConvexHullInternal::get_coordinates(const Vertex *p_v) {
  1446. Vector3 p;
  1447. p[med_axis] = p_v->xvalue();
  1448. p[max_axis] = p_v->yvalue();
  1449. p[min_axis] = p_v->zvalue();
  1450. return p * scaling + center;
  1451. }
  1452. real_t ConvexHullInternal::shrink(real_t p_amount, real_t p_clamp_amount) {
  1453. if (!vertex_list) {
  1454. return 0;
  1455. }
  1456. int32_t stamp = --merge_stamp;
  1457. LocalVector<Vertex *> stack;
  1458. vertex_list->copy = stamp;
  1459. stack.push_back(vertex_list);
  1460. LocalVector<Face *> faces;
  1461. Point32 ref = vertex_list->point;
  1462. Int128 hull_center_x(0, 0);
  1463. Int128 hull_center_y(0, 0);
  1464. Int128 hull_center_z(0, 0);
  1465. Int128 volume(0, 0);
  1466. while (stack.size() > 0) {
  1467. Vertex *v = stack[stack.size() - 1];
  1468. stack.remove(stack.size() - 1);
  1469. Edge *e = v->edges;
  1470. if (e) {
  1471. do {
  1472. if (e->target->copy != stamp) {
  1473. e->target->copy = stamp;
  1474. stack.push_back(e->target);
  1475. }
  1476. if (e->copy != stamp) {
  1477. Face *face = face_pool.alloc();
  1478. face->init(e->target, e->reverse->prev->target, v);
  1479. faces.push_back(face);
  1480. Edge *f = e;
  1481. Vertex *a = nullptr;
  1482. Vertex *b = nullptr;
  1483. do {
  1484. if (a && b) {
  1485. int64_t vol = (v->point - ref).dot((a->point - ref).cross(b->point - ref));
  1486. CHULL_ASSERT(vol >= 0);
  1487. Point32 c = v->point + a->point + b->point + ref;
  1488. hull_center_x += vol * c.x;
  1489. hull_center_y += vol * c.y;
  1490. hull_center_z += vol * c.z;
  1491. volume += vol;
  1492. }
  1493. CHULL_ASSERT(f->copy != stamp);
  1494. f->copy = stamp;
  1495. f->face = face;
  1496. a = b;
  1497. b = f->target;
  1498. f = f->reverse->prev;
  1499. } while (f != e);
  1500. }
  1501. e = e->next;
  1502. } while (e != v->edges);
  1503. }
  1504. }
  1505. if (volume.get_sign() <= 0) {
  1506. return 0;
  1507. }
  1508. Vector3 hull_center;
  1509. hull_center[med_axis] = hull_center_x.to_scalar();
  1510. hull_center[max_axis] = hull_center_y.to_scalar();
  1511. hull_center[min_axis] = hull_center_z.to_scalar();
  1512. hull_center /= 4 * volume.to_scalar();
  1513. hull_center *= scaling;
  1514. int32_t face_count = faces.size();
  1515. if (p_clamp_amount > 0) {
  1516. real_t min_dist = FLT_MAX;
  1517. for (int32_t i = 0; i < face_count; i++) {
  1518. Vector3 normal = get_gd_normal(faces[i]);
  1519. real_t dist = normal.dot(to_gd_vector(faces[i]->origin) - hull_center);
  1520. if (dist < min_dist) {
  1521. min_dist = dist;
  1522. }
  1523. }
  1524. if (min_dist <= 0) {
  1525. return 0;
  1526. }
  1527. p_amount = MIN(p_amount, min_dist * p_clamp_amount);
  1528. }
  1529. uint32_t seed = 243703;
  1530. for (int32_t i = 0; i < face_count; i++, seed = 1664525 * seed + 1013904223) {
  1531. SWAP(faces[i], faces[seed % face_count]);
  1532. }
  1533. for (int32_t i = 0; i < face_count; i++) {
  1534. if (!shift_face(faces[i], p_amount, stack)) {
  1535. return -p_amount;
  1536. }
  1537. }
  1538. return p_amount;
  1539. }
  1540. bool ConvexHullInternal::shift_face(Face *p_face, real_t p_amount, LocalVector<Vertex *> p_stack) {
  1541. Vector3 orig_shift = get_gd_normal(p_face) * -p_amount;
  1542. if (scaling[0] != 0) {
  1543. orig_shift[0] /= scaling[0];
  1544. }
  1545. if (scaling[1] != 0) {
  1546. orig_shift[1] /= scaling[1];
  1547. }
  1548. if (scaling[2] != 0) {
  1549. orig_shift[2] /= scaling[2];
  1550. }
  1551. Point32 shift((int32_t)orig_shift[med_axis], (int32_t)orig_shift[max_axis], (int32_t)orig_shift[min_axis]);
  1552. if (shift.is_zero()) {
  1553. return true;
  1554. }
  1555. Point64 normal = p_face->get_normal();
  1556. #ifdef DEBUG_CONVEX_HULL
  1557. printf("\nShrinking p_face (%d %d %d) (%d %d %d) (%d %d %d) by (%d %d %d)\n",
  1558. 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);
  1559. #endif
  1560. int64_t orig_dot = p_face->origin.dot(normal);
  1561. Point32 shifted_origin = p_face->origin + shift;
  1562. int64_t shifted_dot = shifted_origin.dot(normal);
  1563. CHULL_ASSERT(shifted_dot <= orig_dot);
  1564. if (shifted_dot >= orig_dot) {
  1565. return false;
  1566. }
  1567. Edge *intersection = nullptr;
  1568. Edge *start_edge = p_face->nearby_vertex->edges;
  1569. #ifdef DEBUG_CONVEX_HULL
  1570. printf("Start edge is ");
  1571. start_edge->print();
  1572. printf(", normal is (%lld %lld %lld), shifted dot is %lld\n", normal.x, normal.y, normal.z, shifted_dot);
  1573. #endif
  1574. Rational128 opt_dot = p_face->nearby_vertex->dot(normal);
  1575. int32_t cmp = opt_dot.compare(shifted_dot);
  1576. #ifdef SHOW_ITERATIONS
  1577. int32_t n = 0;
  1578. #endif
  1579. if (cmp >= 0) {
  1580. Edge *e = start_edge;
  1581. do {
  1582. #ifdef SHOW_ITERATIONS
  1583. n++;
  1584. #endif
  1585. Rational128 dot = e->target->dot(normal);
  1586. CHULL_ASSERT(dot.compare(orig_dot) <= 0);
  1587. #ifdef DEBUG_CONVEX_HULL
  1588. printf("Moving downwards, edge is ");
  1589. e->print();
  1590. printf(", dot is %f (%f %lld)\n", (float)dot.to_scalar(), (float)opt_dot.to_scalar(), shifted_dot);
  1591. #endif
  1592. if (dot.compare(opt_dot) < 0) {
  1593. int32_t c = dot.compare(shifted_dot);
  1594. opt_dot = dot;
  1595. e = e->reverse;
  1596. start_edge = e;
  1597. if (c < 0) {
  1598. intersection = e;
  1599. break;
  1600. }
  1601. cmp = c;
  1602. }
  1603. e = e->prev;
  1604. } while (e != start_edge);
  1605. if (!intersection) {
  1606. return false;
  1607. }
  1608. } else {
  1609. Edge *e = start_edge;
  1610. do {
  1611. #ifdef SHOW_ITERATIONS
  1612. n++;
  1613. #endif
  1614. Rational128 dot = e->target->dot(normal);
  1615. CHULL_ASSERT(dot.compare(orig_dot) <= 0);
  1616. #ifdef DEBUG_CONVEX_HULL
  1617. printf("Moving upwards, edge is ");
  1618. e->print();
  1619. printf(", dot is %f (%f %lld)\n", (float)dot.to_scalar(), (float)opt_dot.to_scalar(), shifted_dot);
  1620. #endif
  1621. if (dot.compare(opt_dot) > 0) {
  1622. cmp = dot.compare(shifted_dot);
  1623. if (cmp >= 0) {
  1624. intersection = e;
  1625. break;
  1626. }
  1627. opt_dot = dot;
  1628. e = e->reverse;
  1629. start_edge = e;
  1630. }
  1631. e = e->prev;
  1632. } while (e != start_edge);
  1633. if (!intersection) {
  1634. return true;
  1635. }
  1636. }
  1637. #ifdef SHOW_ITERATIONS
  1638. printf("Needed %d iterations to find initial intersection\n", n);
  1639. #endif
  1640. if (cmp == 0) {
  1641. Edge *e = intersection->reverse->next;
  1642. #ifdef SHOW_ITERATIONS
  1643. n = 0;
  1644. #endif
  1645. while (e->target->dot(normal).compare(shifted_dot) <= 0) {
  1646. #ifdef SHOW_ITERATIONS
  1647. n++;
  1648. #endif
  1649. e = e->next;
  1650. if (e == intersection->reverse) {
  1651. return true;
  1652. }
  1653. #ifdef DEBUG_CONVEX_HULL
  1654. printf("Checking for outwards edge, current edge is ");
  1655. e->print();
  1656. printf("\n");
  1657. #endif
  1658. }
  1659. #ifdef SHOW_ITERATIONS
  1660. printf("Needed %d iterations to check for complete containment\n", n);
  1661. #endif
  1662. }
  1663. Edge *first_intersection = nullptr;
  1664. Edge *face_edge = nullptr;
  1665. Edge *first_face_edge = nullptr;
  1666. #ifdef SHOW_ITERATIONS
  1667. int32_t m = 0;
  1668. #endif
  1669. while (true) {
  1670. #ifdef SHOW_ITERATIONS
  1671. m++;
  1672. #endif
  1673. #ifdef DEBUG_CONVEX_HULL
  1674. printf("Intersecting edge is ");
  1675. intersection->print();
  1676. printf("\n");
  1677. #endif
  1678. if (cmp == 0) {
  1679. Edge *e = intersection->reverse->next;
  1680. start_edge = e;
  1681. #ifdef SHOW_ITERATIONS
  1682. n = 0;
  1683. #endif
  1684. while (true) {
  1685. #ifdef SHOW_ITERATIONS
  1686. n++;
  1687. #endif
  1688. if (e->target->dot(normal).compare(shifted_dot) >= 0) {
  1689. break;
  1690. }
  1691. intersection = e->reverse;
  1692. e = e->next;
  1693. if (e == start_edge) {
  1694. return true;
  1695. }
  1696. }
  1697. #ifdef SHOW_ITERATIONS
  1698. printf("Needed %d iterations to advance intersection\n", n);
  1699. #endif
  1700. }
  1701. #ifdef DEBUG_CONVEX_HULL
  1702. printf("Advanced intersecting edge to ");
  1703. intersection->print();
  1704. printf(", cmp = %d\n", cmp);
  1705. #endif
  1706. if (!first_intersection) {
  1707. first_intersection = intersection;
  1708. } else if (intersection == first_intersection) {
  1709. break;
  1710. }
  1711. int32_t prev_cmp = cmp;
  1712. Edge *prev_intersection = intersection;
  1713. Edge *prev_face_edge = face_edge;
  1714. Edge *e = intersection->reverse;
  1715. #ifdef SHOW_ITERATIONS
  1716. n = 0;
  1717. #endif
  1718. while (true) {
  1719. #ifdef SHOW_ITERATIONS
  1720. n++;
  1721. #endif
  1722. e = e->reverse->prev;
  1723. CHULL_ASSERT(e != intersection->reverse);
  1724. cmp = e->target->dot(normal).compare(shifted_dot);
  1725. #ifdef DEBUG_CONVEX_HULL
  1726. printf("Testing edge ");
  1727. e->print();
  1728. printf(" -> cmp = %d\n", cmp);
  1729. #endif
  1730. if (cmp >= 0) {
  1731. intersection = e;
  1732. break;
  1733. }
  1734. }
  1735. #ifdef SHOW_ITERATIONS
  1736. printf("Needed %d iterations to find other intersection of p_face\n", n);
  1737. #endif
  1738. if (cmp > 0) {
  1739. Vertex *removed = intersection->target;
  1740. e = intersection->reverse;
  1741. if (e->prev == e) {
  1742. removed->edges = nullptr;
  1743. } else {
  1744. removed->edges = e->prev;
  1745. e->prev->link(e->next);
  1746. e->link(e);
  1747. }
  1748. #ifdef DEBUG_CONVEX_HULL
  1749. printf("1: Removed part contains (%d %d %d)\n", removed->point.x, removed->point.y, removed->point.z);
  1750. #endif
  1751. Point64 n0 = intersection->face->get_normal();
  1752. Point64 n1 = intersection->reverse->face->get_normal();
  1753. int64_t m00 = p_face->dir0.dot(n0);
  1754. int64_t m01 = p_face->dir1.dot(n0);
  1755. int64_t m10 = p_face->dir0.dot(n1);
  1756. int64_t m11 = p_face->dir1.dot(n1);
  1757. int64_t r0 = (intersection->face->origin - shifted_origin).dot(n0);
  1758. int64_t r1 = (intersection->reverse->face->origin - shifted_origin).dot(n1);
  1759. Int128 det = Int128::mul(m00, m11) - Int128::mul(m01, m10);
  1760. CHULL_ASSERT(det.get_sign() != 0);
  1761. Vertex *v = vertex_pool.alloc();
  1762. v->point.index = -1;
  1763. v->copy = -1;
  1764. 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,
  1765. 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,
  1766. 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,
  1767. det);
  1768. v->point.x = (int32_t)v->point128.xvalue();
  1769. v->point.y = (int32_t)v->point128.yvalue();
  1770. v->point.z = (int32_t)v->point128.zvalue();
  1771. intersection->target = v;
  1772. v->edges = e;
  1773. p_stack.push_back(v);
  1774. p_stack.push_back(removed);
  1775. p_stack.push_back(nullptr);
  1776. }
  1777. if (cmp || prev_cmp || (prev_intersection->reverse->next->target != intersection->target)) {
  1778. face_edge = new_edge_pair(prev_intersection->target, intersection->target);
  1779. if (prev_cmp == 0) {
  1780. face_edge->link(prev_intersection->reverse->next);
  1781. }
  1782. if ((prev_cmp == 0) || prev_face_edge) {
  1783. prev_intersection->reverse->link(face_edge);
  1784. }
  1785. if (cmp == 0) {
  1786. intersection->reverse->prev->link(face_edge->reverse);
  1787. }
  1788. face_edge->reverse->link(intersection->reverse);
  1789. } else {
  1790. face_edge = prev_intersection->reverse->next;
  1791. }
  1792. if (prev_face_edge) {
  1793. if (prev_cmp > 0) {
  1794. face_edge->link(prev_face_edge->reverse);
  1795. } else if (face_edge != prev_face_edge->reverse) {
  1796. p_stack.push_back(prev_face_edge->target);
  1797. while (face_edge->next != prev_face_edge->reverse) {
  1798. Vertex *removed = face_edge->next->target;
  1799. remove_edge_pair(face_edge->next);
  1800. p_stack.push_back(removed);
  1801. #ifdef DEBUG_CONVEX_HULL
  1802. printf("2: Removed part contains (%d %d %d)\n", removed->point.x, removed->point.y, removed->point.z);
  1803. #endif
  1804. }
  1805. p_stack.push_back(nullptr);
  1806. }
  1807. }
  1808. face_edge->face = p_face;
  1809. face_edge->reverse->face = intersection->face;
  1810. if (!first_face_edge) {
  1811. first_face_edge = face_edge;
  1812. }
  1813. }
  1814. #ifdef SHOW_ITERATIONS
  1815. printf("Needed %d iterations to process all intersections\n", m);
  1816. #endif
  1817. if (cmp > 0) {
  1818. first_face_edge->reverse->target = face_edge->target;
  1819. first_intersection->reverse->link(first_face_edge);
  1820. first_face_edge->link(face_edge->reverse);
  1821. } else if (first_face_edge != face_edge->reverse) {
  1822. p_stack.push_back(face_edge->target);
  1823. while (first_face_edge->next != face_edge->reverse) {
  1824. Vertex *removed = first_face_edge->next->target;
  1825. remove_edge_pair(first_face_edge->next);
  1826. p_stack.push_back(removed);
  1827. #ifdef DEBUG_CONVEX_HULL
  1828. printf("3: Removed part contains (%d %d %d)\n", removed->point.x, removed->point.y, removed->point.z);
  1829. #endif
  1830. }
  1831. p_stack.push_back(nullptr);
  1832. }
  1833. CHULL_ASSERT(p_stack.size() > 0);
  1834. vertex_list = p_stack[0];
  1835. #ifdef DEBUG_CONVEX_HULL
  1836. printf("Removing part\n");
  1837. #endif
  1838. #ifdef SHOW_ITERATIONS
  1839. n = 0;
  1840. #endif
  1841. uint32_t pos = 0;
  1842. while (pos < p_stack.size()) {
  1843. uint32_t end = p_stack.size();
  1844. while (pos < end) {
  1845. Vertex *kept = p_stack[pos++];
  1846. #ifdef DEBUG_CONVEX_HULL
  1847. kept->print();
  1848. #endif
  1849. bool deeper = false;
  1850. Vertex *removed;
  1851. while ((removed = p_stack[pos++]) != nullptr) {
  1852. #ifdef SHOW_ITERATIONS
  1853. n++;
  1854. #endif
  1855. kept->receive_nearby_faces(removed);
  1856. while (removed->edges) {
  1857. if (!deeper) {
  1858. deeper = true;
  1859. p_stack.push_back(kept);
  1860. }
  1861. p_stack.push_back(removed->edges->target);
  1862. remove_edge_pair(removed->edges);
  1863. }
  1864. }
  1865. if (deeper) {
  1866. p_stack.push_back(nullptr);
  1867. }
  1868. }
  1869. }
  1870. #ifdef SHOW_ITERATIONS
  1871. printf("Needed %d iterations to remove part\n", n);
  1872. #endif
  1873. p_stack.resize(0);
  1874. p_face->origin = shifted_origin;
  1875. return true;
  1876. }
  1877. static int32_t get_vertex_copy(ConvexHullInternal::Vertex *p_vertex, LocalVector<ConvexHullInternal::Vertex *> &p_vertices) {
  1878. int32_t index = p_vertex->copy;
  1879. if (index < 0) {
  1880. index = p_vertices.size();
  1881. p_vertex->copy = index;
  1882. p_vertices.push_back(p_vertex);
  1883. #ifdef DEBUG_CONVEX_HULL
  1884. printf("Vertex %d gets index *%d\n", p_vertex->point.index, index);
  1885. #endif
  1886. }
  1887. return index;
  1888. }
  1889. real_t ConvexHullComputer::compute(const Vector3 *p_coords, int32_t p_count, real_t p_shrink, real_t p_shrink_clamp) {
  1890. if (p_count <= 0) {
  1891. vertices.clear();
  1892. edges.clear();
  1893. faces.clear();
  1894. return 0;
  1895. }
  1896. ConvexHullInternal hull;
  1897. hull.compute(p_coords, p_count);
  1898. real_t shift = 0;
  1899. if ((p_shrink > 0) && ((shift = hull.shrink(p_shrink, p_shrink_clamp)) < 0)) {
  1900. vertices.clear();
  1901. edges.clear();
  1902. faces.clear();
  1903. return shift;
  1904. }
  1905. vertices.resize(0);
  1906. edges.resize(0);
  1907. faces.resize(0);
  1908. LocalVector<ConvexHullInternal::Vertex *> old_vertices;
  1909. get_vertex_copy(hull.vertex_list, old_vertices);
  1910. int32_t copied = 0;
  1911. while (copied < (int32_t)old_vertices.size()) {
  1912. ConvexHullInternal::Vertex *v = old_vertices[copied];
  1913. vertices.push_back(hull.get_coordinates(v));
  1914. ConvexHullInternal::Edge *first_edge = v->edges;
  1915. if (first_edge) {
  1916. int32_t first_copy = -1;
  1917. int32_t prev_copy = -1;
  1918. ConvexHullInternal::Edge *e = first_edge;
  1919. do {
  1920. if (e->copy < 0) {
  1921. int32_t s = edges.size();
  1922. edges.push_back(Edge());
  1923. edges.push_back(Edge());
  1924. Edge *c = &edges[s];
  1925. Edge *r = &edges[s + 1];
  1926. e->copy = s;
  1927. e->reverse->copy = s + 1;
  1928. c->reverse = 1;
  1929. r->reverse = -1;
  1930. c->target_vertex = get_vertex_copy(e->target, old_vertices);
  1931. r->target_vertex = copied;
  1932. #ifdef DEBUG_CONVEX_HULL
  1933. printf(" CREATE: Vertex *%d has edge to *%d\n", copied, c->get_target_vertex());
  1934. #endif
  1935. }
  1936. if (prev_copy >= 0) {
  1937. edges[e->copy].next = prev_copy - e->copy;
  1938. } else {
  1939. first_copy = e->copy;
  1940. }
  1941. prev_copy = e->copy;
  1942. e = e->next;
  1943. } while (e != first_edge);
  1944. edges[first_copy].next = prev_copy - first_copy;
  1945. }
  1946. copied++;
  1947. }
  1948. for (int32_t i = 0; i < copied; i++) {
  1949. ConvexHullInternal::Vertex *v = old_vertices[i];
  1950. ConvexHullInternal::Edge *first_edge = v->edges;
  1951. if (first_edge) {
  1952. ConvexHullInternal::Edge *e = first_edge;
  1953. do {
  1954. if (e->copy >= 0) {
  1955. #ifdef DEBUG_CONVEX_HULL
  1956. printf("Vertex *%d has edge to *%d\n", i, edges[e->copy].get_target_vertex());
  1957. #endif
  1958. faces.push_back(e->copy);
  1959. ConvexHullInternal::Edge *f = e;
  1960. do {
  1961. #ifdef DEBUG_CONVEX_HULL
  1962. printf(" Face *%d\n", edges[f->copy].get_target_vertex());
  1963. #endif
  1964. f->copy = -1;
  1965. f = f->reverse->prev;
  1966. } while (f != e);
  1967. }
  1968. e = e->next;
  1969. } while (e != first_edge);
  1970. }
  1971. }
  1972. return shift;
  1973. }
  1974. Error ConvexHullComputer::convex_hull(const Vector<Vector3> &p_points, Geometry::MeshData &r_mesh) {
  1975. return convex_hull(p_points.ptr(), p_points.size(), r_mesh);
  1976. }
  1977. Error ConvexHullComputer::convex_hull(const PoolVector<Vector3> &p_points, Geometry::MeshData &r_mesh) {
  1978. return convex_hull(p_points.read().ptr(), p_points.size(), r_mesh);
  1979. }
  1980. Error ConvexHullComputer::convex_hull(const Vector3 *p_points, int32_t p_point_count, Geometry::MeshData &r_mesh) {
  1981. r_mesh = Geometry::MeshData(); // clear
  1982. if (p_point_count == 0) {
  1983. return FAILED; // matches QuickHull
  1984. }
  1985. ConvexHullComputer ch;
  1986. ch.compute(p_points, p_point_count, -1.0, -1.0);
  1987. r_mesh.vertices = ch.vertices;
  1988. // Copy the edges over. There's two "half-edges" for every edge, so we pick only one of them.
  1989. r_mesh.edges.resize(ch.edges.size() / 2);
  1990. uint32_t edges_copied = 0;
  1991. for (uint32_t i = 0; i < ch.edges.size(); i++) {
  1992. uint32_t a = (&ch.edges[i])->get_source_vertex();
  1993. uint32_t b = (&ch.edges[i])->get_target_vertex();
  1994. if (a < b) { // Copy only the "canonical" edge. For the reverse edge, this will be false.
  1995. ERR_BREAK(edges_copied >= (uint32_t)r_mesh.edges.size());
  1996. r_mesh.edges.write[edges_copied].a = a;
  1997. r_mesh.edges.write[edges_copied].b = b;
  1998. edges_copied++;
  1999. }
  2000. }
  2001. if (edges_copied != (uint32_t)r_mesh.edges.size()) {
  2002. ERR_PRINT("Invalid edge count.");
  2003. }
  2004. r_mesh.faces.resize(ch.faces.size());
  2005. for (uint32_t i = 0; i < ch.faces.size(); i++) {
  2006. const Edge *e_start = &ch.edges[ch.faces[i]];
  2007. const Edge *e = e_start;
  2008. Geometry::MeshData::Face &face = r_mesh.faces.write[i];
  2009. do {
  2010. face.indices.push_back(e->get_target_vertex());
  2011. e = e->get_next_edge_of_face();
  2012. } while (e != e_start);
  2013. // reverse indices: Godot wants clockwise, but this is counter-clockwise
  2014. if (face.indices.size() > 2) {
  2015. // reverse all but the first index.
  2016. int *indices = face.indices.ptrw();
  2017. for (int c = 0; c < (face.indices.size() - 1) / 2; c++) {
  2018. SWAP(indices[c + 1], indices[face.indices.size() - 1 - c]);
  2019. }
  2020. }
  2021. // compute normal
  2022. if (face.indices.size() >= 3) {
  2023. face.plane = Plane(r_mesh.vertices[face.indices[0]], r_mesh.vertices[face.indices[1]], r_mesh.vertices[face.indices[2]]);
  2024. } else {
  2025. WARN_PRINT("Too few vertices per face.");
  2026. }
  2027. }
  2028. return OK;
  2029. }