How do I initialize a Graphics object in Java? - java

this is the code:
import java.awt.*;
import java.applet.*;
public class anim1 extends Applet{
public void paint (Graphics g)
{
g.drawString("",400,300);
}
public static void main(String ad[])
{
anim1 a=new anim1();
Graphics g1;
a.paint(g1);
}
}
It says that g1 is not initialized. But how do I initialize an abstract class?

Well there are two issues here 1:
Graphics g1;
a.paint(g1);
And you are getting the error that G1 is not initialized. That's because the variable g1 is never set to anything, and that causes a compile error. To get the code to compile, you would need to, at the very least do this:
Graphics g1 = null;
a.paint(g1);
However, that obviously won't help you out too much. You'll get a NullPointerException when you try to run your code. In order to actually cause your graphics to draw you need to this:
anim1 a=new anim1();
Graphics g1 = anim1.getGraphics();
a.paint(g1);
However, that still won't work because Anim1 will not appear on the screen. To get it to appear on the screen you need something like:
import java.awt.*;
import javax.swing.*;
import java.applet.*;
public class So1 extends Applet{
public void paint (Graphics g)
{
g.drawString("hello",40,30);
}
public static void main(String ad[])
{
JFrame jp1 = new JFrame();
So1 a=new So1 ();
jp1.getContentPane().add(a, BorderLayout.CENTER);
jp1.setSize(new Dimension(500,500));
jp1.setVisible(true);
}
}
Now notice, we don't actually call the paint() function ourselves. That's handled by the awt, which actually picks the graphics context, and calls our paint function for us. If you want, though, you can pass in any graphics object you want and ask it to draw on to that. (so if you want to draw your component onto an image, you can do it)
(note, I changed the classname from anim1 to So1)

An applet doesn't need a main method like a regular Java application does. I'd recommend starting with Sun's Applets Tutorial. In particular you may want to skip ahead to the section Life Cycle of an Applet to see how the Graphics object is handled within the applet.

All you need to do is simply remove the main method like so:
import java.awt.*;
import java.applet.*;
public class anim1 extends Applet {
public void paint (Graphics g) {
g.drawString("Hello",100,100);
}
}

instead of a call to paint(Graphics g) you need to invoke the repaint or update method. But for this your class must belong to the hierarchy in the java.awt.Container.
For your class you have overriden the Paint method and in the main you are trying to invoke the paint method. Instead of paint you need to invoke the repaint or update method (if your class is in the hierarchy of java.awt.Container) and the event dispatching system of java invokes your overridden paint method itself.

You should manipulate the graphics of a component within the paint method and invoke repaint() or update(), but not the paint method directly.
Start here for some more information.

You dont initialize a Graphics object.
You get the graphics object from a component via Component#getGraphics() method.
In your particular case I think repaint() is all you need!!

You don't, you use getGraphics, but, if you really want to initialize it, then type new Graphics(){}; And have fun filling all the abstract methods. Most of the times just putting code in paint(g) should do, you need to remember to set your applet visible, and usually, it should be the last line in your constructor or even outside it, I have made a mistake once where I made visible and then initialized a bunch of variables, it showed a black screen for a while.

Related

Paint and PaintComponent Methods in JPanel

I am having trouble in understanding the difference between the paint and the paintComponent methods defined in the JPanel class. To put you in context, I am trying to draw a chess table; the following is part of the code I have been working on.
package main;
import javax.swing.JPanel;
import java.awt.Graphics;
import java.awt.Color;
public class Panell extends JPanel {
public Panell() {
}
public void paintComponent(Graphics g) {
super.paintComponent(g);
g.drawRect(100, 100, 400, 400);
}
#Override
public void paint(Graphics g){
boolean white=true;
for(int y=0;y<8;y++){
for(int x=0;x<8;x++){
if(white){
g.setColor(new Color(235, 235, 208));
}
else{
g.setColor(new Color(119, 148, 85));
}
g.fillRect(x*15, y*15, 15, 15);
white=!white;
}
white=!white;
}
}
}
One of my first questions is Are they runned automatically? Also, since they apparently do the same thing, which is to "paint", is it recommended to merge this two methods in one? Which would be the name of this one method?
I'm pretty new to Java and so any help will be very much appeciated. Thanks!
I have been following multiple tutorials online but any of them mentioned my question. I suppose it might be a really indepth topic, but I would really like to know the answer. I have tried everything that I have said in the question and I always end up painting one thing over the other, hence I asked myself if it would be better to only have one single paint method (by merging them), but by doing that, another question arises, Why would they implement another method to do exacly the same as another method?.
Are they runned automatically?
No. They are actually called by the windowing system when the Component needs to be repainted (i.e. first shown, resized, user calls repaint())
Also, since they apparently do the same thing, which is to "paint", is
it recommended to merge this two methods in one?
The difference between paint and paintComponent is that in Swing, JComponent implements paint to call paintBorder, paintChildren, and paintComponent in the proper (expected) order. So normally if you are subclassing a J-whatever in Swing, it is better to override paintComponent, not paint

why is a new Graphics object not passed to paintComponent method in Java swing?

I am reading swing tutorial. From what is mentioned there:
The paintComponent method of JComponent is automatically called
when a frame is drawn/re-drawn.
But, what I do not understand is what is the Graphics Object that is passed to it. I do not see
any new object of Graphics type being instanstiated and passed. so how does all this happen?
public void paintComponent(Graphics g){
Graphics2D g2 = (Graphics2D)g;
g2.drawimage(image,x,y,null);
//
}
I guess it is a similar situation with actionlisteners. But in this case, The actionPerformed is called automatically when event occurs such as button click and the events gets passed to the actionPerformed. There is no need to separately call this method and pass the Actionevent object. But I do not understand how it happens with paintComponent method.
button.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent event){
//do something
}
});
Thanks
The Graphics object is created by the paint sub system.
You should never be calling paintComponent yourself and should simply allow the paint system deal with it. Even if you wanted to capture or print the component using your Graphics context (from something like BufferedImage), you should be using print or printAll
Take a look at Painting in AWT and Swing
They are similar issues. The Graphics object is created by the Swing library at the request o the JVM and passed into the paintComponent(Graphics g) method when the JVM makes this method call. Because you yourself are not directly calling this method, you never see the object being created.

Jr Java-er Wants to Pass Params to Paint

I'm currently able to draw rectangles, elipses, and lines in Java by means of adding a component that extends JComponent in which I modify a paintComponent method:
public class myComponent extends JComponent
{
public void paintComponent(Graphics g)
{
/* do simple draw stuff */
}
}
I also know how to have my class extend either JApplet or JPanel and then draw in a paint method:
public class myClass extends JPanel
{
public void paint(Graphics g)
{
/* do simple draw stuff */
}
}
But, both of these methods suffer from not allowing me to pass them parameters. In the case of a multiframe animated sprite, I could conceivably have some external variable that it reads to determine the frame number and then internally draws only the appropriate "sprite" contents based on that frame number, but I'd prefer to be able to pass the frame number to it directly. Unfortunately, not only do I not know where this is called from, I don't know where to the the Graphics g that it requires as input.
There may be a better way to accomplish what I want, to directly communicate with the draw routine to tell it to draw only what I want, whenever I desire, but I don't know how to accomplish this.
If such a method is possible, how would that be done?
If it is better to use the existing paint or paintComponent methods, how can I best pass additional information to them?
Apparently I wasn't clear in what I asked. I wish to have a component or other entity that has its own paintComponent or paint method, inside of which, based on either a frameNumber parameter that is passed to it, or apparently-more-likely, a class property such as frameNumber that it can access, the method determines which frame of a sprite to draw.
Importantly, though, I wish to be able to re-call paint or paintComponent to redraw the sprite when the frame number changes. My big confusion comes in not knowing how to re-call the method, which, to the best of my understanding, only is called when the frame is resized or otherwise redrawn.
So, how can I redraw my component/object/entity, frame-by-frame?
Firstly, don't override paint, use paintComponent.
Secondly, you need to define some kind of model which records the state of all the graphical objects. When paintComponent is called, you then need to render that state. Instead of trying to pass parameters to the paint methods, you should have a method which allows the paint methods to access the model (ie getModel) which is passed to the component at some earlier time.
Then the update engine would update the model and the component would paint that model
For an example ... Use a timer when a key is pressed
I could conceivably have some external variable that it reads to determine the frame number and then internally draws only the appropriate "sprite" contents based on that frame number
Your class would need to have some internal state, i.e. instance variables.
You can then inspect those within the paint method.
Think "member variables":
public class MyClass extends JPanel {
private final int frameNumber;
public MyClass() {
this(0);
}
public MyClass(int f) {
this.frameNumber = f;
}
public void paint(Graphics g)
{
if (this.frameNumber == x) {
/* do simple draw stuff */
}
}
}

Why isn't my string being displayed in the window?

I am trying to create a simple application that shows a red circle that when clicked displays different messages under it. I believe that this part of the code:
g.drawString("DO NOT PRESS", 100, 100);
is coded correctly but no text is displayed on the window that opens. Here is the full code so far:
import java.awt.Graphics;
import javax.swing.JFrame;
public class BigRedButton extends JFrame {
public BigRedButton() {
setTitle("Big Red Button");
setSize(500, 500);
setResizable(false);
setVisible(true);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
public void graphics(Graphics g) {
g.drawString("DO NOT PRESS", 100, 100);
}
public static void main(String[] args){
new BigRedButton();
}
}
There is no such method graphics in JFrame, so nothing is calling it.
You should avoid painting directly to top level containers, apart from everthing else, they're not double buffered and will flicker when painted. You should, instead, create a custom component (extending from something like JPanel) and override it's paintComponent method.
You should take the time to read through Performing Custom Painting, Painting in AWT and Swing and 2D Graphics
Also, while your reading up, you should have a read through Initial Threads
Amendment
As pointed out by Andrew, you should use the #Override annotation to ensure that the method you think you are overriding is actually the method being overridden in the first place. This would stop the program from being compiled and save lots of lost time trying to figure out why things aren't working the way you expect them.

Paint, repaint , paintComponent

excuse me i search a lot to find how those 3 functions (paint, repaint, paintComponent) interact between them but i have no idea. Can you explain me exactly when they are called ( because sometimes java call it without me asking him) what they do exactly and what is the difference between them. Thank you
I am not sure about "paint", but I can explain the relationship between repaint() and paintComponent().
In my limited experience with java, the paintComponent() method is a method in the JPanel class and is a member of "swing".
The paintComponent() method handles all of the "painting". Essentially, it draws whatever you want into the JPanel usings a Graphic object.
repaint() is an inherited instance method for all JPanel objects. Calling [your_JPanel_object].repaint() calls the paintComponent() method.
Every time you wish to change the appearance of your JPanel, you must call repaint().
Certain actions automatically call the repaint() method:
Re-sizing your window
Minimizing and maximizing your window
to name a few.
IN SHORT paintComponent() is a method defined in JPanel or your own custom class that extends JPanel. repaint() is a method called in another class (such as JFrame) that eventually calls paintComponent().
here is an example:
public class MyPanel extends JPanel{
public void paintComponent(Graphics g){
super.paintComponent(g);
g.draw([whatever you want]);
...
...
}
}
public class MyFrame extends JFrame{
public MyFrame(){
MyPanel myPanel = new MyPanel();
myPanel.repaint();
}
}

Categories

Resources