Skip to content

Commit

Permalink
Merge pull request #125 from sam-wmd/feature/resize_augmentation_aspe…
Browse files Browse the repository at this point in the history
…ct_ratio

Added a constructor to ResizeAugmentation.java with scaleFactor
  • Loading branch information
Samyssmile authored Nov 12, 2023
2 parents 8364d5c + 35703d0 commit 0bf4e42
Show file tree
Hide file tree
Showing 3 changed files with 189 additions and 5 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,10 @@
*/
public class ResizeAugmentation extends AbstractAugmentation {

private final int targetHeight;
private final int targetWidth;
private int targetHeight;
private int targetWidth;
private double scaleFactor;
private final boolean useScaleFactor;
private final ResizeQuality resizeQuality;

/**
Expand All @@ -26,6 +28,7 @@ public ResizeAugmentation(int targetWidth, int targetHeight) {
this.targetWidth = targetWidth;
this.targetHeight = targetHeight;
this.resizeQuality = ResizeQuality.BALANCED;
this.useScaleFactor = false;
}

/**
Expand All @@ -40,20 +43,59 @@ public ResizeAugmentation(int targetWidth, int targetHeight, ResizeQuality resiz
this.targetWidth = targetWidth;
this.targetHeight = targetHeight;
this.resizeQuality = resizeQuality;
this.useScaleFactor = false;
}

/**
* Resizes the given image to the target width and height specified during the instantiation. This
* method applies rendering hints based on the selected resize quality for the output image.
* Creates a ResizeAugmentation instance with a specified scale factor which ensures that the
* image maintains its aspect ratio after the transformation. A scaleFactor between 0 and 1 will
* decrease the image size whereas a value greater than 1 will increase the image size.
*
* @param scaleFactor The multiplier for the width and height of the image.
* @throws IllegalArgumentException if scaleFactor is a negative number
*/
public ResizeAugmentation(double scaleFactor) throws IllegalArgumentException {
this(scaleFactor, ResizeQuality.BALANCED);
}

/**
* Creates a ResizeAugmentation instance with the specified scaleFactor and resizing quality. A
* value between 0 and 1 will decrease the image size whereas a value greater than 1 will increase
* the image size.
*
* @param scaleFactor The multiplier for the width and height of the image.
* @param resizeQuality The quality of the resize process.
* @throws IllegalArgumentException if scaleFActor is a negative number
*/
public ResizeAugmentation(double scaleFactor, ResizeQuality resizeQuality)
throws IllegalArgumentException {
if (scaleFactor <= 0)
throw new IllegalArgumentException("Scale factor must be a positive number.");
this.scaleFactor = scaleFactor;
this.useScaleFactor = true;
this.resizeQuality = resizeQuality;
}

/**
* Resizes the given image to the target width and height which are either specified during the
* instantiation or computed based on the scaleFactor. This method applies rendering hints based
* on the selected resize quality for the output image.
*
* @param image The BufferedImage to resize.
* @return A new BufferedImage object of the specified target width and height.
*/
@Override
public synchronized BufferedImage apply(BufferedImage image) {
if (useScaleFactor) {
targetHeight = (int) (image.getHeight() * scaleFactor);
targetWidth = (int) (image.getWidth() * scaleFactor);
}
return resize(image);
}

protected BufferedImage resize(BufferedImage image) {
BufferedImage result = new BufferedImage(targetWidth, targetHeight, image.getType());
Graphics2D graphics2D = result.createGraphics();

// Apply rendering hints based on the chosen quality of resizing
switch (resizeQuality) {
case QUALITY -> graphics2D.setRenderingHint(
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
package de.edux.augmentation.effects;

import org.junit.jupiter.api.AfterEach;

import javax.imageio.ImageIO;
import java.awt.image.BufferedImage;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.Arrays;

import static org.junit.jupiter.api.Assertions.*;
import static org.junit.jupiter.api.Assertions.assertTrue;

public abstract class AbstractAugmentationTest {
protected BufferedImage originalImage;
protected BufferedImage augmentedImage;

public void shouldHaveSameWidth() {
assertEquals(
originalImage.getWidth(),
augmentedImage.getWidth(),
"Augmented image width should match the specified width.");
}

public void shouldHaveSameHeight() {
assertEquals(
originalImage.getHeight(),
augmentedImage.getHeight(),
"Augmented image height should match the specified height.");
}

public void shouldHaveSamePixels() {
int[] originalPixels =
originalImage.getRGB(
0,
0,
originalImage.getWidth(),
originalImage.getHeight(),
null,
0,
originalImage.getWidth());
int[] augmentedPixels =
augmentedImage.getRGB(
0,
0,
augmentedImage.getWidth(),
augmentedImage.getHeight(),
null,
0,
augmentedImage.getWidth());
assertFalse(
Arrays.equals(originalPixels, augmentedPixels),
"The augmented image should differ from the original.");
}

public void shouldNotBeNull() {
assertNotNull(augmentedImage, "Augmented image should not be null.");
}

public void outputFileShouldExistAndNotBeEmpty() throws IOException {
Path outputPath = Paths.get("augmented.png");
ImageIO.write(augmentedImage, "png", outputPath.toFile());
assertTrue(Files.exists(outputPath), "Output image file should exist.");
assertTrue(Files.size(outputPath) > 0, "Output image file should not be empty.");
}

@AfterEach
public void checkConformity() throws IOException {
shouldNotBeNull();
shouldHaveSameWidth();
shouldHaveSameHeight();
shouldHaveSamePixels();
outputFileShouldExistAndNotBeEmpty();
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
package de.edux.augmentation.effects;

import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.Test;

import static de.edux.augmentation.AugmentationTestUtils.openImageInPreview;
import static org.junit.jupiter.api.Assertions.*;
import java.io.File;
import java.io.IOException;

import static de.edux.augmentation.AugmentationTestUtils.loadTestImage;

public class ResizeAugmentationTest extends AbstractAugmentationTest {

private double originalAspectRatio;

@Override
@AfterEach
public void checkConformity() throws IOException {
shouldNotBeNull();
shouldHaveSamePixels();
outputFileShouldExistAndNotBeEmpty();
}

@AfterEach
public void shouldMaintainAspectRatio() {
double newAspectRatio = (double) augmentedImage.getWidth() / augmentedImage.getHeight();
assertEquals(
originalAspectRatio,
newAspectRatio,
"Augmented image should have the same aspect ratio as the original image");
}

@AfterEach
public void openImagesInPreview() throws InterruptedException {
openImageInPreview(originalImage);
openImageInPreview(augmentedImage);
}

@Test
public void shouldIncreaseImageSize() throws IOException {
originalImage = loadTestImage("augmentation" + File.separator + "cyborg-cyberpunk.png");
originalAspectRatio = (double) originalImage.getWidth() / originalImage.getHeight();

double testScaleFactor = 2;
ResizeAugmentation ResizeAugmentation = new ResizeAugmentation(testScaleFactor);
augmentedImage = ResizeAugmentation.apply(originalImage);

assertEquals(augmentedImage.getHeight(), originalImage.getHeight() * testScaleFactor);
assertEquals(augmentedImage.getWidth(), originalImage.getWidth() * testScaleFactor);
}

@Test
public void shouldDecreaseImageSize() throws IOException {
originalImage = loadTestImage("augmentation" + File.separator + "neo-tokyo.png");
originalAspectRatio = (double) originalImage.getWidth() / originalImage.getHeight();

double testScaleFactor = 0.5;
ResizeAugmentation ResizeAugmentation = new ResizeAugmentation(testScaleFactor);
augmentedImage = ResizeAugmentation.apply(originalImage);

assertEquals(augmentedImage.getHeight(), originalImage.getHeight() * testScaleFactor);
assertEquals(augmentedImage.getWidth(), originalImage.getWidth() * testScaleFactor);
}
}

0 comments on commit 0bf4e42

Please sign in to comment.