このファイル: /home/web6047/www/cgi-bin/prj/20200515-RPG/基本的/20200620-ウィンドウ入力/20200724-新しいメモ2/simple.html
1
<html>
2
<head>
3
<meta content="text/html; charset=UTF-8" http-equiv="content-type">
4
<script>console.clear();</script>
5
<script>
6
function onloadx() {
7
app = new App();
8
}
9
class App {
10
constructor() {
11
this.cc = document.getElementById( "test" ).getContext( "2d" );
12
this.cc.font = "16px monospace";
13
this.drawers = new Array();
14
this.framers = new Array();
15
16
this.chars = new Array();
17
18
this.dougus = {
19
"やくそう" : {
20
title : "やくそう",
21
"キャンプ時" : {
22
title : "どうする?",
23
items : [
24
{
25
title : "つかう",
26
},
27
{
28
title : "わたす",
29
},
30
{
31
title : "すてる",
32
},
33
],
34
},
35
"C1時" : {
36
title : "だれに?",
37
items : this.chars,
38
},
39
},
40
"テスト" : {
41
title : "テスト",
42
},
43
};
44
this.batcoms = {
45
"たたかう" : {
46
title : "たたかう",
47
},
48
"にげる" : {
49
title : "にげる",
50
},
51
"どうぐ" : {
52
title : "どうぐ",
53
submenu : {
54
title : "",
55
items : null,
56
},
57
},
58
"じゅもん" : {
59
title : "じゅもん",
60
},
61
"ぼうぎょ" : {
62
title : "ぼうぎょ",
63
},
64
};
65
66
let char;
67
68
char = {
69
title : "C1",
70
"どうぐ" : [
71
this.dougus[ "やくそう" ],
72
this.dougus[ "やくそう" ],
73
],
74
}
75
char.batcoms = [
76
this.batcoms[ "たたかう" ],
77
this.batcoms[ "にげる" ],
78
{
79
title : "どうぐ",
80
submenu : {
81
title : "",
82
items : char[ "どうぐ" ],
83
},
84
},
85
this.batcoms[ "ぼうぎょ" ],
86
];
87
this.chars[ 0 ] = char;
88
89
char = {
90
title : "C2",
91
"どうぐ" : [
92
this.dougus[ "やくそう" ],
93
this.dougus[ "テスト" ],
94
],
95
}
96
char.batcoms = [
97
this.batcoms[ "たたかう" ],
98
this.batcoms[ "じゅもん" ],
99
{
100
title : "どうぐ",
101
submenu : {
102
title : "",
103
items : char[ "どうぐ" ],
104
},
105
},
106
this.batcoms[ "ぼうぎょ" ],
107
];
108
this.chars[ 1 ] = char;
109
110
111
this.camp = {
112
title : "キャンプ",
113
items : [
114
{
115
title : "どうぐ",
116
submenu : {
117
title : "だれの?",
118
items : this.chars,
119
},
120
bridge : {
121
title : "",
122
propertyName : "どうぐ",
123
},
124
},
125
{
126
title : "じゅもん",
127
submenu : {
128
title : "だれの?",
129
items : this.chars,
130
},
131
},
132
{
133
title : "戦闘する",
134
},
135
],
136
}
137
138
this.timerMs = 100;
139
this.timerId = setInterval( this.frame.bind( this ), this.timerMs );
140
141
142
143
this.campEvent();
144
145
}
146
147
async battleEvent() {
148
for( let i = 0; i < this.chars.length; i++ ) {
149
let char = this.chars[ i ];
150
let menu = new Menu( 1,19,null,null, char.title, char.batcoms, this );
151
await menu.selectionProcedure();
152
menu.close();
153
}
154
}
155
156
async campEvent() {
157
let menu = new Menu( 1,1,null,null, this.camp.title, this.camp.items, this );
158
let res = await menu.selectionProcedure();
159
console.log( "done" );
160
161
if( res == "戦闘する" ) {
162
menu.close();
163
this.battleEvent();
164
}
165
}
166
frame() {
167
for( let i = 0; i < this.framers.length; i++ ) {
168
let framer = this.framers[ i ];
169
framer.frame();
170
}
171
this.draw( this.cc );
172
}
173
174
draw( cc ) {
175
cc.clearRect( 0,0, cc.canvas.width, cc.canvas.height );
176
for( let i = 0; i < this.drawers.length; i++ ) {
177
let drawer = this.drawers[ i ];
178
drawer.draw( cc );
179
}
180
}
181
}
182
183
184
185
186
187
188
189
class Win {
190
constructor( cx, cy, cw, ch ) {
191
this.cx = cx;
192
this.cy = cy;
193
this.cw = cw;
194
this.ch = ch;
195
this.cpadding = 0;
196
}
197
draw( cc ) {
198
let gx = this.cx * 16;
199
let gy = this.cy * 16;
200
let gw = this.cw * 16 + this.cpadding * 16 * 2;
201
let gh = this.ch * 16 + this.cpadding * 16 * 2;
202
cc.fillStyle = "white";
203
cc.fillRect( gx, gy, gw, gh );
204
cc.strokeStyle = "black";
205
cc.strokeRect( gx, gy, gw, gh );
206
}
207
}
208
class CtrlWin extends Win {
209
constructor( cx, cy, cw, ch, app ) {
210
super( cx, cy, cw, ch );
211
this.app = app;
212
213
this.keys = new Object();
214
this.tellOk = function() {}
215
}
216
activate( tellOk ) {
217
this.tellOk = tellOk;
218
this.app.drawers.push( this );
219
window.onkeydown = this.onkeydownx.bind( this );
220
window.onkeyup = this.onkeyupx.bind( this );
221
}
222
frame() {
223
for( let key in this.keys ) {
224
this.keysense( Number( key ) );
225
226
if( ! this.keys[ key ] ) delete this.keys[ key ];
227
}
228
}
229
onkeydownx( e ) {
230
this.keys[ e.which ] = true;
231
this.keytype( e.which );
232
}
233
onkeyupx( e ) {
234
this.keys[ e.which ] = false;
235
}
236
keytype( key ) {
237
}
238
keysense( key ) {
239
}
240
}
241
242
243
244
class Menu extends CtrlWin {
245
constructor( cx, cy, cw, ch, title, items, app, histories ) {
246
247
if( cw == null ) {
248
249
250
let getLen = function( str ){
251
let result = 0;
252
for( let i = 0; i < str.length; i++ ) {
253
let chr = str.charCodeAt(i);
254
if( ( chr >= 0x00 && chr < 0x81 )
255
|| ( chr === 0xf8f0 )
256
|| ( chr >= 0xff61 && chr < 0xffa0 )
257
|| ( chr >= 0xf8f1 && chr < 0xf8f4 ) ) {
258
259
result += 1;
260
} else {
261
262
result += 2;
263
}
264
}
265
266
return result;
267
};
268
cw = Math.max( ...items.map( item => Math.ceil( getLen( item.title ) / 2 ) ), title.length );
269
}
270
if( ch == null ) {
271
ch = items.length + ( title ? 1 : 0 );
272
}
273
super( cx, cy, cw, ch, app );
274
this.cpadding = 1;
275
this.title = title;
276
this.items = items;
277
if( histories ) {
278
this.histories = histories;
279
} else {
280
this.histories = new Array();
281
}
282
this.histories.push( {
283
title : title,
284
menu : this,
285
} );
286
this.cursorY = 0;
287
}
288
289
draw( cc ) {
290
super.draw( cc );
291
292
let gx = this.cx * 16;
293
let gy = this.cy * 16;
294
let gw = this.cw * 16;
295
296
let gx2 = this.cx * 16 + this.cpadding * 16;
297
let gy2 = this.cy * 16 + this.cpadding * 16;
298
let gw2 = this.cw * 16;
299
let gh2 = this.ch * 16;
300
301
if( this.title ) {
302
cc.fillStyle = "black";
303
cc.fillText( this.title, gx2, gy2 + 8 );
304
cc.fillText( this.title, gx2 + 1, gy2 + 8 );
305
gy2 += 16;
306
}
307
for( let i = 0; i < this.items.length; i ++ ) {
308
let item = this.items[ i ];
309
if( i == this.cursorY ) {
310
311
cc.fillStyle = "black";
312
cc.fillRect( gx2, gy2, gw2, 16 );
313
cc.fillStyle = "white";
314
cc.fillText( item.title, gx2, gy2 + 16 );
315
} else {
316
cc.fillStyle = "black";
317
cc.fillText( item.title, gx2, gy2 + 16 );
318
}
319
gy2 += 16;
320
}
321
}
322
323
keytype( key ) {
324
switch( key ) {
325
case 38:
326
if( this.cursorY > 0 )
327
this.cursorY --;
328
break;
329
case 40:
330
if( this.cursorY < this.items.length - 1 )
331
this.cursorY ++;
332
break;
333
case 32:
334
let selectedItem = this.items[ this.cursorY ];
335
336
let context;
337
for( let i = this.histories.length - 2; i >= 0; i-- ) {
338
let history = this.histories[ i ];
339
if( selectedItem[ history.title + "時" ] ) {
340
context = history.title;
341
break;
342
}
343
}
344
345
if( selectedItem.submenu || this.bridge || selectedItem[ context + "時" ] ) {
346
347
let cx = this.cx + this.cw + this.cpadding * 2;
348
let cy = this.cy;
349
let title, items;
350
if( this.bridge ) {
351
352
console.log( "bridge使用", this.bridge.title );
353
title = this.bridge.title;
354
items = selectedItem[ this.bridge.propertyName ];
355
} else if( selectedItem.submenu ) {
356
357
title = selectedItem.submenu.title ? selectedItem.submenu.title : selectedItem.title;
358
items = selectedItem.submenu.items;
359
} else {
360
361
console.log( "コンテキスト使用", context );
362
title = selectedItem[ context + "時" ].title;
363
items = selectedItem[ context + "時" ].items;
364
}
365
this.subMenu = new Menu( cx, cy, null, null, title, items, this.app, this.histories );
366
367
if( selectedItem.bridge ) {
368
this.subMenu.bridge = selectedItem.bridge;
369
}
370
this.subMenu.activate( this.tellOk );
371
} else {
372
373
console.log( selectedItem.title );
374
this.tellOk( selectedItem.title );
375
}
376
break;
377
default:
378
console.log( key );
379
}
380
}
381
382
selectionProcedure() {
383
return new Promise(
384
function( tellOk ) {
385
this.activate( tellOk );
386
}.bind( this )
387
);
388
}
389
close() {
390
for( let i = 0; i < this.histories.length; i++ ) {
391
let history = this.histories[ i ];
392
let idx = this.app.drawers.indexOf( history.menu );
393
this.app.drawers.splice( idx, 1 );
394
}
395
}
396
}
397
class Serif extends CtrlWin {
398
constructor() {
399
}
400
}
401
</script>
402
<style>
403
</style>
404
</head>
405
<body onload="onloadx()">
406
<canvas id="test" width="512" height="448" style="
407
border : solid 1px black;
408
float:left;
409
" onclick="location.reload()">
410
</canvas>
411
<div style="float:left; width:512px; padding-left:1em;">
412
<b>最初、キャンプメニュー(フィールド上のコマンド)が表示されます。</b>
413
上下:↑↓キー、決定:スペースキー、キャンセル:なし
414
どうぐ>C1>やくそう でサブメニューの動作を確認できます。
415
しかし、キャンセルがないので戻れません。ブラウザの更新ボタンを押してください。:-(
416
417
<B>「戦闘する」を選ぶと、キャンプメニューは終了し、戦闘のコマンド入力になります。</B>
418
一人目の どうぐ→やくそう→C1 でサブメニューの動作を確認できます。
419
二人分入力して終わりです。(そのまま何もできなくなります)
420
</div>
421
<script>
422
div = document.getElementsByTagName( "div" )[ 0 ];
423
div.innerHTML = div.innerHTML.replace( /\n/g, "<BR>" );
424
</script>
425
</body>
426
</html>