1

これは私のレンダラーです

class tblCalendarRenderer extends JTextArea implements TableCellRenderer {

    JTextArea textField;

    public tblCalendarRenderer() {
        textField = new JTextArea();
    }

    public Component getTableCellRendererComponent(JTable table,
            Object value, boolean selected, boolean focused, int row,
            int column) {
        textField.setText(value == null ? "" : value.toString());
        textField.setLineWrap(true);
        textField.setWrapStyleWord(true);

        if (column == 0 || column == 6) { // Week-end
            textField.setBackground(new Color(255, 220, 220));
        } else { // Week
            textField.setBackground(new Color(255, 255, 255));
        }
        if (row % 2 == 0) {
            if (value != null) {
                if (Integer.parseInt(value.toString()) == realDay
                        && currentMonth == realMonth
                        && currentYear == realYear) { // Today
                    textField.setBackground(new Color(220, 220, 255));
                }
            }
            textField.setFont(new java.awt.Font("Dialog",
                    java.awt.Font.BOLD, 11));
        } else {
            textField.setFont(new java.awt.Font("Dialog",
                    java.awt.Font.BOLD, 12));
        }
        if (selected && row % 2 != 0) {
            textField.setBackground(Color.LIGHT_GRAY);
            textField.setForeground(Color.black);
        }

        textField.setBorder(null);
        return textField;
    }
}

これは、jTextArea の行を強調表示するために試したコードです。どうすればjTableに追加できますか? 私は追加しようとしました textField.addCaretListener(new ExampleCaretListener()); ただし、jTable セル全体が選択されます。

    class ExampleCaretListener implements CaretListener {

    public void caretUpdate(CaretEvent e) {
        Color HILIT_COLOR = Color.LIGHT_GRAY;
        final Highlighter.HighlightPainter painter;
        painter = new DefaultHighlighter.DefaultHighlightPainter(
                HILIT_COLOR);
        JTextArea textField = (JTextArea) e.getSource();
        String lineText = "";
        try {
            int dot = e.getDot();
            int rowStart = Utilities.getRowStart(textField, dot);
            int rowEnd = Utilities.getRowEnd(textField, dot);
            System.out.println(dot + " " + rowStart + " " + rowEnd);
            lineText = textField.getText(rowStart, (rowEnd - rowStart));
            textField.getHighlighter().removeAllHighlights();
            textField.getHighlighter().addHighlight(rowStart, rowEnd,
                    painter);
        } catch (BadLocationException ex) {
            System.out.println(ex);
        }

    }

}
4

2 に答える 2

0

各セルの内容は日付番号だと思いますので、何をしようとしているのか、実際には単一のセルに複数の行があるのか​​ わかりません。行全体ではなく、表のセルを選択するということでしたか? それが意図したものである場合は、テーブルの行/列選択モデルを変更することで実行できます。そうでない場合は、問題を絞り込み、完全な (クリーンな) ソース コードを提供してください。

編集:

オイゲナーが言ったように、レンダラーはセルの値に基づいてセル内に JTextArea を単純に描画します。ただし、セルの状態を表す独自のカスタム モデルを作成し (たとえば、String といくつかの追加データを含む MyModel を使用できる単一の String 値を持つ代わりに)、そのモデルに基づいてセルをレンダリングすることができます。例: マウス クリックを検出し (マウス リスナーを Jtable にアタッチ)、そのモデルの状態を変更できます。特定のセル値のマウス位置に基づいて、選択の開始と選択の終了を更新します。getCellRenderer 内で、選択開始データと選択終了データを含むオブジェクト タイプ (MyModel) に値をキャストし、それを使用してテキスト領域をレンダリングします。

セルをクリックすると選択範囲が増えるサンプル コードを次に示します (クリックしたマウスの位置に基づいて適切なキャレット位置を設定するように変更する必要があります)。

これをセル レンダラーに挿入します。

CellValue myValue = (CellValue)value;
HighlightPainter painter = new DefaultHighlighter.DefaultHighlightPainter(
        Color.green);
textField.getHighlighter().removeAllHighlights();
try {
    textField.getHighlighter().addHighlight(myValue.highlightStart, myValue.highlightEnd, painter);
} catch (BadLocationException e) {
    System.out.println("Miss");
}

サンプル MyModel は次のとおりです。

public class MyModel extends AbstractTableModel {
    class CellValue {
        String value;
        int highlightStart;
        int highlightEnd;

        CellValue(String val) {
            this.value = val;
        }

        @Override
        public String toString() {
            return value;
        }
    }

    CellValue[][] values = new CellValue[2][7];

    public MyModel() {
        for(int i = 0; i < 2; i++) {
            for(int j=0; j < 7; j++) {
                values[i][j] = new CellValue(i + ":" + j);
            }
        }
    }

    @Override
    public int getColumnCount() {
        return 7;
    }

    @Override
    public int getRowCount() {
        return 2;
    }

    @Override
    public Object getValueAt(int rowIndex, int columnIndex) {
        return values[rowIndex][columnIndex];
    }
}

ここにメインクラスがあります:

public class Main {
    public static void main(String[] args) {
        JFrame frame = new JFrame();
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.setSize(new Dimension(500,500));

        final JTable table = new JTable(new MyModel());
        for(int i =0; i < 7; i++) {
            table.getColumnModel().getColumn(i).setCellRenderer(new tblCalendarRenderer());
        }

        table.addMouseListener(new MouseAdapter() {
            @Override
            public void mouseClicked(MouseEvent e) {
                int row = table.rowAtPoint(e.getPoint());
                int column = table.columnAtPoint(e.getPoint());

                Object obj = table.getValueAt(row, column);
                System.out.println("value " + obj);
                CellValue cellValue = (CellValue)obj;
                cellValue.highlightEnd++;
                table.repaint();
            }
        });
        table.setRowHeight(50);
        JScrollPane scp = new JScrollPane(table);
        frame.add(scp);
        frame.setVisible(true);
    }
}
于 2010-07-03T13:51:24.667 に答える
0

レンダラーは、セル内の JTextArea を画像として描画するだけです。したがって、テキストの強調表示は機能しません。IMO で機能する唯一の方法は、レンダラーに JEditorPane をテキスト スタイルで使用して、その適切な部分を強調表示することです。

詳細については、http://java.sun.com/docs/books/tutorial/uiswing/components/editorpane.html#recapを参照してください。

于 2010-07-03T13:54:02.807 に答える