//
/* ----------------------------------------------------------------------------------------------
tokenring.java トークンリング ver. 1.00 (JDK 1.02)
ueyama@infonet.co.jp 1999.08.17
---------------------------------------------------------------------------------------------- */
import java.applet.Applet;
import java.awt.*;
import java.lang.Math;
import java.util.*;
import java.awt.image.*;
public class tokenring extends Applet implements Runnable
{
int Rr=150; // ケーブル半径
double Ta=90.0; // トークン位置(角度)
int Tx,Ty; // トークン等位置(座標)
int Cx[]={225,15,26,213}; // コンピュータ位置
int Cy[]={15,15,213,213}; // コンピュータ位置
int Ct=-1; // 送信コンピュータ
int Cr=-1; // 受信コンピュータ
int Data[]=new int[300*300];
int Bg[][]=new int[11][11];
boolean Dsp[]=new boolean[13];
boolean Flg[]=new boolean[13];
Thread th=null;
Graphics gr;
Image Gif;
Image img;
boolean Run=false;
boolean Busy=false;
boolean Read=false;
boolean End=false;
int R,G,B;
int Wait=64;
public void start()
{
if(th==null)
{
th=new Thread(this);
th.start();
}
}
public void init()
{
R=Integer.parseInt(getParameter("bg_red"));
G=Integer.parseInt(getParameter("bg_green"));
B=Integer.parseInt(getParameter("bg_blue"));
setBackground(new Color(R,G,B));
gr=getGraphics();
MediaTracker mt=new MediaTracker(this);
Gif=getImage(getCodeBase(),"tokenrng.gif");
mt.addImage(Gif, 0);
try
{
mt.waitForID(0);
}
catch(InterruptedException e){};
img=createImage(300,300);
t_pos(Ta,0,0,gr,0);
Dsp[0]=true;
}
public boolean inside(int x, int a, int b)
{
return (x<=Math.max(a,b) && x>=Math.min(a,b)) ? true:false;
}
public boolean get_pixeldata()
{
update(img.getGraphics());
PixelGrabber pg=new PixelGrabber(img,0,0,300,300,Data,0,300);
try
{
pg.grabPixels(); // 画像データの取得
}
catch (InterruptedException ie) {return false;}
if((pg.status() & ImageObserver.ABORT) !=0) {return false;}
return true;
}
public void t_pos(double a, int n, int c, Graphics g, int m) // トークン・データの表示
{
int x,y;
Tx=(Rr*2+(int)(Math.cos(a*3.14159/180.0)*(Rr*2-11))-11)/2;
Ty=(Rr*2-(int)(Math.sin(a*3.14159/180.0)*(Rr*2-11))-11)/2;
for(x=0;x<11;x++) for(y=0;y<11;y++) Bg[x][y]=Data[(Ty+y)*300+Tx+x];
get_p(Tx,Ty,m);
if(Dsp[m]) dsp_g(Tx,Ty,n,c,g);
}
public int get_p(int x, int y, int m)
{
int n=-1;
if(inside(y,22,44))
{
if(x<67) n=0; // in to A
if(x>223) n=7; // out from D
}
if(inside(y,225,240))
{
if(x>24) n=1; // in to B
if(inside(x,254,265)) n=6; // out from C
}
if(inside(x,15,33) && inside(y,65,75)) n=4; // out from A
if(inside(x,63,87) && y>262) n=5; // out from B
if(inside(x,210,237) && inside(y,273,262)) n=2; // in to C
if(inside(x,260,281) && y<75) n=3; // in to D
if(inside(y,30,64) || inside(y,239,262)) Dsp[m]=false;
else Dsp[m]=true;
return n;
}
public void dsp_g(int x, int y, int n, int c, Graphics g) // 画像の表示
{
int w=0, h=0, ox=0, oy=0, wc=0, hc=0;
Graphics gx=g.create();
switch(n)
{
case 0: w= 11; h= 11; ox= 61; oy= 0; break; // トークン
case 1: w= 11; h= 11; ox= 72; oy= 0; break; // 宛先 ヘッダ
case 2: w= 11; h= 11; ox=116; oy= 0; break; // 送り主 ヘッダ
case 3: w= 11; h= 11; ox=160; oy= 0; break; // 着信確認データ
case 4: w= 11; h= 11; ox=204; oy= 0; break; // データ
case 5: w= 61; h= 60; ox= 0; oy= 0; break; // コンピュータ
case 6: w= 17; h= 21; ox= 61; oy=11; break; // コンピュータ名
case 7: w= 26; h= 23; ox= 61; oy=32; break; // "<<" ボタン
case 8: w= 26; h= 23; ox=113; oy=32; break; // ">>" ボタン
case 9: w= 26; h= 23; ox=191; oy=32; break; // "||" ボタン
case 10: w= 26; h= 23; ox=243; oy=32; break; // "|>" ボタン
}
wc=w; hc=h;
if(n<5)
{
switch(get_p(x, y, 11))
{
case 0: wc=x- 57; ox+=(11-wc); x= 68; break;
case 1: wc=35- x; break;
case 2: hc=y-262; oy+=(11-hc); y=274; break;
case 3: hc=y- 64; oy+=(11-hc); y= 76; break;
case 4: hc=y- 64; oy+=(11-hc); y= 76; break;
case 5: hc=y-262; oy+=(11-hc); y=274; break;
case 6: wc=x-254; ox+=(11-wc); x=265; break;
case 7: wc=234-x; break;
}
}
gx.clipRect(x,y,wc,hc);
gx.drawImage(Gif,x-(ox+w*c),y-oy,this);
gx.dispose();
}
public void dsp_c(int n, int c, Graphics g) // コンピュータ名の表示
{
Graphics gx=g.create();
gx.clipRect(Cx[n]+22,Cy[n]+9,17,21);
gx.drawImage(Gif,Cx[n]+22-(61+68*c+17*n),Cy[n]+9-11,this);
gx.dispose();
}
public void dsp_r(int c, Graphics g) // ネットワークケーブルの表示
{
int i,r;
if(c==0) g.setColor(new Color(102,102,102));
else g.setColor(new Color(128,102,102));
g.fillOval(0,0,Rr*2-1,Rr*2-1);
g.setColor(new Color(R,G,B));
g.fillOval(11,11,Rr*2-22,Rr*2-22);
}
public void paint(Graphics g)
{
int i,j;
dsp_r(0,g); // ネットワークケーブルの表示
for(i=0;i<4;i++) // コンピュータの表示
{
j=0;
if(Ct==i) j=1;
if(Cr==i) j=2;
dsp_g(Cx[i],Cy[i],5,0,g);
dsp_c(i, j, g);
}
dsp_g(105,317,7,0,g); // "<<" ボタンの表示
dsp_g(169,317,8,0,g); // ">>" ボタンの表示
dsp_g(137,317,(Run)?9:10,0,g); // "|>" or "||" ボタンの表示
}
public void t_els() // トークン(データ)の後半を消去
{
int r,g,b,x,y;
double a;
a=(double)(Rr-(Ty+5))/(double)(Tx+5-Rr);
for(x=0;x<11;x++)
{
for(y=0;y<11;y++)
{
if((Tx+5Rr && (double)(Ty+y)>(double)Rr-a*(double)(Tx+x-Rr)) || a<-200.0)
{
r=Bg[x][y] & 0x00ff0000; r/=0x10000;
g=Bg[x][y] & 0x0000ff00; g/=0x100;
b=Bg[x][y] & 0x000000ff;
gr.setColor(new Color(r,g,b));
gr.drawRect(Tx+x,Ty+y,1,1);
}
}
}
}
public void dsp_data(boolean f, double a) // ヘッダ・データ・フッタの表示
{
int i;
boolean fd=true;
if(f) fd=(Ta-4.5Ct*90+45) Flg[1]=true;
if(Flg[1] && fd) t_pos(Ta-4.5,1,Cr,gr,1); // 宛先の表示
if(Flg[1] && (int)(Ta-4.5*2)%360>Ct*90+45) Flg[2]=true;
if(Flg[2])
{
if(f) fd=(Ta-4.5*2Ct*90+45) Flg[i]=true;
if(Flg[i] && fd) t_pos(Ta-i*4.5, 3,(i-3)%4,gr,i); // データの表示
}
}
if(Read && Flg[10])
{
i=(int)(Ta-4.5*11)%360;
if((Cr>0 && i>Cr*90+45) || (Cr==0 && inside(i,40,50))) Flg[11]=true;
if(Flg[11]) t_pos(Ta-11*4.5, 4,Cr,gr,11); // 着信確認の表示
}
}
public void run()
{
int i,j=0,n,x=0;
double a=0.0;
while(th!=null)
{
if(Run)
{
if((int)(Ta+45.0)%90==86 && Ct>=0 && Cr>=0)
{
n=(int)Ta%360; n/=90;
if(Ct==n)
{
if(Busy && Read) // 送信完了
{
a=Ta;
while(Ta-4.5*11=0) Cr=1; else Ct=1;
if(inside(mx,225,286)) if(Ct>=0) Cr=0; else Ct=0;
}
if(inside(my,213,273) && (Ct<0 || Cr<0))
{
if(inside(mx,26,87)) if(Ct>=0) Cr=2; else Ct=2;
if(inside(mx,213,274)) if(Ct>=0) Cr=3; else Ct=3;
}
if(my>317)
{
if(inside(mx,105,131))
{
Wait*=2;
dsp_g(105, 317, 7, 1, gr); // "<<" ボタンの表示
dsp_g(169, 317, 8, 0, gr);
}
if(inside(mx,137,163))
{
dsp_g(137,317,(Run)? 9:10,1,gr); // "||" or "|>" ボタンの表示
if(Ta==90.0) get_pixeldata();
Run=!Run;
}
if(inside(mx,169,195) && Wait>16)
{
Wait/=2;
dsp_g(169, 317, 8, 1, gr); // ">>" ボタンの表示
}
}
if(Ct>=0) dsp_c(Ct,1,gr);
if(Cr>=0) dsp_c(Cr,2,gr);
return true;
}
public boolean mouseUp(Event e, int mx, int my)
{
if(my>317)
{
if(inside(mx,105,131)) dsp_g(105, 317, 7, 0, gr); // "<<" ボタン
if(inside(mx,137,163)) dsp_g(137, 317, (Run)? 9:10, 0, gr); // "||" or "|>" ボタン
if(inside(mx,169,195)) dsp_g(169, 317, 8, (Wait>16)? 0:2, gr); // ">>" ボタン
}
return true;
}
public void stop()
{
if(th!=null)
{
th.stop();
th=null;
}
}
}
// 戻る