OSDN Git Service

ELCCIDE(elcc/elccide.html)を追加。ブラウザ上でソースコードを編集し、即座に実行することができます。
[chnosproject/AI004.git] / webcpu / api.js
1 function BitmapCanvas(){
2         this.canvasDOMObject = null;
3         this.canvasContext = null;
4         this.bufferImageData = null;
5         this.bmp = null;
6         this.width = undefined;
7         this.height = undefined;
8 }
9 BitmapCanvas.prototype = {
10         setCanvas: function(canvasDOMObject){
11                 this.canvasDOMObject = canvasDOMObject;
12                 if(canvasDOMObject){
13                         this.canvasContext = this.canvasDOMObject.getContext("2d");
14                         this.width = this.canvasDOMObject.width;
15                         this.height = this.canvasDOMObject.height;
16                         this.bufferImageData = this.canvasContext.getImageData(0, 0, this.width, this.height);
17                         this.bmp = this.bufferImageData.data;
18                 } else{
19                         this.bmp = null;
20                         this.canvasContext = null;
21                         this.bufferImageData = null;
22                         this.width = undefined;
23                         this.height = undefined;
24                 }
25         },
26         drawPoint: function(x, y, color, mode){
27                 if(this.bmp){
28                         if(mode === undefined){
29                                 mode = 0;
30                         } else{
31                                 mode &= 0x03;
32                         }
33                         x += 0.5;
34                         x |= 0;
35                         y += 0.5;
36                         y |= 0;
37                         //RGBARGBA...
38                         if(mode == 0){
39                                 //PSET
40                                 this.bmp[4 * (y * this.width + x) + 0] = (color >> 16) & 0xFF;
41                                 this.bmp[4 * (y * this.width + x) + 1] = (color >> 8) & 0xFF;
42                                 this.bmp[4 * (y * this.width + x) + 2] = color & 0xFF;
43                         } else if(mode == 1){
44                                 //OR
45                                 this.bmp[4 * (y * this.width + x) + 0] |= (color >> 16) & 0xFF;
46                                 this.bmp[4 * (y * this.width + x) + 1] |= (color >> 8) & 0xFF;
47                                 this.bmp[4 * (y * this.width + x) + 2] |= color & 0xFF;
48                         } else if(mode == 2){
49                                 //XOR
50                                 this.bmp[4 * (y * this.width + x) + 0] ^= (color >> 16) & 0xFF;
51                                 this.bmp[4 * (y * this.width + x) + 1] ^= (color >> 8) & 0xFF;
52                                 this.bmp[4 * (y * this.width + x) + 2] ^= color & 0xFF;
53                         } else if(mode == 3){
54                                 //AND
55                                 this.bmp[4 * (y * this.width + x) + 0] &= (color >> 16) & 0xFF;
56                                 this.bmp[4 * (y * this.width + x) + 1] &= (color >> 8) & 0xFF;
57                                 this.bmp[4 * (y * this.width + x) + 2] &= color & 0xFF;
58                         }
59                 }
60         },
61         drawLine: function(x0, y0, x1, y1, color, mode){
62                 //整数座標のみ対応。
63                 x0 |= 0;
64                 y0 |= 0;
65                 x1 |= 0;
66                 y1 |= 0;
67                 var dx = x1 - x0;
68                 var dy = y1 - y0;
69                 var dxa = dx;
70                 var dya = dy;
71                 var l;
72                 
73                 if(dxa < 0){
74                         dxa = -dxa;
75                 }
76                 if(dya < 0){
77                         dya = -dya;
78                 }
79                 
80                 if(dxa > dya){
81                         //x軸基準
82                         l = dxa + 1;
83                         if(x0 > x1){
84                                 dx = -1;
85                         } else{
86                                 dx = 1;
87                         }
88                         dy /= l;
89                 } else{
90                         //y軸基準
91                         l = dya + 1;
92                         if(y0 > y1){
93                                 dy = -1;
94                         } else{
95                                 dy = 1;
96                         }
97                         dx /= l;
98                 }
99                 
100                 for(var i = 0; i < l; i++){
101                         this.drawPoint(x0 + dx * i, y0 + dy * i, color, mode);
102                 }
103         },
104         fillRect: function(xSize, ySize, x0, y0, col, mode){
105         
106         },
107         fillOval: function(xSize, ySize, x0, y0, col, mode){
108         
109         },
110         flush: function(){
111                 if(this.bufferImageData){
112                         this.canvasContext.putImageData(this.bufferImageData, 0, 0);
113                 }
114         },
115 }
116
117 function WebCPU_API(){
118         this.mainWindowCanvas = null;
119         this.mainWindowContext = null;
120         //this.mainWindowBufferCanvas = document.createElement('canvas');
121         //this.mainWindowBufferContext = this.mainWindowBufferCanvas.getContext("2d");
122         //
123         this.bitmapCanvas = new BitmapCanvas();
124         //
125         //this.mainWindowBufferCanvas.width = 640;
126         //this.mainWindowBufferCanvas.height = 480;
127         //this.initCanvas(this.mainWindowBufferCanvas);
128 }
129 WebCPU_API.prototype = {
130         executeAPI: function(env){
131                 var r = env.registers.Integer;
132                 var APIID = r[0x30];
133                 switch(APIID){
134                         case 0xff40:
135                                 //openWin
136                                 this.API_openWin(env, r[0x31], r[0x32])
137                                 break;
138                         case 0xff41:
139                                 //openWin
140                                 this.API_flushWin(env, r[0x31], r[0x32], r[0x33], r[0x34])
141                                 break;
142                         case 0xff44:
143                                 //drawPoint
144                                 this.API_drawPoint(env, r[0x31], r[0x32], r[0x33], r[0x34]);
145                                 break;
146                         case 0xff45:
147                                 //drawLine
148                                 this.API_drawLine(env, r[0x31], r[0x32], r[0x33], r[0x34], r[0x35], r[0x36]);
149                                 break;
150                         case 0xff46:
151                                 //fillRect
152                                 this.API_fillRect(env, r[0x31], r[0x32], r[0x33], r[0x34], r[0x35], r[0x36]);
153                                 break;
154                         case 0xff47:
155                                 //fillOval
156                                 this.API_fillOval(env, r[0x31], r[0x32], r[0x33], r[0x34], r[0x35], r[0x36]);
157                                 break;
158                         default:
159                                 throw new WebCPU_Exception(0, ["Unknown API Number " + APIID.toString(16)]);
160                 }
161                 env.goToPointerRegister(0x30);
162         },
163         colorTable:[
164                 0x000000, 
165                 0xff0000, 
166                 0x00ff00, 
167                 0xffff00, 
168                 0x0000ff, 
169                 0xff00ff, 
170                 0x00ffff, 
171                 0xffffff
172         ],
173         setMainWindowCanvasDOMObject: function(obj){
174                 this.mainWindowCanvas = obj;
175                 if(this.mainWindowCanvas){
176                         this.mainWindowContext = this.mainWindowCanvas.getContext('2d')
177                         this.initCanvas(this.mainWindowCanvas);
178                         //
179                         this.bitmapCanvas.setCanvas(this.mainWindowCanvas);
180                 } else{
181                         this.mainWindowContext = null;
182                 }
183         },
184         initCanvas: function(c){
185                 var d = c.getContext('2d');
186                 d.fillStyle = "rgba(0,0,0,1)";
187                 d.strokeStyle = "rgba(255, 255, 255, 1)";
188                 d.lineWidth = 1;
189                 //描画域は必ず黒で初期化されます。
190                 d.fillRect(0, 0, c.width, c.height);
191         },
192         //
193         API_openWin: function(env, xSize, ySize){
194                 env.message("junkApi_openWin();\n", 20);
195                 this.mainWindowCanvas.width = xSize;
196                 this.mainWindowCanvas.height = ySize;
197                 //this.mainWindowBufferCanvas.width = xSize;
198                 //this.mainWindowBufferCanvas.height = ySize;
199                 this.initCanvas(this.mainWindowCanvas);
200                 this.bitmapCanvas.setCanvas(this.mainWindowCanvas);
201         },
202         API_flushWin: function(env, xSize, ySize, x0, y0){
203                 env.message("junkApi_flushWin();\n", 20);
204                 //this.mainWindowContext.drawImage(this.mainWindowBufferCanvas, x0, y0, xSize, ySize, 0, 0, xSize, ySize);
205                 this.bitmapCanvas.flush();
206         },
207         API_drawPoint: function(env, mode, x, y, col){
208                 env.message("junkApi_drawPoint();\n", 20);
209                 if((mode & 0x04) != 0){
210                         col = this.colorTable[col];
211                 }
212                 //this.mainWindowBufferContext.fillStyle = "#" + ("000000" + col.toString(16)).slice(-6).toUpperCase();
213                 //this.mainWindowBufferContext.fillRect(x, y, 1, 1);
214                 this.bitmapCanvas.drawPoint(x, y, col, mode);
215         },
216         API_drawLine: function(env, mode, x0, y0, x1, y1, col){
217                 env.message("junkApi_drawLine();\n", 20);
218
219                 if((mode & 0x04) != 0){
220                         col = this.colorTable[col];
221                 }
222                 /*
223                 this.mainWindowBufferContext.strokeStyle = "#" + ("000000" + col.toString(16)).slice(-6).toUpperCase();
224                 this.mainWindowBufferContext.beginPath();
225                 this.mainWindowBufferContext.moveTo(x0, y0);
226                 this.mainWindowBufferContext.lineTo(x1, y1);
227                 this.mainWindowBufferContext.closePath();
228                 this.mainWindowBufferContext.stroke();
229                 */
230                 this.bitmapCanvas.drawLine(x0, y0, x1, y1, col, mode);
231         },
232         API_fillRect: function(env, mode, xSize, ySize, x0, y0, col){
233                 env.message("junkApi_fillRect();\n", 20);
234
235                 if((mode & 0x04) != 0){
236                         col = this.colorTable[col];
237                 }
238                 /*
239                 this.mainWindowBufferContext.fillStyle = "#" + ("000000" + col.toString(16)).slice(-6).toUpperCase();
240                 this.mainWindowBufferContext.fillRect(x0, y0, xSize, ySize);
241                 */
242         },
243         API_fillOval: function(env, mode, xSize, ySize, x0, y0, col){
244                 env.message("junkApi_fillRect();\n", 20);
245
246                 if((mode & 0x04) != 0){
247                         col = this.colorTable[col];
248                 }
249                 /*
250                 this.mainWindowBufferContext.fillStyle = "#" + ("000000" + col.toString(16)).slice(-6).toUpperCase();
251                 this.mainWindowBufferContext.fillEllipse(x0, y0, xSize, ySize);
252                 */
253         },
254 }