@rocketshow/designer 1.32.0 → 1.35.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (362) hide show
  1. package/assets/i18n/de.json +2 -1
  2. package/assets/i18n/en.json +2 -1
  3. package/esm2022/lib/array-sort-pipe.mjs +30 -0
  4. package/esm2022/lib/designer.component.mjs +672 -0
  5. package/esm2022/lib/designer.module.mjs +186 -0
  6. package/esm2022/lib/designer.service.mjs +14 -0
  7. package/esm2022/lib/dropzone/dropzone.component.mjs +93 -0
  8. package/esm2022/lib/effect/effect-curve/effect-curve.component.mjs +577 -0
  9. package/esm2022/lib/effect/effect-pan-tilt/effect-pan-tilt.component.mjs +36 -0
  10. package/esm2022/lib/effect/effect.component.mjs +174 -0
  11. package/esm2022/lib/error-dialog/error-dialog.component.mjs +75 -0
  12. package/esm2022/lib/fixture/fixture-capability/fixture-capability-channel/fixture-capability-channel.component.mjs +222 -0
  13. package/esm2022/lib/fixture/fixture-capability/fixture-capability-color/fixture-capability-color.component.mjs +147 -0
  14. package/esm2022/lib/fixture/fixture-capability/fixture-capability-color-wheel/fixture-capability-color-wheel.component.mjs +213 -0
  15. package/esm2022/lib/fixture/fixture-capability/fixture-capability-dimmer/fixture-capability-dimmer.component.mjs +78 -0
  16. package/esm2022/lib/fixture/fixture-capability/fixture-capability-pan-tilt/fixture-capability-pan-tilt.component.mjs +119 -0
  17. package/esm2022/lib/fixture/fixture-capability/fixture-capability.component.mjs +169 -0
  18. package/esm2022/lib/fixture/fixture-channel/fixture-channel.component.mjs +162 -0
  19. package/esm2022/lib/fixture/fixture-settings/fixture-settings-position/fixture-settings-position.component.mjs +365 -0
  20. package/esm2022/lib/fixture/fixture-settings/fixture-settings-stage/fixture-settings-stage.component.mjs +151 -0
  21. package/esm2022/lib/fixture/fixture-settings/fixture-settings.component.mjs +46 -0
  22. package/esm2022/lib/fixture/fixture.component.mjs +148 -0
  23. package/esm2022/lib/fixture-pool/fixture-pool-create-from-file/fixture-pool-create-from-file.component.mjs +145 -0
  24. package/esm2022/lib/fixture-pool/fixture-pool.component.mjs +643 -0
  25. package/esm2022/lib/intro/intro.component.mjs +95 -0
  26. package/esm2022/lib/master-dimmer/master-dimmer.component.mjs +66 -0
  27. package/esm2022/lib/models/cached-fixture-capability.mjs +9 -0
  28. package/esm2022/lib/models/cached-fixture-channel.mjs +7 -0
  29. package/esm2022/lib/models/cached-fixture.mjs +6 -0
  30. package/esm2022/lib/models/color.mjs +8 -0
  31. package/esm2022/lib/models/composition.mjs +46 -0
  32. package/esm2022/lib/models/effect-curve-profile-channel.mjs +15 -0
  33. package/esm2022/lib/models/effect-curve.mjs +69 -0
  34. package/esm2022/lib/models/effect-pan-tilt.mjs +19 -0
  35. package/esm2022/lib/models/effect.mjs +12 -0
  36. package/esm2022/lib/models/fixture-capability-value.mjs +15 -0
  37. package/esm2022/lib/models/fixture-capability.mjs +84 -0
  38. package/esm2022/lib/models/fixture-channel-value.mjs +11 -0
  39. package/esm2022/lib/models/fixture-channel.mjs +24 -0
  40. package/esm2022/lib/models/fixture-matrix-pixel-group-constraints.mjs +27 -0
  41. package/esm2022/lib/models/fixture-matrix-pixel-group.mjs +12 -0
  42. package/esm2022/lib/models/fixture-matrix.mjs +25 -0
  43. package/esm2022/lib/models/fixture-mode-channel.mjs +26 -0
  44. package/esm2022/lib/models/fixture-mode.mjs +17 -0
  45. package/esm2022/lib/models/fixture-physical.mjs +14 -0
  46. package/esm2022/lib/models/fixture-profile.mjs +85 -0
  47. package/esm2022/lib/models/fixture-wheel-slot.mjs +26 -0
  48. package/esm2022/lib/models/fixture-wheel.mjs +15 -0
  49. package/esm2022/lib/models/fixture.mjs +40 -0
  50. package/esm2022/lib/models/preset-fixture.mjs +10 -0
  51. package/esm2022/lib/models/preset-region-scene.mjs +8 -0
  52. package/esm2022/lib/models/preset.mjs +65 -0
  53. package/esm2022/lib/models/project.mjs +78 -0
  54. package/esm2022/lib/models/scene-playback-region.mjs +11 -0
  55. package/esm2022/lib/models/scene.mjs +27 -0
  56. package/esm2022/lib/preset/preset-settings/preset-settings.component.mjs +194 -0
  57. package/esm2022/lib/preset/preset.component.mjs +131 -0
  58. package/esm2022/lib/preview/models/color-changer-3d.mjs +64 -0
  59. package/esm2022/lib/preview/models/fixture-3d.mjs +274 -0
  60. package/esm2022/lib/preview/models/moving-head-3d.mjs +124 -0
  61. package/esm2022/lib/preview/preview.component.mjs +219 -0
  62. package/esm2022/lib/project/project-browser/project-browser.component.mjs +143 -0
  63. package/esm2022/lib/project/project-import/project-import.component.mjs +107 -0
  64. package/esm2022/lib/project/project-save/project-save.component.mjs +178 -0
  65. package/esm2022/lib/project/project-share/project-share.component.mjs +71 -0
  66. package/esm2022/lib/scene/scene-settings/scene-settings.component.mjs +146 -0
  67. package/esm2022/lib/scene/scene.component.mjs +110 -0
  68. package/esm2022/lib/services/animation.service.mjs +16 -0
  69. package/esm2022/lib/services/config.service.mjs +28 -0
  70. package/esm2022/lib/services/effect.service.mjs +14 -0
  71. package/esm2022/lib/services/error-dialog.service.mjs +39 -0
  72. package/esm2022/lib/services/fixture-pool.service.mjs +30 -0
  73. package/esm2022/lib/services/fixture.service.mjs +639 -0
  74. package/esm2022/lib/services/hotkey-target-exclude.service.mjs +24 -0
  75. package/esm2022/lib/services/intro.service.mjs +140 -0
  76. package/esm2022/lib/services/preset.service.mjs +449 -0
  77. package/esm2022/lib/services/preview-mesh.service.mjs +57 -0
  78. package/esm2022/lib/services/preview.service.mjs +497 -0
  79. package/esm2022/lib/services/project-load.service.mjs +209 -0
  80. package/esm2022/lib/services/project.service.mjs +93 -0
  81. package/esm2022/lib/services/scene.service.mjs +164 -0
  82. package/esm2022/lib/services/timeline.service.mjs +726 -0
  83. package/esm2022/lib/services/user-ensure-login.service.mjs +38 -0
  84. package/esm2022/lib/services/user.service.mjs +89 -0
  85. package/esm2022/lib/services/uuid.service.mjs +23 -0
  86. package/esm2022/lib/services/warning-dialog.service.mjs +38 -0
  87. package/esm2022/lib/timeline/composition-settings/composition-settings.component.mjs +304 -0
  88. package/esm2022/lib/timeline/timeline-grid/timeline-grid.component.mjs +216 -0
  89. package/esm2022/lib/timeline/timeline.component.mjs +418 -0
  90. package/esm2022/lib/user/user-login/user-login.component.mjs +144 -0
  91. package/esm2022/lib/user/user-register/user-register.component.mjs +220 -0
  92. package/esm2022/lib/wait-dialog/wait-dialog.component.mjs +26 -0
  93. package/esm2022/lib/warning-dialog/warning-dialog.component.mjs +68 -0
  94. package/esm2022/public_api.mjs +7 -0
  95. package/esm2022/rocketshow-designer.mjs +5 -0
  96. package/fesm2022/rocketshow-designer.mjs +11171 -0
  97. package/fesm2022/rocketshow-designer.mjs.map +1 -0
  98. package/index.d.ts +5 -0
  99. package/lib/array-sort-pipe.d.ts +3 -0
  100. package/lib/designer.component.d.ts +19 -16
  101. package/lib/designer.module.d.ts +55 -0
  102. package/lib/designer.service.d.ts +3 -0
  103. package/lib/dropzone/dropzone.component.d.ts +24 -0
  104. package/lib/effect/effect-curve/effect-curve.component.d.ts +4 -1
  105. package/lib/effect/effect-pan-tilt/effect-pan-tilt.component.d.ts +3 -0
  106. package/lib/effect/effect.component.d.ts +3 -0
  107. package/lib/error-dialog/error-dialog.component.d.ts +3 -0
  108. package/lib/fixture/fixture-capability/fixture-capability-channel/fixture-capability-channel.component.d.ts +4 -1
  109. package/lib/fixture/fixture-capability/fixture-capability-color/fixture-capability-color.component.d.ts +3 -0
  110. package/lib/fixture/fixture-capability/fixture-capability-color-wheel/fixture-capability-color-wheel.component.d.ts +5 -2
  111. package/lib/fixture/fixture-capability/fixture-capability-dimmer/fixture-capability-dimmer.component.d.ts +3 -0
  112. package/lib/fixture/fixture-capability/fixture-capability-pan-tilt/fixture-capability-pan-tilt.component.d.ts +3 -0
  113. package/lib/fixture/fixture-capability/fixture-capability.component.d.ts +3 -0
  114. package/lib/fixture/fixture-channel/fixture-channel.component.d.ts +3 -0
  115. package/lib/fixture/fixture-settings/fixture-settings-position/fixture-settings-position.component.d.ts +3 -0
  116. package/lib/fixture/fixture-settings/fixture-settings-stage/fixture-settings-stage.component.d.ts +3 -0
  117. package/lib/fixture/fixture-settings/fixture-settings.component.d.ts +3 -0
  118. package/lib/fixture/fixture.component.d.ts +7 -3
  119. package/lib/fixture-pool/fixture-pool-create-from-file/fixture-pool-create-from-file.component.d.ts +3 -0
  120. package/lib/fixture-pool/fixture-pool.component.d.ts +3 -0
  121. package/lib/intro/intro.component.d.ts +3 -0
  122. package/lib/master-dimmer/master-dimmer.component.d.ts +3 -0
  123. package/lib/models/cached-fixture.d.ts +1 -0
  124. package/lib/models/fixture-matrix-pixel-group-constraints.d.ts +8 -0
  125. package/lib/models/fixture-matrix-pixel-group.d.ts +6 -0
  126. package/lib/models/fixture-matrix.d.ts +6 -0
  127. package/lib/models/fixture-mode-channel.d.ts +8 -0
  128. package/lib/models/fixture-mode.d.ts +3 -1
  129. package/lib/models/fixture-physical.d.ts +4 -0
  130. package/lib/models/fixture-profile.d.ts +5 -0
  131. package/lib/models/preset-fixture.d.ts +5 -0
  132. package/lib/models/preset.d.ts +2 -0
  133. package/lib/models/project.d.ts +3 -0
  134. package/lib/preset/preset-settings/preset-settings.component.d.ts +3 -0
  135. package/lib/preset/preset.component.d.ts +3 -0
  136. package/lib/preview/models/color-changer-3d.d.ts +1 -11
  137. package/lib/preview/models/fixture-3d.d.ts +11 -0
  138. package/lib/preview/models/moving-head-3d.d.ts +1 -11
  139. package/lib/preview/preview.component.d.ts +4 -4
  140. package/lib/project/project-browser/project-browser.component.d.ts +3 -0
  141. package/lib/project/project-import/project-import.component.d.ts +3 -0
  142. package/lib/project/project-save/project-save.component.d.ts +3 -0
  143. package/lib/project/project-share/project-share.component.d.ts +3 -0
  144. package/lib/scene/scene-settings/scene-settings.component.d.ts +3 -0
  145. package/lib/scene/scene.component.d.ts +3 -0
  146. package/lib/services/animation.service.d.ts +3 -0
  147. package/lib/services/config.service.d.ts +4 -0
  148. package/lib/services/effect.service.d.ts +3 -0
  149. package/lib/services/error-dialog.service.d.ts +3 -0
  150. package/lib/services/fixture-pool.service.d.ts +3 -0
  151. package/lib/services/fixture.service.d.ts +10 -2
  152. package/lib/services/hotkey-target-exclude.service.d.ts +3 -0
  153. package/lib/services/intro.service.d.ts +3 -0
  154. package/lib/services/preset.service.d.ts +7 -2
  155. package/lib/services/preview-mesh.service.d.ts +3 -0
  156. package/lib/services/preview.service.d.ts +6 -4
  157. package/lib/services/project-load.service.d.ts +8 -1
  158. package/lib/services/project.service.d.ts +5 -3
  159. package/lib/services/scene.service.d.ts +3 -0
  160. package/lib/services/timeline.service.d.ts +3 -0
  161. package/lib/services/user-ensure-login.service.d.ts +3 -0
  162. package/lib/services/user.service.d.ts +3 -0
  163. package/lib/services/uuid.service.d.ts +3 -0
  164. package/lib/services/warning-dialog.service.d.ts +3 -0
  165. package/lib/timeline/composition-settings/composition-settings.component.d.ts +5 -1
  166. package/lib/timeline/timeline-grid/timeline-grid.component.d.ts +3 -0
  167. package/lib/timeline/timeline.component.d.ts +3 -0
  168. package/lib/user/user-login/user-login.component.d.ts +3 -0
  169. package/lib/user/user-register/user-register.component.d.ts +3 -0
  170. package/lib/wait-dialog/wait-dialog.component.d.ts +3 -0
  171. package/lib/warning-dialog/warning-dialog.component.d.ts +3 -0
  172. package/package.json +20 -22
  173. package/rocketshow-designer-1.35.0.tgz +0 -0
  174. package/bundles/rocketshow-designer.umd.js +0 -9966
  175. package/bundles/rocketshow-designer.umd.js.map +0 -1
  176. package/bundles/rocketshow-designer.umd.min.js +0 -17
  177. package/bundles/rocketshow-designer.umd.min.js.map +0 -1
  178. package/esm2015/lib/array-sort-pipe.js +0 -28
  179. package/esm2015/lib/designer.component.js +0 -411
  180. package/esm2015/lib/designer.module.js +0 -117
  181. package/esm2015/lib/designer.service.js +0 -16
  182. package/esm2015/lib/effect/effect-curve/effect-curve.component.js +0 -325
  183. package/esm2015/lib/effect/effect-pan-tilt/effect-pan-tilt.component.js +0 -30
  184. package/esm2015/lib/effect/effect.component.js +0 -73
  185. package/esm2015/lib/error-dialog/error-dialog.component.js +0 -42
  186. package/esm2015/lib/fixture/fixture-capability/fixture-capability-channel/fixture-capability-channel.component.js +0 -141
  187. package/esm2015/lib/fixture/fixture-capability/fixture-capability-color/fixture-capability-color.component.js +0 -128
  188. package/esm2015/lib/fixture/fixture-capability/fixture-capability-color-wheel/fixture-capability-color-wheel.component.js +0 -163
  189. package/esm2015/lib/fixture/fixture-capability/fixture-capability-dimmer/fixture-capability-dimmer.component.js +0 -60
  190. package/esm2015/lib/fixture/fixture-capability/fixture-capability-pan-tilt/fixture-capability-pan-tilt.component.js +0 -87
  191. package/esm2015/lib/fixture/fixture-capability/fixture-capability.component.js +0 -97
  192. package/esm2015/lib/fixture/fixture-channel/fixture-channel.component.js +0 -66
  193. package/esm2015/lib/fixture/fixture-settings/fixture-settings-position/fixture-settings-position.component.js +0 -200
  194. package/esm2015/lib/fixture/fixture-settings/fixture-settings-stage/fixture-settings-stage.component.js +0 -31
  195. package/esm2015/lib/fixture/fixture-settings/fixture-settings.component.js +0 -35
  196. package/esm2015/lib/fixture/fixture.component.js +0 -70
  197. package/esm2015/lib/fixture-pool/fixture-pool-create-from-file/fixture-pool-create-from-file.component.js +0 -128
  198. package/esm2015/lib/fixture-pool/fixture-pool.component.js +0 -331
  199. package/esm2015/lib/intro/intro.component.js +0 -25
  200. package/esm2015/lib/master-dimmer/master-dimmer.component.js +0 -41
  201. package/esm2015/lib/models/cached-fixture-capability.js +0 -9
  202. package/esm2015/lib/models/cached-fixture-channel.js +0 -7
  203. package/esm2015/lib/models/cached-fixture.js +0 -6
  204. package/esm2015/lib/models/color.js +0 -8
  205. package/esm2015/lib/models/composition.js +0 -46
  206. package/esm2015/lib/models/effect-curve-profile-channel.js +0 -15
  207. package/esm2015/lib/models/effect-curve.js +0 -69
  208. package/esm2015/lib/models/effect-pan-tilt.js +0 -19
  209. package/esm2015/lib/models/effect.js +0 -12
  210. package/esm2015/lib/models/fixture-capability-value.js +0 -15
  211. package/esm2015/lib/models/fixture-capability.js +0 -84
  212. package/esm2015/lib/models/fixture-channel-value.js +0 -11
  213. package/esm2015/lib/models/fixture-channel.js +0 -24
  214. package/esm2015/lib/models/fixture-mode.js +0 -14
  215. package/esm2015/lib/models/fixture-profile.js +0 -70
  216. package/esm2015/lib/models/fixture-wheel-slot.js +0 -26
  217. package/esm2015/lib/models/fixture-wheel.js +0 -15
  218. package/esm2015/lib/models/fixture.js +0 -40
  219. package/esm2015/lib/models/preset-region-scene.js +0 -8
  220. package/esm2015/lib/models/preset.js +0 -56
  221. package/esm2015/lib/models/project.js +0 -68
  222. package/esm2015/lib/models/scene-playback-region.js +0 -11
  223. package/esm2015/lib/models/scene.js +0 -27
  224. package/esm2015/lib/models/universe.js +0 -11
  225. package/esm2015/lib/preset/preset-settings/preset-settings.component.js +0 -66
  226. package/esm2015/lib/preset/preset.component.js +0 -85
  227. package/esm2015/lib/preview/models/color-changer-3d.js +0 -167
  228. package/esm2015/lib/preview/models/fixture-3d.js +0 -150
  229. package/esm2015/lib/preview/models/moving-head-3d.js +0 -233
  230. package/esm2015/lib/preview/preview.component.js +0 -242
  231. package/esm2015/lib/project/project-browser/project-browser.component.js +0 -73
  232. package/esm2015/lib/project/project-import/project-import.component.js +0 -89
  233. package/esm2015/lib/project/project-save/project-save.component.js +0 -105
  234. package/esm2015/lib/project/project-share/project-share.component.js +0 -43
  235. package/esm2015/lib/scene/scene-settings/scene-settings.component.js +0 -52
  236. package/esm2015/lib/scene/scene.component.js +0 -56
  237. package/esm2015/lib/services/animation.service.js +0 -17
  238. package/esm2015/lib/services/config.service.js +0 -28
  239. package/esm2015/lib/services/effect.service.js +0 -16
  240. package/esm2015/lib/services/error-dialog.service.js +0 -44
  241. package/esm2015/lib/services/fixture-pool.service.js +0 -34
  242. package/esm2015/lib/services/fixture.service.js +0 -443
  243. package/esm2015/lib/services/hotkey-target-exclude.service.js +0 -26
  244. package/esm2015/lib/services/intro.service.js +0 -144
  245. package/esm2015/lib/services/preset.service.js +0 -416
  246. package/esm2015/lib/services/preview-mesh.service.js +0 -58
  247. package/esm2015/lib/services/preview.service.js +0 -500
  248. package/esm2015/lib/services/project-load.service.js +0 -171
  249. package/esm2015/lib/services/project.service.js +0 -113
  250. package/esm2015/lib/services/scene.service.js +0 -174
  251. package/esm2015/lib/services/timeline.service.js +0 -738
  252. package/esm2015/lib/services/universe.service.js +0 -24
  253. package/esm2015/lib/services/user-ensure-login.service.js +0 -44
  254. package/esm2015/lib/services/user.service.js +0 -93
  255. package/esm2015/lib/services/uuid.service.js +0 -25
  256. package/esm2015/lib/services/warning-dialog.service.js +0 -43
  257. package/esm2015/lib/timeline/composition-settings/composition-settings.component.js +0 -197
  258. package/esm2015/lib/timeline/timeline-grid/timeline-grid.component.js +0 -55
  259. package/esm2015/lib/timeline/timeline.component.js +0 -239
  260. package/esm2015/lib/user/user-login/user-login.component.js +0 -64
  261. package/esm2015/lib/user/user-register/user-register.component.js +0 -89
  262. package/esm2015/lib/wait-dialog/wait-dialog.component.js +0 -16
  263. package/esm2015/lib/warning-dialog/warning-dialog.component.js +0 -42
  264. package/esm2015/public_api.js +0 -7
  265. package/esm2015/rocketshow-designer.js +0 -61
  266. package/esm5/lib/array-sort-pipe.js +0 -31
  267. package/esm5/lib/designer.component.js +0 -468
  268. package/esm5/lib/designer.module.js +0 -120
  269. package/esm5/lib/designer.service.js +0 -17
  270. package/esm5/lib/effect/effect-curve/effect-curve.component.js +0 -386
  271. package/esm5/lib/effect/effect-pan-tilt/effect-pan-tilt.component.js +0 -31
  272. package/esm5/lib/effect/effect.component.js +0 -75
  273. package/esm5/lib/error-dialog/error-dialog.component.js +0 -43
  274. package/esm5/lib/fixture/fixture-capability/fixture-capability-channel/fixture-capability-channel.component.js +0 -159
  275. package/esm5/lib/fixture/fixture-capability/fixture-capability-color/fixture-capability-color.component.js +0 -130
  276. package/esm5/lib/fixture/fixture-capability/fixture-capability-color-wheel/fixture-capability-color-wheel.component.js +0 -215
  277. package/esm5/lib/fixture/fixture-capability/fixture-capability-dimmer/fixture-capability-dimmer.component.js +0 -61
  278. package/esm5/lib/fixture/fixture-capability/fixture-capability-pan-tilt/fixture-capability-pan-tilt.component.js +0 -88
  279. package/esm5/lib/fixture/fixture-capability/fixture-capability.component.js +0 -130
  280. package/esm5/lib/fixture/fixture-channel/fixture-channel.component.js +0 -68
  281. package/esm5/lib/fixture/fixture-settings/fixture-settings-position/fixture-settings-position.component.js +0 -306
  282. package/esm5/lib/fixture/fixture-settings/fixture-settings-stage/fixture-settings-stage.component.js +0 -32
  283. package/esm5/lib/fixture/fixture-settings/fixture-settings.component.js +0 -36
  284. package/esm5/lib/fixture/fixture.component.js +0 -71
  285. package/esm5/lib/fixture-pool/fixture-pool-create-from-file/fixture-pool-create-from-file.component.js +0 -127
  286. package/esm5/lib/fixture-pool/fixture-pool.component.js +0 -430
  287. package/esm5/lib/intro/intro.component.js +0 -26
  288. package/esm5/lib/master-dimmer/master-dimmer.component.js +0 -42
  289. package/esm5/lib/models/cached-fixture-capability.js +0 -11
  290. package/esm5/lib/models/cached-fixture-channel.js +0 -9
  291. package/esm5/lib/models/cached-fixture.js +0 -8
  292. package/esm5/lib/models/color.js +0 -10
  293. package/esm5/lib/models/composition.js +0 -60
  294. package/esm5/lib/models/effect-curve-profile-channel.js +0 -29
  295. package/esm5/lib/models/effect-curve.js +0 -95
  296. package/esm5/lib/models/effect-pan-tilt.js +0 -24
  297. package/esm5/lib/models/effect.js +0 -14
  298. package/esm5/lib/models/fixture-capability-value.js +0 -17
  299. package/esm5/lib/models/fixture-capability.js +0 -86
  300. package/esm5/lib/models/fixture-channel-value.js +0 -13
  301. package/esm5/lib/models/fixture-channel.js +0 -38
  302. package/esm5/lib/models/fixture-mode.js +0 -16
  303. package/esm5/lib/models/fixture-profile.js +0 -114
  304. package/esm5/lib/models/fixture-wheel-slot.js +0 -28
  305. package/esm5/lib/models/fixture-wheel.js +0 -29
  306. package/esm5/lib/models/fixture.js +0 -42
  307. package/esm5/lib/models/preset-region-scene.js +0 -10
  308. package/esm5/lib/models/preset.js +0 -90
  309. package/esm5/lib/models/project.js +0 -122
  310. package/esm5/lib/models/scene-playback-region.js +0 -13
  311. package/esm5/lib/models/scene.js +0 -29
  312. package/esm5/lib/models/universe.js +0 -13
  313. package/esm5/lib/preset/preset-settings/preset-settings.component.js +0 -67
  314. package/esm5/lib/preset/preset.component.js +0 -86
  315. package/esm5/lib/preview/models/color-changer-3d.js +0 -194
  316. package/esm5/lib/preview/models/fixture-3d.js +0 -196
  317. package/esm5/lib/preview/models/moving-head-3d.js +0 -250
  318. package/esm5/lib/preview/preview.component.js +0 -280
  319. package/esm5/lib/project/project-browser/project-browser.component.js +0 -77
  320. package/esm5/lib/project/project-import/project-import.component.js +0 -88
  321. package/esm5/lib/project/project-save/project-save.component.js +0 -120
  322. package/esm5/lib/project/project-share/project-share.component.js +0 -44
  323. package/esm5/lib/scene/scene-settings/scene-settings.component.js +0 -53
  324. package/esm5/lib/scene/scene.component.js +0 -57
  325. package/esm5/lib/services/animation.service.js +0 -18
  326. package/esm5/lib/services/config.service.js +0 -29
  327. package/esm5/lib/services/effect.service.js +0 -17
  328. package/esm5/lib/services/error-dialog.service.js +0 -46
  329. package/esm5/lib/services/fixture-pool.service.js +0 -36
  330. package/esm5/lib/services/fixture.service.js +0 -643
  331. package/esm5/lib/services/hotkey-target-exclude.service.js +0 -27
  332. package/esm5/lib/services/intro.service.js +0 -145
  333. package/esm5/lib/services/preset.service.js +0 -637
  334. package/esm5/lib/services/preview-mesh.service.js +0 -61
  335. package/esm5/lib/services/preview.service.js +0 -754
  336. package/esm5/lib/services/project-load.service.js +0 -185
  337. package/esm5/lib/services/project.service.js +0 -127
  338. package/esm5/lib/services/scene.service.js +0 -251
  339. package/esm5/lib/services/timeline.service.js +0 -845
  340. package/esm5/lib/services/universe.service.js +0 -36
  341. package/esm5/lib/services/user-ensure-login.service.js +0 -45
  342. package/esm5/lib/services/user.service.js +0 -95
  343. package/esm5/lib/services/uuid.service.js +0 -26
  344. package/esm5/lib/services/warning-dialog.service.js +0 -45
  345. package/esm5/lib/timeline/composition-settings/composition-settings.component.js +0 -206
  346. package/esm5/lib/timeline/timeline-grid/timeline-grid.component.js +0 -56
  347. package/esm5/lib/timeline/timeline.component.js +0 -243
  348. package/esm5/lib/user/user-login/user-login.component.js +0 -66
  349. package/esm5/lib/user/user-register/user-register.component.js +0 -91
  350. package/esm5/lib/wait-dialog/wait-dialog.component.js +0 -18
  351. package/esm5/lib/warning-dialog/warning-dialog.component.js +0 -43
  352. package/esm5/public_api.js +0 -7
  353. package/esm5/rocketshow-designer.js +0 -61
  354. package/fesm2015/rocketshow-designer.js +0 -7945
  355. package/fesm2015/rocketshow-designer.js.map +0 -1
  356. package/fesm5/rocketshow-designer.js +0 -9690
  357. package/fesm5/rocketshow-designer.js.map +0 -1
  358. package/lib/models/universe.d.ts +0 -8
  359. package/lib/services/universe.service.d.ts +0 -6
  360. package/rocketshow-designer-1.32.0.tgz +0 -0
  361. package/rocketshow-designer.d.ts +0 -60
  362. package/rocketshow-designer.metadata.json +0 -1
@@ -0,0 +1,639 @@
1
+ import { HttpClient } from '@angular/common/http';
2
+ import { Injectable } from '@angular/core';
3
+ import { TranslateService } from '@ngx-translate/core';
4
+ import { ToastrService } from 'ngx-toastr';
5
+ import { forkJoin, of } from 'rxjs';
6
+ import { map } from 'rxjs/operators';
7
+ import { CachedFixture } from '../models/cached-fixture';
8
+ import { CachedFixtureCapability } from '../models/cached-fixture-capability';
9
+ import { CachedFixtureChannel } from '../models/cached-fixture-channel';
10
+ import { Color } from '../models/color';
11
+ import { Fixture } from '../models/fixture';
12
+ import { FixtureProfile } from '../models/fixture-profile';
13
+ import { FixtureWheelSlotType } from '../models/fixture-wheel-slot';
14
+ import { ProjectService } from './project.service';
15
+ import { UuidService } from './uuid.service';
16
+ import * as i0 from "@angular/core";
17
+ import * as i1 from "@angular/common/http";
18
+ import * as i2 from "./project.service";
19
+ import * as i3 from "@ngx-translate/core";
20
+ import * as i4 from "ngx-toastr";
21
+ import * as i5 from "./uuid.service";
22
+ export class FixtureService {
23
+ constructor(http, projectService, translateService, toastrService, uuidService) {
24
+ this.http = http;
25
+ this.projectService = projectService;
26
+ this.translateService = translateService;
27
+ this.toastrService = toastrService;
28
+ this.uuidService = uuidService;
29
+ this.cachedFixtures = [];
30
+ // is the side-tab settings currently selected?
31
+ this.settingsSelection = false;
32
+ this.selectedSettingsFixtures = [];
33
+ }
34
+ getFixtureByUuid(uuid) {
35
+ for (const fixture of this.projectService.project.fixtures) {
36
+ if (fixture.uuid === uuid) {
37
+ return fixture;
38
+ }
39
+ }
40
+ }
41
+ getCachedFixtureByUuid(uuid, pixelKey) {
42
+ for (const fixture of this.cachedFixtures) {
43
+ if (fixture.fixture.uuid === uuid && ((!fixture.pixelKey && !pixelKey) || fixture.pixelKey === pixelKey)) {
44
+ return fixture;
45
+ }
46
+ }
47
+ }
48
+ // Get all profiles to search for (only metadata)
49
+ getSearchProfiles() {
50
+ return this.http.get('fixtures').pipe(map((response) => {
51
+ const searchProfiles = [];
52
+ for (const profile of response) {
53
+ searchProfiles.push(new FixtureProfile(profile));
54
+ }
55
+ return searchProfiles;
56
+ }));
57
+ }
58
+ getProfileByUuid(uuid) {
59
+ for (const fixtureProfile of this.projectService.project.fixtureProfiles) {
60
+ if (fixtureProfile.uuid === uuid) {
61
+ return fixtureProfile;
62
+ }
63
+ }
64
+ }
65
+ loadProfileByUuid(uuid) {
66
+ const loadedProfile = this.getProfileByUuid(uuid);
67
+ if (loadedProfile) {
68
+ // This profile is already loaded
69
+ return of(undefined);
70
+ }
71
+ // Load the metadata and the profile
72
+ return forkJoin([this.http.get('fixtures?uuid=' + encodeURI(uuid)), this.http.get('fixture?uuid=' + encodeURI(uuid))]).pipe(map((result) => {
73
+ const mergedData = { ...result[0][0], ...result[1] };
74
+ const fixtureProfile = new FixtureProfile(mergedData);
75
+ this.projectService.project.fixtureProfiles.push(fixtureProfile);
76
+ }));
77
+ }
78
+ getRotationAngleDeg(value) {
79
+ // convert a rotation angle value into degrees
80
+ if (value.endsWith('deg')) {
81
+ return Number.parseInt(value.replace('deg', ''), 10);
82
+ }
83
+ else if (value.endsWith('%')) {
84
+ const perc = Number.parseInt(value.replace('%', ''), 10);
85
+ return (perc / 100) * 360;
86
+ }
87
+ return undefined;
88
+ }
89
+ getWheelSlotColors(wheel, slotNumber) {
90
+ let colors = [];
91
+ const wheelSlots = this.getWheelSlots(wheel, slotNumber);
92
+ for (const slot of wheelSlots) {
93
+ if (slot.colors && slot.colors.length > 0) {
94
+ colors = colors.concat(slot.colors);
95
+ }
96
+ }
97
+ return colors;
98
+ }
99
+ getMixedWheelSlotColor(wheel, slotNumber) {
100
+ const colors = this.getWheelSlotColors(wheel, slotNumber);
101
+ const colorsRgb = [];
102
+ if (colors.length === 0) {
103
+ return undefined;
104
+ }
105
+ for (const color of colors) {
106
+ colorsRgb.push(this.hexToRgb(color));
107
+ }
108
+ return this.mixColors(colorsRgb);
109
+ }
110
+ componentToHex(c) {
111
+ const hex = c.toString(16);
112
+ return hex.length === 1 ? '0' + hex : hex;
113
+ }
114
+ rgbToHex(r, g, b) {
115
+ return '#' + this.componentToHex(r) + this.componentToHex(g) + this.componentToHex(b);
116
+ }
117
+ hexToRgb(hex) {
118
+ // expand shorthand form (e.g. "03F") to full form (e.g. "0033FF")
119
+ const shorthandRegex = /^#?([a-f\d])([a-f\d])([a-f\d])$/i;
120
+ hex = hex.replace(shorthandRegex, (m, r, g, b) => {
121
+ return r + r + g + g + b + b;
122
+ });
123
+ const result = /^#?([a-f\d]{2})([a-f\d]{2})([a-f\d]{2})$/i.exec(hex);
124
+ return result ? new Color(parseInt(result[1], 16), parseInt(result[2], 16), parseInt(result[3], 16)) : null;
125
+ }
126
+ mixColors(colors) {
127
+ // mix an array of rgb-colors containing r, g, b values to a new color
128
+ let r = 0;
129
+ let g = 0;
130
+ let b = 0;
131
+ for (const color of colors) {
132
+ r += color.red;
133
+ g += color.green;
134
+ b += color.blue;
135
+ }
136
+ r /= colors.length;
137
+ g /= colors.length;
138
+ b /= colors.length;
139
+ return new Color(r, g, b);
140
+ }
141
+ wheelHasSlotType(wheel, slotType) {
142
+ for (const slot of wheel.slots) {
143
+ if (slot.type === slotType) {
144
+ return true;
145
+ }
146
+ }
147
+ return false;
148
+ }
149
+ getWheelByName(profile, wheelName) {
150
+ for (const property in profile.wheels) {
151
+ if (property === wheelName) {
152
+ return profile.wheels[property];
153
+ }
154
+ }
155
+ // wheel not found
156
+ return undefined;
157
+ }
158
+ getWheelSlots(wheel, slotNumber) {
159
+ // return one slot or two slots, if they are mixed (e.g. slor number 2.5 returns the slots 2 and 3)
160
+ const slots = [];
161
+ if (!wheel) {
162
+ return slots;
163
+ }
164
+ if (slotNumber - Math.floor(slotNumber) > 0) {
165
+ // two slots are set
166
+ const number = Math.floor(slotNumber);
167
+ slots.push(wheel.slots[number - 1]);
168
+ if (number >= 0 && number < wheel.slots.length) {
169
+ slots.push(wheel.slots[number]);
170
+ }
171
+ }
172
+ else {
173
+ // only one slot is set
174
+ slots.push(wheel.slots[slotNumber - 1]);
175
+ }
176
+ return slots;
177
+ }
178
+ getModeByFixture(profile, fixture) {
179
+ for (const mode of profile.modes) {
180
+ if (mode.shortName) {
181
+ if (mode.shortName === fixture.modeShortName) {
182
+ return mode;
183
+ }
184
+ }
185
+ else {
186
+ if (mode.name === fixture.modeShortName) {
187
+ return mode;
188
+ }
189
+ }
190
+ }
191
+ }
192
+ getFixtureCapability(capability, channelName, profile) {
193
+ const cachedFixtureCapability = new CachedFixtureCapability();
194
+ cachedFixtureCapability.capability = capability;
195
+ if (capability.slotNumber) {
196
+ // there is a wheel connected to this capability
197
+ if (typeof capability.wheel === 'string') {
198
+ cachedFixtureCapability.wheelName = capability.wheel;
199
+ }
200
+ else if (Array.isArray(capability.wheel)) {
201
+ cachedFixtureCapability.wheelName = capability.wheel[0];
202
+ }
203
+ else {
204
+ cachedFixtureCapability.wheelName = channelName;
205
+ }
206
+ cachedFixtureCapability.wheel = this.getWheelByName(profile, cachedFixtureCapability.wheelName);
207
+ cachedFixtureCapability.wheelSlots = this.getWheelSlots(cachedFixtureCapability.wheel, capability.slotNumber);
208
+ cachedFixtureCapability.wheelIsColor = this.wheelHasSlotType(cachedFixtureCapability.wheel, FixtureWheelSlotType.Color);
209
+ }
210
+ if (cachedFixtureCapability.capability.dmxRange && cachedFixtureCapability.capability.dmxRange.length === 2) {
211
+ cachedFixtureCapability.centerValue = Math.floor((cachedFixtureCapability.capability.dmxRange[0] + cachedFixtureCapability.capability.dmxRange[1]) / 2);
212
+ }
213
+ return cachedFixtureCapability;
214
+ }
215
+ getCapabilitiesByChannel(fixtureChannel, channelName, profile) {
216
+ const capabilites = [];
217
+ if (fixtureChannel.capability) {
218
+ capabilites.push(this.getFixtureCapability(fixtureChannel.capability, channelName, profile));
219
+ }
220
+ else if (fixtureChannel.capabilities) {
221
+ for (const capability of fixtureChannel.capabilities) {
222
+ capabilites.push(this.getFixtureCapability(capability, channelName, profile));
223
+ }
224
+ }
225
+ return capabilites;
226
+ }
227
+ getMaxValueByChannel(fixtureChannel) {
228
+ return Math.pow(256, 1 + fixtureChannel.fineChannelAliases.length) - 1;
229
+ }
230
+ getDefaultValueByChannel(fixtureChannel) {
231
+ if (!fixtureChannel.defaultValue) {
232
+ return undefined;
233
+ }
234
+ if (isNaN(fixtureChannel.defaultValue) && fixtureChannel.defaultValue.endsWith('%')) {
235
+ // percentage value
236
+ const percentage = Number.parseInt(fixtureChannel.defaultValue.replace('%', ''), 10);
237
+ const maxValue = this.getMaxValueByChannel(fixtureChannel);
238
+ return (maxValue / 100) * percentage;
239
+ }
240
+ else {
241
+ // DMX value
242
+ return Number.parseInt(fixtureChannel.defaultValue, 10);
243
+ }
244
+ }
245
+ getColorWheelByChannel(channel, profile) {
246
+ for (const channelCapability of channel.capabilities) {
247
+ if (channelCapability.wheelIsColor) {
248
+ return channelCapability.wheel;
249
+ }
250
+ }
251
+ return undefined;
252
+ }
253
+ getChannelByName(fixture, channelName) {
254
+ for (const channel of fixture.channels) {
255
+ if ((channel.name && channel.name === channelName) ||
256
+ (channel.channel && channel.channel.fineChannelAliases.indexOf(channelName) > -1)) {
257
+ return channel;
258
+ }
259
+ }
260
+ return undefined;
261
+ }
262
+ addCachedChannel(channels, channel, templateChannelName, pixelKey, profile) {
263
+ const cachedFixtureChannel = new CachedFixtureChannel();
264
+ const channelName = templateChannelName.replace('$pixelKey', pixelKey);
265
+ cachedFixtureChannel.channel = channel;
266
+ cachedFixtureChannel.name = channelName;
267
+ cachedFixtureChannel.capabilities = this.getCapabilitiesByChannel(cachedFixtureChannel.channel, channelName, profile);
268
+ const defaultValue = this.getDefaultValueByChannel(cachedFixtureChannel.channel);
269
+ if (defaultValue) {
270
+ cachedFixtureChannel.defaultValue = defaultValue;
271
+ }
272
+ cachedFixtureChannel.maxValue = this.getMaxValueByChannel(cachedFixtureChannel.channel);
273
+ cachedFixtureChannel.colorWheel = this.getColorWheelByChannel(cachedFixtureChannel, profile);
274
+ channels.push(cachedFixtureChannel);
275
+ }
276
+ alphanumericSort(a, b) {
277
+ return a.localeCompare(b, undefined, { numeric: true, sensitivity: 'base' });
278
+ }
279
+ getPixelKeysInOrder(profile, repeatFor) {
280
+ let result = [];
281
+ // could contain just a single string (e.g. 'eachPixelABC') or
282
+ if (repeatFor.length > 1) {
283
+ // an array of pixel (groups)
284
+ result = repeatFor;
285
+ }
286
+ else if (repeatFor[0] === 'eachPixelABC') {
287
+ // Gets computed into an alphanumerically sorted list of all pixelKeys
288
+ if (profile.matrix.pixelCount.length === 3) {
289
+ for (let x = 0; x < profile.matrix.pixelCount[0]; x++) {
290
+ for (let y = 0; y < profile.matrix.pixelCount[1]; y++) {
291
+ for (let z = 0; z < profile.matrix.pixelCount[2]; z++) {
292
+ result.push('Pixel ' + (x + 1) + '-' + (y + 1) + '-' + (z + 1));
293
+ }
294
+ }
295
+ }
296
+ }
297
+ else {
298
+ for (let pixelKeyX of profile.matrix.pixelKeys) {
299
+ for (let pixelKeyY of pixelKeyX) {
300
+ for (let pixelKeyZ of pixelKeyY) {
301
+ if (pixelKeyZ) {
302
+ result.push(pixelKeyZ);
303
+ }
304
+ }
305
+ }
306
+ }
307
+ }
308
+ result.sort(this.alphanumericSort);
309
+ }
310
+ else if (repeatFor[0] === 'eachPixelGroup') {
311
+ // Gets computed into an array of all pixel group keys, ordered by appearance in the JSON file
312
+ for (const property of Object.keys(profile.matrix.pixelGroups)) {
313
+ result.push(property);
314
+ }
315
+ }
316
+ else if (repeatFor[0] === 'eachPixelXYZ') {
317
+ for (let x = 0; x < profile.matrix.pixelKeys.length; x++) {
318
+ for (let y = 0; y < profile.matrix.pixelKeys[x].length; y++) {
319
+ for (let z = 0; z < profile.matrix.pixelKeys[x][y].length; z++) {
320
+ const pixel = profile.matrix.pixelKeys[x][y][z];
321
+ if (pixel) {
322
+ result.push(pixel);
323
+ }
324
+ }
325
+ }
326
+ }
327
+ }
328
+ else if (repeatFor[0] === 'eachPixelXZY') {
329
+ for (let x = 0; x < profile.matrix.pixelKeys.length; x++) {
330
+ for (let z = 0; z < profile.matrix.pixelKeys[x][0].length; z++) {
331
+ for (let y = 0; y < profile.matrix.pixelKeys[x].length; y++) {
332
+ const pixel = profile.matrix.pixelKeys[x][y][z];
333
+ if (pixel) {
334
+ result.push(pixel);
335
+ }
336
+ }
337
+ }
338
+ }
339
+ }
340
+ else if (repeatFor[0] === 'eachPixelYXZ') {
341
+ for (let y = 0; y < profile.matrix.pixelKeys[0].length; y++) {
342
+ for (let x = 0; x < profile.matrix.pixelKeys.length; x++) {
343
+ for (let z = 0; z < profile.matrix.pixelKeys[x][y].length; z++) {
344
+ const pixel = profile.matrix.pixelKeys[x][y][z];
345
+ if (pixel) {
346
+ result.push(pixel);
347
+ }
348
+ }
349
+ }
350
+ }
351
+ }
352
+ else if (repeatFor[0] === 'eachPixelYZX') {
353
+ for (let y = 0; y < profile.matrix.pixelKeys[0].length; y++) {
354
+ for (let z = 0; z < profile.matrix.pixelKeys[0][y].length; z++) {
355
+ for (let x = 0; x < profile.matrix.pixelKeys.length; x++) {
356
+ const pixel = profile.matrix.pixelKeys[x][y][z];
357
+ if (pixel) {
358
+ result.push(pixel);
359
+ }
360
+ }
361
+ }
362
+ }
363
+ }
364
+ else if (repeatFor[0] === 'eachPixelZXY') {
365
+ for (let z = 0; z < profile.matrix.pixelKeys[0][0].length; z++) {
366
+ for (let x = 0; x < profile.matrix.pixelKeys.length; x++) {
367
+ for (let y = 0; y < profile.matrix.pixelKeys[x].length; y++) {
368
+ const pixel = profile.matrix.pixelKeys[x][y][z];
369
+ if (pixel) {
370
+ result.push(pixel);
371
+ }
372
+ }
373
+ }
374
+ }
375
+ }
376
+ else if (repeatFor[0] === 'eachPixelZYX') {
377
+ for (let z = 0; z < profile.matrix.pixelKeys[0][0].length; z++) {
378
+ for (let y = 0; y < profile.matrix.pixelKeys[0].length; y++) {
379
+ for (let x = 0; x < profile.matrix.pixelKeys.length; x++) {
380
+ const pixel = profile.matrix.pixelKeys[x][y][z];
381
+ if (pixel) {
382
+ result.push(pixel);
383
+ }
384
+ }
385
+ }
386
+ }
387
+ }
388
+ return result;
389
+ }
390
+ getModeChannelCount(profile, mode) {
391
+ let count = 0;
392
+ // already calculated?
393
+ if (mode.channelCount) {
394
+ return mode.channelCount;
395
+ }
396
+ for (let channel of mode.channels) {
397
+ if (channel.insert === 'matrixChannels') {
398
+ if (channel.repeatFor.length > 1) {
399
+ count += channel.repeatFor.length * channel.templateChannels.length;
400
+ }
401
+ else if (channel.repeatFor[0] === 'eachPixelGroup') {
402
+ count += profile.matrix.pixelGroups.length * channel.templateChannels.length;
403
+ }
404
+ else if (channel.repeatFor[0].startsWith('eachPixel')) {
405
+ if (profile.matrix.pixelCount.length === 3) {
406
+ count +=
407
+ profile.matrix.pixelCount[0] * profile.matrix.pixelCount[1] * profile.matrix.pixelCount[2] * channel.templateChannels.length;
408
+ }
409
+ else {
410
+ for (let x = 0; x < profile.matrix.pixelKeys.length; x++) {
411
+ for (let y = 0; y < profile.matrix.pixelKeys[x].length; y++) {
412
+ for (let z = 0; z < profile.matrix.pixelKeys[x][y].length; z++) {
413
+ const pixel = profile.matrix.pixelKeys[x][y][z];
414
+ if (pixel) {
415
+ count += channel.templateChannels.length;
416
+ }
417
+ }
418
+ }
419
+ }
420
+ }
421
+ }
422
+ }
423
+ else {
424
+ count++;
425
+ }
426
+ }
427
+ mode.channelCount = count;
428
+ return mode.channelCount;
429
+ }
430
+ getCachedChannels(profile, mode, pixelKey) {
431
+ const channels = [];
432
+ if (!mode) {
433
+ return channels;
434
+ }
435
+ for (const channel of mode.channels) {
436
+ if (channel.name && !pixelKey) {
437
+ // direct reference to a channel
438
+ for (const availableChannelName of Object.keys(profile.availableChannels)) {
439
+ // don't check the fine channels. only add the coarse channel.
440
+ if (channel.name === availableChannelName) {
441
+ const availableChannel = profile.availableChannels[availableChannelName];
442
+ this.addCachedChannel(channels, availableChannel, availableChannelName, null, profile);
443
+ }
444
+ }
445
+ }
446
+ else {
447
+ // reference a channel through a pixel matrix
448
+ const availablePixelKeys = this.getPixelKeysInOrder(profile, channel.repeatFor);
449
+ if (channel.channelOrder === 'perPixel') {
450
+ // each channel for each pixel
451
+ for (const availablePixelKey of availablePixelKeys) {
452
+ if (availablePixelKey === pixelKey) {
453
+ for (const modeTemplateChannelName of channel.templateChannels) {
454
+ for (const templateChannelName of Object.keys(profile.templateChannels)) {
455
+ // don't check the fine channels. only add the coarse channel.
456
+ if (modeTemplateChannelName === templateChannelName) {
457
+ const templateChannel = profile.templateChannels[templateChannelName];
458
+ this.addCachedChannel(channels, templateChannel, templateChannelName, availablePixelKey, profile);
459
+ }
460
+ }
461
+ }
462
+ }
463
+ }
464
+ }
465
+ else if (channel.channelOrder === 'perChannel') {
466
+ // each pixel for each channel
467
+ for (const modeTemplateChannelName of channel.templateChannels) {
468
+ for (const availablePixelKey of availablePixelKeys) {
469
+ if (availablePixelKey === pixelKey) {
470
+ for (const templateChannelName of Object.keys(profile.templateChannels)) {
471
+ // don't check the fine channels. only add the coarse channel.
472
+ if (modeTemplateChannelName === templateChannelName) {
473
+ const templateChannel = profile.templateChannels[templateChannelName];
474
+ this.addCachedChannel(channels, templateChannel, templateChannelName, availablePixelKey, profile);
475
+ }
476
+ }
477
+ }
478
+ }
479
+ }
480
+ }
481
+ }
482
+ }
483
+ return channels;
484
+ }
485
+ fixtureGetUniquePixelKeys(fixture) {
486
+ let pixelKeys = new Set();
487
+ let profile = this.getProfileByUuid(fixture.profileUuid);
488
+ let mode = this.getModeByFixture(profile, fixture);
489
+ // add the unique pixel keys
490
+ for (let channel of mode.channels) {
491
+ this.getPixelKeysInOrder(profile, channel.repeatFor).forEach((str) => pixelKeys.add(str));
492
+ }
493
+ return Array.from(pixelKeys);
494
+ }
495
+ updateCachedFixtures() {
496
+ // calculate some frequently used values as a cache to save cpu time
497
+ // afterwards
498
+ this.cachedFixtures = [];
499
+ for (const fixture of this.projectService.project.fixtures) {
500
+ const pixelKeys = this.fixtureGetUniquePixelKeys(fixture);
501
+ if (pixelKeys.length > 0) {
502
+ for (let pixelKey of pixelKeys) {
503
+ const cachedFixture = new CachedFixture();
504
+ cachedFixture.fixture = fixture;
505
+ cachedFixture.pixelKey = pixelKey;
506
+ cachedFixture.profile = this.getProfileByUuid(fixture.profileUuid);
507
+ cachedFixture.mode = this.getModeByFixture(cachedFixture.profile, fixture);
508
+ cachedFixture.channels = this.getCachedChannels(cachedFixture.profile, cachedFixture.mode, pixelKey);
509
+ this.cachedFixtures.push(cachedFixture);
510
+ }
511
+ }
512
+ else {
513
+ const cachedFixture = new CachedFixture();
514
+ cachedFixture.fixture = fixture;
515
+ cachedFixture.profile = this.getProfileByUuid(fixture.profileUuid);
516
+ cachedFixture.mode = this.getModeByFixture(cachedFixture.profile, fixture);
517
+ cachedFixture.channels = this.getCachedChannels(cachedFixture.profile, cachedFixture.mode, null);
518
+ this.cachedFixtures.push(cachedFixture);
519
+ }
520
+ }
521
+ }
522
+ capabilitiesMatch(type1, type2, color1, color2, wheel1, wheel2, profileUuid1, profileUuid2) {
523
+ // checks, whether two provided capapabilities match
524
+ return (type1 === type2 &&
525
+ (!color1 || color1 === color2) &&
526
+ (!wheel1 || wheel1 === wheel2) &&
527
+ (!profileUuid1 || profileUuid1 === profileUuid2));
528
+ }
529
+ settingsFixtureIsSelected(fixture) {
530
+ for (const selectedFixture of this.selectedSettingsFixtures) {
531
+ if (selectedFixture === fixture) {
532
+ return true;
533
+ }
534
+ }
535
+ return false;
536
+ }
537
+ switchSettingsFixtureSelection(fixture) {
538
+ if (this.settingsFixtureIsSelected(fixture)) {
539
+ this.selectedSettingsFixtures.splice(this.selectedSettingsFixtures.indexOf(fixture), 1);
540
+ }
541
+ else {
542
+ this.selectedSettingsFixtures.push(fixture);
543
+ }
544
+ }
545
+ getFixtureIconClass(profile) {
546
+ if (!profile) {
547
+ return '';
548
+ }
549
+ if (profile.categories.length === 0) {
550
+ return '';
551
+ }
552
+ if (!profile.categories[0]) {
553
+ return '';
554
+ }
555
+ return profile.categories[0].replace(' ', '-').toLocaleLowerCase();
556
+ }
557
+ updateProfiles() {
558
+ return this.http.post('update-profiles', null);
559
+ }
560
+ getNextFreeDmxChannel(fixturePool, neededChannels) {
561
+ // get the next free space for this fixture
562
+ let freeChannels = 0;
563
+ for (let i = 0; i < 512; i++) {
564
+ let occupiedChannels = 0;
565
+ for (const fixture of fixturePool) {
566
+ const profile = this.getProfileByUuid(fixture.profileUuid);
567
+ const mode = this.getModeByFixture(this.getProfileByUuid(fixture.profileUuid), fixture);
568
+ const channelCount = this.getModeChannelCount(profile, mode);
569
+ if (i >= fixture.dmxFirstChannel && i < fixture.dmxFirstChannel + channelCount) {
570
+ // this channel is already occupied by a fixture -> move forward to the end of the fixture
571
+ if (channelCount > occupiedChannels) {
572
+ occupiedChannels = channelCount - (i - fixture.dmxFirstChannel);
573
+ }
574
+ }
575
+ }
576
+ if (occupiedChannels > 0) {
577
+ i += occupiedChannels - 1;
578
+ freeChannels = 0;
579
+ }
580
+ else {
581
+ freeChannels++;
582
+ }
583
+ if (freeChannels === neededChannels) {
584
+ return i - freeChannels + 1;
585
+ }
586
+ }
587
+ // no free space left for the needed channels
588
+ return -1;
589
+ }
590
+ addFixture(profile, fixturePool) {
591
+ const fixture = new Fixture();
592
+ fixture.uuid = this.uuidService.getUuid();
593
+ fixture.profileUuid = profile.uuid;
594
+ fixture.name = profile.name;
595
+ if (profile.modes && profile.modes.length > 0) {
596
+ fixture.modeShortName = profile.modes[0].shortName;
597
+ }
598
+ // add the same mode as an existing fixture, if available
599
+ let existingModeShortName;
600
+ for (const existingFixture of fixturePool) {
601
+ const existingProfile = this.getProfileByUuid(existingFixture.profileUuid);
602
+ if (existingProfile === profile) {
603
+ existingModeShortName = existingFixture.modeShortName;
604
+ break;
605
+ }
606
+ }
607
+ if (existingModeShortName) {
608
+ fixture.modeShortName = existingModeShortName;
609
+ }
610
+ else {
611
+ fixture.modeShortName = profile.modes[0].shortName || profile.modes[0].name;
612
+ }
613
+ const mode = this.getModeByFixture(profile, fixture);
614
+ const channelCount = this.getModeChannelCount(profile, mode);
615
+ const firstChannel = this.getNextFreeDmxChannel(fixturePool, channelCount);
616
+ if (firstChannel >= 0) {
617
+ fixture.dmxFirstChannel = firstChannel;
618
+ fixturePool.push(fixture);
619
+ return fixture;
620
+ }
621
+ else {
622
+ // no free space anymore
623
+ const msg = 'designer.fixture-pool.no-free-space';
624
+ const title = 'designer.fixture-pool.no-free-space-title';
625
+ this.translateService.get([msg, title]).subscribe((result) => {
626
+ this.toastrService.error(result[msg], result[title]);
627
+ });
628
+ }
629
+ }
630
+ static { this.ɵfac = function FixtureService_Factory(t) { return new (t || FixtureService)(i0.ɵɵinject(i1.HttpClient), i0.ɵɵinject(i2.ProjectService), i0.ɵɵinject(i3.TranslateService), i0.ɵɵinject(i4.ToastrService), i0.ɵɵinject(i5.UuidService)); }; }
631
+ static { this.ɵprov = /*@__PURE__*/ i0.ɵɵdefineInjectable({ token: FixtureService, factory: FixtureService.ɵfac, providedIn: 'root' }); }
632
+ }
633
+ (() => { (typeof ngDevMode === "undefined" || ngDevMode) && i0.ɵsetClassMetadata(FixtureService, [{
634
+ type: Injectable,
635
+ args: [{
636
+ providedIn: 'root',
637
+ }]
638
+ }], () => [{ type: i1.HttpClient }, { type: i2.ProjectService }, { type: i3.TranslateService }, { type: i4.ToastrService }, { type: i5.UuidService }], null); })();
639
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZml4dHVyZS5zZXJ2aWNlLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vcHJvamVjdHMvZGVzaWduZXIvc3JjL2xpYi9zZXJ2aWNlcy9maXh0dXJlLnNlcnZpY2UudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLHNCQUFzQixDQUFDO0FBQ2xELE9BQU8sRUFBRSxVQUFVLEVBQUUsTUFBTSxlQUFlLENBQUM7QUFDM0MsT0FBTyxFQUFFLGdCQUFnQixFQUFFLE1BQU0scUJBQXFCLENBQUM7QUFDdkQsT0FBTyxFQUFFLGFBQWEsRUFBRSxNQUFNLFlBQVksQ0FBQztBQUMzQyxPQUFPLEVBQUUsUUFBUSxFQUFjLEVBQUUsRUFBRSxNQUFNLE1BQU0sQ0FBQztBQUNoRCxPQUFPLEVBQUUsR0FBRyxFQUFFLE1BQU0sZ0JBQWdCLENBQUM7QUFDckMsT0FBTyxFQUFFLGFBQWEsRUFBRSxNQUFNLDBCQUEwQixDQUFDO0FBQ3pELE9BQU8sRUFBRSx1QkFBdUIsRUFBRSxNQUFNLHFDQUFxQyxDQUFDO0FBQzlFLE9BQU8sRUFBRSxvQkFBb0IsRUFBRSxNQUFNLGtDQUFrQyxDQUFDO0FBQ3hFLE9BQU8sRUFBRSxLQUFLLEVBQUUsTUFBTSxpQkFBaUIsQ0FBQztBQUN4QyxPQUFPLEVBQUUsT0FBTyxFQUFFLE1BQU0sbUJBQW1CLENBQUM7QUFJNUMsT0FBTyxFQUFFLGNBQWMsRUFBRSxNQUFNLDJCQUEyQixDQUFDO0FBRTNELE9BQU8sRUFBb0Isb0JBQW9CLEVBQUUsTUFBTSw4QkFBOEIsQ0FBQztBQUN0RixPQUFPLEVBQUUsY0FBYyxFQUFFLE1BQU0sbUJBQW1CLENBQUM7QUFDbkQsT0FBTyxFQUFFLFdBQVcsRUFBRSxNQUFNLGdCQUFnQixDQUFDOzs7Ozs7O0FBTTdDLE1BQU0sT0FBTyxjQUFjO0lBUXpCLFlBQ1UsSUFBZ0IsRUFDaEIsY0FBOEIsRUFDOUIsZ0JBQWtDLEVBQ2xDLGFBQTRC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QztZQUUxRCxJQUFJLENBQUMsZ0JBQWdCLENBQUMsR0FBRyxDQUFDLENBQUMsR0FBRyxFQUFFLEtBQUssQ0FBQyxDQUFDLENBQUMsU0FBUyxDQUFDLENBQUMsTUFBTSxFQUFFLEVBQUU7Z0JBQzNELElBQUksQ0FBQyxhQUFhLENBQUMsS0FBSyxDQUFDLE1BQU0sQ0FBQyxHQUFHLENBQUMsRUFBRSxNQUFNLENBQUMsS0FBSyxDQUFDLENBQUMsQ0FBQztZQUN2RCxDQUFDLENBQUMsQ0FBQztRQUNMLENBQUM7SUFDSCxDQUFDOytFQXBzQlUsY0FBYzt1RUFBZCxjQUFjLFdBQWQsY0FBYyxtQkFGYixNQUFNOztpRkFFUCxjQUFjO2NBSDFCLFVBQVU7ZUFBQztnQkFDVixVQUFVLEVBQUUsTUFBTTthQUNuQiIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IEh0dHBDbGllbnQgfSBmcm9tICdAYW5ndWxhci9jb21tb24vaHR0cCc7XG5pbXBvcnQgeyBJbmplY3RhYmxlIH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyBUcmFuc2xhdGVTZXJ2aWNlIH0gZnJvbSAnQG5neC10cmFuc2xhdGUvY29yZSc7XG5pbXBvcnQgeyBUb2FzdHJTZXJ2aWNlIH0gZnJvbSAnbmd4LXRvYXN0cic7XG5pbXBvcnQgeyBmb3JrSm9pbiwgT2JzZXJ2YWJsZSwgb2YgfSBmcm9tICdyeGpzJztcbmltcG9ydCB7IG1hcCB9IGZyb20gJ3J4anMvb3BlcmF0b3JzJztcbmltcG9ydCB7IENhY2hlZEZpeHR1cmUgfSBmcm9tICcuLi9tb2RlbHMvY2FjaGVkLWZpeHR1cmUnO1xuaW1wb3J0IHsgQ2FjaGVkRml4dHVyZUNhcGFiaWxpdHkgfSBmcm9tICcuLi9tb2RlbHMvY2FjaGVkLWZpeHR1cmUtY2FwYWJpbGl0eSc7XG5pbXBvcnQgeyBDYWNoZWRGaXh0dXJlQ2hhbm5lbCB9IGZyb20gJy4uL21vZGVscy9jYWNoZWQtZml4dHVyZS1jaGFubmVsJztcbmltcG9ydCB7IENvbG9yIH0gZnJvbSAnLi4vbW9kZWxzL2NvbG9yJztcbmltcG9ydCB7IEZpeHR1cmUgfSBmcm9tICcuLi9tb2RlbHMvZml4dHVyZSc7XG5pbXBvcnQgeyBGaXh0dXJlQ2FwYWJpbGl0eSwgRml4dHVyZUNhcGFiaWxpdHlDb2xvciwgRml4dHVyZUNhcGFiaWxpdHlUeXBlIH0gZnJvbSAnLi4vbW9kZWxzL2ZpeHR1cmUtY2FwYWJpbGl0eSc7XG5pbXBvcnQgeyBGaXh0dXJlQ2hhbm5lbCB9IGZyb20gJy4uL21vZGVscy9maXh0dXJlLWNoYW5uZWwnO1xuaW1wb3J0IHsgRml4dHVyZU1vZGUgfSBmcm9tICcuLi9tb2RlbHMvZml4dHVyZS1tb2RlJztcbmltcG9ydCB7IEZpeHR1cmVQcm9maWxlIH0gZnJvbSAnLi4vbW9kZWxzL2ZpeHR1cmUtcHJvZmlsZSc7XG5pbXBvcnQgeyBGaXh0dXJlV2hlZWwgfSBmcm9tICcuLi9tb2RlbHMvZml4dHVyZS13aGVlbCc7XG5pbXBvcnQgeyBGaXh0dXJlV2hlZWxTbG90LCBGaXh0dXJlV2hlZWxTbG90VHlwZSB9IGZyb20gJy4uL21vZGVscy9maXh0dXJlLXdoZWVsLXNsb3QnO1xuaW1wb3J0IHsgUHJvamVjdFNlcnZpY2UgfSBmcm9tICcuL3Byb2plY3Quc2VydmljZSc7XG5pbXBvcnQgeyBVdWlkU2VydmljZSB9IGZyb20gJy4vdXVpZC5zZXJ2aWNlJztcbmltcG9ydCB7IEZpeHR1cmVNb2RlQ2hhbm5lbCB9IGZyb20gJy4uL21vZGVscy9maXh0dXJlLW1vZGUtY2hhbm5lbCc7XG5cbkBJbmplY3RhYmxlKHtcbiAgcHJvdmlkZWRJbjogJ3Jvb3QnLFxufSlcbmV4cG9ydCBjbGFzcyBGaXh0dXJlU2VydmljZSB7XG4gIGNhY2hlZEZpeHR1cmVzOiBDYWNoZWRGaXh0dXJlW10gPSBbXTtcblxuICAvLyBpcyB0aGUgc2lkZS10YWIgc2V0dGluZ3MgY3VycmVudGx5IHNlbGVjdGVkP1xuICBzZXR0aW5nc1NlbGVjdGlvbiA9IGZhbHNlO1xuXG4gIHNlbGVjdGVkU2V0dGluZ3NGaXh0dXJlczogRml4dHVyZVtdID0gW107XG5cbiAgY29uc3RydWN0b3IoXG4gICAgcHJpdmF0ZSBodHRwOiBIdHRwQ2xpZW50LFxuICAgIHByaXZhdGUgcHJvamVjdFNlcnZpY2U6IFByb2plY3RTZXJ2aWNlLFxuICAgIHByaXZhdGUgdHJhbnNsYXRlU2VydmljZTogVHJhbnNsYXRlU2VydmljZSxcbiAgICBwcml2YXRlIHRvYXN0clNlcnZpY2U6IFRvYXN0clNlcnZpY2UsXG4gICAgcHJpdmF0ZSB1dWlkU2VydmljZTogVXVpZFNlcnZpY2VcbiAgKSB7fVxuXG4gIGdldEZpeHR1cmVCeVV1aWQodXVpZDogc3RyaW5nKTogRml4dHVyZSB7XG4gICAgZm9yIChjb25zdCBmaXh0dXJlIG9mIHRoaXMucHJvamVjdFNlcnZpY2UucHJvamVjdC5maXh0dXJlcykge1xuICAgICAgaWYgKGZpeHR1cmUudXVpZCA9PT0gdXVpZCkge1xuICAgICAgICByZXR1cm4gZml4dHVyZTtcbiAgICAgIH1cbiAgICB9XG4gIH1cblxuICBnZXRDYWNoZWRGaXh0dXJlQnlVdWlkKHV1aWQ6IHN0cmluZywgcGl4ZWxLZXk6IHN0cmluZyk6IENhY2hlZEZpeHR1cmUge1xuICAgIGZvciAoY29uc3QgZml4dHVyZSBvZiB0aGlzLmNhY2hlZEZpeHR1cmVzKSB7XG4gICAgICBpZiAoZml4dHVyZS5maXh0dXJlLnV1aWQgPT09IHV1aWQgJiYgKCghZml4dHVyZS5waXhlbEtleSAmJiAhcGl4ZWxLZXkpIHx8IGZpeHR1cmUucGl4ZWxLZXkgPT09IHBpeGVsS2V5KSkge1xuICAgICAgICByZXR1cm4gZml4dHVyZTtcbiAgICAgIH1cbiAgICB9XG4gIH1cblxuICAvLyBHZXQgYWxsIHByb2ZpbGVzIHRvIHNlYXJjaCBmb3IgKG9ubHkgbWV0YWRhdGEpXG4gIGdldFNlYXJjaFByb2ZpbGVzKCk6IE9ic2VydmFibGU8Rml4dHVyZVByb2ZpbGVbXT4ge1xuICAgIHJldHVybiB0aGlzLmh0dHAuZ2V0KCdmaXh0dXJlcycpLnBpcGUoXG4gICAgICBtYXAoKHJlc3BvbnNlOiBvYmplY3RbXSkgPT4ge1xuICAgICAgICBjb25zdCBzZWFyY2hQcm9maWxlczogRml4dHVyZVByb2ZpbGVbXSA9IFtdO1xuXG4gICAgICAgIGZvciAoY29uc3QgcHJvZmlsZSBvZiByZXNwb25zZSkge1xuICAgICAgICAgIHNlYXJjaFByb2ZpbGVzLnB1c2gobmV3IEZpeHR1cmVQcm9maWxlKHByb2ZpbGUpKTtcbiAgICAgICAgfVxuXG4gICAgICAgIHJldHVybiBzZWFyY2hQcm9maWxlcztcbiAgICAgIH0pXG4gICAgKTtcbiAgfVxuXG4gIGdldFByb2ZpbGVCeVV1aWQodXVpZDogc3RyaW5nKTogRml4dHVyZVByb2ZpbGUge1xuICAgIGZvciAoY29uc3QgZml4dHVyZVByb2ZpbGUgb2YgdGhpcy5wcm9qZWN0U2VydmljZS5wcm9qZWN0LmZpeHR1cmVQcm9maWxlcykge1xuICAgICAgaWYgKGZpeHR1cmVQcm9maWxlLnV1aWQgPT09IHV1aWQpIHtcbiAgICAgICAgcmV0dXJuIGZpeHR1cmVQcm9maWxlO1xuICAgICAgfVxuICAgIH1cbiAgfVxuXG4gIGxvYWRQcm9maWxlQnlVdWlkKHV1aWQ6IHN0cmluZyk6IE9ic2VydmFibGU8dm9pZD4ge1xuICAgIGNvbnN0IGxvYWRlZFByb2ZpbGUgPSB0aGlzLmdldFByb2ZpbGVCeVV1aWQodXVpZCk7XG5cbiAgICBpZiAobG9hZGVkUHJvZmlsZSkge1xuICAgICAgLy8gVGhpcyBwcm9maWxlIGlzIGFscmVhZHkgbG9hZGVkXG4gICAgICByZXR1cm4gb2YodW5kZWZpbmVkKTtcbiAgICB9XG5cbiAgICAvLyBMb2FkIHRoZSBtZXRhZGF0YSBhbmQgdGhlIHByb2ZpbGVcbiAgICByZXR1cm4gZm9ya0pvaW4oW3RoaXMuaHR0cC5nZXQoJ2ZpeHR1cmVzP3V1aWQ9JyArIGVuY29kZVVSSSh1dWlkKSksIHRoaXMuaHR0cC5nZXQoJ2ZpeHR1cmU/dXVpZD0nICsgZW5jb2RlVVJJKHV1aWQpKV0pLnBpcGUoXG4gICAgICBtYXAoKHJlc3VsdCkgPT4ge1xuICAgICAgICBjb25zdCBtZXJnZWREYXRhID0geyAuLi5yZXN1bHRbMF1bMF0sIC4uLnJlc3VsdFsxXSB9O1xuICAgICAgICBjb25zdCBmaXh0dXJlUHJvZmlsZSA9IG5ldyBGaXh0dXJlUHJvZmlsZShtZXJnZWREYXRhKTtcbiAgICAgICAgdGhpcy5wcm9qZWN0U2VydmljZS5wcm9qZWN0LmZpeHR1cmVQcm9maWxlcy5wdXNoKGZpeHR1cmVQcm9maWxlKTtcbiAgICAgIH0pXG4gICAgKTtcbiAgfVxuXG4gIGdldFJvdGF0aW9uQW5nbGVEZWcodmFsdWU6IHN0cmluZyk6IG51bWJlciB7XG4gICAgLy8gY29udmVydCBhIHJvdGF0aW9uIGFuZ2xlIHZhbHVlIGludG8gZGVncmVlc1xuICAgIGlmICh2YWx1ZS5lbmRzV2l0aCgnZGVnJykpIHtcbiAgICAgIHJldHVybiBOdW1iZXIucGFyc2VJbnQodmFsdWUucmVwbGFjZSgnZGVnJywgJycpLCAxMCk7XG4gICAgfSBlbHNlIGlmICh2YWx1ZS5lbmRzV2l0aCgnJScpKSB7XG4gICAgICBjb25zdCBwZXJjID0gTnVtYmVyLnBhcnNlSW50KHZhbHVlLnJlcGxhY2UoJyUnLCAnJyksIDEwKTtcbiAgICAgIHJldHVybiAocGVyYyAvIDEwMCkgKiAzNjA7XG4gICAgfVxuXG4gICAgcmV0dXJuIHVuZGVmaW5lZDtcbiAgfVxuXG4gIGdldFdoZWVsU2xvdENvbG9ycyh3aGVlbDogRml4dHVyZVdoZWVsLCBzbG90TnVtYmVyOiBudW1iZXIpOiBzdHJpbmdbXSB7XG4gICAgbGV0IGNvbG9yczogc3RyaW5nW10gPSBbXTtcbiAgICBjb25zdCB3aGVlbFNsb3RzID0gdGhpcy5nZXRXaGVlbFNsb3RzKHdoZWVsLCBzbG90TnVtYmVyKTtcblxuICAgIGZvciAoY29uc3Qgc2xvdCBvZiB3aGVlbFNsb3RzKSB7XG4gICAgICBpZiAoc2xvdC5jb2xvcnMgJiYgc2xvdC5jb2xvcnMubGVuZ3RoID4gMCkge1xuICAgICAgICBjb2xvcnMgPSBjb2xvcnMuY29uY2F0KHNsb3QuY29sb3JzKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gY29sb3JzO1xuICB9XG5cbiAgZ2V0TWl4ZWRXaGVlbFNsb3RDb2xvcih3aGVlbDogRml4dHVyZVdoZWVsLCBzbG90TnVtYmVyOiBudW1iZXIpOiBDb2xvciB7XG4gICAgY29uc3QgY29sb3JzID0gdGhpcy5nZXRXaGVlbFNsb3RDb2xvcnMod2hlZWwsIHNsb3ROdW1iZXIpO1xuICAgIGNvbnN0IGNvbG9yc1JnYjogQ29sb3JbXSA9IFtdO1xuXG4gICAgaWYgKGNvbG9ycy5sZW5ndGggPT09IDApIHtcbiAgICAgIHJldHVybiB1bmRlZmluZWQ7XG4gICAgfVxuXG4gICAgZm9yIChjb25zdCBjb2xvciBvZiBjb2xvcnMpIHtcbiAgICAgIGNvbG9yc1JnYi5wdXNoKHRoaXMuaGV4VG9SZ2IoY29sb3IpKTtcbiAgICB9XG5cbiAgICByZXR1cm4gdGhpcy5taXhDb2xvcnMoY29sb3JzUmdiKTtcbiAgfVxuXG4gIHByaXZhdGUgY29tcG9uZW50VG9IZXgoYzogbnVtYmVyKTogYW55IHtcbiAgICBjb25zdCBoZXggPSBjLnRvU3RyaW5nKDE2KTtcbiAgICByZXR1cm4gaGV4Lmxlbmd0aCA9PT0gMSA/ICcwJyArIGhleCA6IGhleDtcbiAgfVxuXG4gIHJnYlRvSGV4KHI6IG51bWJlciwgZzogbnVtYmVyLCBiOiBudW1iZXIpOiBzdHJpbmcge1xuICAgIHJldHVybiAnIycgKyB0aGlzLmNvbXBvbmVudFRvSGV4KHIpICsgdGhpcy5jb21wb25lbnRUb0hleChnKSArIHRoaXMuY29tcG9uZW50VG9IZXgoYik7XG4gIH1cblxuICBoZXhUb1JnYihoZXg6IHN0cmluZyk6IENvbG9yIHtcbiAgICAvLyBleHBhbmQgc2hvcnRoYW5kIGZvcm0gKGUuZy4gXCIwM0ZcIikgdG8gZnVsbCBmb3JtIChlLmcuIFwiMDAzM0ZGXCIpXG4gICAgY29uc3Qgc2hvcnRoYW5kUmVnZXggPSAvXiM/KFthLWZcXGRdKShbYS1mXFxkXSkoW2EtZlxcZF0pJC9pO1xuICAgIGhleCA9IGhleC5yZXBsYWNlKHNob3J0aGFuZFJlZ2V4LCAobSwgciwgZywgYikgPT4ge1xuICAgICAgcmV0dXJuIHIgKyByICsgZyArIGcgKyBiICsgYjtcbiAgICB9KTtcblxuICAgIGNvbnN0IHJlc3VsdCA9IC9eIz8oW2EtZlxcZF17Mn0pKFthLWZcXGRdezJ9KShbYS1mXFxkXXsyfSkkL2kuZXhlYyhoZXgpO1xuICAgIHJldHVybiByZXN1bHQgPyBuZXcgQ29sb3IocGFyc2VJbnQocmVzdWx0WzFdLCAxNiksIHBhcnNlSW50KHJlc3VsdFsyXSwgMTYpLCBwYXJzZUludChyZXN1bHRbM10sIDE2KSkgOiBudWxsO1xuICB9XG5cbiAgbWl4Q29sb3JzKGNvbG9yczogQ29sb3JbXSk6IENvbG9yIHtcbiAgICAvLyBtaXggYW4gYXJyYXkgb2YgcmdiLWNvbG9ycyBjb250YWluaW5nIHIsIGcsIGIgdmFsdWVzIHRvIGEgbmV3IGNvbG9yXG4gICAgbGV0IHIgPSAwO1xuICAgIGxldCBnID0gMDtcbiAgICBsZXQgYiA9IDA7XG5cbiAgICBmb3IgKGNvbnN0IGNvbG9yIG9mIGNvbG9ycykge1xuICAgICAgciArPSBjb2xvci5yZWQ7XG4gICAgICBnICs9IGNvbG9yLmdyZWVuO1xuICAgICAgYiArPSBjb2xvci5ibHVlO1xuICAgIH1cblxuICAgIHIgLz0gY29sb3JzLmxlbmd0aDtcbiAgICBnIC89IGNvbG9ycy5sZW5ndGg7XG4gICAgYiAvPSBjb2xvcnMubGVuZ3RoO1xuXG4gICAgcmV0dXJuIG5ldyBDb2xvcihyLCBnLCBiKTtcbiAgfVxuXG4gIHdoZWVsSGFzU2xvdFR5cGUod2hlZWw6IEZpeHR1cmVXaGVlbCwgc2xvdFR5cGU6IEZpeHR1cmVXaGVlbFNsb3RUeXBlKTogYm9vbGVhbiB7XG4gICAgZm9yIChjb25zdCBzbG90IG9mIHdoZWVsLnNsb3RzKSB7XG4gICAgICBpZiAoc2xvdC50eXBlID09PSBzbG90VHlwZSkge1xuICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICBnZXRXaGVlbEJ5TmFtZShwcm9maWxlOiBGaXh0dXJlUHJvZmlsZSwgd2hlZWxOYW1lOiBzdHJpbmcpOiBGaXh0dXJlV2hlZWwge1xuICAgIGZvciAoY29uc3QgcHJvcGVydHkgaW4gcHJvZmlsZS53aGVlbHMpIHtcbiAgICAgIGlmIChwcm9wZXJ0eSA9PT0gd2hlZWxOYW1lKSB7XG4gICAgICAgIHJldHVybiBwcm9maWxlLndoZWVsc1twcm9wZXJ0eV07XG4gICAgICB9XG4gICAgfVxuXG4gICAgLy8gd2hlZWwgbm90IGZvdW5kXG4gICAgcmV0dXJuIHVuZGVmaW5lZDtcbiAgfVxuXG4gIHByaXZhdGUgZ2V0V2hlZWxTbG90cyh3aGVlbDogRml4dHVyZVdoZWVsLCBzbG90TnVtYmVyOiBudW1iZXIpOiBGaXh0dXJlV2hlZWxTbG90W10ge1xuICAgIC8vIHJldHVybiBvbmUgc2xvdCBvciB0d28gc2xvdHMsIGlmIHRoZXkgYXJlIG1peGVkIChlLmcuIHNsb3IgbnVtYmVyIDIuNSByZXR1cm5zIHRoZSBzbG90cyAyIGFuZCAzKVxuICAgIGNvbnN0IHNsb3RzOiBGaXh0dXJlV2hlZWxTbG90W10gPSBbXTtcblxuICAgIGlmICghd2hlZWwpIHtcbiAgICAgIHJldHVybiBzbG90cztcbiAgICB9XG5cbiAgICBpZiAoc2xvdE51bWJlciAtIE1hdGguZmxvb3Ioc2xvdE51bWJlcikgPiAwKSB7XG4gICAgICAvLyB0d28gc2xvdHMgYXJlIHNldFxuICAgICAgY29uc3QgbnVtYmVyID0gTWF0aC5mbG9vcihzbG90TnVtYmVyKTtcbiAgICAgIHNsb3RzLnB1c2god2hlZWwuc2xvdHNbbnVtYmVyIC0gMV0pO1xuICAgICAgaWYgKG51bWJlciA+PSAwICYmIG51bWJlciA8IHdoZWVsLnNsb3RzLmxlbmd0aCkge1xuICAgICAgICBzbG90cy5wdXNoKHdoZWVsLnNsb3RzW251bWJlcl0pO1xuICAgICAgfVxuICAgIH0gZWxzZSB7XG4gICAgICAvLyBvbmx5IG9uZSBzbG90IGlzIHNldFxuICAgICAgc2xvdHMucHVzaCh3aGVlbC5zbG90c1tzbG90TnVtYmVyIC0gMV0pO1xuICAgIH1cblxuICAgIHJldHVybiBzbG90cztcbiAgfVxuXG4gIGdldE1vZGVCeUZpeHR1cmUocHJvZmlsZTogRml4dHVyZVByb2ZpbGUsIGZpeHR1cmU6IEZpeHR1cmUpOiBGaXh0dXJlTW9kZSB7XG4gICAgZm9yIChjb25zdCBtb2RlIG9mIHByb2ZpbGUubW9kZXMpIHtcbiAgICAgIGlmIChtb2RlLnNob3J0TmFtZSkge1xuICAgICAgICBpZiAobW9kZS5zaG9ydE5hbWUgPT09IGZpeHR1cmUubW9kZVNob3J0TmFtZSkge1xuICAgICAgICAgIHJldHVybiBtb2RlO1xuICAgICAgICB9XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBpZiAobW9kZS5uYW1lID09PSBmaXh0dXJlLm1vZGVTaG9ydE5hbWUpIHtcbiAgICAgICAgICByZXR1cm4gbW9kZTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgIH1cbiAgfVxuXG4gIHByaXZhdGUgZ2V0Rml4dHVyZUNhcGFiaWxpdHkoY2FwYWJpbGl0eTogRml4dHVyZUNhcGFiaWxpdHksIGNoYW5uZWxOYW1lOiBzdHJpbmcsIHByb2ZpbGU6IEZpeHR1cmVQcm9maWxlKTogQ2FjaGVkRml4dHVyZUNhcGFiaWxpdHkge1xuICAgIGNvbnN0IGNhY2hlZEZpeHR1cmVDYXBhYmlsaXR5ID0gbmV3IENhY2hlZEZpeHR1cmVDYXBhYmlsaXR5KCk7XG4gICAgY2FjaGVkRml4dHVyZUNhcGFiaWxpdHkuY2FwYWJpbGl0eSA9IGNhcGFiaWxpdHk7XG4gICAgaWYgKGNhcGFiaWxpdHkuc2xvdE51bWJlcikge1xuICAgICAgLy8gdGhlcmUgaXMgYSB3aGVlbCBjb25uZWN0ZWQgdG8gdGhpcyBjYXBhYmlsaXR5XG4gICAgICBpZiAodHlwZW9mIGNhcGFiaWxpdHkud2hlZWwgPT09ICdzdHJpbmcnKSB7XG4gICAgICAgIGNhY2hlZEZpeHR1cmVDYXBhYmlsaXR5LndoZWVsTmFtZSA9IGNhcGFiaWxpdHkud2hlZWwgYXMgc3RyaW5nO1xuICAgICAgfSBlbHNlIGlmIChBcnJheS5pc0FycmF5KGNhcGFiaWxpdHkud2hlZWwpKSB7XG4gICAgICAgIGNhY2hlZEZpeHR1cmVDYXBhYmlsaXR5LndoZWVsTmFtZSA9IGNhcGFiaWxpdHkud2hlZWxbMF07XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBjYWNoZWRGaXh0dXJlQ2FwYWJpbGl0eS53aGVlbE5hbWUgPSBjaGFubmVsTmFtZTtcbiAgICAgIH1cbiAgICAgIGNhY2hlZEZpeHR1cmVDYXBhYmlsaXR5LndoZWVsID0gdGhpcy5nZXRXaGVlbEJ5TmFtZShwcm9maWxlLCBjYWNoZWRGaXh0dXJlQ2FwYWJpbGl0eS53aGVlbE5hbWUpO1xuICAgICAgY2FjaGVkRml4dHVyZUNhcGFiaWxpdHkud2hlZWxTbG90cyA9IHRoaXMuZ2V0V2hlZWxTbG90cyhjYWNoZWRGaXh0dXJlQ2FwYWJpbGl0eS53aGVlbCwgY2FwYWJpbGl0eS5zbG90TnVtYmVyKTtcbiAgICAgIGNhY2hlZEZpeHR1cmVDYXBhYmlsaXR5LndoZWVsSXNDb2xvciA9IHRoaXMud2hlZWxIYXNTbG90VHlwZShjYWNoZWRGaXh0dXJlQ2FwYWJpbGl0eS53aGVlbCwgRml4dHVyZVdoZWVsU2xvdFR5cGUuQ29sb3IpO1xuICAgIH1cbiAgICBpZiAoY2FjaGVkRml4dHVyZUNhcGFiaWxpdHkuY2FwYWJpbGl0eS5kbXhSYW5nZSAmJiBjYWNoZWRGaXh0dXJlQ2FwYWJpbGl0eS5jYXBhYmlsaXR5LmRteFJhbmdlLmxlbmd0aCA9PT0gMikge1xuICAgICAgY2FjaGVkRml4dHVyZUNhcGFiaWxpdHkuY2VudGVyVmFsdWUgPSBNYXRoLmZsb29yKFxuICAgICAgICAoY2FjaGVkRml4dHVyZUNhcGFiaWxpdHkuY2FwYWJpbGl0eS5kbXhSYW5nZVswXSArIGNhY2hlZEZpeHR1cmVDYXBhYmlsaXR5LmNhcGFiaWxpdHkuZG14UmFuZ2VbMV0pIC8gMlxuICAgICAgKTtcbiAgICB9XG4gICAgcmV0dXJuIGNhY2hlZEZpeHR1cmVDYXBhYmlsaXR5O1xuICB9XG5cbiAgcHJpdmF0ZSBnZXRDYXBhYmlsaXRpZXNCeUNoYW5uZWwoXG4gICAgZml4dHVyZUNoYW5uZWw6IEZpeHR1cmVDaGFubmVsLFxuICAgIGNoYW5uZWxOYW1lOiBzdHJpbmcsXG4gICAgcHJvZmlsZTogRml4dHVyZVByb2ZpbGVcbiAgKTogQ2FjaGVkRml4dHVyZUNhcGFiaWxpdHlbXSB7XG4gICAgY29uc3QgY2FwYWJpbGl0ZXM6IENhY2hlZEZpeHR1cmVDYXBhYmlsaXR5W10gPSBbXTtcblxuICAgIGlmIChmaXh0dXJlQ2hhbm5lbC5jYXBhYmlsaXR5KSB7XG4gICAgICBjYXBhYmlsaXRlcy5wdXNoKHRoaXMuZ2V0Rml4dHVyZUNhcGFiaWxpdHkoZml4dHVyZUNoYW5uZWwuY2FwYWJpbGl0eSwgY2hhbm5lbE5hbWUsIHByb2ZpbGUpKTtcbiAgICB9IGVsc2UgaWYgKGZpeHR1cmVDaGFubmVsLmNhcGFiaWxpdGllcykge1xuICAgICAgZm9yIChjb25zdCBjYXBhYmlsaXR5IG9mIGZpeHR1cmVDaGFubmVsLmNhcGFiaWxpdGllcykge1xuICAgICAgICBjYXBhYmlsaXRlcy5wdXNoKHRoaXMuZ2V0Rml4dHVyZUNhcGFiaWxpdHkoY2FwYWJpbGl0eSwgY2hhbm5lbE5hbWUsIHByb2ZpbGUpKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gY2FwYWJpbGl0ZXM7XG4gIH1cblxuICBwcml2YXRlIGdldE1heFZhbHVlQnlDaGFubmVsKGZpeHR1cmVDaGFubmVsOiBGaXh0dXJlQ2hhbm5lbCk6IG51bWJlciB7XG4gICAgcmV0dXJuIE1hdGgucG93KDI1NiwgMSArIGZpeHR1cmVDaGFubmVsLmZpbmVDaGFubmVsQWxpYXNlcy5sZW5ndGgpIC0gMTtcbiAgfVxuXG4gIHByaXZhdGUgZ2V0RGVmYXVsdFZhbHVlQnlDaGFubmVsKGZpeHR1cmVDaGFubmVsOiBGaXh0dXJlQ2hhbm5lbCk6IG51bWJlciB7XG4gICAgaWYgKCFmaXh0dXJlQ2hhbm5lbC5kZWZhdWx0VmFsdWUpIHtcbiAgICAgIHJldHVybiB1bmRlZmluZWQ7XG4gICAgfVxuXG4gICAgaWYgKGlzTmFOKGZpeHR1cmVDaGFubmVsLmRlZmF1bHRWYWx1ZSBhcyBhbnkpICYmIChmaXh0dXJlQ2hhbm5lbC5kZWZhdWx0VmFsdWUgYXMgc3RyaW5nKS5lbmRzV2l0aCgnJScpKSB7XG4gICAgICAvLyBwZXJjZW50YWdlIHZhbHVlXG4gICAgICBjb25zdCBwZXJjZW50YWdlID0gTnVtYmVyLnBhcnNlSW50KChmaXh0dXJlQ2hhbm5lbC5kZWZhdWx0VmFsdWUgYXMgc3RyaW5nKS5yZXBsYWNlKCclJywgJycpLCAxMCk7XG4gICAgICBjb25zdCBtYXhWYWx1ZSA9IHRoaXMuZ2V0TWF4VmFsdWVCeUNoYW5uZWwoZml4dHVyZUNoYW5uZWwpO1xuICAgICAgcmV0dXJuIChtYXhWYWx1ZSAvIDEwMCkgKiBwZXJjZW50YWdlO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBETVggdmFsdWVcbiAgICAgIHJldHVybiBOdW1iZXIucGFyc2VJbnQoZml4dHVyZUNoYW5uZWwuZGVmYXVsdFZhbHVlIGFzIGFueSwgMTApO1xuICAgIH1cbiAgfVxuXG4gIHByaXZhdGUgZ2V0Q29sb3JXaGVlbEJ5Q2hhbm5lbChjaGFubmVsOiBDYWNoZWRGaXh0dXJlQ2hhbm5lbCwgcHJvZmlsZTogRml4dHVyZVByb2ZpbGUpOiBGaXh0dXJlV2hlZWwge1xuICAgIGZvciAoY29uc3QgY2hhbm5lbENhcGFiaWxpdHkgb2YgY2hhbm5lbC5jYXBhYmlsaXRpZXMpIHtcbiAgICAgIGlmIChjaGFubmVsQ2FwYWJpbGl0eS53aGVlbElzQ29sb3IpIHtcbiAgICAgICAgcmV0dXJuIGNoYW5uZWxDYXBhYmlsaXR5LndoZWVsO1xuICAgICAgfVxuICAgIH1cblxuICAgIHJldHVybiB1bmRlZmluZWQ7XG4gIH1cblxuICBnZXRDaGFubmVsQnlOYW1lKGZpeHR1cmU6IENhY2hlZEZpeHR1cmUsIGNoYW5uZWxOYW1lOiBzdHJpbmcpOiBDYWNoZWRGaXh0dXJlQ2hhbm5lbCB7XG4gICAgZm9yIChjb25zdCBjaGFubmVsIG9mIGZpeHR1cmUuY2hhbm5lbHMpIHtcbiAgICAgIGlmIChcbiAgICAgICAgKGNoYW5uZWwubmFtZSAmJiBjaGFubmVsLm5hbWUgPT09IGNoYW5uZWxOYW1lKSB8fFxuICAgICAgICAoY2hhbm5lbC5jaGFubmVsICYmIGNoYW5uZWwuY2hhbm5lbC5maW5lQ2hhbm5lbEFsaWFzZXMuaW5kZXhPZihjaGFubmVsTmFtZSkgPiAtMSlcbiAgICAgICkge1xuICAgICAgICByZXR1cm4gY2hhbm5lbDtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gdW5kZWZpbmVkO1xuICB9XG5cbiAgcHJpdmF0ZSBhZGRDYWNoZWRDaGFubmVsKFxuICAgIGNoYW5uZWxzOiBDYWNoZWRGaXh0dXJlQ2hhbm5lbFtdLFxuICAgIGNoYW5uZWw6IEZpeHR1cmVDaGFubmVsLFxuICAgIHRlbXBsYXRlQ2hhbm5lbE5hbWU6IHN0cmluZyxcbiAgICBwaXhlbEtleTogc3RyaW5nLFxuICAgIHByb2ZpbGU6IEZpeHR1cmVQcm9maWxlXG4gICkge1xuICAgIGNvbnN0IGNhY2hlZEZpeHR1cmVDaGFubmVsID0gbmV3IENhY2hlZEZpeHR1cmVDaGFubmVsKCk7XG4gICAgY29uc3QgY2hhbm5lbE5hbWUgPSB0ZW1wbGF0ZUNoYW5uZWxOYW1lLnJlcGxhY2UoJyRwaXhlbEtleScsIHBpeGVsS2V5KTtcblxuICAgIGNhY2hlZEZpeHR1cmVDaGFubmVsLmNoYW5uZWwgPSBjaGFubmVsO1xuICAgIGNhY2hlZEZpeHR1cmVDaGFubmVsLm5hbWUgPSBjaGFubmVsTmFtZTtcbiAgICBjYWNoZWRGaXh0dXJlQ2hhbm5lbC5jYXBhYmlsaXRpZXMgPSB0aGlzLmdldENhcGFiaWxpdGllc0J5Q2hhbm5lbChjYWNoZWRGaXh0dXJlQ2hhbm5lbC5jaGFubmVsLCBjaGFubmVsTmFtZSwgcHJvZmlsZSk7XG4gICAgY29uc3QgZGVmYXVsdFZhbHVlID0gdGhpcy5nZXREZWZhdWx0VmFsdWVCeUNoYW5uZWwoY2FjaGVkRml4dHVyZUNoYW5uZWwuY2hhbm5lbCk7XG4gICAgaWYgKGRlZmF1bHRWYWx1ZSkge1xuICAgICAgY2FjaGVkRml4dHVyZUNoYW5uZWwuZGVmYXVsdFZhbHVlID0gZGVmYXVsdFZhbHVlO1xuICAgIH1cbiAgICBjYWNoZWRGaXh0dXJlQ2hhbm5lbC5tYXhWYWx1ZSA9IHRoaXMuZ2V0TWF4VmFsdWVCeUNoYW5uZWwoY2FjaGVkRml4dHVyZUNoYW5uZWwuY2hhbm5lbCk7XG4gICAgY2FjaGVkRml4dHVyZUNoYW5uZWwuY29sb3JXaGVlbCA9IHRoaXMuZ2V0Q29sb3JXaGVlbEJ5Q2hhbm5lbChjYWNoZWRGaXh0dXJlQ2hhbm5lbCwgcHJvZmlsZSk7XG4gICAgY2hhbm5lbHMucHVzaChjYWNoZWRGaXh0dXJlQ2hhbm5lbCk7XG4gIH1cblxuICBwcml2YXRlIGFscGhhbnVtZXJpY1NvcnQoYTogc3RyaW5nLCBiOiBzdHJpbmcpOiBudW1iZXIge1xuICAgIHJldHVybiBhLmxvY2FsZUNvbXBhcmUoYiwgdW5kZWZpbmVkLCB7IG51bWVyaWM6IHRydWUsIHNlbnNpdGl2aXR5OiAnYmFzZScgfSk7XG4gIH1cblxuICBwcml2YXRlIGdldFBpeGVsS2V5c0luT3JkZXIocHJvZmlsZTogRml4dHVyZVByb2ZpbGUsIHJlcGVhdEZvcjogc3RyaW5nW10pOiBzdHJpbmdbXSB7XG4gICAgbGV0IHJlc3VsdDogc3RyaW5nW10gPSBbXTtcblxuICAgIC8vIGNvdWxkIGNvbnRhaW4ganVzdCBhIHNpbmdsZSBzdHJpbmcgKGUuZy4gJ2VhY2hQaXhlbEFCQycpIG9yXG4gICAgaWYgKHJlcGVhdEZvci5sZW5ndGggPiAxKSB7XG4gICAgICAvLyBhbiBhcnJheSBvZiBwaXhlbCAoZ3JvdXBzKVxuICAgICAgcmVzdWx0ID0gcmVwZWF0Rm9yO1xuICAgIH0gZWxzZSBpZiAocmVwZWF0Rm9yWzBdID09PSAnZWFjaFBpeGVsQUJDJykge1xuICAgICAgLy8gR2V0cyBjb21wdXRlZCBpbnRvIGFuIGFscGhhbnVtZXJpY2FsbHkgc29ydGVkIGxpc3Qgb2YgYWxsIHBpeGVsS2V5c1xuICAgICAgaWYgKHByb2ZpbGUubWF0cml4LnBpeGVsQ291bnQubGVuZ3RoID09PSAzKSB7XG4gICAgICAgIGZvciAobGV0IHggPSAwOyB4IDwgcHJvZmlsZS5tYXRyaXgucGl4ZWxDb3VudFswXTsgeCsrKSB7XG4gICAgICAgICAgZm9yIChsZXQgeSA9IDA7IHkgPCBwcm9maWxlLm1hdHJpeC5waXhlbENvdW50WzFdOyB5KyspIHtcbiAgICAgICAgICAgIGZvciAobGV0IHogPSAwOyB6IDwgcHJvZmlsZS5tYXRyaXgucGl4ZWxDb3VudFsyXTsgeisrKSB7XG4gICAgICAgICAgICAgIHJlc3VsdC5wdXNoKCdQaXhlbCAnICsgKHggKyAxKSArICctJyArICh5ICsgMSkgKyAnLScgKyAoeiArIDEpKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGZvciAobGV0IHBpeGVsS2V5WCBvZiBwcm9maWxlLm1hdHJpeC5waXhlbEtleXMpIHtcbiAgICAgICAgICBmb3IgKGxldCBwaXhlbEtleVkgb2YgcGl4ZWxLZXlYKSB7XG4gICAgICAgICAgICBmb3IgKGxldCBwaXhlbEtleVogb2YgcGl4ZWxLZXlZKSB7XG4gICAgICAgICAgICAgIGlmIChwaXhlbEtleVopIHtcbiAgICAgICAgICAgICAgICByZXN1bHQucHVzaChwaXhlbEtleVopO1xuICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICB9XG4gICAgICByZXN1bHQuc29ydCh0aGlzLmFscGhhbnVtZXJpY1NvcnQpO1xuICAgIH0gZWxzZSBpZiAocmVwZWF0Rm9yWzBdID09PSAnZWFjaFBpeGVsR3JvdXAnKSB7XG4gICAgICAvLyBHZXRzIGNvbXB1dGVkIGludG8gYW4gYXJyYXkgb2YgYWxsIHBpeGVsIGdyb3VwIGtleXMsIG9yZGVyZWQgYnkgYXBwZWFyYW5jZSBpbiB0aGUgSlNPTiBmaWxlXG4gICAgICBmb3IgKGNvbnN0IHByb3BlcnR5IG9mIE9iamVjdC5rZXlzKHByb2ZpbGUubWF0cml4LnBpeGVsR3JvdXBzKSkge1xuICAgICAgICByZXN1bHQucHVzaChwcm9wZXJ0eSk7XG4gICAgICB9XG4gICAgfSBlbHNlIGlmIChyZXBlYXRGb3JbMF0gPT09ICdlYWNoUGl4ZWxYWVonKSB7XG4gICAgICBmb3IgKGxldCB4ID0gMDsgeCA8IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5cy5sZW5ndGg7IHgrKykge1xuICAgICAgICBmb3IgKGxldCB5ID0gMDsgeSA8IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1t4XS5sZW5ndGg7IHkrKykge1xuICAgICAgICAgIGZvciAobGV0IHogPSAwOyB6IDwgcHJvZmlsZS5tYXRyaXgucGl4ZWxLZXlzW3hdW3ldLmxlbmd0aDsgeisrKSB7XG4gICAgICAgICAgICBjb25zdCBwaXhlbCA9IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1t4XVt5XVt6XTtcbiAgICAgICAgICAgIGlmIChwaXhlbCkge1xuICAgICAgICAgICAgICByZXN1bHQucHVzaChwaXhlbCk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICB9XG4gICAgfSBlbHNlIGlmIChyZXBlYXRGb3JbMF0gPT09ICdlYWNoUGl4ZWxYWlknKSB7XG4gICAgICBmb3IgKGxldCB4ID0gMDsgeCA8IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5cy5sZW5ndGg7IHgrKykge1xuICAgICAgICBmb3IgKGxldCB6ID0gMDsgeiA8IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1t4XVswXS5sZW5ndGg7IHorKykge1xuICAgICAgICAgIGZvciAobGV0IHkgPSAwOyB5IDwgcHJvZmlsZS5tYXRyaXgucGl4ZWxLZXlzW3hdLmxlbmd0aDsgeSsrKSB7XG4gICAgICAgICAgICBjb25zdCBwaXhlbCA9IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1t4XVt5XVt6XTtcbiAgICAgICAgICAgIGlmIChwaXhlbCkge1xuICAgICAgICAgICAgICByZXN1bHQucHVzaChwaXhlbCk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICB9XG4gICAgfSBlbHNlIGlmIChyZXBlYXRGb3JbMF0gPT09ICdlYWNoUGl4ZWxZWFonKSB7XG4gICAgICBmb3IgKGxldCB5ID0gMDsgeSA8IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1swXS5sZW5ndGg7IHkrKykge1xuICAgICAgICBmb3IgKGxldCB4ID0gMDsgeCA8IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5cy5sZW5ndGg7IHgrKykge1xuICAgICAgICAgIGZvciAobGV0IHogPSAwOyB6IDwgcHJvZmlsZS5tYXRyaXgucGl4ZWxLZXlzW3hdW3ldLmxlbmd0aDsgeisrKSB7XG4gICAgICAgICAgICBjb25zdCBwaXhlbCA9IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1t4XVt5XVt6XTtcbiAgICAgICAgICAgIGlmIChwaXhlbCkge1xuICAgICAgICAgICAgICByZXN1bHQucHVzaChwaXhlbCk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICB9XG4gICAgfSBlbHNlIGlmIChyZXBlYXRGb3JbMF0gPT09ICdlYWNoUGl4ZWxZWlgnKSB7XG4gICAgICBmb3IgKGxldCB5ID0gMDsgeSA8IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1swXS5sZW5ndGg7IHkrKykge1xuICAgICAgICBmb3IgKGxldCB6ID0gMDsgeiA8IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1swXVt5XS5sZW5ndGg7IHorKykge1xuICAgICAgICAgIGZvciAobGV0IHggPSAwOyB4IDwgcHJvZmlsZS5tYXRyaXgucGl4ZWxLZXlzLmxlbmd0aDsgeCsrKSB7XG4gICAgICAgICAgICBjb25zdCBwaXhlbCA9IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1t4XVt5XVt6XTtcbiAgICAgICAgICAgIGlmIChwaXhlbCkge1xuICAgICAgICAgICAgICByZXN1bHQucHVzaChwaXhlbCk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICB9XG4gICAgfSBlbHNlIGlmIChyZXBlYXRGb3JbMF0gPT09ICdlYWNoUGl4ZWxaWFknKSB7XG4gICAgICBmb3IgKGxldCB6ID0gMDsgeiA8IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1swXVswXS5sZW5ndGg7IHorKykge1xuICAgICAgICBmb3IgKGxldCB4ID0gMDsgeCA8IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5cy5sZW5ndGg7IHgrKykge1xuICAgICAgICAgIGZvciAobGV0IHkgPSAwOyB5IDwgcHJvZmlsZS5tYXRyaXgucGl4ZWxLZXlzW3hdLmxlbmd0aDsgeSsrKSB7XG4gICAgICAgICAgICBjb25zdCBwaXhlbCA9IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1t4XVt5XVt6XTtcbiAgICAgICAgICAgIGlmIChwaXhlbCkge1xuICAgICAgICAgICAgICByZXN1bHQucHVzaChwaXhlbCk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICB9XG4gICAgfSBlbHNlIGlmIChyZXBlYXRGb3JbMF0gPT09ICdlYWNoUGl4ZWxaWVgnKSB7XG4gICAgICBmb3IgKGxldCB6ID0gMDsgeiA8IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1swXVswXS5sZW5ndGg7IHorKykge1xuICAgICAgICBmb3IgKGxldCB5ID0gMDsgeSA8IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1swXS5sZW5ndGg7IHkrKykge1xuICAgICAgICAgIGZvciAobGV0IHggPSAwOyB4IDwgcHJvZmlsZS5tYXRyaXgucGl4ZWxLZXlzLmxlbmd0aDsgeCsrKSB7XG4gICAgICAgICAgICBjb25zdCBwaXhlbCA9IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1t4XVt5XVt6XTtcbiAgICAgICAgICAgIGlmIChwaXhlbCkge1xuICAgICAgICAgICAgICByZXN1bHQucHVzaChwaXhlbCk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIHJlc3VsdDtcbiAgfVxuXG4gIGdldE1vZGVDaGFubmVsQ291bnQocHJvZmlsZTogRml4dHVyZVByb2ZpbGUsIG1vZGU6IEZpeHR1cmVNb2RlKTogbnVtYmVyIHtcbiAgICBsZXQgY291bnQ6IG51bWJlciA9IDA7XG5cbiAgICAvLyBhbHJlYWR5IGNhbGN1bGF0ZWQ/XG4gICAgaWYgKG1vZGUuY2hhbm5lbENvdW50KSB7XG4gICAgICByZXR1cm4gbW9kZS5jaGFubmVsQ291bnQ7XG4gICAgfVxuXG4gICAgZm9yIChsZXQgY2hhbm5lbCBvZiBtb2RlLmNoYW5uZWxzKSB7XG4gICAgICBpZiAoY2hhbm5lbC5pbnNlcnQgPT09ICdtYXRyaXhDaGFubmVscycpIHtcbiAgICAgICAgaWYgKGNoYW5uZWwucmVwZWF0Rm9yLmxlbmd0aCA+IDEpIHtcbiAgICAgICAgICBjb3VudCArPSBjaGFubmVsLnJlcGVhdEZvci5sZW5ndGggKiBjaGFubmVsLnRlbXBsYXRlQ2hhbm5lbHMubGVuZ3RoO1xuICAgICAgICB9IGVsc2UgaWYgKGNoYW5uZWwucmVwZWF0Rm9yWzBdID09PSAnZWFjaFBpeGVsR3JvdXAnKSB7XG4gICAgICAgICAgY291bnQgKz0gcHJvZmlsZS5tYXRyaXgucGl4ZWxHcm91cHMubGVuZ3RoICogY2hhbm5lbC50ZW1wbGF0ZUNoYW5uZWxzLmxlbmd0aDtcbiAgICAgICAgfSBlbHNlIGlmIChjaGFubmVsLnJlcGVhdEZvclswXS5zdGFydHNXaXRoKCdlYWNoUGl4ZWwnKSkge1xuICAgICAgICAgIGlmIChwcm9maWxlLm1hdHJpeC5waXhlbENvdW50Lmxlbmd0aCA9PT0gMykge1xuICAgICAgICAgICAgY291bnQgKz1cbiAgICAgICAgICAgICAgcHJvZmlsZS5tYXRyaXgucGl4ZWxDb3VudFswXSAqIHByb2ZpbGUubWF0cml4LnBpeGVsQ291bnRbMV0gKiBwcm9maWxlLm1hdHJpeC5waXhlbENvdW50WzJdICogY2hhbm5lbC50ZW1wbGF0ZUNoYW5uZWxzLmxlbmd0aDtcbiAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgZm9yIChsZXQgeCA9IDA7IHggPCBwcm9maWxlLm1hdHJpeC5waXhlbEtleXMubGVuZ3RoOyB4KyspIHtcbiAgICAgICAgICAgICAgZm9yIChsZXQgeSA9IDA7IHkgPCBwcm9maWxlLm1hdHJpeC5waXhlbEtleXNbeF0ubGVuZ3RoOyB5KyspIHtcbiAgICAgICAgICAgICAgICBmb3IgKGxldCB6ID0gMDsgeiA8IHByb2ZpbGUubWF0cml4LnBpeGVsS2V5c1t4XVt5XS5sZW5ndGg7IHorKykge1xuICAgICAgICAgICAgICAgICAgY29uc3QgcGl4ZWwgPSBwcm9maWxlLm1hdHJpeC5waXhlbEtleXNbeF1beV1bel07XG4gICAgICAgICAgICAgICAgICBpZiAocGl4ZWwpIHtcbiAgICAgICAgICAgICAgICAgICAgY291bnQgKz0gY2hhbm5lbC50ZW1wbGF0ZUNoYW5uZWxzLmxlbmd0aDtcbiAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGNvdW50Kys7XG4gICAgICB9XG4gICAgfVxuXG4gICAgbW9kZS5jaGFubmVsQ291bnQgPSBjb3VudDtcblxuICAgIHJldHVybiBtb2RlLmNoYW5uZWxDb3VudDtcbiAgfVxuXG4gIGdldENhY2hlZENoYW5uZWxzKHByb2ZpbGU6IEZpeHR1cmVQcm9maWxlLCBtb2RlOiBGaXh0dXJlTW9kZSwgcGl4ZWxLZXk6IHN0cmluZyk6IENhY2hlZEZpeHR1cmVDaGFubmVsW10ge1xuICAgIGNvbnN0IGNoYW5uZWxzOiBDYWNoZWRGaXh0dXJlQ2hhbm5lbFtdID0gW107XG5cbiAgICBpZiAoIW1vZGUpIHtcbiAgICAgIHJldHVybiBjaGFubmVscztcbiAgICB9XG5cbiAgICBmb3IgKGNvbnN0IGNoYW5uZWwgb2YgbW9kZS5jaGFubmVscykge1xuICAgICAgaWYgKGNoYW5uZWwubmFtZSAmJiAhcGl4ZWxLZXkpIHtcbiAgICAgICAgLy8gZGlyZWN0IHJlZmVyZW5jZSB0byBhIGNoYW5uZWxcblxuICAgICAgICBmb3IgKGNvbnN0IGF2YWlsYWJsZUNoYW5uZWxOYW1lIG9mIE9iamVjdC5rZXlzKHByb2ZpbGUuYXZhaWxhYmxlQ2hhbm5lbHMpKSB7XG4gICAgICAgICAgLy8gZG9uJ3QgY2hlY2sgdGhlIGZpbmUgY2hhbm5lbHMuIG9ubHkgYWRkIHRoZSBjb2Fyc2UgY2hhbm5lbC5cbiAgICAgICAgICBpZiAoY2hhbm5lbC5uYW1lID09PSBhdmFpbGFibGVDaGFubmVsTmFtZSkge1xuICAgICAgICAgICAgY29uc3QgYXZhaWxhYmxlQ2hhbm5lbDogRml4dHVyZUNoYW5uZWwgPSBwcm9maWxlLmF2YWlsYWJsZUNoYW5uZWxzW2F2YWlsYWJsZUNoYW5uZWxOYW1lXTtcblxuICAgICAgICAgICAgdGhpcy5hZGRDYWNoZWRDaGFubmVsKGNoYW5uZWxzLCBhdmFpbGFibGVDaGFubmVsLCBhdmFpbGFibGVDaGFubmVsTmFtZSwgbnVsbCwgcHJvZmlsZSk7XG4gICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICB9IGVsc2Uge1xuICAgICAgICAvLyByZWZlcmVuY2UgYSBjaGFubmVsIHRocm91Z2ggYSBwaXhlbCBtYXRyaXhcbiAgICAgICAgY29uc3QgYXZhaWxhYmxlUGl4ZWxLZXlzID0gdGhpcy5nZXRQaXhlbEtleXNJbk9yZGVyKHByb2ZpbGUsIGNoYW5uZWwucmVwZWF0Rm9yKTtcblxuICAgICAgICBpZiAoY2hhbm5lbC5jaGFubmVsT3JkZXIgPT09ICdwZXJQaXhlbCcpIHtcbiAgICAgICAgICAvLyBlYWNoIGNoYW5uZWwgZm9yIGVhY2ggcGl4ZWxcblxuICAgICAgICAgIGZvciAoY29uc3QgYXZhaWxhYmxlUGl4ZWxLZXkgb2YgYXZhaWxhYmxlUGl4ZWxLZXlzKSB7XG4gICAgICAgICAgICBpZiAoYXZhaWxhYmxlUGl4ZWxLZXkgPT09IHBpeGVsS2V5KSB7XG4gICAgICAgICAgICAgIGZvciAoY29uc3QgbW9kZVRlbXBsYXRlQ2hhbm5lbE5hbWUgb2YgY2hhbm5lbC50ZW1wbGF0ZUNoYW5uZWxzKSB7XG4gICAgICAgICAgICAgICAgZm9yIChjb25zdCB0ZW1wbGF0ZUNoYW5uZWxOYW1lIG9mIE9iamVjdC5rZXlzKHByb2ZpbGUudGVtcGxhdGVDaGFubmVscykpIHtcbiAgICAgICAgICAgICAgICAgIC8vIGRvbid0IGNoZWNrIHRoZSBmaW5lIGNoYW5uZWxzLiBvbmx5IGFkZCB0aGUgY29hcnNlIGNoYW5uZWwuXG4gICAgICAgICAgICAgICAgICBpZiAobW9kZVRlbXBsYXRlQ2hhbm5lbE5hbWUgPT09IHRlbXBsYXRlQ2hhbm5lbE5hbWUpIHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3QgdGVtcGxhdGVDaGFubmVsOiBGaXh0dXJlQ2hhbm5lbCA9IHByb2ZpbGUudGVtcGxhdGVDaGFubmVsc1t0ZW1wbGF0ZUNoYW5uZWxOYW1lXTtcblxuICAgICAgICAgICAgICAgICAgICB0aGlzLmFkZENhY2hlZENoYW5uZWwoY2hhbm5lbHMsIHRlbXBsYXRlQ2hhbm5lbCwgdGVtcGxhdGVDaGFubmVsTmFtZSwgYXZhaWxhYmxlUGl4ZWxLZXksIHByb2ZpbGUpO1xuICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfVxuICAgICAgICAgIH1cbiAgICAgICAgfSBlbHNlIGlmIChjaGFubmVsLmNoYW5uZWxPcmRlciA9PT0gJ3BlckNoYW5uZWwnKSB7XG4gICAgICAgICAgLy8gZWFjaCBwaXhlbCBmb3IgZWFjaCBjaGFubmVsXG5cbiAgICAgICAgICBmb3IgKGNvbnN0IG1vZGVUZW1wbGF0ZUNoYW5uZWxOYW1lIG9mIGNoYW5uZWwudGVtcGxhdGVDaGFubmVscykge1xuICAgICAgICAgICAgZm9yIChjb25zdCBhdmFpbGFibGVQaXhlbEtleSBvZiBhdmFpbGFibGVQaXhlbEtleXMpIHtcbiAgICAgICAgICAgICAgaWYgKGF2YWlsYWJsZVBpeGVsS2V5ID09PSBwaXhlbEtleSkge1xuICAgICAgICAgICAgICAgIGZvciAoY29uc3QgdGVtcGxhdGVDaGFubmVsTmFtZSBvZiBPYmplY3Qua2V5cyhwcm9maWxlLnRlbXBsYXRlQ2hhbm5lbHMpKSB7XG4gICAgICAgICAgICAgICAgICAvLyBkb24ndCBjaGVjayB0aGUgZmluZSBjaGFubmVscy4gb25seSBhZGQgdGhlIGNvYXJzZSBjaGFubmVsLlxuICAgICAgICAgICAgICAgICAgaWYgKG1vZGVUZW1wbGF0ZUNoYW5uZWxOYW1lID09PSB0ZW1wbGF0ZUNoYW5uZWxOYW1lKSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHRlbXBsYXRlQ2hhbm5lbDogRml4dHVyZUNoYW5uZWwgPSBwcm9maWxlLnRlbXBsYXRlQ2hhbm5lbHNbdGVtcGxhdGVDaGFubmVsTmFtZV07XG5cbiAgICAgICAgICAgICAgICAgICAgdGhpcy5hZGRDYWNoZWRDaGFubmVsKGNoYW5uZWxzLCB0ZW1wbGF0ZUNoYW5uZWwsIHRlbXBsYXRlQ2hhbm5lbE5hbWUsIGF2YWlsYWJsZVBpeGVsS2V5LCBwcm9maWxlKTtcbiAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gY2hhbm5lbHM7XG4gIH1cblxuICBmaXh0dXJlR2V0VW5pcXVlUGl4ZWxLZXlzKGZpeHR1cmU6IEZpeHR1cmUpOiBzdHJpbmdbXSB7XG4gICAgbGV0IHBpeGVsS2V5czogU2V0PHN0cmluZz4gPSBuZXcgU2V0KCk7XG5cbiAgICBsZXQgcHJvZmlsZSA9IHRoaXMuZ2V0UHJvZmlsZUJ5VXVpZChmaXh0dXJlLnByb2ZpbGVVdWlkKTtcbiAgICBsZXQgbW9kZSA9IHRoaXMuZ2V0TW9kZUJ5Rml4dHVyZShwcm9maWxlLCBmaXh0dXJlKTtcblxuICAgIC8vIGFkZCB0aGUgdW5pcXVlIHBpeGVsIGtleXNcbiAgICBmb3IgKGxldCBjaGFubmVsIG9mIG1vZGUuY2hhbm5lbHMpIHtcbiAgICAgIHRoaXMuZ2V0UGl4ZWxLZXlzSW5PcmRlcihwcm9maWxlLCBjaGFubmVsLnJlcGVhdEZvcikuZm9yRWFjaCgoc3RyKSA9PiBwaXhlbEtleXMuYWRkKHN0cikpO1xuICAgIH1cblxuICAgIHJldHVybiBBcnJheS5mcm9tKHBpeGVsS2V5cyk7XG4gIH1cblxuICB1cGRhdGVDYWNoZWRGaXh0dXJlcygpIHtcbiAgICAvLyBjYWxjdWxhdGUgc29tZSBmcmVxdWVudGx5IHVzZWQgdmFsdWVzIGFzIGEgY2FjaGUgdG8gc2F2ZSBjcHUgdGltZVxuICAgIC8vIGFmdGVyd2FyZHNcbiAgICB0aGlzLmNhY2hlZEZpeHR1cmVzID0gW107XG5cbiAgICBmb3IgKGNvbnN0IGZpeHR1cmUgb2YgdGhpcy5wcm9qZWN0U2VydmljZS5wcm9qZWN0LmZpeHR1cmVzKSB7XG4gICAgICBjb25zdCBwaXhlbEtleXMgPSB0aGlzLmZpeHR1cmVHZXRVbmlxdWVQaXhlbEtleXMoZml4dHVyZSk7XG4gICAgICBpZiAocGl4ZWxLZXlzLmxlbmd0aCA+IDApIHtcbiAgICAgICAgZm9yIChsZXQgcGl4ZWxLZXkgb2YgcGl4ZWxLZXlzKSB7XG4gICAgICAgICAgY29uc3QgY2FjaGVkRml4dHVyZSA9IG5ldyBDYWNoZWRGaXh0dXJlKCk7XG4gICAgICAgICAgY2FjaGVkRml4dHVyZS5maXh0dXJlID0gZml4dHVyZTtcbiAgICAgICAgICBjYWNoZWRGaXh0dXJlLnBpeGVsS2V5ID0gcGl4ZWxLZXk7XG4gICAgICAgICAgY2FjaGVkRml4dHVyZS5wcm9maWxlID0gdGhpcy5nZXRQcm9maWxlQnlVdWlkKGZpeHR1cmUucHJvZmlsZVV1aWQpO1xuICAgICAgICAgIGNhY2hlZEZpeHR1cmUubW9kZSA9IHRoaXMuZ2V0TW9kZUJ5Rml4dHVyZShjYWNoZWRGaXh0dXJlLnByb2ZpbGUsIGZpeHR1cmUpO1xuICAgICAgICAgIGNhY2hlZEZpeHR1cmUuY2hhbm5lbHMgPSB0aGlzLmdldENhY2hlZENoYW5uZWxzKGNhY2hlZEZpeHR1cmUucHJvZmlsZSwgY2FjaGVkRml4dHVyZS5tb2RlLCBwaXhlbEtleSk7XG4gICAgICAgICAgdGhpcy5jYWNoZWRGaXh0dXJlcy5wdXNoKGNhY2hlZEZpeHR1cmUpO1xuICAgICAgICB9XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBjb25zdCBjYWNoZWRGaXh0dXJlID0gbmV3IENhY2hlZEZpeHR1cmUoKTtcbiAgICAgICAgY2FjaGVkRml4dHVyZS5maXh0dXJlID0gZml4dHVyZTtcbiAgICAgICAgY2FjaGVkRml4dHVyZS5wcm9maWxlID0gdGhpcy5nZXRQcm9maWxlQnlVdWlkKGZpeHR1cmUucHJvZmlsZVV1aWQpO1xuICAgICAgICBjYWNoZWRGaXh0dXJlLm1vZGUgPSB0aGlzLmdldE1vZGVCeUZpeHR1cmUoY2FjaGVkRml4dHVyZS5wcm9maWxlLCBmaXh0dXJlKTtcbiAgICAgICAgY2FjaGVkRml4dHVyZS5jaGFubmVscyA9IHRoaXMuZ2V0Q2FjaGVkQ2hhbm5lbHMoY2FjaGVkRml4dHVyZS5wcm9maWxlLCBjYWNoZWRGaXh0dXJlLm1vZGUsIG51bGwpO1xuICAgICAgICB0aGlzLmNhY2hlZEZpeHR1cmVzLnB1c2goY2FjaGVkRml4dHVyZSk7XG4gICAgICB9XG4gICAgfVxuICB9XG5cbiAgY2FwYWJpbGl0aWVzTWF0Y2goXG4gICAgdHlwZTE6IEZpeHR1cmVDYXBhYmlsaXR5VHlwZSxcbiAgICB0eXBlMjogRml4dHVyZUNhcGFiaWxpdHlUeXBlLFxuICAgIGNvbG9yMTogRml4dHVyZUNhcGFiaWxpdHlDb2xvcixcbiAgICBjb2xvcjI6IEZpeHR1cmVDYXBhYmlsaXR5Q29sb3IsXG4gICAgd2hlZWwxOiBzdHJpbmcsXG4gICAgd2hlZWwyOiBzdHJpbmcsXG4gICAgcHJvZmlsZVV1aWQxOiBzdHJpbmcsXG4gICAgcHJvZmlsZVV1aWQyOiBzdHJpbmdcbiAgKTogYm9vbGVhbiB7XG4gICAgLy8gY2hlY2tzLCB3aGV0aGVyIHR3byBwcm92aWRlZCBjYXBhcGFiaWxpdGllcyBtYXRjaFxuICAgIHJldHVybiAoXG4gICAgICB0eXBlMSA9PT0gdHlwZTIgJiZcbiAgICAgICghY29sb3IxIHx8IGNvbG9yMSA9PT0gY29sb3IyKSAmJlxuICAgICAgKCF3aGVlbDEgfHwgd2hlZWwxID09PSB3aGVlbDIpICYmXG4gICAgICAoIXByb2ZpbGVVdWlkMSB8fCBwcm9maWxlVXVpZDEgPT09IHByb2ZpbGVVdWlkMilcbiAgICApO1xuICB9XG5cbiAgc2V0dGluZ3NGaXh0dXJlSXNTZWxlY3RlZChmaXh0dXJlOiBGaXh0dXJlKTogYm9vbGVhbiB7XG4gICAgZm9yIChjb25zdCBzZWxlY3RlZEZpeHR1cmUgb2YgdGhpcy5zZWxlY3RlZFNldHRpbmdzRml4dHVyZXMpIHtcbiAgICAgIGlmIChzZWxlY3RlZEZpeHR1cmUgPT09IGZpeHR1cmUpIHtcbiAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG5cbiAgc3dpdGNoU2V0dGluZ3NGaXh0dXJlU2VsZWN0aW9uKGZpeHR1cmU6IEZpeHR1cmUpIHtcbiAgICBpZiAodGhpcy5zZXR0aW5nc0ZpeHR1cmVJc1NlbGVjdGVkKGZpeHR1cmUpKSB7XG4gICAgICB0aGlzLnNlbGVjdGVkU2V0dGluZ3NGaXh0dXJlcy5zcGxpY2UodGhpcy5zZWxlY3RlZFNldHRpbmdzRml4dHVyZXMuaW5kZXhPZihmaXh0dXJlKSwgMSk7XG4gICAgfSBlbHNlIHtcbiAgICAgIHRoaXMuc2VsZWN0ZWRTZXR0aW5nc0ZpeHR1cmVzLnB1c2goZml4dHVyZSk7XG4gICAgfVxuICB9XG5cbiAgZ2V0Rml4dHVyZUljb25DbGFzcyhwcm9maWxlOiBGaXh0dXJlUHJvZmlsZSk6IHN0cmluZyB7XG4gICAgaWYgKCFwcm9maWxlKSB7XG4gICAgICByZXR1cm4gJyc7XG4gICAgfVxuICAgIGlmIChwcm9maWxlLmNhdGVnb3JpZXMubGVuZ3RoID09PSAwKSB7XG4gICAgICByZXR1cm4gJyc7XG4gICAgfVxuICAgIGlmICghcHJvZmlsZS5jYXRlZ29yaWVzWzBdKSB7XG4gICAgICByZXR1cm4gJyc7XG4gICAgfVxuICAgIHJldHVybiBwcm9maWxlLmNhdGVnb3JpZXNbMF0ucmVwbGFjZSgnICcsICctJykudG9Mb2NhbGVMb3dlckNhc2UoKTtcbiAgfVxuXG4gIHVwZGF0ZVByb2ZpbGVzKCkge1xuICAgIHJldHVybiB0aGlzLmh0dHAucG9zdCgndXBkYXRlLXByb2ZpbGVzJywgbnVsbCk7XG4gIH1cblxuICBnZXROZXh0RnJlZURteENoYW5uZWwoZml4dHVyZVBvb2w6IEZpeHR1cmVbXSwgbmVlZGVkQ2hhbm5lbHM6IG51bWJlcik6IG51bWJlciB7XG4gICAgLy8gZ2V0IHRoZSBuZXh0IGZyZWUgc3BhY2UgZm9yIHRoaXMgZml4dHVyZVxuICAgIGxldCBmcmVlQ2hhbm5lbHMgPSAwO1xuXG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCA1MTI7IGkrKykge1xuICAgICAgbGV0IG9jY3VwaWVkQ2hhbm5lbHMgPSAwO1xuXG4gICAgICBmb3IgKGNvbnN0IGZpeHR1cmUgb2YgZml4dHVyZVBvb2wpIHtcbiAgICAgICAgY29uc3QgcHJvZmlsZSA9IHRoaXMuZ2V0UHJvZmlsZUJ5VXVpZChmaXh0dXJlLnByb2ZpbGVVdWlkKTtcbiAgICAgICAgY29uc3QgbW9kZSA9IHRoaXMuZ2V0TW9kZUJ5Rml4dHVyZSh0aGlzLmdldFByb2ZpbGVCeVV1aWQoZml4dHVyZS5wcm9maWxlVXVpZCksIGZpeHR1cmUpO1xuICAgICAgICBjb25zdCBjaGFubmVsQ291bnQgPSB0aGlzLmdldE1vZGVDaGFubmVsQ291bnQocHJvZmlsZSwgbW9kZSk7XG5cbiAgICAgICAgaWYgKGkgPj0gZml4dHVyZS5kbXhGaXJzdENoYW5uZWwgJiYgaSA8IGZpeHR1cmUuZG14Rmlyc3RDaGFubmVsICsgY2hhbm5lbENvdW50KSB7XG4gICAgICAgICAgLy8gdGhpcyBjaGFubmVsIGlzIGFscmVhZHkgb2NjdXBpZWQgYnkgYSBmaXh0dXJlIC0+IG1vdmUgZm9yd2FyZCB0byB0aGUgZW5kIG9mIHRoZSBmaXh0dXJlXG4gICAgICAgICAgaWYgKGNoYW5uZWxDb3VudCA+IG9jY3VwaWVkQ2hhbm5lbHMpIHtcbiAgICAgICAgICAgIG9jY3VwaWVkQ2hhbm5lbHMgPSBjaGFubmVsQ291bnQgLSAoaSAtIGZpeHR1cmUuZG14Rmlyc3RDaGFubmVsKTtcbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgIH1cblxuICAgICAgaWYgKG9jY3VwaWVkQ2hhbm5lbHMgPiAwKSB7XG4gICAgICAgIGkgKz0gb2NjdXBpZWRDaGFubmVscyAtIDE7XG4gICAgICAgIGZyZWVDaGFubmVscyA9IDA7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBmcmVlQ2hhbm5lbHMrKztcbiAgICAgIH1cblxuICAgICAgaWYgKGZyZWVDaGFubmVscyA9PT0gbmVlZGVkQ2hhbm5lbHMpIHtcbiAgICAgICAgcmV0dXJuIGkgLSBmcmVlQ2hhbm5lbHMgKyAxO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8vIG5vIGZyZWUgc3BhY2UgbGVmdCBmb3IgdGhlIG5lZWRlZCBjaGFubmVsc1xuICAgIHJldHVybiAtMTtcbiAgfVxuXG4gIGFkZEZpeHR1cmUocHJvZmlsZTogRml4dHVyZVByb2ZpbGUsIGZpeHR1cmVQb29sOiBGaXh0dXJlW10pOiBGaXh0dXJlIHtcbiAgICBjb25zdCBmaXh0dXJlID0gbmV3IEZpeHR1cmUoKTtcblxuICAgIGZpeHR1cmUudXVpZCA9IHRoaXMudXVpZFNlcnZpY2UuZ2V0VXVpZCgpO1xuICAgIGZpeHR1cmUucHJvZmlsZVV1aWQgPSBwcm9maWxlLnV1aWQ7XG4gICAgZml4dHVyZS5uYW1lID0gcHJvZmlsZS5uYW1lO1xuXG4gICAgaWYgKHByb2ZpbGUubW9kZXMgJiYgcHJvZmlsZS5tb2Rlcy5sZW5ndGggPiAwKSB7XG4gICAgICBmaXh0dXJlLm1vZGVTaG9ydE5hbWUgPSBwcm9maWxlLm1vZGVzWzBdLnNob3J0TmFtZTtcbiAgICB9XG5cbiAgICAvLyBhZGQgdGhlIHNhbWUgbW9kZSBhcyBhbiBleGlzdGluZyBmaXh0dXJlLCBpZiBhdmFpbGFibGVcbiAgICBsZXQgZXhpc3RpbmdNb2RlU2hvcnROYW1lOiBzdHJpbmc7XG4gICAgZm9yIChjb25zdCBleGlzdGluZ0ZpeHR1cmUgb2YgZml4dHVyZVBvb2wpIHtcbiAgICAgIGNvbnN0IGV4aXN0aW5nUHJvZmlsZSA9IHRoaXMuZ2V0UHJvZmlsZUJ5VXVpZChleGlzdGluZ0ZpeHR1cmUucHJvZmlsZVV1aWQpO1xuXG4gICAgICBpZiAoZXhpc3RpbmdQcm9maWxlID09PSBwcm9maWxlKSB7XG4gICAgICAgIGV4aXN0aW5nTW9kZVNob3J0TmFtZSA9IGV4aXN0aW5nRml4dHVyZS5tb2RlU2hvcnROYW1lO1xuICAgICAgICBicmVhaztcbiAgICAgIH1cbiAgICB9XG5cbiAgICBpZiAoZXhpc3RpbmdNb2RlU2hvcnROYW1lKSB7XG4gICAgICBmaXh0dXJlLm1vZGVTaG9ydE5hbWUgPSBleGlzdGluZ01vZGVTaG9ydE5hbWU7XG4gICAgfSBlbHNlIHtcbiAgICAgIGZpeHR1cmUubW9kZVNob3J0TmFtZSA9IHByb2ZpbGUubW9kZXNbMF0uc2hvcnROYW1lIHx8IHByb2ZpbGUubW9kZXNbMF0ubmFtZTtcbiAgICB9XG5cbiAgICBjb25zdCBtb2RlID0gdGhpcy5nZXRNb2RlQnlGaXh0dXJlKHByb2ZpbGUsIGZpeHR1cmUpO1xuICAgIGNvbnN0IGNoYW5uZWxDb3VudCA9IHRoaXMuZ2V0TW9kZUNoYW5uZWxDb3VudChwcm9maWxlLCBtb2RlKTtcbiAgICBjb25zdCBmaXJzdENoYW5uZWwgPSB0aGlzLmdldE5leHRGcmVlRG14Q2hhbm5lbChmaXh0dXJlUG9vbCwgY2hhbm5lbENvdW50KTtcblxuICAgIGlmIChmaXJzdENoYW5uZWwgPj0gMCkge1xuICAgICAgZml4dHVyZS5kbXhGaXJzdENoYW5uZWwgPSBmaXJzdENoYW5uZWw7XG4gICAgICBmaXh0dXJlUG9vbC5wdXNoKGZpeHR1cmUpO1xuICAgICAgcmV0dXJuIGZpeHR1cmU7XG4gICAgfSBlbHNlIHtcbiAgICAgIC8vIG5vIGZyZWUgc3BhY2UgYW55bW9yZVxuICAgICAgY29uc3QgbXNnID0gJ2Rlc2lnbmVyLmZpeHR1cmUtcG9vbC5uby1mcmVlLXNwYWNlJztcbiAgICAgIGNvbnN0IHRpdGxlID0gJ2Rlc2lnbmVyLmZpeHR1cmUtcG9vbC5uby1mcmVlLXNwYWNlLXRpdGxlJztcblxuICAgICAgdGhpcy50cmFuc2xhdGVTZXJ2aWNlLmdldChbbXNnLCB0aXRsZV0pLnN1YnNjcmliZSgocmVzdWx0KSA9PiB7XG4gICAgICAgIHRoaXMudG9hc3RyU2VydmljZS5lcnJvcihyZXN1bHRbbXNnXSwgcmVzdWx0W3RpdGxlXSk7XG4gICAgICB9KTtcbiAgICB9XG4gIH1cbn1cbiJdfQ==