2013-03-13 3 views
1

Я хочу создать функцию поиска для объекта JTable. У меня есть JTextFiled, где я помещаю свой текст в поиск. Я хочу изменить цвета строк и ячеек, которые содержат этот текст. Теперь я застреваю, потому что я понятия не имею, как менять цвет динамически.Динамические строки и ячейки JTable динамически

public class TableSearchCellRenderer extends DefaultTableCellRenderer { 
    String search = ""; 

    public void setSearch(String search) { 
     this.search = search; 
    } 

    @Override 
    public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) { 
     if (table.getValueAt(row, column).equals(search)) { 
      setBackground(Color.green); 
     } 
     return this; 
    } 
} 

Я пробовал что-то вроде этого, но это не работает.

Я пытался позвонить засавить таблицу как таким образом

String selectedTitle = tabbed.getTitleAt(tabbed.getSelectedIndex()); 
JTable table = tabels.get(selectedTitle); 

((TableSearchCellRenderer)table.getDefaultRenderer(String.class)).setSearch(searchField.getText()); 
table.repaint(); 
((AbstractTableModel) table.getModel()).fireTableDataChanged(); 

но безуспешно :(

Не могли бы вы мне помочь?

+2

Для более эффективной помощи следует отправить сообщение [SSCCE] (http://sscce.org/). –

+0

Как вы обрабатываете события изменений из 'searchField'? – Claude

+0

Я думал, что вызов: table.repaint(); или ((AbstractTableModel) table.getModel()). FireTableDataChanged(); может работать (но не надо) – 2013-03-13 12:30:11

ответ

3

Вот рабочая версия вашей функции поиска на основе TableCellRenderer. Одна из проблем, которые вы, возможно, нажали, заключается в том, что, хотя ваша TableModel содержит String, если вы используете DefaultTableModel, она всегда возвращает Object.class для всех данных, и поэтому JTable будет использовать DefaultTableCellRenderer вместо TableSearchCellRenderer.

import java.awt.BorderLayout; 
import java.awt.Color; 
import java.awt.Component; 
import java.util.Random; 
import java.util.Vector; 

import javax.swing.JFrame; 
import javax.swing.JScrollPane; 
import javax.swing.JTable; 
import javax.swing.JTextField; 
import javax.swing.SwingUtilities; 
import javax.swing.UIManager; 
import javax.swing.UnsupportedLookAndFeelException; 
import javax.swing.event.DocumentEvent; 
import javax.swing.event.DocumentListener; 
import javax.swing.table.DefaultTableCellRenderer; 
import javax.swing.table.DefaultTableModel; 

public class TestTable2 { 

    private String search; 

    public String getSearch() { 
     return search; 
    } 

    public void setSearch(String search) { 
     this.search = search; 
    } 

    private class TableSearchRenderer extends DefaultTableCellRenderer { 

     @Override 
     public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) { 
      setBackground(null); 
      Component tableCellRendererComponent = super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column); 
      if (getSearch() != null && getSearch().length() > 0 && value.toString().contains(getSearch())) { 
       setBackground(Color.RED); 
      } 
      return tableCellRendererComponent; 
     } 
    } 

    protected void initUI() { 
     DefaultTableModel model = new DefaultTableModel(); 
     for (int i = 0; i < 5; i++) { 
      model.addColumn("Column " + (i + 1)); 
     } 
     Random random = new Random(); 
     for (int i = 0; i < 200; i++) { 
      Vector<Object> row = new Vector<Object>(); 
      for (int j = 0; j < 40; j++) { 
       row.add(WORDS[random.nextInt(WORDS.length)]); 
      } 
      model.addRow(row); 
     } 
     table = new JTable(model); 
     TableSearchRenderer renderer = new TableSearchRenderer(); 
     table.setDefaultRenderer(Object.class, renderer); 
     textField = new JTextField(30); 
     textField.getDocument().addDocumentListener(new DocumentListener() { 

      @Override 
      public void removeUpdate(DocumentEvent e) { 
       updateSearch(); 
      } 

      @Override 
      public void insertUpdate(DocumentEvent e) { 
       updateSearch(); 
      } 

      @Override 
      public void changedUpdate(DocumentEvent e) { 
       updateSearch(); 
      } 
     }); 
     JFrame frame = new JFrame(TestTable2.class.getSimpleName()); 
     frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
     JScrollPane scrollpane = new JScrollPane(table); 
     scrollpane.setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_ALWAYS); 
     frame.add(scrollpane, BorderLayout.CENTER); 
     frame.add(textField, BorderLayout.NORTH); 
     frame.setSize(1000, 800); 
     frame.setVisible(true); 
    } 

    protected void updateSearch() { 
     setSearch(textField.getText()); 
     table.repaint(); 
    } 

    public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, 
      UnsupportedLookAndFeelException { 
     UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName()); 
     SwingUtilities.invokeLater(new Runnable() { 

      @Override 
      public void run() { 
       new TestTable2().initUI(); 
      } 
     }); 
    } 

    private static final String[] WORDS = { "art", "australia", "baby", "beach", "birthday", "blue", "bw", "california", "canada", "canon", 
      "cat", "chicago", "china", "christmas", "city", "dog", "england", "europe", "family", "festival", "flower", "flowers", "food", 
      "france", "friends", "fun", "germany", "holiday", "india", "italy", "japan", "london", "me", "mexico", "music", "nature", 
      "new", "newyork", "night", "nikon", "nyc", "paris", "park", "party", "people", "portrait", "sanfrancisco", "sky", "snow", 
      "spain", "summer", "sunset", "taiwan", "tokyo", "travel", "trip", "uk", "usa", "vacation", "water", "wedding" }; 
    private JTable table; 
    private JTextField textField; 

} 
+0

Это работает. Спасибо :) Не могли бы вы рассказать мне, что мне нужно изменить также изменить цвет линии на GREEN? – 2013-03-13 13:26:05

+0

@skoczo в вашем рендерере таблицы, вам нужно проверить, содержит ли какое-либо значение строки искомое слово. Если это так, установите backgournd в зеленый цвет, иначе нет. –

1

См. Table Row Rendering. В примере подчеркивается уровень строки на фиксированном слове. Вам нужно будет изменить код, чтобы сделать выделение в слове поиска.

Другой подход - отфильтровать таблицу, чтобы увидеть только строки, содержащие текст, который вы ищете. См. Sorting and Filtering для рабочего примера.

0

Это работает. Я изменяю make renderer.

JTable table = new JTable() { 
       private static final long serialVersionUID = 1L; 

       public Component prepareRenderer(TableCellRenderer renderer, int row, int column) { 
        Component c = super.prepareRenderer(renderer, row, column); 

        **if (column == 0) { 
         for (int i = 0; i < getModel().getColumnCount(); i++) { 
          if (((TableSearchRenderer) getDefaultRenderer(String.class)).getSearch().length() > 0 && ((TableSearchRenderer) getDefaultRenderer(String.class)).getSearch().toLowerCase().equals(getModel().getValueAt(row, i).toString().toLowerCase())) 
           ((TableSearchRenderer) getDefaultRenderer(String.class)).getRows().add(row); 
         } 
        }** 

        if (((TableSearchRenderer) getDefaultRenderer(String.class)).getRows().contains(row) && c.getBackground() != Color.RED) { 
         c.setBackground(Color.GREEN); 
        } 

        return c; 
       } 
      }; 
Смежные вопросы