Created
June 20, 2017 12:14
-
-
Save whizzter/4918800a16d7bd04151f2252239c5aab to your computer and use it in GitHub Desktop.
Small Missile Command Clone
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package missilecommand_java; | |
import java.awt.Color; | |
import java.awt.Graphics; | |
import java.awt.GraphicsDevice; | |
import java.awt.GraphicsEnvironment; | |
import java.awt.event.ActionEvent; | |
import java.awt.event.ActionListener; | |
import java.awt.event.KeyAdapter; | |
import java.awt.event.KeyEvent; | |
import java.awt.event.MouseEvent; | |
import java.awt.event.MouseListener; | |
import java.awt.event.MouseMotionListener; | |
import java.awt.event.MouseWheelEvent; | |
import java.awt.event.MouseWheelListener; | |
import java.awt.event.WindowAdapter; | |
import java.awt.event.WindowEvent; | |
import java.util.Random; | |
import java.util.Vector; | |
import javax.swing.JComponent; | |
import javax.swing.JFrame; | |
import javax.swing.Timer; | |
/** | |
Small missile command clone written quite quickly and without comments | |
*/ | |
public class MissileMain { | |
static class Missile { | |
Integer target; | |
int state=0; | |
long startTime; | |
long endTime; | |
double x,y; | |
double x1,y1; | |
double x2,y2; | |
double blastRad=0; | |
public Missile(Integer target,double x1,double y1,double x2,double y2) { | |
this.target=target; | |
this.x=this.x1=x1; | |
this.y=this.y1=y1; | |
this.x2=x2; | |
this.y2=y2; | |
startTime=System.currentTimeMillis(); | |
double dx=x2-x1; | |
double dy=y2-y1; | |
double len=Math.sqrt( dx*dx + dy*dy ); | |
endTime= (long) (startTime + (target!=null?4500:1000)*len); | |
} | |
public boolean update() { | |
long curTime=System.currentTimeMillis(); | |
if (curTime>endTime) { | |
if (state==0) { | |
state=1; | |
startTime=curTime; | |
endTime=curTime+1000; | |
if (target!=null) { | |
int mask=(~(1<<target))&0x1f; | |
//System.out.println("Destroying:"+Integer.toBinaryString(mask)); | |
int newState=(MissileMain.state.cities&=mask); | |
if (newState==4 || 0==(newState&4)) { | |
MissileMain.state.gameOver=System.currentTimeMillis()+5000; | |
} | |
} | |
} else if (state==1) | |
return false; | |
} | |
if (state==0) { | |
double dist=(curTime-startTime)/(double)(endTime-startTime); | |
double ddist=1-dist; | |
x=((ddist*x1)+(dist*x2)); | |
y=((ddist*y1)+(dist*y2)); | |
for (Missile b:MissileMain.state.missiles) { | |
if (b.state==0) | |
continue; | |
if (!(b.target==null ^ target==null)) | |
continue; | |
double dx=b.x-x; | |
double dy=b.y-y; | |
double bld=Math.sqrt(dx*dx + dy*dy); | |
//System.out.println(bld+" vs "+b.blastRad); | |
if (bld<b.blastRad/2) { | |
state=1; | |
startTime=curTime; | |
endTime=curTime+1000; | |
} | |
} | |
} else { | |
blastRad=0.15*Math.sin(Math.PI*((curTime-startTime)*0.001)); | |
} | |
return true; | |
} | |
} | |
static class State { | |
int w; | |
int h; | |
int cities=0x1f; | |
long prevTime=1; | |
long nextLaunch=System.currentTimeMillis()+3000; | |
long gameOver=0; | |
Vector<Missile> missiles=new Vector<>(); | |
Random rnd=new Random(System.currentTimeMillis()+this.hashCode()); | |
void tick() { | |
long curTime=System.currentTimeMillis(); | |
if (nextLaunch<curTime) { | |
int target=rnd.nextInt(5); | |
missiles.add(new Missile(target,rnd.nextDouble(),0,0.1+0.2*target,0.75)); | |
nextLaunch=curTime+5000; | |
} | |
if (prevTime<(gameOver-2500) && (curTime>=(gameOver-2500))) { | |
cities=0x1f; | |
missiles.clear(); | |
nextLaunch=System.currentTimeMillis()+3000; | |
} | |
for (int i=0;i<missiles.size();) { | |
if (missiles.get(i).update()) | |
i++; | |
else | |
missiles.remove(i); | |
} | |
prevTime=curTime; | |
} | |
} | |
static State state; | |
static int[][] citypx=new int[5][]; | |
static int[][] citypy=new int[5][]; | |
public static void main(String[] args) { | |
final JFrame jfr=new JFrame() { | |
public String toString() { | |
return "apa"; | |
} | |
}; | |
final JComponent cmp=new JComponent() { | |
int toScreenX(double v) { | |
int dim=Math.min(state.w, state.h); | |
int bx=state.w/2-dim/2; | |
//int by=state.h/2-dim/2; | |
return (int)(bx + dim*v); | |
} | |
int toScreenY(double v) { | |
int dim=Math.min(state.w, state.h); | |
//int bx=state.w/2-dim/2; | |
int by=state.h/2-dim/2; | |
return (int)(by + dim*v); | |
} | |
@Override | |
public void paint(Graphics g) { | |
if (state==null) { | |
state=new State(); | |
state.w=getBounds().width; | |
state.h=getBounds().height; | |
int dim=Math.min(state.w, state.h); | |
for (int i=0;i<5;i++) { | |
//if (i!=0) | |
// continue; | |
int d10=dim/10; | |
int d25=dim/25; | |
int d30=dim/30; | |
int cx=(((1+i+i)*dim)/10)+((state.w-dim)/2); | |
int cy=((dim*3)/4)+((state.h-dim)/2); | |
citypx[i]=new int[]{ cx+d10,cx-d10, cx-d25, cx,cx+d25 }; | |
citypy[i]=new int[]{ cy+d10, cy+d10, cy-d25+d10,cy-d30+d10,cy-d25+d10 }; | |
} | |
return; | |
} | |
g.setColor(Color.black); | |
g.fillRect(0, 0, state.w, state.h); | |
g.setColor(new Color(0xc0c0ff)); | |
int dim=Math.min(state.w, state.h); | |
int bx=state.w/2-dim/2; | |
int by=state.h/2-dim/2; | |
int gl=(dim*3)/4; | |
g.fillRect(bx, by, dim, gl); | |
g.setColor(new Color(0x80ff80)); | |
g.fillRect(bx, by+gl, dim, dim/4); | |
g.setColor(Color.black); | |
long curTime=System.currentTimeMillis(); | |
for (Missile m:state.missiles) { | |
g.drawLine(toScreenX(m.x1) , (int)(by + dim*m.y1),(int)(bx + dim*m.x ) , (int)(by + dim*m.y)); | |
if (m.state==1) { | |
double blastRad=m.blastRad; | |
int sz=(int)(dim*blastRad); | |
g.fillOval(toScreenX(m.x)-sz/2, toScreenY(m.y)-sz/2, sz,sz); | |
} | |
} | |
//System.out.println("State:"+Integer.toBinaryString(state.cities)); | |
for (int i=0;i<5;i++) { | |
int cx=toScreenX(0.1+0.2*i); | |
int cy=toScreenY(0.75); | |
int d1=dim/20; | |
int d2=dim/7; | |
boolean alive=0!=((state.cities>>i)&1); | |
if (alive) { | |
if (i==2) { | |
g.fillArc(cx-d1, cy, d1*2, d2, 0, 180); | |
} else { | |
g.fillRect(cx-d1, cy-d2/3, d1*2, d2); | |
} | |
} else { | |
g.fillPolygon(citypx[i], citypy[i], citypx[i].length); | |
} | |
} | |
if (curTime<state.gameOver) { | |
long diff=state.gameOver-curTime; | |
int alpha=(int) (255*Math.abs( Math.sin( Math.PI * 0.001*diff*(1/5.) ) )); | |
g.setColor(new Color( (alpha<<24)|0xffffff ,true)); | |
g.fillRect(bx,by, dim, dim); | |
} | |
} | |
}; | |
jfr.getContentPane().add(cmp); | |
jfr.setUndecorated(true); | |
jfr.setVisible(true); | |
jfr.setBounds(0, 0, 900, 500); | |
jfr.addWindowListener(new WindowAdapter() { | |
@Override | |
public void windowClosing(WindowEvent e) { | |
jfr.dispose(); | |
} | |
@Override | |
public void windowClosed(WindowEvent e) { | |
System.exit(0); | |
} | |
}); | |
GraphicsDevice gdr=GraphicsEnvironment.getLocalGraphicsEnvironment().getDefaultScreenDevice(); | |
jfr.setBounds(0, 0, gdr.getDisplayMode().getWidth(), gdr.getDisplayMode().getHeight()); | |
cmp.setBounds(0, 0, gdr.getDisplayMode().getWidth(), gdr.getDisplayMode().getHeight()); | |
gdr.setFullScreenWindow(jfr); | |
cmp.requestFocus(); | |
cmp.addMouseWheelListener(new MouseWheelListener() { | |
public void mouseWheelMoved(MouseWheelEvent e) { | |
} | |
}); | |
cmp.addMouseMotionListener(new MouseMotionListener() { | |
public void mouseMoved(MouseEvent e) {} | |
public void mouseDragged(MouseEvent e) { } | |
}); | |
cmp.addMouseListener(new MouseListener() { | |
public void mouseReleased(MouseEvent e) {} | |
public void mousePressed(MouseEvent e) { | |
if (state==null) | |
return; | |
int dim=Math.min(state.w, state.h); | |
double bx=state.w/2-dim/2; | |
double by=state.h/2-dim/2; | |
double x=(e.getX()-bx)/dim; | |
double y=(e.getY()-by)/dim; | |
if (y>0.7) | |
return; | |
state.missiles.add(new Missile(null, 0.5, 0.75, x, y)); | |
} | |
public void mouseExited(MouseEvent e) {} | |
public void mouseEntered(MouseEvent e) {} | |
public void mouseClicked(MouseEvent e) {} | |
}); | |
cmp.addKeyListener(new KeyAdapter() { | |
public void keyPressed(KeyEvent e) { | |
if (e.getKeyCode()==KeyEvent.VK_ESCAPE) | |
jfr.dispose(); | |
} | |
}); | |
new Timer(50, new ActionListener() { | |
public void actionPerformed(ActionEvent e) { | |
//System.out.println("Hopp"); | |
if (state!=null) | |
state.tick(); | |
jfr.repaint(); | |
} | |
}).start(); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment