@openui5/sap.m 1.115.1 → 1.117.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 (465) hide show
  1. package/.reuse/dep5 +0 -5
  2. package/THIRDPARTY.txt +1 -7
  3. package/package.json +4 -4
  4. package/src/sap/m/.library +1 -1
  5. package/src/sap/m/AccButton.js +1 -1
  6. package/src/sap/m/ActionListItem.js +1 -1
  7. package/src/sap/m/ActionSelect.js +1 -1
  8. package/src/sap/m/ActionSheet.js +6 -2
  9. package/src/sap/m/ActionTile.js +1 -1
  10. package/src/sap/m/ActionTileContent.js +1 -1
  11. package/src/sap/m/AdditionalTextButton.js +1 -1
  12. package/src/sap/m/App.js +1 -1
  13. package/src/sap/m/AssociativeOverflowToolbar.js +1 -1
  14. package/src/sap/m/Avatar.js +46 -5
  15. package/src/sap/m/AvatarRenderer.js +16 -10
  16. package/src/sap/m/Bar.js +1 -1
  17. package/src/sap/m/Breadcrumbs.js +6 -5
  18. package/src/sap/m/BusyDialog.js +5 -3
  19. package/src/sap/m/BusyIndicator.js +1 -1
  20. package/src/sap/m/Button.js +1 -1
  21. package/src/sap/m/Carousel.js +24 -8
  22. package/src/sap/m/CarouselLayout.js +1 -1
  23. package/src/sap/m/CarouselRenderer.js +19 -4
  24. package/src/sap/m/CheckBox.js +8 -4
  25. package/src/sap/m/ColorPalette.js +1 -1
  26. package/src/sap/m/ColorPalettePopover.js +1 -1
  27. package/src/sap/m/Column.js +29 -170
  28. package/src/sap/m/ColumnHeaderPopover.js +1 -1
  29. package/src/sap/m/ColumnListItem.js +7 -12
  30. package/src/sap/m/ColumnListItemRenderer.js +16 -27
  31. package/src/sap/m/ColumnPopoverActionItem.js +1 -1
  32. package/src/sap/m/ColumnPopoverCustomItem.js +1 -1
  33. package/src/sap/m/ColumnPopoverItem.js +1 -1
  34. package/src/sap/m/ColumnPopoverSelectListItem.js +1 -1
  35. package/src/sap/m/ColumnPopoverSortItem.js +1 -1
  36. package/src/sap/m/ComboBox.js +1 -1
  37. package/src/sap/m/ComboBoxBase.js +1 -1
  38. package/src/sap/m/ComboBoxTextField.js +1 -1
  39. package/src/sap/m/CustomListItem.js +1 -1
  40. package/src/sap/m/CustomTile.js +1 -1
  41. package/src/sap/m/CustomTreeItem.js +1 -1
  42. package/src/sap/m/DatePicker.js +31 -5
  43. package/src/sap/m/DatePickerRenderer.js +3 -2
  44. package/src/sap/m/DateRangeSelection.js +77 -25
  45. package/src/sap/m/DateTimeField.js +15 -10
  46. package/src/sap/m/DateTimeInput.js +1 -1
  47. package/src/sap/m/DateTimePicker.js +1 -1
  48. package/src/sap/m/DateTimePickerRenderer.js +3 -1
  49. package/src/sap/m/Dialog.js +16 -10
  50. package/src/sap/m/DialogRenderer.js +3 -3
  51. package/src/sap/m/DisplayListItem.js +1 -1
  52. package/src/sap/m/DraftIndicator.js +1 -1
  53. package/src/sap/m/DynamicDate.js +1 -1
  54. package/src/sap/m/DynamicDateOption.js +2 -2
  55. package/src/sap/m/DynamicDateRange.js +42 -5
  56. package/src/sap/m/DynamicDateValueHelpUIType.js +1 -1
  57. package/src/sap/m/ExpandableText.js +1 -1
  58. package/src/sap/m/FacetFilter.js +1 -3
  59. package/src/sap/m/FacetFilterItem.js +1 -1
  60. package/src/sap/m/FacetFilterList.js +1 -1
  61. package/src/sap/m/FeedContent.js +1 -1
  62. package/src/sap/m/FeedInput.js +1 -1
  63. package/src/sap/m/FeedListItem.js +18 -1
  64. package/src/sap/m/FeedListItemAction.js +1 -1
  65. package/src/sap/m/Fiori20Adapter.js +2 -2
  66. package/src/sap/m/FlexBox.js +1 -1
  67. package/src/sap/m/FlexItemData.js +1 -1
  68. package/src/sap/m/FormattedText.js +44 -50
  69. package/src/sap/m/GenericTag.js +1 -1
  70. package/src/sap/m/GenericTile.js +1 -1
  71. package/src/sap/m/GroupHeaderListItem.js +1 -1
  72. package/src/sap/m/GroupHeaderListItemRenderer.js +5 -5
  73. package/src/sap/m/GrowingEnablement.js +34 -32
  74. package/src/sap/m/GrowingList.js +1 -1
  75. package/src/sap/m/HBox.js +1 -1
  76. package/src/sap/m/HeaderContainer.js +1 -1
  77. package/src/sap/m/HeaderContainerItemNavigator.js +1 -1
  78. package/src/sap/m/HyphenationSupport.js +13 -4
  79. package/src/sap/m/IconTabBar.js +3 -1
  80. package/src/sap/m/IconTabBarSelectList.js +1 -1
  81. package/src/sap/m/IconTabFilter.js +3 -3
  82. package/src/sap/m/IconTabFilterExpandButtonBadge.js +1 -1
  83. package/src/sap/m/IconTabHeader.js +1 -1
  84. package/src/sap/m/IconTabSeparator.js +1 -1
  85. package/src/sap/m/IllustratedMessage.js +4 -2
  86. package/src/sap/m/Illustration.js +1 -1
  87. package/src/sap/m/IllustrationPool.js +4 -3
  88. package/src/sap/m/Image.js +1 -1
  89. package/src/sap/m/ImageContent.js +1 -1
  90. package/src/sap/m/Input.js +21 -12
  91. package/src/sap/m/InputBase.js +7 -5
  92. package/src/sap/m/InputBaseRenderer.js +3 -3
  93. package/src/sap/m/InputListItem.js +1 -1
  94. package/src/sap/m/Label.js +1 -1
  95. package/src/sap/m/LabelRenderer.js +3 -3
  96. package/src/sap/m/LightBox.js +1 -1
  97. package/src/sap/m/LightBoxItem.js +1 -1
  98. package/src/sap/m/Link.js +36 -3
  99. package/src/sap/m/List.js +1 -1
  100. package/src/sap/m/ListBase.js +61 -28
  101. package/src/sap/m/ListBaseRenderer.js +12 -4
  102. package/src/sap/m/ListItemBase.js +17 -8
  103. package/src/sap/m/ListItemBaseRenderer.js +6 -6
  104. package/src/sap/m/MaskEnabler.js +1 -1
  105. package/src/sap/m/MaskInput.js +1 -1
  106. package/src/sap/m/MaskInputRule.js +1 -1
  107. package/src/sap/m/Menu.js +14 -1
  108. package/src/sap/m/MenuButton.js +1 -1
  109. package/src/sap/m/MenuItem.js +1 -1
  110. package/src/sap/m/MenuListItem.js +1 -1
  111. package/src/sap/m/MessageItem.js +1 -1
  112. package/src/sap/m/MessageListItem.js +1 -1
  113. package/src/sap/m/MessagePage.js +1 -1
  114. package/src/sap/m/MessagePopover.js +1 -1
  115. package/src/sap/m/MessagePopoverItem.js +1 -1
  116. package/src/sap/m/MessageStrip.js +1 -1
  117. package/src/sap/m/MessageToast.js +1 -12
  118. package/src/sap/m/MessageView.js +2 -2
  119. package/src/sap/m/MultiComboBox.js +3 -3
  120. package/src/sap/m/MultiEditField.js +1 -1
  121. package/src/sap/m/MultiInput.js +13 -2
  122. package/src/sap/m/NavContainer.js +21 -5
  123. package/src/sap/m/NewsContent.js +1 -1
  124. package/src/sap/m/NotificationList.js +1 -1
  125. package/src/sap/m/NotificationListBase.js +1 -1
  126. package/src/sap/m/NotificationListGroup.js +1 -1
  127. package/src/sap/m/NotificationListItem.js +1 -1
  128. package/src/sap/m/NumericContent.js +1 -1
  129. package/src/sap/m/NumericInput.js +1 -1
  130. package/src/sap/m/ObjectAttribute.js +1 -1
  131. package/src/sap/m/ObjectHeader.js +6 -1
  132. package/src/sap/m/ObjectIdentifier.js +1 -1
  133. package/src/sap/m/ObjectListItem.js +9 -2
  134. package/src/sap/m/ObjectMarker.js +1 -1
  135. package/src/sap/m/ObjectNumber.js +1 -1
  136. package/src/sap/m/ObjectStatus.js +63 -4
  137. package/src/sap/m/ObjectStatusRenderer.js +21 -9
  138. package/src/sap/m/OverflowToolbar.js +30 -15
  139. package/src/sap/m/OverflowToolbarAssociativePopover.js +5 -5
  140. package/src/sap/m/OverflowToolbarButton.js +1 -1
  141. package/src/sap/m/OverflowToolbarLayoutData.js +1 -1
  142. package/src/sap/m/OverflowToolbarMenuButton.js +1 -1
  143. package/src/sap/m/OverflowToolbarToggleButton.js +1 -1
  144. package/src/sap/m/P13nAnyFilterItem.js +1 -1
  145. package/src/sap/m/P13nColumnsItem.js +1 -1
  146. package/src/sap/m/P13nColumnsPanel.js +2 -8
  147. package/src/sap/m/P13nConditionPanel.js +1 -1
  148. package/src/sap/m/P13nDialog.js +2 -1
  149. package/src/sap/m/P13nDimMeasureItem.js +1 -1
  150. package/src/sap/m/P13nDimMeasurePanel.js +3 -10
  151. package/src/sap/m/P13nFilterItem.js +1 -1
  152. package/src/sap/m/P13nFilterPanel.js +28 -43
  153. package/src/sap/m/P13nGroupItem.js +1 -1
  154. package/src/sap/m/P13nGroupPanel.js +1 -1
  155. package/src/sap/m/P13nItem.js +1 -1
  156. package/src/sap/m/P13nPanel.js +1 -1
  157. package/src/sap/m/P13nSelectionItem.js +1 -1
  158. package/src/sap/m/P13nSelectionPanel.js +5 -3
  159. package/src/sap/m/P13nSortItem.js +1 -1
  160. package/src/sap/m/P13nSortPanel.js +1 -1
  161. package/src/sap/m/PDFViewer.js +1 -1
  162. package/src/sap/m/PDFViewerRenderer.js +1 -1
  163. package/src/sap/m/Page.js +8 -6
  164. package/src/sap/m/PageAccessibleLandmarkInfo.js +1 -1
  165. package/src/sap/m/PagingButton.js +1 -1
  166. package/src/sap/m/Panel.js +11 -2
  167. package/src/sap/m/PanelRenderer.js +9 -0
  168. package/src/sap/m/PlanningCalendar.js +10 -4
  169. package/src/sap/m/PlanningCalendarHeader.js +1 -1
  170. package/src/sap/m/PlanningCalendarLegend.js +1 -1
  171. package/src/sap/m/PlanningCalendarRow.js +1 -1
  172. package/src/sap/m/PlanningCalendarView.js +1 -1
  173. package/src/sap/m/Popover.js +13 -17
  174. package/src/sap/m/ProgressIndicator.js +1 -1
  175. package/src/sap/m/PullToRefresh.js +1 -1
  176. package/src/sap/m/QuickView.js +1 -1
  177. package/src/sap/m/QuickViewBase.js +1 -1
  178. package/src/sap/m/QuickViewCard.js +14 -1
  179. package/src/sap/m/QuickViewCardRenderer.js +0 -4
  180. package/src/sap/m/QuickViewGroup.js +1 -1
  181. package/src/sap/m/QuickViewGroupElement.js +1 -1
  182. package/src/sap/m/QuickViewPage.js +40 -28
  183. package/src/sap/m/RadioButton.js +1 -1
  184. package/src/sap/m/RadioButtonGroup.js +1 -1
  185. package/src/sap/m/RangeSlider.js +1 -1
  186. package/src/sap/m/RatingIndicator.js +16 -4
  187. package/src/sap/m/RatingIndicatorRenderer.js +9 -2
  188. package/src/sap/m/ResponsivePopover.js +1 -1
  189. package/src/sap/m/ResponsiveScale.js +1 -1
  190. package/src/sap/m/ScrollBar.js +1 -1
  191. package/src/sap/m/ScrollContainer.js +3 -3
  192. package/src/sap/m/SearchField.js +8 -12
  193. package/src/sap/m/SearchFieldRenderer.js +5 -5
  194. package/src/sap/m/SegmentedButton.js +4 -2
  195. package/src/sap/m/SegmentedButtonItem.js +1 -1
  196. package/src/sap/m/SegmentedButtonRenderer.js +3 -3
  197. package/src/sap/m/Select.js +18 -16
  198. package/src/sap/m/SelectDialog.js +1 -1
  199. package/src/sap/m/SelectDialogBase.js +28 -4
  200. package/src/sap/m/SelectList.js +5 -6
  201. package/src/sap/m/SelectionDetails.js +1 -1
  202. package/src/sap/m/SelectionDetailsFacade.js +2 -2
  203. package/src/sap/m/SelectionDetailsItem.js +1 -1
  204. package/src/sap/m/SelectionDetailsItemLine.js +1 -1
  205. package/src/sap/m/Shell.js +1 -1
  206. package/src/sap/m/SimpleFixFlex.js +1 -1
  207. package/src/sap/m/SinglePlanningCalendar.js +1 -1
  208. package/src/sap/m/SinglePlanningCalendarDayView.js +1 -1
  209. package/src/sap/m/SinglePlanningCalendarGrid.js +1 -1
  210. package/src/sap/m/SinglePlanningCalendarMonthGrid.js +43 -43
  211. package/src/sap/m/SinglePlanningCalendarMonthView.js +1 -1
  212. package/src/sap/m/SinglePlanningCalendarView.js +1 -1
  213. package/src/sap/m/SinglePlanningCalendarWeekView.js +1 -1
  214. package/src/sap/m/SinglePlanningCalendarWorkWeekView.js +1 -1
  215. package/src/sap/m/SlideTile.js +1 -1
  216. package/src/sap/m/Slider.js +1 -1
  217. package/src/sap/m/SliderTooltip.js +1 -1
  218. package/src/sap/m/SliderTooltipBase.js +1 -1
  219. package/src/sap/m/SliderTooltipContainer.js +1 -1
  220. package/src/sap/m/SplitApp.js +1 -1
  221. package/src/sap/m/SplitButton.js +1 -1
  222. package/src/sap/m/SplitContainer.js +8 -13
  223. package/src/sap/m/StandardDynamicDateOption.js +2 -2
  224. package/src/sap/m/StandardListItem.js +1 -1
  225. package/src/sap/m/StandardTile.js +1 -1
  226. package/src/sap/m/StandardTileRenderer.js +1 -1
  227. package/src/sap/m/StandardTreeItem.js +1 -1
  228. package/src/sap/m/StepInput.js +3 -3
  229. package/src/sap/m/SuggestionItem.js +4 -2
  230. package/src/sap/m/SuggestionsPopover.js +1 -1
  231. package/src/sap/m/Switch.js +1 -1
  232. package/src/sap/m/TabContainer.js +1 -1
  233. package/src/sap/m/TabContainerItem.js +1 -1
  234. package/src/sap/m/TabStrip.js +1 -1
  235. package/src/sap/m/TabStripItem.js +1 -1
  236. package/src/sap/m/Table.js +59 -180
  237. package/src/sap/m/TablePersoController.js +1 -1
  238. package/src/sap/m/TablePersoDialog.js +1 -1
  239. package/src/sap/m/TablePersoProvider.js +4 -1
  240. package/src/sap/m/TableRenderer.js +98 -126
  241. package/src/sap/m/TableSelectDialog.js +1 -1
  242. package/src/sap/m/Text.js +1 -1
  243. package/src/sap/m/TextArea.js +1 -1
  244. package/src/sap/m/TextRenderer.js +3 -3
  245. package/src/sap/m/Tile.js +1 -1
  246. package/src/sap/m/TileContainer.js +1 -1
  247. package/src/sap/m/TileContent.js +1 -1
  248. package/src/sap/m/TileRenderer.js +7 -4
  249. package/src/sap/m/TimePicker.js +41 -12
  250. package/src/sap/m/TimePickerClock.js +1 -1
  251. package/src/sap/m/TimePickerClocks.js +1 -1
  252. package/src/sap/m/TimePickerClocksRenderer.js +6 -13
  253. package/src/sap/m/TimePickerInputs.js +1 -1
  254. package/src/sap/m/TimePickerInputsRenderer.js +6 -10
  255. package/src/sap/m/TimePickerInternals.js +1 -44
  256. package/src/sap/m/TimePickerRenderer.js +3 -2
  257. package/src/sap/m/TimePickerSlider.js +1 -1
  258. package/src/sap/m/TimePickerSliders.js +1 -1
  259. package/src/sap/m/Title.js +1 -1
  260. package/src/sap/m/TitlePropagationSupport.js +1 -1
  261. package/src/sap/m/ToggleButton.js +15 -3
  262. package/src/sap/m/Token.js +1 -1
  263. package/src/sap/m/Tokenizer.js +1 -1
  264. package/src/sap/m/Toolbar.js +4 -2
  265. package/src/sap/m/ToolbarLayoutData.js +1 -1
  266. package/src/sap/m/ToolbarSeparator.js +1 -1
  267. package/src/sap/m/ToolbarSpacer.js +1 -1
  268. package/src/sap/m/Tree.js +1 -1
  269. package/src/sap/m/TreeItemBase.js +1 -1
  270. package/src/sap/m/UploadCollection.js +2 -2
  271. package/src/sap/m/UploadCollectionItem.js +1 -1
  272. package/src/sap/m/UploadCollectionParameter.js +1 -1
  273. package/src/sap/m/UploadCollectionToolbarPlaceholder.js +1 -1
  274. package/src/sap/m/VBox.js +1 -1
  275. package/src/sap/m/ValueStateHeader.js +1 -1
  276. package/src/sap/m/VariantManagement.js +13 -50
  277. package/src/sap/m/ViewSettingsCustomItem.js +1 -1
  278. package/src/sap/m/ViewSettingsCustomTab.js +1 -1
  279. package/src/sap/m/ViewSettingsDialog.js +2 -2
  280. package/src/sap/m/ViewSettingsFilterItem.js +1 -1
  281. package/src/sap/m/ViewSettingsItem.js +1 -1
  282. package/src/sap/m/VisibleItem.js +1 -1
  283. package/src/sap/m/WheelSlider.js +1 -1
  284. package/src/sap/m/WheelSliderContainer.js +1 -1
  285. package/src/sap/m/Wizard.js +1 -1
  286. package/src/sap/m/WizardProgressNavigator.js +1 -1
  287. package/src/sap/m/WizardStep.js +1 -1
  288. package/src/sap/m/changeHandler/AddTableColumn.js +1 -1
  289. package/src/sap/m/changeHandler/ChangeLinkTarget.js +1 -1
  290. package/src/sap/m/changeHandler/CombineButtons.js +1 -1
  291. package/src/sap/m/changeHandler/MoveTableColumns.js +1 -1
  292. package/src/sap/m/changeHandler/SelectIconTabBarFilter.js +1 -1
  293. package/src/sap/m/changeHandler/SplitMenuButton.js +1 -1
  294. package/src/sap/m/designtime/HBox.designtime.js +16 -0
  295. package/src/sap/m/designtime/IconTabFilter.designtime.js +0 -9
  296. package/src/sap/m/designtime/ObjectHeader.designtime.js +26 -0
  297. package/src/sap/m/designtime/Select.designtime.js +2 -1
  298. package/src/sap/m/designtime/VBox.designtime.js +16 -0
  299. package/src/sap/m/inputUtils/SuggestionsPopoverDialogMixin.js +5 -5
  300. package/src/sap/m/inputUtils/SuggestionsPopoverPopoverMixin.js +4 -0
  301. package/src/sap/m/library.js +62 -7
  302. package/src/sap/m/messagebundle.properties +27 -13
  303. package/src/sap/m/messagebundle_ar.properties +36 -20
  304. package/src/sap/m/messagebundle_bg.properties +102 -86
  305. package/src/sap/m/messagebundle_ca.properties +34 -18
  306. package/src/sap/m/messagebundle_cs.properties +40 -24
  307. package/src/sap/m/messagebundle_cy.properties +35 -19
  308. package/src/sap/m/messagebundle_da.properties +35 -19
  309. package/src/sap/m/messagebundle_de.properties +35 -19
  310. package/src/sap/m/messagebundle_el.properties +36 -20
  311. package/src/sap/m/messagebundle_en.properties +35 -19
  312. package/src/sap/m/messagebundle_en_GB.properties +35 -19
  313. package/src/sap/m/messagebundle_en_US_sappsd.properties +34 -18
  314. package/src/sap/m/messagebundle_en_US_saprigi.properties +34 -18
  315. package/src/sap/m/messagebundle_en_US_saptrc.properties +34 -18
  316. package/src/sap/m/messagebundle_es.properties +33 -17
  317. package/src/sap/m/messagebundle_es_MX.properties +33 -17
  318. package/src/sap/m/messagebundle_et.properties +33 -17
  319. package/src/sap/m/messagebundle_fi.properties +37 -21
  320. package/src/sap/m/messagebundle_fr.properties +38 -22
  321. package/src/sap/m/messagebundle_fr_CA.properties +35 -19
  322. package/src/sap/m/messagebundle_hi.properties +36 -20
  323. package/src/sap/m/messagebundle_hr.properties +36 -20
  324. package/src/sap/m/messagebundle_hu.properties +39 -23
  325. package/src/sap/m/messagebundle_id.properties +38 -22
  326. package/src/sap/m/messagebundle_it.properties +33 -17
  327. package/src/sap/m/messagebundle_iw.properties +40 -24
  328. package/src/sap/m/messagebundle_ja.properties +70 -54
  329. package/src/sap/m/messagebundle_kk.properties +35 -19
  330. package/src/sap/m/messagebundle_ko.properties +36 -20
  331. package/src/sap/m/messagebundle_lt.properties +35 -19
  332. package/src/sap/m/messagebundle_lv.properties +33 -17
  333. package/src/sap/m/messagebundle_ms.properties +35 -19
  334. package/src/sap/m/messagebundle_nl.properties +35 -19
  335. package/src/sap/m/messagebundle_no.properties +38 -22
  336. package/src/sap/m/messagebundle_pl.properties +35 -19
  337. package/src/sap/m/messagebundle_pt.properties +33 -17
  338. package/src/sap/m/messagebundle_pt_PT.properties +33 -17
  339. package/src/sap/m/messagebundle_ro.properties +45 -29
  340. package/src/sap/m/messagebundle_ru.properties +32 -16
  341. package/src/sap/m/messagebundle_sh.properties +43 -27
  342. package/src/sap/m/messagebundle_sk.properties +35 -19
  343. package/src/sap/m/messagebundle_sl.properties +96 -80
  344. package/src/sap/m/messagebundle_sv.properties +37 -21
  345. package/src/sap/m/messagebundle_th.properties +42 -26
  346. package/src/sap/m/messagebundle_tr.properties +36 -20
  347. package/src/sap/m/messagebundle_uk.properties +38 -22
  348. package/src/sap/m/messagebundle_vi.properties +35 -19
  349. package/src/sap/m/messagebundle_zh_CN.properties +40 -24
  350. package/src/sap/m/messagebundle_zh_TW.properties +37 -21
  351. package/src/sap/m/p13n/AbstractContainer.js +2 -2
  352. package/src/sap/m/p13n/AbstractContainerItem.js +2 -2
  353. package/src/sap/m/p13n/BasePanel.js +11 -5
  354. package/src/sap/m/p13n/Container.js +9 -6
  355. package/src/sap/m/p13n/Engine.js +33 -5
  356. package/src/sap/m/p13n/FlexUtil.js +7 -3
  357. package/src/sap/m/p13n/GroupController.js +1 -1
  358. package/src/sap/m/p13n/GroupPanel.js +6 -1
  359. package/src/sap/m/p13n/MetadataHelper.js +1 -1
  360. package/src/sap/m/p13n/PersistenceProvider.js +2 -92
  361. package/src/sap/m/p13n/Popup.js +25 -2
  362. package/src/sap/m/p13n/QueryPanel.js +18 -3
  363. package/src/sap/m/p13n/SelectionController.js +6 -7
  364. package/src/sap/m/p13n/SelectionPanel.js +16 -5
  365. package/src/sap/m/p13n/SortController.js +1 -1
  366. package/src/sap/m/p13n/SortPanel.js +8 -4
  367. package/src/sap/m/p13n/enum/PersistenceMode.js +9 -0
  368. package/src/sap/m/p13n/handler/xConfigHandler.js +13 -13
  369. package/src/sap/m/p13n/modification/FlexModificationHandler.js +24 -1
  370. package/src/sap/m/p13n/modules/DefaultProviderRegistry.js +1 -13
  371. package/src/sap/m/p13n/modules/StateHandlerRegistry.js +1 -1
  372. package/src/sap/m/p13n/modules/UIManager.js +5 -4
  373. package/src/sap/m/p13n/modules/xConfigAPI.js +26 -0
  374. package/src/sap/m/plugins/CellSelector.js +534 -799
  375. package/src/sap/m/plugins/ColumnResizer.js +1 -9
  376. package/src/sap/m/plugins/CopyProvider.js +2 -10
  377. package/src/sap/m/plugins/DataStateIndicator.js +8 -2
  378. package/src/sap/m/plugins/PasteProvider.js +1 -1
  379. package/src/sap/m/plugins/PluginBase.js +1 -1
  380. package/src/sap/m/semantic/AddAction.js +1 -1
  381. package/src/sap/m/semantic/CancelAction.js +1 -1
  382. package/src/sap/m/semantic/DeleteAction.js +1 -1
  383. package/src/sap/m/semantic/DetailPage.js +1 -1
  384. package/src/sap/m/semantic/DiscussInJamAction.js +1 -1
  385. package/src/sap/m/semantic/EditAction.js +1 -1
  386. package/src/sap/m/semantic/FavoriteAction.js +1 -1
  387. package/src/sap/m/semantic/FilterAction.js +1 -1
  388. package/src/sap/m/semantic/FilterSelect.js +1 -1
  389. package/src/sap/m/semantic/FlagAction.js +1 -1
  390. package/src/sap/m/semantic/ForwardAction.js +1 -1
  391. package/src/sap/m/semantic/FullscreenPage.js +1 -1
  392. package/src/sap/m/semantic/GroupAction.js +1 -1
  393. package/src/sap/m/semantic/GroupSelect.js +1 -1
  394. package/src/sap/m/semantic/MainAction.js +1 -1
  395. package/src/sap/m/semantic/MasterPage.js +1 -1
  396. package/src/sap/m/semantic/MessagesIndicator.js +1 -1
  397. package/src/sap/m/semantic/MultiSelectAction.js +1 -1
  398. package/src/sap/m/semantic/NegativeAction.js +1 -1
  399. package/src/sap/m/semantic/OpenInAction.js +1 -1
  400. package/src/sap/m/semantic/PositiveAction.js +1 -1
  401. package/src/sap/m/semantic/PrintAction.js +1 -1
  402. package/src/sap/m/semantic/SaveAction.js +1 -1
  403. package/src/sap/m/semantic/Segment.js +1 -1
  404. package/src/sap/m/semantic/SegmentedContainer.js +1 -1
  405. package/src/sap/m/semantic/SemanticButton.js +1 -1
  406. package/src/sap/m/semantic/SemanticConfiguration.js +3 -3
  407. package/src/sap/m/semantic/SemanticControl.js +1 -1
  408. package/src/sap/m/semantic/SemanticOverflowToolbarButton.js +1 -1
  409. package/src/sap/m/semantic/SemanticOverflowToolbarToggleButton.js +1 -1
  410. package/src/sap/m/semantic/SemanticPage.js +1 -1
  411. package/src/sap/m/semantic/SemanticSelect.js +1 -1
  412. package/src/sap/m/semantic/SemanticToggleButton.js +1 -1
  413. package/src/sap/m/semantic/SendEmailAction.js +1 -1
  414. package/src/sap/m/semantic/SendMessageAction.js +1 -1
  415. package/src/sap/m/semantic/ShareInJamAction.js +1 -1
  416. package/src/sap/m/semantic/ShareMenu.js +1 -1
  417. package/src/sap/m/semantic/ShareMenuPage.js +1 -1
  418. package/src/sap/m/semantic/SortAction.js +1 -1
  419. package/src/sap/m/semantic/SortSelect.js +1 -1
  420. package/src/sap/m/table/Util.js +6 -5
  421. package/src/sap/m/table/columnmenu/ActionItem.js +1 -1
  422. package/src/sap/m/table/columnmenu/Entry.js +1 -1
  423. package/src/sap/m/table/columnmenu/Item.js +1 -1
  424. package/src/sap/m/table/columnmenu/ItemBase.js +1 -1
  425. package/src/sap/m/table/columnmenu/Menu.js +1 -1
  426. package/src/sap/m/table/columnmenu/QuickAction.js +1 -1
  427. package/src/sap/m/table/columnmenu/QuickActionBase.js +1 -1
  428. package/src/sap/m/table/columnmenu/QuickActionItem.js +1 -1
  429. package/src/sap/m/table/columnmenu/QuickGroup.js +1 -1
  430. package/src/sap/m/table/columnmenu/QuickGroupItem.js +1 -1
  431. package/src/sap/m/table/columnmenu/QuickSort.js +1 -1
  432. package/src/sap/m/table/columnmenu/QuickSortItem.js +1 -1
  433. package/src/sap/m/table/columnmenu/QuickTotal.js +1 -1
  434. package/src/sap/m/table/columnmenu/QuickTotalItem.js +1 -1
  435. package/src/sap/m/themes/base/Avatar.less +78 -7
  436. package/src/sap/m/themes/base/Carousel.less +7 -0
  437. package/src/sap/m/themes/base/CellSelector.less +50 -105
  438. package/src/sap/m/themes/base/IconTabBar.less +1 -1
  439. package/src/sap/m/themes/base/Link.less +20 -24
  440. package/src/sap/m/themes/base/MessageStrip.less +1 -1
  441. package/src/sap/m/themes/base/NumericContent.less +4 -0
  442. package/src/sap/m/themes/base/ObjectStatus.less +1 -2
  443. package/src/sap/m/themes/base/Panel.less +14 -0
  444. package/src/sap/m/themes/base/PlanningCalendarHeader.less +2 -1
  445. package/src/sap/m/themes/base/RadioButton.less +3 -1
  446. package/src/sap/m/themes/base/SearchField.less +13 -3
  447. package/src/sap/m/themes/base/Select.less +32 -2
  448. package/src/sap/m/themes/base/Table.less +4 -8
  449. package/src/sap/m/themes/base/TimePickerClocks.less +4 -0
  450. package/src/sap/m/themes/base/UploadSet.less +13 -1
  451. package/src/sap/m/themes/base/UploadSetTable.less +80 -0
  452. package/src/sap/m/themes/base/ValueStateMessage.less +1 -0
  453. package/src/sap/m/themes/base/VariantManagement.less +1 -0
  454. package/src/sap/m/themes/base/Wizard.less +1 -1
  455. package/src/sap/m/themes/base/library.source.less +1 -0
  456. package/src/sap/m/upload/FilePreviewDialog.js +257 -0
  457. package/src/sap/m/upload/UploadSet.js +140 -67
  458. package/src/sap/m/upload/UploadSetItem.js +51 -27
  459. package/src/sap/m/upload/UploadSetTable.js +929 -0
  460. package/src/sap/m/upload/UploadSetTableItem.js +327 -0
  461. package/src/sap/m/upload/UploadSetTableItemRenderer.js +22 -0
  462. package/src/sap/m/upload/UploadSetTableRenderer.js +34 -0
  463. package/src/sap/m/upload/UploadSetToolbarPlaceholder.js +1 -1
  464. package/src/sap/m/upload/UploaderTableItem.js +276 -0
  465. package/ui5.yaml +1 -1
@@ -12,51 +12,27 @@ sap.ui.define([
12
12
  ], function (PluginBase, KeyCodes, Core, Element, Log) {
13
13
  "use strict";
14
14
 
15
- var SELECTION_DIRECTION = {
16
- NEXT: 1,
17
- PREVIOUS: 2
15
+ var DIRECTION = {
16
+ ROW: "row",
17
+ COL: "col"
18
18
  };
19
19
 
20
- var MOUSE_POSITION = {
21
- ABOVE: 0,
22
- RIGHT: 1,
23
- BELOW: 2,
24
- LEFT: 3,
25
- IN: 4
26
- };
27
-
28
- var CSS_CLASS = "sapMPluginsCellSelector";
29
-
30
20
  /**
31
21
  * Constructor for a new CellSelector plugin.
32
22
  *
33
23
  * @param {string} [sId] id for the new control, generated automatically if no id is given
34
24
  * @param {object} [mSettings] initial settings for the new control
35
25
  *
36
- * The CellSelector plugins enables cell selection inside the table, when added as a dependent to the control.
26
+ * The CellSelector plugins enables cell selection inside the table, when it is added as a dependent to the control.
37
27
  * It allows the user to individually select a cell block.
38
28
  *
39
- * Keyboard Usage:
40
- * - SPACE: Select the currently focused cell.
41
- * - SHIFT + ARROW_KEYS: Expands/shrink the current cell selection block into the specified direction by one row/column.
42
- * - SHIFT + SPACE: Enahnces the current cell selection block to cover the whole row.
43
- * - CTRL + SPACE: Enhances the current cell selection block to cover the whole column.
44
- * - SHIFT + HOME: Enhances the current cell selection block to the begin of the covered rows.
45
- * - SHIFT + END: Enhances the current cell selection block to the end of the covered rows.
46
- * - CTRL + SHIFT + A: Clears the selection.
47
- *
48
- * Mouse Usage:
49
- * - Left Click: Select the clicked cell.
50
- * - Mousedown + Moving: Select an area of cells.
51
- * - Drag Borders: Drag the horizontal/vertical borders to enhance the cell selection in the corresponding direction.
52
- * - Drag Edge: Enhance your current cell selection in any direction, when dragging a corner.
53
- *
54
29
  * @extends sap.m.plugins.PluginBase
55
30
  * @class
56
- * @version 1.115.1
31
+ * @version 1.117.0
57
32
  * @author SAP SE
58
33
  *
59
34
  * @private
35
+ * @experimental
60
36
  * @alias sap.m.plugins.CellSelector
61
37
  */
62
38
  var CellSelector = PluginBase.extend("sap.m.plugins.CellSelector", {
@@ -82,50 +58,99 @@ sap.ui.define([
82
58
  }
83
59
  });
84
60
 
61
+ /*
62
+ CellSelector Interactions
63
+ Keyboard Usage:
64
+ - SPACE: Select the currently focused cell. If pressed inside a selection block, removes selection.
65
+ - SHIFT + ARROW_KEYS: Adjusts an already existing selection block OR creates a new one, if used outside of selection block.
66
+ - SHIFT + SPACE: Transforms current selection block into row selection. Result depends on selection mode applied to table.
67
+ - CTRL + SPACE: Extends selection to all cells of the column (up to the range limit).
68
+ - CTRL + SHIFT + A: Clears selection
69
+ Mouse Usage:
70
+ - CTRL + Click: Select cell. If click is on selection block, removes selection block.
71
+ - Mousedown + Movement: Selects the cell where mouse was pressed down. If move goes outside, extends selection.
72
+ - Borders: Extend/reduce selection either horizontally or vertically.
73
+ - Edge: Extend/reduce selection freely.
74
+ */
75
+
85
76
  CellSelector.prototype.onActivate = function (oControl) {
77
+ this._iRtl = Core.getConfiguration().getRTL() ? -1 : 1;
86
78
  oControl.addDelegate(this, true, this);
87
- this._oSession = {};
88
- this._oSession.oCanvas = {};
89
- this._oSession.oEdge = {};
90
- this._oSession.oBorderLine = {};
91
-
92
- var sScrollEvent = this.getConfig("scrollEvent");
93
- sScrollEvent && oControl.attachEvent(sScrollEvent, this._handleScroll, this);
94
-
95
- this._fnMouseupHandler = this._onmouseup.bind(this);
96
- document.addEventListener("mouseup", this._fnMouseupHandler);
97
- var oContainerRef = this.getControl().getDomRef(this.getConfig("scrollContainer"));
98
- if (oContainerRef) {
99
- this._fnMouseleaveHandler = this._onMouseLeave.bind(this);
100
- oContainerRef.addEventListener("mouseleave", this._fnMouseleaveHandler);
101
- }
79
+ this._oSession = { cellRefs: [] };
80
+ this._mTimeouts = {};
81
+ this._fnControlUpdate = function(oEvent) {
82
+ if (this._bScrolling) {
83
+ this._scrollSelect(this._oSession.scrollForward, this._oSession.isVertical, oEvent);
84
+ } else {
85
+ this._selectCells();
86
+ }
87
+ }.bind(this);
88
+ this._fnOnMouseEnter = this._onmouseenter.bind(this);
89
+ this._fnOnMouseOut = this._onmouseout.bind(this);
90
+ this._fnOnMouseMove = this._onmousemove.bind(this);
91
+ this._fnOnMouseUp = this.onmouseup.bind(this);
92
+
93
+ // Register Events, as adding dependent does not trigger rerendering
94
+ this._registerEvents();
102
95
  };
103
96
 
104
97
  CellSelector.prototype.onDeactivate = function (oControl) {
105
98
  oControl.removeDelegate(this, this);
106
- this._oSession = {};
107
- this._oSession.oCanvas = {};
108
- this._oSession.oEdge = {};
109
- this._oSession.oBorderLine = {};
110
-
111
- var sScrollEvent = this.getConfig("scrollEvent");
112
- sScrollEvent && oControl.detachEvent(sScrollEvent, this._handleScroll, this);
113
-
114
- document.removeEventListener("mouseup", this._fnMouseupHandler);
115
- var oContainerRef = this.getControl().getDomRef(this.getConfig("scrollContainer"));
116
- if (oContainerRef) {
117
- oContainerRef.removeEventListener("mouseleave", this._fnMouseleaveHandler);
99
+ if (this._oSession) {
100
+ this.removeSelection();
101
+ this._oSession = null;
102
+ this._mTimeouts = null;
118
103
  }
104
+
105
+ this._deregisterEvents();
119
106
  };
120
107
 
121
- CellSelector.prototype.onAfterRendering = function () {
122
- this._fnMouseupHandler = this._onmouseup.bind(this);
123
- document.addEventListener("mouseup", this._fnMouseupHandler);
124
- var oContainerRef = this.getControl().getDomRef(this.getConfig("scrollContainer"));
125
- if (oContainerRef) {
126
- this._fnMouseleaveHandler = this._onMouseLeave.bind(this);
127
- oContainerRef.addEventListener("mouseleave", this._fnMouseleaveHandler);
108
+ CellSelector.prototype.destroy = function() {
109
+ if (this.getControl() && !this.getControl().isDestroyed()) {
110
+ this.removeSelection();
128
111
  }
112
+ this._deregisterEvents();
113
+ this._oSession = null;
114
+ this._mTimeouts = null;
115
+
116
+ return PluginBase.prototype.destroy.call(this);
117
+ };
118
+
119
+ CellSelector.prototype.onBeforeRendering = function() {
120
+ if (this._oResizer) {
121
+ // remove resizer, as due to rerendering table element may be gone
122
+ this._oResizer.remove();
123
+ this._oResizer = null;
124
+ }
125
+ };
126
+
127
+ CellSelector.prototype.onAfterRendering = function() {
128
+ this._deregisterEvents();
129
+ this._registerEvents();
130
+ };
131
+
132
+ CellSelector.prototype._registerEvents = function() {
133
+ if (this.getControl()) {
134
+ this.getControl().attachEvent(this.getConfig("scrollEvent"), this._fnControlUpdate);
135
+ var oScrollArea = this.getControl().getDomRef(this.getConfig("scrollArea"));
136
+ if (oScrollArea) {
137
+ oScrollArea.addEventListener("mouseleave", this._fnOnMouseOut);
138
+ oScrollArea.addEventListener("mouseenter", this._fnOnMouseEnter);
139
+ }
140
+ }
141
+ document.addEventListener("mousemove", this._fnOnMouseMove);
142
+ document.addEventListener("mouseup", this._fnOnMouseUp);
143
+ };
144
+
145
+ CellSelector.prototype._deregisterEvents = function() {
146
+ if (this.getControl()) {
147
+ this.getControl().detachEvent(this.getConfig("scrollEvent"), this._fnControlUpdate);
148
+ var oScrollArea = this.getControl().getDomRef(this.getConfig("scrollArea"));
149
+ oScrollArea.removeEventListener("mouseleave", this._fnOnMouseOut);
150
+ oScrollArea.removeEventListener("mouseenter", this._fnOnMouseEnter);
151
+ }
152
+ document.removeEventListener("mousemove", this._fnOnMouseMove);
153
+ document.removeEventListener("mouseup", this._fnOnMouseUp);
129
154
  };
130
155
 
131
156
  /**
@@ -143,7 +168,7 @@ sap.ui.define([
143
168
  return null;
144
169
  }
145
170
 
146
- var mSelectionRange = getNormalizedBounds(this._oSession.mSource, this._oSession.mTarget);
171
+ var mSelectionRange = this._getNormalizedBounds(this._oSession.mSource, this._oSession.mTarget, true);
147
172
  if (isNaN(mSelectionRange.from.rowIndex) || isNaN(mSelectionRange.to.rowIndex)) {
148
173
  return null;
149
174
  }
@@ -174,319 +199,265 @@ sap.ui.define([
174
199
  };
175
200
 
176
201
  CellSelector.prototype.onsapspace = function (oEvent) {
177
- if (oEvent.isMarked()) {
178
- return;
179
- } else if (!this.getConfig("isSelectionEnabled", this.getControl())) {
180
- Log.error("Cell selection is inactive, because preconditions are not met.");
181
- return;
182
- }
183
-
184
- var oTarget = oEvent.target;
185
- var oCellInfo = this.getConfig("getCellInfo", this.getControl(), oTarget);
186
-
187
- if (oCellInfo) {
188
- this._bSelecting = true;
189
- if (this._oSession.mSource) {
190
- if (this._oSession.mSource.rowIndex !== oCellInfo.rowIndex || this._oSession.mSource.colIndex !== oCellInfo.colIndex) {
191
- this._oSession.mSource = null;
192
- this._oSession.mTarget = null;
193
- }
194
- }
195
- this._oSession.mSource = oCellInfo;
196
- this._oSession.mStart = oCellInfo;
197
- this._selectCells(this._oSession.mSource, oCellInfo, {info: {focus: oCellInfo}});
198
-
199
- oEvent.preventDefault();
200
- oEvent.setMarked();
201
- }
202
+ this._startSelection(oEvent, false);
202
203
  };
203
204
 
204
- CellSelector.prototype.onsapnext = CellSelector.prototype.onsapprevious = function (oEvent) {
205
- if (!this._bSelecting) {
206
- return;
207
- }
208
- this.clearSelection();
205
+ CellSelector.prototype.onsapupmodifiers = function(oEvent) {
206
+ this._onsaparrowmodifiers(oEvent, DIRECTION.ROW, -1, 0);
209
207
  };
210
208
 
211
- CellSelector.prototype.onsaphome = CellSelector.prototype.onsapend = CellSelector.prototype.onsapnext;
209
+ CellSelector.prototype.onsapdownmodifiers = function(oEvent) {
210
+ this._onsaparrowmodifiers(oEvent, DIRECTION.ROW, 1, 0);
211
+ };
212
212
 
213
- CellSelector.prototype.onsapnextmodifiers = function (oEvent) {
214
- this._selectNextCell(oEvent, false, 1);
213
+ CellSelector.prototype.onsapleftmodifiers = function(oEvent) {
214
+ this._onsaparrowmodifiers(oEvent, DIRECTION.COL, 0, -1);
215
215
  };
216
216
 
217
- CellSelector.prototype.onsappreviousmodifiers = function (oEvent) {
218
- this._selectNextCell(oEvent, true.valueOf, -1);
217
+ CellSelector.prototype.onsaprightmodifiers = function(oEvent) {
218
+ this._onsaparrowmodifiers(oEvent, DIRECTION.COL, 0, 1);
219
219
  };
220
220
 
221
- CellSelector.prototype._selectNextCell = function (oEvent, bIsPrevious, iDirectionIndex) {
222
- if (!this._bSelecting || !oEvent.shiftKey || oEvent.isMarked() || !this._isInSelectionArea(oEvent.target)) {
221
+ CellSelector.prototype._onsaparrowmodifiers = function(oEvent, sDirectionType, iRowDiff, iColDiff) {
222
+ if (oEvent.isMarked() || !oEvent.shiftKey) {
223
223
  return;
224
224
  }
225
225
 
226
- var oFocusCellInfo = this.getConfig("getCellInfo", this.getControl(), oEvent.target);
227
- var mFrom = Object.assign({}, this._oSession.mSource);
228
- var mTo = Object.assign({}, this._oSession.mTarget);
226
+ var oSelectableCell = this._getSelectableCell(oEvent.target);
227
+ if (!oSelectableCell) {
228
+ return;
229
+ }
229
230
 
230
- var sKeyCode = bIsPrevious ? KeyCodes.ARROW_UP : KeyCodes.ARROW_DOWN,
231
- iDirection = bIsPrevious ? SELECTION_DIRECTION.PREVIOUS : SELECTION_DIRECTION.NEXT;
231
+ var oInfo = this.getConfig("getCellInfo", this.getControl(), oSelectableCell);
232
+ if (!this._inSelection(oEvent.target) || !this._oSession.mSource || !this._oSession.mTarget) {
233
+ // If not in selection block, start new selection block
234
+ this._oSession.mSource = this._oSession.mTarget = oInfo;
235
+ }
232
236
 
233
- var sType = oEvent.keyCode == sKeyCode ? "row" : "col";
234
- mTo[sType + "Index"] += iDirectionIndex;
235
- oFocusCellInfo[sType + "Index"] += iDirectionIndex;
237
+ var mBounds = this._getNormalizedBounds(this._oSession.mSource, this._oSession.mTarget);
238
+ const { from, to, focus } = this._getUpdatedBounds(iRowDiff, iColDiff * this._iRtl, oInfo);
236
239
 
237
- if (!this.getConfig("isNavigatableCell", this.getControl(), mTo)) {
240
+ if (focus[sDirectionType + "Index"] < 0 || focus.colIndex >= this.getConfig("getVisibleColumns", this.getControl()).length) {
238
241
  return;
239
242
  }
240
243
 
241
- this._selectCells(mFrom, mTo, {info: {focus: oFocusCellInfo, direction: iDirection}});
242
- oEvent.preventDefault();
243
- oEvent.setMarked();
244
+ this.getConfig("focusCell", this.getControl(), focus, iRowDiff > 0);
245
+ if (sDirectionType == DIRECTION.ROW && (oInfo.rowIndex == mBounds.from.rowIndex || oInfo.rowIndex == mBounds.to.rowIndex)
246
+ || sDirectionType == DIRECTION.COL && (oInfo.colIndex == mBounds.from.colIndex || oInfo.colIndex == mBounds.to.colIndex)) {
247
+ this._bSelecting = true;
248
+ this._selectCells(from, to);
249
+
250
+ oEvent.preventDefault();
251
+ oEvent.setMarked();
252
+ oEvent.setMarked("sapUiTableSkipItemNavigation", true); // Required to prevent item navigation in GridTable for MultiToggle
253
+ }
244
254
  };
245
255
 
246
- CellSelector.prototype.onsapspacemodifiers = function (oEvent) {
256
+ // To be implemented. See internal documentation.
257
+ CellSelector.prototype.onsaphomemodifiers = function (oEvent) {};
258
+
259
+ // To be implemented. See internal documentation.
260
+ CellSelector.prototype.onsapendmodifiers = function (oEvent) {};
261
+
262
+ /**
263
+ * Handles:
264
+ * - CTRL + SHIFT + A
265
+ * - CTRL + A
266
+ * @param {sap.ui.base.Event} oEvent event instance
267
+ */
268
+ CellSelector.prototype.onkeydown = function (oEvent) {
247
269
  if (!this._bSelecting || oEvent.isMarked()) {
248
270
  return;
249
271
  }
250
272
 
251
- var mTo = Object.assign({}, this._oSession.mTarget);
252
- var oFocusCellInfo = this.getConfig("getCellInfo", this.getControl(), oEvent.target);
253
-
254
- if (oEvent.shiftKey) {
255
- // Select rows, if single row selection, only select focused row
256
- this._oSession.mSource.colIndex = -Infinity;
257
- mTo.colIndex = Infinity;
258
- this._selectCells(this._oSession.mSource, mTo, {info: {focus: oFocusCellInfo, boundaryChange: true}});
259
- } else if (oEvent.ctrlKey || oEvent.metaKey) {
260
- // Select columns
261
- this._oSession.mSource.rowIndex = -Infinity;
262
- mTo.rowIndex = Infinity;
263
- this._selectCells(this._oSession.mSource, mTo, {info: {focus: oFocusCellInfo, boundaryChange: true}});
264
- }
265
- oEvent.preventDefault();
266
- oEvent.setMarked();
267
- };
268
-
269
- CellSelector.prototype.onsaphomemodifiers = function (oEvent) {
270
- if (!this._bSelecting || oEvent.isMarked() || !oEvent.shiftKey || !this._isInSelectionArea(oEvent.target)) {
271
- return;
273
+ if (isKeyCombination(oEvent, KeyCodes.A, true, true) || isKeyCombination(oEvent, KeyCodes.A, false, false)) {
274
+ this.removeSelection();
272
275
  }
273
276
 
274
- var mTo = Object.assign({}, this._oSession.mTarget);
275
- mTo.colIndex = -Infinity;
276
- this._selectCells(this._oSession.mSource, mTo, {info: {focus: mTo, boundaryChange: true}});
277
- oEvent.setMarked();
277
+ oEvent.preventDefault();
278
278
  };
279
279
 
280
- CellSelector.prototype.onsapendmodifiers = function (oEvent) {
281
- if (!this._bSelecting || oEvent.isMarked() || !oEvent.shiftKey || !this._isInSelectionArea(oEvent.target)) {
280
+ /**
281
+ * Handles:
282
+ * - SPACE + SHIFT
283
+ * - SPACE + CTRL/CMD
284
+ * @param {sap.ui.base.Event} oEvent event instance
285
+ */
286
+ CellSelector.prototype.onkeyup = function(oEvent) {
287
+ if (oEvent.isMarked()) {
282
288
  return;
283
289
  }
284
290
 
285
- var mTo = Object.assign({}, this._oSession.mTarget);
286
- mTo.colIndex = Infinity;
287
- this._selectCells(this._oSession.mSource, mTo, {info: {focus: mTo, boundaryChange: true}});
288
- oEvent.setMarked();
289
- };
290
-
291
- CellSelector.prototype.onkeydown = function (oEvent) {
292
- if (this._bSelecting) {
293
- // CTRL+SHIFT+A: Clear Selection
294
- if (isKeyCombination(oEvent, KeyCodes.A, true, true)) {
295
- this.clearSelection();
296
- oEvent.preventDefault();
291
+ var mBounds = this._bSelecting ? this._getNormalizedBounds(this._oSession.mSource, this._oSession.mTarget) : undefined;
292
+ if (isKeyCombination(oEvent, KeyCodes.SPACE, true, false)) {
293
+ if (this._inSelection(oEvent.target)) {
294
+ var oInfo = this.getConfig("getCellInfo", this.getControl(), oEvent.target);
295
+ this.getConfig("selectRows", this.getControl(), mBounds.from.rowIndex, mBounds.to.rowIndex, oInfo.rowIndex) && this.removeSelection();
297
296
  oEvent.setMarked();
298
297
  }
298
+ } else if (this._bSelecting && isKeyCombination(oEvent, KeyCodes.SPACE, false, true)) {
299
+ if (!this._inSelection(oEvent.target)) {
300
+ // If focus is on cell outside of selection, select focused column
301
+ var oInfo = this.getConfig("getCellInfo", this.getControl(), oEvent.target);
302
+ mBounds.from.colIndex = mBounds.to.colIndex = oInfo.colIndex;
303
+ }
304
+ mBounds.from.rowIndex = 0;
305
+ mBounds.to.rowIndex = Infinity;
306
+ this._selectCells(mBounds.from, mBounds.to);
299
307
  }
308
+
309
+ oEvent.preventDefault();
300
310
  };
301
311
 
302
312
  // Mouse Navigation
303
313
 
304
- CellSelector.prototype.ontouchstart = function (oEvent) {
305
- var oCellRef = this._getSelectableCell(oEvent.target);
306
- if (oEvent.isMarked() || !oCellRef) {
307
- return;
308
- } else if (!this.getConfig("isSelectionEnabled", this.getControl())) {
309
- Log.error("Cell selection is inactive, because preconditions are not met.");
314
+ CellSelector.prototype.onmousedown = function(oEvent) {
315
+ if (oEvent.isMarked && oEvent.isMarked()) {
310
316
  return;
311
317
  }
312
318
 
313
- var oCellInfo = this.getConfig("getCellInfo", this.getControl(), oCellRef);
314
-
315
- if (oCellInfo) {
316
- this._bSelecting = true;
317
- this._bMouseDown = true;
318
- this._bByEdge = false;
319
- if (this._oSession.mSource) {
320
- if (this._oSession.mSource.rowIndex !== oCellInfo.rowIndex || this._oSession.mSource.colIndex !== oCellInfo.colIndex) {
321
- this._oSession.mSource = null;
322
- this._oSession.mTarget = null;
323
- }
324
- }
319
+ if (oEvent.ctrlKey || oEvent.metaKey) {
320
+ this._startSelection(oEvent);
321
+ }
325
322
 
326
- this._oSession.mSource = oCellInfo;
327
- this._oSession.mStart = oCellInfo;
328
- this._selectCells(this._oSession.mSource, oCellInfo, {info: {focus: oCellInfo}});
329
- oEvent.preventDefault();
323
+ this._bMouseDown = true;
324
+ var oSelectableCell = this._getSelectableCell(oEvent.target);
325
+ if (oSelectableCell) {
326
+ this._mClickedCell = this.getConfig("getCellInfo", this.getControl(), oSelectableCell);
330
327
  }
331
- oEvent.setMarked();
332
328
  };
333
329
 
334
- CellSelector.prototype.ontouchmove = function (oEvent) {
335
- if (!this._bMouseDown || !this._bSelecting) {
336
- return;
330
+ /**
331
+ * Event handler for mouse movement. Handles mouse movement during cell selection. Takes on tasks like:
332
+ * - updating resizer positions
333
+ * - mouse selection via cell click and move
334
+ * - selection enhancement via border and edge
335
+ * @param {sap.ui.base.Event} oEvent event
336
+ */
337
+ CellSelector.prototype._onmousemove = function(oEvent) {
338
+ // Only update the resizer, if we are selecting and the border is not pressed. During border/edge pressing, don't update it
339
+ if (this._bSelecting && !this._bMouseDown) {
340
+ var mBounds = this._getNormalizedBounds(this._oSession.mSource, this._oSession.mTarget);
341
+ this._updateResizers(mBounds, oEvent.clientX, oEvent.clientY);
337
342
  }
338
343
 
339
- var oTouchPosition = this._getMousePosition(this.getConfig("scrollContainer"), oEvent.clientX, oEvent.clientY);
340
- if (oTouchPosition.x == MOUSE_POSITION.IN && oTouchPosition.y == MOUSE_POSITION.IN) {
341
- this._bScrollSelecting = false;
344
+ var oSelectableCell = this._getSelectableCell(oEvent.target);
345
+ if (!oSelectableCell || !this._bMouseDown) {
346
+ return;
342
347
  }
343
348
 
344
- var oTargetRef = this._getSelectableCell(oEvent.target);
345
- if (!oTargetRef) {
349
+ // If clicked cell (=starting cell) is equal to currently hovered cell, don't do anything
350
+ var oInfo = this.getConfig("getCellInfo", this.getControl(), oSelectableCell);
351
+ if (this._mClickedCell
352
+ && oInfo.rowIndex == this._mClickedCell.rowIndex
353
+ && oInfo.colIndex == this._mClickedCell.colIndex) {
346
354
  return;
347
355
  }
348
356
 
349
- var oTargetInfo = this.getConfig("getCellInfo", this.getControl(), oTargetRef);
350
- if (oTargetInfo) {
351
- if (oTargetInfo.rowIndex == this._oSession.mTarget.rowIndex && oTargetInfo.colIndex == this._oSession.mTarget.colIndex) {
352
- // if current mouse position is equal to current saved target position, no change is needed
353
- return;
354
- }
357
+ // Remove text selection during mouse cell selection
358
+ window.getSelection().removeAllRanges();
355
359
 
356
- var oBounds = getNormalizedBounds(this._oSession.mSource, this._oSession.mTarget);
357
-
358
- if (this._oEdgeInfo && this._oEdgeInfo.isActive && this._oEdgeInfo.moveStart) {
359
- this._oEdgeInfo.moveStart = false;
360
-
361
- // Move Start position to opposite edge to ensure correct enlarging/decreasing of selection area
362
- if (this._oEdgeInfo.edgePosition === "NE") {
363
- this._oSession.mStart.rowIndex = oBounds.to.rowIndex;
364
- this._oSession.mStart.colIndex = oBounds.from.colIndex;
365
- } else if (this._oEdgeInfo.edgePosition === "SE") {
366
- this._oSession.mStart = oBounds.from;
367
- } else if (this._oEdgeInfo.edgePosition === "SW") {
368
- this._oSession.mStart.rowIndex = oBounds.from.rowIndex;
369
- this._oSession.mStart.colIndex = oBounds.to.colIndex;
370
- } else if (this._oEdgeInfo.edgePosition === "NW") {
371
- this._oSession.mStart = oBounds.to;
372
- }
373
- } else if (this._oBorderMoveInfo && this._oBorderMoveInfo.isActive) {
374
- // Move Start position to opposite border to ensure correct enlarging/decreasing of selection area
375
- var sDirection = this._oBorderMoveInfo.direction, bMoveStart = this._oBorderMoveInfo.moveStart;
376
- if (sDirection === "N") {
377
- this._oSession.mStart = bMoveStart ? oBounds.to : this._oSession.mStart;
378
- oTargetInfo.colIndex = oBounds.from.colIndex;
379
- } else if (sDirection === "E") {
380
- this._oSession.mStart = bMoveStart ? oBounds.from : this._oSession.mStart;
381
- oTargetInfo.rowIndex = oBounds.to.rowIndex;
382
- } else if (sDirection === "S") {
383
- this._oSession.mStart = bMoveStart ? oBounds.from : this._oSession.mStart;
384
- oTargetInfo.colIndex = oBounds.to.colIndex;
385
- } else if (sDirection === "W") {
386
- this._oSession.mStart = bMoveStart ? oBounds.to : this._oSession.mStart;
387
- oTargetInfo.rowIndex = oBounds.from.rowIndex;
388
- }
389
- this._oBorderMoveInfo.moveStart = false;
360
+ if (this._bBorderDown && !this._bScrolling) {
361
+ var oBorder = this._oSession.border;
362
+ var mDiff = {
363
+ colIndex: isNaN(oBorder.colIndex) ? 0 : oInfo.colIndex - oBorder.colIndex,
364
+ rowIndex: isNaN(oBorder.rowIndex) ? 0 : oInfo.rowIndex - oBorder.rowIndex
365
+ };
366
+
367
+ if (mDiff.rowIndex != 0 || mDiff.colIndex != 0) {
368
+ const { from, to } = this._getUpdatedBounds(mDiff.rowIndex, mDiff.colIndex, oBorder);
369
+
370
+ this._selectCells(from, to);
371
+
372
+ this._oSession.border.rowIndex += mDiff.rowIndex;
373
+ this._oSession.border.colIndex += mDiff.colIndex;
390
374
  }
391
- var mFrom = this._oSession.mStart, mTo = oTargetInfo;
392
- this._selectCells(mFrom, mTo, {info: {focus: oTargetInfo}});
375
+ } else {
376
+ this._startSelection(oEvent, true);
393
377
  }
394
378
  };
395
379
 
396
- CellSelector.prototype._onMouseLeave = function (oEvent) {
397
- if (this._bMouseDown && this._bSelecting) {
398
- this._bScrollSelecting = true;
399
- var oMousePosition = this._getMousePosition(this.getConfig("scrollContainer"), oEvent.clientX, oEvent.clientY);
400
- this._onScrollSelect(oMousePosition);
380
+ /** Event Handler for Mouse Selection (leaving table, etc.) */
381
+ CellSelector.prototype._onmouseout = function(oEvent) {
382
+ var oScrollAreaRef = this.getControl().getDomRef(this.getConfig("scrollArea"));
383
+
384
+ if (!oScrollAreaRef || !this._bMouseDown) { return; }
385
+
386
+ var oScrollAreaRect = oScrollAreaRef.getBoundingClientRect();
387
+
388
+ var bForward, bVertical;
389
+ this._bScrolling = false;
390
+ if (oEvent.clientY > oScrollAreaRect.bottom || oEvent.clientY < oScrollAreaRect.top) {
391
+ this._oSession.scrollForward = bForward = oEvent.clientY > oScrollAreaRect.bottom;
392
+ this._oSession.isVertical = bVertical = true;
393
+ this._bScrolling = true;
394
+ }
395
+
396
+ if (oEvent.clientX > oScrollAreaRect.right || oEvent.clientX < oScrollAreaRect.left) {
397
+ this._oSession.scrollForward = bForward = oEvent.clientX > oScrollAreaRect.right;
398
+ this._oSession.isVertical = bVertical = false;
399
+ this._bScrolling = true;
400
+ }
401
+
402
+ if (this._bScrolling) {
403
+ this._doScroll(bForward, bVertical, oEvent);
401
404
  }
402
405
  };
403
406
 
404
- /**
405
- * Event handler for scroll selection. If the mouse is outside of the table while selecting cells, the table will be scrolled accordingly.
406
- *
407
- * Returns a promise, which will resolve if selection is stopped or the control has been destroyed.
408
- * @param {object} oMousePosition mouse position information
409
- * @param {MOUSE_POSITION} oMousePosition.x x position
410
- * @param {MOUSE_POSITION} oMousePosition.y y position
411
- * @returns {Promise} event promise
412
- */
413
- CellSelector.prototype._onScrollSelect = function (oMousePosition) {
414
- // recursively calls _onScrollSelect every 100ms, as long as scroll selecting is active
415
- return new Promise(function (resolve, reject) {
416
- if (!this._bScrollSelecting) {
417
- resolve();
418
- return;
419
- }
420
- setTimeout(function () {
421
- if (!this.getControl()) {
422
- // If during the asynchronous process, the control is somehow destroyed, simply resolve and return
423
- resolve();
424
- return;
425
- }
426
- var oContainerRef = this.getControl().getDomRef(this.getConfig("container"));
427
- if (oMousePosition.x === MOUSE_POSITION.LEFT) {
428
- if (this._oSession.mSource.colIndex < this._oSession.mTarget.colIndex && this._oSession.mSource.colIndex > 0) {
429
- this._oSession.mSource.colIndex--;
430
- } else if (this._oSession.mTarget.colIndex > 0) {
431
- this._oSession.mTarget.colIndex--;
432
- }
433
- oContainerRef.dispatchEvent(new WheelEvent("wheel", {deltaX: -1, deltaMode: window.WheelEvent.DOM_DELTA_LINE}));
434
- this._selectCells(this._oSession.mSource, this._oSession.mTarget);
435
- } else if (oMousePosition.x === MOUSE_POSITION.RIGHT) {
436
- this._oSession.mTarget.colIndex++;
437
- oContainerRef.dispatchEvent(new WheelEvent("wheel", {deltaX: 1, deltaMode: window.WheelEvent.DOM_DELTA_LINE}));
438
- this._selectCells(this._oSession.mSource, this._oSession.mTarget);
439
- }
440
- if (oMousePosition.y === MOUSE_POSITION.ABOVE) {
441
- if (this._oSession.mSource.rowIndex < this._oSession.mTarget.rowIndex && this._oSession.mSource.rowIndex > 0) {
442
- this._oSession.mSource.rowIndex--;
443
- } else if (this._oSession.mTarget.rowIndex > 0) {
444
- this._oSession.mTarget.rowIndex--;
445
- }
446
- oContainerRef.dispatchEvent(new WheelEvent("wheel", {deltaY: -1, deltaMode: window.WheelEvent.DOM_DELTA_LINE}));
447
- } else if (oMousePosition.y === MOUSE_POSITION.BELOW) {
448
- this._oSession.mTarget.rowIndex++;
449
- oContainerRef.dispatchEvent(new WheelEvent("wheel", {deltaY: 1, deltaMode: window.WheelEvent.DOM_DELTA_LINE}));
450
- }
451
- resolve();
452
- }.bind(this), 100);
453
- }.bind(this)).then(function () {
454
- if (!this._bScrollSelecting) {
455
- return;
407
+ CellSelector.prototype._onmouseenter = function(oEvent) {
408
+ this._bScrolling = false;
409
+ this._clearScroller();
410
+ };
411
+
412
+ CellSelector.prototype._doScroll = function(bForward, bVertical, oEvent) {
413
+ this._clearScroller();
414
+ if (this._bScrolling) {
415
+ this.getConfig("scroll", this.getControl(), bForward, bVertical);
416
+ this._mTimeouts.scrollTimerId = setTimeout(this._doScroll.bind(this, bForward, bVertical), 500);
417
+
418
+ // If vertical scrolling, wait for the event, then select the next cells, not possible currently with horizontal scrolling
419
+ if (!bVertical) {
420
+ this._scrollSelect(bForward, bVertical, oEvent);
456
421
  }
457
- this._onScrollSelect(oMousePosition);
458
- }.bind(this));
422
+ }
459
423
  };
460
424
 
461
- /**
462
- * Event handler for mouse movement with border or edge handles while selecting cells. Sets the according selection flags, if a selection is active.
463
- * @param {String} sFacing direction of movement
464
- * @param {boolean} bBorder is the movement by border dragging
465
- * @private
466
- */
467
- CellSelector.prototype._onHandleMove = function (sFacing, bBorder) {
468
- if (this._oBorderMoveInfo && this._oBorderMoveInfo.isActive) {
425
+ CellSelector.prototype._scrollSelect = function(bForward, bVertical, oEvent) {
426
+ if (!this._bSelecting) {
469
427
  return;
470
428
  }
471
- this._bSelecting = true;
472
- this._bMouseDown = true;
473
- if (bBorder) {
474
- this._oBorderMoveInfo = {isActive: true, direction: sFacing, moveStart: true};
475
- } else {
476
- this._oEdgeInfo = {isActive: true, moveStart: true, edgePosition: sFacing};
429
+ var mBounds = this._getNormalizedBounds(this._oSession.mSource, this._oSession.mTarget);
430
+ if (this._bScrolling) {
431
+ var sDirectionType = bVertical ? DIRECTION.ROW : DIRECTION.COL;
432
+ var mDiff = { "row": 0, "col": 0 };
433
+ var sType = bForward ? "to" : "from";
434
+
435
+ mDiff[sDirectionType] = bForward ? 1 : -1;
436
+ const { from, to } = this._getUpdatedBounds(mDiff[DIRECTION.ROW], mDiff[DIRECTION.COL], mBounds[sType]);
437
+ this._selectCells(from, to);
477
438
  }
478
439
  };
479
440
 
480
- /**
481
- * Event handler for mouseup. Stops the cell selection and sets the necessary flags accordingly.
482
- * @param {sap.ui.base.Event} oEvent event object
483
- * @private
484
- */
485
- CellSelector.prototype._onmouseup = function (oEvent) {
441
+ CellSelector.prototype._clearScroller = function() {
442
+ if (this._mTimeouts.scrollTimerId) {
443
+ window.clearTimeout(this._mTimeouts.scrollTimerId);
444
+ this._mTimeouts.scrollTimerId = null;
445
+ }
446
+ };
447
+
448
+ CellSelector.prototype.onmouseup = function(oEvent) {
486
449
  this._bMouseDown = false;
487
- this._oEdgeInfo = null;
488
- this._oBorderMoveInfo = null;
489
- this._bScrollSelecting = false;
450
+ this._bBorderDown = false;
451
+ this._mClickedCell = undefined;
452
+ this._bScrolling = false;
453
+ this._clearScroller();
454
+ };
455
+
456
+ CellSelector.prototype._onborderdown = function(oEvent) {
457
+ this._oSession.border = Object.assign({}, this._oCurrentBorder);
458
+ this._bBorderDown = true;
459
+ this._bMouseDown = true;
460
+ // TODO: when borderdown, make "border" active
490
461
  };
491
462
 
492
463
  /**
@@ -498,29 +469,69 @@ sap.ui.define([
498
469
  return oDomRef && oDomRef.closest(this.getConfig("selectableCells"));
499
470
  };
500
471
 
472
+ CellSelector.prototype._inSelection = function(oTarget) {
473
+ var oInfo = this.getConfig("getCellInfo", this.getControl(), oTarget);
474
+ if (!oInfo || !this._oSession.mSource || !this._oSession.mTarget) {
475
+ return false;
476
+ }
477
+
478
+ var oBounds = this._getNormalizedBounds(this._oSession.mSource, this._oSession.mTarget);
479
+
480
+ return !(oInfo.rowIndex < oBounds.from.rowIndex || oInfo.rowIndex > oBounds.to.rowIndex
481
+ || oInfo.colIndex < oBounds.from.colIndex || oInfo.colIndex > oBounds.to.colIndex);
482
+ };
483
+
484
+ CellSelector.prototype._startSelection = function(oEvent, bMove) {
485
+ if (oEvent.isMarked && oEvent.isMarked()) {
486
+ return;
487
+ }
488
+
489
+ var oTarget = this._getSelectableCell(oEvent.target);
490
+ if (!oTarget) {
491
+ return;
492
+ }
493
+
494
+ if (this._inSelection(oTarget) && !bMove) {
495
+ this.removeSelection();
496
+ } else {
497
+ var oCellInfo = this.getConfig("getCellInfo", this.getControl(), oTarget);
498
+ var mStart = this._mClickedCell ? this._mClickedCell : oCellInfo;
499
+
500
+ this._bSelecting = true;
501
+ this._oSession.mSource = oCellInfo;
502
+ this._selectCells(mStart, oCellInfo);
503
+ this.getConfig("focusCell", this.getControl(), oCellInfo);
504
+ }
505
+
506
+ oEvent.preventDefault();
507
+ oEvent.setMarked && oEvent.setMarked();
508
+ };
509
+
501
510
  /**
502
- * Checks if the given target element is in the selection area.
503
- * @param {HTMLElement} oTarget target element
504
- * @returns {boolean} bInArea - true: in selection area, false: not in area
511
+ * Selects the next cells in a specific direction (ROW, COL).
505
512
  * @private
506
513
  */
507
- CellSelector.prototype._isInSelectionArea = function (oTarget) {
508
- var oFocusInfo = this.getConfig("getCellInfo", this.getControl(), oTarget);
509
- var bInArea = false;
510
-
511
- if (oFocusInfo) {
512
- var oNormalizedBounds = getNormalizedBounds(this._oSession.mSource, this._oSession.mTarget);
513
- var aRows = this.getControl().getRows();
514
-
515
- bInArea = !(oFocusInfo.rowIndex < oNormalizedBounds.from.rowIndex
516
- || oFocusInfo.rowIndex > oNormalizedBounds.to.rowIndex
517
- || oFocusInfo.colIndex < oNormalizedBounds.from.colIndex
518
- || oFocusInfo.colIndex > oNormalizedBounds.to.colIndex)
519
- || oFocusInfo.rowIndex == aRows[0].getIndex()
520
- || oFocusInfo.rowIndex == aRows[aRows.length - 1].getIndex();
514
+ CellSelector.prototype._getUpdatedBounds = function(iRowDiff, iColDiff, mOldFocus) {
515
+ var mBounds = this._getNormalizedBounds(this._oSession.mSource, this._oSession.mTarget);
516
+ var mFocus = Object.assign({}, mOldFocus);
517
+
518
+ // Determine which "side" to adjust according to current position
519
+ var sAdjustRowType = mFocus.rowIndex == mBounds.from.rowIndex ? "from" : "to";
520
+ var sAdjustColType = mFocus.colIndex == mBounds.from.colIndex ? "from" : "to";
521
+
522
+ mBounds[sAdjustRowType].rowIndex += iRowDiff;
523
+ mBounds[sAdjustColType].colIndex += iColDiff;
524
+
525
+ if (!this._bBorderDown) {
526
+ mFocus.rowIndex = Math.max(0, mFocus.rowIndex + iRowDiff);
527
+ mFocus.colIndex = Math.max(0, mFocus.colIndex + iColDiff);
521
528
  }
522
529
 
523
- return bInArea;
530
+ return {
531
+ from: mBounds.from,
532
+ to: mBounds.to,
533
+ focus: mFocus
534
+ };
524
535
  };
525
536
 
526
537
  /**
@@ -537,87 +548,27 @@ sap.ui.define([
537
548
  * @param {Object} mTo target cell coordinates
538
549
  * @param {int} mTo.rowIndex row index
539
550
  * @param {int} mTo.colIndex column index
540
- * @param {object} oOptions cell selection options
541
- * @param {object} oOptions.info options info
542
- * @param {object} oOptions.info.focus focus info
543
- * @param {boolean} oOptions.info.boundaryChange change of both both boundaries
544
551
  * @private
545
552
  */
546
- CellSelector.prototype._selectCells = function (mFrom, mTo, oOptions) {
553
+ CellSelector.prototype._selectCells = function (mFrom, mTo, mFocus) {
547
554
  if (!this._bSelecting) {
548
555
  return;
549
556
  }
550
557
 
551
- this._oSession.aCells = [];
552
- this._savePreviousSelectionAreas();
553
- this._eraseSelection();
554
-
555
- if (!this._oSession.mTarget) {
556
- this._oSession.mTarget = mTo;
557
- }
558
- if (!mFrom) {
559
- this._oSession.mSource = mFrom = mTo;
560
- }
561
- if (!oOptions) {
562
- oOptions = {};
563
- }
564
-
565
- var mBounds = getNormalizedBounds(mFrom, mTo);
566
-
567
- // "Select cells" - returns the area to draw on (boundaries), border information for drawing and selected cell information
568
- var oSelection = this.getConfig("selectCells", this.getControl(), mBounds, oOptions);
558
+ this._clearSelection();
569
559
 
570
- var mDrawableBounds = this._getDrawableBounds(mBounds);
571
-
572
- if (!mDrawableBounds.from || !mDrawableBounds.to) {
573
- // If there are no drawable bounds, do not continue.
574
- return;
575
- }
560
+ mFrom = mFrom ? mFrom : this._oSession.mSource;
561
+ mTo = mTo ? mTo : this._oSession.mTarget;
562
+ var mBounds = this._getNormalizedBounds(mFrom, mTo);
576
563
 
577
- if (mBounds.to.rowIndex == Infinity) {
564
+ if (mTo.rowIndex == Infinity || mFrom.rowIndex == Infinity) {
578
565
  this.getConfig("loadContexts", this.getControl(), mBounds.from.rowIndex, this.getRangeLimit());
579
566
  }
580
567
 
581
- var oBorderOptions = this._getBorderOptions(mBounds, mDrawableBounds);
582
- this._oSession.aCells = oSelection.cells;
583
- this._drawSelection(mDrawableBounds, oBorderOptions);
568
+ this._drawSelection(mBounds);
584
569
 
585
- if (!oOptions.info || (oOptions.info && !oOptions.info.boundaryChange)) {
586
- // Set new source and target positions
587
- this._oSession.mSource = mFrom;
588
- this._oSession.mTarget = mTo;
589
- } else {
590
- // If it is something like column, row (begin/end/whole) selection, the source and target positions need to be adjusted to the normalized bounds
591
- this._oSession.mSource = mBounds.from;
592
- this._oSession.mTarget = mBounds.to;
593
- }
594
- };
595
-
596
- CellSelector.prototype._getDrawableBounds = function (mBounds) {
597
- var mDrawableBounds = {from: {}, to: {}};
598
-
599
- var mRange = this.getConfig("getVisibleRange", this.getControl(), mBounds); // from, to
600
-
601
- if (mBounds.to.rowIndex < mRange.from.rowIndex || mBounds.from.rowIndex > mRange.to.rowIndex) {
602
- mDrawableBounds = {};
603
- } else {
604
- mDrawableBounds.from.rowIndex = Math.max(mBounds.from.rowIndex, mRange.from.rowIndex);
605
- mDrawableBounds.from.colIndex = Math.max(mBounds.from.colIndex, mRange.from.colIndex);
606
- mDrawableBounds.to.rowIndex = Math.min(mBounds.to.rowIndex, mRange.to.rowIndex);
607
- mDrawableBounds.to.colIndex = Math.min(mBounds.to.colIndex, mRange.to.colIndex);
608
- }
609
- return mDrawableBounds;
610
- };
611
-
612
- CellSelector.prototype._getBorderOptions = function (mBounds, mDrawableBounds) {
613
- var oBorderOptions = {top: true, bottom: true};
614
- if (mDrawableBounds.from.rowIndex > mBounds.from.rowIndex) {
615
- oBorderOptions.top = false;
616
- }
617
- if (mDrawableBounds.to.rowIndex < mBounds.to.rowIndex) {
618
- oBorderOptions.bottom = false;
619
- }
620
- return oBorderOptions;
570
+ this._oSession.mSource = mFrom;
571
+ this._oSession.mTarget = mTo;
621
572
  };
622
573
 
623
574
  /**
@@ -627,237 +578,136 @@ sap.ui.define([
627
578
  * @param {Object} mBounds.to to position
628
579
  * @private
629
580
  */
630
- CellSelector.prototype._drawSelection = function (mBounds, oOptions) {
581
+ CellSelector.prototype._drawSelection = function (mBounds) {
631
582
  if (!mBounds.from || !mBounds.to) {
632
583
  return;
633
584
  }
634
585
 
635
- var aSelectionAreas = this.getConfig("getSelectionAreas", this.getControl(), mBounds.from, mBounds.to);
636
-
637
- // Iterate through every selection area
638
- aSelectionAreas.forEach(function (oArea, iIndex) {
639
- var oTableDomRef = this.getControl().getDomRef(oArea.container),
640
- oFromDomRef = this.getConfig("getCellRef", this.getControl(), oArea.from),
641
- oToDomRef = this.getConfig("getCellRef", this.getControl(), oArea.to);
642
- var mFromRect, mToRect, oTableRect;
643
- var oStyle = {};
644
-
645
- if (!oFromDomRef || !oToDomRef) {
646
- return;
586
+ this._oSession.cellRefs = [];
587
+ for (var iRow = mBounds.from.rowIndex; iRow <= mBounds.to.rowIndex; iRow++) {
588
+ for (var iCol = mBounds.from.colIndex; iCol <= mBounds.to.colIndex; iCol++) {
589
+ var oCellRef = this.getConfig("getCellRef", this.getControl(), {rowIndex: iRow, colIndex: iCol});
590
+ if (oCellRef) {
591
+ oCellRef.classList.toggle("sapMPluginsCellSelectorTop", iRow == mBounds.from.rowIndex);
592
+ oCellRef.classList.toggle("sapMPluginsCellSelectorBottom", iRow == mBounds.to.rowIndex);
593
+ oCellRef.classList.toggle("sapMPluginsCellSelectorRight", iCol == mBounds.to.colIndex);
594
+ oCellRef.classList.toggle("sapMPluginsCellSelectorSelected", true);
595
+ oCellRef.setAttribute("aria-selected", "true");
596
+ this._oSession.cellRefs.push(oCellRef);
597
+
598
+ // Grid Table has only border-right, so adding border-left would change the size of the column. Instead, for the left border, take the previous cell and set border-right.
599
+ if (iCol == mBounds.from.colIndex) {
600
+ const oPrevCellRef = this.getConfig("getCellRef", this.getControl(), {rowIndex: iRow, colIndex: iCol - 1});
601
+ let sClass = "sapMPluginsCellSelectorLeft";
602
+ if (oPrevCellRef) {
603
+ oCellRef = oPrevCellRef;
604
+ sClass = "sapMPluginsCellSelectorRight";
605
+ this._oSession.cellRefs.push(oCellRef);
606
+ }
607
+ oCellRef.classList.toggle(sClass, iCol == mBounds.from.colIndex);
608
+ }
609
+ }
647
610
  }
611
+ }
612
+ };
648
613
 
649
- mFromRect = oFromDomRef.getBoundingClientRect();
650
- mToRect = oToDomRef.getBoundingClientRect();
651
- oTableRect = oTableDomRef.getBoundingClientRect();
614
+ CellSelector.prototype._updateResizers = function(mBounds, iPositionX, iPositionY) {
615
+ var oResizer = this._getResizer();
652
616
 
653
- // There are instances, where no offset needs to be factored in (e.g. fixed columns).
654
- var mOffsetLeft = oArea.hasOffset ? oTableRect.left : 0;
617
+ var oFromRef = this.getConfig("getCellRef", this.getControl(), mBounds.from, false),
618
+ oToRef = this.getConfig("getCellRef", this.getControl(), mBounds.to, false);
619
+ var mOutOfBounds = { 0: false, 1: false }; // 0: top, 1: bottom
655
620
 
656
- oStyle.left = Math.min(mFromRect.left, mToRect.left) - mOffsetLeft;
657
- oStyle.top = Math.min(mFromRect.top, mToRect.top) - oTableRect.top;
658
- oStyle.width = Math.max(mToRect.right, mFromRect.right) - oStyle.left - mOffsetLeft;
659
- oStyle.height = Math.max(mToRect.bottom, mFromRect.bottom) - oStyle.top - oTableRect.top;
621
+ if (!oFromRef) {
622
+ mOutOfBounds[0] = true;
623
+ oFromRef = this.getConfig("getCellRef", this.getControl(), mBounds.from, true);
624
+ }
660
625
 
661
- oStyle.noBorderTop = !oOptions.top;
662
- oStyle.noBorderBottom = !oOptions.bottom;
626
+ if (!oToRef) {
627
+ mOutOfBounds[1] = true;
628
+ oToRef = this.getConfig("getCellRef", this.getControl(), mBounds.to, true);
629
+ }
663
630
 
664
- // if there are multiple areas omit the left/right border accordingly
665
- oStyle.noBorderRight = aSelectionAreas.length > 1 && iIndex < (aSelectionAreas.length - 1) ? true : false;
666
- oStyle.noBorderLeft = aSelectionAreas.length > 1 && iIndex > 0 ? true : false;
631
+ var oFromRect = oFromRef.getBoundingClientRect(),
632
+ oToRect = oToRef.getBoundingClientRect(),
633
+ oTableRect = this.getControl().getDomRef().getBoundingClientRect();
667
634
 
668
- // Draw selection area
669
- this._drawSelectionArea(oStyle, oArea.container);
635
+ var mStyleMap = {
636
+ x: { 0: oFromRect.left, 1: oToRect.left + oToRect.width },
637
+ y: { 0: oFromRect.top - oTableRect.top, 1: oToRect.top + oToRect.height - oTableRect.top }
638
+ };
639
+ var mDiffMap = {
640
+ x: { 0: iPositionX - oFromRect.left, 1: iPositionX - oToRect.right },
641
+ y: { 0: iPositionY - oFromRect.top, 1: iPositionY - oToRect.bottom }
642
+ };
670
643
 
671
- // Draw Edge Handles
672
- if (!this._oSession.oEdge[oArea.container]) {
673
- this._oSession.oEdge[oArea.container] = {};
674
- }
675
- this._drawEdgeHandle(oStyle, oArea.container, "NE");
676
- this._drawEdgeHandle(oStyle, oArea.container, "SE");
677
- this._drawEdgeHandle(oStyle, oArea.container, "SW");
678
- this._drawEdgeHandle(oStyle, oArea.container, "NW");
679
-
680
- // Draw Border Lines
681
- if (!this._oSession.oBorderLine[oArea.container]) {
682
- this._oSession.oBorderLine[oArea.container] = {};
683
- }
684
- this._drawBorderLine(oStyle, oArea.container, "N");
685
- this._drawBorderLine(oStyle, oArea.container, "E");
686
- this._drawBorderLine(oStyle, oArea.container, "S");
687
- this._drawBorderLine(oStyle, oArea.container, "W");
688
- }.bind(this));
689
- };
644
+ // 2 Bit Flags:
645
+ // Y Direction | X Direction
646
+ // 0 | 0
647
+ var mFlags = 0;
648
+ mFlags |= Math.abs(mDiffMap.x[0]) < Math.abs(mDiffMap.x[1]) ? 0 : 1;
649
+ mFlags |= Math.abs(mDiffMap.y[0]) < Math.abs(mDiffMap.y[1]) ? 0 : 2;
690
650
 
691
- /**
692
- * Draw the selection area for the given style in the given container.
693
- * @param {Object} oTargetStyle object containing style information (left, top, width, height)
694
- * @param {float} oTargetStyle.left left position
695
- * @param {float} oTargetStyle.top top position
696
- * @param {float} oTargetStyle.width width
697
- * @param {float} oTargetStyle.height height
698
- * @param {string} sContainer name of the container
699
- * @private
700
- */
701
- CellSelector.prototype._drawSelectionArea = function (oTargetStyle, sContainer) {
702
- if (!this._oSession.oCanvas[sContainer]) {
703
- this._oSession.oCanvas[sContainer] = document.createElement("div");
704
- this._oSession.oCanvas[sContainer].className = CSS_CLASS + "Canvas";
705
- }
706
- if (!this._oSession.oCanvas[sContainer].isConnected) {
707
- this.getControl().getDomRef(sContainer).append(this._oSession.oCanvas[sContainer]);
651
+ var iDiffX = Math.abs(mDiffMap.x[mFlags & 1]), iDiffY = Math.abs(mDiffMap.y[(mFlags >> 1) & 1]);
652
+ if (iDiffX > 10 && iDiffY > 10 || iDiffX > 10 && mOutOfBounds[(mFlags >> 1) & 1]) {
653
+ return;
708
654
  }
709
655
 
710
- var oStyle = this._oSession.oCanvas[sContainer].style;
711
- oStyle.left = oTargetStyle.left + "px";
712
- oStyle.top = oTargetStyle.top + "px";
713
- oStyle.width = oTargetStyle.width + "px";
714
- oStyle.height = oTargetStyle.height + "px";
715
- oStyle.display = "block";
716
-
717
- oStyle.borderTop = oTargetStyle.noBorderTop ? "0px" : "";
718
- oStyle.borderBottom = oTargetStyle.noBorderBottom ? "0px" : "";
719
- oStyle.borderRight = oTargetStyle.noBorderRight ? "0px" : "";
720
- oStyle.borderLeft = oTargetStyle.noBorderLeft ? "0px" : "";
721
- };
656
+ oResizer.style.left = iDiffX <= 10 ? mStyleMap.x[mFlags & 1] + "px" : mStyleMap.x[0] + "px";
657
+ oResizer.style.top = iDiffY <= 10 ? mStyleMap.y[(mFlags >> 1) & 1] + "px" : mStyleMap.y[0] + "px";
658
+ oResizer.style.width = iDiffX <= 10 ? "" : oToRect.right - oFromRect.left + "px";
659
+ oResizer.style.height = iDiffX <= 10 ? oToRect.bottom - oFromRect.top + "px" : "";
722
660
 
723
- /**
724
- * Draws the edge handles, which can be used to extend the cell selection in any direction.
725
- * @param {object} oTargetStyle object containing style information
726
- * @param {String} sContainer container name
727
- * @param {String} sFacing direction of edge
728
- * @private
729
- */
730
- CellSelector.prototype._drawEdgeHandle = function (oTargetStyle, sContainer, sFacing) {
731
- if (!this._oSession.oEdge[sContainer][sFacing]) {
732
- this._oSession.oEdge[sContainer][sFacing] = {};
661
+ const bXinRange = iDiffX <= 10, bYinRange = iDiffY <= 10;
662
+ oResizer.classList.toggle("sapMPluginsVerticalBorder", bXinRange);
663
+ oResizer.classList.toggle("sapMPluginsHorizontalBorder", bYinRange);
664
+ oResizer.classList.toggle("sapMPluginsEdge", bXinRange && bYinRange);
665
+ oResizer.classList.toggle("sapMPluginsNESW", bXinRange && bYinRange && (mFlags == 2 || mFlags == 1));
666
+ oResizer.classList.toggle("sapMPluginsNWSE", bXinRange && bYinRange && (mFlags == 3 || mFlags == 0));
733
667
 
734
- this._oSession.oEdge[sContainer][sFacing].wrapper = document.createElement("div");
735
- this._oSession.oEdge[sContainer][sFacing].wrapper.className = CSS_CLASS + "EdgeWrapper";
668
+ this._oCurrentBorder = {};
669
+ if (bXinRange) {
670
+ this._oCurrentBorder.colIndex = mFlags & 1 ? mBounds.to.colIndex : mBounds.from.colIndex;
671
+ this._oCurrentBorder.type = DIRECTION.COL;
736
672
  }
737
- if (!this._oSession.oEdge[sContainer][sFacing].wrapper.isConnected) {
738
- this._oSession.oCanvas[sContainer].append(this._oSession.oEdge[sContainer][sFacing].wrapper);
739
- this._oSession.oEdge[sContainer][sFacing].wrapper.addEventListener("mousedown", this._onHandleMove.bind(this, sFacing, false));
740
- }
741
- this._oSession.oEdge[sContainer][sFacing].wrapper.classList.add("sapMPluginsEdge" + sFacing);
742
- };
743
673
 
744
- /**
745
- * Draws a line for the border, which can be dragged to extend selection.
746
- * @param {object} oTargetStyle object containing style information
747
- * @param {String} sContainer container name
748
- * @param {String} sFacing direction of border
749
- * @private
750
- */
751
- CellSelector.prototype._drawBorderLine = function (oTargetStyle, sContainer, sFacing) {
752
- if (!this._oSession.oBorderLine[sContainer][sFacing]) {
753
- this._oSession.oBorderLine[sContainer][sFacing] = document.createElement("div");
754
- this._oSession.oBorderLine[sContainer][sFacing].className = CSS_CLASS + "BorderLine";
674
+ if (bYinRange) {
675
+ this._oCurrentBorder.rowIndex = (mFlags >> 1) & 1 ? mBounds.to.rowIndex : mBounds.from.rowIndex;
676
+ this._oCurrentBorder.type = DIRECTION.ROW;
755
677
  }
756
- if (!this._oSession.oBorderLine[sContainer][sFacing].isConnected) {
757
- this._oSession.oCanvas[sContainer].append(this._oSession.oBorderLine[sContainer][sFacing]);
758
- this._oSession.oBorderLine[sContainer][sFacing].addEventListener("mousedown", this._onHandleMove.bind(this, sFacing, true));
759
- }
760
-
761
- var oStyle = this._oSession.oBorderLine[sContainer][sFacing].style;
762
- this._oSession.oBorderLine[sContainer][sFacing].classList.add("sapMPluginsBorder" + sFacing);
763
- if (sFacing === "N" || sFacing === "S") {
764
- oStyle.width = oTargetStyle.width + "px";
765
- } else {
766
- oStyle.height = oTargetStyle.height + "px";
767
- }
768
- oStyle.display = "block";
769
678
  };
770
679
 
771
- /**
772
- * Clears the currently selected cells.
773
- */
774
- CellSelector.prototype.clearSelection = function () {
775
- this._bSelecting = false;
776
- this._eraseSelection();
777
- this._oSession.mSource = null;
778
- this._oSession.mTarget = null;
779
- };
680
+ CellSelector.prototype._getResizer = function() {
681
+ if (!this._oResizer) {
682
+ this._oResizer = document.createElement("div");
683
+ this._oResizer.setAttribute("id", "cs-rsz");
684
+ this._oResizer.classList.add("sapMPluginsCellSelectorRsz");
780
685
 
781
- /**
782
- * Erases the selection
783
- * @private
784
- */
785
- CellSelector.prototype._eraseSelection = function () {
786
- Object.values(this._oSession.oCanvas).forEach(function (oArea) {
787
- oArea.style = "";
788
- });
789
- Object.values(this._oSession.oBorderLine).forEach(function (oArea) {
790
- Object.values(oArea).forEach(function (oBorder) {
791
- oBorder.style = "";
792
- });
793
- });
794
- Object.values(this._oSession.oEdge).forEach(function (oArea) {
795
- Object.values(oArea).forEach(function (oEdge) {
796
- Object.values(oEdge).forEach(function (oEdgePart) {
797
- oEdgePart.style = "";
798
- });
799
- });
800
- });
801
- };
686
+ this._oResizer.addEventListener("mousedown", this._onborderdown.bind(this));
802
687
 
803
- /**
804
- * A special scroll handler, which handles selection accordingly when the table is scrolling vertically.
805
- * @param {sap.ui.base.Event} oEvent scroll event
806
- * @private
807
- */
808
- CellSelector.prototype._handleScroll = function (oEvent) {
809
- // Rerender selection
810
- if (!this._bSelecting) {
811
- return;
688
+ this.getControl().getDomRef().appendChild(this._oResizer);
812
689
  }
813
- this._selectCells(this._oSession.mSource, this._oSession.mTarget);
690
+ return this._oResizer;
814
691
  };
815
692
 
816
- /**
817
- * Saves all the previous selection areas for later reference and calculation.
818
- * @private
819
- */
820
- CellSelector.prototype._savePreviousSelectionAreas = function () {
821
- Object.entries(this._oSession.oCanvas).forEach(function (aEntries) {
822
- var sContainer = aEntries[0], oArea = aEntries[1];
823
- if (oArea.style.left && oArea.style.top && oArea.style.width && oArea.style.height) {
824
- if (!this._oSession.previousSelection) {
825
- this._oSession.previousSelection = {};
826
- }
827
- this._oSession.previousSelection[sContainer] = {
828
- top: parseFloat(oArea.style.top),
829
- left: parseFloat(oArea.style.left),
830
- width: parseFloat(oArea.style.width),
831
- height: parseFloat(oArea.style.height)
832
- };
833
- }
834
- }.bind(this));
693
+ CellSelector.prototype._clearSelection = function() {
694
+ this._oSession.cellRefs.forEach(function(oCellRef) {
695
+ oCellRef.classList.remove("sapMPluginsCellSelectorSelected", "sapMPluginsCellSelectorTop", "sapMPluginsCellSelectorBottom", "sapMPluginsCellSelectorLeft", "sapMPluginsCellSelectorRight");
696
+ oCellRef.removeAttribute("aria-selected");
697
+ });
698
+ var oResizer = this._getResizer();
699
+ oResizer.style.left = "-10000px";
700
+ oResizer.style.top = "-10000px";
835
701
  };
836
702
 
837
703
  /**
838
- * Retrieves the current mouse position and returns info on whether the mouse is inside the control or not.
839
- * @param {String} sContainer container name
840
- * @param {number} iX x position of mouse
841
- * @param {y} iY y position of mouse
842
- * @returns {object} object containing position information for x, y
704
+ * Remove the current selection block.
843
705
  */
844
- CellSelector.prototype._getMousePosition = function (sContainer, iX, iY) {
845
- var oContainerRef = this.getControl().getDomRef(sContainer);
846
- var oPosition = {x: MOUSE_POSITION.IN, y: MOUSE_POSITION.IN};
847
- if (oContainerRef) {
848
- var oContainerRect = oContainerRef.getBoundingClientRect();
849
- if (iY > oContainerRect.bottom) {
850
- oPosition.y = MOUSE_POSITION.BELOW;
851
- } else if (iY < oContainerRect.top) {
852
- oPosition.y = MOUSE_POSITION.ABOVE;
853
- }
854
- if (iX > oContainerRect.right) {
855
- oPosition.x = MOUSE_POSITION.RIGHT;
856
- } else if (iX < oContainerRect.left) {
857
- oPosition.x = MOUSE_POSITION.LEFT;
858
- }
859
- }
860
- return oPosition;
706
+ CellSelector.prototype.removeSelection = function () {
707
+ this._clearSelection();
708
+
709
+ this._bSelecting = false;
710
+ this._oSession = { cellRefs: [] };
861
711
  };
862
712
 
863
713
  /**
@@ -872,12 +722,23 @@ sap.ui.define([
872
722
  * @param {int} mTo.colIndex column index
873
723
  * @returns object containing coordinates for from and to
874
724
  */
875
- function getNormalizedBounds(mFrom, mTo) {
725
+ CellSelector.prototype._getNormalizedBounds = function(mFrom, mTo, bKeepBounds) {
726
+ const iMaxColumns = this.getConfig("getVisibleColumns", this.getControl()).length;
727
+ const iMaxRows = this.getRangeLimit() == 0 ? this.getConfig("getRowCount", this.getControl()) : this.getRangeLimit();
728
+
729
+ let toRowIndex = Math.max(mFrom.rowIndex, mTo.rowIndex);
730
+ let toColIndex = Math.max(mFrom.colIndex, mTo.colIndex);
731
+
732
+ if (!bKeepBounds) {
733
+ toRowIndex = Math.min(iMaxRows - 1, toRowIndex);
734
+ toColIndex = Math.min(iMaxColumns, toColIndex);
735
+ }
736
+
876
737
  return {
877
- from: {rowIndex: Math.min(mFrom.rowIndex, mTo.rowIndex), colIndex: Math.min(mFrom.colIndex, mTo.colIndex)},
878
- to: {rowIndex: Math.max(mFrom.rowIndex, mTo.rowIndex), colIndex: Math.max(mFrom.colIndex, mTo.colIndex)}
738
+ from: {rowIndex: Math.max(0, Math.min(mFrom.rowIndex, mTo.rowIndex)), colIndex: Math.max(0, Math.min(mFrom.colIndex, mTo.colIndex))},
739
+ to: {rowIndex: toRowIndex, colIndex: toColIndex}
879
740
  };
880
- }
741
+ };
881
742
 
882
743
  /**
883
744
  * Check if the given key combination applies to the event.
@@ -893,33 +754,9 @@ sap.ui.define([
893
754
 
894
755
  PluginBase.setConfigs({
895
756
  "sap.ui.table.Table": {
896
- container: "tableCCnt",
897
- scrollContainer: "sapUiTableCtrlScr",
898
757
  selectableCells: ".sapUiTableDataCell",
899
- scrollEvent: "firstVisibleRowChanged",
900
- onActivate: function (oControl, oPlugin) {
901
- var sEvent = "rowSelectionChange";
902
- var oSelectionPlugin = oControl;
903
- oControl.getPlugins().forEach(function (oPlugin) {
904
- if (oPlugin.isA("sap.ui.table.plugins.SelectionPlugin")) {
905
- sEvent = "selectionChange";
906
- oSelectionPlugin = oPlugin;
907
- }
908
- });
909
- oSelectionPlugin.attachEvent(sEvent, oPlugin.clearSelection, oPlugin);
910
- },
911
- onDeactivate: function (oControl, oPlugin) {
912
- var sEvent = "rowSelectionChange";
913
- var oSelectionPlugin = oControl;
914
- oControl.getPlugins().forEach(function (oPlugin) {
915
- if (oPlugin.isA("sap.ui.table.plugins.SelectionPlugin")) {
916
- sEvent = "selectionChange";
917
- oSelectionPlugin = oPlugin;
918
- return;
919
- }
920
- });
921
- oSelectionPlugin.detachEvent(sEvent, oPlugin.clearSelection, oPlugin);
922
- },
758
+ scrollArea: "sapUiTableCtrlScr",
759
+ scrollEvent: "_rowsUpdated",
923
760
  /**
924
761
  * Get visible columns of the table.
925
762
  * @param {sap.ui.table.Table} oTable table instance
@@ -930,13 +767,8 @@ sap.ui.define([
930
767
  return oColumn.getDomRef();
931
768
  });
932
769
  },
933
- /**
934
- * Checks if the selection is enabled for the control.
935
- * @param {sap.ui.core.Control} oControl control instance
936
- * @returns {boolean} is selection enabled or not
937
- */
938
- isSelectionEnabled: function (oControl) {
939
- return !(oControl.getSelectionBehavior() !== "RowSelector" || oControl.getSelectionMode() == "None");
770
+ getRowCount: function(oTable) {
771
+ return oTable._getTotalRowCount();
940
772
  },
941
773
  /**
942
774
  * Retrieve the cell reference for a given position
@@ -946,14 +778,33 @@ sap.ui.define([
946
778
  * @param {int} mPosition.colIndex column index
947
779
  * @returns {HTMLElement} cell's DOM element
948
780
  */
949
- getCellRef: function (oTable, mPosition) {
950
- var oRow = this._getRowByIndex(oTable, mPosition.rowIndex);
781
+ getCellRef: function (oTable, mPosition, bRange) {
782
+ var aRows = oTable.getRows();
783
+ var oRow = aRows.find(function(oRow) {
784
+ return oRow.getIndex() == mPosition.rowIndex;
785
+ });
951
786
  if (oRow) {
952
787
  var oColumn = this.getVisibleColumns(oTable)[mPosition.colIndex];
953
788
  var oCell = oColumn && oRow.getCells()[mPosition.colIndex];
954
789
  if (oCell) {
955
790
  return oCell.$().closest(this.selectableCells)[0];
956
791
  }
792
+ } else if (bRange) {
793
+ if (aRows[0].getIndex() > mPosition.rowIndex) {
794
+ oRow = aRows[0];
795
+ var oColumn = this.getVisibleColumns(oTable)[mPosition.colIndex];
796
+ var oCell = oColumn && oRow.getCells()[mPosition.colIndex];
797
+ if (oCell) {
798
+ return oCell.$().closest(this.selectableCells)[0];
799
+ }
800
+ } else if (aRows[aRows.length - 1].getIndex() < mPosition.rowIndex) {
801
+ oRow = aRows[aRows.length - 1];
802
+ var oColumn = this.getVisibleColumns(oTable)[mPosition.colIndex];
803
+ var oCell = oColumn && oRow.getCells()[mPosition.colIndex];
804
+ if (oCell) {
805
+ return oCell.$().closest(this.selectableCells)[0];
806
+ }
807
+ }
957
808
  }
958
809
  },
959
810
  /**
@@ -964,113 +815,10 @@ sap.ui.define([
964
815
  */
965
816
  getCellInfo: function (oTable, oTarget) {
966
817
  return {
967
- rowIndex: this.rowIndex(null, oTarget),
968
- colIndex: this.colIndex(oTable, oTarget)
969
- };
970
- },
971
- /**
972
- * Retrieve the visible row range for the given table.
973
- * @param {sap.ui.table.Table} oTable table instance
974
- * @returns {Object} object containing from - to table range
975
- */
976
- getVisibleRange: function (oTable) {
977
- var aRows = oTable.getRows();
978
- return {
979
- from: {rowIndex: aRows[0].getIndex(), colIndex: 0},
980
- to: {rowIndex: aRows[aRows.length - 1].getIndex(), colIndex: this.getVisibleColumns(oTable).length - 1}
818
+ rowIndex: Element.closestTo(oTarget, true).getIndex(),
819
+ colIndex: this.getVisibleColumns(oTable).indexOf(Core.byId(oTarget.getAttribute("data-sap-ui-colid")))
981
820
  };
982
821
  },
983
- /**
984
- * Returns the controls' available selection areas for the given bounds.
985
- *
986
- * Note: The order of the areas is from left to right. Area at index 0 is the leftmost area, etc.
987
- * @param {sap.ui.table.Table} oTable table instance
988
- * @param {Object} mFrom from position
989
- * @param {Object} mTo to position
990
- * @returns {Object[]} array of objects (container, from, to) containing information for each area. It contains the name of the container
991
- * and the area that will be selected in said container.
992
- */
993
- getSelectionAreas: function (oTable, mFrom, mTo) {
994
- // push selection areas from left to right
995
- var aAreas = [], iFixedColumnCount = oTable.getFixedColumnCount();
996
- if (iFixedColumnCount > 0 && (mFrom.colIndex < iFixedColumnCount || mFrom.colIndex === -Infinity)) {
997
- var iToCol = mTo.colIndex === Infinity ? iFixedColumnCount - 1 : Math.min(mTo.colIndex, iFixedColumnCount - 1);
998
- var mFixedFrom = {rowIndex: mFrom.rowIndex, colIndex: mFrom.colIndex},
999
- mFixedTo = {rowIndex: mTo.rowIndex, colIndex: iToCol};
1000
- aAreas.push({container: "sapUiTableCtrlScrFixed", from: mFixedFrom, to: mFixedTo});
1001
- }
1002
- if (mTo.colIndex >= iFixedColumnCount || mTo.colIndex === Infinity) {
1003
- aAreas.push({container: "tableCtrlCnt", from: mFrom, to: mTo, hasOffset: true});
1004
- }
1005
- return aAreas;
1006
- },
1007
- /**
1008
- * Retrieves selected cells and returns their position and the boundaries of the selection area fitted to the table and its border options.
1009
- *
1010
- * Note: As the selection area may vary based on control-specific settings (e.g. SingleSelection), the information is returned as well.
1011
- * @param {sap.ui.table.Table} oTable table instance
1012
- * @param {Object} mSelectionBounds selection options
1013
- * @param {Object} oOptions selection options
1014
- * @returns {Object} oSelection object containg <code>bounds</code> (selection bounds) and <code>cells</code> (selected cell positions)
1015
- * @returns {Object} oSelection.bounds
1016
- * @returns {int[]} oSelection.cells
1017
- */
1018
- selectCells: function (oTable, mSelectionBounds, oOptions) {
1019
- var mBounds = {}, oBorderOptions = {top: true, bottom: true};
1020
- var iBindingLength = oTable.getBinding("rows").getLength();
1021
- mBounds.from = Object.assign({}, mSelectionBounds.from);
1022
- mBounds.to = Object.assign({}, mSelectionBounds.to);
1023
-
1024
- mBounds.from.rowIndex = Math.max(mBounds.from.rowIndex, 0);
1025
- mBounds.from.colIndex = Math.max(mBounds.from.colIndex, 0);
1026
-
1027
- mBounds.to.rowIndex = Math.min(mBounds.to.rowIndex, iBindingLength);
1028
- mBounds.to.colIndex = Math.min(mBounds.to.colIndex, this.getVisibleColumns(oTable).length - 1);
1029
-
1030
- var aCells = [];
1031
-
1032
- // Replace MIN/MAX with according number for focus object
1033
- if (oOptions && oOptions.info) {
1034
- oOptions.info.focus.rowIndex = Math.min(Math.max(oOptions.info.focus.rowIndex, 0), iBindingLength);
1035
- oOptions.info.focus.colIndex = Math.min(Math.max(oOptions.info.focus.colIndex, 0), this.getVisibleColumns(oTable).length - 1);
1036
- this._focusCell(oTable, oOptions.info.focus, oOptions.info.direction);
1037
- }
1038
-
1039
- // If table is in Single Selection Mode, only select the row with focus in it
1040
- if (mBounds.from.colIndex === 0 && mBounds.to.colIndex === (this.getVisibleColumns(oTable).length - 1) && oTable.getSelectionMode() == "Single") {
1041
- mBounds.from.rowIndex = mSelectionBounds.from.rowIndex = oOptions.info.focus.rowIndex;
1042
- mBounds.to.rowIndex = mSelectionBounds.to.rowIndex = oOptions.info.focus.rowIndex;
1043
- }
1044
-
1045
- for (var iRow = mBounds.from.rowIndex; iRow <= mBounds.to.rowIndex; iRow++) {
1046
- var oRow = this._getRowByIndex(oTable, iRow);
1047
- if (oRow) {
1048
- for (var iCol = mBounds.from.colIndex; iCol <= mBounds.to.colIndex; iCol++) {
1049
- aCells.push([iRow, iCol]);
1050
- }
1051
- }
1052
- }
1053
-
1054
- return {borderOptions: oBorderOptions, cells: aCells};
1055
- },
1056
- /**
1057
- * Retrieves the row index for the given cell's DOM reference.
1058
- * @param {sap.ui.table.Table} oTable table instance
1059
- * @param {HTMLElement} oCellDomRef DOM reference of cell
1060
- * @returns {int} row index
1061
- */
1062
- rowIndex: function (oTable, oCellDomRef) {
1063
- return Element.closestTo(oCellDomRef, true).getIndex();
1064
- },
1065
- /**
1066
- * Retrieves the column index for the given cell's DOM reference.
1067
- * @param {sap.ui.table.Table} oTable table instance
1068
- * @param {HTMLElement} oCellDomRef DOM reference of cell
1069
- * @returns {int} column index
1070
- */
1071
- colIndex: function (oTable, oCellDomRef) {
1072
- return this.getVisibleColumns(oTable).indexOf(Core.byId(oCellDomRef.getAttribute("data-sap-ui-colid")));
1073
- },
1074
822
  /**
1075
823
  * Loads contexts according to the provided parameters without changing the binding's state.
1076
824
  *
@@ -1106,74 +854,61 @@ sap.ui.define([
1106
854
  }
1107
855
  return aContexts;
1108
856
  },
1109
- columnByIndex: function(oTable, iColIndex) {
1110
- var oColumn = this.getVisibleColumns(oTable)[iColIndex];
1111
- if (!oColumn.getVisible()) {
1112
- return;
1113
- }
1114
- return oColumn;
1115
- },
1116
- isNavigatableCell: function (oTable, mPosition) {
1117
- if ((mPosition.rowIndex < 0 || mPosition.rowIndex >= oTable.getBinding("rows").getLength()
1118
- || mPosition.colIndex < 0 || mPosition.colIndex >= this.getVisibleColumns(oTable).length)
1119
- && !(mPosition.rowIndex == -Infinity || mPosition.rowIndex == Infinity
1120
- || mPosition.colIndex == -Infinity || mPosition.colIndex == Infinity)) {
1121
- return false;
1122
- }
1123
- return true;
1124
- },
1125
857
  /**
1126
- * Scroll one row up or down based on the given direction.
1127
- * @param {sap.ui.table.Table} oTable table instance
1128
- * @param {int} iDirection scroll direction
1129
- * @param {int} iRow row index
858
+ * Select rows beginning at iFrom to iTo.
859
+ * @param {sap.ui.table.Table} oTable The table instance
860
+ * @param {int} iFrom starting row index
861
+ * @param {int} iTo ending row index
862
+ * @param {int} mFocus focused row index
1130
863
  */
1131
- _scrollRow: function (oTable, iDirection, iRow) {
1132
- var iFirstRow = oTable.getFirstVisibleRow();
1133
- if (iRow >= 0 && iRow < oTable.getBinding("rows").getLength()) {
1134
- if (oTable.getFixedRowCount() > 0 && iRow == oTable.getFixedRowCount()) {
1135
- oTable.setFirstVisibleRow(0);
1136
- } else {
1137
- iDirection == SELECTION_DIRECTION.NEXT ? iFirstRow++ : iFirstRow--;
1138
- iFirstRow = iFirstRow < 0 ? 0 : iFirstRow;
1139
- oTable.setFirstVisibleRow(iFirstRow);
1140
- }
864
+ selectRows: function(oTable, iFrom, iTo, iFocus) {
865
+ var oSelectionOwner = PluginBase.getPlugin(oTable, "sap.ui.table.plugins.SelectionPlugin") || oTable;
866
+ var sSelectionMode = oTable.getSelectionMode();
867
+
868
+ if (sSelectionMode == "None") {
869
+ return false;
870
+ } else if (sSelectionMode == "Single") {
871
+ iFrom = iTo = iFocus;
872
+ }
873
+
874
+ if (oSelectionOwner.addSelectionInterval) {
875
+ oSelectionOwner.addSelectionInterval(iFrom, iTo);
876
+ return true;
1141
877
  }
1142
- },
1143
- /**
1144
- * Focus the specified cell and scroll if necessary.
1145
- * @param {sap.ui.table.Table} oTable table instance
1146
- * @param {Object} mPosition position object
1147
- * @param {int} mPosition.rowIndex row index
1148
- * @param {int} mPosition.colIndex column index
1149
- * @param {int} iDirection scroll direction
1150
- */
1151
- _focusCell: function (oTable, mPosition, iDirection) {
1152
- var oCellRef = this.getCellRef(oTable, mPosition);
1153
878
 
879
+ // TODO: Handle V4 correctly. Currrently only selects visible rows
880
+ var aRows = oTable.getRows().filter(function(oRow) {
881
+ return oRow.getIndex() >= iFrom && oRow.getIndex() <= iTo;
882
+ });
883
+ aRows.forEach(function(oRow) {
884
+ oSelectionOwner.setSelected(oRow, true);
885
+ });
886
+ return true;
887
+ },
888
+ focusCell: function(oTable, mFocus, bForward) {
889
+ var oCellRef = this.getCellRef(oTable, mFocus);
1154
890
  if (!oCellRef) {
1155
- this._scrollRow(oTable, iDirection, mPosition.rowIndex);
1156
- oCellRef = this.getCellRef(oTable, mPosition);
1157
- if (!oCellRef) {
1158
- oTable.setFirstVisibleRow(mPosition.rowIndex);
1159
- oCellRef = this.getCellRef(oTable, mPosition);
1160
- }
891
+ this.scroll(oTable, bForward, true);
892
+ return;
1161
893
  }
1162
- oCellRef && oCellRef.focus();
894
+ oCellRef.focus();
1163
895
  },
1164
- /**
1165
- * Retrieve a row by its index.
1166
- * @param {sap.ui.table.Table} oTable table instance
1167
- * @param {int} iRowIndex row index
1168
- * @returns {sap.ui.table.Row|null} row instance
1169
- */
1170
- _getRowByIndex: function (oTable, iRowIndex) {
1171
- var aItems = oTable.getRows();
1172
- for (var i = 0; i < aItems.length; i++) {
1173
- if (aItems[i].getIndex() == iRowIndex) {
1174
- return aItems[i];
896
+ scroll: function(oTable, bForward, bVertical) {
897
+ if (bVertical) {
898
+ var iFirstVisibleRowIndex = oTable.getFirstVisibleRow();
899
+ var iIndex = bForward ? iFirstVisibleRowIndex + 1 : iFirstVisibleRowIndex - 1;
900
+ if (iIndex >= 0 && iIndex != iFirstVisibleRowIndex) {
901
+ oTable.setFirstVisibleRow(iIndex);
902
+ return Promise.resolve();
1175
903
  }
904
+ } else {
905
+ var oScrollBar = oTable._getScrollExtension().getHorizontalScrollbar();
906
+ var iScrollDiff = Math.pow(-1, +!bForward) * 10;
907
+
908
+ oScrollBar.scrollLeft = Math.max(0, oScrollBar.scrollLeft + iScrollDiff);
909
+ return Promise.resolve();
1176
910
  }
911
+ return false;
1177
912
  }
1178
913
  }
1179
914
  }, CellSelector);