Bug 542940 - Method setEditor of class TreeEditor raises java
nullException

Calling gtk_widget_show and then gtk_widget_hide in Control#setBounds
from TreeEditor.setEditor causes display to be null. The workaround is
to force Text to be visible on initialization so that we do not need to
force show/hide in order to set bound for the TreeEditor text. See
similar fix for Button in Bug 533469.

Tested with attached snippet, Bug533469_GhostButton,
Bug497705_setBoundsAfterSetVisible.

Change-Id: I9fe8cfb63358608700246d9a6c9355b53169045d
Signed-off-by: Xi Yan <xixiyan@redhat.com>
diff --git a/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Text.java b/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Text.java
index 921cd12..31d1279 100644
--- a/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Text.java
+++ b/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Text.java
@@ -1657,11 +1657,22 @@
 @Override
 long /*int*/ gtk_draw (long /*int*/ widget, long /*int*/ cairo) {
 	if ((state & OBSCURED) != 0) return 0;
+	if (GTK.GTK_VERSION >= OS.VERSION (3, 20, 0) && (state & ZERO_WIDTH) != 0 && (state & ZERO_HEIGHT) != 0) {
+		if (GTK.gtk_widget_get_visible(widget)) GTK.gtk_widget_set_visible(widget, false);
+		// Display should not be disposed after hiding widget
+		if (isDisposed() || display == null || display.isDisposed()) error (SWT.ERROR_DEVICE_DISPOSED);
+	}
 	long /*int*/ result = super.gtk_draw (widget, cairo);
 	return result;
 }
 
 @Override
+boolean mustBeVisibleOnInitBounds() {
+	// Bug 542940: Workaround to avoid NPE, make Text visible on initialization
+	return true;
+}
+
+@Override
 long /*int*/ gtk_focus_out_event (long /*int*/ widget, long /*int*/ event) {
 	fixIM ();
 	return super.gtk_focus_out_event (widget, event);
diff --git a/tests/org.eclipse.swt.tests.gtk/ManualTests/org/eclipse/swt/tests/gtk/snippets/Bug542940_NPETreeSetEditor.java b/tests/org.eclipse.swt.tests.gtk/ManualTests/org/eclipse/swt/tests/gtk/snippets/Bug542940_NPETreeSetEditor.java
new file mode 100644
index 0000000..5d748ec
--- /dev/null
+++ b/tests/org.eclipse.swt.tests.gtk/ManualTests/org/eclipse/swt/tests/gtk/snippets/Bug542940_NPETreeSetEditor.java
@@ -0,0 +1,87 @@
+package org.eclipse.swt.tests.gtk.snippets;
+
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.custom.TreeEditor;
+import org.eclipse.swt.events.FocusAdapter;
+import org.eclipse.swt.events.FocusEvent;
+import org.eclipse.swt.events.KeyAdapter;
+import org.eclipse.swt.events.KeyEvent;
+import org.eclipse.swt.layout.FillLayout;
+import org.eclipse.swt.widgets.Display;
+import org.eclipse.swt.widgets.Shell;
+import org.eclipse.swt.widgets.Text;
+import org.eclipse.swt.widgets.Tree;
+import org.eclipse.swt.widgets.TreeItem;
+
+public class Bug542940_NPETreeSetEditor {
+	public static void main(String[] args) {
+		Display display = new Display();
+		Shell shell = new Shell(display);
+		shell.setText("Text Tree Editor");
+		shell.setLayout(new FillLayout());
+
+		final Tree tree = new Tree(shell, SWT.SINGLE);
+		for (int i = 0; i < 3; i++) {
+			TreeItem iItem = new TreeItem(tree, SWT.NONE);
+			iItem.setText("Item " + (i + 1));
+			for (int j = 0; j < 3; j++) {
+				TreeItem jItem = new TreeItem(iItem, SWT.NONE);
+				jItem.setText("Sub Item " + (j + 1));
+				for (int k = 0; k < 3; k++) {
+					new TreeItem(jItem, SWT.NONE).setText("Sub Sub Item " + (k + 1));
+				}
+				jItem.setExpanded(true);
+			}
+			iItem.setExpanded(true);
+		}
+
+		final TreeEditor editor = new TreeEditor(tree);
+		editor.horizontalAlignment = SWT.LEFT;
+		editor.grabHorizontal = true;
+
+		tree.addKeyListener(new KeyAdapter() {
+			@Override
+			public void keyPressed(KeyEvent event) {
+				if (event.keyCode == SWT.F2 && tree.getSelectionCount() == 1) {
+					final TreeItem item = tree.getSelection()[0];
+
+					final Text text = new Text(tree, SWT.NONE);
+//					text.setBounds(0, 0, 1, 1);
+					text.setText(item.getText());
+					text.selectAll();
+					text.setFocus();
+
+					text.addFocusListener(new FocusAdapter() {
+						@Override
+						public void focusLost(FocusEvent event) {
+							item.setText(text.getText());
+							text.dispose();
+						}
+					});
+
+					text.addKeyListener(new KeyAdapter() {
+						@Override
+						public void keyPressed(KeyEvent event) {
+							switch (event.keyCode) {
+							case SWT.CR:
+								item.setText(text.getText());
+							case SWT.ESC:
+								text.dispose();
+								break;
+							}
+						}
+					});
+					editor.setEditor(text, item);
+				}
+			}
+		});
+
+		shell.open();
+		while (!shell.isDisposed()) {
+			if (!display.readAndDispatch()) {
+				display.sleep();
+			}
+		}
+		display.dispose();
+	}
+}
\ No newline at end of file