Próbowałem zmiany rozmiaru obrazu za pomocą buforowanego AffineTransform jak Scalr.resizeDynamiczne zmiany rozmiaru BufferedImage w java
Oto moje kody dla obu z nich.
użyciu Scalr.resize:
BufferedImage buff = robot.createScreenCapture(new Rectangle(bufx,bufy,bufwidth,bufheight)); // x-coord, y-coord, width, height
BufferedImage scrCapt = Scalr.resize(buff, Method.BALANCED, scrwidth, scrheight);
użyciu AffineTransform:
BufferedImage buff = robot.createScreenCapture(new Rectangle(bufx,bufy,bufwidth,bufheight)); // x-coord, y-coord, width, height
BufferedImage scrCapt = new BufferedImage(bufwidth,bufheight,BufferedImage.TYPE_INT_ARGB);
AffineTransform atscr = new AffineTransform();
atscr.scale(aspectRatioWidth,aspectRatioHeight);
AffineTransformOp scaleOp = new AffineTransformOp(atscr, AffineTransformOp.TYPE_BILINEAR);
scrCapt = scaleOp.filter(buff, scrCapt);
zmienne zostały zadeklarowane na początku wewnątrz klasy:
static int bufx = 0;
static int bufy = 0;
static int bufwidth = 1;
static int bufheight = 1;
static int scrwidth = 0;
static int scrheight = 0;
static float aspectRatioWidth = 0;
static float aspectRatioHeight = 0;
otrzymuję wartości dla wszystkich zmiennych dynamicznie w innej metodzie:
aspectRatioWidth = bufwidth/scrwidth;
aspectRatioHeight = bufheight/scrheight;
Jednakże gdy ten kod pojawia się błąd w obie funkcje AffineTransform jak Scalr.resize:
Scalr.resize:
Exception in thread "Thread-2" java.lang.IllegalArgumentException: Width (0) and height (0) cannot be <= 0
at java.awt.image.DirectColorModel.createCompatibleWritableRaster(DirectColorModel.java:1016)
at java.awt.image.BufferedImage.<init>(BufferedImage.java:331)
at org.imgscalr.Scalr.createOptimalImage(Scalr.java:2006)
at org.imgscalr.Scalr.scaleImage(Scalr.java:2133)
at org.imgscalr.Scalr.resize(Scalr.java:1667)
at org.imgscalr.Scalr.resize(Scalr.java:1415)
AffineTransform:
Exception in thread "Thread-2" java.awt.image.ImagingOpException: Unable to invert transform AffineTransform[[0.0, 0.0, 0.0], [0.0, 1.0, 0.0]]
at java.awt.image.AffineTransformOp.validateTransform(AffineTransformOp.java:558)
at java.awt.image.AffineTransformOp.<init>(AffineTransformOp.java:151)
Jak mogę to zrobić? Rozumiem, że tak się dzieje, ponieważ zmienię zmienną w inny sposób i uzyskuję do niej dostęp w innej. Ale tych dwóch metod nie można łączyć. Czy mogę w jakiś sposób to wykonać?
EDIT:
zmieniłem metodę zmiany rozmiaru Oto co zrobiłem teraz
public static BufferedImage resizeImage(BufferedImage image, double scalewidth, double scaleheight){
BufferedImage img = new BufferedImage(image.getWidth(), image.getHeight(),BufferedImage.SCALE_FAST);
Graphics2D g = img.createGraphics();
g.scale(scalewidth, scaleheight);
g.drawImage(image, null, 0, 0);
g.dispose();
return image;
}
EDIT (2):
Dla jaśniejszego pojęcia, co się dzieje dokładnie:
To jest metoda, która ponownie Okazuje scrwidth i scrheight
public static void showOnScreen(int screen, JFrame framenew)
{
GraphicsEnvironment ge = GraphicsEnvironment
.getLocalGraphicsEnvironment();
GraphicsDevice[] gs = ge.getScreenDevices();
for (int i = 0; i < gs.length; i++) {
screenwidth.add(gs[i].getDisplayMode().getWidth());
screenheight.add(gs[i].getDisplayMode().getHeight());
}
scrwidth = screenwidth.get(screenwidth.size()-1);
scrheight = screenheight.get(screenheight.size()-1);
System.out.print(ge);
System.out.print(gs);
if(screen > -1 && screen < gs.length)
{gs[screen].setFullScreenWindow(framenew);}
else if(gs.length > 0)
{gs[0].setFullScreenWindow(framenew);}
else
{throw new RuntimeException("No Screens Found");}}
I to jest ActionListener która zwraca bufwidth i bufheight:
btnNewButton.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e)
{
//Execute when button is pressed
System.out.println("You clicked the button");
int ind = c.getSelectedIndex();
bufx = capx.get(ind);
bufy = capy.get(ind);
bufwidth = capwidth.get(ind);
bufheight = capheight.get(ind);
frame.setVisible(false);
framenew.setVisible(true);
showOnScreen(1,framenew);
aspectRatioWidth = (double) bufwidth/scrwidth;
aspectRatioHeight = (double) bufheight/scrheight;
System.out.print("aspectRatioWidth: ");
System.out.println(aspectRatioWidth);
System.out.print("aspectRatioHeight: ");
System.out.println(aspectRatioHeight);
}
});
I aspectRatios są używane wewnątrz Run:
public void run() {
System.out.print("aspectRatioWidth: ");
System.out.println(aspectRatioWidth);
System.out.print("aspectRatioHeight: ");
System.out.println(aspectRatioHeight);
while(true){
BufferedImage buff = robot.createScreenCapture(new Rectangle(bufx,bufy,bufwidth,bufheight)); // x-coord, y-coord, width, height
BufferedImage resizedbuff = resizeImage(buff, aspectRatioWidth, aspectRatioHeight);}
Więc ... po dokonaniu pewnych zmian (masz dokonał zmienić, które poleciłem?) - co zrobiły twoje zmiany? Czy Twój kod działa? Czy nadal widzisz wyjątek? –
yes Przekonwertowałem liczby na podwójne. To daje właściwą wartość, kiedy wykonać podział wewnątrz metody, która wraca bufwidth, bufheight i wszystkie zmienne Jednak wraca do zera kiedy wydrukować aspectRatioWidth i aspectRatioHeight wewnątrz run() Rozumiem, że to się dzieje, ponieważ po uruchomieniu funkcji run() wartości wszystkich zmiennych nie zostały jeszcze zwiększone. Jak mogę się upewnić, że funkcja run() występuje tylko po zwiększeniu wartości? – newbie2015