2010-11-02 9 views
1

我需要一个静态工具方法来从List<T>中选择对象。我遇到了两个问题。下面是一个短的测试程序:摆动:在一组对象中进行选择

package com.example.test.gui; 

import java.util.Arrays; 
import java.util.List; 
import javax.swing.JOptionPane; 

public class SelectionTest { 
    public interface NameExtractor<T> { 
     public String extractName(T object); 
    } 

    static public <T> T selectFromList(String message, List<T> list, NameExtractor<T> nameExtractor) { 
     String[] choices = new String[list.size()]; 
     int i = 0; 
     for (T t : list) 
      choices[i++] = nameExtractor.extractName(t); 
     Object s = JOptionPane.showInputDialog(null, message, "", 
       JOptionPane.QUESTION_MESSAGE, null, choices, null); 
     System.out.println(s); 
     // crap, we get a string back. Now how do we get back the object in question? 
     return null; 
    } 

    static public void main(String[] args) 
    { 
     List<Integer> numbers = Arrays.asList(1,2,3,4,10); 
     System.out.println(selectFromList("Pick one", numbers, new NameExtractor<Integer>(){ 
      @Override public String extractName(Integer object) { 
       return object.toString(); 
      } 
     })); 
    } 
} 

是否有到JOptionPane.showInputDialog(),让我得到列表,而不是一个字符串显示的索引的方法吗?

编辑:我也宁愿强制使用JList而不是组合框或任何JOptionPane想要的默认值。

回答

2

为什么不把对象放入JOptionPane而不是放入一个字符串数组? JOptionPane将调用该对象的toString方法用于显示目的。

Object selectedObject = JOptionPane.showInputDialog(null, message, "", 
      JOptionPane.QUESTION_MESSAGE, null, list.toArray(), null); 

    return (T)selectedObject; 

OR

搜索通过名称所选名称和返回对象:

for(int j = 0 ; j < choices.length; j++){ 
     if(selectedObject.equals(choices[j])){ 
      return list.get(j); 
     } 
    } 
    return null; 
+0

因为toString()不一定是我想要显示对象描述的方法。我在对象类外部使用NameExtractor接口。 – 2010-11-02 14:56:55

+0

+1 for list.toArray()虽然,这是我没有想到的东西 – 2010-11-02 15:30:17

2

最后我做以下,这似乎有点麻烦,所以如果别人想出了一个更干净的方式来做到这一点,我会接受你的答案。

/** 
* @param <T> element class 
* @param title dialog title 
* @param message message 
* @param list list 
* @param nameExtractor gets names from element 
* @return item from the list 
*/ 
static public <T> T selectFromList(String title, String message, List<T> list, NameExtractor<T> nameExtractor) { 
    JPanel p = new JPanel(); 
    JList jlist = new JList(); 
    DefaultListModel model = new DefaultListModel(); 
    for (T t : list) 
     model.addElement(nameExtractor.extractName(t)); 
    jlist.setModel(model); 
    p.setLayout(new BorderLayout()); 
    p.add(new JLabel(message), BorderLayout.NORTH); 
    p.add(jlist, BorderLayout.CENTER); 
    JOptionPane op = new JOptionPane(p, JOptionPane.QUESTION_MESSAGE, JOptionPane.OK_CANCEL_OPTION); 
    JDialog d = op.createDialog(title); 
    d.setVisible(true); 
    Object sel = op.getValue(); 
    int i = jlist.getSelectedIndex(); 
    d.dispose(); 
    if (i != -1 && sel instanceof Integer && (Integer)sel == JOptionPane.OK_OPTION) 
     return list.get(i); 
    else 
     return null; 
} 
2

是否有可以JOptionPane.showInputDialog(),让我得到列表,而不是一个字符串显示的索引的方法吗?

所有选项窗格showXXX方法都允许您将任何对象直接添加到选项窗格。所以你可以添加你的列表(滚动窗格?)到对话框。

JList list = new JList(...); 
int value = JOptionPane.showOptionDialog(null, list, ...); 

请阅读Swing教程How to Use Dialogs中的部分。如果您愿意,您甚至可以防止对话框关闭,直到从列表中选择一个项目。