New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Features/cgu/24.2/isd #984
base: releases/24.2
Are you sure you want to change the base?
Conversation
5f85d49
to
32a52ef
Compare
32a52ef
to
bb154e5
Compare
aeb7ec7
to
e0acb81
Compare
Also, don't fail if there is no parent, because tiles may be created without one (e.g. by hybrid manager for a scout js tile grid)
Focus manager calls preventDefault() if user presses mouse down on a non-focusable element to ensure the currently active element does not lose focus. Unfortunately, this also prevents the dragstart event which is needed if a widget requires drag & drop support.
The method already works correctly. The new early === check may be a tiny bit faster. The other changes are just code style related.
FormFieldMenu uses the ColumnLayout which makes the widgets as width as they prefer to be. This means the size may change if an error status appears or the label changes so the parent needs to be invalidated. This does currently not happen because HtmlComponent.isValidatorRoot() returns true if layoutData.useUiWidth is set to false. This is the case here because a LogicalGridData is used instead of a ColumnLayoutData.
This enables automatic serialization / deserialization if the enum is used in a data object.
The returned jquery collection contained jquery objects instead of html elements which is different to jquery collection by jquery and prevents using methods like .on()
Makes it possible to add custom save needed behavior. Also removed saveNeeded from model because it is a computed property
60ed66c
to
dbe6c31
Compare
If the resizable element is inside a scroll container, the scroll position needs to be considered when drawing the overlay
This ensures the resizable is always visible even on inverted tiles.
If there are many tests, the sandbox will be moved out of view which may break tests that need to interact with the sandbox elements, e.g. by clicking on them This fix reduces the height of the jasmine reporter section so the sandbox is always on top. Because of the overflowing, the content of the reporter section is still visible even though its height is 0.
Remove obsolete namespace in spec name. Remove obsolete jshint annotation. Remove DEFAULT_TIMEOUT_INTERVAL because it will affect every spec not only FocusManagerSpec and it does not seem to be needed.
This is useful if the splitter itself should be visualized in another way, e.g. by using one of the fields border.
Not every icon always has the same width. If icons are used in table cells along with text, the alignment of the texts in a column may be off. This typically affects list boxes or smart fields if the lookup rows have icons. The tree doesn't have that problem because it uses a min-width for the icons. The same logic is now applied to table cells as well.
HybridActionEvent uses actionType instead of eventType. Also move HybridEvent type to Adapter because it is only relevant for the communication with Java and not part of the hybrid manager api.
Sometimes the result object is already available. In that case it would be cumbersome to map the values into the given result object. With the new method the result object can be returned directly.
When importing the main index file from files in the testing folder, the import must not necessarily end with 'index'. For example if the index is in a folder called src/main/js, the import could be ../main/js. In fact, this how IntelliJ adds the import by default.
Codes delivered by the CodeResource are DOs and can therefor contain a _type property
If some of the tiles have h or w > 1 and others don't, the navigation between the tiles did not work properly.
dbe6c31
to
9d05a6f
Compare
jenkins run tests |
@@ -390,4 +390,5 @@ | |||
/* -------------------------------- */ | |||
@iphone5-height: 568px; | |||
@iphone5-width: 320px; | |||
@iphone6-width: 375px; | |||
@iphone6-width: 375px; // includes iphone 6, 6s, 6s plus, 7, 8 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks good but the comment of this commit has a typo: sizes.lesS
@@ -56,4 +56,25 @@ public static UserAgent getCurrentUserAgent() { | |||
} | |||
} | |||
|
|||
/** |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is this method really necessary? It would also be possible to use the ClientRunContext instead?
this.spy?.dispose(); | ||
this.spy = null; | ||
} else { | ||
this.spy = new LogicalGridLayoutSpy(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
trigger layout in order to draw the spies cell bounds?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this is not possible here since we don't have the $container. The idea is to use scout.setLogicalGridSpyEnabled
@@ -228,77 +230,67 @@ export class LogicalGridLayoutInfo implements LogicalGridLayoutInfoModel { | |||
prefw = this.logicalWidthInPixel(cons); | |||
} | |||
prefw = Math.floor(prefw); | |||
for (j = cons.gridx; j < cons.gridx + cons.gridw && j < this.cols; j++) { | |||
for (let j = cons.gridx; j < cons.gridx + cons.gridw && j < this.cols; j++) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please simplify this loop. As cons.gridw
is 1
this loop is pointless and can be replaced by a simple if-statement.
for (let j = cons.gridx; j < cons.gridx + cons.gridw && j < this.cols; j++) { | |
if (cons.gridx < this.cols) { |
if (cons.widthHint > 0) { | ||
distWidth = cons.widthHint - spanWidth - (hSpan - 1) * this.hgap; | ||
distWidth[lc.PREF] = cons.widthHint - spanWidth[lc.PREF] - hGaps; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please simplify:
distWidth[lc.PREF]
will always be value - spanWidth[lc.PREF] - hGaps
and distWidth[lc.MAX]
is cons.maxWidth - spanWidth[lc.MAX] - hGaps
.
Then distWidth[lc.PREF]
and spanWidth[lc.PREF]
(or distWidth[lc.MAX]
and spanWidth[lc.MAX]
) are passed to _distributeWidth
where the values are summed up again.
So it will be the same to just calculate distWidth = value - hGaps
and pass only this value to the _distributeWidth
method.
*/ | ||
protected _distributeWidth<T>(cons: LogicalGridData, distWidth: number, spanWidth: number, widths: number[], fixedWidths: boolean[], calc: (equalWidth: number, width: number) => number) { | ||
let hSpan = cons.gridw; | ||
let equalWidth = Math.floor((distWidth + spanWidth) / hSpan); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is not a proper way to distribute equally.
Consider the 99 distributed to 10 columns.
This will lead to 9 columns being 9 wide and the last one being 18 wide.
See pie charts or #222794 for a proper algorithm (ticket has a proof attached).
expect(rows[0][1]).toEqual(new Rectangle(75, 0, parentSize.width - 75, 30)); | ||
}); | ||
|
||
describe('maxWidth', () => { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
add test cases for the problems pointed out in LogicalGridLayoutInfo
...rt.shared/src/main/java/org/eclipse/scout/rt/chart/shared/data/basic/chart/IChartConfig.java
Show resolved
Hide resolved
DO_ENTITY result = exportResult(form); | ||
if (result == null) { | ||
result = createEmptyResult(); | ||
} | ||
fireHybridWidgetEvent("save", result); | ||
} | ||
else if (FormEvent.TYPE_RESET_COMPLETE == e.getType()) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Result needs to be exported and sent to the UI in the reset case as well.
See HybridManager._onHybridFormEvent
. The sent data
will be set onto the Form and then a reset-Event is triggered. Therefore, the current data (after reset) needs to be sent otherwise it will be empty in the UI after a reset.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How did it work before my change? Nothing was done with the result. Does it need to be passed to fireHybridWidgetEvent?
@@ -1266,7 +1266,7 @@ export class TileGrid<TTile extends Tile = Tile> extends Widget implements TileG | |||
findTileIndexAt(x: number, y: number, startIndex?: number, reverse?: boolean): number { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Test?
* If there are tiles selected but there is no focused tile, an object is returned containing the tile to be focused. | ||
* This is the last tile if diff is > 0 and the first tile otherwise. | ||
*/ | ||
protected _computeFocusedTileOrSelection(diff: number): TileGridSelectionInstruction { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I find it a bit confusing that the first part of this method looks exactly like the implementation of computeFocusedTile(). Maybe this could be combined by passing the array of tiles as an argument to computeFocusedTile()?
Why does the method use the word "or", but the implementation returns both the focused tile "and" the selection?
If all other computeXYZ() methods are public, shouldn't this method be public as well?
let focusedTile = null; | ||
let focusedTileIndex = -1; | ||
let result = this._computeFocusedTile(xDiff); | ||
let result = this._computeFocusedTileOrSelection(xDiff); | ||
if (result.selectedTiles !== null) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
if (result.selectedTiles !== null) { | |
if (result.selectedTiles) { |
Or should we even need to check the length of the array? Maybe a JsDoc on the interface would help clarify the API.
Same with computeSelectionY.
org.eclipse.scout.rt.client/src/main/java/org/eclipse/scout/rt/client/ui/tile/AbstractTile.java
Show resolved
Hide resolved
@Override | ||
public void cancelLoading() { | ||
if (m_loadJob != null) { | ||
m_loadJob.cancel(true); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe set the member to null? Or add .whenDone() when scheduling the job and set it to null, so it will also be reset upon normal completion.
@@ -61,6 +62,8 @@ export class TileGrid<TTile extends Tile = Tile> extends Widget implements TileG | |||
updateTextFilterText: string; | |||
defaultMenuTypes: string[]; | |||
wrappable: boolean; | |||
movableProducer: (tile: Tile) => TileMoveHandler; | |||
resizableProducer: (tile: Tile) => Resizable; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same issue as with movableProducer.
minBounds: Rectangle; | ||
maxBounds: Rectangle; | ||
distance: number[]; | ||
edge: string; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Consider using a string union type: edge: 'e' | 'n' | ...;
if (this._context.currentBounds.equals(this._context.initialBounds)) { | ||
return; | ||
} | ||
this.$container.trigger('resizeend', { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is the spelling here intentional? It does not seem to be a native event, and I could not find any other reference to "resizeend" in the code.
distance = this._calcDistance(ctx.mousedownEvent, event); | ||
let newBounds = this._computeBounds(event); | ||
if (newBounds) { | ||
$.throttle(this._resizeHandler, Resizable.FPS)(newBounds); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Does that work? I think
@@ -294,6 +324,16 @@ export class TileGrid<TTile extends Tile = Tile> extends Widget implements TileG | |||
this.setTiles([]); | |||
} | |||
|
|||
moveTileBefore(tileToMove: ObjectOrModel<TTile>, sibling: TTile) { | |||
let tiles = arrays.moveBefore(this._tiles, tileToMove as Tile, sibling); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why does the type of the first argument allow models? this._tiles does not contain any models (according to its type), therefore a model could never be moved.
No description provided.