2012-10-01 2 views
2

나는 사용자 지정 선택 모드를 포함하는 사용자 지정 ListSelectionModelJTable을 가지고 있습니다. 이 선택 모드는 선택이 한 행에서만 이루어 지지만 여러 개의 셀을 사용하도록합니다. 사용자가 표에서 일부 셀을 클릭하면 선택한 셀이 모두 첫 번째 선택된 셀과 같은 행에 있습니다.JTable의 선행 선택 셀에 메시지를 표시하는 방법은 무엇입니까?

이제 선행 선택 셀의 오른쪽 상단 모서리 위에 작은 메시지를 작성하여 일부 데이터, 즉 선택한 셀의 수를 표시하고 싶습니다. 선행 선택이 변경되면 메시지를 이동해야합니다.

하지만 어떻게해야합니까? 사용자가 테이블을 클릭하고 셀 위로 마우스를 가져 가면 셀을 선택하지 않을 때 툴팁이 표시되지 않으므로 툴팁이 아닙니다.

제안 사항?

안부, HTZ

답변

3

JTable은 다른 모든 요소와 마찬가지로 JComponent이므로 하위 구성 요소를 추가 할 수 있다는 이점을 활용할 수 있습니다. 해야 할 일은 구성 요소의 크기를 올바르게 지정하는 것입니다 (JTable이 null 레이아웃을 사용하기 때문에).

다음은 선택된 항목의 수를 표시하는 JLabel이있는 작은 데모입니다.

import java.awt.BorderLayout; 
import java.awt.Point; 
import java.util.Vector; 

import javax.swing.JFrame; 
import javax.swing.JLabel; 
import javax.swing.JScrollPane; 
import javax.swing.JTable; 
import javax.swing.ListSelectionModel; 
import javax.swing.SwingUtilities; 
import javax.swing.UIManager; 
import javax.swing.UnsupportedLookAndFeelException; 
import javax.swing.event.ChangeEvent; 
import javax.swing.event.ChangeListener; 
import javax.swing.event.ListSelectionEvent; 
import javax.swing.event.ListSelectionListener; 

public class TestTable { 

    protected void initUI() { 
     Vector<Vector<Object>> data = new Vector<Vector<Object>>(); 
     Vector<String> colNames = new Vector<String>(); 
     for (int i = 0; i < 5; i++) { 
      colNames.add("Col-" + (i + 1)); 
     } 
     for (int i = 0; i < 200; i++) { 
      Vector<Object> row = new Vector<Object>(); 
      for (int j = 0; j < 5; j++) { 
       row.add("Cell " + (i + 1) + "-" + (j + 1)); 
      } 
      data.add(row); 
     } 
     table = new JTable(data, colNames); 
     someText = new JLabel(); 
     someText.setOpaque(true); 
     table.add(someText); 
     table.setSelectionMode(ListSelectionModel.MULTIPLE_INTERVAL_SELECTION); 
     table.getSelectionModel().addListSelectionListener(new ListSelectionListener() { 

      @Override 
      public void valueChanged(ListSelectionEvent e) { 
       int count = table.getSelectedRowCount(); 
       someText.setText("You currently have selected " + count + " item" + (count > 1 ? "s" : "")); 
       layoutLabel(); 
      } 
     }); 
     JFrame frame = new JFrame(); 
     frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
     scrollpane = new JScrollPane(table); 
     scrollpane.getViewport().addChangeListener(new ChangeListener() { 

      @Override 
      public void stateChanged(ChangeEvent e) { 
       layoutLabel(); 
      } 
     }); 
     frame.add(scrollpane, BorderLayout.CENTER); 
     frame.pack(); 
     frame.setVisible(true); 
    } 

    private JLabel someText; 
    private JTable table; 
    private JScrollPane scrollpane; 

    private void layoutLabel() { 
     someText.setSize(someText.getPreferredSize()); 
     Point location = scrollpane.getViewport().getViewRect().getLocation(); 
     int leadSelectionIndex = table.getSelectionModel().getLeadSelectionIndex(); 
     if (leadSelectionIndex > -1) { 
      if (table.rowAtPoint(location) == leadSelectionIndex) { 
       location.y += table.getRowHeight(leadSelectionIndex); 
      } 
     } 
     someText.setLocation(location); 
    } 

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

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

} 
+0

이것은 내가 필요한 것입니다! 리스너를'TableColumnModelListener'로 변경하여 열 선택 항목의 변경 사항을 수신하고'layoutLabel()'메소드를 편집하여 선행 선택 색인의 오른쪽 상단 모서리에 레이블을 배치합니다. 고맙습니다! – htz

2
    당신이 그것을 할 의도로이 도구 설명하지

, MsExcell에서와 같이 similair 효과 ToolTip에 대한 Locations을 설정하기 위해 할 수있는

  • 사용자가 표를 클릭하여 셀을 선택하고 커서를 가리키면 표시되지 않습니다.

    • 당신은 할 수없는 사용자 입력에 대한 JComponent (JTextComponents)

    • 편집 포함 non_editable contens

      기본적으로
    • JPopup/JWindow에 대한 JPopup/JWindow 대신 ToolTip, 사용할 수 있습니다 당신은 장식되지 않은 JDialod만을 사용할 수 있습니다

    2

    또 다른 옵션은 단위 구성 요소를 구현하는 것이다 : 그것은 현재 리드 선택되는 경우, 라벨은 상기 제 2 표시의 행으로 이동이 아닌 경우 라벨이 자동 최초로 표시되는 행에 위치 아래 그림과 같이 glassPane (JLayer의 1.7 역할, JLayer의 1.6 역할) 중 하나입니다. 내가 (@ Guillaume이 한 것처럼) 그 위치를 가장 잘 나타내려고하지는 않았다. 또한 테이블 영역 안에 상자가 표시되도록하려면 Rob의 DragLayout을 약간 수정해야합니다.

    public static class ToolTipUI extends LayerUI<JTable> { 
        private JLayer<JTable> layer; 
        private JToolTip toolTip; 
    
        @Override 
        public void installUI(JComponent c) { 
         super.installUI(c); 
         this.layer = (JLayer) c; 
         installGlassPane(); 
         installListeners(); 
        } 
    
        private void installListeners() { 
         ListSelectionListener l = new ListSelectionListener() { 
    
          @Override 
          public void valueChanged(ListSelectionEvent e) { 
           if (e.getValueIsAdjusting()) return; 
           updateToolTip(); 
          } 
    
         }; 
         getTable().getColumnModel().getSelectionModel().addListSelectionListener(l); 
         getTable().getSelectionModel().addListSelectionListener(l); 
        } 
    
        private void updateToolTip() { 
         int[] selectedColumns = getTable().getColumnModel().getSelectedColumns(); 
         int selectedRow = getTable().getSelectedRow(); 
         if (selectedRow < 0 || selectedColumns.length == 0) { 
          setToolTipText(""); 
         } else { 
          String text = "selected cells: "; 
          for (int i = 0; i < selectedColumns.length; i++) { 
           text += " " + selectedColumns[i]; 
          } 
          setToolTipText(text); 
         } 
        } 
    
        private void setToolTipText(String string) { 
         toolTip.setTipText(string); 
         Rectangle cellBounds = getTable().getCellRect(getTable().getSelectedRow(), 0, false); 
         toolTip.setLocation(cellBounds.getLocation()); 
         doLayout(layer); 
        } 
    
        @Override 
        public void doLayout(JLayer<? extends JTable> l) { 
         super.doLayout(l); 
         l.getGlassPane().doLayout(); 
        } 
    
        private JTable getTable() { 
         return layer.getView(); 
        } 
    
        private void installGlassPane() { 
         toolTip = ((JComponent) layer.getView()).createToolTip(); 
         layer.getGlassPane().setBorder(BorderFactory.createLineBorder(Color.RED)); 
         // DragLayout by Rob Camick http://tips4java.wordpress.com/2011/10/23/drag-layout/ 
         layer.getGlassPane().setLayout(new DragLayout()); 
         layer.getGlassPane().add(toolTip); 
         layer.getGlassPane().setVisible(true); 
        } 
    
    } 
    
    // usage: 
    JTable table = new JTable(new AncientSwingTeam()); 
    JLayer layer = new JLayer<JTable>(table, new ToolTipUI()); 
    
    +0

    우수하고 간단한 아이디어 – mKorbel

    관련 문제