diff --git a/bin/SigShare.jar b/bin/SigShare.jar index f07544d..29dfa90 100644 Binary files a/bin/SigShare.jar and b/bin/SigShare.jar differ diff --git a/bin/screenshot.jpg b/bin/screenshot.jpg new file mode 100644 index 0000000..e8b8116 Binary files /dev/null and b/bin/screenshot.jpg differ diff --git a/bin/screenshot_out.jpg b/bin/screenshot_out.jpg new file mode 100644 index 0000000..e69de29 diff --git a/bin/screenshot_part.jpg b/bin/screenshot_part.jpg new file mode 100644 index 0000000..5af4793 Binary files /dev/null and b/bin/screenshot_part.jpg differ diff --git a/src/sig/SigShare.java b/src/sig/SigShare.java index d4f6279..b232e00 100644 --- a/src/sig/SigShare.java +++ b/src/sig/SigShare.java @@ -1,20 +1,18 @@ package sig; -import java.io.BufferedInputStream; import java.io.BufferedOutputStream; import java.io.BufferedReader; import java.io.DataInputStream; import java.io.DataOutputStream; import java.io.File; import java.io.FileInputStream; +import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStreamReader; -import java.io.OutputStream; -import java.io.PrintWriter; import java.net.ServerSocket; import java.net.Socket; -import java.util.Arrays; +import java.util.HashMap; import java.util.Iterator; import java.util.regex.Pattern; @@ -24,7 +22,6 @@ import javax.imageio.ImageWriteParam; import javax.imageio.ImageWriter; import javax.imageio.stream.ImageOutputStream; import javax.swing.JFrame; -import java.awt.Toolkit; import sig.engine.Panel; import java.awt.AWTException; @@ -38,8 +35,18 @@ public class SigShare { static Robot r; public static final String PROGRAM_NAME="SigShare"; public static double SCREEN_MULT=2; - public static int SCREEN_WIDTH=(int)(GraphicsEnvironment.getLocalGraphicsEnvironment().getMaximumWindowBounds().getWidth()/SCREEN_MULT); - public static int SCREEN_HEIGHT=(int)(GraphicsEnvironment.getLocalGraphicsEnvironment().getMaximumWindowBounds().getHeight()/SCREEN_MULT); + public static int REGION_X_COUNT = 8; + public static int REGION_Y_COUNT = 8; + public static int SCREEN_WIDTH=((int)(GraphicsEnvironment.getLocalGraphicsEnvironment().getMaximumWindowBounds().getWidth()/SCREEN_MULT)/REGION_X_COUNT)*REGION_X_COUNT; + public static int SCREEN_HEIGHT=((int)(GraphicsEnvironment.getLocalGraphicsEnvironment().getMaximumWindowBounds().getHeight()/SCREEN_MULT)/REGION_Y_COUNT)*REGION_Y_COUNT; + public static int[] img = new int[SCREEN_WIDTH*SCREEN_HEIGHT]; //Store the number of changes in the last 8 bits of ints. Use 2 ints per section, meaning an 8x8 section uses 128 integers to store 64 values. + public static int CHANGE_THRESHOLD = 1000; + public static char[] changes = new char[REGION_X_COUNT*REGION_Y_COUNT]; + public static int REGION_WIDTH = SCREEN_WIDTH/REGION_X_COUNT; + public static int REGION_HEIGHT = SCREEN_HEIGHT/REGION_Y_COUNT; + public static long LAST_CLEANUP = System.currentTimeMillis(); + public static int CLEANUP_FREQUENCY = 2000; + public static HashMap REGION_CHECK = new HashMap<>(); public static void main(String[] args) throws AWTException { r = new Robot(); if (args.length==2&&args[1].equalsIgnoreCase("server")) { @@ -68,21 +75,73 @@ public class SigShare { } }*/ int frame=0; + CaptureScreen(SCREEN_WIDTH,SCREEN_HEIGHT); + FileInputStream stream = new FileInputStream(new File("screenshot.jpg")); + while (stream.available()>0) { + clientOutput.writeByte(stream.read()); + } + stream.close(); + BufferedImage image = ImageIO.read(new File("screenshot.jpg")); + for (int y=0;y0) { - clientOutput.writeByte(stream.read()); - } - stream.close(); - for (int i=0;i<10;i++) { - clientOutput.writeChar('-'); + boolean fullCleanup=false; + BufferedImage newCapture = CaptureScreen(SCREEN_WIDTH,SCREEN_HEIGHT); + REGION_CHECK.clear(); + for (int y=0;y=5000) { + if (!REGION_CHECK.containsKey((char)(gridY*REGION_X_COUNT+gridX))) { + performSubimageUpdate(in, clientOutput, newCapture, gridX, gridY); + } + fullCleanup=true; + } else + if (currentPixel!=newPixel) { + img[y*newCapture.getWidth()+x]=newPixel; + if (gridY*REGION_X_COUNT+gridX>=changes.length) { + System.out.println(gridY+"/"+REGION_X_COUNT+"/"+gridX+" "+x+","+y); + } + //System.out.println("Changes ("+gridX+","+gridY+"): "+changes[gridY*REGION_X_COUNT+gridX]); + if (!REGION_CHECK.containsKey((char)(gridY*REGION_X_COUNT+gridX))) { + changes[gridY*REGION_X_COUNT+gridX]+=2; + if (gridY>0) { + changes[(gridY-1)*REGION_X_COUNT+gridX]+=1; + } + if (gridY0) { + changes[(gridY)*REGION_X_COUNT+(gridX-1)]+=1; + } + if (gridX=CHANGE_THRESHOLD) { + performSubimageUpdate(in, clientOutput, newCapture, gridX, gridY); + } + } + } + } } - System.out.println("Frame "+frame+++" processed. Waiting on client."); - while (!in.ready()) { + if (fullCleanup) { + LAST_CLEANUP=System.currentTimeMillis(); } - System.out.println("Client no longer idle."); - in.readLine(); } } catch (IOException e) { e.printStackTrace(); @@ -109,56 +168,106 @@ public class SigShare { String line; if (in.available()>0) { line=in.readLine(); - System.out.println(line); - if (line.contains("DESKTOP")) { - String[] split = line.split(Pattern.quote(" ")); - - SCREEN_WIDTH=Integer.parseInt(split[1]); - SCREEN_HEIGHT=Integer.parseInt(split[2]); - p.init(SCREEN_WIDTH,SCREEN_HEIGHT); - - f.add(p); - f.setSize(SCREEN_WIDTH,SCREEN_HEIGHT); - f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); - f.setVisible(true); + System.out.println(line); + if (line.contains("DESKTOP")) { + String[] split = line.split(Pattern.quote(" ")); + + SCREEN_WIDTH=Integer.parseInt(split[1]); + SCREEN_HEIGHT=Integer.parseInt(split[2]); + p.init(SCREEN_WIDTH,SCREEN_HEIGHT); + + f.add(p); + f.setSize(SCREEN_WIDTH,SCREEN_HEIGHT); + f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); + f.setVisible(true); - int frame=0; - int dashCount=0; - BufferedOutputStream stream = null; - while (true) - { - while (in.available()>0) { - if (stream==null) { - //System.out.println("Stream opened."); - stream=new BufferedOutputStream(new FileOutputStream(new File("screenshot_out.jpg"),true)); + int frame=0; + int dashCount=0; + BufferedOutputStream stream = null; + while (true) { + while (in.available()>0) { + if (stream==null) { + //System.out.println("Stream opened."); + stream=new BufferedOutputStream(new FileOutputStream(new File("screenshot_out.jpg"),true)); + } + int val = in.read(); + stream.write(val); + //System.out.print((char)val); + if (val=='-') { + dashCount++; + } else + if (val!=0) { + dashCount=0; + } } - int val = in.read(); - stream.write(val); - if (val=='-') { - dashCount++; - } else - if (val!=0) { + if (dashCount>=10) { + stream.close(); + stream=null; dashCount=0; + System.out.println("Frame "+frame+++" processed."); + BufferedImage i = ImageIO.read(new File("screenshot_out.jpg")); + if (i!=null) { + for (int y=0;y=10) { - stream.close(); - stream=null; - dashCount=0; - System.out.println("Frame "+frame+++" processed."); - BufferedImage i = ImageIO.read(new File("screenshot_out.jpg")); - if (i!=null) { - for (int y=0;y0) { + if (regionInfo==-1) { + regionInfo=in.read(); + } else { + while (in.available()>0) { + if (stream==null) { + //System.out.println("Stream opened."); + stream=new BufferedOutputStream(new FileOutputStream(new File("screenshot_out.jpg"),true)); + } + int val = in.read(); + stream.write(val); + if (val=='-') { + dashCount++; + } else + if (val!=0) { + dashCount=0; + } + } + if (dashCount>=10) { + stream.close(); + stream=null; + dashCount=0; + System.out.println("Frame "+frame+++" processed."); + BufferedImage i = ImageIO.read(new File("screenshot_out.jpg")); + if (i!=null) { + int yy=0; + for (int y=(regionInfo/REGION_X_COUNT)*REGION_HEIGHT;y<(regionInfo/REGION_X_COUNT)*REGION_HEIGHT+REGION_HEIGHT;y++) { + int xx=0; + for (int x=(regionInfo%REGION_X_COUNT)*REGION_WIDTH;x<(regionInfo%REGION_X_COUNT)*REGION_WIDTH+REGION_WIDTH;x++) { + Panel.pixel[y*SCREEN_WIDTH+x]=i.getRGB(xx,yy); + xx++; + } + yy++; + } + } + System.out.println("Region ("+(regionInfo%REGION_X_COUNT)+","+(regionInfo/REGION_X_COUNT)+") updated."); + System.out.println("Waiting for region data..."); + regionInfo=-1; + out.writeChars("Done\r\n"); + stream=new BufferedOutputStream(new FileOutputStream(new File("screenshot_out.jpg"),false)); } } } - out.writeChars("Done\r\n"); - stream=new BufferedOutputStream(new FileOutputStream(new File("screenshot_out.jpg"),false)); } } - } } } } catch (IOException e) { @@ -169,9 +278,32 @@ public class SigShare { return; } } - private static void CaptureScreen(int w, int h) throws IOException { + private static void performSubimageUpdate(BufferedReader in, DataOutputStream clientOutput, BufferedImage newCapture, int gridX, + int gridY) throws IOException, FileNotFoundException { + FileInputStream stream; + changes[gridY*REGION_X_COUNT+gridX]=0; + GetSubimage(newCapture, gridX*REGION_WIDTH, gridY*REGION_HEIGHT, REGION_WIDTH, REGION_HEIGHT); + System.out.println("Preparing to send region("+gridX+","+gridY+")."); + stream = new FileInputStream(new File("screenshot_part.jpg")); + clientOutput.writeByte(gridY*REGION_X_COUNT+gridX); + while (stream.available()>0) { + clientOutput.writeByte(stream.read()); + } + stream.close(); + for (int i=0;i<10;i++) { + clientOutput.writeChar('-'); + } + System.out.println("Region sent, waiting for reply."); + while (!in.ready()); + in.readLine(); + System.out.println("Client no longer idle."); + REGION_CHECK.put((char)(gridY*REGION_X_COUNT+gridX),true); + /*x=(x/REGION_WIDTH)*REGION_WIDTH+REGION_WIDTH; + y=(y/REGION_HEIGHT)*REGION_HEIGHT+REGION_HEIGHT;*/ + } + private static BufferedImage CaptureScreen(int w, int h) throws IOException { //BufferedImage screenshot = toBufferedImage(r.createScreenCapture(GraphicsEnvironment.getLocalGraphicsEnvironment().getMaximumWindowBounds()).getScaledInstance(w, h, Image.SCALE_DEFAULT)); - + BufferedImage screenshot; ImageOutputStream ios = ImageIO.createImageOutputStream(new File("screenshot.jpg")); Iterator iter = ImageIO.getImageWritersByFormatName("jpeg"); ImageWriter writer = iter.next(); @@ -179,10 +311,15 @@ public class SigShare { iwp.setCompressionMode(ImageWriteParam.MODE_EXPLICIT); iwp.setCompressionQuality(0.8f); writer.setOutput(ios); - writer.write(null, new IIOImage(resizeImage(r.createScreenCapture(GraphicsEnvironment.getLocalGraphicsEnvironment().getMaximumWindowBounds()),w,h),null,null),iwp); + writer.write(null, new IIOImage(screenshot=resizeImage(r.createScreenCapture(GraphicsEnvironment.getLocalGraphicsEnvironment().getMaximumWindowBounds()),w,h),null,null),iwp); writer.dispose(); - //return screenshot; + return screenshot; + } + private static BufferedImage GetSubimage(BufferedImage screenshot, int x, int y, int w, int h) throws IOException { + BufferedImage newimg = screenshot.getSubimage(x, y, w, h); + ImageIO.write(newimg,"jpeg",new File("screenshot_part.jpg")); + return newimg; } static BufferedImage resizeImage(BufferedImage originalImage, int targetWidth, int targetHeight) throws IOException { Image resultingImage = originalImage.getScaledInstance(targetWidth, targetHeight, Image.SCALE_SMOOTH);