Encoding transparent animated gif in Java - java

I am using GifDecoder to read an animated .gif file and AnimGifEncoder to write it. (link)
If I display the original frames read by GifDecoder they display correctly and are transparent, but if I display the frames created by AnimatedGifEncoder the transparency is all wrong.
GifDecoder gif = new GifDecoder();
gif.read("image.gif");
AnimatedGifEncoder e = new AnimatedGifEncoder();
e.start("newimage.gif");
e.setTransparent(Color.BLACK);
for (int i=0;i<gif.getFrameCount();i++) {
anim.addFrame(gif.getFrame(i));
anim.setDelay(gif.getDelay(i));
}
anim.finish();
In this example I set the transparent color to black. But actually I want to get the transparent color information from the GifDecoder but I don't know how.

I'm using the following solution, although there are still some gif files that
are a mess after scaling... :
(At least it seems to get along with most non-transparent gifs)
Color transparentColor = null;
BufferedImage firstFrameImage = ImageIO.read([sourceFileHere]);
if (firstFrameImage.getColorModel() instanceof IndexColorModel) {
IndexColorModel cm = (IndexColorModel) firstFrameImage.getColorModel();
int transparentPixel = cm.getTransparentPixel();
transparentColor = new Color(cm.getRGB(transparentPixel), true);
}
e.setTransparent(transparentColor);

This was all a long time ago, but I did manage to get it working at the time. Without digging out the code again... I got it working by:
Scan the original image and set the transparent areas to a colour that does not exist inside the original image.
Set the transparent colour inside the AnimGifEncoder to the colour that was previously assigned to the transparent areas.

Related

JavaFX .setStyle(...) isn't not working when `-fx-background-image` changes

What i want to achieve:
I am using a FileChooser and the user selects an appropriate .jpg image file . Then i am copying that image , renaming it background.jpg to a known folder and trying to set it as the background image of the application using .setStyle(...); There is not problem of copying the image [ i am checking it]
The Problem that occurs:
I have a Stage with a BorderPane . The BorderPane has an background Image , i do that using
borderPane.setStyle("-fx-background-image:url('filepath')");
!It works well the first time!
->Then i am deleting that file [background.jpg] and i am replacing it with another file named also [background.jpg] . The background image of the BorderPane isn't changing ....
I have tried also resetting the same style using again :
borderPane.setStyle("-fx-background-image:url('filepath')");
Finally when i am changing the filename , for example to [background-12.jpg] and reseting the style using the above it changes the background image.
Which exactly is the problem ? I mean i am sure that the background.jpg has been created , i am checking it and also when i am changing the name to something other again and again it works .
Is the Java CSS Parser lazy to parse the new style which is the same but has other -fx-background-image resource ?
As for the File path i am sure it is well , i am using the code below :
//Maou is the File URL in appropriate format for CSS
String maou = file.getAbsoluteFile().toURI().toString()
//Here i add the appropriate file separator, if not JavaFX will report error
maou = maou.replaceAll("\\Q\\\\E", "//");
//Print maou
System.out.println("Maou=\n" + maou);
Solution :
I found as best solution using James_D answer , a little bit modified so it covers the whole window:
BackgroundImage bgImg = new BackgroundImage(image, BackgroundRepeat.NO_REPEAT, BackgroundRepeat.NO_REPEAT, BackgroundPosition.DEFAULT,
new BackgroundSize(window.getWidth(), window.getHeight(), true, true, true, true));
Rather than using an inline style, I would recommend setting the background via the background property directly:
Image img = new Image(file.getAbsoluteFile().toURI().toString());
BackgroundImage bgImg = new BackgroundImage(img,
BackgroundRepeat.NO_REPEAT,
BackgroundRepeat.NO_REPEAT,
BackgroundPosition.DEFAULT,
BackgroundSize.DEFAULT);
borderPane.setBackground(new Background(bgImg));
The Background class provides Java API programmatic access to all the same properties that can be set by CSS.
While I don't know exactly what's going on, presumably it's some form of caching which JavaFX is doing to try to be "helpful". I may look into the source code later.
To be honest, though, setting a background via CSS feels like the wrong approach to me. I always avoid setting any styles explicitly, like:
borderPane.setStyle("something");
and prefer to add and remove style classes:
borderPane.getStyleClass().add("foo");
borderPane.getStyleClass().remove("foo");
I don't think this is possible in your situation, so I would instead use a StackPane
to layer your content over an ImageView.
ImageView img = new ImageView(new Image(new URL("path")));
StackPane stack = new StackPane();
stack.getChildren.addAll(img, /*overlaid content*/);

Partially transparent images in javafx

I am making a project in eclipse. I have uploaded a .png file using 'image view' option.It has some transparent areas .I want to write code such that it only detects the click of the user's mouse when it is over opaque area and take that user to a new window defined by me.
This code should work in most circumstances.
imageView.addEventFilter(MouseEvent.MOUSE_CLICKED, e -> {
Color color = image.getPixelReader().getColor(e.getX(),e.getY()));
if(color.getAlpha() != 0)
{
//execute your code here
}
});

is it right to use batcher.drawSprite to draw all images in game?

I'm developing a game and use batcher.drawSprite method to draw all images in the game (background and all characters)
in assets.java :
charAtlas = new Texture(game, "charAtlas.png");
charEnemy = new TextureRegion(charAtlas, 0,0,250,300);
in worldGame.java :
batcher.beginBatch(Assets.charAtlas); // set atlas
batcher.drawSprite(130, 628, 120,140, Assets.charEnemy);
//assets.charEnemy
is it right to use this method in all condition ?
I have 3 atlas in game , i even use 2048x2048 atlas size so i can include all my images in there..
However, the image looks blurry in game (Tested in galaxy note, tab, and galaxy young). looks at the code above, i even have the enemy char take size in my atlas as much as 250x300 , it's not make sense that it'll look blurry as i only draw it in 120x140.
note : i use no layout (i mean no layout file in res folder) .. i use drawsprite to draw all image (Character,menu, button, etc)..
update :
I tried to use character image files from other game that i unzipped, when i run the app, it also looks blurry and jagged. while in the original game, it's so smooth and sharp. why is that ?
check your code, you might use scaledbitmap , see if you can set like this.
Options options = new BitmapFactory.Options();
options.inScaled = false;
Bitmap source = BitmapFactory.decodeResource(a.getResources(), path, options);

How to save as image an on-screen Canvas3D?

I'm doing a program to create a die (cube) with different image textures based on the input of the user (user choose images on a SWT GUI).
Once the user choose the images, it can visualize the dice on a separate dialog, and perform some rotate operations over it (see, after perform a small rotation to see three faces in the screenshots).
See screenshots: http://pastebin.com/XqJfXL6i
And my problem starts here: I want to save the content of the canvas (the dice with the background in its current form, after being rotated). I've been searching for several codes and I think that my problem is because my current canvas is an "on-screen" canvas and I need an off-screen canvas, which will allow to save the content.
My current code is the following:
http://pastebin.com/ZAv0ATJN
And.. here starts the problem. It throws this exception:
java.lang.IllegalStateException: Canvas3D: Not in off-screen mode
Concretely it fails in this line:
ImageComponent2D ic2d = canvas.getOffScreenBuffer();
As you can see there are several lines commented that I tried before, but they didn't work neither.
Any clue about how to do it?
Thanks!
Based on the comment provided by gouessej (thanks!) finally I use this code, which works fine for my doubt:
private void saveImage(String img) throws Exception {
FileOutputStream fileOut = new FileOutputStream(img);
Robot r = new Robot();
BufferedImage bi = r.createScreenCapture(new java.awt.Rectangle(
(int) frame.getLocationOnScreen().getX(), (int) frame
.getLocationOnScreen().getY(), frame.getBounds().width,
frame.getBounds().height));
ImageIO.write(bi, "jpeg", fileOut);
fileOut.flush();
fileOut.close();
}

displaying a custom map and placing pin/images on the map

i wanted to create a directory app for a grocery. i already have the floor plan of the place. i just wanted to display it in a view and i want to put some markers/pins/images to it.. i have no idea where to start. someone told me to use bitmap and canvass but i have no idea how to use it as the other tutorials in google is quite vague and hard to understand..
what my app requires:
display a custom map from an image source
enable me to put markers,pins and some images on top of it
A simple way is to use use ImageView:
//make a bitmap from your floorPlanImage, example from file
Bitmap floorPlanImage = BitmapFactory.decodeFile(filePath, options);
//make a mutable bitmap, so it can be changed
Bitmap mutableFloorPlanImage = floorPlanImage.copy(Bitmap.Config.ARGB_8888, true);
//create a canvas to draw on your floorPlanImage
Canvas mCanvas = new Canvas(mutableFloorPlanImage);
//draw a marker or another image on the floorPlanImage, you can position it using left and top //coordinates, in this example both 0
mCanvas.drawBitmap(markerBitmap, 0, 0, null);
//show the resulting bitmap in ImageView
imageView.setImageBitmap(mutableFloorPlanImage);

Categories