So I have this canvas, a BufferedImage, and I have two default calls where I make a line and a circle. My issue here is that I'm trying to call, lets say drawCircle(...) in when a user lets say put 1 into the textfield and sumbit it with enter like this:
if (input.equals("1")){
System.out.println("drawCircle");
DrawCanvas drawCanvas = new DrawCanvas();
drawCanvas.drawCircle(330,310,50);
}
But when I write 1 in the textfield and submit that, I only get the system output "drawCircle", but the circle is not shown?
I thought that my reprint() would update it, but it doesn't, so I'm a bit stuck..
Here is the code I use for making the circle and line and so on:
package DrawCanvas;
import javax.swing.*;
import java.awt.*;
import java.awt.image.BufferedImage;
public class DrawCanvas extends JPanel {
final private BufferedImage canvas;
final private Color def_c = Color.BLACK; final private Color def_bg = Color.LIGHT_GRAY;
public DrawCanvas() {
int width = 1280; int height = 720;
canvas = new BufferedImage(width, height, BufferedImage.TYPE_INT_ARGB);
fillCanvas(def_bg);
int x0 = 0;
int x1 = 100;
int y0 = 0;
int y1 = 100;
//drawRect(Color.RED, 0, 0, width/2, height/2);
drawLine(def_c, x0, y0, x1, y1);
//drawLineRecInit(Color.yellow, x0, y0+2, x1, y1+2);
drawCircle(300,300,100);
}
#Override
public Dimension getPreferredSize() {
return new Dimension(canvas.getWidth(), canvas.getHeight());
}
#Override
public void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2 = (Graphics2D) g;
g2.drawImage(canvas, null, null);
}
public void fillCanvas(Color c) {
int color = c.getRGB();
for (int x = 0; x < canvas.getWidth(); x++) {
for (int y = 0; y < canvas.getHeight(); y++) {
canvas.setRGB(x, y, color);
}
}
repaint();
}
// Implementation from Wikipedia: https://en.wikipedia.org/wiki/Bresenham%27s_line_algorithm#All_cases
public void drawLine(Color c, int x0, int y0, int x1, int y1)
{
int dx = Math.abs(x1-x0);
int sx = x0 < x1 ? 1 : -1;
int dy = -Math.abs(y1-y0);
int sy = y0 < y1 ? 1 : -1;
int err = dx + dy; /* error value e_xy */
while (true) /* loop */
{
canvas.setRGB(x0, y0, c.getRGB());
if (x0 == x1 && y0 == y1) break;
int e2 = 2*err;
if (e2 >= dy) /* e_xy+e_x > 0 */
{
err += dy;
x0 += sx;
}
if (e2 <= dx) /* e_xy+e_y < 0 */
{
err += dx;
y0 += sy;
}
}
repaint();
}
public void drawCircle(int x_center, int y_center, int r){
// inspiration : https://www.gatevidyalay.com/mid-point-circle-drawing-algorithm/
Color c = def_c;
int x=r, y=0, p = 1-r;
// checking for radius of circle
if(r==0){
drawPoint(x_center,y_center,c);
}
if(r<0)
return;
// initialising point p
while(x>y){
y++;
if (p < 0) {
p = p + 2 * y + 1;
} else {
x--;
p = p+2*y-2*x+1;
}
//print all octaves
drawPoint(x + x_center,y + y_center,c); // 1. (x,y)
drawPoint(y + x_center,x + y_center,c); // 1. (y,x)
drawPoint(y + x_center,-x + y_center,c); // 4. (y,-x)
drawPoint(x + x_center,-y + y_center,c); // 4. (x,-y)
drawPoint(-x + x_center,-y + y_center,c); // 3. (-x,-y)
drawPoint(-y + x_center,-x + y_center,c); // 3. (-y,-x)
drawPoint(-y + x_center,x + y_center,c); // 2. (-y,x)
drawPoint(-x + x_center,y + y_center,c); // 2. (-x,y)
}
//show
repaint();
}
void drawPoint(int x,int y,Color c){
canvas.setRGB(x,y, c.getRGB());
}
}
My User interface
import DrawCanvas.DrawCanvas;
import TextDemo.TextDemo;
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.Locale;
public class GUI extends JPanel{
public static void main(String[] args){
//Schedule a job for the event dispatch thread:
//creating and showing this application's GUI.
javax.swing.SwingUtilities.invokeLater(new Runnable() {
public void run() {
createAndShowGUI();
}
});
}
private static void createAndShowGUI() {
int width = 1280; int height = 720;
//Create and set up the window.
JFrame frame = new JFrame();
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setSize(width, height);
frame.setLayout(new BorderLayout(3,3));
JPanel panel1 = new JPanel();
JPanel panel2 = new JPanel();
JPanel panel3 = new JPanel();
panel1.setBackground(Color.red);
panel2.setBackground(Color.green);
panel3.setBackground(Color.yellow);
panel1.setPreferredSize(new Dimension(200, 100));
panel2.setSize(new Dimension(500, 500));
panel3.setPreferredSize(new Dimension(100, 100));
//Add contents to the window.
//frame.add(panel1,BorderLayout.WEST);
frame.add(new TextDemo(),BorderLayout.WEST);
frame.add(new DrawCanvas(),BorderLayout.CENTER);
frame.add(panel3,BorderLayout.SOUTH);
//Display the window.
frame.pack();
frame.setVisible(true);
}
}
This is where the user can ener a text
package TextDemo;
import DrawCanvas.DrawCanvas;
import java.awt.*;
import java.awt.event.*;
import java.util.Locale;
import javax.swing.*;
public class TextDemo extends JPanel implements ActionListener {
protected JTextField textField;
protected JTextArea textArea;
private final static String newline = "\n";
public static Boolean circle = false;
public TextDemo() {
super(new GridBagLayout());
textField = new JTextField(20);
textField.addActionListener(this);
textArea = new JTextArea(5, 20);
textArea.setEditable(false);
JScrollPane scrollPane = new JScrollPane(textArea);
//Add Components to this panel.
GridBagConstraints c = new GridBagConstraints();
c.gridwidth = GridBagConstraints.REMAINDER;
c.fill = GridBagConstraints.BOTH;
c.weightx = 1.0;
c.weighty = 1.0;
add(scrollPane, c);
c.weightx = 0;
c.weighty = 0;
c.fill = GridBagConstraints.HORIZONTAL;
add(textField, c);
}
public void actionPerformed(ActionEvent evt) {
String text = textField.getText();
textArea.append(text + newline);
//Make sure the new text is visible, even if there
//was a selection in the text area.
textArea.setCaretPosition(textArea.getDocument().getLength());
System.out.println("String is: " + textField.getText().toLowerCase(Locale.ROOT).replaceAll("\\s+",""));
String input = textField.getText().toLowerCase(Locale.ROOT).replaceAll("\\s+","");
if (input.equals("1")){
System.out.println("Here");
DrawCanvas drawCanvas = new DrawCanvas();
drawCanvas.drawCircle(330,310,50);
}
textField.setText("");
}
}
Related
I have been trying very hard these past days to understand Graphics2d. I do understand the shapes an all, however I can not draw a simple Graph with it.
My Goal is to draw a Coordinate System, that you can change its length if you want to. Like you say the min x Value would be -5 and the max x Value would be 10 and it would scale it self to it and the function too. However I have a really big Problem just creating and scaling the axis correctly. I think this just comes from a high not understanding everything correctly. This is why I would be glad if someone could help me with this matter.
Here is the code I have been working on. It is absolutely not finished. However I would like to get the scaling and all right. But ever other correction is gladly welcomed, due to me being a newbie in java.
I also tried to make it that if like min x would be positive there would be no x axis. Which just does not work.
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.FocusAdapter;
import java.awt.event.FocusEvent;
public class GraphPlotter extends JFrame {
//f(x) = ax² + bx + c
//Knöpfe
private JButton _ploten = new JButton("Plot");
private JButton _limits = new JButton("Limits");
//Text
private JLabel _funk = new JLabel("f(x) =");
private JLabel _x2 = new JLabel("x² +");
private JLabel _x = new JLabel("x +");
private JLabel _xmin = new JLabel("X min");
private JLabel _ymin = new JLabel("Y min");
private JLabel _ymax = new JLabel("Y max");
private JLabel _xmax = new JLabel("X max");
private String _nummber = "0";
//Textfelder
private JTextField _a = new JTextField(_nummber, 3);
private JTextField _b = new JTextField(_nummber, 3);
private JTextField _c = new JTextField(_nummber, 3);
private JTextField _xMinField = new JTextField("-10");
private JTextField _xMaxField = new JTextField("10");
private JTextField _yMinField = new JTextField("-10");
private JTextField _yMaxField = new JTextField("10");
//Felder
private JPanel _top = new JPanel();
private JPanel _zoom = new JPanel();
private JPanel _graph = new Graph();
public GraphPlotter() {
setDefaultCloseOperation(EXIT_ON_CLOSE);
setSize(500, 500);
setTitle("Graph Plotter");
//Alignment
_funk.setAlignmentX(Component.CENTER_ALIGNMENT);
_x2.setAlignmentX(Component.CENTER_ALIGNMENT);
_x.setAlignmentX(Component.CENTER_ALIGNMENT);
_ploten.setAlignmentX(Component.CENTER_ALIGNMENT);
_a.setAlignmentX(Component.CENTER_ALIGNMENT);
_b.setAlignmentX(Component.CENTER_ALIGNMENT);
_c.setAlignmentX(Component.CENTER_ALIGNMENT);
//So if you click on the TextField that it marks it
_a.addFocusListener(new FocusAdapter() {
public void focusGained(FocusEvent fe) {
_a.setSelectionStart(0);
_a.setSelectionEnd(_a.getText().length());
}
});
_b.addFocusListener(new FocusAdapter() {
public void focusGained(FocusEvent fe) {
_b.setSelectionStart(0);
_b.setSelectionEnd(_b.getText().length());
}
});
_c.addFocusListener(new FocusAdapter() {
public void focusGained(FocusEvent fe) {
_c.setSelectionStart(0);
_c.setSelectionEnd(_c.getText().length());
}
});
_xMinField.addFocusListener(new FocusAdapter() {
public void focusGained(FocusEvent fe) {
_xMinField.setSelectionStart(0);
_xMinField.setSelectionEnd(_xMinField.getText().length());
}
});
_xMaxField.addFocusListener(new FocusAdapter() {
public void focusGained(FocusEvent fe) {
_xMaxField.setSelectionStart(0);
_xMaxField.setSelectionEnd(_xMaxField.getText().length());
}
});
_yMinField.addFocusListener(new FocusAdapter() {
public void focusGained(FocusEvent fe) {
_yMinField.setSelectionStart(0);
_yMinField.setSelectionEnd(_yMinField.getText().length());
}
});
_yMaxField.addFocusListener(new FocusAdapter() {
public void focusGained(FocusEvent fe) {
_yMaxField.setSelectionStart(0);
_yMaxField.setSelectionEnd(_yMaxField.getText().length());
}
});
//Aktions for the buttons
_ploten.addActionListener(new AbstractAction() {
#Override
public void actionPerformed(ActionEvent e) {
//draw a new function
}
});
_limits.addActionListener(new AbstractAction() {
#Override
public void actionPerformed(ActionEvent e) {
//reskale the Graph
}
});
//Layouts
//Main
setLayout(new GridBagLayout());
GridBagConstraints c = new GridBagConstraints();
c.anchor = GridBagConstraints.FIRST_LINE_START;
c.fill = GridBagConstraints.HORIZONTAL;
c.ipady = 20;
c.gridwidth = 3;
c.gridx = 0;
c.gridy = 0;
add(_top, c);
c.anchor = GridBagConstraints.FIRST_LINE_START;
c.fill = GridBagConstraints.BOTH;
c.weightx = 1.0;
c.gridwidth = 2;
c.gridx = 0;
c.gridy = 1;
add(_graph, c);
c.anchor = GridBagConstraints.FIRST_LINE_END;
c.fill = GridBagConstraints.VERTICAL;
c.weightx = 0.0;
c.weighty = 0.5;
c.ipadx = 20;
c.gridwidth = 1;
c.gridx = 2;
c.gridy = 1;
add(_zoom, c);
//Skalling
_zoom.setLayout(new BoxLayout(_zoom, BoxLayout.PAGE_AXIS));
//Borders to better see the layout
_top.setBorder(BorderFactory.createStrokeBorder(new BasicStroke(5.0f)));
_graph.setBorder(BorderFactory.createStrokeBorder(new BasicStroke(5.0f)));
_zoom.setBorder(BorderFactory.createStrokeBorder(new BasicStroke(5.0f)));
_top.add(_funk);
_top.add(_a);
_top.add(_x2);
_top.add(_b);
_top.add(_x);
_top.add(_c);
_top.add(_ploten);
_zoom.add(_xmin);
_zoom.add(_xMinField);
_zoom.add(_xmax);
_zoom.add(_xMaxField);
_zoom.add(_ymin);
_zoom.add(_yMinField);
_zoom.add(_ymax);
_zoom.add(_yMaxField);
_zoom.add(_limits);
setVisible(true);
}
public class Graph extends JPanel {
Color[] _color = {Color.RED, Color.BLUE, Color.GREEN, Color.YELLOW, Color.MAGENTA, Color.CYAN, Color.ORANGE, Color.PINK};
int c = 0;
int _width;
int _hight;
int _diffX;
int _diffY;
int _midx;
int _midy;
int xMAX;
int xMIN;
int yMAX;
int yMIN;
public void paintComponent(Graphics g) {
_width = getWidth();
_hight = getHeight();
//Max und Min
xMAX = Integer.parseInt(_xMaxField.getText());
xMIN = Integer.parseInt(_xMinField.getText());
yMAX = Integer.parseInt(_yMaxField.getText());
yMIN = Integer.parseInt(_yMinField.getText());
//Diff
_diffX = xMAX + xMIN;
_diffY = yMAX + yMIN;
if (!(xMIN > 0) && !(xMAX < 0)) {
_midx = (_width / 2) - _diffX;
} else {
_midx = 0;
}
if (!(yMIN > 0) && !(yMAX < 0)) {
_midy = (_hight /2) - _diffY;
} else {
_midy = 0;
}
super.paintComponent(g);
Graphics2D g2D = (Graphics2D) g;
drawAxis(g2D);
}
private void drawAxis(Graphics2D g2d) {
g2d.setColor(Color.BLACK);
g2d.setStroke(new BasicStroke(2));
//X-Achse
if (!(xMIN > 0) && !(xMAX < 0)) {
g2d.drawLine(0, _midy, _width, _midy);
}
//Y-Achse
if (!(yMIN > 0) && !(yMAX < 0)) {
g2d.drawLine(_midx, 0, _midx, _hight);
}
//Scales drawing
g2d.setStroke(new BasicStroke(1));
for (int n = 0; n < _width; n = n + 5) {
g2d.drawLine(n + _midx, _midy, n + _midx, _midy + 5);
g2d.drawLine(n - _midx, _midy, n - _midx, _midy + 5);
}
for (int n = 0; n < _hight; n = n +5) {
g2d.drawLine(_midx, n + _midy, _midx - 5, n + _midy);
g2d.drawLine(_midx, n - _midy, _midx - 5, n - _midy);
}
}
private void drawGraph(Graphics2D g2d) {
if (!(Integer.parseInt(_a.getText()) == 0) && !(Integer.parseInt(_b.getText()) == 0) && !(Integer.parseInt(_c.getText())== 0)) {
}
}
}
}
Introduction
Oracle has a helpful tutorial, Creating a GUI With Swing. Skip the Learning Swing with the NetBeans IDE section. Pay particular attention to the Performing Custom Painting section.
I reworked your GUI. Here's what it looks like now.
I move the X and Y axis around so that the graph fits in the drawing area. The minimum and maximum V values are no less than -10 and 10, respectively. I show the calculated Y minimum and maximum values in the entry panel. The X axis and Y axis are not to the same scale.
Explanation
When I create a Swing GUI, I use the model-view-controller (MVC) pattern. This pattern helps me to separate my concerns and focus on one small part of the application at a time.
The application model for a Swing GUI consists of one or more plain Java getter/setter classes.
The view consists of one and only one JFrame and as many JPanels as I need to create the GUI. You can nest multiple simple JPanels to create a complex layout.
The controller consists of one or more Actions or Listeners. There's usually not one controller to "rule them all". Each Action or Listener is responsible for its part of the model and view.
I didn't write all the code at once. I wrote a little and tested a lot. I probably ran 150 - 200 tests of the GUI before I was satisfied.
Model
I created one plain Java getter/setter class, the GraphPlotterModel class. This class holds the X and Y minimum and maximum values, and a java.util.List of Point2D instances that make up the graph. I also define a starting Dimension in pixels for the drawing JPanel. The dimensions of the drawing JPanel can change. One way is to maximize the GUI.
The model also holds the calculation of the quadratic equation. I go from the X minimum to the X maximum, calculating the corresponding Y value. The X and Y values are in units.
View
I started the GUI with a call to the SwingUtilities invokeLater method. This method ensures that the Swing components are created and executed on the Event Dispatch Thread.
I separated the creation of the JFrame from the creation of the JPanels. This allows me to separate my concerns and focus on one small part of the application at a time. The top JPanel is made up of two individual JPanels, one for the title and one for the entry fields. The center JPanel is a standard drawing panel.
Generally, you define Swing components on a JPanel in column, row order. This makes the code easier to read and understand.
The drawing panel has a method to convert units to pixels. This method probably took 1/3 of my total development time. The biggest hurdle is that a standard graph goes up from the Y minimum to the Y maximum and the Y pixels go from top to bottom. I basically use ratios to calculate the pixels.
Controller
There's only one JButton, so there's only one ActionListener. I made it a separate private class because it has a lot of code and I didn't want to have to pass 5 input fields to a separate class. I check to make sure all the inputs are valid double values, but I didn't display any error message.
Code
Here's the complete runnable code. I made all the additional public classes inner classes so I could post the code as one block.
import java.awt.BasicStroke;
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Point;
import java.awt.RenderingHints;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.geom.Point2D;
import java.util.ArrayList;
import java.util.List;
import javax.swing.BorderFactory;
import javax.swing.Box;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextField;
import javax.swing.SwingUtilities;
public class GraphPlotter implements Runnable {
public static void main(String[] args) {
SwingUtilities.invokeLater(new GraphPlotter());
}
private final GraphPlotterModel model;
private final DrawingPanel drawingPanel;
private JTextField aField, bField, cField;
private JTextField xMinField, xMaxField, yMinField, yMaxField;
public GraphPlotter() {
this.model = new GraphPlotterModel();
this.drawingPanel = new DrawingPanel(model);
}
#Override
public void run() {
JFrame frame = new JFrame("Graph Plotter");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(createEntryPanel(), BorderLayout.NORTH);
frame.add(drawingPanel, BorderLayout.CENTER);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
private JPanel createEntryPanel() {
JPanel panel = new JPanel(new BorderLayout());
panel.setBorder(BorderFactory.createEmptyBorder(5, 5, 5, 5));
Font font = panel.getFont().deriveFont(16f);
Font titleFont = panel.getFont().deriveFont(Font.BOLD, 24f);
JPanel titlePanel = new JPanel(new FlowLayout());
titlePanel.setBorder(BorderFactory.createEmptyBorder(0, 5, 0, 5));
JLabel label = new JLabel(
"Plot the quadratic equation f(x) = ax² + bx + c");
label.setFont(titleFont);
titlePanel.add(label);
JPanel entryPanel = new JPanel(new FlowLayout());
entryPanel.setBorder(BorderFactory.createEmptyBorder(0, 5, 5, 5));
label = new JLabel("f(x) =");
label.setFont(font);
entryPanel.add(label);
aField = new JTextField(5);
aField.setFont(font);
entryPanel.add(aField);
label = new JLabel("x² +");
label.setFont(font);
entryPanel.add(label);
bField = new JTextField(5);
bField.setFont(font);
entryPanel.add(bField);
label = new JLabel("x +");
label.setFont(font);
entryPanel.add(label);
cField = new JTextField(5);
cField.setFont(font);
entryPanel.add(cField);
entryPanel.add(Box.createHorizontalStrut(30));
label = new JLabel("X min:");
label.setFont(font);
entryPanel.add(label);
xMinField = new JTextField(5);
xMinField.setFont(font);
entryPanel.add(xMinField);
label = new JLabel("X max:");
label.setFont(font);
entryPanel.add(label);
xMaxField = new JTextField(5);
xMaxField.setFont(font);
entryPanel.add(xMaxField);
label = new JLabel("Y min:");
label.setFont(font);
entryPanel.add(label);
yMinField = new JTextField(5);
yMinField.setEditable(false);
yMinField.setFont(font);
entryPanel.add(yMinField);
label = new JLabel("Y max:");
label.setFont(font);
entryPanel.add(label);
yMaxField = new JTextField(5);
yMaxField.setEditable(false);
yMaxField.setFont(font);
entryPanel.add(yMaxField);
entryPanel.add(Box.createHorizontalStrut(30));
JButton button = new JButton("Plot");
button.addActionListener(new PlotListener());
button.setFont(font);
entryPanel.add(button);
updateEntryPanel();
panel.add(titlePanel, BorderLayout.NORTH);
panel.add(entryPanel, BorderLayout.SOUTH);
return panel;
}
public void updateEntryPanel() {
String formatter = "%.2f";
aField.setText(String.format(formatter, model.getA()));
bField.setText(String.format(formatter, model.getB()));
cField.setText(String.format(formatter, model.getC()));
xMinField.setText(String.format(formatter, model.getxMin()));
xMaxField.setText(String.format(formatter, model.getxMax()));
yMinField.setText(String.format(formatter, model.getyMin()));
yMaxField.setText(String.format(formatter, model.getyMax()));
}
public void repaint() {
drawingPanel.repaint();
}
public class DrawingPanel extends JPanel {
private static final long serialVersionUID = 1L;
private final int margin;
private final GraphPlotterModel model;
public DrawingPanel(GraphPlotterModel model) {
this.model = model;
this.margin = 20;
this.setPreferredSize(model.getDrawingAreaDimension());
}
#Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g;
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
RenderingHints.VALUE_ANTIALIAS_ON);
g2d.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING,
RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
g2d.setRenderingHint(RenderingHints.KEY_FRACTIONALMETRICS,
RenderingHints.VALUE_FRACTIONALMETRICS_ON);
g2d.setColor(Color.BLACK);
g2d.setStroke(new BasicStroke(3f));
int width = getWidth() - margin - margin;
int height = getHeight() - margin - margin;
double xMin = model.getxMin();
double xMax = model.getxMax();
double yMin = model.getyMin();
double yMax = model.getyMax();
// Draw X Axis
Point2D a = new Point2D.Double(xMin, 0.0);
Point2D b = new Point2D.Double(xMax, 0.0);
Point startPoint = toPixels(a, width, height);
Point endPoint = toPixels(b, width, height);
g2d.drawLine(startPoint.x, startPoint.y, endPoint.x, endPoint.y);
// Draw Y axis
a = new Point2D.Double(0.0, yMin);
b = new Point2D.Double(0.0, yMax);
startPoint = toPixels(a, width, height);
endPoint = toPixels(b, width, height);
g2d.drawLine(startPoint.x, startPoint.y, endPoint.x, endPoint.y);
// Draw graph
g2d.setColor(Color.BLUE);
Point previousPoint = null;
List<Point2D> points = model.getPoints();
for (Point2D point : points) {
Point drawPoint = toPixels(point, width, height);
// System.out.println(point + " " + drawPoint);
if (previousPoint != null) {
g2d.drawLine(previousPoint.x, previousPoint.y, drawPoint.x,
drawPoint.y);
}
previousPoint = (Point) drawPoint.clone();
}
}
private Point toPixels(Point2D point, int width, int height) {
double xMin = model.getxMin();
double xMax = model.getxMax();
double yMin = model.getyMin();
double yMax = model.getyMax();
// System.out.println(yMin + " " + yMax);
double xDelta = (xMax - xMin) / width;
double yDelta = (yMax - yMin) / height;
double xx = Math.round((point.getX() - xMin) / xDelta);
double yy = Math.round((point.getY() - yMin) / yDelta);
// X in pixels goes from left to right
int x = (int) xx + margin;
// Y in pixels goes from top to bottom
int y = height - (int) yy + margin;
return new Point(x, y);
}
}
private class PlotListener implements ActionListener {
#Override
public void actionPerformed(ActionEvent event) {
String aString = aField.getText().trim();
String bString = bField.getText().trim();
String cString = cField.getText().trim();
String xMinString = xMinField.getText().trim();
String xMaxString = xMaxField.getText().trim();
double a = valueOf(aString);
if (a == Double.MIN_VALUE) {
return;
}
double b = valueOf(bString);
if (b == Double.MIN_VALUE) {
return;
}
double c = valueOf(cString);
if (c == Double.MIN_VALUE) {
return;
}
double xMin = valueOf(xMinString);
if (xMin == Double.MIN_VALUE) {
return;
}
double xMax = valueOf(xMaxString);
if (xMax == Double.MIN_VALUE) {
return;
}
model.setA(a);
model.setB(b);
model.setC(c);
model.setxMin(xMin);
model.setxMax(xMax);
model.calculatePlot();
updateEntryPanel();
repaint();
}
private double valueOf(String s) {
try {
return Double.valueOf(s);
} catch (NumberFormatException e) {
return Double.MIN_VALUE;
}
}
}
public class GraphPlotterModel {
/** f(x) = ax² + bx + c */
private double a, b, c, xMin, xMax, yMin, yMax;
private final List<Point2D> points;
private final Dimension drawingAreaDimension;
public GraphPlotterModel() {
this.drawingAreaDimension = new Dimension(500, 500);
this.points = new ArrayList<>();
this.xMin = -10.0;
this.xMax = 10.0;
this.yMin = -10.0;
this.yMax = 10.0;
}
public void calculatePlot() {
// steps should be an even number
int steps = 100;
double xDelta = (xMax - xMin) / steps;
double x = xMin;
double yMin = Double.MAX_VALUE;
double yMax = Double.MIN_VALUE;
points.clear();
for (int index = 0; index <= steps; index++) {
double y = a * x * x + b * x + c;
Point2D point = new Point2D.Double(x, y);
points.add(point);
x += xDelta;
yMax = Math.max(yMax, y);
yMin = Math.min(yMin, y);
}
// Make sure that Y goes from -10 to 10 at a minimum
this.yMax = Math.max(yMax, 10.0);
this.yMin = Math.min(yMin, -10.0);
}
public Dimension getDrawingAreaDimension() {
return drawingAreaDimension;
}
public double getA() {
return a;
}
public void setA(double a) {
this.a = a;
}
public double getB() {
return b;
}
public void setB(double b) {
this.b = b;
}
public double getC() {
return c;
}
public void setC(double c) {
this.c = c;
}
public double getxMin() {
return xMin;
}
public void setxMin(double xMin) {
this.xMin = xMin;
}
public double getxMax() {
return xMax;
}
public void setxMax(double xMax) {
this.xMax = xMax;
}
public List<Point2D> getPoints() {
return points;
}
public double getyMin() {
return yMin;
}
public double getyMax() {
return yMax;
}
}
}
I'm new to gui java and I've been trying to recreate the game called" jump it" (http://www.crazygames.com/game/jump-it) and I'm currently on the process of making the randomized rectangles for my character to jump on. However I ran my code and I had no errors, but the rectangles that I made isn't showing up. I attached my code underneath, it's kinda long sorry about that.
import javax.swing.*;
import java.awt.event.*;
import java.awt.*;
import java.util.Random;
import java.util.TimerTask;
class GuiGame{
public static void main(String args[]) {
JFrame f = new JFrame("RUN - Christine & Esther"); //title of frame
Container cont = f.getContentPane(); // get container - top of the frame
cont.setLayout(new BorderLayout());
BtnActPanel bp = new BtnActPanel(); // create an object of our game panel
cont.add(bp, BorderLayout.CENTER );
f.setVisible(true);
f.setSize(975,613); //size of frame
}
}
class Rectangle{
static Random r = new Random();
static int upperX = 100;
static int lowerX = 20;
static int upperY = 550;
static int lowerY = 450;
static int minWidth = 200;
static int maxWidth = 600;
static int minHeight = 40;
static int maxHeight = 140;
static int x = 0, y = 0, w = 0, h = 0, check = 0;
public Rectangle(){
check++;
int x = 650 + 50*check;
int y = r.nextInt(upperY-lowerY + 1) + lowerY; // from 450 to 550
int w = r.nextInt(maxWidth-minWidth + 1) + minWidth; // from 200 to 600
int h = r.nextInt(maxHeight - minHeight + 1) + minHeight; // from 40 to 140
}
public int getx(){
return x;
}
public int gety(){
return y;
}
public int getw(){
return w;
}
public int geth(){
return h;
}
}
class BtnActPanel extends JPanel implements ActionListener{
//variables
private JButton b1, b2, b3;
private JPanel background;
private JPanel game;
private Timer t, timer;
private int x = 0, check1 = 0, index = 0, x1 = 650, count2 = 0,
y2 = (int)(Math.random()*100)+40, y1 = (int)(Math.random()*100)+450,
x2 = (int)(Math.random()*600)+200, xaxis = 0, yaxis = 0, w = 0, h = 0, count = 0;
private ImageIcon []arrImage;
private boolean check2;
private static ImageIcon icon, exitButton, startButton, questionButton, b, instruct, c ;
public BtnActPanel(){
c = new ImageIcon("character.png"); // constructor
t = new Timer (100,this);
arrImage = new ImageIcon[2];
arrImage[0] = new ImageIcon("character.png");
arrImage[1] = new ImageIcon("character2.png");
startButton = new ImageIcon("startButton.png");//start button image
questionButton = new ImageIcon("QuestionButton.png"); //question button image
exitButton = new ImageIcon("exitButton.png"); //exit button image
icon = new ImageIcon("Title.jpg");//title image
b1 = new JButton(questionButton); // creates first button
//only shows button image with borders
b1.setOpaque(false);
b1.setContentAreaFilled(false);
b1.setBorderPainted(false);
b1.setFocusPainted(false);
b2 = new JButton(startButton);// creates second button
//only shows button image with borders
b2.setOpaque(false);
b2.setContentAreaFilled(false);
b2.setBorderPainted(false);
b2.setFocusPainted(false);
b3 = new JButton(exitButton);// creates third button
//only shows button image with borders
b3.setOpaque(false);
b3.setContentAreaFilled(false);
b3.setBorderPainted(false);
b3.setFocusPainted(false);
//adds buttons to code
this.add(b1);
this.add(b2);
this.add(b3);
b1.addActionListener(this);
b2.addActionListener(this);
b3.addActionListener(this);
}// end of constructor
public void actionPerformed(ActionEvent e) { //checks which button the user presses and performs actions based off choice
if(e.getSource() == b1){
check1 = 2;
this.remove(b1);
this.remove(b3);
repaint();
instruct = new ImageIcon("Instructions.jpg");
}
else if (e.getSource() == b2){
t.start();
check1 = 1;
this.remove(b1);
this.remove(b2);
this.remove(b3);
repaint();
b = new ImageIcon("toskyline.png");
}
else if (e.getSource() == b3){
JOptionPane.showMessageDialog(null, "This is an exit button, hope you enjoyed the game! :)", "Exit message",JOptionPane.WARNING_MESSAGE ); //shows exit message
System.exit(0);//exits program
}
else if (e.getSource() == t){
if (index == 0){
index = 1;
c = arrImage[1];
}
else{
index = 0;
c = arrImage[0];
}
if(count%50 == 0 && count >= 50){
Rectangle obstacle = new Rectangle();
int xaxis = obstacle.getx();
int yaxis = obstacle.gety();
int w = obstacle.getw();
int h = obstacle.geth();
xaxis = xaxis - 10;
count2 = 1;
}
x = x - 10;
x1 = x1 - 10;
repaint();
}
}
public void paintComponent(Graphics g){//this method draws and paints images and icons based on the user decisions
super.paintComponent(g);
if(check1 == 0)[enter image description here][1]
g.drawImage(icon.getImage(),0,0,null);
if(check1 == 1){
g.drawImage(b.getImage(),0,0,null);
g.setColor(Color.black);
g.fillRect(x,495, 500, 35);
g.fillRect(x1, y1, x2, y2);
count++;
System.out.println(count);
if(count2 == 1){
g.fillRect(xaxis, yaxis, w, h);
count2 = 0;
}
g.drawImage(c.getImage(), 100, 460, null);
}
if(check1 == 2)
g.drawImage(instruct.getImage(),0,0,null);
b1.setBounds(320, 350, 100, 100);
b2.setBounds(420, 350, 100, 100);
b3.setBounds(520, 350, 100, 100);
}
}//end of class
Using your ranges I made a demo.
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Rectangle;
import java.awt.RenderingHints;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
import javax.swing.Timer;
public class Demo extends JPanel implements ActionListener {
final static int height = 800;
final static int width = 800;
final static String title = "title";
JFrame frame = new JFrame("default title");
Timer timer;
static Random r = new Random();
static int upperX = 100;
static int lowerX = 20;
static int upperY = 550;
static int lowerY = 450;
static int minWidth = 200;
static int maxWidth = 600;
static int minHeight = 40;
static int maxHeight = 140;
List<MyRectangle> rectangles = new ArrayList<>();
public static void main(String[] args) {
SwingUtilities
.invokeLater(() -> new Demo().start());
}
public Demo() {
frame.setDefaultCloseOperation(
JFrame.EXIT_ON_CLOSE);
frame.add(this);
frame.setPreferredSize(
new Dimension(width, height));
setBackground(Color.WHITE);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
public void start() {
timer = new Timer(0, this);
timer.setDelay(1000);
timer.start();
}
public void actionPerformed(ActionEvent ae) {
rectangles.add(createRectangle());
repaint();
}
public void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g.create();
g2d.setRenderingHint(
RenderingHints.KEY_ANTIALIASING,
RenderingHints.VALUE_ANTIALIAS_ON);
for (MyRectangle r : rectangles) {
g2d.setColor(Color.black);
g2d.drawRect(r.x, r.y, r.width, r.height);
g2d.setColor(r.color);
g2d.fillRect(r.x+1, r.y+1, r.width-1,r.height-1);
}
g2d.dispose();
}
Color[] colors = {Color.RED, Color.BLUE, Color.GREEN, Color.ORANGE, Color.GRAY};
int color = 0;
public MyRectangle createRectangle() {
int y = r.nextInt(upperY - lowerY + 1) + lowerY; // from 450 to 550
int w = r.nextInt(maxWidth - minWidth + 1)
+ minWidth; // from 200 to 600
int h = r.nextInt(maxHeight - minHeight + 1)
+ minHeight; // from 40 to 140
int x = r.nextInt(upperX - lowerX + 1) + lowerX;
Color c = colors[color++ % colors.length];
return new MyRectangle(c, x, y, w, h);
}
class MyRectangle extends Rectangle {
Color color;
MyRectangle(Color c, int x, int y, int w, int h) {
super(x, y, w, h);
this.color = c;
}
}
}
This extends the JDK class Rectangle and adds a color field to the subclass. It displays a new rectangle very second.
i try to make a simple java game . ıt work fine but i draw a background but i didn't stop square's color , it always change
i write another class for that and i call it in main but i didn't work it
#SuppressWarnings("serial")
class BackPan extends JFrame{
private JLayeredPane layers;
private JPanel down;
static int width = Board.boardWidth;
static int height = Board.boardHeight;
Random rnd = new Random();
public BackPan(){
layers = new JLayeredPane();
rnd =new Random();
down = new JPanel(){
public void paintComponent(Graphics g){
Graphics2D g2d = (Graphics2D)g;
//***************************************************************
int low = 50;
int high = 255;
for(int i = 0; i<= width; i+=50){
g2d.setColor(new Color(rnd.nextInt(high-low)+low,rnd.nextInt(high-low)+low,rnd.nextInt(high-low)+low));
g2d.fillRect(i, 50, 50, 50);
for(int j = 0; j<= height; j += 50 ){
g2d.setColor(new Color(rnd.nextInt(high-low)+low,rnd.nextInt(high-low)+low,rnd.nextInt(high-low)+low));
g2d.fillRect(i, j, 50, 50);
}
}
}
};
//****************************************************************
down.setBounds(0, 0, width, height);
layers.add(down, new Integer(1));
getContentPane().add(layers, BorderLayout.CENTER);
}
}
Better than using a set seed for your randomization, simply fix the random image by one of two ways:
Create an array of colors that you randomize when needed and then use this array when drawing the background
Even better, simply draw your random colors to a BufferedImage and draw that in the paintComponent method. If this needs to be re-randomized, then re-create the image.
For an example of the latter, note that the image re-randomizes only when the button is pressed (by calling the createBackground() method):
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.event.ActionEvent;
import java.awt.image.BufferedImage;
import javax.swing.*;
#SuppressWarnings("serial")
public class ColorSquares extends JPanel {
public static final int SQR_SIDE = 50;
public static final int COLUMNS = 20;
public static final int ROWS = 16;
private int columns;
private int rows;
private int sqrSide;
private Image backgroundImg;
public ColorSquares(int columns, int rows, int sqrSide) {
this.columns = columns;
this.rows = rows;
this.sqrSide = sqrSide;
backgroundImg = createBackground();
add(new JButton(new AbstractAction("New Background") {
#Override
public void actionPerformed(ActionEvent arg0) {
backgroundImg = createBackground();
repaint();
}
}));
}
public Image createBackground() {
int w = columns * sqrSide;
int h = rows * sqrSide;
BufferedImage img = new BufferedImage(w, h, BufferedImage.TYPE_INT_ARGB);
Graphics g = img.getGraphics();
for (int r = 0; r < rows; r++) {
for (int c = 0; c < columns; c++) {
float hue = (float) Math.random();
float saturation = (float) (Math.random() * 0.5 + 0.5);
float brightness = (float) (Math.random() * 0.5 + 0.5);
Color randColor = Color.getHSBColor(hue, saturation, brightness);
g.setColor(randColor);
int x = c * sqrSide;
int y = r * sqrSide;
g.fillRect(x, y, sqrSide, sqrSide);
}
}
g.dispose();
return img;
}
#Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
if (backgroundImg != null) {
g.drawImage(backgroundImg, 0, 0, this);
}
}
#Override
public Dimension getPreferredSize() {
if (isPreferredSizeSet()) {
return super.getPreferredSize();
}
return new Dimension(columns * sqrSide, rows * sqrSide);
}
private static void createAndShowGui() {
JFrame frame = new JFrame("Colors");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().add(new ColorSquares(COLUMNS, ROWS, SQR_SIDE));
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(() -> createAndShowGui());
}
}
An additional benefit of using a BufferedImage is that it's quicker to draw this than as you're doing it.
The simplest solution would be to remember a constant random seed and set it via rnd.setSeed() each time paintComponent is called. For example:
private final static int SEED = 1000;
rnd.setSeed(SEED);
I am having problem with the JFrame textfield.
I am trying to make a word game, but the problem is that when I try to create textfield to set an input and then check if it's the right word, I have got the word thing covered.
The problem is that when I try to add Textfield, it disappears when i render things to JFrame.
public teksti() {
setTitle("Hirsipuu");
setSize(leveys,korkeus);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setResizable(false);
setVisible(true);
setLocationRelativeTo(null);
setBackground(Color.white);
jp.add(tf); // adding JtextField (JTextField tf = new JTextField(30);)
add(jp);
}
and my render() is like this (just for testing purpose).
private void render() {
BufferStrategy bs = this.getBufferStrategy(); // tehdään uusi bufferi
if (bs == null) {
createBufferStrategy(3);
return;
}
int R = (int) (Math.random( )*256);
int G = (int)(Math.random( )*256);
int B= (int)(Math.random( )*256);
Color randomColor = new Color(R, G, B);
Graphics g = bs.getDrawGraphics();
g.drawString("Arvaa sana", 100 , 100);
g.setColor(Color.white);
g.fillRect(0, 50, leveys, korkeus);
g.setColor(randomColor);
g.setFont(h);
// g.drawLine(0,0,liikey*2-1,liikex);
for(int i = 0; i < salat.size(); i ++) {
g.drawString(salat.get(i),liikex+rand.nextInt(50),liikey+rand.nextInt(50));
}
System.out.println(liikex + " " + liikey);
g.dispose();
bs.show();
g.dispose();
}
I can get the textfield to be displayed on top at the start, but then it disappears.
Anyone knows if there is a better way to do this?
Don't draw directly in a JFrame
Instead, if you need to draw a background image, do so in the paintComponent method of a JPanel. This will likely work much better than using BufferStrategy for your purposes.
Then you can add components, such as your JTextField to this JPanel.
And then add this JPanel to your JFrame.
Always call the super's paintComponent method in your own paintComponent method override.
Be careful to never dispose of a Graphics object given to you from the JVM, such as the one passed into your paintComponent method.
For example:
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.GradientPaint;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Paint;
import javax.swing.*;
public class BackgroundPanel extends JPanel {
private static final int PREF_W = 800;
private static final int PREF_H = 600;
private static final Font PROMPT_FONT = new Font(Font.SANS_SERIF, Font.BOLD,
24);
private Paint gradientPaint;
private JTextField textField = new JTextField(20);
public BackgroundPanel() {
int red = (int) (Math.random() * 256);
int green = (int) (Math.random() * 256);
int blue = (int) (Math.random() * 256);
Color color1 = new Color(red, green, blue);
red = (int) (Math.random() * 256);
green = (int) (Math.random() * 256);
blue = (int) (Math.random() * 256);
Color color2 = new Color(red, green, blue);
gradientPaint = new GradientPaint(0, 0, color1, 20, 20, color2, true);
JLabel promptLabel = new JLabel("Input:");
promptLabel.setFont(PROMPT_FONT);
add(promptLabel);
add(textField);
}
#Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2 = (Graphics2D) g;
g2.setPaint(gradientPaint);
g.fillRect(0, 0, getWidth(), getHeight());
g.setColor(Color.black);
g.setFont(PROMPT_FONT);
g.drawString("Arvaa sana", 100, 100);
}
#Override
public Dimension getPreferredSize() {
if (isPreferredSizeSet()) {
return super.getPreferredSize();
}
return new Dimension(PREF_W, PREF_H);
}
private static void createAndShowGui() {
BackgroundPanel mainPanel = new BackgroundPanel();
JFrame frame = new JFrame("BackgroundPanel");
frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
frame.getContentPane().add(mainPanel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
createAndShowGui();
}
});
}
}
this is basically whole thing i got done now.
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.image.BufferStrategy;
import java.io.BufferedReader;
import java.io.FileReader;
import java.util.ArrayList;
import java.util.Random;
import java.util.Scanner;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JTextField;
public class teksti extends JFrame implements Runnable {
/**
*
*/
private static final long serialVersionUID = 1L;
ArrayList<String> sanat = new ArrayList<String>();
ArrayList<String> salat = new ArrayList<String>();
String dir = System.getProperty("user.dir");
String pathname = dir + "\\src\\kotus_sanat.txt";
Random rand = new Random();
Scanner lukija = new Scanner(System.in);
String syote,salasana,salasana2;
int leveys=500,korkeus=500;
int liikex=300, liikey=300;
Font h = new Font("Helvetica", Font.PLAIN, 18);
JTextField tf = new JTextField(30);
JPanel jp = new JPanel();
JFrame jf = new JFrame();
public teksti() {
setTitle("Hirsipuu");
setSize(leveys,korkeus);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setResizable(false);
setVisible(true);
setLocationRelativeTo(null);
setBackground(Color.white);
jp.add(tf);
add(jp);
}
public static void main(String args[]){
teksti teksti = new teksti();
teksti.start();
}
private void start() {
run();
}
public void run() {
sanat = lataa();
System.out.println(pathname);
System.out.println(sanat.size() + " sanaa ladattu..");
int sanoja=sanat.size();
for (int i = 0; i < 10; i++){
salat.add(sanat.get(rand.nextInt(sanoja)));
}
System.out.println("salasana on " + salasana);
long lastTime = System.nanoTime(); // fps sälää
long timer = System.currentTimeMillis();
final double ns = 1000000000.0 / 60.0;
double delta = 0;
int frames = 0;
int updates = 0;
requestFocus();
boolean running=true;
while (running){
long now = System.nanoTime();
delta += (now-lastTime) / ns;
lastTime = now;
while ( delta >= 1) {
update();
updates++;
delta--;
}
render();
frames++;
if (System.currentTimeMillis() - timer > 1000){
timer += 1000;
setTitle("Hirsipuu"+ " | " + updates + " ups " + frames + " fps" );
updates = 0;
frames = 0;
}
}
}
private void update() {
liikex = liikex + 1;
liikey= liikey - 4;
if (liikey>korkeus)
liikey = 1;
if (liikex>leveys)
liikex= 1;
if (liikey<20)
liikey = korkeus;
}
private void render() {
BufferStrategy bs = this.getBufferStrategy(); // tehdään uusi bufferi
if (bs == null) {
createBufferStrategy(3);
return;
}
int R = (int) (Math.random( )*256);
int G = (int)(Math.random( )*256);
int B= (int)(Math.random( )*256);
Color randomColor = new Color(R, G, B);
Graphics g = bs.getDrawGraphics();
g.drawString("Arvaa sana", 100 , 100);
g.setColor(Color.white);
g.fillRect(0, 50, leveys, korkeus);
g.setColor(randomColor);
g.setFont(h);
// g.drawLine(0,0,liikey*2-1,liikex);
for(int i = 0; i < salat.size(); i ++) {
g.drawString(salat.get(i), liikex+rand.nextInt(50),liikey+rand.nextInt(50));
}
System.out.println(liikex + " " + liikey);
g.dispose();
bs.show();
g.dispose();
}
private void stop() {
}
private void vertaa() {
System.out.println("Anna sana niin tarkastaan onko se oikea suomenkielinen sana: ");
syote = lukija.next();
boolean oikea = false;
int i = 0;
int z = 0;
while (i < sanat.size()) {
if (syote.equals(sanat.get(i))) {
oikea = true;
System.out.println (syote + " on oikea suomalainen sana.");
break;
}
else{
}
}
if (!oikea) {
System.out.println(syote + " ei ole oikea suomalainen sana.");
}
}
public ArrayList<String> lataa() {
String line = null;
try {
BufferedReader reader = new BufferedReader(new FileReader(pathname));
while((line = reader.readLine()) != null){
sanat.add(line);
}
} catch (Exception e) {
e.printStackTrace();
}
return sanat;
}
}
vertaa() is not used.
I have displayed an image(ball) inside the JApplet, now I want the image to move in a vertical way (up and down). The problem is I don't know how to do it.
Could someone has an idea about this matter?
You need to set the position of that image to some calculated value (means you caculate the vertical position using time, speed and maybe other restrictions).
How you'd set that position depends on how you draw the image.
Example, based on drawing in the applet's (or a nested component's) paint(Graphics g) method:
//first calculate the y-position
int yPos += timeSinceLastPaint * speed; //increment the position
if( (speed > 0 && yPos > someMaxY) || (speed < 0 && yPos <0 ) ) {
speed *= -1; //if the position has reached the bottom (max y) or the top invert the direction
}
//in your paint(Graphics g) method:
g.drawImage(image, yPos, x, null);
Then you'd have to constantly repaint the applet.
More information on animations in applets can be found here: http://download.oracle.com/javase/tutorial/uiswing/components/applet.html
another example for javax.swing.Timer with moving Ojbects created by paintComponent(Graphics g), and I have lots of Start, not some blurred Mikado :-)
import java.awt.*;
import java.awt.event.*;
import java.util.*;
import javax.swing.*;
import javax.swing.Timer;
public class AnimationBackground {
private Random random = new Random();
private JFrame frame = new JFrame("Animation Background");
private final MyJPanel panel = new MyJPanel();
private JLabel label = new JLabel("This is a Starry background.", JLabel.CENTER);
private JPanel stopPanel = new JPanel();
private JPanel startPanel = new JPanel();
public AnimationBackground() {
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setResizable(false);
panel.setBackground(Color.BLACK);
for (int i = 0; i < 50; i++) {
Star star = new Star(new Point(random.nextInt(490), random.nextInt(490)));
star.setColor(new Color(100 + random.nextInt(155), 100 + random.nextInt(155), 100 + random.nextInt(155)));
star.setxIncr(-3 + random.nextInt(7));
star.setyIncr(-3 + random.nextInt(7));
panel.add(star);
}
panel.setLayout(new GridLayout(10, 1));
label.setForeground(Color.WHITE);
panel.add(label);
stopPanel.setOpaque(false);
stopPanel.add(new JButton(new AbstractAction("Stop this madness!!") {
private static final long serialVersionUID = 1L;
#Override
public void actionPerformed(ActionEvent e) {
panel.stopAnimation();
}
}));
panel.add(stopPanel);
startPanel.setOpaque(false);
startPanel.add(new JButton(new AbstractAction("Start moving...") {
private static final long serialVersionUID = 1L;
#Override
public void actionPerformed(ActionEvent e) {
panel.startAnimation();
}
}));
panel.add(startPanel);
frame.add(panel);
frame.pack();
frame.setLocation(150, 150);
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
AnimationBackground aBg = new AnimationBackground();
}
});
}
private class Star extends Polygon {
private static final long serialVersionUID = 1L;
private Point location = null;
private Color color = Color.YELLOW;
private int xIncr, yIncr;
static final int WIDTH = 500, HEIGHT = 500;
Star(Point location) {
int x = location.x;
int y = location.y;
this.location = location;
this.addPoint(x, y + 8);
this.addPoint(x + 8, y + 8);
this.addPoint(x + 11, y);
this.addPoint(x + 14, y + 8);
this.addPoint(x + 22, y + 8);
this.addPoint(x + 17, y + 12);
this.addPoint(x + 21, y + 20);
this.addPoint(x + 11, y + 14);
this.addPoint(x + 3, y + 20);
this.addPoint(x + 6, y + 12);
}
public void setColor(Color color) {
this.color = color;
}
public void move() {
if (location.x < 0 || location.x > WIDTH) {
xIncr = -xIncr;
}
if (location.y < 0 || location.y > WIDTH) {
yIncr = -yIncr;
}
translate(xIncr, yIncr);
location.setLocation(location.x + xIncr, location.y + yIncr);
}
public void setxIncr(int xIncr) {
this.xIncr = xIncr;
}
public void setyIncr(int yIncr) {
this.yIncr = yIncr;
}
public Color getColor() {
return color;
}
}
private class MyJPanel extends JPanel {
private static final long serialVersionUID = 1L;
private ArrayList<Star> stars = new ArrayList<Star>();
private Timer timer = new Timer(20, new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
for (Star star : stars) {
star.move();
}
repaint();
}
});
public void stopAnimation() {
if (timer.isRunning()) {
timer.stop();
}
}
public void startAnimation() {
if (!timer.isRunning()) {
timer.start();
}
}
#Override
public void addNotify() {
super.addNotify();
timer.start();
}
#Override
public void removeNotify() {
super.removeNotify();
timer.stop();
}
MyJPanel() {
this.setPreferredSize(new Dimension(512, 512));
}
public void add(Star star) {
stars.add(star);
}
#Override
public void paintComponent(Graphics g) {
super.paintComponent(g);
((Graphics2D) g).setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
for (Star star : stars) {
g.setColor(star.getColor());
g.fillPolygon(star);
}
}
}
}
How to move the image inside the JApplet ..?
Pretty much exactly the same way you might do it in a JFrame, JComponent or JPanel or...
Or to put that another way, nothing to do with applets and everything to do with Graphics2D. For more details, see the 2D Graphics Trail of the Java Tutorial.
When you've figured how to move an image and paint it to a Graphics2D, implement that logic in a JComponent or JPanel's paintComponent(Graphics) method and drop the component with moving image into a JApplet or JFrame (or a JPanel etc.).
For the animation side of it, use a javax.swing.Timer as seen in this example. This example does not extend any component. Instead, it creates a BufferedImage and adds it to a JLabel that is displayed to the user. When the timer fires, the code grabs the Graphics object of the image, and proceeds from there to draw the bouncing lines.
import java.awt.image.BufferedImage;
import java.awt.event.*;
import java.awt.geom.*;
import java.awt.*;
import javax.swing.*;
import java.util.Random;
class LineAnimator {
public static void main(String[] args) {
final int w = 640;
final int h = 480;
final RenderingHints hints = new RenderingHints(
RenderingHints.KEY_ANTIALIASING,
RenderingHints.VALUE_ANTIALIAS_ON
);
hints.put(
RenderingHints.KEY_ALPHA_INTERPOLATION,
RenderingHints.VALUE_ALPHA_INTERPOLATION_QUALITY
);
final BufferedImage bi = new BufferedImage(w,h, BufferedImage.TYPE_INT_ARGB);
final JLabel l = new JLabel(new ImageIcon(bi));
final BouncingLine[] lines = new BouncingLine[100];
int factor = 1;
for (int ii=0; ii<lines.length; ii++) {
lines[ii] = new BouncingLine(w*factor,h*factor);
}
final Font font = new Font("Arial", Font.BOLD, 30);
ActionListener al = new ActionListener() {
int count = 0;
long lastTime;
String fps = "";
private final BasicStroke stroke = new BasicStroke(6);
public void actionPerformed(ActionEvent ae) {
count++;
Graphics2D g = bi.createGraphics();
g.setRenderingHints(hints);
g.setColor(new Color(55,12,59));
g.fillRect(0,0,w,h);
g.setStroke(stroke);
for (int ii=0; ii<lines.length; ii++) {
lines[ii].move();
lines[ii].paint(g);
}
if ( System.currentTimeMillis()-lastTime>1000 ) {
lastTime = System.currentTimeMillis();
fps = count + " FPS";
count = 0;
}
g.setColor(Color.YELLOW);
g.setFont(font);
g.drawString(fps,5,h-5);
l.repaint();
g.dispose();
}
};
Timer timer = new Timer(25,al);
timer.start();
JOptionPane.showMessageDialog(null, l);
//System.exit(0);
timer.stop();
}
}
class BouncingLine {
private final Color color;
private static final Random random = new Random();
Line2D line;
int w;
int h;
int x1;
int y1;
int x2;
int y2;
BouncingLine(int w, int h) {
line = new Line2D.Double(random.nextInt(w),random.nextInt(h),random.nextInt(w),random.nextInt(h));
this.w = w;
this.h = h;
this.color = new Color(
random.nextInt(255)
,random.nextInt(255)
,random.nextInt(255)
,64+random.nextInt(128)
);
x1 = (random.nextBoolean() ? 1 : -1);
y1 = (random.nextBoolean() ? 1 : -1);
x2 = -x1;
y2 = -y1;
}
public void move() {
int tx1 = 0;
if (line.getX1()+x1>0 && line.getX1()+x1<w) {
tx1 = (int)line.getX1()+x1;
} else {
x1 = -x1;
tx1 = (int)line.getX1()+x1;
}
int ty1 = 0;
if (line.getY1()+y1>0 && line.getY1()+y1<h) {
ty1 = (int)line.getY1()+y1;
} else {
y1 = -y1;
ty1 = (int)line.getY1()+y1;
}
int tx2 = 0;
if (line.getX2()+x2>0 && line.getX2()+x2<w) {
tx2 = (int)line.getX2()+x2;
} else {
x2 = -x2;
tx2 = (int)line.getX2()+x2;
}
int ty2 = 0;
if (line.getY2()+y2>0 && line.getY2()+y2<h) {
ty2 = (int)line.getY2()+y2;
} else {
y2 = -y2;
ty2 = (int)line.getY2()+y2;
}
line.setLine(tx1,ty1,tx2,ty2);
}
public void paint(Graphics g) {
Graphics2D g2 = (Graphics2D)g;
g2.setColor(color);
//line.set
g2.draw(line);
}
}
Update 1
I want to do it in JApplet(1) using the image(2), is it possible(3)?
The examples by mKorbel and myself feature either an image in a JLabel or custom rendering in a JPanel. In our case, we added the components to a JOptionPane & a JFrame. Either example could be just as easily added to a JApplet, or a JDialog, or as part of another panel, or.. See the Laying Out Components Within a Container lesson & Using Top-Level Containers in the Java Tutorial for more details.
Instead of the stars or lines in our examples, ..paint your image. My example goes so far as to demonstrate how to get the position to bounce around within the bounds of the container.
Sure it is possible, but "Batteries not included". Our intention is to give you some ideas that you can then adapt to your bouncing ball applet. I doubt anyone is going to create an example for you, using balls, in an applet. Though if you post an SSCCE that shows your intent and what you tried, I (and others) would often run with that source. If you want more specific answers, ask a more specific SSCCE. ;)
I want to do it in JApplet.
Why not both? You can have a hybrid application/applet as shown in this animation.