Projet

Général

Profil

Paste
Télécharger (17,3 ko) Statistiques
| Branche: | Révision:

root / js / pano_old.js @ 8b0958ea

1
if (img_prefix == undefined) var img_prefix = './tiles/ttn_mediatheque/mediatheque_70';
2
if (to_cap == undefined) var to_cap = 0;
3
if (to_ele == undefined) var to_ele = 0;
4
if (cap == undefined) var cap = 0;
5
if (elevation == undefined) var elevation = 0;
6
if (cap_min == undefined) var cap_min = cap;
7
if (cap_max == undefined) var cap_max = cap_min+360;
8

    
9
var inserted_points = new Array();
10
var canvas;
11
var cntext;
12
var point_list = new Array();
13
var zoom;
14
var to_zoom;
15
var zooms = new Array();
16
var prev_zm;
17
var zm;
18
var tile = {width:256, height:256};
19
var ntiles = {x:228, y:9};
20
var border_width = 5;
21
var imageObj = new Array();
22

    
23
var last  = {x:0,y:0};
24
var shift = {x:0,y:0};
25
var mouse = {x:0,y:0};
26
var speed = {x:0,y:0};
27
var canvas_pos = {x:0,y:0};
28
var tmt;
29

    
30
var test = {x:0, y:0, i:100};
31

    
32
function nmodulo(val, div) {                // pour obtenir un modulo dans l'espace des nombres naturels N.
33
    return Math.floor((val%div+div)%div);   // il y a peut être plus simple, mais en attendant .... 
34
}
35

    
36
function fmodulo(val, div) {                // pour obtenir un modulo dans l'espace des nombres réels positifs.
37
    return (val%div+div)%div;               // il y a peut être plus simple, mais en attendant .... 
38
}
39

    
40
function distort_canvas(p, x, y) {
41
    if (p == 0) distort = 0;
42
    else {
43
        cntext.save();
44
        distort++;
45
        cntext.clearRect(0, 0, canvas.width, 2*canvas.height);
46
        var ratio = (canvas.width-2*distort)/canvas.width;
47
        var shift = canvas.height/2*(1-ratio);
48
        cntext.scale(1, ratio);
49
        if (p == 1) cntext.translate(0, 0);
50
        else if (p == -1) cntext.translate(0, 0);
51
        draw_image(x, y);
52
        cntext.restore();
53
        document.getElementById('res').innerHTML = 'distort : ' + distort + ' shift ' + shift + ' ratio : ' + ratio + '<br/>';
54
    }
55
}
56

    
57
function draw_image(ox, oy) {
58
    ox = nmodulo(ox-canvas.width/2, zm.im.width);        // pour placer l'origine au centre du canvas 
59
    var ocx = nmodulo(ox - zm.phase_pix, zm.im.width);
60
    //document.getElementById('res').innerHTML = zm.phase_pix + ' -- ' + zm.im.width + ' shift(x,y) ' + shift.x;
61
    oy = Math.floor(oy-canvas.height/2);                             // pas de rebouclage vertical
62

    
63
    cntext.clearRect(0, 0, canvas.width, canvas.height);
64
    cntext.fillStyle = "rgba(128,128,128,0.8)";
65
    
66
    if (canvas.height > zm.im.height) {
67
        var fy = Math.floor((oy+canvas.height/2-zm.im.height/2)/(tile.height*zm.ntiles.y))*zm.ntiles.y;
68
        if (fy < 0) fy = 0; 
69
        var ly = fy + zm.ntiles.y;
70
    } else {
71
        var fy = Math.floor(oy/tile.height);
72
        var ly = Math.floor((oy+canvas.height+tile.height-1)/tile.height+1);
73
        if (fy < 0) fy = 0; 
74
        if (ly > zm.ntiles.y) ly = zm.ntiles.y; 
75
    }
76

    
77
    for (var j=fy; j<ly; j++) {
78
        var delta_y = (Math.floor(j/zm.ntiles.y) - Math.floor(fy/zm.ntiles.y)) * (tile.height - zm.last_tile.height);
79
        var dy = j*tile.height - oy - delta_y;
80
        var ny = j%ntiles.y;
81
        var wy = zm.tile.width;
82
        if (ny == zm.ntiles.y - 1) wy = zm.last_tile.height;
83

    
84
        var cpx = 0;
85
        var i = 0;
86
        var Nx = zm.ntiles.x;
87
        if (zm.im.unused_width != 0) Nx++;
88
        while (cpx < ocx+canvas.width) {
89
            var cur_width = zm.tile.width;
90
            if (i%Nx == zm.ntiles.x-1) cur_width = zm.last_tile.width;
91
            else if (i%Nx == Nx-1) cur_width = zm.im.unused_width;
92
            if (cpx >= ocx-cur_width) {
93
                if (i%Nx == Nx-1 && zm.im.unused_width != 0) {
94
                    cntext.fillRect(cpx-ocx, dy, zm.im.unused_width, wy);
95
                } else {
96
                    var nx = i%Nx;
97
                    load_image(nx, ny, cpx-ocx, dy, ox, oy);
98
                }
99
            }
100
            cpx += cur_width;
101
            i++;
102
        }
103
    }
104
    drawDecorations(ox, oy);
105
}
106

    
107
function load_image(nx, ny, ox, oy, x, y) {
108
    var idx = nx+'-'+ny+'-'+zoom;
109
    if (imageObj[idx] && imageObj[idx].complete) {
110
        draw_tile(idx, ox, oy); // l'image est déja en mémoire, on force le dessin sans attendre.
111
    } else {
112
        var fname = get_file_name(nx, ny, zoom);
113
        imageObj[idx] = new Image();
114
        imageObj[idx].src = fname;
115
        var ts = zm.get_tile_size(nx, ny);
116
        cntext.fillRect(ox, oy, ts.width, ts.height);
117
        var dx = shift.x;
118
        var dy = shift.y;
119
        imageObj[idx].addEventListener('load', function() {draw_tile_del(zoom, dx, dy, idx, ox, oy, x, y)}, false);
120
    }
121
}
122

    
123
function draw_tile_del(ezoom, dx, dy, idx, ox, oy, x, y) {
124
    if (ezoom == zoom && dx == shift.x && dy == shift.y) {
125
        draw_tile(idx, ox, oy);
126
        drawDecorations(x, y);
127
    }
128
}
129

    
130
function draw_tile(idx, ox, oy) {
131
    var img = imageObj[idx];
132
    cntext.drawImage(img, ox, oy);
133
}
134

    
135
function drawDecorations(ox, oy) {
136
    var wgrd = zm.im.width/360;
137
    var od = ((ox+canvas.width/2)/wgrd)%360;
138
    var el = (zm.im.height/2 - (oy+canvas.height/2))/wgrd;
139
//    document.getElementById('angle_ctrl').value = od.toFixed(2);
140
//    document.getElementById('elvtn_ctrl').value = el.toFixed(2);
141
    cntext.fillStyle = "rgba(0,128,128,0.9)";
142
    cntext.strokeStyle = "rgb(255,255,255)";
143
    cntext.lineWidth = 1;
144
    cntext.fillRect(canvas.width/2-5, canvas.height/2-5, 10, 10);
145
    cntext.strokeRect(canvas.width/2-5, canvas.height/2-5, 10, 10);
146
    for(var i = 0; i < zm.pt_list.length; i++) {
147
        var cx = zm.pt_list[i]['xc'] - ox;
148
        var cy = zm.pt_list[i]['yc'] - oy;
149
        if (zm.pt_list[i]['lnk'] != undefined) cntext.fillStyle = "rgba(255,128,128,0.5)";
150
        else cntext.fillStyle = "rgba(128,255,128,0.5)";
151
        cntext.beginPath();
152
        cntext.arc(cx, cy, 20, 0, 2*Math.PI, true);
153
        cntext.fill();
154
    }
155

    
156
    //cntext.font = "20pt Arial";
157
    //cntext.fillRect(0, 0, 200, 20);
158
    //cntext.fillStyle = "rgb(255,0,0)";
159
    //cntext.fillText(od.toFixed(2), 5, 20);
160
    //for (i=0; i<canvas.width/wgrd; i++) {
161
        //cntext.strokeRect(i*wgrd, 0, wgrd, 20);
162
    //}
163
}
164

    
165
function get_file_name(x, y, z) { // recherche du fichier correspondant au zoom et à la position
166
    var prm = [z, x, y];
167
    var fname = img_prefix;
168
    for (var i = 0; i < prm.length; i++) {
169
        fname += '_';
170
        if (prm[i] < 10) fname += '00';
171
        else if (prm[i] < 100) fname += '0';
172
        fname += prm[i];
173
    }
174
    fname += '.jpg';
175
    return fname;
176
}
177

    
178
function keys(key) {
179
    event.preventDefault();
180
    event.stopPropagation();
181
    if (!key) {
182
        key = event;
183
        key.which = key.keyCode;
184
    }
185
    evt = key || event;
186
//    alert(key);
187
//    if (!evt.shiftKey) return;
188
    switch (key.which) {
189
    case 36: // home
190
        test.x=0;
191
        test.y=0;
192
        putImage(test.x, test.y);
193
        return;
194
    case 66: // b
195
        alert(key.pageX);
196
        test.x=tile.width*(ntiles.x-3);
197
        test.y=0;
198
        putImage(test.x, test.y);
199
        return;
200
    case 67: // c
201
        test.x=0;
202
        test.y=tile.height*(ntiles.y-3);
203
        putImage(test.x, test.y);
204
        return;
205
    case 35: // end
206
        test.x=tile.width*(ntiles.x-3);
207
        test.y=tile.height*(ntiles.y-3);
208
        putImage(test.x, test.y);
209
        return;
210
    case 39: // left
211
        test.x+=test.i;
212
        putImage(test.x, test.y);
213
        return;
214
    case 40: // up
215
        test.y+=test.i;
216
        putImage(test.x, test.y);
217
        return;
218
    case 37: // right
219
        test.x-=test.i;
220
        putImage(test.x, test.y);
221
        return;
222
    case 38: // down
223
        test.y-=test.i;
224
        putImage(test.x, test.y);
225
        return;
226
    case 33: // pageup
227
        test.y=0;
228
        putImage(test.x, test.y);
229
        return;
230
    case 34: // pagedown
231
        test.y=tile.height*(ntiles.y-3);
232
        putImage(test.x, test.y);
233
        return;
234
    default:
235
        //alert(key.which)
236
        return;
237
    }
238
}
239

    
240
function onImageClick(e) {
241
    shift.x = last.x;
242
    shift.y = last.y;
243
    speed.x = 0;
244
    speed.y = 0;
245
    mouse.x = e.pageX;
246
    mouse.y = e.pageY;
247
    clearTimeout(tmt);  //arrêt de l'éffet eventuel d'amorti en cours.
248
    canvas.addEventListener('mousemove', stickImage, false);
249
    canvas.addEventListener('mouseup', launchImage, false);
250
    //canvas.addEventListener('mouseout', launchImage, false);
251
    canvas.style.cursor='move';
252
    //document.onmousemove = stickImage;
253
    document.onmouseup = launchImage;
254
    hide_links();
255
}
256

    
257

    
258
function stickImage(e) {
259
    var xs = mouse.x - e.pageX + shift.x;
260
    var ys = mouse.y - e.pageY + shift.y;
261
    speed.x = xs - last.x;  //mémorisation des vitesses horizontales
262
    speed.y = ys - last.y;  //et verticales lors de ce déplacement
263
    putImage(xs, ys);
264
}
265

    
266
function launchImage(e) {
267
    distort_canvas(0);
268
    canvas.removeEventListener('mousemove', stickImage, false);
269
    show_links();
270
    //document.onmousemove = null;
271
    shift.x = e.pageX - mouse.x + shift.x;
272
    shift.y = e.pageY - mouse.y + shift.y;
273
    tmt = setTimeout(inertialImage, 100);
274
}
275

    
276
function putImage(x, y) { // est destiné à permettre l'effet d'amortissement par la mémorisation de la position courante.
277
    if (!zm.is_updated) return; 
278
    if (x >= zm.im.width) {   // rebouclage horizontal
279
        shift.x -= zm.im.width;
280
        x -= zm.im.width;
281
    } else if (x < 0) {
282
        shift.x += zm.im.width;
283
        x += zm.im.width;
284
    }
285
    if (y >= zm.im.height) {   // pas de rebouclage vertical mais blocage
286
        //distort_canvas(1, x, y);
287
        shift.y = zm.im.height-1;
288
        y = zm.im.height-1;
289
    } else if (y < 0) {
290
        //distort_canvas(-1, x, y);
291
        shift.y = 0;
292
        y = 0;
293
    }
294

    
295
    draw_image(x, y);
296
    last.x = x;
297
    last.y = y;
298
}
299

    
300
function inertialImage() {
301
    speed.x *= 0.9;
302
    speed.y *= 0.9;
303
    if (Math.abs(speed.x) > 2 || Math.abs(speed.y) > 2) {
304
        putImage(last.x+speed.x, last.y+speed.y);
305
        tmt = setTimeout(inertialImage, 100);
306
    }
307
}
308

    
309
function tzoom(zv) {
310
    this.value = zv;
311
    this.ntiles = {x:0,y:0};
312
    this.tile = {width:0,height:0};
313
    this.last_tile = {width:0,height:0};
314
    this.max_tile = {width:0,height:0};
315
    this.im = {width:0,height:0};
316
    this.im.unused_width = 0;
317
    this.pt_list = new Array();
318
    this.is_updated = false;
319
    this.refresh = function() {
320
        this.im.visible_width = this.tile.width*(this.ntiles.x-1)+this.last_tile.width;
321
        this.is_updated = true;
322
        var cap_int = (Math.abs(cap_max - cap_min + 0.005)) % 360.0;
323
        if (cap_int < 0.01) this.im.unused_width = 0;
324
        else this.im.unused_width = Math.floor(fmodulo(cap_min - cap_max, 360)*this.im.visible_width/fmodulo(cap_max - cap_min, 360));
325
//        document.getElementById('res').innerHTML += 'unuse_cap ' + fmodulo(cap_min - cap_max) + ' used_cap ' + fmodulo(cap_max - cap_min);
326

    
327
        this.im.width = this.im.visible_width+this.im.unused_width;
328
        this.im.height = this.tile.height*(this.ntiles.y-1)+this.last_tile.height;
329
        if (this.im.unused_width > this.tile.width) this.max_tile.width = this.im.unused_width;
330
        else this.max_tile.width = this.tile.width;
331
        this.max_tile.height = this.tile.height;
332
        this.max_tile.width = 
333
        this.phase_pix = Math.floor(this.im.width*cap_min/360);
334
        for (var i=0; i<point_list.length; i++) {
335
            var tmp = fmodulo(point_list[i][2], 360);
336
            this.pt_list[i] = new Array();
337
            this.pt_list[i]['label'] = point_list[i][0];
338
            this.pt_list[i]['xc'] = Math.floor(tmp * this.im.width/360);
339
            this.pt_list[i]['yc'] = Math.floor(this.im.height/2 - (point_list[i][3] + elevation) * this.im.width/360);
340
            this.pt_list[i]['angle'] = point_list[i][2];
341
            if (point_list[i][4] != '') this.pt_list[i]['lnk'] = point_list[i][4]+'&to_zoom='+zv;
342
        }
343
    }
344
    this.get_tile_size = function(nx, ny) {
345
        var res = {width:0, height:0};
346
        if (nx == this.ntiles.x-1) res.width = this.last_tile.width;
347
        else res.width = this.tile.width;
348
        if (ny == this.ntiles.y-1) res.height = this.last_tile.height;
349
        else res.height = this.tile.height;
350
        return res;
351
    }
352
}
353

    
354
function wheel_zoom (event) {
355
    var zshift = {x:0, y:0};
356
    if (event.pageX != undefined && event.pageX != undefined) {
357
        zshift.x = event.pageX-canvas.width/2-canvas_pos.x;
358
        zshift.y = event.pageY-canvas.height/2-canvas_pos.y;
359
    }
360
    event.preventDefault();
361
    if (event.wheelDelta < 0 && zoom_control.value < zoom_control.max) {
362
        zoom_control.value++;
363
        change_zoom(zshift.x, zshift.y);
364
    } else if (event.wheelDelta > 0 && zoom_control.value > zoom_control.min) {
365
        zoom_control.value--; 
366
        change_zoom(zshift.x, zshift.y);
367
    }
368
}
369

    
370
function change_zoom(shx, shy) {
371
    var zoom_control = document.getElementById("zoom_ctrl");
372
    var v = zoom_control.value;
373

    
374
    prev_zm = zm;
375

    
376
    if (zooms[v]) {
377
        if (!zooms[v].is_updated) zooms[v].refresh();
378
    } else {
379
        zooms[v] = new tzoom(v);
380
    }
381

    
382
    if (zooms[v].is_updated) {
383
        if (shx == undefined || shy == undefined) {
384
            shx=0;
385
            shy=0;
386
        }
387
        zm = zooms[v];
388
        var px = (last.x+shx)*zm.im.width/prev_zm.im.width - shx;
389
        var py = (last.y+shy)*zm.im.height/prev_zm.im.height - shy;
390
        if (py < zm.im.height && py >= 0) {
391
            zoom = zm.value;
392
            tile = zm.tile;
393
            ntiles = zm.ntiles;
394
            putImage(px, py);
395
        } else {
396
            zm = prev_zm;
397
            zoom_control.value = zm.value;
398
        }
399
    }
400
}
401

    
402
function change_angle() {
403
    var elvtn_control = document.getElementById('elvtn_ctrl');
404
    var angle_control = document.getElementById('angle_ctrl');
405
    var pos_x = zm.im.width*angle_control.value/360;
406
    var pos_y = Math.floor(zm.im.height/2 - zm.im.width*elvtn_control.value/360);
407
    putImage(pos_x, pos_y);
408
}
409

    
410
function check_links(e) {
411
    var mouse_x = e.pageX-canvas_pos.x;
412
    var mouse_y = e.pageY-canvas_pos.y;
413
    var pos_x = nmodulo(last.x + mouse_x - canvas.width/2, zm.im.width);
414
    var pos_y = last.y + mouse_y - canvas.height/2;
415
    for(var i = 0; i < zm.pt_list.length; i++) {
416
        if (Math.sqrt((zm.pt_list[i]['xc'] - pos_x) * (zm.pt_list[i]['xc'] - pos_x) + (zm.pt_list[i]['yc'] - pos_y) * (zm.pt_list[i]['yc'] - pos_y)) < 20) {
417
            if (zm.pt_list[i]['lnk'] != undefined) window.location = zm.pt_list[i]['lnk'];
418
            break;
419
        }
420
    }
421
}
422

    
423
function display_links(e) {
424
    var info = document.getElementById('info');
425
    var mouse_x = e.pageX-canvas_pos.x;
426
    var mouse_y = e.pageY-canvas_pos.y;
427
    var pos_x = nmodulo(last.x + mouse_x - canvas.width/2, zm.im.width);
428
    var pos_y = last.y + mouse_y - canvas.height/2;
429
    var cap = ((pos_x/zm.im.width)*360).toFixed(2);
430
    var elev = (((zm.im.height/2 - pos_y)/zm.im.width)*360 - elevation).toFixed(2);
431
    info.innerHTML = 'élévation :'+elev+'<br/>cap :'+cap;
432
    info.style.top = e.pageY+'px';
433
    info.style.left = e.pageX+'px';
434
    info.style.backgroundColor = '#FFC';
435
    canvas.style.cursor='crosshair';
436
    for(var i = 0; i < zm.pt_list.length; i++) {
437
        if (Math.sqrt((zm.pt_list[i]['xc'] - pos_x) * (zm.pt_list[i]['xc'] - pos_x) + (zm.pt_list[i]['yc'] - pos_y) * (zm.pt_list[i]['yc'] - pos_y)) < 20) {
438
            info.innerHTML = zm.pt_list[i]['label'];
439
            info.style.backgroundColor = '#FC8';
440
            canvas.style.cursor='auto';
441
            break;
442
        }
443
    }
444
}
445

    
446
function hide_links() {
447
    canvas.removeEventListener( "mousemove", display_links, false);
448
    var info = document.getElementById('info');
449
    info.style.display = 'none';
450
}
451

    
452
function show_links() {
453
    canvas.addEventListener( "mousemove", display_links, false);
454
    var info = document.getElementById('info');
455
    info.style.display = 'block';
456
}
457

    
458
function show_insert_point(e) {
459
    event.preventDefault();
460
    event.stopPropagation();
461
    var insrt = document.getElementById('insert');
462
    document.getElementById('do-insert').onclick = function() {insert_point(insert, e.pageX-canvas_pos.x, e.pageY-canvas_pos.y)};
463
    document.getElementById('do-cancel').onclick = function() {insert.style.display = 'none'};
464
    insrt.style.left = e.pageX+'px';
465
    insrt.style.top = e.pageY+'px';
466
    insrt.style.display = 'block';
467
}
468

    
469
function insert_point(el, x, y) {
470
    el.style.display = 'none';
471
    for(var i = 0; i < zm.pt_list.length; i++) {
472
        if(zm.pt_list[i]['label'] == document.getElementById('sel_point').value) {
473
            var posx = nmodulo(last.x + x - canvas.width/2 - zm.phase_pix, zm.im.width)/zm.im.width;
474
            var pval = {ratio:posx, angle:zm.pt_list[i]['angle']};
475
            inserted_points.push(pval);
476
            document.getElementById('res').innerHTML += zm.pt_list[i]['label'] + '. ' + posx + '=' + zm.pt_list[i]['angle'] + '<br/>';
477
            if (inserted_points.length > 1) {
478
                var pval0 = inserted_points[inserted_points.length-2];
479
                var origin = fmodulo(pval0.angle - ((pval.angle - pval0.angle)/(pval.ratio - pval0.ratio))*pval0.ratio, 360);
480
                var end = fmodulo(pval.angle + ((pval.angle - pval0.angle)/(pval.ratio - pval0.ratio))*(1-pval.ratio), 360);
481
                document.getElementById('res').innerHTML += 'cap_min = ' + origin + '<br/>';
482
                document.getElementById('res').innerHTML += 'cap_max = ' + end + '<br/>';
483
            }
484
            break;
485
        }
486
    }
487
}
488

    
489
function clean_canvas_events(e) {
490
    canvas.removeEventListener('mousemove', stickImage, false);
491
    document.getElementById('info').style.display = 'none';
492
    speed.x = 0;
493
    speed.y = 0;
494
}
495

    
496
window.onload = function() {
497
    canvas = document.getElementById("mon-canvas");
498
    canvas.style.border = border_width+"px solid red";
499
    cntext = canvas.getContext("2d");
500
    canvas.width = window.innerWidth-200;
501
    canvas.height = window.innerHeight-20;
502
    canvas.addEventListener("click", check_links, false);
503
    canvas_pos.x = canvas.offsetLeft+border_width;
504
    canvas_pos.y = canvas.offsetTop+border_width;
505
    canvas.addEventListener("contextmenu", show_insert_point, false);
506
    canvas.addEventListener("mouseout", clean_canvas_events, false);
507

    
508
    show_links();
509

    
510
    var max_zoom = zooms.length - 1;
511
    zoom_control = document.getElementById("zoom_ctrl");
512
    zoom_control.onchange = change_zoom;
513
    zoom_control.max = max_zoom;
514
    if (to_zoom == undefined || to_zoom > max_zoom) to_zoom = Math.floor(max_zoom/2);
515
    zm = zooms[to_zoom];
516
    zoom_control.value = to_zoom;
517
    zm.refresh();
518

    
519
    zoom = zm.value;
520
    tile = zm.tile;
521
    ntiles = zm.ntiles;
522

    
523
    angle_control = document.getElementById("angle_ctrl");
524
    angle_control.value = to_cap;
525
    angle_control.onchange = change_angle;
526
    angle_control.onclick = change_angle;
527
    angle_control.onkeyup = change_angle;
528
    elvtn_control = document.getElementById("elvtn_ctrl");
529
    elvtn_control.value = to_ele+elevation;
530
    elvtn_control.onchange = change_angle;
531
    elvtn_control.onclick = change_angle;
532
    elvtn_control.onkeyup = change_angle;
533

    
534
    change_angle();
535

    
536
    canvas.addEventListener('mousedown', onImageClick, false);
537
    addEventListener('keyup', keys, false);
538
    canvas.addEventListener('mousewheel', wheel_zoom, false);
539
};