«

»

(转载)java编写俄罗斯方块时旋转的方法

快抢沙发

import java.util.Arrays;

/**

* @author Biao

*

* 在写俄罗斯方块时,可以为每个图形的每种状态都定义一个数组来表示(效率高)。

* 因为每个图形有四个方向的状态:上右下左,所以每个图形要定义四个数组来表示他的状态。

* 如果把这些图形都放在一个方阵中,图形的重心为方阵的中心,旋转时绕方阵中心旋转,

* 则图形的四个方向的状态可以通过旋转方阵来实现,这样为每种图形只需要定义一个状态数组。

* 而方阵向左或向右旋转 90 度通过算法可以很方便的实现。

*

* 一般的如图像旋转任意角度 delta,也是要放在一个方阵中进行处理,以方阵的中心为坐标轴原心,

* 然后使用sin, cos计算出旋转后的坐标点,取整。

* 如图像上某一点离原心的距离为 r, 它的角度为 alpha, 逆时针旋转 delta:

* x = r * cos(delta + alpha)

* y = r * sin(delta + alpha)

* 可以把2D坐标 (x, y) 归一化,变成(x, y, 1),然后使用上面的公式计算出旋转矩阵来计算更为方便。

*/

public class RotateUtil {

public static enum Direction { LEFT, RIGHT };

/**

* 方阵向右或向左旋转90度。

*/

public static int[][] rotateSquareMatrix(int[][] data, Direction dir) {

int len = data.length;

int last = len – 1;

temp = createTempSquareMatrix(len);

// 代码量换取计算效率

if (dir == Direction.LEFT) {

// 向左旋转,第一行变第一列,第二行变第二列

for (int i = 0; i < len; ++i) {

for (int j = 0; j < len; ++j) {

temp[last – j][i] = data[i][j];

}

}

} else if (dir == Direction.RIGHT) {

// 向右旋转,第一行变第四列,第二行变第n – 2列

for (int i = 0; i < len; ++i) {

for (int j = 0; j < len; ++j) {

temp[j][last – i] = data[i][j];

}

}

}

// 复制旋转后的数据

for (int i = 0; i < len; ++i) {

for (int j = 0; j < len; ++j) {

data[i][j] = temp[i][j];

}

}

return data;

}

public static void printMatrix(int[][] data) {

for (int i = 0; i < data.length; ++i) {

System.out.println(Arrays.toString(data[i]));

}

}

private static int[][] createTempSquareMatrix(int size) {

if (temp == null || temp.length != size) {

temp = new int[size][size];

}

return temp;

}

private static int[][] temp = null;

public static void main(String[] args) {

// 一般的俄罗斯方式 5 * 5 的方阵正好

int[][] data = {

{0, 0, 1, 0, 0},

{0, 0, 1, 0, 0},

{0, 0, 1, 1, 0},

{0, 0, 0, 0, 0},

{0, 0, 0, 0, 0}

};

Direction dir = Direction.LEFT;

String info = “Rotate ” + ((dir == Direction.LEFT) ? “left” : “right”);

System.out.println(“Original Data:”);

printMatrix(data);

System.out.println(info);

rotateSquareMatrix(data, dir);

printMatrix(data);

System.out.println(info);

rotateSquareMatrix(data, dir);

printMatrix(data);

System.out.println(info);

rotateSquareMatrix(data, dir);

printMatrix(data);

System.out.println(info);

rotateSquareMatrix(data, dir);

printMatrix(data);

System.out.println(“——————————————-“);

dir = Direction.RIGHT;

info = “Rotate ” + ((dir == Direction.LEFT) ? “left” : “right”);

System.out.println(“Original Data:”);

printMatrix(data);

System.out.println(info);

rotateSquareMatrix(data, dir);

printMatrix(data);

System.out.println(info);

rotateSquareMatrix(data, dir);

printMatrix(data);

System.out.println(info);

rotateSquareMatrix(data, dir);

printMatrix(data);

System.out.println(info);

rotateSquareMatrix(data, dir);

printMatrix(data);

}

}

测试结果:

Original Data:

[0, 0, 1, 0, 0]

[0, 0, 1, 0, 0]

[0, 0, 1, 1, 0]

[0, 0, 0, 0, 0]

[0, 0, 0, 0, 0]

Rotate left

[0, 0, 0, 0, 0]

[0, 0, 1, 0, 0]

[1, 1, 1, 0, 0]

[0, 0, 0, 0, 0]

[0, 0, 0, 0, 0]

Rotate left

[0, 0, 0, 0, 0]

[0, 0, 0, 0, 0]

[0, 1, 1, 0, 0]

[0, 0, 1, 0, 0]

[0, 0, 1, 0, 0]

Rotate left

[0, 0, 0, 0, 0]

[0, 0, 0, 0, 0]

[0, 0, 1, 1, 1]

[0, 0, 1, 0, 0]

[0, 0, 0, 0, 0]

Rotate left

[0, 0, 1, 0, 0]

[0, 0, 1, 0, 0]

[0, 0, 1, 1, 0]

[0, 0, 0, 0, 0]

[0, 0, 0, 0, 0]

——————————————-

Original Data:

[0, 0, 1, 0, 0]

[0, 0, 1, 0, 0]

[0, 0, 1, 1, 0]

[0, 0, 0, 0, 0]

[0, 0, 0, 0, 0]

Rotate right

[0, 0, 0, 0, 0]

[0, 0, 0, 0, 0]

[0, 0, 1, 1, 1]

[0, 0, 1, 0, 0]

[0, 0, 0, 0, 0]

Rotate right

[0, 0, 0, 0, 0]

[0, 0, 0, 0, 0]

[0, 1, 1, 0, 0]

[0, 0, 1, 0, 0]

[0, 0, 1, 0, 0]

Rotate right

[0, 0, 0, 0, 0]

[0, 0, 1, 0, 0]

[1, 1, 1, 0, 0]

[0, 0, 0, 0, 0]

[0, 0, 0, 0, 0]

Rotate right

[0, 0, 1, 0, 0]

[0, 0, 1, 0, 0]

[0, 0, 1, 1, 0]

[0, 0, 0, 0, 0]

[0, 0, 0, 0, 0]

原文地址点此进入

2012.03.29
H
阅读全文...

Android BlueStacksAppPlayer最新测试版发布

快抢沙发

Android BlueStacksAppPlayer
windows上玩android应用
无需设置复杂的SDK就能让你的Windows运行Android应用。神奇的BlueStacks App Player beta1版本发布,支持显卡硬件加速,让你手机上的Android软件直接在Windows上运行!下载地址:http://down.tech.sina.com.cn/page/53034.html

2012.03.28
H
阅读全文...

今天完成java坦克大战

快抢沙发

今天练习了几个java版的坦克大战,有单机版,图片版,网络版。继续练习其它java程序。

2012.03.27
H
阅读全文...

java制作坦克大战TankWar

快抢沙发

学习的第二个小项目是坦克大战单机版,有机会会将它做成图片版,或者网络版的。
这个单机版经过了26个版本,最终成为一个简单的单机版,大家可以体验一下哦。
tankwar
程序的主窗口 TankClient.java

import java.awt.*;
import java.awt.event.*;
import java.util.List;
import java.util.ArrayList;

public class TankClient extends Frame{
	
	public static final int GAME_WIDTH = 600;
	public static final int GAME_HEIGHT = 400;
	
	Tank myTank = new Tank(50, 50,true, Tank.Direction.STOP, this);
	

	
	List<Explode> explodes = new ArrayList<Explode>();
	List<Missile> missiles = new ArrayList<Missile>();
	List<Tank> tanks = new ArrayList<Tank>();
	
	Wall w1 = new Wall(300, 200, 20, 150, this);
	
	Wall w2 = new Wall(100, 200, 20, 150, this);
	
	Blood b = new Blood();
	
	Image offScreenImage = null;

	public void paint(Graphics g) {
		//显示相关信息
		g.drawString("missiles count : " + missiles.size(),10,50);
		g.drawString("explodes count : " + explodes.size(),10,70);
		g.drawString("tanks count : " + tanks.size(),10,90);
		g.drawString("my life : " + myTank.getLife(),10,110);
		//画出子弹
		for(int i=0;i<missiles.size(); i++){
			Missile m = missiles.get(i);
			m.hitTanks(tanks);
			m.hitTank(myTank);
			m.hitWall(w1);
			m.hitWall(w2);
			m.draw(g);
		}
		//画出玩家的坦克
		if(myTank.isLive()) {
			myTank.draw(g); 
			myTank.eat(b);
		}
		//画出爆炸
		for(int i=0;i<explodes.size();i++){
			Explode e = explodes.get(i);
			e.draw(g);
		}
		
		//画出敌人坦克
		if(tanks.size() <=0) {
			for(int i=0;i<5;i++){
				tanks.add(new Tank(50 + 40*(i+1), 50, false,Tank.Direction.D, this));
			}
		}
		
		for(int i=0;i<tanks.size();i++){
			Tank t = tanks.get(i);
			t.hitWall(w1);
			t.hitWall(w2);
			t.hitTanks(tanks);
			if(t.isLive()) t.draw(g);
		}
		
		//画出墙
		w1.draw(g);
		w2.draw(g);
		
		//画出血块
		b.draw(g);
	}
	
	public void update(Graphics g) {
		if(offScreenImage == null){
			offScreenImage = this.createImage(GAME_WIDTH,GAME_HEIGHT);
		}
		Graphics gOffScreen = offScreenImage.getGraphics();
		Color c = gOffScreen.getColor();
		gOffScreen.setColor(Color.green);
		gOffScreen.fillRect(0, 0, GAME_WIDTH, GAME_HEIGHT);
		gOffScreen.setColor(c);
		paint(gOffScreen);
		g.drawImage(offScreenImage, 0, 0, null);
	}

	public static void main(String[] args) {
		TankClient tc=new TankClient();
		tc.LaunchFrame();
	}
	
	public void LaunchFrame(){
		// 添加10个敌方坦克
		for(int i=0;i<10;i++){
			tanks.add(new Tank(50 + 40*(i+1), 50, false,Tank.Direction.D, this));
		}
		setLocation(100, 100);
		setSize(GAME_WIDTH,GAME_HEIGHT);
		setTitle("TankWar");
		addWindowListener(new WindowAdapter() {
			public void windowClosing(WindowEvent e) {
				System.exit(0);
			}
		});
		this.setResizable(false);
		this.setBackground(Color.green);
		addKeyListener(new KeyMonitor());
		setVisible(true);
		
		new Thread(new PaintThread()).start();
	}
	
	private class PaintThread implements Runnable {
		public void run() {
			while (true) {
				repaint();
				try {
					Thread.sleep(80);
				} catch (InterruptedException e) {
					e.printStackTrace();
				}
			}
		}
	}
	
	private class KeyMonitor extends KeyAdapter {
		public void keyReleased(KeyEvent e) {
			myTank.keyReleased(e);
		}

		public void keyPressed(KeyEvent e) {
			myTank.keyPressed(e);
		}
	}
}

控制坦克的类Tank.java

import java.awt.*;
import java.awt.event.*;
import java.util.*;

public class Tank {

	public static final int XSPEED=5;
	public static final int YSPEED=5;
	
	public static final int WIDTH = 30;
	public static final int HEIGHT = 30;
	
	private int x, y;
	private int oldX, oldY;
	
	private boolean needReset = false;
	
	private int life = 100;
	private BloodBar bb = new BloodBar();
	
	public void setLife(int life) {
		this.life = life;
	}

	public int getLife() {
		return life;
	}

	TankClient tc;
	
	private boolean good;
	
	private static Random r = new Random();
	
	private boolean live = true;
	
	private int step = r.nextInt(12) + 3;
	
	public boolean isLive() {
		return live;
	}

	public void setLive(boolean live) {
		this.live = live;
	}
	
	public boolean isGood(){
		return good;
	}
	
	public void setGood(boolean good){
		this.good = good;
	}

	enum Direction {L, LU, U, RU, R, RD, D, LD, STOP};
	private Direction dir = Direction.STOP;
	//炮筒方向
	private Direction ptDir = Direction.D;
	
	private boolean bL=false, bU=false,bR=false,bD=false;
	
	public Tank(int x, int y, boolean good) {
		this.x = x;
		this.y = y;
		this.oldX = x;
		this.oldY = y;
		this.good = good;
	}
	
	public Tank(int x, int y, boolean good, Direction dir, TankClient tc){
		this(x, y, good);
		this.dir = dir;
		this.tc = tc;
	}
	
	public void draw(Graphics g){
		Color c = g.getColor();
		if(good) g.setColor(Color.red);
		else g.setColor(Color.yellow);
		g.fillOval(x, y, WIDTH, HEIGHT);
		g.setColor(c);
		
		if(this.isGood()) bb.draw(g);
		
		switch(ptDir) {
		case L:
			g.drawLine(x + Tank.WIDTH/2, y + Tank.HEIGHT/2, x, y + Tank.HEIGHT/2);
			break;
		case LU:
			g.drawLine(x + Tank.WIDTH/2, y + Tank.HEIGHT/2, x, y);
			break;
		case U:
			g.drawLine(x + Tank.WIDTH/2, y + Tank.HEIGHT/2, x + Tank.WIDTH/2, y);
			break;
		case RU:
			g.drawLine(x + Tank.WIDTH/2, y + Tank.HEIGHT/2, x + Tank.WIDTH, y);
			break;
		case R:
			g.drawLine(x + Tank.WIDTH/2, y + Tank.HEIGHT/2, x + Tank.WIDTH, y + Tank.HEIGHT/2);
			break;
		case RD:
			g.drawLine(x + Tank.WIDTH/2, y + Tank.HEIGHT/2, x + Tank.WIDTH, y + Tank.HEIGHT);
			break;
		case D:
			g.drawLine(x + Tank.WIDTH/2, y + Tank.HEIGHT/2, x + Tank.WIDTH/2, y + Tank.HEIGHT);
			break;
		case LD:
			g.drawLine(x + Tank.WIDTH/2, y + Tank.HEIGHT/2, x, y + Tank.HEIGHT);
			break;
		}
		
		
		move();
	}
	
	void move(){
		this.oldX = x;
		this.oldY = y;
		
		switch(dir) {
		case L:
			x -= XSPEED;
			break;
		case LU:
			x -= XSPEED;
			y -= YSPEED;
			break;
		case U:
			y -= YSPEED;
			break;
		case RU:
			x += XSPEED;
			y -= YSPEED;
			break;
		case R:
			x += XSPEED;
			break;
		case RD:
			x += XSPEED;
			y += YSPEED;
			break;
		case D:
			y += YSPEED;
			break;
		case LD:
			x -= XSPEED;
			y += YSPEED;
			break;
		case STOP:
			break;
		}
		
		//只要坦克不是停着的,调整炮筒方向,使之与前进方向一致
		if (this.dir != Direction.STOP) {
			this.ptDir = this.dir;
		}
		
		//避免坦克出界
		if(x < 0) x = 0;
		if(y < 25 ) y = 25;
		if(x + Tank.WIDTH > TankClient.GAME_WIDTH) x = TankClient.GAME_WIDTH - Tank.WIDTH;
		if(y + Tank.HEIGHT > TankClient.GAME_HEIGHT) y = TankClient.GAME_HEIGHT - Tank.HEIGHT;
		
		//给敌方坦克设定随机方向
		if(!good){
			Direction[] dirs = Direction.values();
			if(step == 0){
				step = r.nextInt(12) + 3;
				int rn = r.nextInt(dirs.length);
				dir = dirs[rn];
			}
			step --;
			
			//设置敌方坦克发子弹
			if(r.nextInt(40) > 38) this.fire();
		}
	}
	
	public void keyPressed(KeyEvent e){
		int key = e.getKeyCode();
		switch(key) {
		case KeyEvent.VK_LEFT :
			bL = true;
			break;
		case KeyEvent.VK_UP :
			bU = true;
			break;
		case KeyEvent.VK_RIGHT :
			bR = true;
			break;
		case KeyEvent.VK_DOWN :
			bD = true;
			break;
		}
		
		locateDirection();
	}
	
	void locateDirection(){
		if(bL && !bU && !bR && !bD) dir =Direction.L;
		else if(bL && bU && !bR && !bD) dir =Direction.LU;
		else if(!bL && bU && !bR && !bD) dir =Direction.U;
		else if(!bL && bU && bR && !bD) dir =Direction.RU;
		else if(!bL && !bU && bR && !bD) dir =Direction.R;
		else if(!bL && !bU && bR && bD) dir =Direction.RD;
		else if(!bL && !bU && !bR && bD) dir =Direction.D;
		else if(bL && !bU && !bR && bD) dir =Direction.LD;
		else if(!bL && !bU && !bR && !bD) dir =Direction.STOP;
	}

	public void keyReleased(KeyEvent e) {
		int key = e.getKeyCode();
		switch(key) {
		case KeyEvent.VK_CONTROL :
			fire();
			break;
		case KeyEvent.VK_LEFT :
			bL = false;
			break;
		case KeyEvent.VK_UP :
			bU = false;
			break;
		case KeyEvent.VK_RIGHT :
			bR = false;
			break;
		case KeyEvent.VK_DOWN :
			bD = false;
			break;
		case KeyEvent.VK_A :
			superFire();
			break;
		case KeyEvent.VK_B :
			if(!this.live) {
				this.live = true;
				this.life = 100;
			}
			break;
		}
		
	}
	
	public Missile fire(){
		if(!live) return null;
		int x = this.x + Tank.WIDTH/2 -Missile.WIDTH/2;
		int y = this.y + Tank.HEIGHT/2 -Missile.HEIGHT/2;
		Missile m = new Missile(x, y, ptDir, good, this.tc);
		tc.missiles.add(m);
		return m;
	}
	
	public Missile fire(Direction dir){
		if(!live) return null;
		int x = this.x + Tank.WIDTH/2 -Missile.WIDTH/2;
		int y = this.y + Tank.HEIGHT/2 -Missile.HEIGHT/2;
		Missile m = new Missile(x, y, dir, good, this.tc);
		tc.missiles.add(m);
		return m;
	}
	
	//超级子弹
	private void superFire(){
		Direction[] dirs = Direction.values();
		for(int i=0;i<8;i++){
			fire(dirs[i]);
		}
	}
	
	
	public Rectangle getRect() {
		return new Rectangle(x, y, WIDTH, HEIGHT);
	}
	
	private void stayOld(){
		x = oldX;
		y = oldY;
	}
	
	public boolean hitWall(Wall w){
		if(this.live && this.getRect().intersects(w.getRect())){
			this.stayOld();
			return true;
		}
		return false;
	}
	
	public boolean hitTanks(java.util.List<Tank> tanks){
		for(int i=0;i<tanks.size();i++){
			Tank t = tanks.get(i);
			if(this != t){
				if(this.live && t.live && this.getRect().intersects(t.getRect())){
					this.stayOld();
					t.stayOld();
					return true;
				}
			}
		}
		
		return false;
	}
	
	private class BloodBar{
		public void draw(Graphics g){
			Color c = g.getColor();
			// 先画外面的空心框
			g.setColor(Color.red);
			g.drawRect(x, y-10, WIDTH, 10);
			//画里面的实心框
			int w = WIDTH * life/100;
			g.fillRect(x, y-10, w, 10);
			
		}
	}
	
	public boolean eat(Blood b){
		if(this.isLive() && b.isLive() && this.getRect().intersects(b.getRect())){
			this.life = 100;
			b.setLive(false);
			return true;
		}
		return false;
	}
	
}

控制子弹的类Missile.java

import java.awt.*;
import java.util.List;

public class Missile {
	public static final int XSPEED =10;
	public static final int YSPEED =10;
	
	public static final int WIDTH = 10;
	public static final int HEIGHT = 10;
	
	int x,y;
	
	Tank.Direction dir;
	
	private TankClient tc;
	
	private boolean live = true ;
	
	private boolean good;

	public boolean isLive() {
		return live;
	}

	public void setLive(boolean live) {
		this.live = live;
	}

	public Missile(int x, int y, Tank.Direction dir) {
		super();
		this.x = x;
		this.y = y;
		this.dir = dir;
	}
	
	public Missile(int x, int y, Tank.Direction dir, boolean good, TankClient tc){
		this(x, y, dir);
		this.good = good;
		this.tc = tc ;
	}
	
	public void draw(Graphics g) {
		if(!live) {
			tc.missiles.remove(this);
			return;
		}
		Color c = g.getColor();
		if(this.good) g.setColor(Color.red);
		else g.setColor(Color.yellow);
		g.fillOval(x, y, WIDTH, HEIGHT);
		g.setColor(c);
		
		move();
	}
	
	private void move(){
		switch(dir) {
		case L:
			x -= XSPEED;
			break;
		case LU:
			x -= XSPEED;
			y -= YSPEED;
			break;
		case U:
			y -= YSPEED;
			break;
		case RU:
			x += XSPEED;
			y -= YSPEED;
			break;
		case R:
			x += XSPEED;
			break;
		case RD:
			x += XSPEED;
			y += YSPEED;
			break;
		case D:
			y += YSPEED;
			break;
		case LD:
			x -= XSPEED;
			y += YSPEED;
			break;
		case STOP:
			break;
		}
		
		if(x < 0 || y < 0 || x > TankClient.GAME_WIDTH || y > TankClient.GAME_HEIGHT){
			live = false;
			tc.missiles.remove(this);
		}
	}
	
	public Rectangle getRect() {
		return new Rectangle(x, y, WIDTH, HEIGHT);
	}
	
	public boolean hitTank(Tank t){
		//子弹击中目标坦克
		if(this.getRect().intersects(t.getRect()) && (t.isLive()) && this.good != t.isGood()){
			if(t.isGood()) {
				t.setLife(t.getLife() -20);
				if(t.getLife() <= 0) {
					t.setLive(false);
					t.setLive(false);
				}
			}
			this.live = false;
			tc.missiles.remove(this);
			Explode e = new Explode(x, y, tc);
			tc.explodes.add(e);
			return true;
		}
		return false;
	}
	
	public boolean hitTanks(List<Tank> tanks){
		for(int i=0;i<tanks.size();i++){
			if(hitTank(tanks.get(i))){
				tanks.get(i).setLive(false);
				tanks.remove(i);
				return true;
			}
		}
		return false;
	}
	
	public boolean hitWall(Wall w){
		if(this.live && this.getRect().intersects(w.getRect())){
			this.live = false;
			return true;
		}
		return false;
	}
}

控制爆炸的类Explode.java

import java.awt.*;

public class Explode {
	int x, y;
	private boolean live = true;
	int[] diameter = {2, 6, 13, 18, 25, 16, 10, 6};
	int step = 0;
	
	private TankClient tc;
	
	public Explode(int x, int y, TankClient tc){
		this.x = x;
		this.y = y;
		this.tc = tc;
	}
	
	public void draw(Graphics g){
		if(!live) {
			tc.explodes.remove(this);
			return;
		}
		
		if(step == diameter.length){
			live = false;
			step = 0;
			return;
		}
		Color c = g.getColor();
		g.setColor(Color.white);
		g.fillOval(x, y, diameter[step], diameter[step]);
		g.setColor(c);
		
		step ++;
	}
}

显示玩家坦克生命值的类Blood.java

import java.awt.*;

public class Blood {
	int x, y, w, h;
	TankClient tc;
	boolean live = true ;
	
	public boolean isLive() {
		return live;
	}

	public void setLive(boolean live) {
		this.live = live;
	}

	private int[][] pos = {{50, 360}, {70, 360}, {90, 360}, {110, 380}, {130, 320}, {150, 250}, {170, 200}};
	
	int step = 0;
	
	public Blood(){
		x = pos[0][0];
		y = pos[0][1];
		w = h = 15 ;
	}
	
	public void draw(Graphics g){
		if(!isLive()) return;
		
		Color c = g.getColor();
		g.setColor(Color.magenta);
		g.fillRect(x, y, w, h);
		g.setColor(c);
		
		move();
		
	}
	
	private void move(){
		step ++;
		if(step == pos.length){
			step = 0;
		}
		x = pos[step][0];
		y = pos[step][1];
	}
	
	public Rectangle getRect(){
		return new Rectangle(x, y, w, h);
	}
}

显示障碍物的类Wall.java

import java.awt.*;

public class Wall {
	int x, y, w, h;
	TankClient tc;
	
	public Wall(int x, int y, int w, int h, TankClient tc){
		this.x = x;
		this.y = y;
		this.w = w;
		this.h = h;
		this.tc = tc;
	}
	
	public void draw(Graphics g) {
		Color c = g.getColor();
		g.setColor(Color.black);
		g.fillRect(x, y, w, h);
		g.setColor(c);
	}
	
	public Rectangle getRect() {
		return new Rectangle(x, y, w, h);
	}
}
2012.03.24
H
阅读全文...

j2se java编写简易聊天室程序

快抢沙发

今天学习了老师讲的java的第一个小项目,是一个聊天程序雏形。
一个服务器端ChatServer.java,一个是客户端ChatClient.java
监听的是18881接口。
此小程序的截图如下,有兴趣的可以看一下
java聊天室
ChatServer.java的源代码如下:

import java.io.*;
import java.net.*;
import java.util.*;

public class ChatServer
{
	boolean started = false;
	ServerSocket ss = null;
	
	List<Client> clients = new ArrayList<Client>();

	public static void main(String[] args){
		new ChatServer().start();
	}
		
	public void start(){
		try	{
			ss = new ServerSocket(18881);
			started = true;
			System.out.println("This is 18881 chatting room chatting history");
		} catch (BindException b) {
			System.out.println("端口使用中");
			System.out.println("请关掉相关程序并重新运行服务器");
			System.exit(0);
		} catch (IOException e) {
			e.printStackTrace();
		}
		
		try	{
			int i = 1;
			while(started) {
				Socket s = ss.accept();
				Client c = new Client(s);
				System.out.println(i + " chatter connected,it's IP:" + s.getInetAddress() + ",it's port:" + s.getPort());
				i++;
				//一个客户端启动一个对应的服务器线程
				new Thread(c).start();
				clients.add(c);
			}
		} catch (IOException e)	{
			System.out.println("a chatter out");
		}finally {
			try {
				ss.close();
			} catch (IOException i){
				i.printStackTrace();
			}
		}
	}
	
	class Client implements Runnable {
		private Socket s = null;
		private DataInputStream dis = null;
		private DataOutputStream dos = null;
		private boolean bConnected = false;
		public Client(Socket s){
			this.s = s;
			try {
				dis = new DataInputStream(s.getInputStream());
				dos = new DataOutputStream(s.getOutputStream());
				bConnected = true;
			} catch (IOException e) {
				e.printStackTrace();
			}
		}
		
		public void send(String str){
			try {
				dos.writeUTF(str);
			} catch (IOException e) {
				clients.remove(this);
				System.out.println("一个client退出了,我将它去除了");
			}
		}
		
		public void run() {
			Client c = null;
			try{
				while (bConnected) {
					String str=dis.readUTF();
					System.out.println(s.getPort() + ":" + str);
					for(int i=0;i<clients.size();i++){
						c=clients.get(i);
						c.send(s.getPort() + ":" + str);
					}
				}
			} catch (SocketException s) {
				System.out.println("quit");
			} catch (EOFException e){
				System.out.println("a quit");
			}catch (IOException e)	{
				System.out.println("a client quit");
			} finally {
				try {
					if(dis != null) dis.close();
					if(dos != null) dos.close();
					if(s != null) s.close();
				} catch (IOException e1) {
					e1.printStackTrace();
				}
			}	
		}
	}
}

ChatClient.java的源代码如下:

import java.awt.*;
import java.awt.event.*;
import java.io.*;
import java.net.*;

public class ChatClient extends Frame
{
	TextField tf;
	TextArea ta;
	Socket s = null;
	DataOutputStream dos = null;
	DataInputStream dis=null;
	private boolean bConnected = false;
	public static void main(String[] args){
		new ChatClient().LaunchFrame();
	}

	public void LaunchFrame(){
		setLocation(100,100);
		setSize(400,300);
		tf = new TextField();
		ta = new TextArea();
		add(tf,BorderLayout.SOUTH);
		add(ta,BorderLayout.NORTH);
		pack();
		addWindowListener(new WindowAdapter(){
			public void windowClosing(WindowEvent e){
				disconnect();
				System.exit(0);
			}
		});
		tf.addActionListener(new TFListener());
		setVisible(true);
		connect();
		
		new Thread(new RecvThread()).start();
	}

	private void connect(){
		try
		{
			s = new Socket("127.0.0.1",18881);
			dos = new DataOutputStream(s.getOutputStream());
			dis = new DataInputStream(s.getInputStream());
			ta.setText("-----welcome to 18881 chatting room-----" + '\n');
			
			bConnected = true;
		}
		catch (IOException e)
		{
			e.printStackTrace();
		}
	}
	
	public void disconnect(){
		try{
			dos.close();
			s.close();
		} catch (IOException i) {
			i.printStackTrace();
		}
		
	}


	class TFListener implements ActionListener
	{
		public void actionPerformed(ActionEvent e){
			String str=tf.getText();
			//ta.setText(str);
			tf.setText("");
			try {
				dos.writeUTF(str);
				dos.flush();
				//System.out.println(dis.readUTF());
				//dos.close();
			} catch (IOException e1) {
				e1.printStackTrace();
			}
		}
	}
	
	private class RecvThread implements Runnable{
		public void run(){
			try {
				while(bConnected){
					String str = dis.readUTF();
					ta.setText(ta.getText() + str + '\n');
				}
			} catch (SocketException s) {
				System.out.println("退");
			} catch (EOFException e){
				System.out.println("退出");
			}catch (IOException e)	{
				System.out.println("退出了");
			}
			
		}
	}
}
2012.03.22
H
阅读全文...

mac版冰封王座安装慢解决办法

快抢沙发

应该不少mac玩家会尝试安装mac版的魔兽争霸3,虽然在mac下面没有浩方,vs,妖妖等对战平台,但是如果能玩玩魔兽争霸还是不错的事情的,在安装魔兽争霸3的时候,一般都是先安装混沌之治,再安装冰封王座。安装过的朋友应该有感觉,在安装混乱之制很快,但是安装冰封王座时总是无响应。后来查了下,原来是安装冰封王座时安装程序会自动搜索魔兽的位置然后安装,如果你的分区很多且是NTFS格式,那个搜索就是很漫长,有人等了半个小时才好。为了避免这种情况,我是在磁盘工具里面把其他的分区都推出,只留着MAC分区,然后再安装冰封王座,这样就没有问题了。

2012.03.18
H
阅读全文...

mac的finder不显示桌面内容

快抢沙发

今天碰到自己mac的在桌面不显示文件和文件夹了,而在finder里面打开desktop文件夹,里面的东西都在,为何在桌面什么都不显示了,在finder的设置里面的设置也是正确的啊。

突然想到自己今天刚卸载了path finder,是在卸载path finder之后碰到这种情况的,于是又重装了path finder,在path finder的设置里面找到答案了。里面的“隐藏finder桌面”默认是打勾的,难怪在finder的桌面看不到东西,取消此勾就搞定了,将path finder里面对finder的更改还原后再卸载path finder不迟。

2012.03.17
H
阅读全文...

Chrome插件将Android Market应用(apk)直接下载到本地电脑

快抢沙发
0.jpg
在Android Market下载应用都是通过电子市场账号直接同步你的Android机上,APK文件你是看不见摸不着的,但国外达人redphx最近开发了一款Chrome小插件“APK Downloader ”,能够将市场上的应用下载到本地机器上,这个平实的功能你真的很需要哦,下面来说一下安装配置方法:

要求:Chrome 17及以上版本/谷歌账号/APK Downloader专属应用程序密码/科学上网状态

流程:

1. 下载APK Downloader

2. 取消SSL错误告警

右键点击Chrome图标,在目标项,也就是Chrome执行文件路径后面加上“空格+–ignore-certificate-errors”,加完后的值应该为“C:…chrome.exe –ignore-certificate-errors”

确定后,要关闭当前Chrome浏览器,重新启动;记住,同时要在后台关闭Chrome程序,否则在第3步依然会看到“取消SSL错误告警”的提示。

1.jpg 2.jpg 下载 (32.68 KB)
4 分钟前

3. 登录Apk Downloader的设置页,点击Chrome右上角的设置图标 ,然后进入“工具”-“扩展程序”,找到“APK Downloader”,点击选项

3.jpg 4.jpg

输入谷歌账户邮箱,APK Downloader专属应用程序密码*和你的Android机Device ID*(见备注)

5.jpg 6.jpg

如果看到这样的提示,说明第二步操作没有生效

7.jpg 8.jpg 下载 (21.62 KB)
4 分钟前

登录成功后可以看到以下:

9.jpg 10.jpg

这是你就可以使用APK Downloader咯:

在APP页面,你会在地址栏看到这样的图标,点击它就可以下载了。
11.jpg 12.jpg

备注:关于如何获得APK Downloader专属应用程序密码和Device ID

我一开始登录APK Downloader时输入谷歌账户密码,经常报错,其实不是你的密码不对,而是这里的密码是要求你输入APK Downloader连接Google Account的专属密码,你需要去这里设置APK Downloader的应用密码,自动生成,一次性使用,终生受益!

Device ID有两种方式获得,详情请见

轻松查看自己android手机的Device ID

13.jpg

14.jpg

15.jpg

16.jpg

17.jpg

18.jpg

19.jpg

20.jpg

2012.03.17
H
阅读全文...

轻松查看自己android手机的Device ID

快抢沙发

Device ID有两种方式获得,
1.通过Android App “Device ID”(比较繁琐,不详述了)
2.在拨号键盘输入“*#*#8255#*#*”,会出现““GTalk Service Monitor”界面,找到Device ID,应该是“android-”开头,后面就是要输入的16位ID。

2012.03.17
H
阅读全文...

java中int、string相互转换

快抢沙发

int -> String
int i=12345;
String s=””;
第一种方法:s=i+””;
第二种方法:s=String.valueOf(i);
这两种方法有什么区别呢?作用是不是一样的呢?是不是在任何下都能互换呢?
String -> int
s=”12345″;
int i;
第一种方法:i=Integer.parseInt(s);
第二种方法:i=Integer.valueOf(s).intValue();
这两种方法有什么区别呢?作用是不是一样的呢?是不是在任何下都能互换呢?

以下是答案:
第一种方法:s=i+””; //会产生两个String对象
第二种方法:s=String.valueOf(i); //直接使用String类的静态方法,只产生一个对象
第一种方法:i=Integer.parseInt(s);//直接使用静态方法,不会产生多余的对象,但会抛出异常
第二种方法:i=Integer.valueOf(s).intValue();//Integer.valueOf(s) 相当于 new Integer(Integer.parseInt(s)),也会抛异常,但会多产生一个对象

注: 字串转成 Double, Float, Long 的方法大同小异.

文章来源 http://blog.sina.com.cn/s/blog_4f9d6b1001000bfo.html

2012.03.16
H
阅读全文...

多玩歪歪yy申述系统真是不行

我读大学的时候申请了一个YY,当时绑定了手机号,现在早就换号了,我想取消手机绑定(修改手机绑定的话得原手机号的验证码,此法行不通)。于是乎提交了很多证据,包括我的身份证号,及其正反面图片,还提交了历史密码,常用登陆地点,注册地点,密码问题其答案,以及好友等信息,个人认为这给出的证据已经足够充分了,最好YY给的答复是申述失败,我无语了,我都能给出密保问题和答案了,有假的几率能有多少啊,操你妹哦。

2012.03.15
H
阅读全文...

java多线程生产者消费者例子

快抢沙发

java多线程一章里面举了一个很经典的例子,它就是生产者和消费者的例子,比如说有一个篮子,里面能放6个饼,有厨师生产饼子,顾客吃饼子,厨师生产一个就往篮子里面放,放满的话,线程暂停,提醒顾客快吃;顾客一次吃一个饼子,如果篮子空了,线程也暂停,提醒厨师继续生产。
ProducerConsumer.java的源代码如下


package com.daozhao.java.thread;

public class ProducerConsumer {
	public static void main(String[] args){
		Basket b=new Basket();
		Producer p=new Producer(b);
		Consumer c=new Consumer(b);
		new Thread(p).start();
		new Thread(c).start();
	}
}

class WoTou{
	int id;
	WoTou(int id){
		this.id=id;
	}
	public String toString(){
		return &quot;WoTou:&quot; + id;
	}
}

class Basket{
	int index=0;
	WoTou[] arrWT=new WoTou[6];
	
	public synchronized void push(WoTou wt){
		while(index == arrWT.length){
			try{
				this.wait();
			}catch(InterruptedException i){
				i.printStackTrace();
			}
		}
		this.notify();
		arrWT[index]=wt;
		index++;
	}
	
	public synchronized WoTou pop(){
		while(index==0){
			try{
				this.wait();
			}catch(InterruptedException i){
				i.printStackTrace();
			}
		}
		this.notify();
		index--;
		return arrWT[index];
	}
}

class Producer implements Runnable{
	Basket b=null;
	Producer(Basket b){
		this.b=b;
	}
	
	public void run(){
		for(int i=0;i&lt;20;i++){
			WoTou wt=new WoTou(i);
			b.push(wt);
			i++;
			System.out.println(&quot;生产了&quot;+ wt);
			try{
				Thread.sleep(2000);
			}catch(InterruptedException ie){
				ie.printStackTrace();
			}
		}
	}
}

class Consumer implements Runnable{
	Basket b=null;
	Consumer(Basket b){
		this.b=b;
	}
	
	public void run(){
		for(int i=0;i&lt;20;i++){
			WoTou wt=b.pop();
			System.out.println(&quot;消费了&quot; + wt);
			try{
				Thread.sleep(1000);
			}catch(InterruptedException ie){
				ie.printStackTrace();
			}
		}
	}
}
2012.03.15
H
阅读全文...

道招网近期出现无法访问

近期我站出现了打不开的现象,主要还是因为本人的粗心导致,daozhao.com的域名是3月13日过期,我在3.12续费了,但是西部数码提示续费的太晚了,可能要续费成功得等1~5天,在我续费后不久就发现网站好像打不开了,没有在意,我在怀疑是不是因为我的域名续费太晚的缘故。到了今天我发现道招网还是打不开,于是我联系了我的主机提供商–衡天小张。询问得知,主机的IP调整了,于是里面重新解析,现在道招已经恢复正常。

2012.03.13
H
阅读全文...

115用户页面改版

快抢沙发

今天登陆了115网盘,发现用户页面改版了,改的比较大气,我比较喜欢。
115改版

2012.03.10
H
阅读全文...

ipad3发布会视频

快抢沙发

IPAD3发布会现场

85分钟的现场视频

2012.03.09
H
阅读全文...

Java获取某个文件的编码

快抢沙发

我们可能会经常打开某个文档,发现里面有乱码,有时候我们可能会试着把它另存为其它编码的文件以希望能恢复它的原来状况。如果很幸运的话,很快就能搞定,但是有时候我们还是希望知道这个乱码文件当前是什么编码。
我们用java(其它语言应该也是可以的)可以很轻松的得到该文件的编码,比如T.java这个文件出现了乱码,我们可以在该文件的同一目录下新建一个java文件来获取编码。比如TestEncoding.java
TestEncoding.java的源代码如下:

import java.io.*;

public class TestEncoding {
	public static void main(String[] args){
		try{
			FileInputStream fis=new FileInputStream("T.java");
			InputStreamReader osr =new InputStreamReader(fis);
			System.out.println(osr.getEncoding());
		} catch(IOException i){}
	}
}
2012.03.07
H
阅读全文...

wordpress连接微博老是更新,作者也忒勤奋了吧

快抢沙发

相信不少wordpress博客程序都使用了wordpress连接微博,但是近些时间作者更新太频繁了,老是添加一些其他sns的账号登陆功能,大有将所有开放开放登陆功能的网站全部网罗进来的意思啊。个人不是太喜欢,每次发现提示插件更新,想都不用想,肯定是它了。

2012.03.07
H
阅读全文...

黑苹果选虚拟机很纠结

快抢沙发

我的黑苹果是10.6.8,安装了最新版的virtualbox for mac,刚准备给自己刚建立的虚拟机装系统呢,virtualbox就重启了,屡试不爽啊。呵呵,开启了AMD Virtualization重启,关闭了AMD Virtualization提示要开启,反正就是不行。是不是黑苹果有哪些地方还没有弄好啊。无奈之下,只好用vmware fusion,下载了最新版4.1.3,安装了,提示系统不能使用该应用程序,难道4.1.3是给lion,或更高版本的?如果真这样的话,想起来就害怕了,现在好像不少软件都要求10.6以上,有的是10.6.8或以上,过不了多久,snow leopard用不了了怎么办,我这AMD的cpu目前又用不了lion,迟早要悲剧啊。
闲话不说了。车到山前必有路!
虚拟机
我最好安装了Vmware Fusion Version 3.1.3 (416484),现在正在开启着虚拟的win7呢,听说vmware比virtualbox耗资源,它还不是免费的,现在我也管不了这些了。能虚拟个windows应急,总不至于老是重启电脑进win7吧。

2012.03.01
H
阅读全文...
  • sitemap_baidu