bm-core-ui 2.7.0 → 2.8.3
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.
- package/CHANGELOG.md +147 -0
- package/build/@types/index.d.ts +672 -92
- package/build/BMCodeEditor/BMCodeEditor.js +24 -27
- package/build/BMCollectionView/BMCollectionView.js +404 -55
- package/build/BMCollectionView/BMCollectionViewFlowLayout.js +423 -33
- package/build/BMCollectionView/BMCollectionViewLayout.js +158 -0
- package/build/BMCollectionView/BMCollectionViewMasonryLayout.js +145 -5
- package/build/BMCollectionView/BMCollectionViewTileLayout.js +147 -2
- package/build/BMCoreUI.css +60 -10
- package/build/BMView/BMMenu.js +155 -8
- package/build/BMView/BMTextField.js +25 -14
- package/build/BMView/BMView_v2.5.js +205 -3
- package/build/BMViewLayoutEditor/BMLayoutEditor.js +188 -168
- package/build/BMViewLayoutEditor/BMLayoutEditorSettingCells.js +2 -2
- package/build/BMWindow/BMConfirmationPopup.js +15 -0
- package/build/BMWindow/BMKeyboardShortcut.js +122 -3
- package/build/BMWindow/BMWindow.js +25 -90
- package/build/Core/BMAnimationContext.js +0 -4
- package/build/Core/BMCoreUI.js +9 -1
- package/lib/@types/BMCoreUI.min.d.ts +672 -92
- package/lib/BMCoreUI.min.js +1 -1
- package/package.json +1 -1
|
@@ -152,6 +152,164 @@ BMCollectionViewLayout.prototype = {
|
|
|
152
152
|
this._copy = undefined;
|
|
153
153
|
},
|
|
154
154
|
|
|
155
|
+
|
|
156
|
+
/************************************* CELL HIGHLIGHTING ********************************/
|
|
157
|
+
|
|
158
|
+
/**
|
|
159
|
+
* Invoked by the collection view to obtain the first index path in the layout.
|
|
160
|
+
* The default implementation returns the first index path in the data set.
|
|
161
|
+
* @returns <BMIndexPath, nullable> The first index path, or `undefined` if no index path exists.
|
|
162
|
+
*/
|
|
163
|
+
firstIndexPath() {
|
|
164
|
+
const sectionCount = this.collectionView.numberOfSections();
|
|
165
|
+
|
|
166
|
+
for (let i = 0; i < sectionCount; i++) {
|
|
167
|
+
const rowCount = this.collectionView.numberOfObjectsInSectionAtIndex(i);
|
|
168
|
+
|
|
169
|
+
if (rowCount) return this.collectionView.indexPathForObjectAtRow(0, {inSectionAtIndex: i});
|
|
170
|
+
}
|
|
171
|
+
},
|
|
172
|
+
|
|
173
|
+
/**
|
|
174
|
+
* Invoked by the collection to obtain the index path that is visually to the left of the given index path.
|
|
175
|
+
*
|
|
176
|
+
* Subclasses may override this method to return an appropriate index path.
|
|
177
|
+
* If the given index path is at the left edge of the content area, the same index path should be returned.
|
|
178
|
+
*
|
|
179
|
+
* The default implementation returns the previous index path in the data set.
|
|
180
|
+
* @param indexPath <BMIndexPath> The starting index path.
|
|
181
|
+
* @returns <BMIndexPath> The index path to the left of the starting index path.
|
|
182
|
+
*/
|
|
183
|
+
indexPathToTheLeftOfIndexPath(indexPath) {
|
|
184
|
+
if (indexPath.row > 0) {
|
|
185
|
+
return this.collectionView.indexPathForObjectAtRow(indexPath.row - 1, {inSectionAtIndex: indexPath.section});
|
|
186
|
+
}
|
|
187
|
+
|
|
188
|
+
if (indexPath.section > 0) {
|
|
189
|
+
let previousSection = indexPath.section - 1;
|
|
190
|
+
do {
|
|
191
|
+
const rowCount = this.collectionView.numberOfObjectsInSectionAtIndex(previousSection);
|
|
192
|
+
if (rowCount) {
|
|
193
|
+
return this.collectionView.indexPathForObjectAtRow(rowCount - 1, {inSectionAtIndex: previousSection});
|
|
194
|
+
}
|
|
195
|
+
else {
|
|
196
|
+
previousSection = previousSection - 1;
|
|
197
|
+
}
|
|
198
|
+
} while (previousSection >= 0);
|
|
199
|
+
}
|
|
200
|
+
|
|
201
|
+
return indexPath;
|
|
202
|
+
},
|
|
203
|
+
|
|
204
|
+
/**
|
|
205
|
+
* Invoked by the collection to obtain the index path that is visually on top of the given index path.
|
|
206
|
+
*
|
|
207
|
+
* Subclasses may override this method to return an appropriate index path.
|
|
208
|
+
* If the given index path is at the top edge of the content area, the same index path should be returned.
|
|
209
|
+
*
|
|
210
|
+
* The default implementation returns the result of calling `indexPathToTheLeftOfIndexPath`.
|
|
211
|
+
* @param indexPath <BMIndexPath> The starting index path.
|
|
212
|
+
* @returns <BMIndexPath> The index path above the starting index path.
|
|
213
|
+
*/
|
|
214
|
+
indexPathAboveIndexPath(indexPath) {
|
|
215
|
+
return this.indexPathToTheLeftOfIndexPath(indexPath);
|
|
216
|
+
},
|
|
217
|
+
|
|
218
|
+
/**
|
|
219
|
+
* Invoked by the collection to obtain the index path that is visually to the right of the given index path.
|
|
220
|
+
*
|
|
221
|
+
* Subclasses may override this method to return an appropriate index path.
|
|
222
|
+
* If the given index path is at the right edge of the content area, the same index path should be returned.
|
|
223
|
+
*
|
|
224
|
+
* The default implementation returns the next index path in the data set.
|
|
225
|
+
* @param indexPath <BMIndexPath> The starting index path.
|
|
226
|
+
* @returns <BMIndexPath> The index path to the right of the starting index path.
|
|
227
|
+
*/
|
|
228
|
+
indexPathToTheRightOfIndexPath(indexPath) {
|
|
229
|
+
const rowCount = this.collectionView.numberOfObjectsInSectionAtIndex(indexPath.section);
|
|
230
|
+
if (indexPath.row < rowCount - 1) {
|
|
231
|
+
return this.collectionView.indexPathForObjectAtRow(indexPath.row + 1, {inSectionAtIndex: indexPath.section});
|
|
232
|
+
}
|
|
233
|
+
|
|
234
|
+
const sectionCount = this.collectionView.numberOfSections();
|
|
235
|
+
if (indexPath.section < sectionCount - 1) {
|
|
236
|
+
let nextSection = indexPath.section + 1;
|
|
237
|
+
do {
|
|
238
|
+
const rowCount = this.collectionView.numberOfObjectsInSectionAtIndex(nextSection);
|
|
239
|
+
if (rowCount) {
|
|
240
|
+
return this.collectionView.indexPathForObjectAtRow(0, {inSectionAtIndex: nextSection});
|
|
241
|
+
}
|
|
242
|
+
else {
|
|
243
|
+
nextSection = nextSection + 1;
|
|
244
|
+
}
|
|
245
|
+
} while (nextSection < sectionCount);
|
|
246
|
+
}
|
|
247
|
+
|
|
248
|
+
return indexPath;
|
|
249
|
+
},
|
|
250
|
+
|
|
251
|
+
/**
|
|
252
|
+
* Invoked by the collection view to obtain the index path that is visually below the given index path.
|
|
253
|
+
*
|
|
254
|
+
* Subclasses may override this method to return an appropriate index path.
|
|
255
|
+
* If the given index path is at the bottom edge of the content area, the same index path should be returned.
|
|
256
|
+
*
|
|
257
|
+
* The default implementation returns the result of calling `indexPathToTheRightOfIndexPath`.
|
|
258
|
+
* @param indexPath <BMIndexPath> The starting index path.
|
|
259
|
+
* @returns <BMIndexPath> The index path below the starting index path.
|
|
260
|
+
*/
|
|
261
|
+
indexPathBelowIndexPath(indexPath) {
|
|
262
|
+
return this.indexPathToTheRightOfIndexPath(indexPath);
|
|
263
|
+
},
|
|
264
|
+
|
|
265
|
+
/**
|
|
266
|
+
* Invoked by the collection view to obtain a list of index paths that are visually between
|
|
267
|
+
* the two given index paths.
|
|
268
|
+
*
|
|
269
|
+
* The default implementation returns a list containing the index paths from the data set that
|
|
270
|
+
* start at the given index path, stopping at the target index path.
|
|
271
|
+
*
|
|
272
|
+
* The starting and ending index paths should be included in the result.
|
|
273
|
+
* @param indexPath <BMIndexPath> The starting index path.
|
|
274
|
+
* {
|
|
275
|
+
* @param toIndexPath <BMIndexPath> The ending index path.
|
|
276
|
+
* }
|
|
277
|
+
* @return <[BMIndexPath]> An array of index paths.
|
|
278
|
+
*/
|
|
279
|
+
indexPathsFromIndexPath(indexPath, {toIndexPath}) {
|
|
280
|
+
const indexPaths = [];
|
|
281
|
+
|
|
282
|
+
// Swap the index paths if the target index path is before the source index path
|
|
283
|
+
if (toIndexPath.section < indexPath.section) {
|
|
284
|
+
const swapIndexPath = toIndexPath;
|
|
285
|
+
toIndexPath = indexPath;
|
|
286
|
+
indexPath = swapIndexPath;
|
|
287
|
+
}
|
|
288
|
+
else if (indexPath.section == toIndexPath.section && toIndexPath.row < indexPath.row) {
|
|
289
|
+
const swapIndexPath = toIndexPath;
|
|
290
|
+
toIndexPath = indexPath;
|
|
291
|
+
indexPath = swapIndexPath;
|
|
292
|
+
}
|
|
293
|
+
|
|
294
|
+
let i = indexPath.row;
|
|
295
|
+
const targetSection = toIndexPath.section;
|
|
296
|
+
|
|
297
|
+
for (let j = indexPath.section; j < targetSection + 1; j++) {
|
|
298
|
+
let rowCount = this.collectionView.numberOfObjectsInSectionAtIndex(j);
|
|
299
|
+
if (j == targetSection) {
|
|
300
|
+
rowCount = toIndexPath.row + 1;
|
|
301
|
+
}
|
|
302
|
+
|
|
303
|
+
for (; i < rowCount; i++) {
|
|
304
|
+
indexPaths.push(this.collectionView.indexPathForObjectAtRow(i, {inSectionAtIndex: j}));
|
|
305
|
+
}
|
|
306
|
+
|
|
307
|
+
i = 0;
|
|
308
|
+
}
|
|
309
|
+
|
|
310
|
+
return indexPaths;
|
|
311
|
+
},
|
|
312
|
+
|
|
155
313
|
/****************************************** UPDATES ***********************************************/
|
|
156
314
|
|
|
157
315
|
/**
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
import {YES, NO, BMExtend} from '../Core/BMCoreUI'
|
|
4
4
|
import {BMSizeMake} from '../Core/BMSize'
|
|
5
5
|
import {BMRectMake} from '../Core/BMRect'
|
|
6
|
-
import {BMCollectionViewLayoutAttributesMakeForCellAtIndexPath} from './BMCollectionViewLayoutAttributes'
|
|
6
|
+
import {BMCollectionViewLayoutAttributesMakeForCellAtIndexPath, BMCollectionViewLayoutAttributesType} from './BMCollectionViewLayoutAttributes'
|
|
7
7
|
import {BMCollectionViewLayout} from './BMCollectionViewLayout'
|
|
8
8
|
|
|
9
9
|
// @type BMCollectionViewMasonryLayout extends BMCollectionViewLayout
|
|
@@ -331,15 +331,29 @@ BMCollectionViewMasonryLayout.prototype = BMExtend({}, BMCollectionViewLayout.pr
|
|
|
331
331
|
|
|
332
332
|
/**
|
|
333
333
|
* Retrieves the cached attributes for the cell at the given index path.
|
|
334
|
+
* @param indexPath <BMIndexPath> The cell's index path.
|
|
335
|
+
* {
|
|
336
|
+
* @param usingCache <Object, nullable> Defaults to this layout's current cache. The cache object to use.
|
|
337
|
+
* }
|
|
338
|
+
* @return <BMCollectionViewLayoutAttributes, nullable> The layout attributes if the index path exists in the data set, `undefined` otherwise.
|
|
339
|
+
*/
|
|
340
|
+
cachedAttributesForCellAtIndexPath: function (indexPath, options) {
|
|
341
|
+
return this._extendedCachedAttributesForCellAtIndexPath(indexPath, options).attribute;
|
|
342
|
+
},
|
|
343
|
+
|
|
344
|
+
/**
|
|
345
|
+
* Retrieves the cached attributes for the cell at the given index path and information about
|
|
346
|
+
* the column it is on.
|
|
334
347
|
* @param indexPath <BMIndexPath> The cell's index path.
|
|
335
348
|
* {
|
|
336
349
|
* @param usingCache <Object, nullable> Defaults to this layout's current cache. The cache object to use.
|
|
337
350
|
* }
|
|
351
|
+
* @return <Object, nullable> An object that describes the requested attributes and its position in the layout.
|
|
338
352
|
*/
|
|
339
|
-
|
|
353
|
+
_extendedCachedAttributesForCellAtIndexPath: function(indexPath, args) {
|
|
340
354
|
var offset = this.collectionView.scrollOffset;
|
|
341
355
|
|
|
342
|
-
var cache = (
|
|
356
|
+
var cache = (args && args.usingCache) || this.cachedLayout;
|
|
343
357
|
|
|
344
358
|
// Find the attributes in each column
|
|
345
359
|
var columns = cache.columns;
|
|
@@ -367,12 +381,15 @@ BMCollectionViewMasonryLayout.prototype = BMExtend({}, BMCollectionViewLayout.pr
|
|
|
367
381
|
attribute.frame.origin.y = (attribute.frame.origin.y + speedAdjustment) | 0;
|
|
368
382
|
attribute.speed = column.speed;
|
|
369
383
|
|
|
370
|
-
return
|
|
384
|
+
return {
|
|
385
|
+
attribute,
|
|
386
|
+
columnIndex: i,
|
|
387
|
+
rowIndex: attributeIndex
|
|
388
|
+
};
|
|
371
389
|
}
|
|
372
390
|
}
|
|
373
391
|
|
|
374
392
|
}
|
|
375
|
-
|
|
376
393
|
},
|
|
377
394
|
|
|
378
395
|
|
|
@@ -460,6 +477,129 @@ BMCollectionViewMasonryLayout.prototype = BMExtend({}, BMCollectionViewLayout.pr
|
|
|
460
477
|
|
|
461
478
|
return attributes;
|
|
462
479
|
},
|
|
480
|
+
|
|
481
|
+
/************************************* CELL HIGHLIGHTING ********************************/
|
|
482
|
+
|
|
483
|
+
// @override - BMCollectionViewLayout
|
|
484
|
+
indexPathToTheLeftOfIndexPath(indexPath) {
|
|
485
|
+
// Create a rect starting at the left edge of the given index path and request attributes in it
|
|
486
|
+
const extendedAttributes = this._extendedCachedAttributesForCellAtIndexPath(indexPath);
|
|
487
|
+
|
|
488
|
+
if (extendedAttributes.columnIndex == 0) return indexPath;
|
|
489
|
+
|
|
490
|
+
const startingAttributes = extendedAttributes.attribute;
|
|
491
|
+
const center = startingAttributes.frame.center.y;
|
|
492
|
+
|
|
493
|
+
const offset = this.collectionView.scrollOffset;
|
|
494
|
+
|
|
495
|
+
const cache = this.cachedLayout;
|
|
496
|
+
|
|
497
|
+
// Find the attributes in previous column with the smallest vertical distance from the starting attributes
|
|
498
|
+
const column = cache.columns[extendedAttributes.columnIndex - 1];
|
|
499
|
+
|
|
500
|
+
// The speedTop is the unscaled top position at which to start retrieving cells.
|
|
501
|
+
var speedTop = offset.y * column.speed;
|
|
502
|
+
|
|
503
|
+
// The speedAdjustment is the amount by which to displace each attribute's Y origin.
|
|
504
|
+
var speedAdjustment = offset.y - speedTop;
|
|
505
|
+
|
|
506
|
+
let minIndex = -1;
|
|
507
|
+
let minDistance = Number.MAX_SAFE_INTEGER;
|
|
508
|
+
for (let i = 0; i < column.attributes.length; i++) {
|
|
509
|
+
const attribute = column.attributes[i];
|
|
510
|
+
const position = attribute.frame.center.y + speedAdjustment | 0;
|
|
511
|
+
|
|
512
|
+
const distance = Math.abs(position - center);
|
|
513
|
+
if (distance < minDistance) {
|
|
514
|
+
minIndex = i;
|
|
515
|
+
minDistance = distance;
|
|
516
|
+
}
|
|
517
|
+
}
|
|
518
|
+
|
|
519
|
+
if (minIndex != -1) {
|
|
520
|
+
return column.attributes[minIndex].indexPath;
|
|
521
|
+
}
|
|
522
|
+
|
|
523
|
+
return indexPath;
|
|
524
|
+
},
|
|
525
|
+
|
|
526
|
+
// @override - BMCollectionViewLayout
|
|
527
|
+
indexPathAboveIndexPath(indexPath) {
|
|
528
|
+
// Return the row above the given index path in the same column
|
|
529
|
+
const extendedAttributes = this._extendedCachedAttributesForCellAtIndexPath(indexPath);
|
|
530
|
+
|
|
531
|
+
if (extendedAttributes.rowIndex > 0) {
|
|
532
|
+
return this.cachedLayout.columns[extendedAttributes.columnIndex].attributes[extendedAttributes.rowIndex - 1].indexPath;
|
|
533
|
+
}
|
|
534
|
+
|
|
535
|
+
return indexPath;
|
|
536
|
+
},
|
|
537
|
+
|
|
538
|
+
// @override - BMCollectionViewLayout
|
|
539
|
+
indexPathToTheRightOfIndexPath(indexPath) {
|
|
540
|
+
// Create a rect starting at the left edge of the given index path and request attributes in it
|
|
541
|
+
const extendedAttributes = this._extendedCachedAttributesForCellAtIndexPath(indexPath);
|
|
542
|
+
|
|
543
|
+
const cache = this.cachedLayout;
|
|
544
|
+
|
|
545
|
+
if (extendedAttributes.columnIndex >= this.cachedLayout.columns.length - 1) return indexPath;
|
|
546
|
+
|
|
547
|
+
const startingAttributes = extendedAttributes.attribute;
|
|
548
|
+
const center = startingAttributes.frame.center.y;
|
|
549
|
+
|
|
550
|
+
const offset = this.collectionView.scrollOffset;
|
|
551
|
+
|
|
552
|
+
// Find the attributes in next column with the smallest vertical distance from the starting attributes
|
|
553
|
+
const column = cache.columns[extendedAttributes.columnIndex + 1];
|
|
554
|
+
|
|
555
|
+
// The speedTop is the unscaled top position at which to start retrieving cells.
|
|
556
|
+
var speedTop = offset.y * column.speed;
|
|
557
|
+
|
|
558
|
+
// The speedAdjustment is the amount by which to displace each attribute's Y origin.
|
|
559
|
+
var speedAdjustment = offset.y - speedTop;
|
|
560
|
+
|
|
561
|
+
let minIndex = -1;
|
|
562
|
+
let minDistance = Number.MAX_SAFE_INTEGER;
|
|
563
|
+
for (let i = 0; i < column.attributes.length; i++) {
|
|
564
|
+
const attribute = column.attributes[i];
|
|
565
|
+
const position = attribute.frame.center.y + speedAdjustment | 0;
|
|
566
|
+
|
|
567
|
+
const distance = Math.abs(position - center);
|
|
568
|
+
if (distance < minDistance) {
|
|
569
|
+
minIndex = i;
|
|
570
|
+
minDistance = distance;
|
|
571
|
+
}
|
|
572
|
+
}
|
|
573
|
+
|
|
574
|
+
if (minIndex != -1) {
|
|
575
|
+
return column.attributes[minIndex].indexPath;
|
|
576
|
+
}
|
|
577
|
+
|
|
578
|
+
return indexPath;
|
|
579
|
+
},
|
|
580
|
+
|
|
581
|
+
// @override - BMCollectionViewLayout
|
|
582
|
+
indexPathBelowIndexPath(indexPath) {
|
|
583
|
+
// Return the row below the given index path in the same column
|
|
584
|
+
const extendedAttributes = this._extendedCachedAttributesForCellAtIndexPath(indexPath);
|
|
585
|
+
|
|
586
|
+
if (extendedAttributes.rowIndex < this.cachedLayout.columns[extendedAttributes.columnIndex].attributes.length - 1) {
|
|
587
|
+
return this.cachedLayout.columns[extendedAttributes.columnIndex].attributes[extendedAttributes.rowIndex + 1].indexPath;
|
|
588
|
+
}
|
|
589
|
+
|
|
590
|
+
return indexPath;
|
|
591
|
+
},
|
|
592
|
+
|
|
593
|
+
// @override - BMCollectionViewLayout
|
|
594
|
+
indexPathsFromIndexPath(indexPath, {toIndexPath}) {
|
|
595
|
+
// Create and return the index paths available in the union of the two index paths' frames.
|
|
596
|
+
const startingAttributes = this.attributesForCellAtIndexPath(indexPath);
|
|
597
|
+
const targetAttributes = this.attributesForCellAtIndexPath(toIndexPath);
|
|
598
|
+
|
|
599
|
+
const attributes = this.attributesForElementsInRect(startingAttributes.frame.rectByUnionWithRect(targetAttributes.frame));
|
|
600
|
+
|
|
601
|
+
return attributes.filter(a => a.itemType == BMCollectionViewLayoutAttributesType.Cell).map(a => a.indexPath);
|
|
602
|
+
},
|
|
463
603
|
|
|
464
604
|
// @override - BMCollectionViewLayout
|
|
465
605
|
copy: function () {
|
|
@@ -6,7 +6,7 @@ import {BMPointMakeWithX} from '../Core/BMPoint'
|
|
|
6
6
|
import {BMSizeMake} from '../Core/BMSize'
|
|
7
7
|
import {BMRectMake, BMRectMakeWithX, BMRectMakeWithOrigin} from '../Core/BMRect'
|
|
8
8
|
import {BMIndexPathMakeWithIndexes} from '../Core/BMIndexPath'
|
|
9
|
-
import {BMCollectionViewLayoutAttributesMakeForCellAtIndexPath, BMCollectionViewLayoutAttributesMakeForSupplementaryViewWithIdentifier} from './BMCollectionViewLayoutAttributes'
|
|
9
|
+
import {BMCollectionViewLayoutAttributesMakeForCellAtIndexPath, BMCollectionViewLayoutAttributesMakeForSupplementaryViewWithIdentifier, BMCollectionViewLayoutAttributesType} from './BMCollectionViewLayoutAttributes'
|
|
10
10
|
import {BMCollectionViewFlowLayoutSupplementaryView, BMCollectionViewTableLayoutSupplementaryView} from './BMCollectionViewFlowLayout'
|
|
11
11
|
import {BMCollectionViewLayout} from './BMCollectionViewLayout'
|
|
12
12
|
|
|
@@ -1106,7 +1106,152 @@ BMCollectionViewTileLayout.prototype = BMExtend({}, BMCollectionViewLayout.proto
|
|
|
1106
1106
|
|
|
1107
1107
|
// Control shouldn't reach this point
|
|
1108
1108
|
debugger;
|
|
1109
|
-
}
|
|
1109
|
+
},
|
|
1110
|
+
|
|
1111
|
+
/************************************* CELL HIGHLIGHTING ********************************/
|
|
1112
|
+
|
|
1113
|
+
// @override - BMCollectionViewLayout
|
|
1114
|
+
indexPathToTheLeftOfIndexPath(indexPath) {
|
|
1115
|
+
// Create a rect starting at the left edge of the given index path and request attributes in it
|
|
1116
|
+
const startingAttributes = this.attributesForCellAtIndexPath(indexPath);
|
|
1117
|
+
|
|
1118
|
+
const extent = BMRectMake(
|
|
1119
|
+
startingAttributes.frame.origin.x - this.collectionView.bounds.size.width - 1,
|
|
1120
|
+
startingAttributes.frame.origin.y,
|
|
1121
|
+
this.collectionView.bounds.size.width,
|
|
1122
|
+
startingAttributes.frame.size.height
|
|
1123
|
+
);
|
|
1124
|
+
|
|
1125
|
+
// Filter to only include cell attributes
|
|
1126
|
+
const attributes = this.attributesForElementsInRect(extent).filter(a => a.itemType == BMCollectionViewLayoutAttributesType.Cell);
|
|
1127
|
+
|
|
1128
|
+
// return the rightmost attributes, if any
|
|
1129
|
+
let maxAttributesX = extent.left;
|
|
1130
|
+
let maxAttributesIndex = -1;
|
|
1131
|
+
|
|
1132
|
+
for (let i = 0; i < attributes.length; i++) {
|
|
1133
|
+
if (attributes[i].frame.origin.x > maxAttributesX) {
|
|
1134
|
+
maxAttributesX = attributes[i].frame.origin.x;
|
|
1135
|
+
maxAttributesIndex = i;
|
|
1136
|
+
}
|
|
1137
|
+
}
|
|
1138
|
+
|
|
1139
|
+
if (maxAttributesIndex != -1) {
|
|
1140
|
+
return attributes[maxAttributesIndex].indexPath;
|
|
1141
|
+
}
|
|
1142
|
+
|
|
1143
|
+
return indexPath;
|
|
1144
|
+
},
|
|
1145
|
+
|
|
1146
|
+
// @override - BMCollectionViewLayout
|
|
1147
|
+
indexPathAboveIndexPath(indexPath) {
|
|
1148
|
+
// Create a rect starting at the top edge of the given index path and request attributes in it
|
|
1149
|
+
const startingAttributes = this.attributesForCellAtIndexPath(indexPath);
|
|
1150
|
+
|
|
1151
|
+
const extent = BMRectMake(
|
|
1152
|
+
startingAttributes.frame.origin.x,
|
|
1153
|
+
startingAttributes.frame.origin.y - this.collectionView.bounds.size.height - 1,
|
|
1154
|
+
startingAttributes.frame.size.width,
|
|
1155
|
+
this.collectionView.bounds.size.height
|
|
1156
|
+
);
|
|
1157
|
+
|
|
1158
|
+
// Filter to only include cell attributes
|
|
1159
|
+
const attributes = this.attributesForElementsInRect(extent).filter(a => a.itemType == BMCollectionViewLayoutAttributesType.Cell);
|
|
1160
|
+
|
|
1161
|
+
// return the bottommost attributes, if any
|
|
1162
|
+
let maxAttributesY = extent.origin.y;
|
|
1163
|
+
let maxAttributesIndex = -1;
|
|
1164
|
+
|
|
1165
|
+
for (let i = 0; i < attributes.length; i++) {
|
|
1166
|
+
if (attributes[i].frame.origin.y > maxAttributesY) {
|
|
1167
|
+
maxAttributesY = attributes[i].frame.origin.y;
|
|
1168
|
+
maxAttributesIndex = i;
|
|
1169
|
+
}
|
|
1170
|
+
}
|
|
1171
|
+
|
|
1172
|
+
if (maxAttributesIndex != -1) {
|
|
1173
|
+
return attributes[maxAttributesIndex].indexPath;
|
|
1174
|
+
}
|
|
1175
|
+
|
|
1176
|
+
return indexPath;
|
|
1177
|
+
},
|
|
1178
|
+
|
|
1179
|
+
// @override - BMCollectionViewLayout
|
|
1180
|
+
indexPathToTheRightOfIndexPath(indexPath) {
|
|
1181
|
+
// Create a rect starting at the right edge of the given index path and request attributes in it
|
|
1182
|
+
const startingAttributes = this.attributesForCellAtIndexPath(indexPath);
|
|
1183
|
+
|
|
1184
|
+
const extent = BMRectMake(
|
|
1185
|
+
startingAttributes.frame.right + 1,
|
|
1186
|
+
startingAttributes.frame.origin.y,
|
|
1187
|
+
this.collectionView.bounds.size.width,
|
|
1188
|
+
startingAttributes.frame.size.height
|
|
1189
|
+
);
|
|
1190
|
+
|
|
1191
|
+
// Filter to only include cell attributes
|
|
1192
|
+
const attributes = this.attributesForElementsInRect(extent).filter(a => a.itemType == BMCollectionViewLayoutAttributesType.Cell);
|
|
1193
|
+
|
|
1194
|
+
// return the leftmost attributes, if any
|
|
1195
|
+
let minAttributesX = extent.right;
|
|
1196
|
+
let minAttributesIndex = -1;
|
|
1197
|
+
|
|
1198
|
+
for (let i = 0; i < attributes.length; i++) {
|
|
1199
|
+
if (attributes[i].frame.origin.x < minAttributesX) {
|
|
1200
|
+
minAttributesX = attributes[i].frame.origin.x;
|
|
1201
|
+
minAttributesIndex = i;
|
|
1202
|
+
}
|
|
1203
|
+
}
|
|
1204
|
+
|
|
1205
|
+
if (minAttributesIndex != -1) {
|
|
1206
|
+
return attributes[minAttributesIndex].indexPath;
|
|
1207
|
+
}
|
|
1208
|
+
|
|
1209
|
+
return indexPath;
|
|
1210
|
+
},
|
|
1211
|
+
|
|
1212
|
+
// @override - BMCollectionViewLayout
|
|
1213
|
+
indexPathBelowIndexPath(indexPath) {
|
|
1214
|
+
// Create a rect starting at the bottom edge of the given index path and request attributes in it
|
|
1215
|
+
const startingAttributes = this.attributesForCellAtIndexPath(indexPath);
|
|
1216
|
+
|
|
1217
|
+
const extent = BMRectMake(
|
|
1218
|
+
startingAttributes.frame.origin.x,
|
|
1219
|
+
startingAttributes.frame.bottom + 1,
|
|
1220
|
+
startingAttributes.frame.size.width,
|
|
1221
|
+
this.collectionView.bounds.size.height
|
|
1222
|
+
);
|
|
1223
|
+
|
|
1224
|
+
// Filter to only include cell attributes
|
|
1225
|
+
const attributes = this.attributesForElementsInRect(extent).filter(a => a.itemType == BMCollectionViewLayoutAttributesType.Cell);
|
|
1226
|
+
|
|
1227
|
+
// return the topmost attributes, if any
|
|
1228
|
+
let minAttributesY = extent.bottom;
|
|
1229
|
+
let minAttributesIndex = -1;
|
|
1230
|
+
|
|
1231
|
+
for (let i = 0; i < attributes.length; i++) {
|
|
1232
|
+
if (attributes[i].frame.origin.y < minAttributesY) {
|
|
1233
|
+
minAttributesY = attributes[i].frame.origin.y;
|
|
1234
|
+
minAttributesIndex = i;
|
|
1235
|
+
}
|
|
1236
|
+
}
|
|
1237
|
+
|
|
1238
|
+
if (minAttributesIndex != -1) {
|
|
1239
|
+
return attributes[minAttributesIndex].indexPath;
|
|
1240
|
+
}
|
|
1241
|
+
|
|
1242
|
+
return indexPath;
|
|
1243
|
+
},
|
|
1244
|
+
|
|
1245
|
+
// @override - BMCollectionViewLayout
|
|
1246
|
+
indexPathsFromIndexPath(indexPath, {toIndexPath}) {
|
|
1247
|
+
// Create and return the index paths available in the union of the two index paths' frames.
|
|
1248
|
+
const startingAttributes = this.attributesForCellAtIndexPath(indexPath);
|
|
1249
|
+
const targetAttributes = this.attributesForCellAtIndexPath(toIndexPath);
|
|
1250
|
+
|
|
1251
|
+
const attributes = this.attributesForElementsInRect(startingAttributes.frame.rectByUnionWithRect(targetAttributes.frame));
|
|
1252
|
+
|
|
1253
|
+
return attributes.filter(a => a.itemType == BMCollectionViewLayoutAttributesType.Cell).map(a => a.indexPath);
|
|
1254
|
+
},
|
|
1110
1255
|
|
|
1111
1256
|
});
|
|
1112
1257
|
|
package/build/BMCoreUI.css
CHANGED
|
@@ -32,6 +32,8 @@
|
|
|
32
32
|
position: fixed;
|
|
33
33
|
|
|
34
34
|
box-shadow: 0px 4px 12px rgba(0, 0, 0, .33);
|
|
35
|
+
|
|
36
|
+
pointer-events: none;
|
|
35
37
|
}
|
|
36
38
|
|
|
37
39
|
.BMDragIndicatorRed {
|
|
@@ -387,7 +389,7 @@
|
|
|
387
389
|
}
|
|
388
390
|
|
|
389
391
|
/* BMWindowSublabel should be used together with BMWindowLabel */
|
|
390
|
-
.BMWindowSublabel {
|
|
392
|
+
.BMWindowSublabel, .BMSublabel {
|
|
391
393
|
font-size: 14px;
|
|
392
394
|
color: rgba(0, 0, 0, .33);
|
|
393
395
|
}
|
|
@@ -397,7 +399,7 @@
|
|
|
397
399
|
color: rgba(255, 255, 255, .9);
|
|
398
400
|
}
|
|
399
401
|
|
|
400
|
-
.BMWindowSublabel, .
|
|
402
|
+
.BMWindowSublabel, .BMSubLabel {
|
|
401
403
|
color: rgba(255, 255, 255, .5);
|
|
402
404
|
}
|
|
403
405
|
}
|
|
@@ -643,7 +645,7 @@
|
|
|
643
645
|
border: none;
|
|
644
646
|
}
|
|
645
647
|
|
|
646
|
-
.BMWindowButton:active, .BMButton:
|
|
648
|
+
.BMWindowButton:active, .BMButton:active {
|
|
647
649
|
background: rgb(0, 108, 235);
|
|
648
650
|
}
|
|
649
651
|
|
|
@@ -1188,7 +1190,7 @@ input:not(:checked) + .BMWindowSwitchGutter > .BMWindowSwitchKnob, .BMWindowSwit
|
|
|
1188
1190
|
|
|
1189
1191
|
border-radius: 8px !important;
|
|
1190
1192
|
box-shadow: 0px 4px 8px rgba(0, 0, 0, .1), 0px 0px 1px 1px rgba(0, 0, 0, .1);
|
|
1191
|
-
z-index:
|
|
1193
|
+
z-index: 9999999 !important;
|
|
1192
1194
|
overflow: hidden !important;
|
|
1193
1195
|
}
|
|
1194
1196
|
|
|
@@ -1222,8 +1224,8 @@ input:not(:checked) + .BMWindowSwitchGutter > .BMWindowSwitchKnob, .BMWindowSwit
|
|
|
1222
1224
|
}
|
|
1223
1225
|
|
|
1224
1226
|
.BMLayoutEditorConstraintPopupOption, .BMMenuItem {
|
|
1225
|
-
height:
|
|
1226
|
-
line-height:
|
|
1227
|
+
height: 28px;
|
|
1228
|
+
line-height: 28px;
|
|
1227
1229
|
vertical-align: middle;
|
|
1228
1230
|
|
|
1229
1231
|
padding-left: 16px;
|
|
@@ -1259,16 +1261,43 @@ input:not(:checked) + .BMWindowSwitchGutter > .BMWindowSwitchKnob, .BMWindowSwit
|
|
|
1259
1261
|
margin-right: 16px;
|
|
1260
1262
|
}
|
|
1261
1263
|
|
|
1262
|
-
|
|
1264
|
+
@keyframes BMMenuItemActiveAnimation {
|
|
1265
|
+
from {
|
|
1266
|
+
background: transparent;
|
|
1267
|
+
color: rgba(0, 0, 0, .8);
|
|
1268
|
+
}
|
|
1269
|
+
|
|
1270
|
+
49% {
|
|
1271
|
+
background: transparent;
|
|
1272
|
+
color: rgba(0, 0, 0, .8);
|
|
1273
|
+
}
|
|
1274
|
+
|
|
1275
|
+
50% {
|
|
1276
|
+
background: rgb(0, 128, 255);
|
|
1277
|
+
color: white;
|
|
1278
|
+
}
|
|
1279
|
+
|
|
1280
|
+
to {
|
|
1281
|
+
background: rgb(0, 128, 255);
|
|
1282
|
+
color: white;
|
|
1283
|
+
}
|
|
1284
|
+
}
|
|
1285
|
+
|
|
1286
|
+
.BMLayoutEditorConstraintPopupOption:hover, .BMMenuTouch > .BMMenuItem:active, .BMMenuItem.BMMenuItemHighlighted {
|
|
1263
1287
|
background: rgb(0, 128, 255);
|
|
1264
1288
|
color: white;
|
|
1265
1289
|
}
|
|
1266
1290
|
|
|
1267
|
-
.BMLayoutEditorConstraintPopupOption:active, .
|
|
1291
|
+
.BMLayoutEditorConstraintPopupOption:active, .BMMenuTouch > .BMMenuItem:hover {
|
|
1268
1292
|
background: transparent;
|
|
1269
1293
|
color: rgba(0, 0, 0, .8);
|
|
1270
1294
|
}
|
|
1271
1295
|
|
|
1296
|
+
.BMMenuItem.BMMenuItemActive {
|
|
1297
|
+
animation: .2s linear BMMenuItemActiveAnimation;
|
|
1298
|
+
animation-fill-mode: both;
|
|
1299
|
+
}
|
|
1300
|
+
|
|
1272
1301
|
.BMLayoutEditorConstraintPopupOptionHighlighted, .BMMenuItemHighlighted {
|
|
1273
1302
|
background: rgba(0, 128, 255, .5);
|
|
1274
1303
|
}
|
|
@@ -1278,7 +1307,7 @@ input:not(:checked) + .BMWindowSwitchGutter > .BMWindowSwitchKnob, .BMWindowSwit
|
|
|
1278
1307
|
color: rgba(255, 255, 255, .9);
|
|
1279
1308
|
}
|
|
1280
1309
|
|
|
1281
|
-
.BMLayoutEditorConstraintPopupOption:active, .
|
|
1310
|
+
.BMLayoutEditorConstraintPopupOption:active, .BMMenuTouch > .BMMenuItem:hover {
|
|
1282
1311
|
background: transparent;
|
|
1283
1312
|
color: white;
|
|
1284
1313
|
}
|
|
@@ -1286,6 +1315,28 @@ input:not(:checked) + .BMWindowSwitchGutter > .BMWindowSwitchKnob, .BMWindowSwit
|
|
|
1286
1315
|
.BMMenuTouch > .BMMenuItem {
|
|
1287
1316
|
border-bottom-color: rgba(255, 255, 255, .1);
|
|
1288
1317
|
}
|
|
1318
|
+
|
|
1319
|
+
@keyframes BMMenuItemActiveAnimation {
|
|
1320
|
+
from {
|
|
1321
|
+
background: transparent;
|
|
1322
|
+
color: rgba(255, 255, 255, .9);
|
|
1323
|
+
}
|
|
1324
|
+
|
|
1325
|
+
49% {
|
|
1326
|
+
background: transparent;
|
|
1327
|
+
color: rgba(255, 255, 255, .9);
|
|
1328
|
+
}
|
|
1329
|
+
|
|
1330
|
+
50% {
|
|
1331
|
+
background: rgb(0, 128, 255);
|
|
1332
|
+
color: white;
|
|
1333
|
+
}
|
|
1334
|
+
|
|
1335
|
+
to {
|
|
1336
|
+
background: rgb(0, 128, 255);
|
|
1337
|
+
color: white;
|
|
1338
|
+
}
|
|
1339
|
+
}
|
|
1289
1340
|
}
|
|
1290
1341
|
|
|
1291
1342
|
.BMLayoutEditorWorkspaceToolbarSizeClass .BMLayoutEditorConstraintPopupOption {
|
|
@@ -2606,7 +2657,6 @@ The background layer contains the background.
|
|
|
2606
2657
|
|
|
2607
2658
|
.BMLayoutEditorConstantSuggestions, .BMTextFieldSuggestions {
|
|
2608
2659
|
pointer-events: all;
|
|
2609
|
-
max-height: 420px;
|
|
2610
2660
|
overflow: hidden;
|
|
2611
2661
|
}
|
|
2612
2662
|
|