Capture a image from the clipboard whenever Print screen is pressed and save it in a file (.doc) using java
Main aim is to copy the data from the clipboard and automatically save it into local disk without going to the desired program (i.e MS Word)- click new - pressing (Ctrl+V) to paste and save it with a name.
The code should perform all of the above three steps automatically.
My Source Code
public class CaptureScreenShot {
private static String DIR ="C:\\QUIS\\";
private static JTextField txtDocNumber;
public static void main(String[] args) throws Exception{
txtDocNumber = new JTextField();
Robot robot = new Robot();
Dimension d = new Dimension(Toolkit.getDefaultToolkit().getScreenSize());
int width = (int) d.getWidth();
int height = (int) d.getHeight();
robot.delay(5000);
Image image = robot.createScreenCapture(new Rectangle(0, 0, width,
height));
BufferedImage bi = new BufferedImage(width, height,
BufferedImage.TYPE_INT_RGB);
Graphics g = bi.createGraphics();
g.drawImage(image, 0, 0, width, height, null);
String fileNameToSaveTo = "C:/QUIS/screenCapture_" + createTimeStampStr() + ".PNG";
String newFile = "C:/QUIS/x" + ".org";
File newFilee = new File(newFile);
writeImage(bi, fileNameToSaveTo, "PNG");
System.out.println("Screen Captured Successfully and Saved to:\n"+fileNameToSaveTo);
Desktop desktop = Desktop.getDesktop();
writeImage(bi, newFile, "org");
desktop.open(newFilee);
}
public static int writeImage(BufferedImage img, String fileLocation,
String extension) {
try {
BufferedImage bi = img;
File outputfile = new File(fileLocation);
ImageIO.write(bi, extension, outputfile);
} catch (IOException e) {
e.printStackTrace();
}
return 1;
}
public static String createTimeStampStr() throws Exception {
Calendar mycalendar = Calendar.getInstance();
SimpleDateFormat formatter = new SimpleDateFormat("yyyyMMdd_hhmmss");
String timeStamp = formatter.format(mycalendar.getTime());
return timeStamp;
}
}
If you are not particular about a java code, you could use some screen capture tool instead. Snagit is a good tool. You could find it on http://www.techsmith.com/snagit.html
Try this sample code, according to your question it will copy contents from clipboard and will generate image file
Clipboard clipboard = Toolkit.getDefaultToolkit().getSystemClipboard();
try {
//Get data from clipboard and assign it to an image.
//clipboard.getData() returns an object, so we need to cast it to a BufferdImage.
BufferedImage image = (BufferedImage)clipboard.getData(DataFlavor.imageFlavor);
//file that we'll save to disk.
File file = new File("image.jpg");
//class to write image to disk. You specify the image to be saved, its type,
// and then the file in which to write the image data.
ImageIO.write(image, "jpg", file);
}
Related
I am trying to merge two TIFF images which are in form of FileInputStream into a single Tiff image. Although the image is getting merged the output file is coming up as Black. While comparing the original image and the converted image I could see that the bit depth of the converted image changes to 1. Could anybody provide a solution to this?
The code that I am using is:
public class MergerTiffUsingBuffer {
public static void main(String[] args) {
File imageFile1 = new File("D:/Software/pdfbox-1.3.1.jar/tiff/FLAG_T24.TIF");
File imageFile2 = new File("D:/Software/pdfbox-1.3.1.jar/tiff/CCITT_3.TIF");
try {
FileInputStream fis1 = new FileInputStream(imageFile1);
FileInputStream fis2 = new FileInputStream(imageFile2);
List<BufferedImage> bufferedImages=new ArrayList<>();
List<FileInputStream> inputStreams=new ArrayList<>();
inputStreams.add(fis1);
inputStreams.add(fis2);
Iterator<?> readers = ImageIO.getImageReadersByFormatName("tiff");
ImageReader reader = (ImageReader) readers.next();
for(FileInputStream inputStream:inputStreams){
ImageInputStream iis = ImageIO.createImageInputStream(inputStream);
reader.setInput(iis);
ImageReadParam param = reader.getDefaultReadParam();
Image image = reader.read(0, param);
BufferedImage bufferedImage = new BufferedImage(image.getWidth(null), image.getHeight(null), BufferedImage.TYPE_INT_RGB);
OutputStream out = new FileOutputStream("D:/Software/pdfbox-1.3.1.jar/tiff/MergedTiff.TIF");
BufferedImage binarized = new BufferedImage(bufferedImage.getWidth(), bufferedImage.getHeight(),BufferedImage.TYPE_BYTE_BINARY);
ImageIO.write(binarized, "tiff", out);
bufferedImages.add(bufferedImage);
}
System.out.println(bufferedImages.size());
} catch (IOException e2) {
e2.printStackTrace();
}
}
}
You seem to be a little confused about how to copy image data. Simply creating a new, blank image, by passing the dimensions of another image, will not copy it... So a fully black image is what I would expect after running your code.
Replace your for loop with something like this:
for (FileInputStream inputStream : inputStreams) {
ImageInputStream iis = ImageIO.createImageInputStream(inputStream);
reader.setInput(iis);
BufferedImage image = reader.read(0, null); // a) BufferedImage is returned! b) null param is fine!
BufferedImage binarized = new BufferedImage(image.getWidth(), image.getHeight(), BufferedImage.TYPE_BYTE_BINARY);
// The following 7 lines is the important part you were missing:
Graphics2D g = binarized.createGraphics();
try {
g.drawImage(image, 0, 0, null);
}
finally {
g.dispose();
}
OutputStream out = new FileOutputStream("D:/Software/pdfbox-1.3.1.jar/tiff/MergedTiff.TIF");
ImageIO.write(binarized, "tiff", out); // You probably want to check return value (true/false)!
bufferedImages.add(image);
}
I'm trying to read 2 image files, then merge image2 on top of image1, but the code below does not seem to work. After saving, I only see image1 as original.
Both images are PNG.
String url= uploadPath + filename;
BufferedImage im = ImageIO.read(url);
String url2= "image2.png";
BufferedImage im2 = ImageIO.read(url);
Graphics2D g = im.createGraphics();
g.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER, 0.8f));
g.drawImage(im2, im.getWidth()/2, im.getHeight()/2, null);
g.dispose();
ImageIO.write(im, "png", new File( url ));
What did I miss here?
Thanks
I had no issues getting it to work.
I did find this line...
g.drawImage(im2, im.getWidth()/2, im.getHeight()/2, null);
Of a little concern. It MIGHT be possible to render the image outside of the background image, if the image sizes are just right. You should be using coordinates that are relative to the master image...
public class MergeImages {
public static void main(String[] args) {
File inner = new File("Inner.png");
File outter = new File("Outter.png");
try {
BufferedImage biInner = ImageIO.read(inner);
BufferedImage biOutter = ImageIO.read(outter);
System.out.println(biInner);
System.out.println(biOutter);
Graphics2D g = biOutter.createGraphics();
g.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER, 0.8f));
int x = (biOutter.getWidth() - biInner.getWidth()) / 2;
int y = (biOutter.getHeight() - biInner.getHeight()) / 2;
System.out.println(x + "x" + y);
g.drawImage(biInner, x, y, null);
g.dispose();
ImageIO.write(biOutter, "PNG", new File("Outter.png"));
} catch (Exception e) {
e.printStackTrace();
}
}
}
I'd also double check shuangwhywhy suggestion of making sure you not reading in the same file twice ... I did that some thing when testing the code :P
Your problem is im2 is exactly the same as im:
BufferedImage im = ImageIO.read(url);
BufferedImage im2 = ImageIO.read(url);
I guess it is a typo: it should be url2 rather than url to be read as im2, Am I right?
BufferedImage im2 = ImageIO.read(url2);
You can also try SRC_ATOP with the transparency 0.5.
So I'm trying to write my encoded buffered image to an output stream but I can't get any data to come through on the stream... Could anyone tell me what I'm doing wrong and why I can't see any output?
I would expect that when I call the write.encodeVideo method that it encode's video into my ByteArrayOutputStream... is that assumption wrong?
ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
// video parameters
final int videoStreamIndex = 0;
final int videoStreamId = 0;
final long frameRate = DEFAULT_TIME_UNIT.convert(15, MILLISECONDS);
final int width = 512;
final int height = 254;
long nextFrameTime = 0;
// create a media writer and specify the output file
final IMediaWriter writer = ToolFactory.makeWriter("aaa.ogg");
IContainer ic = writer.getContainer();
ic.open(outputStream, writer.getContainer().getContainerFormat(), true, false);
ICodec codec = ICodec.guessEncodingCodec(null, null,"aaa.ogg", null, ICodec.Type.CODEC_TYPE_VIDEO);
// add the video stream
writer.addVideoStream(videoStreamIndex, videoStreamId, codec, width, height);
BufferedImage img = null;
try
{
img = ImageIO.read(new File("/data/aaa.png"));
}
catch (final IOException e)
{
e.printStackTrace();
}
for(int yy =0; yy < 2048-height; yy=yy+8)
{
nextFrameTime++;
BufferedImage frame = new BufferedImage(width, height, BufferedImage.TYPE_3BYTE_BGR);
frame = img.getSubimage(0, yy, width, height);
BufferedImage frame2 = convertToType(frame, BufferedImage.TYPE_3BYTE_BGR);
//encode the video
writer.encodeVideo(videoStreamIndex, frame2, nextFrameTime, DEFAULT_TIME_UNIT);
nextFrameTime += frameRate;
}
writer.close();
outputStream.flush();
outputStream.close();
I believe the way you are creating the IMediaWriter is incorrect. You don't want to open the writer's container yourself either. When you are using an OutputStream instead of a file you can do it by using the com.xuggle.xuggler.io.XugglerIO mapper like this:
// create a media writer and specify the output stream
final IMediaWriter writer = ToolFactory.makeWriter(XugglerIO.map(outputStream));
// manually set the container format (because it can't detect it by filename anymore)
IContainerFormat containerFormat = IContainerFormat.make();
containerFormat.setOutputFormat("ogg", null, "application/ogg");
mWriter.getContainer().setFormat(containerFormat);
// add the video stream
writer.addVideoStream(videoStreamIndex, videoStreamId, ICodec.ID.CODEC_ID_THEORA, width, height);
Keep in mind that if you are trying to create a format that has to be able to "seek" within the output bytes as part of it's creation process (e.g. .mov), then it won't work with a simple OutputStream as I have shown. You would have to write to a file instead of an OutputStream.
Is it possible to feed an array of image names into code which converts images to greyscale?
I am able to convert an image into greyscale by using this code:
public static void makeGrey() {
try{
//Read in original image.
BufferedImage image = ImageIO.read(new File("images\\012.jpg"));
//Obtain width and height of image.
double image_width = image.getWidth();
double image_height = image.getHeight();
BufferedImage bimg = null;
BufferedImage img = image;
//Draw the new image.
bimg = new BufferedImage((int)image_width, (int)image_height, BufferedImage.TYPE_BYTE_GRAY);
Graphics2D gg = bimg.createGraphics();
gg.drawImage(img, 0, 0, img.getWidth(null), img.getHeight(null), null);
//Save new greyscale (output) image.
String temp = "_inverted";
File fi = new File("images\\" + temp + ".jpg");
ImageIO.write(bimg, "jpg", fi);
}
catch (Exception e){
System.out.println(e);
}
}
However, this code only works on a single file at a time and I would like to know how to go about getting it to work through all files located in the images directory?
I have created an array which goes through the images directory and stores the names of all of the files and I would like to know how to pass these filenames into my makeGrey() method?
static File dir = new File("images");
static File imgList[] = dir.listFiles();
public static void listFiles(String imageName) {
if(dir.isDirectory()){
for(File img : imgList){
if(img.isFile()){
MakeGrey.makeGrey();
}
}
}
Thank you.
Your makeGray() method should look like this:
public static void makeGrey(File image) {
try{
//Read in original image.
BufferedImage inputImage = ImageIO.read(image);
...
...
//Save new greyscale (output) image. (Or you'll rewrite same image all the time...)
File fi = new File("images\\inverted_" + image.getName()
...
...
and other part of the code should call it like this:
static File dir = new File("images");
static File imgList[] = dir.listFiles();
public static void listFiles(String imageName) {
if(dir.isDirectory()){
for(File img : imgList){
if(img.isFile()){
MakeGrey.makeGrey(img);
}
}
}
Is it possible to generate a new image name for each image that is processed using the following code (I have highlighted the relevant section)?
public static void makeBinary(File image) {
try{
//Read in original image.
BufferedImage inputImg = ImageIO.read(image);
//Obtain width and height of image.
double image_width = inputImg.getWidth();
double image_height = inputImg.getHeight();
//New images to draw to.
BufferedImage bimg = null;
BufferedImage img = inputImg;
//Draw the new image.
bimg = new BufferedImage((int)image_width, (int)image_height, BufferedImage.TYPE_BYTE_BINARY);
Graphics2D gg = bimg.createGraphics();
gg.drawImage(img, 0, 0, img.getWidth(null), img.getHeight(null), null);
// ************* THIS IS WHERE I AM HAVING DIFFICULTY ***************
//Save new binary (output) image.
String temp = "_inverted";
File fi = new File("images\\" + temp + ".jpg");
ImageIO.write(bimg, "jpg", fi);
// ******************************************************************
}
catch (Exception e){
System.out.println(e);
}
}
I have 300 images, numbered 001.jpg - 300.jpg, and what I would like is for each new outputted image to be named something along the lines of, binary_001.jpg - binary_300.jpg.
The method that calls makeBinary() is located in another class and is:
public static void listFiles() {
File dir = new File("images");
File imgList[] = dir.listFiles();
if(dir.isDirectory()){
for(File img : imgList){
if(img.isFile()){
MakeBinary.makeBinary(img);
System.out.println(img + ": processed successfully.");
}
else{
System.out.println("Directory detected; skipping to next file,");
}
}
}
}
How can I go about achieving this?
Many thanks.
Get the filename from your File image parameter and add it to the new filename:
String temp = image.getName() + "_inverted";
File fi = new File("images\\" + temp + ".jpg");
ImageIO.write(bimg, "jpg", fi);
You can just concatenate name from the original image (in your code 'image' you pass to ImageIO with the string "_inverted", this way you would have original name for each image you process: image.jpg -> image_inverted.jpg
File fi = new File("images\\" + "binary_" + image.getName());
Should do the trick.
Or even better:
File fi = new File(image.getParent(), "binary_" + image.getName());