当前位置: 首页 > 知识库问答 >
问题:

java中图像缩放的内存问题

毕胡非
2023-03-14

JDK:1.8U112 oracle

JRE:10.0.2

JVM最大堆大小:~2GB。

一个简单的GUI,可以打开图像文件(JPG/PNG)并通过用户输入放大它。

DESC

类扩展了JFrame。框架的contentPane有一个JButton、一个JLabel和一个JScrollPane。单击该按钮将显示一个JFileChooser。标签位于滚动窗格内。选择一个文件将在标签中打开它(仅为本问题的目的打开图像文件-JPG/PNG测试)。标签有一个鼠标滚轮侦听器,它通过image.getScaledInstance导致图像缩放。每次缩放时,magnifiaction(新图像宽度(或高度)与对应的原始图像的比值)和runtime.totalmemory都会被打印出来。

    null
import java.awt.Dimension;
import java.awt.Image;
import java.io.File;
import java.io.IOException;
import javax.imageio.ImageIO;
import javax.swing.ImageIcon;
import javax.swing.JFileChooser;
import javax.swing.SwingUtilities;
import javax.swing.UIManager;

public class gui extends javax.swing.JFrame {

Image image;
Dimension size;
private double mag = 1;
Runtime runtime = Runtime.getRuntime();

public gui() {
    initComponents();

}

private void zoom() {

    int[] newSize = {(int) (size.width * mag), (int) (size.height * mag)};

    if (newSize[0] > 0 && newSize[1] > 0) {
        label.setIcon(new ImageIcon(image.getScaledInstance(newSize[0], newSize[1], Image.SCALE_DEFAULT)));
    }

    System.out.println("mag:" + (int) (mag * 100) + "% mem:" + runtime.totalMemory() / 1024 / 1024 + "MB");

}

private void loadImage(File imgFile) throws IOException {

    String path = imgFile.getPath().toLowerCase();
    if (path.endsWith("gif")) {
        ImageIcon icon = new ImageIcon(path);

        image = icon.getImage();

        label.setIcon(icon);

    } else {
        image = ImageIO.read(imgFile);
        ImageIcon icon = new ImageIcon(image);
        label.setIcon(icon);
    }

    size = new Dimension(image.getWidth(null), image.getHeight(null));

}

@SuppressWarnings("unchecked")
// <editor-fold defaultstate="collapsed" desc="Generated Code">                          
private void initComponents() {

    dialog = new javax.swing.JFileChooser();
    jScrollPane1 = new javax.swing.JScrollPane();
    label = new javax.swing.JLabel();
    button = new javax.swing.JButton();

    dialog.setCurrentDirectory(new java.io.File("D:\\"));
        dialog.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                dialogActionPerformed(evt);
            }
        });

        setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE);
        setTitle("Image Viewer");

        label.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);
        label.setVerticalAlignment(javax.swing.SwingConstants.TOP);
        label.addMouseWheelListener(new java.awt.event.MouseWheelListener() {
            public void mouseWheelMoved(java.awt.event.MouseWheelEvent evt) {
                labelMouseWheelMoved(evt);
            }
        });
        jScrollPane1.setViewportView(label);

        button.setText("open");
        button.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                buttonActionPerformed(evt);
            }
        });

        javax.swing.GroupLayout layout = new javax.swing.GroupLayout(getContentPane());
        getContentPane().setLayout(layout);
        layout.setHorizontalGroup(
            layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(layout.createSequentialGroup()
                .addContainerGap()
                .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                    .addComponent(jScrollPane1, javax.swing.GroupLayout.DEFAULT_SIZE, 689, Short.MAX_VALUE)
                    .addGroup(layout.createSequentialGroup()
                        .addComponent(button)
                        .addGap(0, 0, Short.MAX_VALUE)))
                .addContainerGap())
        );
        layout.setVerticalGroup(
            layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, layout.createSequentialGroup()
                .addContainerGap()
                .addComponent(button)
                .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
                .addComponent(jScrollPane1, javax.swing.GroupLayout.DEFAULT_SIZE, 430, Short.MAX_VALUE)
                .addContainerGap())
        );

        pack();
    }// </editor-fold>                        

private void dialogActionPerformed(java.awt.event.ActionEvent evt) {                                       
    // TODO add your handling code here:

    if (evt.getActionCommand().equals(JFileChooser.APPROVE_SELECTION)) {

        try {
            File file = dialog.getSelectedFile();

            loadImage(file);

            setTitle(file.getPath());
        } catch (IOException ex) {
            ex.printStackTrace();
        }

    }

}                                      

private void labelMouseWheelMoved(java.awt.event.MouseWheelEvent evt) {                                      

    if (image != null) {
        int amt = -evt.getWheelRotation();
        double newMag = mag + amt * 0.1;

        if (newMag > 0) {
            mag = newMag;
            zoom();

        }

    }


}                                     

private void buttonActionPerformed(java.awt.event.ActionEvent evt) {                                       
    // TODO add your handling code here:
    dialog.showOpenDialog(this);
}                                      

public static void main(String args[]) throws Exception {

    UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());

    SwingUtilities.invokeLater(new Runnable() {
        public void run() {

            new gui().setVisible(true);

        }
    });
}

// Variables declaration - do not modify                     
private javax.swing.JButton button;
private javax.swing.JFileChooser dialog;
private javax.swing.JScrollPane jScrollPane1;
private javax.swing.JLabel label;
// End of variables declaration                   
}

任何jpg或png图像应该做除了测试文件。

测试文件的输出

共有1个答案

甄成弘
2023-03-14

丢弃的ImageIcon对象(请参见代码)是否没有被GCED?

如果没有GC运行,如何对它们进行GC?

当内存足够时,为什么要运行GC?

是的,因为GC不需要运行。

为什么堆会扩展这么多(在大约17倍mag时,它会达到2GB)

所有中间尺寸的图像都无法到达,但尚未收集。

 类似资料:
  • 我在控制igraph所做网络图中对象的大小时遇到问题。命令的文档说明: bbox::绘图的边界框。这必须是包含所需绘图宽度和高度的元组。默认打印宽度为600像素,高度为600像素 arrow_size:如果图形有方向,则边上箭头的大小(长度)相对于15像素 顶点大小:顶点的大小(以像素为单位) 据我所知,所有这些参数都代表像素数。因此,如果将它们全部乘以一个系数,我希望图像能够完全按照这个系数缩放

  • 问题内容: 我想更改多页TIFF图像的高度,所以我在下面的代码段中进行缩放。但是它仅从tiff文件返回第一页,我想它会将其转换为JPEG图像。如何保留文件的所有页面? 更新的代码: 问题答案: 只会写入单个独立映像。将多个图像写入同一输出流并不能解决此问题。但是,ImageIO软件包完全支持您所需的内容,只需要更多代码即可。 使用以下命令获取适用于TIFF格式的格式: 有关更多信息,请参见Imag

  • 问题内容: 改变的大小的图像在GWT部件改变所述图像元素的大小,但不重新调整屏幕上的图像。因此,以下操作将无效: 这是因为GWT 通过使用CSS 将HTML 元素的设置为图像来实现其Image小部件。 如何获得要调整尺寸的实际图像? 问题答案: 我看到了此博客条目,该条目通过使用GWT DataResource而不是ImageResource解决了问题。事实证明,如果您按以下方式使用它,则Imag

  • 我正在用“原生脚本-照片-缩放”和原生脚本-图像-缩放在我的角应用程序中尝试图像缩放,但它引发了“PhotoDraweeView不是构造函数错误”,有人能帮我吗? 我的代码HTML: 导出类AppModule{}

  • 然后,我根据页面大小与图像大小计算缩放的维度,返回:java.awt.dimension[width=562,height=792]我使用下面的代码来计算缩放的维度: 为了实际执行图像缩放,我使用image Scalr API: 我的问题是我做错了什么?当缩放到较小的尺寸时,大的图像不应该被模糊。这与PDF页面的分辨率/大小有关吗?