-----Original Message----- From: Dejan Pecar [mailto:[EMAIL PROTECTED] Sent: Friday, May 19, 2006 9:45 PM To: Janak Mulani Subject: Re[2]: [ULC-developer] checkbox editor and renderer in a ulctree
hi janak,
thanks a lot for your help.
but the solution covers only "the tip of the mountain".
we're currently developing an application framework for about 50 application
programmers.
so what we do is we take the ulc classes subclass or wrap them that the
programmers can port their swing applications
with minimal effort to ulc (we have such a application framework for swing).
nearly all of the the components are done. but we have problems to support
the previous functionality for the tree.
one thing is checkbox but we have cases where we have 2 checkboxes and a
picture in a tree leaf.
the swing sample below covers the functionality we basically need (the
sample is senseless but it shows what we need).
the workaround you showed me i could use when i knew that i had one or two
cases to use this but this isn't the case.
the tree will be used in ten'th or even hundereds of cases with slighty
different editors or renderers.
so, when can we expect the bug entry you made to be fixed ?
and do see the possiblity to have also a container as tree renderer and
editor ?
import javax.swing.*;
import javax.swing.event.ChangeEvent;
import javax.swing.tree.TreeCellRenderer;
import javax.swing.tree.DefaultTreeCellRenderer;
import javax.swing.tree.DefaultMutableTreeNode;
import javax.swing.tree.TreeCellEditor;
import javax.swing.tree.TreePath;
import java.util.Vector;
import java.util.EventObject;
import java.awt.*;
import java.awt.event.MouseEvent;
import java.awt.event.ItemListener;
import java.awt.event.ItemEvent;
public class SwingTreeCheckTest {
public static void main(String args[]) {
JFrame frame = new JFrame("CheckBox Tree");
CheckBoxNode accessibilityOptions[] = {
new CheckBoxNode("Move system caret with focus/selection
changes", "1.png", false, true),
new CheckBoxNode("Always expand alt text for images",
"2.png", true, true)};
CheckBoxNode browsingOptions[] = {
new CheckBoxNode("Notify when downloads complete", "3.png",
false, false),
new CheckBoxNode("Disable script debugging", "4.png", true,
false),
new CheckBoxNode("Use AutoComplete", "5.png", true, true),
new CheckBoxNode("Browse in a new process", "6.png", false,
true)};
Vector accessVector = new NamedVector("Accessibility",
accessibilityOptions);
Vector browseVector = new NamedVector("Browsing", browsingOptions);
Object rootNodes[] = {accessVector, browseVector};
Vector rootVector = new NamedVector("Root", rootNodes);
JTree tree = new JTree(rootVector);
CheckBoxNodeRenderer renderer = new CheckBoxNodeRenderer();
tree.setCellRenderer(renderer);
tree.setCellEditor(new CheckBoxNodeEditor(tree));
tree.setEditable(true);
JScrollPane scrollPane = new JScrollPane(tree);
tree.setRowHeight(0);
frame.getContentPane().add(scrollPane, BorderLayout.CENTER);
frame.setSize(300, 150);
frame.setVisible(true);
}
}
class CheckBoxNodeRenderer implements TreeCellRenderer {
private JPanel leafRenderer = new JPanel();
public JLabel img = new JLabel();
public JCheckBox box1 = new JCheckBox();
public JCheckBox box2 = new JCheckBox();
public JLabel label = new JLabel();
public String imgname;
private DefaultTreeCellRenderer nonLeafRenderer = new
DefaultTreeCellRenderer();
Color selectionBorderColor, selectionForeground, selectionBackground,
textForeground, textBackground;
public CheckBoxNodeRenderer() {
leafRenderer.setLayout(new BoxLayout(leafRenderer,
BoxLayout.X_AXIS));
leafRenderer.setBorder(BorderFactory.createEmptyBorder());
Font fontValue;
fontValue = UIManager.getFont("Tree.font");
if(fontValue != null) {
box1.setFont(fontValue);
box2.setFont(fontValue);
label.setFont(fontValue);
}
Boolean booleanValue = (Boolean)
UIManager.get("Tree.drawsFocusBorderAroundIcon");
box1.setFocusPainted((booleanValue != null) && booleanValue);
box2.setFocusPainted((booleanValue != null) && booleanValue);
leafRenderer.add(img);
leafRenderer.add(box1);
leafRenderer.add(box2);
leafRenderer.add(label);
selectionBorderColor =
UIManager.getColor("Tree.selectionBorderColor");
selectionForeground =
UIManager.getColor("Tree.selectionForeground");
selectionBackground =
UIManager.getColor("Tree.selectionBackground");
textForeground = UIManager.getColor("Tree.textForeground");
textBackground = UIManager.getColor("Tree.textBackground");
}
public Component getTreeCellRendererComponent(JTree tree, Object value,
boolean selected, boolean expanded, boolean leaf, int row, boolean hasFocus)
{
Component returnValue;
if(leaf) {
String stringValue = tree.convertValueToText(value, selected,
expanded, leaf, row, false);
label.setText(stringValue);
box1.setSelected(false);
box2.setSelected(false);
img.setIcon(null);
imgname = "";
leafRenderer.setEnabled(tree.isEnabled());
box1.setEnabled(tree.isEnabled());
box2.setEnabled(tree.isEnabled());
label.setEnabled(tree.isEnabled());
if(selected) {
leafRenderer.setForeground(selectionForeground);
leafRenderer.setBackground(selectionBackground);
box1.setForeground(selectionForeground);
box1.setBackground(selectionBackground);
box2.setForeground(selectionForeground);
box2.setBackground(selectionBackground);
label.setForeground(selectionForeground);
label.setBackground(selectionBackground);
} else {
leafRenderer.setForeground(textForeground);
leafRenderer.setBackground(textBackground);
box1.setForeground(textForeground);
box1.setBackground(textBackground);
box2.setForeground(textForeground);
box2.setBackground(textBackground);
label.setForeground(textForeground);
label.setBackground(textBackground);
}
if((value != null) && (value instanceof DefaultMutableTreeNode))
{
Object userObject = ((DefaultMutableTreeNode)
value).getUserObject();
if(userObject instanceof CheckBoxNode) {
CheckBoxNode node = (CheckBoxNode) userObject;
label.setText(node.getText());
box1.setSelected(node.isSelected());
box2.setSelected(node.isSelected2());
imgname = node.img;
img.setIcon(new
ImageIcon(this.getClass().getResource(node.img)));
}
}
returnValue = leafRenderer;
} else {
returnValue = nonLeafRenderer.getTreeCellRendererComponent(tree,
value, selected, expanded, leaf, row, hasFocus);
}
return returnValue;
}
}
class CheckBoxNodeEditor extends AbstractCellEditor implements
TreeCellEditor {
CheckBoxNodeRenderer renderer = new CheckBoxNodeRenderer();
ChangeEvent changeEvent = null;
JTree tree;
public CheckBoxNodeEditor(JTree tree) {
this.tree = tree;
}
public Object getCellEditorValue() {
return new CheckBoxNode(renderer.label.getText(), renderer.imgname,
renderer.box1.isSelected(), renderer.box2.isSelected());
}
public boolean isCellEditable(EventObject event) {
//System.out.println("isCellEditable: " + event);
boolean returnValue = false;
if(event instanceof MouseEvent) {
MouseEvent mouseEvent = (MouseEvent) event;
TreePath path = tree.getPathForLocation(mouseEvent.getX(),
mouseEvent.getY());
if(path != null) {
Object node = path.getLastPathComponent();
if((node != null) && (node instanceof
DefaultMutableTreeNode)) {
DefaultMutableTreeNode treeNode =
(DefaultMutableTreeNode) node;
Object userObject = treeNode.getUserObject();
returnValue = ((treeNode.isLeaf()) && (userObject
instanceof CheckBoxNode));
}
}
}
return returnValue;
}
public Component getTreeCellEditorComponent(JTree tree, Object value,
boolean selected, boolean expanded, boolean leaf, int row) {
Component editor = renderer.getTreeCellRendererComponent(tree,
value, true, expanded, leaf, row, true);
// editor always selected / focused
ItemListener itemListener = new ItemListener() {
public void itemStateChanged(ItemEvent itemEvent) {
if(stopCellEditing()) {
fireEditingStopped();
}
}
};
if(editor instanceof JPanel) {
renderer.box1.addItemListener(itemListener);
renderer.box2.addItemListener(itemListener);
}
return editor;
}
}
class CheckBoxNode {
String text;
String img;
boolean selected;
boolean selected2;
public CheckBoxNode(String text, String img, boolean selected, boolean
selected2) {
this.text = text;
this.img = img;
this.selected = selected;
this.selected2 = selected2;
}
public boolean isSelected() {
return selected;
}
public void setSelected(boolean newValue) {
selected = newValue;
}
public boolean isSelected2() {
return selected2;
}
public void setSelected2(boolean selected2) {
this.selected2 = selected2;
}
public String getText() {
return text;
}
public void setText(String newValue) {
text = newValue;
}
public String toString() {
return getClass().getName() + "[" + text + "/" + selected + "/" +
selected2 + "]";
}
}
class NamedVector extends Vector<Object> {
String name;
public NamedVector(String name) {
this.name = name;
}
public NamedVector(String name, Object elements[]) {
this.name = name;
for(int i = 0, n = elements.length; i < n; i++) {
add(elements[i]);
}
}
public String toString() {
return "[" + name + "]";
}
}
gruss
Dejan
mailto:[EMAIL PROTECTED]
Wednesday, May 17, 2006, 4:11:47 PM, you wrote:
JM> Hi Dejan,
JM> It is possible to set a ULCCheckBox as a cell renderer on a Tree node
(see
JM> the first snippet below).
JM> However, at present it is NOT possible to set a ULCCheckBox as a cell
editor
JM> on a Tree node.
JM> I have opened a bug report: https://www.canoo.com/jira/browse/UBA-6920.
JM> However, you could set ULCCheckBox as a renderer and editor on
ULCTableTree
JM> (see second snippet below). So as a work around you can create a single
JM> column ULCTableTree.
JM> Thanks and regards,
JM> Janak
>>-----Original Message-----
>>From: [EMAIL PROTECTED]
>>[mailto:[EMAIL PROTECTED] Behalf Of Dejan Pecar
>>Sent: Monday, May 15, 2006 9:04 PM
>>To: [email protected]
>>Subject: [ULC-developer] checkbox editor and renderer in a ulctree
>>
>>
>>hi,
>>
>>i'm trying to use a checkbox as renderer and editor in a tree.
>>but i think it's not possible with ulc 6.0.4.
>>
>>the renderer was possible to get work with an abbrivation of
>>UICheckBox on the client side.
>>but this seems more than a hack than a proper solution. i needed
>>to override
>>
>>getTableTreeCellRendererComponent(JTableTree tableTree, Object
>>value, boolean selected, boolean hasFocus, boolean expanded,
>>boolean leaf, Object node, int row,
>>
>>on UICheckBox and ignore the value == null case.
>>
>>
>>has anybody an idea how to get this work ? (it seems like nobody
>>has done this before)
>>i would prefer a solution with serverside code only.
>>
>>regards
>> Dejan
>>mailto:[EMAIL PROTECTED]
JM> ---------------------------------
JM> import com.ulcjava.base.application.AbstractApplication;
JM> import com.ulcjava.base.application.IEditorComponent;
JM> import com.ulcjava.base.application.IRendererComponent;
JM> import com.ulcjava.base.application.ULCBoxPane;
JM> import com.ulcjava.base.application.ULCCheckBox;
JM> import com.ulcjava.base.application.ULCFrame;
JM> import com.ulcjava.base.application.ULCTree;
JM> import com.ulcjava.base.application.tree.DefaultMutableTreeNode;
JM> import com.ulcjava.base.application.tree.DefaultTreeModel;
JM> import com.ulcjava.base.application.tree.ITreeCellEditor;
JM> import com.ulcjava.base.application.tree.ITreeCellRenderer;
JM> import com.ulcjava.base.development.DevelopmentRunner;
JM> public class TreeCellRenderSnippet extends AbstractApplication {
JM> public void start() {
JM> final DefaultMutableTreeNode root = new
DefaultMutableTreeNode(
JM> new MyUserObject("root", false));
JM> root.add(new DefaultMutableTreeNode(new
MyUserObject("child 1", true),
JM> true));
JM> root.add(new DefaultMutableTreeNode(new
MyUserObject("child 2", false),
JM> true));
JM> final DefaultMutableTreeNode child3 = new
DefaultMutableTreeNode(
JM> new MyUserObject("child 3", true));
JM> final DefaultMutableTreeNode grandChild1 = new
DefaultMutableTreeNode(
JM> new MyUserObject("grandchild 1", false),
true);
JM> child3.add(grandChild1);
JM> DefaultMutableTreeNode grandChild2 = new
DefaultMutableTreeNode(
JM> new MyUserObject("grandchild 2", true),
true);
JM> child3.add(grandChild2);
JM> root.add(child3);
JM> root.add(new DefaultMutableTreeNode(new
MyUserObject("child 4", false),
JM> true));
JM> ULCBoxPane contentPane = new ULCBoxPane(1, 0);
JM> final ULCTree tree = new ULCTree();
JM> final DefaultTreeModel treeModel = new
DefaultTreeModel(root);
JM> tree.setModel(treeModel);
JM> tree.setCellRenderer(new MyTreeCellRenderer());
JM> tree.setCellEditor(new MyTreeCellEditor());
JM> tree.setEditable(true);
JM> contentPane.add(ULCBoxPane.BOX_EXPAND_EXPAND, tree);
JM> ULCFrame frame = new ULCFrame("TreeNodeLabelSnippet");
JM>
frame.setDefaultCloseOperation(ULCFrame.TERMINATE_ON_CLOSE);
JM> frame.add(contentPane);
JM> frame.setVisible(true);
JM> }
JM> public static void main(String[] args) {
JM>
DevelopmentRunner.setApplicationClass(TreeCellRenderSnippet.class);
JM> DevelopmentRunner.main(args);
JM> }
JM> public static class MyTreeCellRenderer extends ULCCheckBox
implements
JM> ITreeCellRenderer {
JM> public MyTreeCellRenderer() {
JM> }
JM> public IRendererComponent
getTreeCellRendererComponent(ULCTree tree,
JM> Object value, boolean selected, boolean
expanded, boolean leaf,
JM> boolean hasFocus) {
JM> DefaultMutableTreeNode node =
((DefaultMutableTreeNode) value);
JM> MyUserObject element = (MyUserObject)
node.getUserObject();
JM> this.setText(element.getText() +
element.toString());
JM> return this;
JM> }
JM> }
JM> public static class MyTreeCellEditor extends ULCCheckBox
implements
JM> ITreeCellEditor {
JM> public MyTreeCellEditor() {
JM> }
JM> public IEditorComponent
getTreeCellEditorComponent(ULCTree tree,
JM> Object value, boolean selected, boolean
expanded, boolean leaf) {
JM> return this;
JM> }
JM> }
JM> class MyUserObject {
JM> String text;
JM> boolean selected;
JM> public MyUserObject(String text, boolean selected) {
JM> this.text = text;
JM> this.selected = selected;
JM> }
JM> public boolean isSelected() {
JM> return selected;
JM> }
JM> public void setSelected(boolean newValue) {
JM> selected = newValue;
JM> }
JM> public String getText() {
JM> return text;
JM> }
JM> public void setText(String newValue) {
JM> text = newValue;
JM> }
JM> public String toString() {
JM> return Boolean.toString(selected); //"[" + text
+ "/" + selected + "]";
JM> }
JM> }
JM> }
JM> ---------------------------------
JM> import com.ulcjava.base.application.*;
JM> import com.ulcjava.base.application.tabletree.*;
JM> import com.ulcjava.base.application.tree.AbstractTreeModel;
JM> import com.ulcjava.base.application.tree.ITreeCellRenderer;
JM> import com.ulcjava.base.application.util.ULCIcon;
JM> import com.ulcjava.base.application.util.Dimension;
JM> import com.ulcjava.base.development.DevelopmentRunner;
JM> /*
JM> * Copyright C 2000-2003 Canoo Engineering AG, Switzerland.
JM> */
JM> public class TreeCheckBoxTest extends AbstractApplication {
JM> private ULCTableTree fTableTree;
JM> public void start() {
JM> ULCFrame frame = new ULCFrame("TreeCheckBoxTest");
JM> fTableTree = new ULCTableTree(new AbstractTableTreeModel() {
JM> public boolean isCellEditable(Object node, int columnIndex)
{
JM> return true;
JM> }
JM> public void setValueAt(Object value, Object node, int
column) {
JM> }
JM> public int getColumnCount() {
JM> return 1;
JM> }
JM> public Object getValueAt(Object node, int column) {
JM> return Boolean.FALSE;
JM> }
JM> public Object getRoot() {
JM> return "Label";
JM> }
JM> public Object getChild(Object parent, int index) {
JM> return parent + " : " + index;
JM> }
JM> public int getChildCount(Object parent) {
JM> return 3;
JM> }
JM> public boolean isLeaf(Object node) {
JM> return ((String)node).lastIndexOf(":") > 20;
JM> }
JM> public int getIndexOfChild(Object parent, Object child) {
JM> String childString = (String)child;
JM> String parentString = (String)parent;
JM> String indexString =
JM> childString.substring(parentString.length() + 3);
JM> return Integer.parseInt(indexString);
JM> }
JM> });
JM> // make the table tree look like a tree
JM> fTableTree.setTableTreeHeader(null);
JM> fTableTree.setShowGrid(false);
JM> fTableTree.setIntercellSpacing(new Dimension(0, 0));
JM> fTableTree.setShowsRootHandles(true);
JM> // set renderer and editor
JM> fTableTree.getColumnModel().getColumn(0).setCellEditor(new
JM> MyCellEditor(new ULCCheckBox()));
JM> fTableTree.getColumnModel().getColumn(0).setCellRenderer(new
JM> MyTreeCellRenderer());
JM> frame.add(fTableTree);
JM> frame.setVisible(true);
JM> }
JM> public static void main(String[] args) {
JM> DevelopmentRunner.setApplicationClass(TreeCheckBoxTest.class);
JM> DevelopmentRunner.main(args);
JM> }
JM> private static class MyCellEditor extends DefaultCellEditor {
JM> public MyCellEditor(ULCCheckBox checkBox) {
JM> super(checkBox);
JM> }
JM> public IEditorComponent
getTableTreeCellEditorComponent(ULCTableTree
JM> tableTree, Object value, boolean selected, boolean expanded, boolean
leaf,
JM> Object node) {
JM> ULCCheckBox checkBox = (ULCCheckBox)getEditorComponent();
JM> checkBox.setText((String)node);
JM> return checkBox;
JM> }
JM> }
JM> private class MyTreeCellRenderer extends ULCCheckBox implements
JM> ITableTreeCellRenderer {
JM> public IRendererComponent
JM> getTableTreeCellRendererComponent(ULCTableTree tableTree, Object value,
JM> boolean selected, boolean hasFocus, boolean expanded, boolean leaf,
Object
JM> node) {
JM> // adapt the color of the checkbox to the color of the
tabletree
JM> setBackground(selected ? fTableTree.getSelectionBackground()
:
JM> fTableTree.getBackground());
JM> setForeground(selected ? fTableTree.getSelectionForeground()
:
JM> fTableTree.getForeground());
JM> setText((String)node);
JM> return this;
JM> }
JM> }
JM> }
JM> ---------------------------------
1.png
Description: PNG image
2.png
Description: PNG image
3.png
Description: PNG image
4.png
Description: PNG image
5.png
Description: PNG image
6.png
Description: PNG image
