[JAVA][SWING]JTable Row Header Example
위 이미지와 같은 이쁜놈을 만들고 싶었다
JTable 로는 왼편 1 ~ 를 만들어주는 방법을 몰랐다.
그래서 찾아본 검색 결과
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 | // Example from http://www.crionics.com/products/opensource/faq/swing_ex/SwingExamples.html /* (swing1.1beta3) */ import java.awt.BorderLayout; import java.awt.Component; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; import javax.swing.AbstractListModel; import javax.swing.JFrame; import javax.swing.JLabel; import javax.swing.JList; import javax.swing.JScrollPane; import javax.swing.JTable; import javax.swing.ListCellRenderer; import javax.swing.ListModel; import javax.swing.UIManager; import javax.swing.table.DefaultTableModel; import javax.swing.table.JTableHeader; /** * @version 1.0 11/09/98 */ class RowHeaderRenderer extends JLabel implements ListCellRenderer { RowHeaderRenderer(JTable table) { JTableHeader header = table.getTableHeader(); setOpaque(true); setBorder(UIManager.getBorder("TableHeader.cellBorder")); setHorizontalAlignment(CENTER); setForeground(header.getForeground()); setBackground(header.getBackground()); setFont(header.getFont()); } public Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) { setText((value == null) ? "" : value.toString()); return this; } } public class RowHeaderExample extends JFrame { public RowHeaderExample() { super("Row Header Example"); setSize(300, 150); ListModel lm = new AbstractListModel() { String headers[] = { "a", "2", "c", "d", "e", "f", "g", "h", "i" }; public int getSize() { return headers.length; } public Object getElementAt(int index) { return headers[index]; } }; DefaultTableModel dm = new DefaultTableModel(lm.getSize(), 100); JTable table = new JTable(dm); table.setAutoResizeMode(JTable.AUTO_RESIZE_OFF); JList rowHeader = new JList(lm); rowHeader.setFixedCellWidth(50); rowHeader.setFixedCellHeight(table.getRowHeight() + table.getRowMargin()); // + table.getIntercellSpacing().height); rowHeader.setCellRenderer(new RowHeaderRenderer(table)); JScrollPane scroll = new JScrollPane(table); scroll.setRowHeaderView(rowHeader); getContentPane().add(scroll, BorderLayout.CENTER); } public static void main(String[] args) { RowHeaderExample framwlrmae = new RowHeaderExample(); framwlrmae.addWindowListener(new WindowAdapter() { public void windowClosing(WindowEvent e) { System.exit(0); } }); framwlrmae.setVisible(true); } } | cs |
출처 : http://www.java2s.com/Code/Java/Swing-Components/TableRowHeaderExample.htm
출력 결과는
위 이미지에서 보다싶이 왼편에 숫자대신 a b c d 찍어주긴 하지만 라인이 딱딱 맞아 떨어지지 않음을 확인할 수 있다
즉 ... 죄송하지만 어설퍼 보인다는것 대중성을 고려한다면 ... X
조금더 조회해보니
위 이미지와 같은 결과가 나오는 소스가 있었으니
출처는 : https://tips4java.wordpress.com/2008/11/18/row-number-table/
하지만 소스는
RowNumberTable.java
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 | import java.awt.*; import java.awt.event.*; import java.beans.*; import javax.swing.*; import javax.swing.event.*; import javax.swing.table.*; /* * Use a JTable as a renderer for row numbers of a given main table. * This table must be added to the row header of the scrollpane that * contains the main table. */ public class RowNumberTable extends JTable implements ChangeListener, PropertyChangeListener, TableModelListener { private JTable main; public RowNumberTable(JTable table) { main = table; main.addPropertyChangeListener( this ); main.getModel().addTableModelListener( this ); setFocusable( false ); setAutoCreateColumnsFromModel( false ); setSelectionModel( main.getSelectionModel() ); TableColumn column = new TableColumn(); column.setHeaderValue(" "); addColumn( column ); column.setCellRenderer(new RowNumberRenderer()); getColumnModel().getColumn(0).setPreferredWidth(50); setPreferredScrollableViewportSize(getPreferredSize()); } @Override public void addNotify() { super.addNotify(); Component c = getParent(); // Keep scrolling of the row table in sync with the main table. if (c instanceof JViewport) { JViewport viewport = (JViewport)c; viewport.addChangeListener( this ); } } /* * Delegate method to main table */ @Override public int getRowCount() { return main.getRowCount(); } @Override public int getRowHeight(int row) { int rowHeight = main.getRowHeight(row); if (rowHeight != super.getRowHeight(row)) { super.setRowHeight(row, rowHeight); } return rowHeight; } /* * No model is being used for this table so just use the row number * as the value of the cell. */ @Override public Object getValueAt(int row, int column) { return Integer.toString(row + 1); } /* * Don't edit data in the main TableModel by mistake */ @Override public boolean isCellEditable(int row, int column) { return false; } /* * Do nothing since the table ignores the model */ @Override public void setValueAt(Object value, int row, int column) {} // // Implement the ChangeListener // public void stateChanged(ChangeEvent e) { // Keep the scrolling of the row table in sync with main table JViewport viewport = (JViewport) e.getSource(); JScrollPane scrollPane = (JScrollPane)viewport.getParent(); scrollPane.getVerticalScrollBar().setValue(viewport.getViewPosition().y); } // // Implement the PropertyChangeListener // public void propertyChange(PropertyChangeEvent e) { // Keep the row table in sync with the main table if ("selectionModel".equals(e.getPropertyName())) { setSelectionModel( main.getSelectionModel() ); } if ("rowHeight".equals(e.getPropertyName())) { repaint(); } if ("model".equals(e.getPropertyName())) { main.getModel().addTableModelListener( this ); revalidate(); } } // // Implement the TableModelListener // @Override public void tableChanged(TableModelEvent e) { revalidate(); } /* * Attempt to mimic the table header renderer */ private static class RowNumberRenderer extends DefaultTableCellRenderer { public RowNumberRenderer() { setHorizontalAlignment(JLabel.CENTER); } public Component getTableCellRendererComponent( JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) { if (table != null) { JTableHeader header = table.getTableHeader(); if (header != null) { setForeground(header.getForeground()); setBackground(header.getBackground()); setFont(header.getFont()); } } if (isSelected) { setFont( getFont().deriveFont(Font.BOLD) ); } setText((value == null) ? "" : value.toString()); setBorder(UIManager.getBorder("TableHeader.cellBorder")); return this; } } } | cs |
위와 같이 달랑 public class RowNumberTable extends JTable
JTable 을 상속 받은놈이 전부였다.
You can use the RowNumberTable in your program with code like the following…
다음과 같은 코드를 사용하여 프로그램에서 RowNumberTable을 사용할 수 있습니다.
1 2 3 4 5 6 | JTable mainTable = new JTable(...); JScrollPane scrollPane = new JScrollPane(mainTable); JTable rowTable = new RowNumberTable(mainTable); scrollPane.setRowHeaderView(rowTable); scrollPane.setCorner(JScrollPane.UPPER_LEFT_CORNER, rowTable.getTableHeader()); | cs |
which will generate a table looking something like…
테이블을 생성합니다.
구글 번역기 돌리니 저런식으로 어케 어케 쓰라는데
지금 보니 소스가 보이긴하는데
당시엔 뭔소린지 당췌 몰라서 1시간가량 삽질하다가 소스를 첨부한다
RowNumberTable.java 과는 별개로 class 를 하나더 만들었다
RowHeaderExample.java
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 | // Example from http://www.crionics.com/products/opensource/faq/swing_ex/SwingExamples.html /* (swing1.1beta3) */ import java.awt.BorderLayout; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; import javax.swing.AbstractListModel; import javax.swing.JFrame; import javax.swing.JList; import javax.swing.JScrollPane; import javax.swing.JTable; import javax.swing.ListModel; import javax.swing.table.DefaultTableModel; public class RowHeaderExample extends JFrame { public RowHeaderExample() { super("Row Header Example"); setSize(300, 150); ListModel lm = new AbstractListModel() { String headers[] = { "a", "2", "c", "d", "e", "f", "g", "h", "i" }; public int getSize() { return headers.length; } public Object getElementAt(int index) { return headers[index]; } }; String colNames[] = {"A","B","C","D","E","F","G","H","I","J"}; Object data[][]; data = new Object[10][10]; for(int i=0 ; i<10 ; i++) { for(int j=0 ; j<10 ; j++) { data[i][j] = String.valueOf(i) + " " + String.valueOf(j); } } DefaultTableModel dm = new DefaultTableModel(data, colNames) { public boolean isCellEditable(int rowIndex, int mColindex) { return false; } }; JTable table = new JTable(dm); table.setAutoResizeMode(JTable.AUTO_RESIZE_OFF); RowNumberTable rowNumberTable = new RowNumberTable(table); // JList rowHeader = new JList(lm); // rowHeader.setFixedCellWidth(50); // // rowHeader.setFixedCellHeight(table.getRowHeight() + table.getRowMargin()); // + table.getIntercellSpacing().height); //rowHeader.setCellRenderer(new RowHeaderRenderer(table)); JScrollPane scroll = new JScrollPane(table); scroll.setRowHeaderView(rowNumberTable); getContentPane().add(scroll, BorderLayout.CENTER); } public static void main(String[] args) { RowHeaderExample framwlrmae = new RowHeaderExample(); framwlrmae.addWindowListener(new WindowAdapter() { public void windowClosing(WindowEvent e) { System.exit(0); } }); framwlrmae.setVisible(true); } } | cs |
뭐 ... 불필요한 소스도 있고 해서 정리가 필요하다
가장 큰 문제는 문제는
https://docs.oracle.com/javase/7/docs/api/javax/swing/table/DefaultTableModel.html
여기도 나와있듯이
아 18 나는 data 만 넘겨주고 싶은데
인자로 해더도 받아쳐먹고 있다
걍 count 만 넘기면 안이런다
아주 깔끔하게 엑셀마냥 A, B, C ... 찍어준다
아 근데 왜 data 를 넣어주면 안찍어주냐고!
해서 ...
하나 만들어야 할듯 하다
어쩨꺼나 이건 다음 숙제 ~
끝