@ckeditor/ckeditor5-table 0.0.0-nightly-next-20260127.0 → 0.0.0-nightly-20260128.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 (356) hide show
  1. package/build/table.js +5 -0
  2. package/build/translations/af.js +1 -0
  3. package/build/translations/ar.js +1 -0
  4. package/build/translations/ast.js +1 -0
  5. package/build/translations/az.js +1 -0
  6. package/build/translations/be.js +1 -0
  7. package/build/translations/bg.js +1 -0
  8. package/build/translations/bn.js +1 -0
  9. package/build/translations/bs.js +1 -0
  10. package/build/translations/ca.js +1 -0
  11. package/build/translations/cs.js +1 -0
  12. package/build/translations/da.js +1 -0
  13. package/build/translations/de-ch.js +1 -0
  14. package/build/translations/de.js +1 -0
  15. package/build/translations/el.js +1 -0
  16. package/build/translations/en-au.js +1 -0
  17. package/build/translations/en-gb.js +1 -0
  18. package/build/translations/eo.js +1 -0
  19. package/build/translations/es-co.js +1 -0
  20. package/build/translations/es.js +1 -0
  21. package/build/translations/et.js +1 -0
  22. package/build/translations/eu.js +1 -0
  23. package/build/translations/fa.js +1 -0
  24. package/build/translations/fi.js +1 -0
  25. package/build/translations/fr.js +1 -0
  26. package/build/translations/gl.js +1 -0
  27. package/build/translations/gu.js +1 -0
  28. package/build/translations/he.js +1 -0
  29. package/build/translations/hi.js +1 -0
  30. package/build/translations/hr.js +1 -0
  31. package/build/translations/hu.js +1 -0
  32. package/build/translations/hy.js +1 -0
  33. package/build/translations/id.js +1 -0
  34. package/build/translations/it.js +1 -0
  35. package/build/translations/ja.js +1 -0
  36. package/build/translations/jv.js +1 -0
  37. package/build/translations/kk.js +1 -0
  38. package/build/translations/km.js +1 -0
  39. package/build/translations/kn.js +1 -0
  40. package/build/translations/ko.js +1 -0
  41. package/build/translations/ku.js +1 -0
  42. package/build/translations/lt.js +1 -0
  43. package/build/translations/lv.js +1 -0
  44. package/build/translations/ms.js +1 -0
  45. package/build/translations/nb.js +1 -0
  46. package/build/translations/ne.js +1 -0
  47. package/build/translations/nl.js +1 -0
  48. package/build/translations/no.js +1 -0
  49. package/build/translations/oc.js +1 -0
  50. package/build/translations/pl.js +1 -0
  51. package/build/translations/pt-br.js +1 -0
  52. package/build/translations/pt.js +1 -0
  53. package/build/translations/ro.js +1 -0
  54. package/build/translations/ru.js +1 -0
  55. package/build/translations/si.js +1 -0
  56. package/build/translations/sk.js +1 -0
  57. package/build/translations/sl.js +1 -0
  58. package/build/translations/sq.js +1 -0
  59. package/build/translations/sr-latn.js +1 -0
  60. package/build/translations/sr.js +1 -0
  61. package/build/translations/sv.js +1 -0
  62. package/build/translations/th.js +1 -0
  63. package/build/translations/ti.js +1 -0
  64. package/build/translations/tk.js +1 -0
  65. package/build/translations/tr.js +1 -0
  66. package/build/translations/tt.js +1 -0
  67. package/build/translations/ug.js +1 -0
  68. package/build/translations/uk.js +1 -0
  69. package/build/translations/ur.js +1 -0
  70. package/build/translations/uz.js +1 -0
  71. package/build/translations/vi.js +1 -0
  72. package/build/translations/zh-cn.js +1 -0
  73. package/build/translations/zh.js +1 -0
  74. package/ckeditor5-metadata.json +7 -16
  75. package/dist/index-content.css +30 -30
  76. package/dist/index-editor.css +170 -104
  77. package/dist/index.css +237 -147
  78. package/dist/index.css.map +1 -1
  79. package/dist/index.js +2433 -448
  80. package/dist/index.js.map +1 -1
  81. package/lang/contexts.json +82 -0
  82. package/lang/translations/af.po +332 -0
  83. package/lang/translations/ar.po +332 -0
  84. package/lang/translations/ast.po +332 -0
  85. package/lang/translations/az.po +332 -0
  86. package/lang/translations/be.po +332 -0
  87. package/lang/translations/bg.po +332 -0
  88. package/lang/translations/bn.po +334 -0
  89. package/lang/translations/bs.po +332 -0
  90. package/lang/translations/ca.po +332 -0
  91. package/lang/translations/cs.po +332 -0
  92. package/lang/translations/da.po +332 -0
  93. package/lang/translations/de-ch.po +332 -0
  94. package/lang/translations/de.po +332 -0
  95. package/lang/translations/el.po +332 -0
  96. package/lang/translations/en-au.po +332 -0
  97. package/lang/translations/en-gb.po +332 -0
  98. package/lang/translations/en.po +332 -0
  99. package/lang/translations/eo.po +332 -0
  100. package/lang/translations/es-co.po +332 -0
  101. package/lang/translations/es.po +332 -0
  102. package/lang/translations/et.po +332 -0
  103. package/lang/translations/eu.po +332 -0
  104. package/lang/translations/fa.po +332 -0
  105. package/lang/translations/fi.po +332 -0
  106. package/lang/translations/fr.po +332 -0
  107. package/lang/translations/gl.po +332 -0
  108. package/lang/translations/gu.po +332 -0
  109. package/lang/translations/he.po +332 -0
  110. package/lang/translations/hi.po +332 -0
  111. package/lang/translations/hr.po +332 -0
  112. package/lang/translations/hu.po +332 -0
  113. package/lang/translations/hy.po +332 -0
  114. package/lang/translations/id.po +332 -0
  115. package/lang/translations/it.po +332 -0
  116. package/lang/translations/ja.po +332 -0
  117. package/lang/translations/jv.po +332 -0
  118. package/lang/translations/kk.po +332 -0
  119. package/lang/translations/km.po +332 -0
  120. package/lang/translations/kn.po +332 -0
  121. package/lang/translations/ko.po +332 -0
  122. package/lang/translations/ku.po +332 -0
  123. package/lang/translations/lt.po +332 -0
  124. package/lang/translations/lv.po +332 -0
  125. package/lang/translations/ms.po +332 -0
  126. package/lang/translations/nb.po +332 -0
  127. package/lang/translations/ne.po +332 -0
  128. package/lang/translations/nl.po +332 -0
  129. package/lang/translations/no.po +332 -0
  130. package/lang/translations/oc.po +332 -0
  131. package/lang/translations/pl.po +332 -0
  132. package/lang/translations/pt-br.po +332 -0
  133. package/lang/translations/pt.po +332 -0
  134. package/lang/translations/ro.po +332 -0
  135. package/lang/translations/ru.po +332 -0
  136. package/lang/translations/si.po +332 -0
  137. package/lang/translations/sk.po +332 -0
  138. package/lang/translations/sl.po +332 -0
  139. package/lang/translations/sq.po +332 -0
  140. package/lang/translations/sr-latn.po +332 -0
  141. package/lang/translations/sr.po +332 -0
  142. package/lang/translations/sv.po +332 -0
  143. package/lang/translations/th.po +332 -0
  144. package/lang/translations/ti.po +332 -0
  145. package/lang/translations/tk.po +332 -0
  146. package/lang/translations/tr.po +332 -0
  147. package/lang/translations/tt.po +332 -0
  148. package/lang/translations/ug.po +332 -0
  149. package/lang/translations/uk.po +332 -0
  150. package/lang/translations/ur.po +332 -0
  151. package/lang/translations/uz.po +332 -0
  152. package/lang/translations/vi.po +332 -0
  153. package/lang/translations/zh-cn.po +332 -0
  154. package/lang/translations/zh.po +332 -0
  155. package/package.json +49 -26
  156. package/{dist → src}/augmentation.d.ts +15 -0
  157. package/src/augmentation.js +5 -0
  158. package/{dist → src}/commands/insertcolumncommand.d.ts +1 -1
  159. package/src/commands/insertcolumncommand.js +71 -0
  160. package/{dist → src}/commands/insertrowcommand.d.ts +1 -1
  161. package/src/commands/insertrowcommand.js +70 -0
  162. package/{dist → src}/commands/inserttablecommand.d.ts +1 -1
  163. package/src/commands/inserttablecommand.js +69 -0
  164. package/{dist → src}/commands/inserttablelayoutcommand.d.ts +1 -1
  165. package/src/commands/inserttablelayoutcommand.js +65 -0
  166. package/{dist → src}/commands/mergecellcommand.d.ts +3 -3
  167. package/src/commands/mergecellcommand.js +206 -0
  168. package/{dist → src}/commands/mergecellscommand.d.ts +1 -1
  169. package/src/commands/mergecellscommand.js +94 -0
  170. package/{dist → src}/commands/removecolumncommand.d.ts +1 -1
  171. package/src/commands/removecolumncommand.js +109 -0
  172. package/{dist → src}/commands/removerowcommand.d.ts +1 -1
  173. package/src/commands/removerowcommand.js +82 -0
  174. package/{dist → src}/commands/selectcolumncommand.d.ts +1 -1
  175. package/src/commands/selectcolumncommand.js +60 -0
  176. package/{dist → src}/commands/selectrowcommand.d.ts +1 -1
  177. package/src/commands/selectrowcommand.js +56 -0
  178. package/{dist → src}/commands/setheadercolumncommand.d.ts +1 -1
  179. package/src/commands/setheadercolumncommand.js +76 -0
  180. package/{dist → src}/commands/setheaderrowcommand.d.ts +1 -1
  181. package/src/commands/setheaderrowcommand.js +83 -0
  182. package/{dist → src}/commands/splitcellcommand.d.ts +1 -1
  183. package/src/commands/splitcellcommand.js +58 -0
  184. package/{dist → src}/converters/downcast.d.ts +2 -2
  185. package/src/converters/downcast.js +298 -0
  186. package/{dist → src}/converters/table-caption-post-fixer.d.ts +1 -1
  187. package/src/converters/table-caption-post-fixer.js +55 -0
  188. package/{dist → src}/converters/table-cell-paragraph-post-fixer.d.ts +1 -1
  189. package/src/converters/table-cell-paragraph-post-fixer.js +109 -0
  190. package/{dist → src}/converters/table-cell-refresh-handler.d.ts +1 -1
  191. package/src/converters/table-cell-refresh-handler.js +47 -0
  192. package/{dist → src}/converters/table-headings-refresh-handler.d.ts +1 -1
  193. package/src/converters/table-headings-refresh-handler.js +51 -0
  194. package/{dist → src}/converters/table-layout-post-fixer.d.ts +1 -1
  195. package/src/converters/table-layout-post-fixer.js +369 -0
  196. package/{dist → src}/converters/tableproperties.d.ts +2 -2
  197. package/src/converters/tableproperties.js +444 -0
  198. package/{dist → src}/converters/upcasttable.d.ts +1 -1
  199. package/src/converters/upcasttable.js +385 -0
  200. package/{dist → src}/index.d.ts +5 -2
  201. package/src/index.js +98 -0
  202. package/{dist → src}/plaintableoutput.d.ts +1 -1
  203. package/src/plaintableoutput.js +49 -0
  204. package/{dist → src}/table.d.ts +2 -2
  205. package/src/table.js +50 -0
  206. package/{dist → src}/tablecaption/tablecaptionediting.d.ts +2 -2
  207. package/src/tablecaption/tablecaptionediting.js +136 -0
  208. package/{dist → src}/tablecaption/tablecaptionui.d.ts +1 -1
  209. package/src/tablecaption/tablecaptionui.js +64 -0
  210. package/{dist → src}/tablecaption/toggletablecaptioncommand.d.ts +1 -1
  211. package/src/tablecaption/toggletablecaptioncommand.js +105 -0
  212. package/{dist → src}/tablecaption/utils.d.ts +1 -1
  213. package/src/tablecaption/utils.js +61 -0
  214. package/{dist → src}/tablecaption.d.ts +1 -1
  215. package/src/tablecaption.js +34 -0
  216. package/{dist → src}/tablecellproperties/commands/tablecellbackgroundcolorcommand.d.ts +1 -1
  217. package/src/tablecellproperties/commands/tablecellbackgroundcolorcommand.js +30 -0
  218. package/{dist → src}/tablecellproperties/commands/tablecellbordercolorcommand.d.ts +2 -2
  219. package/src/tablecellproperties/commands/tablecellbordercolorcommand.js +44 -0
  220. package/{dist → src}/tablecellproperties/commands/tablecellborderstylecommand.d.ts +2 -2
  221. package/src/tablecellproperties/commands/tablecellborderstylecommand.js +44 -0
  222. package/{dist → src}/tablecellproperties/commands/tablecellborderwidthcommand.d.ts +2 -2
  223. package/src/tablecellproperties/commands/tablecellborderwidthcommand.js +64 -0
  224. package/{dist → src}/tablecellproperties/commands/tablecellheightcommand.d.ts +1 -1
  225. package/src/tablecellproperties/commands/tablecellheightcommand.js +51 -0
  226. package/{dist → src}/tablecellproperties/commands/tablecellhorizontalalignmentcommand.d.ts +1 -1
  227. package/src/tablecellproperties/commands/tablecellhorizontalalignmentcommand.js +30 -0
  228. package/{dist → src}/tablecellproperties/commands/tablecellpaddingcommand.d.ts +2 -2
  229. package/src/tablecellproperties/commands/tablecellpaddingcommand.js +64 -0
  230. package/{dist → src}/tablecellproperties/commands/tablecellpropertycommand.d.ts +2 -2
  231. package/src/tablecellproperties/commands/tablecellpropertycommand.js +138 -0
  232. package/{dist → src}/tablecellproperties/commands/tablecelltypecommand.d.ts +6 -2
  233. package/src/tablecellproperties/commands/tablecelltypecommand.js +167 -0
  234. package/{dist → src}/tablecellproperties/commands/tablecellverticalalignmentcommand.d.ts +1 -1
  235. package/src/tablecellproperties/commands/tablecellverticalalignmentcommand.js +38 -0
  236. package/{dist → src}/tablecellproperties/tablecellpropertiesediting.d.ts +1 -1
  237. package/src/tablecellproperties/tablecellpropertiesediting.js +412 -0
  238. package/{dist → src}/tablecellproperties/tablecellpropertiesui.d.ts +2 -2
  239. package/src/tablecellproperties/tablecellpropertiesui.js +385 -0
  240. package/src/tablecellproperties/tablecellpropertiesuiexperimental.d.ts +128 -0
  241. package/src/tablecellproperties/tablecellpropertiesuiexperimental.js +408 -0
  242. package/src/tablecellproperties/ui/tablecellpropertiesview.d.ts +229 -0
  243. package/src/tablecellproperties/ui/tablecellpropertiesview.js +612 -0
  244. package/{dist/tablecellproperties/ui/tablecellpropertiesview.d.ts → src/tablecellproperties/ui/tablecellpropertiesviewexperimental.d.ts} +12 -11
  245. package/src/tablecellproperties/ui/tablecellpropertiesviewexperimental.js +744 -0
  246. package/{dist → src}/tablecellproperties.d.ts +1 -1
  247. package/src/tablecellproperties.js +40 -0
  248. package/{dist → src}/tablecellwidth/commands/tablecellwidthcommand.d.ts +1 -1
  249. package/src/tablecellwidth/commands/tablecellwidthcommand.js +51 -0
  250. package/{dist → src}/tablecellwidth/tablecellwidthediting.d.ts +1 -1
  251. package/src/tablecellwidth/tablecellwidthediting.js +53 -0
  252. package/{dist → src}/tableclipboard.d.ts +3 -3
  253. package/src/tableclipboard.js +500 -0
  254. package/src/tablecolumnresize/constants.js +33 -0
  255. package/{dist → src}/tablecolumnresize/converters.d.ts +1 -1
  256. package/src/tablecolumnresize/converters.js +62 -0
  257. package/{dist → src}/tablecolumnresize/tablecolumnresizeediting.d.ts +2 -2
  258. package/src/tablecolumnresize/tablecolumnresizeediting.js +734 -0
  259. package/{dist → src}/tablecolumnresize/tablewidthscommand.d.ts +2 -2
  260. package/src/tablecolumnresize/tablewidthscommand.js +61 -0
  261. package/{dist → src}/tablecolumnresize/utils.d.ts +2 -2
  262. package/src/tablecolumnresize/utils.js +370 -0
  263. package/{dist → src}/tablecolumnresize.d.ts +1 -1
  264. package/src/tablecolumnresize.js +36 -0
  265. package/{dist → src}/tableconfig.d.ts +6 -26
  266. package/src/tableconfig.js +5 -0
  267. package/{dist → src}/tableediting.d.ts +3 -3
  268. package/src/tableediting.js +246 -0
  269. package/{dist → src}/tablekeyboard.d.ts +3 -3
  270. package/src/tablekeyboard.js +273 -0
  271. package/{dist → src}/tablelayout/commands/tabletypecommand.d.ts +1 -1
  272. package/src/tablelayout/commands/tabletypecommand.js +68 -0
  273. package/{dist → src}/tablelayout/tablelayoutediting.d.ts +1 -1
  274. package/src/tablelayout/tablelayoutediting.js +295 -0
  275. package/{dist → src}/tablelayout/tablelayoutui.d.ts +1 -1
  276. package/src/tablelayout/tablelayoutui.js +196 -0
  277. package/{dist → src}/tablelayout.d.ts +1 -1
  278. package/src/tablelayout.js +37 -0
  279. package/{dist → src}/tablemouse/mouseeventsobserver.d.ts +1 -1
  280. package/src/tablemouse/mouseeventsobserver.js +34 -0
  281. package/{dist → src}/tablemouse.d.ts +1 -1
  282. package/src/tablemouse.js +178 -0
  283. package/{dist → src}/tableproperties/commands/tablealignmentcommand.d.ts +1 -1
  284. package/src/tableproperties/commands/tablealignmentcommand.js +30 -0
  285. package/{dist → src}/tableproperties/commands/tablebackgroundcolorcommand.d.ts +1 -1
  286. package/src/tableproperties/commands/tablebackgroundcolorcommand.js +30 -0
  287. package/{dist → src}/tableproperties/commands/tablebordercolorcommand.d.ts +2 -2
  288. package/src/tableproperties/commands/tablebordercolorcommand.js +44 -0
  289. package/{dist → src}/tableproperties/commands/tableborderstylecommand.d.ts +2 -2
  290. package/src/tableproperties/commands/tableborderstylecommand.js +44 -0
  291. package/{dist → src}/tableproperties/commands/tableborderwidthcommand.d.ts +2 -2
  292. package/src/tableproperties/commands/tableborderwidthcommand.js +64 -0
  293. package/{dist → src}/tableproperties/commands/tableheightcommand.d.ts +1 -1
  294. package/src/tableproperties/commands/tableheightcommand.js +54 -0
  295. package/{dist → src}/tableproperties/commands/tablepropertycommand.d.ts +2 -2
  296. package/src/tableproperties/commands/tablepropertycommand.js +103 -0
  297. package/{dist → src}/tableproperties/commands/tablewidthcommand.d.ts +1 -1
  298. package/src/tableproperties/commands/tablewidthcommand.js +54 -0
  299. package/{dist → src}/tableproperties/tablepropertiesediting.d.ts +1 -1
  300. package/src/tableproperties/tablepropertiesediting.js +546 -0
  301. package/{dist → src}/tableproperties/tablepropertiesui.d.ts +2 -2
  302. package/src/tableproperties/tablepropertiesui.js +374 -0
  303. package/src/tableproperties/tablepropertiesuiexperimental.d.ts +136 -0
  304. package/src/tableproperties/tablepropertiesuiexperimental.js +375 -0
  305. package/{dist → src}/tableproperties/ui/tablepropertiesview.d.ts +2 -10
  306. package/src/tableproperties/ui/tablepropertiesview.js +520 -0
  307. package/src/tableproperties/ui/tablepropertiesviewexperimental.d.ts +216 -0
  308. package/src/tableproperties/ui/tablepropertiesviewexperimental.js +544 -0
  309. package/{dist → src}/tableproperties.d.ts +1 -1
  310. package/src/tableproperties.js +40 -0
  311. package/{dist → src}/tableselection.d.ts +2 -2
  312. package/src/tableselection.js +323 -0
  313. package/{dist → src}/tabletoolbar.d.ts +2 -2
  314. package/src/tabletoolbar.js +63 -0
  315. package/{dist → src}/tableui.d.ts +1 -1
  316. package/src/tableui.js +335 -0
  317. package/{dist → src}/tableutils.d.ts +2 -2
  318. package/src/tableutils.js +1282 -0
  319. package/{dist → src}/tablewalker.d.ts +1 -1
  320. package/src/tablewalker.js +489 -0
  321. package/{dist → src}/ui/colorinputview.d.ts +2 -2
  322. package/src/ui/colorinputview.js +305 -0
  323. package/{dist → src}/ui/inserttableview.d.ts +2 -2
  324. package/src/ui/inserttableview.js +192 -0
  325. package/{dist → src}/utils/common.d.ts +2 -2
  326. package/src/utils/common.js +118 -0
  327. package/{dist → src}/utils/structure.d.ts +1 -1
  328. package/src/utils/structure.js +452 -0
  329. package/{dist → src}/utils/table-properties.d.ts +1 -1
  330. package/src/utils/table-properties.js +121 -0
  331. package/{dist → src}/utils/ui/contextualballoon.d.ts +2 -2
  332. package/src/utils/ui/contextualballoon.js +111 -0
  333. package/{dist → src}/utils/ui/table-properties.d.ts +2 -2
  334. package/src/utils/ui/table-properties.js +390 -0
  335. package/src/utils/ui/table-propertiesexperimental.d.ts +215 -0
  336. package/src/utils/ui/table-propertiesexperimental.js +391 -0
  337. package/{dist → src}/utils/ui/widget.d.ts +1 -1
  338. package/src/utils/ui/widget.js +56 -0
  339. package/theme/colorinput.css +39 -0
  340. package/theme/formrow-experimental.css +15 -0
  341. package/theme/formrow.css +13 -0
  342. package/theme/inserttable.css +10 -0
  343. package/theme/table.css +144 -0
  344. package/theme/tablecaption.css +66 -0
  345. package/theme/tablecellproperties-experimental.css +4 -0
  346. package/theme/tablecellproperties.css +28 -0
  347. package/theme/tablecolumnresize.css +62 -0
  348. package/theme/tableediting.css +10 -0
  349. package/theme/tableform-experimental.css +61 -0
  350. package/theme/tableform.css +64 -0
  351. package/theme/tablelayout.css +74 -0
  352. package/theme/tableproperties-experimental.css +78 -0
  353. package/theme/tableproperties.css +18 -0
  354. package/theme/tableselection.css +10 -0
  355. package/dist/tablecellproperties/tablecellpropertiesutils.d.ts +0 -18
  356. /package/{dist → src}/tablecolumnresize/constants.d.ts +0 -0
@@ -0,0 +1,500 @@
1
+ /**
2
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
3
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
4
+ */
5
+ import { ClipboardPipeline, ClipboardMarkersUtils } from 'ckeditor5/src/clipboard.js';
6
+ import { Plugin } from 'ckeditor5/src/core.js';
7
+ import { TableSelection } from './tableselection.js';
8
+ import { TableWalker } from './tablewalker.js';
9
+ import { TableUtils } from './tableutils.js';
10
+ import { cropTableToDimensions, getHorizontallyOverlappingCells, getVerticallyOverlappingCells, removeEmptyRowsColumns, splitHorizontally, splitVertically, trimTableCellIfNeeded, adjustLastRowIndex, adjustLastColumnIndex } from './utils/structure.js';
11
+ /**
12
+ * This plugin adds support for copying/cutting/pasting fragments of tables.
13
+ * It is loaded automatically by the {@link module:table/table~Table} plugin.
14
+ */
15
+ export class TableClipboard extends Plugin {
16
+ /**
17
+ * @inheritDoc
18
+ */
19
+ static get pluginName() {
20
+ return 'TableClipboard';
21
+ }
22
+ /**
23
+ * @inheritDoc
24
+ */
25
+ static get isOfficialPlugin() {
26
+ return true;
27
+ }
28
+ /**
29
+ * @inheritDoc
30
+ */
31
+ static get requires() {
32
+ return [ClipboardMarkersUtils, ClipboardPipeline, TableSelection, TableUtils];
33
+ }
34
+ /**
35
+ * @inheritDoc
36
+ */
37
+ init() {
38
+ const editor = this.editor;
39
+ const viewDocument = editor.editing.view.document;
40
+ this.listenTo(viewDocument, 'copy', (evt, data) => this._onCopyCut(evt, data));
41
+ this.listenTo(viewDocument, 'cut', (evt, data) => this._onCopyCut(evt, data));
42
+ this._listenToContentInsertion();
43
+ this.decorate('_replaceTableSlotCell');
44
+ }
45
+ /**
46
+ * Sets up listening for events from the clipboard pipeline to properly handle
47
+ * table content merging during paste/drop operations.
48
+ *
49
+ * When a user is dragging and dropping a table, we want to insert the entire table into
50
+ * a table cell instead of merging table contents. For paste and other events,
51
+ * the normal table merge behavior is applied.
52
+ */
53
+ _listenToContentInsertion() {
54
+ const { editor } = this;
55
+ const clipboardPipeline = editor.plugins.get(ClipboardPipeline);
56
+ const tableSelection = editor.plugins.get(TableSelection);
57
+ let isPaste = false;
58
+ clipboardPipeline.on('contentInsertion', (evt, data) => {
59
+ isPaste = data.method === 'paste';
60
+ });
61
+ this.listenTo(editor.model, 'insertContent', (evt, [content, selectable]) => {
62
+ // Handles drag-and-drop of tables, where tables are inserted into selected cells rather than merged.
63
+ // The `isPaste` flag handles scenarios where other features (e.g., Templates) insert tables into specific cells.
64
+ if (isPaste || tableSelection.getSelectedTableCells() !== null) {
65
+ this._onInsertContent(evt, content, selectable);
66
+ }
67
+ }, { priority: 'high' });
68
+ clipboardPipeline.on('contentInsertion', () => {
69
+ isPaste = false;
70
+ }, { priority: 'lowest' });
71
+ }
72
+ /**
73
+ * Copies table content to a clipboard on "copy" & "cut" events.
74
+ *
75
+ * @param evt An object containing information about the handled event.
76
+ * @param data Clipboard event data.
77
+ */
78
+ _onCopyCut(evt, data) {
79
+ const view = this.editor.editing.view;
80
+ const tableSelection = this.editor.plugins.get(TableSelection);
81
+ const clipboardMarkersUtils = this.editor.plugins.get(ClipboardMarkersUtils);
82
+ if (!tableSelection.getSelectedTableCells()) {
83
+ return;
84
+ }
85
+ if (evt.name == 'cut' && !this.editor.model.canEditAt(this.editor.model.document.selection)) {
86
+ return;
87
+ }
88
+ data.preventDefault();
89
+ evt.stop();
90
+ this.editor.model.enqueueChange({ isUndoable: evt.name === 'cut' }, () => {
91
+ const documentFragment = clipboardMarkersUtils._copySelectedFragmentWithMarkers(evt.name, this.editor.model.document.selection, () => tableSelection.getSelectionAsFragment());
92
+ view.document.fire('clipboardOutput', {
93
+ dataTransfer: data.dataTransfer,
94
+ content: this.editor.data.toView(documentFragment),
95
+ method: evt.name
96
+ });
97
+ });
98
+ }
99
+ /**
100
+ * Overrides default {@link module:engine/model/model~Model#insertContent `model.insertContent()`} method to handle pasting table inside
101
+ * selected table fragment.
102
+ *
103
+ * Depending on selected table fragment:
104
+ * - If a selected table fragment is smaller than paste table it will crop pasted table to match dimensions.
105
+ * - If dimensions are equal it will replace selected table fragment with a pasted table contents.
106
+ *
107
+ * @param content The content to insert.
108
+ * @param selectable The selection into which the content should be inserted.
109
+ * If not provided the current model document selection will be used.
110
+ */
111
+ _onInsertContent(evt, content, selectable) {
112
+ if (selectable && !selectable.is('documentSelection')) {
113
+ return;
114
+ }
115
+ const model = this.editor.model;
116
+ const tableUtils = this.editor.plugins.get(TableUtils);
117
+ const clipboardMarkersUtils = this.editor.plugins.get(ClipboardMarkersUtils);
118
+ // We might need to crop table before inserting so reference might change.
119
+ const pastedTable = this.getTableIfOnlyTableInContent(content, model);
120
+ if (!pastedTable) {
121
+ return;
122
+ }
123
+ const selectedTableCells = tableUtils.getSelectionAffectedTableCells(model.document.selection);
124
+ if (!selectedTableCells.length) {
125
+ removeEmptyRowsColumns(pastedTable, tableUtils);
126
+ return;
127
+ }
128
+ // Override default model.insertContent() handling at this point.
129
+ evt.stop();
130
+ if (content.is('documentFragment')) {
131
+ clipboardMarkersUtils._pasteMarkersIntoTransformedElement(content.markers, writer => this._replaceSelectedCells(pastedTable, selectedTableCells, writer));
132
+ }
133
+ else {
134
+ this.editor.model.change(writer => {
135
+ this._replaceSelectedCells(pastedTable, selectedTableCells, writer);
136
+ });
137
+ }
138
+ }
139
+ /**
140
+ * Inserts provided `selectedTableCells` into `pastedTable`.
141
+ */
142
+ _replaceSelectedCells(pastedTable, selectedTableCells, writer) {
143
+ const tableUtils = this.editor.plugins.get(TableUtils);
144
+ const pastedDimensions = {
145
+ width: tableUtils.getColumns(pastedTable),
146
+ height: tableUtils.getRows(pastedTable)
147
+ };
148
+ // Prepare the table for pasting.
149
+ const selection = prepareTableForPasting(selectedTableCells, pastedDimensions, writer, tableUtils);
150
+ // Beyond this point we operate on a fixed content table with rectangular selection and proper last row/column values.
151
+ const selectionHeight = selection.lastRow - selection.firstRow + 1;
152
+ const selectionWidth = selection.lastColumn - selection.firstColumn + 1;
153
+ // Crop pasted table if:
154
+ // - Pasted table dimensions exceeds selection area.
155
+ // - Pasted table has broken layout (ie some cells sticks out by the table dimensions established by the first and last row).
156
+ //
157
+ // Note: The table dimensions are established by the width of the first row and the total number of rows.
158
+ // It is possible to programmatically create a table that has rows which would have cells anchored beyond first row width but
159
+ // such table will not be created by other editing solutions.
160
+ const cropDimensions = {
161
+ startRow: 0,
162
+ startColumn: 0,
163
+ endRow: Math.min(selectionHeight, pastedDimensions.height) - 1,
164
+ endColumn: Math.min(selectionWidth, pastedDimensions.width) - 1
165
+ };
166
+ pastedTable = cropTableToDimensions(pastedTable, cropDimensions, writer);
167
+ // Content table to which we insert a pasted table.
168
+ const selectedTable = selectedTableCells[0].findAncestor('table');
169
+ const cellsToSelect = this._replaceSelectedCellsWithPasted(pastedTable, pastedDimensions, selectedTable, selection, writer);
170
+ if (this.editor.plugins.get('TableSelection').isEnabled) {
171
+ // Selection ranges must be sorted because the first and last selection ranges are considered
172
+ // as anchor/focus cell ranges for multi-cell selection.
173
+ const selectionRanges = tableUtils.sortRanges(cellsToSelect.map(cell => writer.createRangeOn(cell)));
174
+ writer.setSelection(selectionRanges);
175
+ }
176
+ else {
177
+ // Set selection inside first cell if multi-cell selection is disabled.
178
+ writer.setSelection(cellsToSelect[0], 0);
179
+ }
180
+ return selectedTable;
181
+ }
182
+ /**
183
+ * Replaces the part of selectedTable with pastedTable.
184
+ */
185
+ _replaceSelectedCellsWithPasted(pastedTable, pastedDimensions, selectedTable, selection, writer) {
186
+ const { width: pastedWidth, height: pastedHeight } = pastedDimensions;
187
+ // Holds two-dimensional array that is addressed by [ row ][ column ] that stores cells anchored at given location.
188
+ const pastedTableLocationMap = createLocationMap(pastedTable, pastedWidth, pastedHeight);
189
+ const selectedTableMap = [...new TableWalker(selectedTable, {
190
+ startRow: selection.firstRow,
191
+ endRow: selection.lastRow,
192
+ startColumn: selection.firstColumn,
193
+ endColumn: selection.lastColumn,
194
+ includeAllSlots: true
195
+ })];
196
+ // Selection must be set to pasted cells (some might be removed or new created).
197
+ const cellsToSelect = [];
198
+ // Store next cell insert position.
199
+ let insertPosition;
200
+ // Content table replace cells algorithm iterates over a selected table fragment and:
201
+ //
202
+ // - Removes existing table cells at current slot (location).
203
+ // - Inserts cell from a pasted table for a matched slots.
204
+ //
205
+ // This ensures proper table geometry after the paste
206
+ for (const tableSlot of selectedTableMap) {
207
+ const { row, column } = tableSlot;
208
+ // Save the insert position for current row start.
209
+ if (column === selection.firstColumn) {
210
+ insertPosition = tableSlot.getPositionBefore();
211
+ }
212
+ // Map current table slot location to an pasted table slot location.
213
+ const pastedRow = row - selection.firstRow;
214
+ const pastedColumn = column - selection.firstColumn;
215
+ const pastedCell = pastedTableLocationMap[pastedRow % pastedHeight][pastedColumn % pastedWidth];
216
+ // Clone cell to insert (to duplicate its attributes and children).
217
+ // Cloning is required to support repeating pasted table content when inserting to a bigger selection.
218
+ const cellToInsert = pastedCell ? writer.cloneElement(pastedCell) : null;
219
+ // Replace the cell from the current slot with new table cell.
220
+ const newTableCell = this._replaceTableSlotCell(tableSlot, cellToInsert, insertPosition, writer);
221
+ // The cell was only removed.
222
+ if (!newTableCell) {
223
+ continue;
224
+ }
225
+ // Trim the cell if it's row/col-spans would exceed selection area.
226
+ trimTableCellIfNeeded(newTableCell, row, column, selection.lastRow, selection.lastColumn, writer);
227
+ cellsToSelect.push(newTableCell);
228
+ insertPosition = writer.createPositionAfter(newTableCell);
229
+ }
230
+ // If there are any headings, all the cells that overlap from heading must be splitted.
231
+ const headingRows = parseInt(selectedTable.getAttribute('headingRows') || '0');
232
+ const headingColumns = parseInt(selectedTable.getAttribute('headingColumns') || '0');
233
+ const areHeadingRowsIntersectingSelection = selection.firstRow < headingRows && headingRows <= selection.lastRow;
234
+ const areHeadingColumnsIntersectingSelection = selection.firstColumn < headingColumns && headingColumns <= selection.lastColumn;
235
+ if (areHeadingRowsIntersectingSelection) {
236
+ const columnsLimit = { first: selection.firstColumn, last: selection.lastColumn };
237
+ const newCells = doHorizontalSplit(selectedTable, headingRows, columnsLimit, writer, selection.firstRow);
238
+ cellsToSelect.push(...newCells);
239
+ }
240
+ if (areHeadingColumnsIntersectingSelection) {
241
+ const rowsLimit = { first: selection.firstRow, last: selection.lastRow };
242
+ const newCells = doVerticalSplit(selectedTable, headingColumns, rowsLimit, writer);
243
+ cellsToSelect.push(...newCells);
244
+ }
245
+ return cellsToSelect;
246
+ }
247
+ /**
248
+ * Replaces a single table slot.
249
+ *
250
+ * @returns Inserted table cell or null if slot should remain empty.
251
+ * @private
252
+ */
253
+ _replaceTableSlotCell(tableSlot, cellToInsert, insertPosition, writer) {
254
+ const { cell, isAnchor } = tableSlot;
255
+ // If the slot is occupied by a cell in a selected table - remove it.
256
+ // The slot of this cell will be either:
257
+ // - Replaced by a pasted table cell.
258
+ // - Spanned by a previously pasted table cell.
259
+ if (isAnchor) {
260
+ writer.remove(cell);
261
+ }
262
+ // There is no cell to insert (might be spanned by other cell in a pasted table) - advance to the next content table slot.
263
+ if (!cellToInsert) {
264
+ return null;
265
+ }
266
+ writer.insert(cellToInsert, insertPosition);
267
+ return cellToInsert;
268
+ }
269
+ /**
270
+ * Extracts the table for pasting into a table.
271
+ *
272
+ * @param content The content to insert.
273
+ * @param model The editor model.
274
+ */
275
+ getTableIfOnlyTableInContent(content, model) {
276
+ if (!content.is('documentFragment') && !content.is('element')) {
277
+ return null;
278
+ }
279
+ // Table passed directly.
280
+ if (content.is('element', 'table')) {
281
+ return content;
282
+ }
283
+ // We do not support mixed content when pasting table into table.
284
+ // See: https://github.com/ckeditor/ckeditor5/issues/6817.
285
+ if (content.childCount == 1 && content.getChild(0).is('element', 'table')) {
286
+ return content.getChild(0);
287
+ }
288
+ // If there are only whitespaces around a table then use that table for pasting.
289
+ const contentRange = model.createRangeIn(content);
290
+ for (const element of contentRange.getItems()) {
291
+ if (element.is('element', 'table')) {
292
+ // Stop checking if there is some content before table.
293
+ const rangeBefore = model.createRange(contentRange.start, model.createPositionBefore(element));
294
+ if (model.hasContent(rangeBefore, { ignoreWhitespaces: true })) {
295
+ return null;
296
+ }
297
+ // Stop checking if there is some content after table.
298
+ const rangeAfter = model.createRange(model.createPositionAfter(element), contentRange.end);
299
+ if (model.hasContent(rangeAfter, { ignoreWhitespaces: true })) {
300
+ return null;
301
+ }
302
+ // There wasn't any content neither before nor after.
303
+ return element;
304
+ }
305
+ }
306
+ return null;
307
+ }
308
+ }
309
+ /**
310
+ * Prepares a table for pasting and returns adjusted selection dimensions.
311
+ */
312
+ function prepareTableForPasting(selectedTableCells, pastedDimensions, writer, tableUtils) {
313
+ const selectedTable = selectedTableCells[0].findAncestor('table');
314
+ const columnIndexes = tableUtils.getColumnIndexes(selectedTableCells);
315
+ const rowIndexes = tableUtils.getRowIndexes(selectedTableCells);
316
+ const selection = {
317
+ firstColumn: columnIndexes.first,
318
+ lastColumn: columnIndexes.last,
319
+ firstRow: rowIndexes.first,
320
+ lastRow: rowIndexes.last
321
+ };
322
+ // Single cell selected - expand selection to pasted table dimensions.
323
+ const shouldExpandSelection = selectedTableCells.length === 1;
324
+ if (shouldExpandSelection) {
325
+ selection.lastRow += pastedDimensions.height - 1;
326
+ selection.lastColumn += pastedDimensions.width - 1;
327
+ expandTableSize(selectedTable, selection.lastRow + 1, selection.lastColumn + 1, tableUtils);
328
+ }
329
+ // In case of expanding selection we do not reset the selection so in this case we will always try to fix selection
330
+ // like in the case of a non-rectangular area. This might be fixed by re-setting selected cells array but this shortcut is safe.
331
+ if (shouldExpandSelection || !tableUtils.isSelectionRectangular(selectedTableCells)) {
332
+ // For a non-rectangular selection (ie in which some cells sticks out from a virtual selection rectangle) we need to create
333
+ // a table layout that has a rectangular selection. This will split cells so the selection become rectangular.
334
+ // Beyond this point we will operate on fixed content table.
335
+ splitCellsToRectangularSelection(selectedTable, selection, writer);
336
+ }
337
+ // However a selected table fragment might be invalid if examined alone. Ie such table fragment:
338
+ //
339
+ // +---+---+---+---+
340
+ // 0 | a | b | c | d |
341
+ // + + +---+---+
342
+ // 1 | | e | f | g |
343
+ // + +---+ +---+
344
+ // 2 | | h | | i | <- last row, each cell has rowspan = 2,
345
+ // + + + + + so we need to return 3, not 2
346
+ // 3 | | | | |
347
+ // +---+---+---+---+
348
+ //
349
+ // is invalid as the cells "h" and "i" have rowspans.
350
+ // This case needs only adjusting the selection dimension as the rest of the algorithm operates on empty slots also.
351
+ else {
352
+ selection.lastRow = adjustLastRowIndex(selectedTable, selection);
353
+ selection.lastColumn = adjustLastColumnIndex(selectedTable, selection);
354
+ }
355
+ return selection;
356
+ }
357
+ /**
358
+ * Expand table (in place) to expected size.
359
+ */
360
+ function expandTableSize(table, expectedHeight, expectedWidth, tableUtils) {
361
+ const tableWidth = tableUtils.getColumns(table);
362
+ const tableHeight = tableUtils.getRows(table);
363
+ if (expectedWidth > tableWidth) {
364
+ tableUtils.insertColumns(table, {
365
+ at: tableWidth,
366
+ columns: expectedWidth - tableWidth
367
+ });
368
+ }
369
+ if (expectedHeight > tableHeight) {
370
+ tableUtils.insertRows(table, {
371
+ at: tableHeight,
372
+ rows: expectedHeight - tableHeight
373
+ });
374
+ }
375
+ }
376
+ /**
377
+ * Returns two-dimensional array that is addressed by [ row ][ column ] that stores cells anchored at given location.
378
+ *
379
+ * At given row & column location it might be one of:
380
+ *
381
+ * * cell - cell from pasted table anchored at this location.
382
+ * * null - if no cell is anchored at this location.
383
+ *
384
+ * For instance, from a table below:
385
+ *
386
+ * +----+----+----+----+
387
+ * | 00 | 01 | 02 | 03 |
388
+ * + +----+----+----+
389
+ * | | 11 | 13 |
390
+ * +----+ +----+
391
+ * | 20 | | 23 |
392
+ * +----+----+----+----+
393
+ *
394
+ * The method will return an array (numbers represents cell element):
395
+ *
396
+ * ```ts
397
+ * const map = [
398
+ * [ '00', '01', '02', '03' ],
399
+ * [ null, '11', null, '13' ],
400
+ * [ '20', null, null, '23' ]
401
+ * ]
402
+ * ```
403
+ *
404
+ * This allows for a quick access to table at give row & column. For instance to access table cell "13" from pasted table call:
405
+ *
406
+ * ```ts
407
+ * const cell = map[ 1 ][ 3 ]
408
+ * ```
409
+ */
410
+ function createLocationMap(table, width, height) {
411
+ // Create height x width (row x column) two-dimensional table to store cells.
412
+ const map = new Array(height).fill(null)
413
+ .map(() => new Array(width).fill(null));
414
+ for (const { column, row, cell } of new TableWalker(table)) {
415
+ map[row][column] = cell;
416
+ }
417
+ return map;
418
+ }
419
+ /**
420
+ * Make selected cells rectangular by splitting the cells that stand out from a rectangular selection.
421
+ *
422
+ * In the table below a selection is shown with "::" and slots with anchor cells are named.
423
+ *
424
+ * +----+----+----+----+----+ +----+----+----+----+----+
425
+ * | 00 | 01 | 02 | 03 | | 00 | 01 | 02 | 03 |
426
+ * + +----+ +----+----+ | ::::::::::::::::----+
427
+ * | | 11 | | 13 | 14 | | ::11 | | 13:: 14 | <- first row
428
+ * +----+----+ + +----+ +----::---| | ::----+
429
+ * | 20 | 21 | | | 24 | select cells: | 20 ::21 | | :: 24 |
430
+ * +----+----+ +----+----+ 11 -> 33 +----::---| |---::----+
431
+ * | 30 | | 33 | 34 | | 30 :: | | 33:: 34 | <- last row
432
+ * + + +----+ + | :::::::::::::::: +
433
+ * | | | 43 | | | | | 43 | |
434
+ * +----+----+----+----+----+ +----+----+----+----+----+
435
+ * ^ ^
436
+ * first & last columns
437
+ *
438
+ * Will update table to:
439
+ *
440
+ * +----+----+----+----+----+
441
+ * | 00 | 01 | 02 | 03 |
442
+ * + +----+----+----+----+
443
+ * | | 11 | | 13 | 14 |
444
+ * +----+----+ + +----+
445
+ * | 20 | 21 | | | 24 |
446
+ * +----+----+ +----+----+
447
+ * | 30 | | | 33 | 34 |
448
+ * + +----+----+----+ +
449
+ * | | | | 43 | |
450
+ * +----+----+----+----+----+
451
+ *
452
+ * In th example above:
453
+ * - Cell "02" which have `rowspan = 4` must be trimmed at first and at after last row.
454
+ * - Cell "03" which have `rowspan = 2` and `colspan = 2` must be trimmed at first column and after last row.
455
+ * - Cells "00", "03" & "30" which cannot be cut by this algorithm as they are outside the trimmed area.
456
+ * - Cell "13" cannot be cut as it is inside the trimmed area.
457
+ */
458
+ function splitCellsToRectangularSelection(table, dimensions, writer) {
459
+ const { firstRow, lastRow, firstColumn, lastColumn } = dimensions;
460
+ const rowIndexes = { first: firstRow, last: lastRow };
461
+ const columnIndexes = { first: firstColumn, last: lastColumn };
462
+ // 1. Split cells vertically in two steps as first step might create cells that needs to split again.
463
+ doVerticalSplit(table, firstColumn, rowIndexes, writer);
464
+ doVerticalSplit(table, lastColumn + 1, rowIndexes, writer);
465
+ // 2. Split cells horizontally in two steps as first step might create cells that needs to split again.
466
+ doHorizontalSplit(table, firstRow, columnIndexes, writer);
467
+ doHorizontalSplit(table, lastRow + 1, columnIndexes, writer, firstRow);
468
+ }
469
+ function doHorizontalSplit(table, splitRow, limitColumns, writer, startRow = 0) {
470
+ // If selection starts at first row then no split is needed.
471
+ if (splitRow < 1) {
472
+ return;
473
+ }
474
+ const overlappingCells = getVerticallyOverlappingCells(table, splitRow, startRow);
475
+ // Filter out cells that are not touching insides of the rectangular selection.
476
+ const cellsToSplit = overlappingCells.filter(({ column, cellWidth }) => isAffectedBySelection(column, cellWidth, limitColumns));
477
+ return cellsToSplit.map(({ cell }) => splitHorizontally(cell, splitRow, writer));
478
+ }
479
+ function doVerticalSplit(table, splitColumn, limitRows, writer) {
480
+ // If selection starts at first column then no split is needed.
481
+ if (splitColumn < 1) {
482
+ return;
483
+ }
484
+ const overlappingCells = getHorizontallyOverlappingCells(table, splitColumn);
485
+ // Filter out cells that are not touching insides of the rectangular selection.
486
+ const cellsToSplit = overlappingCells.filter(({ row, cellHeight }) => isAffectedBySelection(row, cellHeight, limitRows));
487
+ return cellsToSplit.map(({ cell, column }) => splitVertically(cell, column, splitColumn, writer));
488
+ }
489
+ /**
490
+ * Checks if cell at given row (column) is affected by a rectangular selection defined by first/last column (row).
491
+ *
492
+ * The same check is used for row as for column.
493
+ */
494
+ function isAffectedBySelection(index, span, limit) {
495
+ const endIndex = index + span - 1;
496
+ const { first, last } = limit;
497
+ const isInsideSelection = index >= first && index <= last;
498
+ const overlapsSelectionFromOutside = index < first && endIndex >= first;
499
+ return isInsideSelection || overlapsSelectionFromOutside;
500
+ }
@@ -0,0 +1,33 @@
1
+ /**
2
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
3
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
4
+ */
5
+ /**
6
+ * @module table/tablecolumnresize/constants
7
+ */
8
+ /**
9
+ * The minimum column width given as a percentage value. Used in situations when the table is not yet rendered, so it is impossible to
10
+ * calculate how many percentage of the table width would be {@link ~COLUMN_MIN_WIDTH_IN_PIXELS minimum column width in pixels}.
11
+ *
12
+ * @internal
13
+ */
14
+ export const COLUMN_MIN_WIDTH_AS_PERCENTAGE = 5;
15
+ /**
16
+ * The minimum column width in pixels when the maximum table width is known.
17
+ * This value is an equivalent of `10%` of the default editor width (600px).
18
+ *
19
+ * @internal
20
+ */
21
+ export const COLUMN_MIN_WIDTH_IN_PIXELS = 40;
22
+ /**
23
+ * Determines how many digits after the decimal point are used to store the column width as a percentage value.
24
+ *
25
+ * @internal
26
+ */
27
+ export const COLUMN_WIDTH_PRECISION = 2;
28
+ /**
29
+ * The distance in pixels that the mouse has to move to start resizing the column.
30
+ *
31
+ * @internal
32
+ */
33
+ export const COLUMN_RESIZE_DISTANCE_THRESHOLD = 3;
@@ -5,7 +5,7 @@
5
5
  /**
6
6
  * @module table/tablecolumnresize/converters
7
7
  */
8
- import type { DowncastDispatcher, UpcastDispatcher } from '@ckeditor/ckeditor5-engine';
8
+ import type { DowncastDispatcher, UpcastDispatcher } from 'ckeditor5/src/engine.js';
9
9
  import { type TableUtils } from '../tableutils.js';
10
10
  /**
11
11
  * Returns a upcast helper that ensures the number of `<tableColumn>` elements corresponds to the actual number of columns in the table,
@@ -0,0 +1,62 @@
1
+ /**
2
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
3
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
4
+ */
5
+ import { normalizeColumnWidths, updateColumnElements, getColumnGroupElement, getTableColumnElements, translateColSpanAttribute } from './utils.js';
6
+ /**
7
+ * Returns a upcast helper that ensures the number of `<tableColumn>` elements corresponds to the actual number of columns in the table,
8
+ * because the input data might have too few or too many <col> elements.
9
+ *
10
+ * @internal
11
+ */
12
+ export function upcastColgroupElement(tableUtilsPlugin) {
13
+ return dispatcher => dispatcher.on('element:colgroup', (evt, data, conversionApi) => {
14
+ const modelTable = data.modelCursor.findAncestor('table');
15
+ const tableColumnGroup = getColumnGroupElement(modelTable);
16
+ if (!tableColumnGroup) {
17
+ return;
18
+ }
19
+ const columnElements = getTableColumnElements(tableColumnGroup);
20
+ const columnsCount = tableUtilsPlugin.getColumns(modelTable);
21
+ let columnWidths = translateColSpanAttribute(tableColumnGroup, conversionApi.writer);
22
+ // Fill the array with 'auto' values if the number of columns is higher than number of declared values.
23
+ columnWidths = Array.from({ length: columnsCount }, (_, index) => columnWidths[index] || 'auto');
24
+ if (columnWidths.length != columnElements.length || columnWidths.includes('auto')) {
25
+ updateColumnElements(columnElements, tableColumnGroup, normalizeColumnWidths(columnWidths), conversionApi.writer);
26
+ }
27
+ }, { priority: 'low' });
28
+ }
29
+ /**
30
+ * Returns downcast helper for adding `ck-table-resized` class if there is a `<tableColumnGroup>` element inside the table.
31
+ *
32
+ * @internal
33
+ */
34
+ export function downcastTableResizedClass() {
35
+ return dispatcher => dispatcher.on('insert:table', (evt, data, conversionApi) => {
36
+ const viewWriter = conversionApi.writer;
37
+ const modelTable = data.item;
38
+ const viewElement = conversionApi.mapper.toViewElement(modelTable);
39
+ const viewTable = viewElement.is('element', 'table') ?
40
+ viewElement :
41
+ Array.from(viewElement.getChildren()).find(viewChild => viewChild.is('element', 'table'));
42
+ const tableColumnGroup = getColumnGroupElement(modelTable);
43
+ if (tableColumnGroup) {
44
+ viewWriter.addClass('ck-table-resized', viewTable);
45
+ }
46
+ else {
47
+ viewWriter.removeClass('ck-table-resized', viewTable);
48
+ }
49
+ }, { priority: 'low' });
50
+ }
51
+ /**
52
+ * Returns a upcast helper that removes the `ck-table-resized` class from the table element.
53
+ *
54
+ * @internal
55
+ */
56
+ export function upcastTableResizedClass() {
57
+ return (dispatcher) => {
58
+ dispatcher.on('element:table', (evt, data, conversionApi) => {
59
+ conversionApi.consumable.consume(data.viewItem, { classes: 'ck-table-resized' });
60
+ });
61
+ };
62
+ }
@@ -2,8 +2,8 @@
2
2
  * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
4
4
  */
5
- import { Plugin, type Editor } from '@ckeditor/ckeditor5-core';
6
- import type { ModelElement } from '@ckeditor/ckeditor5-engine';
5
+ import { Plugin, type Editor } from 'ckeditor5/src/core.js';
6
+ import type { ModelElement } from 'ckeditor5/src/engine.js';
7
7
  import { TableEditing } from '../tableediting.js';
8
8
  import { TableUtils } from '../tableutils.js';
9
9
  /**