Absolute Positioning Image Icons in java swing - java

So I am trying to write for my project essentially a pokemon battle between 3 different pokemon using java swing. However the part which is stalling me is the animations. I tried using a null layout with setLocation so that I can move the imageicons based on a timer but the issue is, as you probably know, the imageicons won't show up in the null layout. Is there anyway to change it so that it will work this way.
This is how I have declared my pictures
java.net.URL torterraPic = getClass().getResource("torterra-1.gif");
ImageIcon torterra = new ImageIcon(new ImageIcon(torterraPic).getImage().getScaledInstance(100, 100, Image.SCALE_DEFAULT));
then I place my Image Icon in a JLabel which I add to the frame and then I do setLocation to chose where it goes.
I understand that it is discouraged to use absolute positioning but I feel that this is the best way to do this (assuming it is possible to add a picture) because that way I can manipulate the setLocation to make it move upwards during the attack. I have tried using gridbag and grid layout to try to do it but neither are as convenient for me.
So if there is someway to make this workout please tell me.
Thanks in advance!

No need to use null layouts and component absolute positioning since your image sprites shouldn't be JLabels or other components but rather create BufferedImage sprites and then draw them in a single drawing JPanel's paintComponent method as per the painting tutorials -- Lesson: Performing Custom Painting.
Draw the background image(s) first in a static position, and then move the position of the sprites via g.drawImage(...) override's x and y parameters. Drive the animation via a Swing Timer which uses an ActionListener or via other listeners such as Key Bindings.

I tried using a null layout with setLocation so that I can move the imageicons based on a timer but the issue is, as you probably know, the imageicons won't show up in the null layout.
Yes they will but you are now responsible to doing the layout manager functions, which means you need to set the location and size of the label.
Typically you would do something like:
label.setIcon(...);
label.setSize( label.getPreferredSize() ):
label.setLocation(...);
Then in your animation you just change the location as desired.

JLabel label=new JLabel("");
Image img=new ImageIcon(this.getClass().getResource("hancie.png")).getImage();
label.setIcon(new ImageIcon(img));
label.setBounds(10,50,200,200);
label.setBorder(new LineBorder(Color.BLACK,4));
frame.add(label);

Related

Java Layer JPanels

I need to layer JPanels but I don't know how. I have 3 panels, the first is for the background, the second is for a Character/Sprite to move around and layers the first panel(background, and the third is a bar off to the side (Used for buttons and has nothing to do with they layers). How do I layer panel 1 and panel 2?
edit: The background is made up of a grid of 25x25 labels with an icon in each.
Some options:
Use a JLayeredPane which can layer components using a z-order Integer constant. Remember that when doing this, you are also essentially using a null layout, and so you will be fully responsible for setting the size and position of all components added to the JLayeredPane.
If all the background is doing is painting an image, you could use a single JPanel, and then simply paint the image as a BufferedImage that is displayed in the JPanel's paintComponent method. The sprite would also be painted but its location would vary.
See How to Use Layered Panes.
Don't forget to use:
panel.setOpaque(false);
Or you don't need to layer panels. You can just paint a background image on the panel. See Background Panel for an example of this.
We just recently worked on a top-down video game for my CSC class. All we did was draw the background and then all the sprites after it in the paint() method on the JPanel. We also used a Timer and an ActionListener to constantly update the JPanel.

Adding JPanel to Canvas

Since JPanel and Canvas are both same-level components, the solution would probably be some sort of a 'hack'. This question says that you won't be able to add the lightweight component to the heavyweight canvas (I want JPanel transparent).
If this isn't posible, then would putting a transparent Component work? Also, is it feasible to add Swing components to the Component (it just has to work, even if it's bad). And how would I go about actually putting it over the canvas (since they are both same-level components)?
Note: I would never do something like this in a real app, I just need it in this case
One possiblity is to add the JPanel to whatever container the Canvas is on, then setting the color of the JPanel to have an alpha of 0. This should add it over the old one, without blocking out the Canvas. Is this what you want?
EDIT: Thinking about it, the JPanel's default color is transparent... You should just be able to add the JPanel the Canvas's parent, and lay it over it

permanent background image on a JPanel

I am building a swing interface for drawing overlays over a particular image. I have found several examples of how to draw an image on a JPanel, and I am able to do this without difficulty. However, I would like to keep this image completely static while dynamically drawing overlays on top of it. With that in mind, it would be better if I could set the image as a permanent background of the panel, rather than having paintComponent() redraw the image every time. This would be particularly useful, as there will frequently be situations where I want to removeAll() graphics currently on the panel and redraw new ones.
So my question is this: is there a way to set a permanent background image in JPanel, or do I have to redraw the image every time paintComponent() is called?
put Image as Icon / ImageIcon to the JLabel
use this JLabel instread of JPanel
JLabel hasn't implemented any LayoutManager in compare with JFrame(BorderLayout) or JPanel(FlowLayout)
you have to define the proper LayoutManager, that accepting PreferredSize came its child(s)
then there are accesible (almost nearly) all methods as for JPanel, as container works
maybe you can try putting the Jpanel inside another Jpanel. You draw the image on the container JPanel. then make your inner JPanel a transparent one. this way, when there are no objects on it, you see the background of the parent JPanel which did not change.

Resizing a JPanel with resampling to preserve content

Give that I have written a JPanel with many different components on it, is there a way to apply an overall "dilate" ability on the panel so that everything in it stretches proportionally when I resize my window?
That is, if I manually resize my window to be 1/4 the size, everything in the panel should also shrink by 1/4 so the new panel is just a dilation of the first. Given that I have not designed the individual components inside to do this (there are many) is there any easy way to make the panel behave this way?
UPDATE: In order to be more clear on the solution I need, I will describe the panel contents:
The panel is a "game" of sorts, with a single null-layout and dozens of ImageIcons flying around the screen at any time. The ImageIcons are preloaded PNG files, which already have a permanent size. Of course, I could manually resize each ImageIcon and reposition them relative to window size, but that would involve recoding many components.
There are no buttons or text to worry about, so what I'm really looking for is some kind of "postprocessed" resize where the panel simply shrinks whatever's rendered by some porportion (think of resizing an image in Photoshop).
One option is of course to give up swing all together and use some 3rd party widget component library which draws itself using any Graphics. Then you can either draw the widgets on the image and resize the image, or, better yet, apply a transform to the graphics object you pass to the library.
If you do want to stick with swing there is the SwingUtilities.paintComponent method, which you could use to paint the Panel onto a BufferedImage which you could then resize. (I've used this myself to do some nice transitions between "views" in a game.)
The problem is of course that you somehow need to translate the user input accordingly. I have no solution for this right now, but the above perhaps helps you in some way.
You can try to override paintChildren() method of the panel and scale graphics to achieve desired visible size.
You could try J(X)Layer, see http://www.pbjar.org/blogs/jxlayer/jxlayer40/
Using layout managers instead of absolute positioning of the widgets will give you this behaviour. See the oracle tutorials: Using Layout Managers.
Do you really want fonts to resize on resize events? I don't know a layout manager which will do that for you.

Is this possible to do with images in java?

Is there any way I can print/show images on top of each other. The picture on top will always be positioned a little lower so that the one under will show partially. How can I decide which image is on top of what image? What layout lets me do this kind of positioning?
Is there any way that I can make a border appear on the image when I click it, and then move to (doesnt have to be animated, can be a "jump") where I click next inside the JFrame.
I've been trying to do this whole day now (I'm pretty new to swing), before I carry on I'd like to know if I'm trying something impossible.
So far I've been printing the images right on to the JFrame as JPanels... Inside the JPanel I add in the paintComponent(Graphics g) method: g.drawImage
Sounds like a Swing tutorial is in order.
What you're describing shouldn't be very hard. Instead of painting the images directly, load them up in ImageIcons, and pass those to JLabels. That way you can manipulate your images as JComponents, using layout managers, or direct coordinates by setting the layout to null. You can set the Z-Order with setComponentZOrder regardless of the layout you choose. You can draw borders by adding swing borders (see BorderFactory) to the JLabels. You can handle the manipulation with MouseListeners.
Look into Root Panes. You may be able to do something with the Layered Pane or the Glass Pane. I would try the Layered Pane first.

Categories