Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>View-based filtering is definitely the way to go. You can use something like the example I've coded below. Another common practice when filtering trees is to switch to a list view when filtering a tree, since the list won't require you to show hidden nodes whose descendants need to be shown.</p> <p>This is absolutely horrendous code (I tried to cut every corner possible in whipping it up just now), but it should be enough to get you started. Just type your query in the search box and press Enter, and it'll filter the JTree's default model. (FYI, the first 90 lines are just generated boilerplate and layout code.)</p> <pre><code>package com.example.tree; import java.awt.BorderLayout; public class FilteredJTreeExample extends JFrame { private JPanel contentPane; private JTextField textField; /** * Launch the application. */ public static void main(String[] args) { EventQueue.invokeLater(new Runnable() { public void run() { try { FilteredJTreeExample frame = new FilteredJTreeExample(); frame.setVisible(true); } catch (Exception e) { e.printStackTrace(); } } }); } /** * Create the frame. */ public FilteredJTreeExample() { setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); setBounds(100, 100, 450, 300); contentPane = new JPanel(); contentPane.setBorder(new EmptyBorder(5, 5, 5, 5)); contentPane.setLayout(new BorderLayout(0, 0)); setContentPane(contentPane); JPanel panel = new JPanel(); contentPane.add(panel, BorderLayout.NORTH); GridBagLayout gbl_panel = new GridBagLayout(); gbl_panel.columnWidths = new int[]{34, 116, 0}; gbl_panel.rowHeights = new int[]{22, 0}; gbl_panel.columnWeights = new double[]{0.0, 1.0, Double.MIN_VALUE}; gbl_panel.rowWeights = new double[]{0.0, Double.MIN_VALUE}; panel.setLayout(gbl_panel); JLabel lblFilter = new JLabel("Filter:"); GridBagConstraints gbc_lblFilter = new GridBagConstraints(); gbc_lblFilter.anchor = GridBagConstraints.WEST; gbc_lblFilter.insets = new Insets(0, 0, 0, 5); gbc_lblFilter.gridx = 0; gbc_lblFilter.gridy = 0; panel.add(lblFilter, gbc_lblFilter); JScrollPane scrollPane = new JScrollPane(); contentPane.add(scrollPane, BorderLayout.CENTER); final JTree tree = new JTree(); scrollPane.setViewportView(tree); textField = new JTextField(); GridBagConstraints gbc_textField = new GridBagConstraints(); gbc_textField.fill = GridBagConstraints.HORIZONTAL; gbc_textField.anchor = GridBagConstraints.NORTH; gbc_textField.gridx = 1; gbc_textField.gridy = 0; panel.add(textField, gbc_textField); textField.setColumns(10); textField.addActionListener(new ActionListener() { @Override public void actionPerformed(ActionEvent evt) { TreeModel model = tree.getModel(); tree.setModel(null); tree.setModel(model); } }); tree.setCellRenderer(new DefaultTreeCellRenderer() { private JLabel lblNull = new JLabel(); @Override public Component getTreeCellRendererComponent(JTree tree, Object value, boolean arg2, boolean arg3, boolean arg4, int arg5, boolean arg6) { Component c = super.getTreeCellRendererComponent(tree, value, arg2, arg3, arg4, arg5, arg6); DefaultMutableTreeNode node = (DefaultMutableTreeNode) value; if (matchesFilter(node)) { c.setForeground(Color.BLACK); return c; } else if (containsMatchingChild(node)) { c.setForeground(Color.GRAY); return c; } else { return lblNull; } } private boolean matchesFilter(DefaultMutableTreeNode node) { return node.toString().contains(textField.getText()); } private boolean containsMatchingChild(DefaultMutableTreeNode node) { Enumeration&lt;DefaultMutableTreeNode&gt; e = node.breadthFirstEnumeration(); while (e.hasMoreElements()) { if (matchesFilter(e.nextElement())) { return true; } } return false; } }); } } </code></pre> <p>When you implement it for real, you'll probably want to create your own TreeNode and TreeCellRenderer implementations, use a less stupid method for triggering an update, and follow MVC separation. Note that the "hidden" nodes are still rendered, but they're so small that you can't see them. If you use the arrow keys to navigate the tree, though, you'll notice that they're still there. If you just need something that works, this might be good enough.</p> <p><img src="https://i.stack.imgur.com/W6x1T.png" alt="Filtered tree (windows)"></p> <p><strong>Edit</strong></p> <p>Here are screenshots of the unfiltered and filtered version of the tree in Mac OS, showing that the whitespace is visible in Mac OS:</p> <p><img src="https://i.stack.imgur.com/5dOvq.png" alt="Unfiltered tree"><img src="https://i.stack.imgur.com/iAuP5.png" alt="Filtered tree"></p>
    singulars
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. VO
      singulars
      1. This table or related slice is empty.
    2. VO
      singulars
      1. This table or related slice is empty.
    3. VO
      singulars
      1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload