Настройка Java JTable Ширина столбца

У меня есть JTable, в котором я устанавливаю размер столбца следующим образом:

table.setAutoResizeMode(JTable.AUTO_RESIZE_OFF);
table.getColumnModel().getColumn(0).setPreferredWidth(27);
table.getColumnModel().getColumn(1).setPreferredWidth(120);
table.getColumnModel().getColumn(2).setPreferredWidth(100);
table.getColumnModel().getColumn(3).setPreferredWidth(90);
table.getColumnModel().getColumn(4).setPreferredWidth(90);
table.getColumnModel().getColumn(6).setPreferredWidth(120);
table.getColumnModel().getColumn(7).setPreferredWidth(100);
table.getColumnModel().getColumn(8).setPreferredWidth(95);
table.getColumnModel().getColumn(9).setPreferredWidth(40);
table.getColumnModel().getColumn(10).setPreferredWidth(400);

Это работает нормально, но когда таблица развернута, я получаю пустое пространство справа от последнего столбца. Можно ли изменить размер последнего столбца до конца окна при изменении размера?

я нашелAUTO_RESIZE_LAST_COLUMN собственность в документах, но это не работает.

Редактировать:JTable находится вJScrollPane его предпочтительный размер установлен.

Ответы на вопрос(7)

змените значение цикла для вашего кода.

TableColumn column = null;
        for (int i = 0; i < 3; i++) {
            column = table.getColumnModel().getColumn(i);
            if (i == 0) 
                column.setMaxWidth(10);
            if (i == 2)
                column.setMaxWidth(50);
        }

JTable.AUTO_RESIZE_OFFтаблица не изменит размер столбцов для вас, поэтому примет ваши предпочтительные настройки. Если ваша цель состоит в том, чтобы столбцы по умолчанию соответствовали вашему предпочтительному размеру, за исключением того, что последний столбец заполнял остальную часть панели, у вас есть возможность использоватьJTable.AUTO_RESIZE_LAST_COLUMN autoResizeMode, но он может быть наиболее эффективным при использовании сTableColumn.setMaxWidth() вместо TableColumn.setPreferredWidth () для всех, кроме последнего столбца.

Как только вы убедитесь, чтоAUTO_RESIZE_LAST_COLUMN действительно работает, вы можете поэкспериментировать с комбинациейTableColumn.setMaxWidth() а такжеTableColumn.setMinWidth()

 akf05 июн. 2009 г., 06:36
чтобы добавить к моему последнему комментарию: используйте TableColumn.setMinWidth () для каждого столбца в вашей таблице, включая последний столбец.
 Hamza Yerlikaya05 июн. 2009 г., 06:11
Когда используется AUTO_RESIZE_LAST_COLUMN, размер таблицы изменяется в соответствии с областью прокрутки. Моя цель состоит в том, чтобы таблица имела определенный минимальный размер, но увеличивала ее, если она больше моего минимального размера.
 Hamza Yerlikaya05 июн. 2009 г., 08:50
установка минимальной и максимальной ширины решила проблему, но теперь полосы прокрутки отсутствуют.
 akf05 июн. 2009 г., 06:35
Вы можете иметь это поведение, если вы используете TableColumn.setMinWidth () вместо TableColumn.setMaxWidth ().

setMinWidth(400) в последнем столбцевместо изsetPreferredWidth(400)?

В JavaDoc дляJTable, прочитайте документы дляdoLayout() очень осторожно. Вот несколько битов выбора:

Когда метод вызывается в результате изменения размера окружающего окна, resizingColumn имеет значение null. Это означает, что изменение размера произошло «вне» JTable, и изменение - или «дельта» - должно распространяться на все столбцы независимо от режима автоматического изменения размера этого JTable.

Это может быть почемуAUTO_RESIZE_LAST_COLUMN не помог тебе

Примечание. Когда JTable корректирует ширину столбцов, он полностью учитывает их минимальное и максимальное значения.

Это говорит о том, что вы можете установить Min == Max для всех столбцов, кроме последних, затем установить Min = Preferred для последнего столбца и либо не устанавливать Max, либо установить очень большое значение для Max.

 Eddie05 июн. 2009 г., 06:26
Удалить строку table.setAutoResizeMode (JTable.AUTO_RESIZE_OFF); Это может предотвратить изменение размера, которое вы хотите.
 Hamza Yerlikaya05 июн. 2009 г., 05:48
setMinWidth (400) все еще заставляет право таблицы быть пустым
 Hamza Yerlikaya05 июн. 2009 г., 06:07
изменил это, но без эффекта.
 Brian Knoblauch13 дек. 2011 г., 19:17
Убедитесь, что вы делаете вызов setMinWidthпосле применение модели стола ... Это меня на некоторое время сбило с толку.
 Eddie05 июн. 2009 г., 06:03
Попробуйте добавить setMaxWidth (10000), чтобы увидеть, если это имеет значение.
fireTableStructureChanged();

по умолчанию будет изменять размер ! Если этот метод вызывается где-то в вашем коде ПОСЛЕ того, как вы установили свойства изменения размера столбца, все ваши настройки будут сброшены. Этот побочный эффект может произойти косвенно. F.E. как следствие изменения связанной модели данных способом, вызываемым этим методом, после установки свойств.

Используйте этот метод

public static void setColumnWidths(JTable table, int... widths) {
    TableColumnModel columnModel = table.getColumnModel();
    for (int i = 0; i < widths.length; i++) {
        if (i < columnModel.getColumnCount()) {
            columnModel.getColumn(i).setMaxWidth(widths[i]);
        }
        else break;
    }

Или продлитьJTable класс:

public class Table extends JTable {
    public void setColumnWidths(int... widths) {
        for (int i = 0; i < widths.length; i++) {
            if (i < columnModel.getColumnCount()) {
                columnModel.getColumn(i).setMaxWidth(widths[i]);
            }
            else break;
        }
    }
}

А потом

table.setColumnWidths(30, 150, 100, 100);

javax.swing.JXTableи теперь мне жаль, что я не заглянул в первый раз :)) Предлагаю перейти по ссылке

У меня было решение для той же проблемы: (но я предлагаю вам перейти по ссылке выше) При изменении размера таблицы масштабируйте ширину столбцов таблицы до общей ширины текущей таблицы. Для этого я использую глобальный массив целых значений (относительной) ширины столбца):

private int[] columnWidths=null;

Я использую эту функцию, чтобы установить ширину столбцов таблицы:

public void setColumnWidths(int[] widths){
    int nrCols=table.getModel().getColumnCount();
    if(nrCols==0||widths==null){
        return;
    }
    this.columnWidths=widths.clone();

    //current width of the table:
    int totalWidth=table.getWidth();

    int totalWidthRequested=0;
    int nrRequestedWidths=columnWidths.length;
    int defaultWidth=(int)Math.floor((double)totalWidth/(double)nrCols);

    for(int col=0;col<nrCols;col++){
        int width = 0;
        if(columnWidths.length>col){
            width=columnWidths[col];
        }
        totalWidthRequested+=width;
    }
    //Note: for the not defined columns: use the defaultWidth
    if(nrRequestedWidths<nrCols){
        log.fine("Setting column widths: nr of columns do not match column widths requested");
        totalWidthRequested+=((nrCols-nrRequestedWidths)*defaultWidth);
    }
    //calculate the scale for the column width
    double factor=(double)totalWidth/(double)totalWidthRequested;

    for(int col=0;col<nrCols;col++){
        int width = defaultWidth;
        if(columnWidths.length>col){
            //scale the requested width to the current table width
            width=(int)Math.floor(factor*(double)columnWidths[col]);
        }
        table.getColumnModel().getColumn(col).setPreferredWidth(width);
        table.getColumnModel().getColumn(col).setWidth(width);
    }

}

При настройке данных я звоню:

    setColumnWidths(this.columnWidths);

и при изменении я вызываю ComponentListener, установленный для родительского элемента таблицы (в моем случае JScrollPane, который является контейнером моей таблицы):

public void componentResized(ComponentEvent componentEvent) {
    this.setColumnWidths(this.columnWidths);
}

обратите внимание, что таблица JTable также является глобальной:

private JTable table;

И вот я установил слушателя:

    scrollPane=new JScrollPane(table);
    scrollPane.addComponentListener(this);
 michel.iamit12 дек. 2011 г., 21:05
Вы были правы, посмотрите мое замечание поверх моего ответа, я проголосовал за ваше замечание!
 Solostaran1408 нояб. 2013 г., 18:10
По крайней мере, это было полезно для меня, я использовал этот подход для моего случая с принципом веса столбца.
 michel.iamit12 дек. 2011 г., 20:55
Я знаю, что это не реагирует на изменение пользователем ширины таблицы вручную, таким образом, это взлом ... но опять же: это лучше, чем предложено выше. Но вы сделали меня любопытным JXTable .... Я посмотрю там! (и приятно снова зайти к вам на столик :))
 kleopatra12 дек. 2011 г., 20:57
пожалуйста :-)
 kleopatra12 дек. 2011 г., 20:51
насколько я понимаю, это (очень хрупкий) взлом: он не обновляется при изменении пользователем ширины столбца. Опять же, я бы посоветовал вам заглянуть в исходный код JXTable - у него есть дополнительное свойство horizontalScroll, которое запускает заполнение доступной ширины, если сумма префиксов столбцов меньше текущей ширины, и в противном случае показывает горизонтальную полосу прокрутки

JTable.AUTO_RESIZE_LAST_COLUMN определяется как«Во время всех операций изменения размера применять корректировки только к последнему столбцу» Это означает, что вы должны установитьautoresizemode в конце вашего кодаиначе setPreferredWidth () ни на что не повлияет!

Так что в вашем случае это будет правильный путь:

table.getColumnModel().getColumn(0).setPreferredWidth(27);
table.getColumnModel().getColumn(1).setPreferredWidth(120);
table.getColumnModel().getColumn(2).setPreferredWidth(100);
table.getColumnModel().getColumn(3).setPreferredWidth(90);
table.getColumnModel().getColumn(4).setPreferredWidth(90);
table.getColumnModel().getColumn(6).setPreferredWidth(120);
table.getColumnModel().getColumn(7).setPreferredWidth(100);
table.getColumnModel().getColumn(8).setPreferredWidth(95);
table.getColumnModel().getColumn(9).setPreferredWidth(40);
table.getColumnModel().getColumn(10).setPreferredWidth(400);
table.setAutoResizeMode(JTable.AUTO_RESIZE_LAST_COLUMN);
 sg55215 янв. 2016 г., 15:24
Спасибо за четкое объяснение и пример.

Ваш ответ на вопрос