Есть ли способ сохранить мой bufferedImage с расширением, выбранным в моем JfileChooser? - PullRequest
1 голос
/ 03 апреля 2019

У меня проблема с моим кодом.Прежде всего, я создал JfileChooser, чтобы сохранить мой bufferedImage в файл.Проблема в том, что когда я сохраняю его, если я не пишу расширение в окне, это будет обычный файл вместо jpg / png или другого. Как я могу это сделать?

Я попробовал несколькостранный код, такой как получение описания fileextension, но он не работает

    JFileChooser savechooser = new JFileChooser();
    savechooser.setFileFilter(new FileNameExtensionFilter("JPEG File", "jpg"));
    savechooser.setFileFilter(new FileNameExtensionFilter("PNG File", "png"));
    savechooser.setFileFilter(new FileNameExtensionFilter("GIF File", "gif"));
    int returnVal = savechooser.showSaveDialog(null);
    if(returnVal == JFileChooser.APPROVE_OPTION) {
        ImageIO.write(bImage, "png" , new File(savechooser.getSelectedFile().getAbsolutePath()));

Я ожидаю "test.png" или "test.jpeg", но фактическим выводом будет "тестовый" файл..

1 Ответ

0 голосов
/ 04 апреля 2019

Второй параметр ImageIO.write(...) ("png" в вашем коде) - это формат файла. Это не имеет прямого отношения к имени файла. «расширение файла» или суффикс является просто частью имени файла и может быть любым, хотя по соглашению он используется для указания формата файла (т. Е. Ничто не мешает вам назвать Файл JPEG "foo.gif", если вы действительно хотите, и это все еще файл JPEG) Windows обычно использует это соглашение для определения типа файла и выбора соответствующего приложения для открытия файла, поэтому использование нестандартного расширения может привести к путанице.

Чтобы устранить проблему, которую вы видите, вероятно, лучше убедиться, что имя файла заканчивается правильным расширением, если только пользователь не добавил его. Например (предполагается, что пользователь выбрал формат PNG, но вы можете легко адаптировать его и к другим форматам):

// JFileChooser code as is

if (returnVal == JFileChooser.APPROVE_OPTION) {
   File file = savechooser.getSelectedFile();

   String fileName = file.getName();
   if (!fileName.toLowerCase().endsWith(".png")) {
       file = new File(file.getParent(), fileName + ".png");
   }

   if (!ImageIO.write(image, "PNG" , file)) {
       // TODO: Handle file could not be written case
   }
}

Вышеуказанное будет гарантировать, что файл имеет правильное расширение, если пользователь не предоставил его сам.

Я также вижу другую проблему в вашем коде. Вы вызываете savechooser.setFileFilter(..) три раза. Каждый вызов заменит текущий фильтр новым. Вы, вероятно, хотите использовать savechooser.addChoosableFileFilter(...) вместо этого (и, возможно, setFileFilter(..) для того, который вы хотите использовать по умолчанию). Фильтр отфильтрует файлы, показанные в диалоговом окне, и, следовательно, файлы, по которым пользователь щелкает, но не влияет на имя, которое он сам указал. Вы можете получить текущий фильтр из savechooser.getFileFilter() и использовать его для определения используемого формата.

Вот более полное решение:

JFileChooser savechooser = new JFileChooser();
FileNameExtensionFilter pngFilter = new FileNameExtensionFilter("PNG File", "png")
savechooser.addChoosableFileFilter(pngFilter);
savechooser.addChoosableFileFilter(new FileNameExtensionFilter("JPEG File", "jpg"));
savechooser.addChoosableFileFilter(new FileNameExtensionFilter("GIF File", "gif"));

savechooser.setFileFilter(pngFilter); // Default choose PNG

int returnVal = savechooser.showSaveDialog(null);

if (returnVal == JFileChooser.APPROVE_OPTION) {
   File file = savechooser.getSelectedFile();

   FileNameExtensionFilter currentFilter = (FileNameExtensionFilter) savechooser.getFileFilter();
   String ext = currentFilter.getExtensions()[0];

   if (!currentFilter.accept(file)) {
       // File does not not have the correct extension, fix it
       String fileName = file.getName();
       file = new File(file.getParent(), fileName + "." + ext);
   }

   String format = "jpg".equals(ext) ? "JPEG" : ext; // May not be strictly necessary, just a reminder that file ext != file format

   if (!ImageIO.write(image, format , file)) {
       // TODO: Handle file could not be written case
   }
}
...