如何创建带有图标和文本的 JList?

Posted

技术标签:

【中文标题】如何创建带有图标和文本的 JList?【英文标题】:How to create JList with icon and text? 【发布时间】:2012-10-31 11:14:58 【问题描述】:

我有这段代码想让JList 谈论文字和图标必须做什么。 有些人建议我制作标签列表并在表格中放置文本图标是否可能?如何?

///////////////// 上搜索嵌入评论。

import javax.swing.JPanel;
import javax.swing.JButton;
import javax.swing.JLabel;
import java.awt.datatransfer.DataFlavor;
import java.awt.datatransfer.Transferable;
import java.awt.datatransfer.UnsupportedFlavorException;
import java.awt.dnd.DropTarget;
import java.awt.dnd.DropTargetDragEvent;
import java.awt.dnd.DropTargetDropEvent;
import java.awt.dnd.DropTargetEvent;
import java.awt.dnd.DropTargetListener;
import java.io.File;
import java.io.IOException;
import java.util.List;
import javax.swing.DefaultListModel;
import javax.swing.Icon;
import javax.swing.JList;
import javax.swing.JScrollPane;
import javax.swing.filechooser.FileSystemView;

public class pan extends JPanel implements DropTargetListener 

private DefaultListModel listModel = new DefaultListModel();
private DropTarget dropTarget;
private JLabel jLabel1;
private JScrollPane jScrollPane1;
private JList list;

/**
 * Create the panel.
 */
public pan() 
    setLayout(null);        
    list = new JList();
    dropTarget = new DropTarget(list, this);
    list.setModel(listModel);
    list.setDragEnabled(true);
    //list.setTransferHandler(new FileTransferHandler());
    jScrollPane1 = new JScrollPane();

    jScrollPane1.setViewportView(list);
    jScrollPane1.setBounds(10, 150, 635, 330);
    add(jScrollPane1);


public void dragEnter(DropTargetDragEvent arg0) 
    // nothing


public void dragOver(DropTargetDragEvent arg0) 
    // nothing


public void dropActionChanged(DropTargetDragEvent arg0) 
    // nothing


public void dragExit(DropTargetEvent arg0) 
    // nothing


public void drop(DropTargetDropEvent evt) 
    int action = evt.getDropAction();
    evt.acceptDrop(action);
    try 
        Transferable data = evt.getTransferable();
        if (data.isDataFlavorSupported(DataFlavor.javaFileListFlavor)) 
              List<File> files = (List<File>) data.getTransferDat(DataFlavor.javaFileListFlavor);
            for (File file : files) 

    Icon icon=FileSystemView.getFileSystemView().getSystemIcon(file);
/////////////////listModel.addElement(filepath+icon);///////////////////////want code do this

            
        
     catch (UnsupportedFlavorException e) 
        e.printStackTrace();
     catch (IOException e) 
        e.printStackTrace();
     finally 
        evt.dropComplete(true);
    
 


解决此问题后,如果双击它会打开桌面,我将为每个元素添加操作 到存储在列表中的路径。

【问题讨论】:

见How to Use Lists: Writing a Custom Cell Renderer。 【参考方案1】:

import java.awt.*;
import java.awt.datatransfer.*;
import java.awt.dnd.*;
import javax.swing.*;
import javax.swing.border.LineBorder;
import javax.swing.filechooser.FileSystemView;
import java.io.*;
import java.util.List;

public class FileDropList extends JPanel implements DropTargetListener 

    private DefaultListModel listModel = new DefaultListModel();
    private DropTarget dropTarget;
    private JLabel jLabel1;
    private JScrollPane jScrollPane1;
    private JList list;

    /**
     * Create the panel.
     */
    public FileDropList() 
        //setLayout(null);        
        list = new JList();
        dropTarget = new DropTarget(list, this);
        list.setModel(listModel);
        list.setDragEnabled(true);
        FileListCellRenderer renderer = new FileListCellRenderer();
        list.setCellRenderer(renderer);
        //list.setTransferHandler(new FileTransferHandler());
        jScrollPane1 = new JScrollPane(list);

        //jScrollPane1.setBounds(10, 150, 635, 330);
        add(jScrollPane1);

    
    public static void main(String[] args) throws Exception 
        Runnable r = new Runnable() 
            @Override
            public void run() 
                JPanel pan = new FileDropList();
                pan.setBorder(new LineBorder(Color.BLACK));
                JOptionPane.showMessageDialog(null, pan);
            
        ;
        SwingUtilities.invokeLater(r);
    

    public void dragEnter(DropTargetDragEvent arg0) 
        // nothing
    

    public void dragOver(DropTargetDragEvent arg0) 
        // nothing
    

    public void dropActionChanged(DropTargetDragEvent arg0) 
        // nothing
    

    public void dragExit(DropTargetEvent arg0) 
        // nothing
    

    public void drop(DropTargetDropEvent evt) 
        int action = evt.getDropAction();
        evt.acceptDrop(action);
        try 
            Transferable data = evt.getTransferable();
            if (data.isDataFlavorSupported(DataFlavor.javaFileListFlavor)) 
                List<File> files = (List<File>) data.getTransferData(DataFlavor.javaFileListFlavor);
                for (File file : files) 
                    listModel.addElement(file);
                
            
         catch (UnsupportedFlavorException e) 
            e.printStackTrace();
         catch (IOException e) 
            e.printStackTrace();
         finally 
            evt.dropComplete(true);
        
    


/** A FileListCellRenderer for a File. */
class FileListCellRenderer extends DefaultListCellRenderer 

    private static final long serialVersionUID = -7799441088157759804L;
    private FileSystemView fileSystemView;
    private JLabel label;
    private Color textSelectionColor = Color.BLACK;
    private Color backgroundSelectionColor = Color.CYAN;
    private Color textNonSelectionColor = Color.BLACK;
    private Color backgroundNonSelectionColor = Color.WHITE;

    FileListCellRenderer() 
        label = new JLabel();
        label.setOpaque(true);
        fileSystemView = FileSystemView.getFileSystemView();
    

    @Override
    public Component getListCellRendererComponent(
            JList list,
            Object value,
            int index,
            boolean selected,
            boolean expanded) 

        File file = (File)value;
        label.setIcon(fileSystemView.getSystemIcon(file));
        label.setText(fileSystemView.getSystemDisplayName(file));
        label.setToolTipText(file.getPath());

        if (selected) 
            label.setBackground(backgroundSelectionColor);
            label.setForeground(textSelectionColor);
         else 
            label.setBackground(backgroundNonSelectionColor);
            label.setForeground(textNonSelectionColor);
        

        return label;
    

原答案

import java.awt.datatransfer.*;
import java.awt.dnd.*;
import javax.swing.*;
import javax.swing.filechooser.FileSystemView;
import java.io.*;
import java.util.List;

public class FileDragList extends JPanel implements DropTargetListener 

    private static final long serialVersionUID = 1L;
    private DefaultListModel listModel = new DefaultListModel();
    private JScrollPane jScrollPane1;
    private JList list;

    /**
     * Create the panel.
     */
    public FileDragList() 
        setLayout(null);        
        list = new JList();
        DropTarget dropTarget = new DropTarget(list, this);
        list.setModel(listModel);
        list.setDragEnabled(true);
        FileListCellRenderer renderer = new FileListCellRenderer();
        list.setCellRenderer(renderer);
        //list.setTransferHandler(new FileTransferHandler());
        jScrollPane1 = new JScrollPane();

        jScrollPane1.setViewportView(list);
        jScrollPane1.setBounds(10, 150, 635, 330);
        add(jScrollPane1);

    
    public static void main(String[] args) throws Exception 
        Runnable r = new Runnable() 
            @Override
            public void run() 
                JOptionPane.showMessageDialog(null, new FileDragList());
            
        ;
        SwingUtilities.invokeLater(r);
    

    public void dragEnter(DropTargetDragEvent arg0) 
        // nothing
    

    public void dragOver(DropTargetDragEvent arg0) 
        // nothing
    

    public void dropActionChanged(DropTargetDragEvent arg0) 
        // nothing
    

    public void dragExit(DropTargetEvent arg0) 
        // nothing
    

    public void drop(DropTargetDropEvent evt) 
        int action = evt.getDropAction();
        evt.acceptDrop(action);
        try 
            Transferable data = evt.getTransferable();
            if (data.isDataFlavorSupported(DataFlavor.javaFileListFlavor)) 
                List<File> files = (List<File>) data.getTransferData(DataFlavor.javaFileListFlavor);
                for (File file : files) 

                    Icon icon=FileSystemView.getFileSystemView().getSystemIcon(file);
                    /////////////////listModel.addElement(filepath+icon);///////////////////////want code do this

                
            
         catch (UnsupportedFlavorException e) 
            e.printStackTrace();
         catch (IOException e) 
            e.printStackTrace();
         finally 
            evt.dropComplete(true);
        
    


Icon icon=FileSystemView.getFileSystemView().getSystemIcon(file);

哦,对了。尝试使用File Browser GUI 的FileTreeCellRenderer 的变体。

就是这样,用于左边的树。

FileTreeCellRenderer

/** A TreeCellRenderer for a File. */
class FileTreeCellRenderer extends DefaultTreeCellRenderer 

    private FileSystemView fileSystemView;
    private JLabel label;

    FileTreeCellRenderer() 
        label = new JLabel();
        label.setOpaque(true);
        fileSystemView = FileSystemView.getFileSystemView();
    

    @Override
    public Component getTreeCellRendererComponent(
        JTree tree,
        Object value,
        boolean selected,
        boolean expanded,
        boolean leaf,
        int row,
        boolean hasFocus) 

        DefaultMutableTreeNode node = (DefaultMutableTreeNode)value;
        File file = (File)node.getUserObject();
        label.setIcon(fileSystemView.getSystemIcon(file));
        label.setText(fileSystemView.getSystemDisplayName(file));
        label.setToolTipText(file.getPath());

        if (selected) 
            label.setBackground(backgroundSelectionColor);
            label.setForeground(textSelectionColor);
         else 
            label.setBackground(backgroundNonSelectionColor);
            label.setForeground(textNonSelectionColor);
        

        return label;
    

更新

一个 SSCCE,它使上面的渲染器适应列表。

import java.awt.*;
import javax.swing.*;
import javax.swing.filechooser.FileSystemView;
import java.io.File;

public class FileList 
    public static void main(String[] args) throws Exception 
        Runnable r = new Runnable() 
            @Override
            public void run() 
                JPanel gui = new JPanel(new BorderLayout(2,2));

                File userHome = new File(System.getProperty("user.home"));
                File[] files = userHome.listFiles();
                JList list = new JList(files);
                list.setCellRenderer(new FileListCellRenderer());
                gui.add(new JScrollPane(list));

                JOptionPane.showMessageDialog(null, gui);
            
        ;
        SwingUtilities.invokeLater(r);
    


/** A FileListCellRenderer for a File. */
class FileListCellRenderer extends DefaultListCellRenderer 

    private static final long serialVersionUID = -7799441088157759804L;
    private FileSystemView fileSystemView;
    private JLabel label;
    private Color textSelectionColor = Color.BLACK;
    private Color backgroundSelectionColor = Color.CYAN;
    private Color textNonSelectionColor = Color.BLACK;
    private Color backgroundNonSelectionColor = Color.WHITE;

    FileListCellRenderer() 
        label = new JLabel();
        label.setOpaque(true);
        fileSystemView = FileSystemView.getFileSystemView();
    

    @Override
    public Component getListCellRendererComponent(
        JList list,
        Object value,
        int index,
        boolean selected,
        boolean expanded) 

        File file = (File)value;
        label.setIcon(fileSystemView.getSystemIcon(file));
        label.setText(fileSystemView.getSystemDisplayName(file));
        label.setToolTipText(file.getPath());

        if (selected) 
            label.setBackground(backgroundSelectionColor);
            label.setForeground(textSelectionColor);
         else 
            label.setBackground(backgroundNonSelectionColor);
            label.setForeground(textNonSelectionColor);
        

        return label;
    

【讨论】:

以上是关于如何创建带有图标和文本的 JList?的主要内容,如果未能解决你的问题,请参考以下文章

如何在左侧按钮上创建一个带有文本并在右侧按钮上与其分开的图标的 JButton

如何从 JList 中的组件中获取文本?

Java order jlist 按状态

Flutter - 如何在图像下方使用带有图像和文本/图标的容器小部件

带有左图标和文本的按钮完全对齐

如何在 AppCompatActivity 中显示带有图标和文本的菜单项