app.tsx 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423
  1. import * as React from "react";
  2. import * as _ from "lodash";
  3. import {Grid, AppShell, Navbar, Header, Text, Title, MantineProvider, Tooltip, Group} from "@mantine/core";
  4. import {IconInfoCircle} from "@tabler/icons";
  5. import {Graph} from "./graph"
  6. import {InteractiveGraph} from "./interactive_graph";
  7. const graph = {
  8. "nodes": [
  9. { "id": "Myriel", "group": 1 },
  10. { "id": "Napoleon", "group": 1 },
  11. { "id": "Mlle.Baptistine", "group": 1 },
  12. { "id": "Mme.Magloire", "group": 1 },
  13. { "id": "CountessdeLo", "group": 1 },
  14. { "id": "Geborand", "group": 1 },
  15. { "id": "Champtercier", "group": 1 },
  16. { "id": "Cravatte", "group": 1 },
  17. { "id": "Count", "group": 1 },
  18. { "id": "OldMan", "group": 1 },
  19. { "id": "Labarre", "group": 2 },
  20. { "id": "Valjean", "group": 2 },
  21. { "id": "Marguerite", "group": 3 },
  22. { "id": "Mme.deR", "group": 2 },
  23. { "id": "Isabeau", "group": 2 },
  24. { "id": "Gervais", "group": 2 },
  25. { "id": "Tholomyes", "group": 3 },
  26. { "id": "Listolier", "group": 3 },
  27. { "id": "Fameuil", "group": 3 },
  28. { "id": "Blacheville", "group": 3 },
  29. { "id": "Favourite", "group": 3 },
  30. { "id": "Dahlia", "group": 3 },
  31. { "id": "Zephine", "group": 3 },
  32. { "id": "Fantine", "group": 3 },
  33. { "id": "Mme.Thenardier", "group": 4 },
  34. { "id": "Thenardier", "group": 4 },
  35. { "id": "Cosette", "group": 5 },
  36. { "id": "Javert", "group": 4 },
  37. { "id": "Fauchelevent", "group": 0 },
  38. { "id": "Bamatabois", "group": 2 },
  39. { "id": "Perpetue", "group": 3 },
  40. { "id": "Simplice", "group": 2 },
  41. { "id": "Scaufflaire", "group": 2 },
  42. { "id": "Woman1", "group": 2 },
  43. { "id": "Judge", "group": 2 },
  44. { "id": "Champmathieu", "group": 2 },
  45. { "id": "Brevet", "group": 2 },
  46. { "id": "Chenildieu", "group": 2 },
  47. { "id": "Cochepaille", "group": 2 },
  48. { "id": "Pontmercy", "group": 4 },
  49. { "id": "Boulatruelle", "group": 6 },
  50. { "id": "Eponine", "group": 4 },
  51. { "id": "Anzelma", "group": 4 },
  52. { "id": "Woman2", "group": 5 },
  53. { "id": "MotherInnocent", "group": 0 },
  54. { "id": "Gribier", "group": 0 },
  55. { "id": "Jondrette", "group": 7 },
  56. { "id": "Mme.Burgon", "group": 7 },
  57. { "id": "Gavroche", "group": 8 },
  58. { "id": "Gillenormand", "group": 5 },
  59. { "id": "Magnon", "group": 5 },
  60. { "id": "Mlle.Gillenormand", "group": 5 },
  61. { "id": "Mme.Pontmercy", "group": 5 },
  62. { "id": "Mlle.Vaubois", "group": 5 },
  63. { "id": "Lt.Gillenormand", "group": 5 },
  64. { "id": "Marius", "group": 8 },
  65. { "id": "BaronessT", "group": 5 },
  66. { "id": "Mabeuf", "group": 8 },
  67. { "id": "Enjolras", "group": 8 },
  68. { "id": "Combeferre", "group": 8 },
  69. { "id": "Prouvaire", "group": 8 },
  70. { "id": "Feuilly", "group": 8 },
  71. { "id": "Courfeyrac", "group": 8 },
  72. { "id": "Bahorel", "group": 8 },
  73. { "id": "Bossuet", "group": 8 },
  74. { "id": "Joly", "group": 8 },
  75. { "id": "Grantaire", "group": 8 },
  76. { "id": "MotherPlutarch", "group": 9 },
  77. { "id": "Gueulemer", "group": 4 },
  78. { "id": "Babet", "group": 4 },
  79. { "id": "Claquesous", "group": 4 },
  80. { "id": "Montparnasse", "group": 4 },
  81. { "id": "Toussaint", "group": 5 },
  82. { "id": "Child1", "group": 10 },
  83. { "id": "Child2", "group": 10 },
  84. { "id": "Brujon", "group": 4 },
  85. { "id": "Mme.Hucheloup", "group": 8 }
  86. ],
  87. "links": [
  88. { "source": "Napoleon", "target": "Myriel", "value": 1 },
  89. { "source": "Mlle.Baptistine", "target": "Myriel", "value": 8 },
  90. { "source": "Mme.Magloire", "target": "Myriel", "value": 10 },
  91. { "source": "Mme.Magloire", "target": "Mlle.Baptistine", "value": 6 },
  92. { "source": "CountessdeLo", "target": "Myriel", "value": 1 },
  93. { "source": "Geborand", "target": "Myriel", "value": 1 },
  94. { "source": "Champtercier", "target": "Myriel", "value": 1 },
  95. { "source": "Cravatte", "target": "Myriel", "value": 1 },
  96. { "source": "Count", "target": "Myriel", "value": 2 },
  97. { "source": "OldMan", "target": "Myriel", "value": 1 },
  98. { "source": "Valjean", "target": "Labarre", "value": 1 },
  99. { "source": "Valjean", "target": "Mme.Magloire", "value": 3 },
  100. { "source": "Valjean", "target": "Mlle.Baptistine", "value": 3 },
  101. { "source": "Valjean", "target": "Myriel", "value": 5 },
  102. { "source": "Marguerite", "target": "Valjean", "value": 1 },
  103. { "source": "Mme.deR", "target": "Valjean", "value": 1 },
  104. { "source": "Isabeau", "target": "Valjean", "value": 1 },
  105. { "source": "Gervais", "target": "Valjean", "value": 1 },
  106. { "source": "Listolier", "target": "Tholomyes", "value": 4 },
  107. { "source": "Fameuil", "target": "Tholomyes", "value": 4 },
  108. { "source": "Fameuil", "target": "Listolier", "value": 4 },
  109. { "source": "Blacheville", "target": "Tholomyes", "value": 4 },
  110. { "source": "Blacheville", "target": "Listolier", "value": 4 },
  111. { "source": "Blacheville", "target": "Fameuil", "value": 4 },
  112. { "source": "Favourite", "target": "Tholomyes", "value": 3 },
  113. { "source": "Favourite", "target": "Listolier", "value": 3 },
  114. { "source": "Favourite", "target": "Fameuil", "value": 3 },
  115. { "source": "Favourite", "target": "Blacheville", "value": 4 },
  116. { "source": "Dahlia", "target": "Tholomyes", "value": 3 },
  117. { "source": "Dahlia", "target": "Listolier", "value": 3 },
  118. { "source": "Dahlia", "target": "Fameuil", "value": 3 },
  119. { "source": "Dahlia", "target": "Blacheville", "value": 3 },
  120. { "source": "Dahlia", "target": "Favourite", "value": 5 },
  121. { "source": "Zephine", "target": "Tholomyes", "value": 3 },
  122. { "source": "Zephine", "target": "Listolier", "value": 3 },
  123. { "source": "Zephine", "target": "Fameuil", "value": 3 },
  124. { "source": "Zephine", "target": "Blacheville", "value": 3 },
  125. { "source": "Zephine", "target": "Favourite", "value": 4 },
  126. { "source": "Zephine", "target": "Dahlia", "value": 4 },
  127. { "source": "Fantine", "target": "Tholomyes", "value": 3 },
  128. { "source": "Fantine", "target": "Listolier", "value": 3 },
  129. { "source": "Fantine", "target": "Fameuil", "value": 3 },
  130. { "source": "Fantine", "target": "Blacheville", "value": 3 },
  131. { "source": "Fantine", "target": "Favourite", "value": 4 },
  132. { "source": "Fantine", "target": "Dahlia", "value": 4 },
  133. { "source": "Fantine", "target": "Zephine", "value": 4 },
  134. { "source": "Fantine", "target": "Marguerite", "value": 2 },
  135. { "source": "Fantine", "target": "Valjean", "value": 9 },
  136. { "source": "Mme.Thenardier", "target": "Fantine", "value": 2 },
  137. { "source": "Mme.Thenardier", "target": "Valjean", "value": 7 },
  138. { "source": "Thenardier", "target": "Mme.Thenardier", "value": 13 },
  139. { "source": "Thenardier", "target": "Fantine", "value": 1 },
  140. { "source": "Thenardier", "target": "Valjean", "value": 12 },
  141. { "source": "Cosette", "target": "Mme.Thenardier", "value": 4 },
  142. { "source": "Cosette", "target": "Valjean", "value": 31 },
  143. { "source": "Cosette", "target": "Tholomyes", "value": 1 },
  144. { "source": "Cosette", "target": "Thenardier", "value": 1 },
  145. { "source": "Javert", "target": "Valjean", "value": 17 },
  146. { "source": "Javert", "target": "Fantine", "value": 5 },
  147. { "source": "Javert", "target": "Thenardier", "value": 5 },
  148. { "source": "Javert", "target": "Mme.Thenardier", "value": 1 },
  149. { "source": "Javert", "target": "Cosette", "value": 1 },
  150. { "source": "Fauchelevent", "target": "Valjean", "value": 8 },
  151. { "source": "Fauchelevent", "target": "Javert", "value": 1 },
  152. { "source": "Bamatabois", "target": "Fantine", "value": 1 },
  153. { "source": "Bamatabois", "target": "Javert", "value": 1 },
  154. { "source": "Bamatabois", "target": "Valjean", "value": 2 },
  155. { "source": "Perpetue", "target": "Fantine", "value": 1 },
  156. { "source": "Simplice", "target": "Perpetue", "value": 2 },
  157. { "source": "Simplice", "target": "Valjean", "value": 3 },
  158. { "source": "Simplice", "target": "Fantine", "value": 2 },
  159. { "source": "Simplice", "target": "Javert", "value": 1 },
  160. { "source": "Scaufflaire", "target": "Valjean", "value": 1 },
  161. { "source": "Woman1", "target": "Valjean", "value": 2 },
  162. { "source": "Woman1", "target": "Javert", "value": 1 },
  163. { "source": "Judge", "target": "Valjean", "value": 3 },
  164. { "source": "Judge", "target": "Bamatabois", "value": 2 },
  165. { "source": "Champmathieu", "target": "Valjean", "value": 3 },
  166. { "source": "Champmathieu", "target": "Judge", "value": 3 },
  167. { "source": "Champmathieu", "target": "Bamatabois", "value": 2 },
  168. { "source": "Brevet", "target": "Judge", "value": 2 },
  169. { "source": "Brevet", "target": "Champmathieu", "value": 2 },
  170. { "source": "Brevet", "target": "Valjean", "value": 2 },
  171. { "source": "Brevet", "target": "Bamatabois", "value": 1 },
  172. { "source": "Chenildieu", "target": "Judge", "value": 2 },
  173. { "source": "Chenildieu", "target": "Champmathieu", "value": 2 },
  174. { "source": "Chenildieu", "target": "Brevet", "value": 2 },
  175. { "source": "Chenildieu", "target": "Valjean", "value": 2 },
  176. { "source": "Chenildieu", "target": "Bamatabois", "value": 1 },
  177. { "source": "Cochepaille", "target": "Judge", "value": 2 },
  178. { "source": "Cochepaille", "target": "Champmathieu", "value": 2 },
  179. { "source": "Cochepaille", "target": "Brevet", "value": 2 },
  180. { "source": "Cochepaille", "target": "Chenildieu", "value": 2 },
  181. { "source": "Cochepaille", "target": "Valjean", "value": 2 },
  182. { "source": "Cochepaille", "target": "Bamatabois", "value": 1 },
  183. { "source": "Pontmercy", "target": "Thenardier", "value": 1 },
  184. { "source": "Boulatruelle", "target": "Thenardier", "value": 1 },
  185. { "source": "Eponine", "target": "Mme.Thenardier", "value": 2 },
  186. { "source": "Eponine", "target": "Thenardier", "value": 3 },
  187. { "source": "Anzelma", "target": "Eponine", "value": 2 },
  188. { "source": "Anzelma", "target": "Thenardier", "value": 2 },
  189. { "source": "Anzelma", "target": "Mme.Thenardier", "value": 1 },
  190. { "source": "Woman2", "target": "Valjean", "value": 3 },
  191. { "source": "Woman2", "target": "Cosette", "value": 1 },
  192. { "source": "Woman2", "target": "Javert", "value": 1 },
  193. { "source": "MotherInnocent", "target": "Fauchelevent", "value": 3 },
  194. { "source": "MotherInnocent", "target": "Valjean", "value": 1 },
  195. { "source": "Gribier", "target": "Fauchelevent", "value": 2 },
  196. { "source": "Mme.Burgon", "target": "Jondrette", "value": 1 },
  197. { "source": "Gavroche", "target": "Mme.Burgon", "value": 2 },
  198. { "source": "Gavroche", "target": "Thenardier", "value": 1 },
  199. { "source": "Gavroche", "target": "Javert", "value": 1 },
  200. { "source": "Gavroche", "target": "Valjean", "value": 1 },
  201. { "source": "Gillenormand", "target": "Cosette", "value": 3 },
  202. { "source": "Gillenormand", "target": "Valjean", "value": 2 },
  203. { "source": "Magnon", "target": "Gillenormand", "value": 1 },
  204. { "source": "Magnon", "target": "Mme.Thenardier", "value": 1 },
  205. { "source": "Mlle.Gillenormand", "target": "Gillenormand", "value": 9 },
  206. { "source": "Mlle.Gillenormand", "target": "Cosette", "value": 2 },
  207. { "source": "Mlle.Gillenormand", "target": "Valjean", "value": 2 },
  208. { "source": "Mme.Pontmercy", "target": "Mlle.Gillenormand", "value": 1 },
  209. { "source": "Mme.Pontmercy", "target": "Pontmercy", "value": 1 },
  210. { "source": "Mlle.Vaubois", "target": "Mlle.Gillenormand", "value": 1 },
  211. { "source": "Lt.Gillenormand", "target": "Mlle.Gillenormand", "value": 2 },
  212. { "source": "Lt.Gillenormand", "target": "Gillenormand", "value": 1 },
  213. { "source": "Lt.Gillenormand", "target": "Cosette", "value": 1 },
  214. { "source": "Marius", "target": "Mlle.Gillenormand", "value": 6 },
  215. { "source": "Marius", "target": "Gillenormand", "value": 12 },
  216. { "source": "Marius", "target": "Pontmercy", "value": 1 },
  217. { "source": "Marius", "target": "Lt.Gillenormand", "value": 1 },
  218. { "source": "Marius", "target": "Cosette", "value": 21 },
  219. { "source": "Marius", "target": "Valjean", "value": 19 },
  220. { "source": "Marius", "target": "Tholomyes", "value": 1 },
  221. { "source": "Marius", "target": "Thenardier", "value": 2 },
  222. { "source": "Marius", "target": "Eponine", "value": 5 },
  223. { "source": "Marius", "target": "Gavroche", "value": 4 },
  224. { "source": "BaronessT", "target": "Gillenormand", "value": 1 },
  225. { "source": "BaronessT", "target": "Marius", "value": 1 },
  226. { "source": "Mabeuf", "target": "Marius", "value": 1 },
  227. { "source": "Mabeuf", "target": "Eponine", "value": 1 },
  228. { "source": "Mabeuf", "target": "Gavroche", "value": 1 },
  229. { "source": "Enjolras", "target": "Marius", "value": 7 },
  230. { "source": "Enjolras", "target": "Gavroche", "value": 7 },
  231. { "source": "Enjolras", "target": "Javert", "value": 6 },
  232. { "source": "Enjolras", "target": "Mabeuf", "value": 1 },
  233. { "source": "Enjolras", "target": "Valjean", "value": 4 },
  234. { "source": "Combeferre", "target": "Enjolras", "value": 15 },
  235. { "source": "Combeferre", "target": "Marius", "value": 5 },
  236. { "source": "Combeferre", "target": "Gavroche", "value": 6 },
  237. { "source": "Combeferre", "target": "Mabeuf", "value": 2 },
  238. { "source": "Prouvaire", "target": "Gavroche", "value": 1 },
  239. { "source": "Prouvaire", "target": "Enjolras", "value": 4 },
  240. { "source": "Prouvaire", "target": "Combeferre", "value": 2 },
  241. { "source": "Feuilly", "target": "Gavroche", "value": 2 },
  242. { "source": "Feuilly", "target": "Enjolras", "value": 6 },
  243. { "source": "Feuilly", "target": "Prouvaire", "value": 2 },
  244. { "source": "Feuilly", "target": "Combeferre", "value": 5 },
  245. { "source": "Feuilly", "target": "Mabeuf", "value": 1 },
  246. { "source": "Feuilly", "target": "Marius", "value": 1 },
  247. { "source": "Courfeyrac", "target": "Marius", "value": 9 },
  248. { "source": "Courfeyrac", "target": "Enjolras", "value": 17 },
  249. { "source": "Courfeyrac", "target": "Combeferre", "value": 13 },
  250. { "source": "Courfeyrac", "target": "Gavroche", "value": 7 },
  251. { "source": "Courfeyrac", "target": "Mabeuf", "value": 2 },
  252. { "source": "Courfeyrac", "target": "Eponine", "value": 1 },
  253. { "source": "Courfeyrac", "target": "Feuilly", "value": 6 },
  254. { "source": "Courfeyrac", "target": "Prouvaire", "value": 3 },
  255. { "source": "Bahorel", "target": "Combeferre", "value": 5 },
  256. { "source": "Bahorel", "target": "Gavroche", "value": 5 },
  257. { "source": "Bahorel", "target": "Courfeyrac", "value": 6 },
  258. { "source": "Bahorel", "target": "Mabeuf", "value": 2 },
  259. { "source": "Bahorel", "target": "Enjolras", "value": 4 },
  260. { "source": "Bahorel", "target": "Feuilly", "value": 3 },
  261. { "source": "Bahorel", "target": "Prouvaire", "value": 2 },
  262. { "source": "Bahorel", "target": "Marius", "value": 1 },
  263. { "source": "Bossuet", "target": "Marius", "value": 5 },
  264. { "source": "Bossuet", "target": "Courfeyrac", "value": 12 },
  265. { "source": "Bossuet", "target": "Gavroche", "value": 5 },
  266. { "source": "Bossuet", "target": "Bahorel", "value": 4 },
  267. { "source": "Bossuet", "target": "Enjolras", "value": 10 },
  268. { "source": "Bossuet", "target": "Feuilly", "value": 6 },
  269. { "source": "Bossuet", "target": "Prouvaire", "value": 2 },
  270. { "source": "Bossuet", "target": "Combeferre", "value": 9 },
  271. { "source": "Bossuet", "target": "Mabeuf", "value": 1 },
  272. { "source": "Bossuet", "target": "Valjean", "value": 1 },
  273. { "source": "Joly", "target": "Bahorel", "value": 5 },
  274. { "source": "Joly", "target": "Bossuet", "value": 7 },
  275. { "source": "Joly", "target": "Gavroche", "value": 3 },
  276. { "source": "Joly", "target": "Courfeyrac", "value": 5 },
  277. { "source": "Joly", "target": "Enjolras", "value": 5 },
  278. { "source": "Joly", "target": "Feuilly", "value": 5 },
  279. { "source": "Joly", "target": "Prouvaire", "value": 2 },
  280. { "source": "Joly", "target": "Combeferre", "value": 5 },
  281. { "source": "Joly", "target": "Mabeuf", "value": 1 },
  282. { "source": "Joly", "target": "Marius", "value": 2 },
  283. { "source": "Grantaire", "target": "Bossuet", "value": 3 },
  284. { "source": "Grantaire", "target": "Enjolras", "value": 3 },
  285. { "source": "Grantaire", "target": "Combeferre", "value": 1 },
  286. { "source": "Grantaire", "target": "Courfeyrac", "value": 2 },
  287. { "source": "Grantaire", "target": "Joly", "value": 2 },
  288. { "source": "Grantaire", "target": "Gavroche", "value": 1 },
  289. { "source": "Grantaire", "target": "Bahorel", "value": 1 },
  290. { "source": "Grantaire", "target": "Feuilly", "value": 1 },
  291. { "source": "Grantaire", "target": "Prouvaire", "value": 1 },
  292. { "source": "MotherPlutarch", "target": "Mabeuf", "value": 3 },
  293. { "source": "Gueulemer", "target": "Thenardier", "value": 5 },
  294. { "source": "Gueulemer", "target": "Valjean", "value": 1 },
  295. { "source": "Gueulemer", "target": "Mme.Thenardier", "value": 1 },
  296. { "source": "Gueulemer", "target": "Javert", "value": 1 },
  297. { "source": "Gueulemer", "target": "Gavroche", "value": 1 },
  298. { "source": "Gueulemer", "target": "Eponine", "value": 1 },
  299. { "source": "Babet", "target": "Thenardier", "value": 6 },
  300. { "source": "Babet", "target": "Gueulemer", "value": 6 },
  301. { "source": "Babet", "target": "Valjean", "value": 1 },
  302. { "source": "Babet", "target": "Mme.Thenardier", "value": 1 },
  303. { "source": "Babet", "target": "Javert", "value": 2 },
  304. { "source": "Babet", "target": "Gavroche", "value": 1 },
  305. { "source": "Babet", "target": "Eponine", "value": 1 },
  306. { "source": "Claquesous", "target": "Thenardier", "value": 4 },
  307. { "source": "Claquesous", "target": "Babet", "value": 4 },
  308. { "source": "Claquesous", "target": "Gueulemer", "value": 4 },
  309. { "source": "Claquesous", "target": "Valjean", "value": 1 },
  310. { "source": "Claquesous", "target": "Mme.Thenardier", "value": 1 },
  311. { "source": "Claquesous", "target": "Javert", "value": 1 },
  312. { "source": "Claquesous", "target": "Eponine", "value": 1 },
  313. { "source": "Claquesous", "target": "Enjolras", "value": 1 },
  314. { "source": "Montparnasse", "target": "Javert", "value": 1 },
  315. { "source": "Montparnasse", "target": "Babet", "value": 2 },
  316. { "source": "Montparnasse", "target": "Gueulemer", "value": 2 },
  317. { "source": "Montparnasse", "target": "Claquesous", "value": 2 },
  318. { "source": "Montparnasse", "target": "Valjean", "value": 1 },
  319. { "source": "Montparnasse", "target": "Gavroche", "value": 1 },
  320. { "source": "Montparnasse", "target": "Eponine", "value": 1 },
  321. { "source": "Montparnasse", "target": "Thenardier", "value": 1 },
  322. { "source": "Toussaint", "target": "Cosette", "value": 2 },
  323. { "source": "Toussaint", "target": "Javert", "value": 1 },
  324. { "source": "Toussaint", "target": "Valjean", "value": 1 },
  325. { "source": "Child1", "target": "Gavroche", "value": 2 },
  326. { "source": "Child2", "target": "Gavroche", "value": 2 },
  327. { "source": "Child2", "target": "Child1", "value": 3 },
  328. { "source": "Brujon", "target": "Babet", "value": 3 },
  329. { "source": "Brujon", "target": "Gueulemer", "value": 3 },
  330. { "source": "Brujon", "target": "Thenardier", "value": 3 },
  331. { "source": "Brujon", "target": "Gavroche", "value": 1 },
  332. { "source": "Brujon", "target": "Eponine", "value": 1 },
  333. { "source": "Brujon", "target": "Claquesous", "value": 1 },
  334. { "source": "Brujon", "target": "Montparnasse", "value": 1 },
  335. { "source": "Mme.Hucheloup", "target": "Bossuet", "value": 1 },
  336. { "source": "Mme.Hucheloup", "target": "Joly", "value": 1 },
  337. { "source": "Mme.Hucheloup", "target": "Grantaire", "value": 1 },
  338. { "source": "Mme.Hucheloup", "target": "Bahorel", "value": 1 },
  339. { "source": "Mme.Hucheloup", "target": "Courfeyrac", "value": 1 },
  340. { "source": "Mme.Hucheloup", "target": "Gavroche", "value": 1 },
  341. { "source": "Mme.Hucheloup", "target": "Enjolras", "value": 1 }
  342. ]
  343. };
  344. const emptyGraph = {
  345. nodes: [],
  346. links: [],
  347. }
  348. const graph2 = {
  349. nodes: [
  350. {id: "0", group: 0},
  351. {id: "1", group: 0},
  352. {id: "2", group: 0},
  353. ],
  354. links: [
  355. {source: "0", target: "1", value: 1},
  356. {source: "1", target: "2", value: 1},
  357. {source: "2", target: "0", value: 1},
  358. ],
  359. }
  360. export class App extends React.Component {
  361. render() {
  362. return (
  363. <MantineProvider
  364. withGlobalStyles
  365. withNormalizeCSS
  366. theme={{
  367. colorScheme: 'dark',
  368. colors: {
  369. // override dark colors to change them for all components
  370. dark: [
  371. '#d5d7e0',
  372. '#acaebf',
  373. '#8c8fa3',
  374. '#666980',
  375. '#4d4f66',
  376. '#34354a',
  377. '#2b2c3d',
  378. '#1d1e30',
  379. '#0c0d21',
  380. '#01010a',
  381. ],
  382. },
  383. }}
  384. >
  385. <AppShell
  386. padding="md"
  387. // navbar={<Navbar width={{ base: 300 }} height={500} p="xs">{/* Navbar content */}</Navbar>}
  388. header={<Header height={60} p="xs">{<Title>Onion VCS Demo</Title>}</Header>}
  389. styles={(theme) => ({
  390. main: { backgroundColor: theme.colorScheme === 'dark' ? theme.colors.dark[8] : theme.colors.gray[0] },
  391. })}
  392. >
  393. <Grid grow columns={4}>
  394. <Grid.Col span={2}>
  395. <Group>
  396. <Title order={4}>Graph state</Title>
  397. <Tooltip label="Double click to create node">
  398. <Text><IconInfoCircle/></Text>
  399. </Tooltip>
  400. </Group>
  401. <InteractiveGraph graph={_.cloneDeep(graph2)} />
  402. </Grid.Col>
  403. <Grid.Col span={1}>
  404. <Title order={4}>Version</Title>
  405. <Graph graph={_.cloneDeep(emptyGraph)} mouseDownHandler={()=>{}} mouseUpHandler={()=>{}} />
  406. </Grid.Col>
  407. <Grid.Col span={1}>
  408. <Title order={4}>Delta</Title>
  409. <Graph graph={_.cloneDeep(emptyGraph)} mouseDownHandler={()=>{}} mouseUpHandler={()=>{}} />
  410. </Grid.Col>
  411. </Grid>
  412. </AppShell>
  413. </MantineProvider>
  414. );
  415. }
  416. }