Skip to content

Commit b89e6dc

Browse files
authored
Fix layout of tables that have checkboxes on mac (#14)
2 parents 5ad2dbb + bd577fc commit b89e6dc

File tree

7 files changed

+105
-16
lines changed

7 files changed

+105
-16
lines changed

CHANGES.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
# DurianSwt releases
22

33
## [Unreleased]
4+
### Fixed
5+
- Mac tables with a checkbox column now size the rest of their columns correctly. ([#14](https://github.com/diffplug/durian-swt/pull/14))
46

57
## [3.4.0] - 2021-07-17
68
### Added

durian-swt/build.gradle

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -27,21 +27,23 @@ dependencies {
2727
}
2828
*/
2929
// in java-library mode, durian-swt.os remains as a folder of classes for gradle internally, which the osgi plugin does not like
30-
tasks.jar.dependsOn(':durian-swt.os:jar')
30+
tasks.named('jar').configure {
31+
dependsOn(':durian-swt.os:jar')
32+
}
3133

3234
/////////////////////////
3335
// INTERACTIVE TESTING //
3436
/////////////////////////
3537
// standard `gradlew test` will autoclose after 500ms
38+
boolean isMac = System.getProperty("os.name").toLowerCase().contains("mac")
3639
test {
3740
systemProperty 'com.diffplug.test.autoclose.milliseconds', '500'
3841
useJUnit {
3942
// there are some tests that can't pass without a user, so we'll exclude them
4043
excludeCategories 'com.diffplug.common.swt.InteractiveTest$FailsWithoutUser'
4144
// SWT tests don't work in gradle on OS X (https://github.com/ReadyTalk/swt-bling/issues/4)
42-
boolean isMac = System.getProperty("os.name").toLowerCase().contains("mac");
4345
if (isMac) {
44-
excludeCategories 'com.diffplug.common.swt.InteractiveTest'
46+
jvmArgs = ['-XstartOnFirstThread']
4547
}
4648
}
4749
// log all test events
@@ -51,9 +53,12 @@ test {
5153
}
5254

5355
// only run the interactive tests
54-
task interactiveTest(type: Test) {
56+
tasks.register('interactiveTest', Test) {
5557
systemProperty 'com.diffplug.test.autoclose.milliseconds', null
5658
useJUnit {
5759
includeCategories 'com.diffplug.common.swt.InteractiveTest'
60+
if (isMac) {
61+
jvmArgs = ['-XstartOnFirstThread']
62+
}
5863
}
5964
}

durian-swt/src/main/java/com/diffplug/common/swt/ColumnFormat.java

Lines changed: 34 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2020 DiffPlug
2+
* Copyright (C) 2020-2021 DiffPlug
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -16,6 +16,7 @@
1616
package com.diffplug.common.swt;
1717

1818

19+
import com.diffplug.common.swt.os.OS;
1920
import java.util.ArrayList;
2021
import java.util.Collections;
2122
import java.util.List;
@@ -109,12 +110,43 @@ protected static Table buildTable(Composite parent, int style, boolean linesVisi
109110
// create the columns and layout
110111
Function<ColumnBuilder, TableColumn> buildFunc = builder -> builder.build(control);
111112
List<TableColumn> columns = columnBuilders.stream().map(buildFunc).collect(Collectors.toList());
112-
buildLayout(control, new TableColumnLayout(), columns, columnBuilders);
113+
114+
boolean needsSpecialLayout = SwtMisc.flagIsSet(SWT.CHECK, style) && OS.getNative().isMac();
115+
TableColumnLayout layout = needsSpecialLayout ? new MacCheckTableColumnLayout() : new TableColumnLayout();
116+
buildLayout(control, layout, columns, columnBuilders);
113117

114118
// return the control
115119
return control;
116120
}
117121

122+
/** Adds a phantom column for the checkboxes so that the rest of the space is calculated correctly. */
123+
private static class MacCheckTableColumnLayout extends TableColumnLayout {
124+
private static final int CHECK_COLUMN_WIDTH = 15;
125+
126+
@Override
127+
protected int getColumnCount(Scrollable tableTree) {
128+
return super.getColumnCount(tableTree) + 1;
129+
}
130+
131+
@Override
132+
protected void setColumnWidths(Scrollable tableTree, int[] widths) {
133+
TableColumn[] columns = ((Table) tableTree).getColumns();
134+
for (int i = 0; i < columns.length; i++) {
135+
columns[i].setWidth(widths[i]);
136+
}
137+
}
138+
139+
@Override
140+
protected ColumnLayoutData getLayoutData(Scrollable tableTree, int columnIndex) {
141+
Table table = (Table) tableTree;
142+
if (columnIndex < table.getColumnCount()) {
143+
return (ColumnLayoutData) table.getColumn(columnIndex).getData(LAYOUT_DATA);
144+
} else {
145+
return new ColumnPixelData(CHECK_COLUMN_WIDTH);
146+
}
147+
}
148+
}
149+
118150
/** Builds a table with the given columns. */
119151
protected static Tree buildTree(Composite parent, int style, boolean linesVisible, boolean headerVisible, List<? extends ColumnBuilder> columnBuilders) {
120152
SwtMisc.assertClean(parent);
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
/*
2+
* Copyright (C) 2020-2021 DiffPlug
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* https://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
package com.diffplug.common.swt.jface;
17+
18+
19+
import com.diffplug.common.swt.InteractiveTest;
20+
import com.diffplug.common.swt.Layouts;
21+
import java.util.Arrays;
22+
import org.eclipse.jface.viewers.ArrayContentProvider;
23+
import org.eclipse.jface.viewers.TableViewer;
24+
import org.eclipse.swt.SWT;
25+
import org.eclipse.swt.widgets.Composite;
26+
import org.junit.Test;
27+
import org.junit.experimental.categories.Category;
28+
29+
@Category(InteractiveTest.class)
30+
public class ColumnViewerFormatTest {
31+
@Test
32+
public void testCopy() {
33+
InteractiveTest.testCoat("Column viewer", 10, 10, cmp -> {
34+
Layouts.setFill(cmp);
35+
buildTableWithCheck(new Composite(cmp, SWT.BORDER), true);
36+
buildTableWithCheck(new Composite(cmp, SWT.BORDER), false);
37+
});
38+
}
39+
40+
private void buildTableWithCheck(Composite cmp, boolean hasCheck) {
41+
ColumnViewerFormat<String> format = ColumnViewerFormat.builder();
42+
format.setStyle(SWT.FULL_SELECTION | (hasCheck ? SWT.CHECK : SWT.NONE));
43+
format.addColumn().setLabelProviderText(s -> s);
44+
TableViewer viewer = format.buildTable(cmp);
45+
viewer.setContentProvider(ArrayContentProvider.getInstance());
46+
viewer.setInput(Arrays.asList("Onesy twosy threesy foursy", "red orange yellow green blue purple"));
47+
}
48+
}
Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
distributionBase=GRADLE_USER_HOME
22
distributionPath=wrapper/dists
3-
distributionUrl=https\://services.gradle.org/distributions/gradle-7.1.1-bin.zip
3+
distributionUrl=https\://services.gradle.org/distributions/gradle-7.2-bin.zip
44
zipStoreBase=GRADLE_USER_HOME
55
zipStorePath=wrapper/dists

gradlew

Lines changed: 10 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
#!/usr/bin/env bash
1+
#!/usr/bin/env sh
22

33
#
44
# Copyright 2015 the original author or authors.
@@ -172,12 +172,14 @@ if [ "$cygwin" = "true" -o "$msys" = "true" ] ; then
172172
esac
173173
fi
174174

175-
ARGV=("$@")
176-
eval set -- $DEFAULT_JVM_OPTS
175+
# Escape application args
176+
save () {
177+
for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done
178+
echo " "
179+
}
180+
APP_ARGS=`save "$@"`
177181

178-
IFS=$'
179-
' read -rd '' -a JAVA_OPTS_ARR <<< "$(echo $JAVA_OPTS | xargs -n1)"
180-
IFS=$'
181-
' read -rd '' -a GRADLE_OPTS_ARR <<< "$(echo $GRADLE_OPTS | xargs -n1)"
182+
# Collect all arguments for the java command, following the shell quoting and substitution rules
183+
eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS"
182184

183-
exec "$JAVACMD" "$@" "${JAVA_OPTS_ARR[@]}" "${GRADLE_OPTS_ARR[@]}" "-Dorg.gradle.appname=$APP_BASE_NAME" -classpath "$CLASSPATH" org.gradle.wrapper.GradleWrapperMain "${ARGV[@]}"
185+
exec "$JAVACMD" "$@"

settings.gradle

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ plugins {
2020
id 'org.jdrupes.mdoclet' apply false
2121
}
2222
blowdryerSetup {
23-
github 'diffplug/blowdryer-diffplug', 'tag', '5.0.4'
23+
github 'diffplug/blowdryer-diffplug', 'tag', '5.0.6'
2424
//devLocal '../blowdryer-diffplug'
2525
}
2626

0 commit comments

Comments
 (0)