class
es to represent types of objects public class Person {
private String name; // an individual's name
public Person (String name) {
this.name = name;
}
public String getName() {return name;}
public void sayGreeting () {System.out.println(name + ": Hello there!");}
}
public class Student {
private String name; // an individual's name
private String institution;
public Student (String name, String institution) {
this.name = name;
this.institution = institution;
}
public String getName() {return name;}
public void sayGreeting () {System.out.println(name + ": What's Up?");}
}
public class Student {
private String name; // same as Person
private String institution;
public Student (String name, String institution) {
this.name = name; // same as Person
this.institution = institution;
}
public String getName() {return name;} // same as Person
public void sayGreeting () {System.out.println(name + ": What's Up?");}
}
Why should we make a whole new class just to make minor modifications to the Person
class?
institution
fieldGiven Person
, we can make a subclass Student
that
extends
Making Student
a subclass:
public class Student extends Person {
private String institution;
public Student (String name, String institution) {
super(name); // call the constructor for the superclass
this.institution = institution;
}
@Override
public void sayGreeting () {System.out.println(name + ": What's up?");}
}
Student.java:10: error: name has private access in Person
public void sayGreeting () {System.out.println(name + ": What's up?");}
^
1 error
private
variables and methods cannot be called from subclassesgetName()
name
to protected
protected
methods/variables Student alice = new Student("Alice", "Amherst College");
Person bob = new Person("Bob");
alice.sayGreeting(); // prints "Alice: What's up?"
bob.sayGreeting(); // prints "Bob: Hello there!"
public class BouncingDisk {
public static final int DEFAULT_RADIUS = 25;
private Pair curPosition; // position of the center
private Pair curVelocity; // disk velocity (px / sec)
private Pair nextPosition; // position in next frame
private Pair nextVelocity; // velocity in next frame
private double radius;
private Color color;
private World world; // the world to which the disk belongs
public BouncingDisk(World world, double radius, Color color, Pair position, Pair velocity) {
this.world = world;
this.radius = radius;
this.color = color;
curPosition = new Pair(position);
curVelocity = new Pair(velocity);
nextPosition = new Pair(position);
nextVelocity = new Pair(velocity);
}
public void update (double time) {
Pair delta = curVelocity.times(time);
nextPosition.set(curPosition.plus(delta));
bounce();
}
public void advance () {
curPosition.set(nextPosition);
curVelocity.set(nextVelocity);
}
public void setPosition(Pair p){
curPosition.set(p);
}
public void setVelocity(Pair v){
curVelocity.set(v);
}
public void draw(Graphics g) {
g.setColor(color);
g.fillOval( (int) (curPosition.getX() - radius),
(int) (curPosition.getY() - radius),
(int) (2 * radius), (int) (2 * radius));
}
private void bounce() {
// more code here
}
}
Modifications:
width
and height
(instead of radius)position
, velocity
, etc protected
so subclasses can see these fieldsdraw(Graphics g)
method
abstract
Note. We cannot make instances of of abstract classes, but we can define subclasses that are not abstract
.
import java.awt.Color;
import java.awt.Graphics;
import java.util.Random;
public abstract class BouncingShape {
public static final int DEFAULT_WIDTH = 25;
public static final int DEFAULT_HEIGHT = 25;
protected Pair curPosition; // position of the center
protected Pair curVelocity; // disk velocity (px / sec)
protected Pair nextPosition; // position in next frame
protected Pair nextVelocity; // velocity in next frame
protected double width;
protected double height;
protected Color color;
protected World world; // the world to which the disk belongs
public BouncingShape(World world, double width, double height, Color color, Pair position, Pair velocity) {
this.world = world;
this.width = width;
this.height = height;
this.color = color;
curPosition = new Pair(position);
curVelocity = new Pair(velocity);
nextPosition = new Pair(position);
nextVelocity = new Pair(velocity);
}
public void update (double time) {
Pair delta = curVelocity.times(time);
nextPosition.set(curPosition.plus(delta));
bounce();
}
public void advance () {
curPosition.set(nextPosition);
curVelocity.set(nextVelocity);
}
public void setPosition(Pair p){
curPosition.set(p);
}
public void setVelocity(Pair v){
curVelocity.set(v);
}
public abstract void draw(Graphics g);
protected void bounce() {
if (nextPosition.getX() - width / 2 <= 0){
nextVelocity.flipX();
nextPosition.setX(width / 2);
} else if (nextPosition.getX() + width / 2 >= world.getWidth()){
nextVelocity.flipX();
nextPosition.setX(world.getWidth() - width / 2);
}
if (nextPosition.getY() - height / 2 <= 0){
nextVelocity.flipY();
nextPosition.setY(height / 2);
} else if (nextPosition.getY() + height / 2 >= world.getHeight()) {
nextVelocity.flipY();
nextPosition.setY(world.getHeight() - height / 2);
}
}
}