comparison src/de/mpg/mpiwg/itgroup/digilib/icons/greyskin/dllib.js @ 1:83c58ea33792

first release (continued)
author dwinter
date Mon, 03 Jan 2011 09:11:25 +0100
parents
children
comparison
equal deleted inserted replaced
0:6829553d2378 1:83c58ea33792
1 /* Copyright (C) 2003,2004 IT-Group MPIWG, WTWG Uni Bern and others
2
3 This program is free software; you can redistribute it and/or
4 modify it under the terms of the GNU General Public License
5 as published by the Free Software Foundation; either version 2
6 of the License, or (at your option) any later version.
7
8 This program is distributed in the hope that it will be useful,
9 but WITHOUT ANY WARRANTY; without even the implied warranty of
10 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 GNU General Public License for more details.
12
13 You should have received a copy of the GNU General Public License
14 along with this program; if not, write to the Free Software
15 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
16
17 Authors:
18 Christian Luginbuehl, 01.05.2003 (first version)
19 DW 24.03.2004 (Changed for digiLib in Zope)
20 Robert Casties, 8.11.2005
21 Martin Raspe <hertzhaft@biblhertz.it>, 12.12.2005
22 Robert Casties, 4.9.2009
23
24 ! Requires baselib.js !
25 */
26 digilibVersion = "Digilib NG";
27 dllibVersion = "2.042";
28
29 function identify() {
30 // used for identifying a digilib instance
31 // Relato uses that function - lugi
32 return digilibVersion;
33 }
34
35 function createMarkDiv(index) {
36 var div = document.createElement("div");
37 div.className = "mark";
38 div.id = "mark" + index;
39 div.innerHTML = index + 1;
40 document.body.appendChild(div);
41 return div;
42 }
43
44 function bestPicSize(elem, inset) {
45 // returns a Size with the best image size for the given element
46 if (! defined(inset)) {
47 inset = 0;
48 // original value was 25
49 // digilib seems to use the available space better without inset
50 }
51 var ws = getWinSize();
52 var es = getElementPosition(elem);
53 if (es) {
54 ws.width = ws.width - es.x - inset;
55 ws.height = ws.height - es.y - inset;
56 }
57 return ws;
58 }
59
60
61 /****************************************************
62 * digilib specific classes (must be defined first)
63 ****************************************************/
64
65 /*
66 * Marks class
67 */
68 function Marks() {
69 return this;
70 }
71 // Marks inherits from Array
72 Marks.prototype = new Array();
73 Marks.prototype.parse = function(query) {
74 this.length = 0;
75 if (query.indexOf(";") >= 0) {
76 var pa = query.split(";"); // old format with ";"
77 } else {
78 var pa = query.split(","); // new format
79 }
80 for (var i = 0; i < pa.length ; i++) {
81 var pos = pa[i].split("/");
82 if (pos.length > 1) this.push(new Position(pos[0], pos[1]));
83 }
84 }
85 Marks.prototype.getAll = function() {
86 var ma = new Array();
87 for (var i = 0; i < this.length; i++) {
88 ma.push(cropFloat(this[i].x) + "/" + cropFloat(this[i].y));
89 }
90 return ma.join(",");
91 }
92 Marks.prototype.addEvent = function(evt, digilib) {
93 // add a mark from a screen event
94 if (!digilib) digilib = dl;
95 var pos = digilib.trafo.invtransform(evtPosition(evt));
96 this.push(pos);
97 }
98
99 /*
100 * DLParameters -- digilib parameter class
101 */
102 function DLParameters() {
103 // flags for parameter sets
104 this.PARAM_FILE = 1;
105 this.PARAM_MODE = 2;
106 this.PARAM_DIM = 4;
107 this.PARAM_IMAGE = 8;
108 this.PARAM_DPI = 16;
109 this.PARAM_SIZE = 32;
110 this.PARAM_MARK = 64;
111 this.PARAM_PAGES = 128;
112 this.PARAM_CLIENT = 256;
113 /* request parameters */
114 with (this) {
115 // file
116 define('fn', '', PARAM_FILE);
117 define('pn', '1', PARAM_FILE);
118 // mode
119 define('mo', '', PARAM_MODE);
120 // relative dimensions of zoomed image
121 define('wx', '0.0', PARAM_DIM);
122 define('wy', '0.0', PARAM_DIM);
123 define('ww', '1.0', PARAM_DIM);
124 define('wh', '1.0', PARAM_DIM);
125 // image manipulation
126 define('brgt', '0.0', PARAM_IMAGE);
127 define('cont', '0.0', PARAM_IMAGE);
128 define('rot', '0.0', PARAM_IMAGE);
129 define('rgba', '', PARAM_IMAGE);
130 define('rgbm', '', PARAM_IMAGE);
131 // resolution
132 define('ddpi', '', PARAM_DPI);
133 define('ddpix', '', PARAM_DPI);
134 define('ddpiy', '', PARAM_DPI);
135 // marks
136 define('mk', '', PARAM_MARK);
137 // pages total
138 define('pt', '0', PARAM_PAGES);
139 // size
140 define('ws', '1.0', PARAM_SIZE);
141 // client side options
142 define('clop', '', PARAM_CLIENT);
143 }
144 return this;
145 }
146 DLParameters.prototype = new Parameters();
147 // move the inherited getAll because we need it later
148 DLParameters.prototype._getAll = Parameters.prototype.getAll;
149 DLParameters.prototype.getAll = function(paDetail, moDetail, digilib) {
150 if (!digilib) digilib = dl;
151 // get Flags and Marks first
152 var mo = digilib.flags.getAll(moDetail);
153 this.set("mo", mo);
154 var clop = digilib.opts.getAll();
155 this.set("clop", clop);
156 var mk = digilib.marks.getAll();
157 this.set("mk", mk);
158 var ret = this._getAll(paDetail);
159 return ret;
160 }
161
162 /*
163 * DLModes -- digilib flags class
164 */
165 function DLFlags() {
166 // flags for mode sets
167 this.MODE_QUAL = 1;
168 this.MODE_SIZE = 2;
169 this.MODE_MIR = 4;
170 this.MODE_OTHER = 128;
171 this.MODE_ALL = 255;
172 /* mode flags */
173 with (this) {
174 define('q0', MODE_QUAL);
175 define('q1', MODE_QUAL);
176 define('q2', MODE_QUAL);
177 define('fit', MODE_SIZE);
178 define('clip', MODE_SIZE);
179 define('osize', MODE_SIZE);
180 define('vmir', MODE_MIR);
181 define('hmir', MODE_MIR);
182 }
183 return this;
184 }
185 // inherits from Flags
186 DLFlags.prototype = new Flags();
187
188
189 /*
190 * Digilib -- digilib base class
191 */
192 function Digilib() {
193 if (!baseLibVersion) alert("ERROR: baselib.js not loaded!");
194 /* constants */
195 this.MAX_AREA = new Rectangle(0.0, 0.0, 1.0, 1.0);
196 // default inset (for scalerImg relativ to scalerDiv
197 this.INSET = 40; // because of scrollbars of main window and scaler [Firefox bug?]
198 // mouse drag area that counts as one click
199 this.MIN_AREA_SIZE = 3 * 3 + 1;
200 // standard zoom factor
201 this.ZOOMFACTOR = Math.sqrt(2);
202 // bird's eye view dimensions
203 this.BIRD_MAXX = 200;
204 this.BIRD_MAXY = 200;
205 // witdh of arrow bars
206 this.ARROW_WIDTH = 32;
207 // width of calibration bar
208 this.CALIBRATION_WIDTH = 64;
209 /* variables */
210 this.fitOnlyWidth = false;
211 this.fitOnlyHeight = false;
212 this.trafo = null;
213 // page elements
214 this.scalerDiv = null;
215 this.scalerImg = null;
216 this.buttons1Div = null;
217 this.buttons2Div = null;
218 /* parse parameters */
219 this.params = new DLParameters();
220 // put the query parameters (sans "?") in the parameters array
221 this.params.parse(location.search.slice(1));
222 // treat special parameters
223 this.area = this.parseArea();
224 this.marks = new Marks();
225 this.marks.parse(this.params.get("mk"));
226 this.flags = new DLFlags();
227 this.flags.parse(this.params.get("mo"));
228 this.opts = new Flags();
229 this.opts.parse(this.params.get("clop"));
230 return this;
231 }
232 Digilib.prototype.setDLParam = function(e, s, relative) {
233 // sets parameter based on HTML event
234 var nam;
235 var val;
236 if (s.type && (s.type == "select-one")) {
237 nam = s.name;
238 val = s.options[s.selectedIndex].value;
239 } else if (s.name && s.value) {
240 nam = s.name;
241 val = s.value;
242 }
243 if (nam && val) {
244 dl.params.set(nam, val, relative);
245 display();
246 } else {
247 alert("ERROR: unable to process event!");
248 }
249 return true;
250 }
251 Digilib.prototype.parseArea = function() {
252 // returns area Rectangle from current parameters
253 return new Rectangle(
254 this.params.get("wx"),
255 this.params.get("wy"),
256 this.params.get("ww"),
257 this.params.get("wh"));
258 }
259 Digilib.prototype.setParamFromArea = function(rect) {
260 // sets digilib wx etc. from rect
261 this.params.set("wx", cropFloat(rect.x));
262 this.params.set("wy", cropFloat(rect.y));
263 this.params.set("ww", cropFloat(rect.width));
264 this.params.set("wh", cropFloat(rect.height));
265 return true;
266 }
267
268 Digilib.prototype.parseTrafo = function(elem) {
269 // returns Transform from current dlArea and picsize
270 var picsize = getElementRect(elem);
271 var trafo = new Transform();
272 // subtract area offset and size
273 trafo.concat(trafo.getTranslation(new Position(-this.area.x, -this.area.y)));
274 trafo.concat(trafo.getScale(new Size(1/this.area.width, 1/this.area.height)));
275 // scale to screen size
276 trafo.concat(trafo.getScale(picsize));
277 trafo.concat(trafo.getTranslation(picsize));
278 // FIX ME: Robert, kannst Du mal nachsehen, ob das folgende tut, was es soll?
279 // oder gibt es dafuer neuen Code? -- ROC: Bisher funktioniert es nicht!
280 // rotate
281 //var rot = getRotation(- dl.params.get("rot"), new Position(0.5*picsize.width, 0.5*picsize.height));
282 //trafo.concat(rot);
283 // mirror
284 //if (hasFlag("hmir")) trafo.m00 = - trafo.m00; // ??
285 //if (hasFlag("vmir")) trafo.m11 = - trafo.m11; // ??
286 return trafo;
287 }
288
289 Digilib.prototype.onLoad = function() {
290 // initialize digilib; called by body.onload
291 this.scalerDiv = getElement("scaler", true);
292 this.scalerImg = getElement("pic", true);
293 this.buttons1Div = getElement("buttons", true);
294 this.buttons2Div = getElement("options", true);
295 /*
296 * if (this.scalerImg == null && this.scalerDiv) { // in N4 pic is in the
297 * scaler layer this.scalerImg = this.scalerDiv.document.images[0]; }
298 */
299 if ((!this.scalerImg)||(!this.scalerDiv)) {
300 alert("Sorry, digilib doesn't work here!");
301 return false;
302 }
303 // fix fixed menus
304 var ms1 = getElementSize(this.buttons1Div);
305 var ms2 = getElementSize(this.buttons2Div);
306 var maxh = (ms1.height > ms2.height) ? ms1.height : ms2.height;
307 var wins = getWinSize();
308 if ((wins.height <= maxh) || (browserType.isIE && (browserType.versIE < 7))) {
309 // unlock fixed menus to absolute if window is too small or IE
310 this.buttons1Div.style.position = "absolute";
311 this.buttons2Div.style.position = "absolute";
312 }
313 this.setScalerImage(); // setzt auch onImgLoad
314 this.setBirdImage(); // laedt das Bird's Eye Bild
315 }
316
317 Digilib.prototype.setScalerImage = function() {
318 // set the scaler image source (needs the browser size)
319 var picsize = bestPicSize(this.scalerDiv);
320 var menusize = getElementSize(this.buttons1Div);
321 // subtract menu width
322 picsize.width -= menusize.width;
323 picsize.height -= this.INSET;
324 // compose Scaler URL
325 var src = "../servlet/Scaler?"
326 + this.params.getAll(this.params.PARAM_ALL & ~(this.params.PARAM_MARK | this.params.PARAM_PAGES));
327 if (this.opts.get('fitwidth')) {
328 src += "&dw=" + picsize.width;
329 } else if (this.opts.get('fitheight')) {
330 src += "&dh=" + picsize.height;
331 } else {
332 src += "&dw=" + picsize.width + "&dh=" + picsize.height;
333 }
334 // debug(src);
335 this.scalerImg.onload = onImgLoad;
336 this.scalerImg.src = src;
337
338 var digilib = this;
339 // this is a local callback function that can use the current scope
340
341 function onImgLoad() {
342 if (! digilib)
343 return;
344 // make sure the image is loaded so we know its size
345 /* this test seems to have problems sometimes :-(
346 if (defined(digilib.scalerImg.complete) && !digilib.scalerImg.complete) {
347 alert("ERROR: the image seems not to be complete in onImgLoad!?");
348 } */
349 digilib.trafo = digilib.parseTrafo(digilib.scalerImg);
350 // display marks
351 digilib.renderMarks();
352 digilib.showBirdDiv(isBirdDivVisible);
353 digilib.showArrows(); // show arrow overlays for zoom navigation
354 //digilib.moveCenter(true); // click to move point to center
355 // new Slider("sizes", 1, 5, 2);
356
357 //Drag Image (8.9.2009)
358 if (!digilib.isFullArea())
359 registerEvent("mousedown", digilib.scalerDiv, dragImage);
360
361 focus();
362 }
363 }
364
365 Digilib.prototype.renderMarks = function() {
366 // make sure the image is loaded so we know its size
367 if (!this.trafo) {
368 alert("ERROR: trafo missing, cannot render marks!");
369 return;
370 }
371 // debugProps(dlArea, "dlArea");
372 for (var i = 0; i < this.marks.length; i++) {
373 var div = getElement("mark" + i, true) || createMarkDiv(i);
374 var mark = this.marks[i];
375 // debugProps(mark, "mark");
376 if (this.area.containsPosition(mark)) {
377 var mpos = this.trafo.transform(mark);
378 // debugProps(mark, "mpos");
379 // better not hide the marked spot (MR)
380 // suboptimal to place -5 pixels and not half size of mark-image
381 // mpos.x = mpos.x -5;
382 // mpos.y = mpos.y -5;
383 moveElement(div, mpos);
384 showElement(div, true);
385 } else {
386 // hide the other marks
387 showElement(div, false);
388 }
389 }
390 }
391
392 Digilib.prototype.display = function(detail, moDetail) {
393 // redisplay the page
394 var queryString = this.params.getAll(detail, moDetail);
395 location.href
396 = location.protocol + "//"
397 + location.host
398 + location.pathname
399 + "?" + queryString;
400 }
401
402 /* **********************************************
403 * interactive digilib functions
404 * ******************************************** */
405
406 Digilib.prototype.setMark = function() {
407 // add a mark where clicked
408 window.focus();
409 this.moveCenter(false);
410
411 // start event capturing
412 registerEvent("mousedown", this.scalerDiv, markEvent);
413
414 // our own reference to this for the local function
415 var digilib = this;
416
417 function markEvent(evt) {
418 // event handler adding a new mark
419 unregisterEvent("mousedown", digilib.scalerDiv, markEvent);
420 digilib.marks.addEvent(evt);
421 digilib.display();
422 return stopEvent(evt);
423 }
424
425 }
426
427 Digilib.prototype.removeMark = function() {
428 // remove the last mark
429 this.marks.pop();
430 this.display();
431 }
432
433 Digilib.prototype.resetImage = function() {
434 // reset the image to its original state
435 this.display(this.params.PARAM_FILE); // keep only fn/pn
436 }
437
438 Digilib.prototype.dragImage = function(evt) {
439 // drag the image and load a new detail on mouse up
440 // makes sense only when zoomed
441 if (this.isFullArea())
442 return;
443 if(evt.preventDefault) evt.preventDefault(); // no Firefox drag and drop
444 var digilib = this; // our own reference to this for the local function
445 var startPos = evtPosition(evt);
446 var pic = this.scalerImg;
447 var picRect = getElementRect(pic);
448 // fit the grey div to the scaler image
449 var div = getElement("bg");
450 var dx = 0;
451 var dy = 0;
452 moveElement(div, picRect);
453 // hide the scaler image, show it as background of div instead
454 showElement(pic, false);
455 showElement(div, true);
456 div.style.backgroundImage = "url(" + pic.src + ")";
457 div.style.cursor = "move";
458 // start event capturing
459 registerEvent("mousemove", document, moveDragEvent);
460 registerEvent("mouseup", document, moveEndEvent);
461 window.focus();
462
463 function moveDragEvent(evt) {
464 // mousemove handler: drag
465 var pos = evtPosition(evt);
466 // don't use Firefox Drag and Drop feature
467 if(evt.preventDefault) evt.preventDefault();
468 dx = pos.x - startPos.x;
469 dy = pos.y - startPos.y;
470 // move the background image to the new position
471 div.style.backgroundPosition = dx + "px " + dy + "px";
472 return stopEvent(evt);
473 }
474
475 function moveEndEvent(evt) {
476 // mouseup handler: reload digilib
477 div.style.cursor = "default";
478 unregisterEvent("mousemove", document, moveDragEvent);
479 unregisterEvent("mouseup", document, moveEndEvent);
480 // calculate relative offset
481 var x = -dx / pic.width;
482 var y = -dy / pic.height;
483 stopEvent(evt);
484 if (dx == 0 && dy == 0)
485 return // no movement
486 // reload with scaler image showing the new ausschnitt
487 return digilib.moveBy(x, y);
488 }
489 }
490
491 Digilib.prototype.zoomArea = function() {
492 var pt1, pt2;
493 var zoomdiv = getElement("zoom");
494 var overlay = getElement("overlay");
495 // use overlay div to avoid <img> mousemove problems
496 var picRect = getElementRect(this.scalerImg);
497 // FIX ME: is there a way to query the border width from CSS info?
498 // rect.x -= 2; // account for overlay borders
499 // rect.y -= 2;
500 moveElement(overlay, picRect);
501 showElement(overlay, true);
502 // start event capturing
503 registerEvent("mousedown", overlay, zoomStart);
504 registerEvent("mousedown", this.scalerImg, zoomStart);
505 window.focus();
506
507 // our own reference to "this" for the local functions
508 var digilib = this;
509
510 // mousedown handler: start moving
511 function zoomStart(evt) {
512 pt1 = evtPosition(evt);
513 unregisterEvent("mousedown", overlay, zoomStart);
514 unregisterEvent("mousedown", digilib.scalerImg, zoomStart);
515 // setup and show zoom div
516 moveElement(zoomdiv, Rectangle(pt1.x, pt1.y, 0, 0));
517 showElement(zoomdiv, true);
518 // register events
519 registerEvent("mousemove", document, zoomMove);
520 registerEvent("mouseup", document, zoomEnd);
521 return stopEvent(evt);
522 }
523
524 // mouseup handler: end moving
525 function zoomEnd(evt) {
526 pt2 = evtPosition(evt);
527 // assume a click if the area is too small (up to 3 x 3 pixel)
528 var clickRect = new Rectangle(pt1, pt2);
529 clickRect.normalize();
530 if (clickRect.getArea() <= digilib.MIN_AREA_SIZE) {
531 return stopEvent(evt);
532 }
533 // hide zoom div
534 showElement(zoomdiv, false);
535 showElement(overlay, false);
536 // unregister events
537 unregisterEvent("mousemove", document, zoomMove);
538 unregisterEvent("mouseup", document, zoomEnd);
539 // clip and transform
540 clickRect.clipTo(picRect);
541 var area = digilib.trafo.invtransform(clickRect);
542 digilib.setParamFromArea(area);
543 // zoomed is always fit
544 digilib.params.set("ws", 1);
545 digilib.display();
546 return stopEvent(evt);
547 }
548
549 // mouse move handler
550 function zoomMove(evt) {
551 pt2 = evtPosition(evt);
552 var rect = new Rectangle(pt1, pt2);
553 rect.normalize();
554 rect.clipTo(picRect);
555 // update zoom div
556 moveElement(zoomdiv, rect);
557 return stopEvent(evt);
558 }
559 }
560
561 Digilib.prototype.zoomBy = function(factor) {
562 // zooms by the given factor
563 var newarea = this.area.copy();
564 newarea.width /= factor;
565 newarea.height /= factor;
566 newarea.x -= 0.5 * (newarea.width - this.area.width);
567 newarea.y -= 0.5 * (newarea.height - this.area.height);
568 newarea = this.MAX_AREA.fit(newarea);
569 this.setParamFromArea(newarea);
570 this.display();
571 }
572
573
574 Digilib.prototype.zoomFullpage = function(fit) {
575 // zooms out to show the whole image
576 this.params.set("wx", 0.0);
577 this.params.set("wy", 0.0);
578 this.params.set("ww", 1.0);
579 this.params.set("wh", 1.0);
580 if (fit == "width") {
581 this.opts.set('fitwidth');
582 } else if (fit == "height") {
583 this.opts.set('fitheight');
584 } else {
585 this.opts.reset('fitwidth');
586 this.opts.reset('fitheight');
587 }
588 this.display();
589 }
590
591
592 Digilib.prototype.moveCenter = function(on) {
593 // move visible area so that it's centered around the clicked point
594 if (this.isFullArea()) return; // nothing to do
595 // starting event capture
596 if (on) registerEvent("mousedown", this.scalerImg, moveCenterEvent);
597 else unregisterEvent("mousedown", this.scalerImg, moveCenterEvent);
598 window.focus();
599
600 // our own reference to this for the local function
601 var digilib = this;
602
603 function moveCenterEvent(evt) {
604 // move to handler
605 var pt = digilib.trafo.invtransform(evtPosition(evt));
606 var newarea = digilib.area.copy();
607 newarea.setCenter(pt);
608 newarea.stayInside(this.MAX_AREA);
609 // newarea = dlMaxArea.fit(newarea);
610 // debugProps(newarea, "newarea");
611 // debugProps(dlArea, "dlArea");
612 if (newarea.equals(digilib.area)) return; // keep event handler
613 unregisterEvent("mousedown", digilib.scalerImg, moveCenterEvent);
614 // set parameters
615 digilib.setParamFromArea(newarea);
616 digilib.display();
617 }
618 }
619
620 Digilib.prototype.isFullArea = function(area) {
621 if (!area) area = this.area;
622 return (area.width == 1.0) && (area.height == 1.0);
623 }
624
625 Digilib.prototype.canMove = function(movx, movy) {
626 if (this.isFullArea()) return false;
627 var x2 = this.area.x + this.area.width;
628 var y2 = this.area.y + this.area.height;
629 // debugProps(dlArea);
630 return ((movx < 0) && (this.area.x > 0))
631 || ((movx > 0) && (x2 < 1.0))
632 || ((movy < 0) && (this.area.y > 0))
633 || ((movy > 0) && (y2 < 1.0))
634 }
635
636 Digilib.prototype.moveBy = function(movx, movy) {
637 // move visible area by movx and movy (in units of ww, wh)
638 if (!this.canMove(movx, movy)) return; // nothing to do
639 var newarea = this.area.copy();
640 newarea.x += parseFloat(movx)*this.area.width;
641 newarea.y += parseFloat(movy)*this.area.height;
642 newarea = this.MAX_AREA.fit(newarea);
643 // set parameters
644 this.setParamFromArea(newarea);
645 this.display();
646 }
647
648 Digilib.prototype.getRef = function(baseUrl) {
649 // returns a reference to the current digilib set
650 if (!baseUrl) baseUrl
651 = location.protocol
652 + "//"
653 + location.host
654 + location.pathname;
655 var hyperlinkRef = baseUrl;
656 with (this.params) {
657 // all without ddpi, pt
658 var ps = getAll(PARAM_ALL & ~(PARAM_DPI | PARAM_PAGES | PARAM_CLIENT));
659 }
660 if (ps.length > 0) hyperlinkRef += "?" + ps;
661 return hyperlinkRef;
662 }
663
664 Digilib.prototype.getRefWin = function(type, msg) {
665 // shows an alert with a reference to the current digilib set
666 if (! msg) msg = "URL reference to the current view";
667 prompt(msg, this.getRef());
668 }
669
670 Digilib.prototype.getQuality = function() {
671 // returns the current q setting
672 for (var i = 0; i < 3; i++) {
673 if (this.flags.get("q"+i)) return i;
674 }
675 return 1
676 }
677
678 Digilib.prototype.setQuality = function(qual) {
679 // set the image quality
680 if ((qual < 0)||(qual > 2)) return alert("Quality setting not supported");
681 for (var i = 0; i < 3; i++) this.flags.reset("q" + i);
682 this.flags.set("q" + qual);
683 this.display();
684 }
685
686 Digilib.prototype.setQualityWin = function(msg) {
687 // dialog for setting quality
688 if (! msg) msg = "Quality (0..2)";
689 var q = this.getQuality();
690 var newq = window.prompt(msg, q);
691 if (newq) this.setQuality(newq);
692 }
693
694 Digilib.prototype.mirror = function(dir) {
695 // mirror the image horizontally or vertically
696 if (dir == "h") {
697 this.flags.toggle("hmir");
698 } else {
699 this.flags.toggle("vmir");
700 }
701 this.display();
702 }
703
704 Digilib.prototype.gotoPage = function(gopage, keep) {
705 // goto given page nr (+/-: relative)
706 var oldpn = parseInt(this.params.get("pn"));
707 // set with relative=true uses the sign
708 this.params.set("pn", gopage, true);
709 // now check the outcome
710 var pn = parseInt(this.params.get("pn"));
711 if (pn < 1) {
712 alert("No such page! (Page number too low)");
713 this.params.set("pn", oldpn);
714 return;
715 }
716 if (this.params.isSet("pt")) {
717 pt = parseInt(this.params.get("pt"))
718 if (pn > pt) {
719 alert("No such page! (Page number too high)");
720 this.params.set("pn", oldpn);
721 return;
722 }
723 }
724 if (keep) {
725 this.display(this.params.PARAM_ALL & ~this.params.PARAM_MARK); // all, no mark
726 } else {
727 this.display(this.params.PARAM_FILE | this.params.PARAM_MODE | this.params.PARAM_PAGES, this.params.MODE_QUAL | this.params.MODE_OTHER); // fn, pn, ws, mo + pt
728 }
729 }
730
731 Digilib.prototype.gotoPageWin = function() {
732 // dialog to ask for new page nr
733 var pn = this.params.get("pn");
734 var gopage = window.prompt("Go to page", pn);
735 if (gopage) this.gotoPage(gopage);
736 }
737
738 Digilib.prototype.setParamWin = function(param, text, relative) {
739 // dialog to ask for new parameter value
740 var val = this.params.get(param);
741 var newval = window.prompt(text, val);
742 if (newval) {
743 this.params.set(param, newval, relative);
744 this.display();
745 }
746 }
747
748 Digilib.prototype.showOptions = function(show) {
749 // show or hide option div
750 var elem = getElement("dloptions");
751 showElement(elem, show);
752 // FIX ME: get rid of the dotted line around the buttons when focused
753 }
754
755 Digilib.prototype.showAboutDiv = function(show) {
756 // show or hide "about" div
757 var elem = getElement("about");
758 if (elem == null) {
759 if (show) alert("About Digilib - dialog missing in HTML code!"
760 + "\nDigilib Version: " + digilibVersion
761 + "\JSP Version: " + jspVersion
762 + "\ndlLib Version: " + dllibVersion
763 + "\nbaseLib Version: " + baseLibVersion);
764 return;
765 }
766 if (show) {
767 getElement("digilib-version").innerHTML = "Digilib Version: " + digilibVersion;
768 getElement("jsp-version").innerHTML = "JSP Version: " + jspVersion;
769 getElement("baselib-version").innerHTML = "baseLib Version: " + baseLibVersion;
770 getElement("dllib-version").innerHTML = "dlLib Version: " + dllibVersion;
771 var aboutRect = getElementRect(elem);
772 aboutRect.setCenter(getWinRect().getCenter());
773 moveElement(elem, aboutRect);
774 }
775 showElement(elem, show);
776 }
777
778 Digilib.prototype.setBirdImage = function() {
779 var img = getElement("bird-image");
780 var src = "../servlet/Scaler?"
781 + this.params.getAll(this.params.PARAM_FILE)
782 + "&dw=" + this.BIRD_MAXX
783 + "&dh=" + this.BIRD_MAXY;
784 img.src = src;
785 }
786
787 Digilib.prototype.showBirdDiv = function(show) {
788 // show or hide "bird's eye" div
789 var startPos; // anchor for dragging
790 var newRect; // position after drag
791 var birdImg = getElement("bird-image");
792 var birdArea = getElement("bird-area");
793 var overlay = getElement("bird-overlay");
794 showElement(birdImg, show);
795 // dont show selector if area has full size
796 if (!show || this.isFullArea()) {
797 // hide area
798 showElement(birdArea, false);
799 showElement(overlay, false);
800 return;
801 };
802 var birdImgRect = getElementRect(birdImg);
803 var area = this.area;
804 if (this.flags.get("osize") || this.flags.get("clip")) {
805 // in original-size and pixel-by-pixel mode the area size is not valid
806 var birdAreaRect = new Rectangle(
807 birdImgRect.x + birdImgRect.width * area.x,
808 birdImgRect.y + birdImgRect.height * area.y,
809 5,
810 5);
811 } else {
812 // scale area down to img size
813 var birdAreaRect = new Rectangle(
814 // what about borders ??
815 birdImgRect.x + birdImgRect.width * area.x,
816 birdImgRect.y + birdImgRect.height * area.y,
817 birdImgRect.width * area.width,
818 birdImgRect.height * area.height);
819 }
820 moveElement(birdArea, birdAreaRect);
821 showElement(birdArea, true);
822 moveElement(overlay, birdImgRect);
823 showElement(overlay, true);
824 registerEvent("mousedown", overlay, birdAreaStartDrag);
825 registerEvent("mousedown", birdImg, birdAreaStartDrag);
826
827 // our own reference to this for local functions
828 var digilib = this;
829
830 function birdAreaStartDrag(evt) {
831 // mousedown handler: start drag
832 startPos = evtPosition(evt);
833 unregisterEvent("mousedown", overlay, birdAreaStartDrag);
834 unregisterEvent("mousedown", birdImg, birdAreaStartDrag);
835 registerEvent("mousemove", document, birdAreaMove);
836 registerEvent("mouseup", document, birdAreaEndDrag);
837 // debugProps(getElementRect(bird))
838 return stopEvent(evt);
839 }
840
841 function birdAreaMove(evt) {
842 // mousemove handler: drag
843 var pos = evtPosition(evt);
844 var dx = pos.x - startPos.x;
845 var dy = pos.y - startPos.y;
846 // move birdArea div, keeping size
847 newRect = new Rectangle(
848 birdAreaRect.x + dx,
849 birdAreaRect.y + dy,
850 birdAreaRect.width,
851 birdAreaRect.height);
852 // stay within image
853 newRect.stayInside(birdImgRect);
854 moveElement(birdArea, newRect);
855 showElement(birdArea, true);
856 return stopEvent(evt);
857 }
858
859 function birdAreaEndDrag(evt) {
860 // mouseup handler: reload page
861 unregisterEvent("mousemove", document, birdAreaMove);
862 unregisterEvent("mouseup", document, birdAreaEndDrag);
863 showElement(overlay, false);
864 if (newRect == null) { // no movement happened
865 startPos = birdAreaRect.getCenter();
866 birdAreaMove(evt); // set center to click position
867 }
868 digilib.params.set("wx", cropFloat((newRect.x - birdImgRect.x) / birdImgRect.width));
869 digilib.params.set("wy", cropFloat((newRect.y - birdImgRect.y) / birdImgRect.height));
870 // zoomed is always fit
871 digilib.params.set("ws", 1);
872 digilib.display();
873 return stopEvent(evt);
874 }
875 }
876
877 Digilib.prototype.showArrow = function(name, rect, show) {
878 var arrow = getElement(name);
879 moveElement(arrow, rect);
880 showElement(arrow, show);
881 }
882
883 Digilib.prototype.showArrows = function() {
884 // show the 4 arrow bars on top of scaler img according to current dlArea
885 var r = getElementRect(this.scalerImg);
886 this.showArrow('up',
887 new Rectangle(r.x, r.y, r.width, this.ARROW_WIDTH),
888 this.canMove(0, -1)
889 );
890 this.showArrow('down',
891 new Rectangle(r.x, r.y + r.height - this.ARROW_WIDTH, r.width, this.ARROW_WIDTH),
892 this.canMove(0, 1)
893 );
894 this.showArrow('left',
895 new Rectangle(r.x, r.y, this.ARROW_WIDTH, r.height),
896 this.canMove(-1, 0)
897 );
898 this.showArrow('right',
899 new Rectangle(r.x + r.width - this.ARROW_WIDTH, r.y, this.ARROW_WIDTH, r.height),
900 this.canMove(1, 0)
901 );
902 }
903
904 Digilib.prototype.calibrate = function() {
905 // calibrate screen resolution
906 var calDiv = getElement("calibration");
907 var calRect = getElementRect(calDiv);
908 moveCenter(false);
909 var wins = getWinSize();
910 calRect.setCenter(new Position(wins.width / 2, wins.height / 2));
911 moveElement(calDiv, calRect);
912 showElement(calDiv, true);
913 var cm = window.prompt("The length of the scale on your screen in centimeter:");
914 if (cm) {
915 var dpi = calRect.width / parseFloat(cm) * 2.54;
916 this.params.set("ddpi", cropFloat(dpi));
917 }
918 showElement(calDiv, false);
919 }
920
921
922 Digilib.prototype.setScale = function(scale) {
923 // sets original-size, pixel-by-pixel or fit-to-screen scale type
924 if (scale == "pixel") {
925 // pixel by pixel
926 this.flags.set("clip");
927 this.flags.reset("osize");
928 this.flags.reset("fit");
929 } else if (scale == "original") {
930 // original size -- needs calibrated screen
931 if (!this.params.isSet("ddpi")) {
932 var dpi = cookie.get("ddpi");
933 if (dpi == null) {
934 alert("Your screen has not yet been calibrated - using default value of 72 dpi");
935 dpi = 72;
936 }
937 this.params.set("ddpi", dpi);
938 }
939 this.flags.set("osize");
940 this.flags.reset("clip");
941 this.flags.reset("fit");
942 } else {
943 // scale to screen size (default)
944 this.flags.reset("clip");
945 this.flags.reset("osize");
946 }
947 this.display();
948 }
949
950 Digilib.prototype.getScale = function() {
951 // returns scale type
952 if (this.flags.get("clip")) {
953 return "pixel";
954 } else if (this.flags.get("osize")) {
955 return "original";
956 } else {
957 return "fit";
958 }
959 }
960
961 Digilib.prototype.pageWidth = function() {
962 this.zoomFullpage('width');
963 }
964
965 Digilib.prototype.setSize = function(factor) {
966 this.params.set("ws", factor);
967 this.display();
968 }
969
970 Digilib.prototype.showMenu = function(menuId, buttonId, show) {
971 var menu = getElement(menuId);
972 if (show) {
973 // align right side of menu with button
974 var buttonPos = getElementPosition(getElement(buttonId));
975 var menusize = getElementSize(menu);
976 moveElement(menu, new Position(buttonPos.x - menusize.width - 3, buttonPos.y));
977 }
978 showElement(menu, show);
979 }
980
981
982 /********************************
983 * global variables
984 ********************************/
985
986 var dl = new Digilib();
987
988 /* old parameter function compatibility stuff */
989 function newParameter(a,b,c) {return dl.params.define(a,b,c)};
990 function resetParameter(a) {return dl.params.reset(a)};
991 function deleteParameter(a) {return dl.params.remove(a)};
992 function getParameter(a) {return dl.params.get(a)};
993 function setParameter(a,b,c) {return dl.params.set(a,b,c)};
994 function hasParameter(a) {return dl.params.isSet(a)};
995 function getAllParameters(a) {return dl.params.getAll(a)};
996 getQueryString = getAllParameters;
997 function parseParameters(a) {return dl.params.parse(a)};
998 function getAllMarks() {return dl.marks.getAll()};
999 getMarksQueryString = getAllMarks;
1000 function addMark(evt) {return dl.marks.addEvent(evt)};
1001 function deleteMark() {return dl.marks.pop()};
1002 function deleteAllMarks() {return dl.marks = new Marks()};
1003 function hasFlag(mode) {return dl.flags.get(mode)};
1004 function addFlag(mode) {return dl.flags.set(mode)};
1005 function removeFlag(mode) {return dl.flags.reset(mode)};
1006 function toggleFlag(mode) {return dl.flags.toggle(mode)};
1007 function getAllFlags() {return dl.flags.getAll()};
1008 /* old digilib function compatibility */
1009 function setDLParam(e, s, relative) {dl.setDLParam(e, s, relative)};
1010 function display(detail, moDetail) {dl.display(detail, moDetail)};
1011 function setMark(reload) {dl.setMark(reload)};
1012 function removeMark(reload) {dl.removeMark(reload)};
1013 function resetImage() {dl.resetImage()};
1014 function dragImage(evt) {dl.dragImage(evt)};
1015 function zoomArea() {dl.zoomArea()};
1016 function zoomBy(factor) {dl.zoomBy(factor)};
1017 function zoomFullpage(a) {dl.zoomFullpage(a)};
1018 function moveCenter(on) {dl.moveCenter(on)};
1019 function isFullArea(area) {dl.isFullArea(area)};
1020 function canMove(movx, movy) {dl.canMove(movx, movy)};
1021 function moveBy(movx, movy) {dl.moveBy(movx, movy)};
1022 function getRef(baseURL) {dl.getRef(baseURL)};
1023 function getRefWin(type, msg) {dl.getRefWin(type, msg)};
1024 function getQuality() {dl.getQuality()};
1025 function setQuality(qual) {dl.setQuality(qual)};
1026 function setQualityWin(msg) {dl.setQualityWin(msg)};
1027 function mirror(dir) {dl.mirror(dir)};
1028 function gotoPage(gopage, keep) {dl.gotoPage(gopage, keep)};
1029 function gotoPageWin() {dl.gotoPageWin()};
1030 function setParamWin(param, text, relative) {dl.setParamWin(param, text, relative)};
1031 function showOptions(show) {dl.showOptions(show)};
1032 function showBirdDiv(show) {dl.showBirdDiv(show)};
1033 function showAboutDiv(show) {dl.showAboutDiv(show)};
1034 function calibrate(direction) {dl.calibrate(direction)};
1035 function setScale(a) {dl.setScale(a)};
1036 function getScale(a) {dl.getScale(a)};
1037 function originalSize(on) {dl.originalSize(on)};
1038 function pixelByPixel(on) {dl.pixelByPixel(on)};
1039 function pageWidth() {dl.pageWidth()};
1040 function setSize(factor) {dl.setSize(factor)};
1041 function showMenu(a,b,c) {dl.showMenu(a,b,c)};
1042
1043
1044 // :tabSize=4:indentSize=4:noTabs=true:
1045