14

サイズ変更可能な列を使用してJScrollPane内にJTableを作成する必要があります(ユーザーが列幅を増やすと、水平スクロールバーが表示されます)。このために私は使用していますtable.setAutoResizeMode(JTable.AUTO_RESIZE_OFF);。また、ビューポートがテーブル全体を含むのに十分な幅である場合、列はビューポートの幅を満たすように引き伸ばされる必要があります。これを実現するためにgetScrollableTracksViewportWidth()、次のようにJTableクラスのオーバーライドメソッドを使用します。

@Override
public boolean getScrollableTracksViewportWidth() {
    return getPreferredSize().width < getParent().getWidth();
}

このアプローチは、1つのことを除いて、うまく機能します。最初に列のサイズを変更しようとすると、開始位置に独自の幅が返されます。列のサイズをすばやく変更してマウステーブルを離すと、引き続き正常に機能します。それで、そのような行動の理由は何ですか?getScrollableTracksViewportWidth()falseを返してもテーブルのサイズを変更しようとするのはなぜですか?または、おそらく、そのようなサイズ変更モードを実装するためのより良いソリューションを提案できますか?

以下は、上記の問題の簡単な実例です。

import javax.swing.*;

public class TestTable {
    private static Object[][] data = new Object[][] {
            { "a", "b", "c" },
            { "d", "e", "f" }
    };
    private static Object[] colNames = new Object[] { "1", "2", "3" };

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                JTable table = new JTable(data, colNames) {
                    @Override
                    public boolean getScrollableTracksViewportWidth() {
                        return getPreferredSize().width < getParent().getWidth();
                    }
                };
                table.setAutoResizeMode(JTable.AUTO_RESIZE_OFF);

                JFrame frame = new JFrame();
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.add(new JScrollPane(table));
                frame.pack();
                frame.setVisible(true);
            }
        });
    }
}
4

1 に答える 1

18

doLayout()水平スクロールバーが表示されていないときに列のサイズを大きくしようとすると、デフォルトロジックが機能していないように見えたので、デフォルトロジックを削除し、列の幅を調整せずに受け入れました。 。

import javax.swing.*;
import javax.swing.table.*;

public class TestTable {
    private static Object[][] data = new Object[][] {
            { "a", "b", "c" },
            { "d", "e", "f" }
    };
    private static Object[] colNames = new Object[] { "1", "2", "3" };

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                JTable table = new JTable(data, colNames)
                {
                    @Override
                    public boolean getScrollableTracksViewportWidth()
                    {
                        return getPreferredSize().width < getParent().getWidth();
                    }

                    @Override
                    public void doLayout()
                    {
                        TableColumn resizingColumn = null;

                        if (tableHeader != null)
                            resizingColumn = tableHeader.getResizingColumn();

                        //  Viewport size changed. May need to increase columns widths

                        if (resizingColumn == null)
                        {
                            setAutoResizeMode(JTable.AUTO_RESIZE_ALL_COLUMNS);
                            super.doLayout();
                        }

                        //  Specific column resized. Reset preferred widths

                        else
                        {
                            TableColumnModel tcm = getColumnModel();

                            for (int i = 0; i < tcm.getColumnCount(); i++)
                            {
                                TableColumn tc = tcm.getColumn(i);
                                tc.setPreferredWidth( tc.getWidth() );
                            }

                            // Columns don't fill the viewport, invoke default layout

                            if (tcm.getTotalColumnWidth() < getParent().getWidth())
                                setAutoResizeMode(JTable.AUTO_RESIZE_ALL_COLUMNS);
                                super.doLayout();
                        }

                        setAutoResizeMode(JTable.AUTO_RESIZE_OFF);
                    }

                };
                table.setAutoResizeMode(JTable.AUTO_RESIZE_OFF);

                JFrame frame = new JFrame();
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.add(new JScrollPane(table));
                frame.pack();
                frame.setVisible(true);
            }
        });
    }
}

AUTO_RESIZE_ALL_COLUMNSを使用するように編集されました。

于 2013-03-06T06:50:10.230 に答える