Annotation of loncom/html/adm/jsMath/plugins/spriteImageFonts.js, revision 1.2

1.1       albertel    1: /*
                      2:  *  plugins/spriteImageFonts.js
                      3:  *  
                      4:  *  Part of the jsMath package for mathematics on the web.
                      5:  *
                      6:  *  This file makes jsMath use single files for the image fonts
                      7:  *  rather than individual images for each character.
                      8:  *
                      9:  *  ---------------------------------------------------------------------
                     10:  *
                     11:  *  Copyright 2006 by Davide P. Cervone
                     12:  * 
                     13:  *  Licensed under the Apache License, Version 2.0 (the "License");
                     14:  *  you may not use this file except in compliance with the License.
                     15:  *  You may obtain a copy of the License at
                     16:  * 
                     17:  *      http://www.apache.org/licenses/LICENSE-2.0
                     18:  * 
                     19:  *  Unless required by applicable law or agreed to in writing, software
                     20:  *  distributed under the License is distributed on an "AS IS" BASIS,
                     21:  *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
                     22:  *  See the License for the specific language governing permissions and
                     23:  *  limitations under the License.
                     24:  */
                     25: 
                     26: if (!window.jsMath) {window.jsMath = {}}
                     27: if (!jsMath.styles) {jsMath.styles = []}
                     28: 
                     29: jsMath.styles['.typeset .img']     = 'position:relative; display:inline-block; overflow:hidden; background-repeat: no-repeat';
                     30: jsMath.styles['.typeset .img .xy'] = 'position:relative; left:0px; top:0px';
                     31: 
                     32: // for Mozilla
                     33: jsMath.styles['.typeset .mimg']       = 'position:relative';
                     34: jsMath.styles['.typeset .mimg .size'] = 'display:-moz-inline-box';
                     35: jsMath.styles['.typeset .mimg .wh']   = 'position:absolute; left:0px; top:0px; overflow:hidden';
                     36: jsMath.styles['.typeset .mimg .xy']   = 'position:relative; left:0px; top:0px';
                     37: // for MSIE
                     38: jsMath.styles['.typeset .mimg .h']    = 'position:relative; display:inline-block; width:0px';
                     39: 
                     40: /*
                     41:  *  Replace the TeXIMG function with one that uses the sprite fonts
                     42:  */
                     43: if (!jsMath.Box) {jsMath.Box = {}}
                     44:   jsMath.Box.TeXIMG = function (font,C,size) {
                     45:     var c = jsMath.TeX[font][C];
                     46:     if (c.img.reload && jsMath.Img[c.img.reload][font].loaded == 1)
                     47:       {delete c.img.reload; c.img.size = null}
                     48:     if (c.img.size != null && c.img.size == size &&
                     49:         c.img.best != null && c.img.best == jsMath.Img.best) return;
                     50:     var mustScale = (jsMath.Img.scale != 1);
                     51:     var id = jsMath.Img.best + size - 4;
                     52:     if (id < 0) {id = 0; mustScale = 1} else
                     53:     if (id >= jsMath.Img.fonts.length) {id = jsMath.Img.fonts.length-1; mustScale = 1}
                     54:     var imgFont = jsMath.Img[jsMath.Img.fonts[id]][font];
                     55:     if (!imgFont.loaded && jsMath.Browser.waitForImages) {
                     56:       // store information so several fonts can be loaded at once
                     57:       jsMath.Img.mustLoad[jsMath.Img.mustLoad.length] = [font,jsMath.Img.fonts[id]];
                     58:       imgFont.loaded = -1;
                     59:     }
                     60:     var img = imgFont[C];
                     61:     var scale = 1/jsMath.Img.w[jsMath.Img.fonts[id]];
                     62:     if (id != jsMath.Img.best + size - 4) {
                     63:       if (c.w != null) {scale = c.w/img[0]} else {
                     64:         scale *= jsMath.Img.fonts[size]/jsMath.Img.fonts[4]
                     65:               *  jsMath.Img.fonts[jsMath.Img.best]/jsMath.Img.fonts[id];
                     66:       }
                     67:     }
                     68: 
                     69:     // get the metrics for the character glyph
                     70:     var bScale = jsMath.Browser.imgScale;
                     71:     if (img[3] == null) {img[3] = 0}
                     72:     var w = (img[0]-img[3])*scale; var h = img[1]*scale; var d = -img[2]*scale;
                     73:     var x = img[3]-imgFont.x[C%16]; var y = img[1]-img[2]-imgFont.y[Math.floor(C/16)];
                     74:     var wh; var xy; var v;
                     75:     var ladjust = ""; var resize = ""; var vadjust; var wadjust;
                     76: 
                     77:     if ((mustScale || jsMath.Controls.cookie.scaleImg) && !jsMath.Browser.operaImageFonts) {
                     78:       w += 2/jsMath.em; h += 2/jsMath.em; d -= 1/jsMath.em; y += 1; x += 1; // try to adjust for rounding errors
                     79:       resize = "width:"+jsMath.HTML.Em(imgFont.wh[0]*scale*bScale)+";";
                     80:       wh = "width:"+jsMath.HTML.Em(w*bScale)+";height:"+jsMath.HTML.Em(h*bScale)+";";
                     81:       xy = "left:"+jsMath.HTML.Em(x*scale*bScale)+";top:"+jsMath.HTML.Em(y*scale*bScale)+";";
                     82:       vadjust = "vertical-align:"+jsMath.HTML.Em(d*bScale)+";";
                     83:       v = jsMath.HTML.Em(h+d);
                     84:       if (img[3]) {ladjust = "margin-left:"+jsMath.HTML.Em(-img[3]*scale*bScale)+";"}
                     85:     } else {
                     86:       if (jsMath.Browser.msieAlphaBug && jsMath.Controls.cookie.alpha) {
                     87:         resize = "height:"+(imgFont.wh[1]*jsMath.Browser.imgScale)+"px;"
                     88:                + "width:"+(imgFont.wh[0]*jsMath.Browser.imgScale)+"px;";
                     89:       }
                     90:       wh = "width:"+img[0]+"px; height:"+img[1]+"px;";
                     91:       xy = "left:"+x+"px; top:"+y+"px;";
                     92:       vadjust = "vertical-align:"+(-img[2])+"px;"; v = (img[1]-img[2])+"px";
                     93:       if (img[3]) {ladjust = "margin-left:"+(-img[3])+"px;"}
                     94:     }
                     95: 
                     96:     wadjust = (c.w == null || Math.abs(c.w-w) < .01)? "" : " margin-right:"+jsMath.HTML.Em(c.w-w)+';';
                     97:     if (img[2] == 0 || jsMath.Browser.valignBug) {vadjust = ""}
                     98: 
                     99:     // get the image
                    100:     var URL = jsMath.Img.URL(font,jsMath.Img.fonts[id],C); var IMG;
                    101:     if (jsMath.Browser.msieAlphaBug && jsMath.Controls.cookie.alpha) {
                    102:       IMG = '<span class="xy" style="'+xy+'">'
                    103:           +   '<img src="'+jsMath.blank+'" style="' + resize
                    104:           +      'filter:progid:DXImageTransform.Microsoft.AlphaImageLoader(src='
                    105:           +      "'" + URL + "', sizingMethod='scale'" + ');" />'
                    106:           + '</span>';
                    107:     } else {
                    108:       IMG = '<img src="'+URL+'" class="xy" style="'+xy+resize+'" />';
                    109:     }
                    110:     if (imgFont.loaded == -1) {IMG = ""; c.img.reload = jsMath.Img.fonts[id]}
                    111: 
                    112:     // get the HTML for cropping the image
                    113:     c.c = this.IMG(IMG,wh,vadjust,wadjust,ladjust,v,x,y,URL);
                    114:     c.tclass = "normal";
                    115:     c.img.bh = h+d; c.img.bd = -d;
                    116:     c.img.size = size; c.img.best = jsMath.Img.best;
                    117:   };
                    118: 
                    119:   /*
                    120:    *  Default uses inline-box containing an image
                    121:    */
                    122:   jsMath.Box.IMG = function (IMG,wh,vadjust,wadjust,ladjust,v,x,y,URL) {
                    123:     return '<span class="img" style="'+wh+vadjust+wadjust+ladjust+'">'
                    124:              + IMG + '</span>' + jsMath.Browser.msieImgFontBBoxFix;
                    125:   };
                    126: 
                    127:   /*
                    128:    *  Opera bug in inline-block alignment forces use of background image
                    129:    */
                    130:   jsMath.Box.IMG_opera = function (IMG,wh,vadjust,wadjust,ladjust,v,x,y,URL) {
                    131:     var html = '<span class="img" style="background-image: url('+URL+');'
                    132:              +    wh + vadjust + 'background-position: '+x+'px '+y+'px"></span>';
                    133:     if (wadjust || ladjust)
                    134:       {html = '<span style="'+wadjust+ladjust+'">' + html + '</span>'}
                    135:     return html;
                    136:   };
                    137: 
                    138:   /*
                    139:    *  Mozilla's -moz-inline-box has top aligned with baseline, so adjust
                    140:    */
                    141:   jsMath.Box.IMG_mozilla = function (IMG,wh,vadjust,wadjust,ladjust,v,x,y,URL) {
                    142:     vadjust = "vertical-align:"+v+";";
                    143:     var html = '<span class="mimg" style="'+vadjust+'">'
                    144:              +   '<span class="size" style="'+wh+'"></span>'
                    145:              +   '<span class="wh" style="'+wh+'">' + IMG + '</span>'
                    146:              + '</span>';
                    147:     if (wadjust || ladjust)
                    148:       {html = '<span style="'+wadjust+ladjust+'">' + html + '</span>'}
                    149:     return html;
                    150:   };
                    151: 
                    152:   /*
                    153:    *  MSIE screws up vadjust on inline-box elements, so use absolute
                    154:    *  positioning and an extra span to set the width and height
                    155:    */
                    156:   jsMath.Box.IMG_msie = function (IMG,wh,vadjust,wadjust,ladjust,v,x,y,URL) {
                    157:     var html = '<span class="mimg">'
                    158:              +   '<span class="h" style="height:'+v+'">'
                    159:              +     '<span class="wh" style="'+wh+'">' + IMG + '</span>'
                    160:              +   '</span>'
                    161:              +   '<span class="img" style="'+wh+vadjust+'"></span>'
                    162:              + '</span>';
                    163:     if (wadjust || ladjust) {
                    164:       html = jsMath.Browser.msieSpaceFix
                    165:            +    '<span style="'+wadjust+ladjust+'">' + html + '</span>';
                    166:     }
                    167:     return html;
                    168:   };
                    169: 
                    170: if (!jsMath.Img) {jsMath.Img = {}}
                    171: 
                    172:   /*
1.2     ! albertel  173:    *  Called by the extra-font definition files to add an image font
1.1       albertel  174:    *  into the mix (save offset data and image size)
                    175:    */
                    176:   jsMath.Img.AddFont = function (size,def) {
                    177:     if (!jsMath.Img[size]) {jsMath.Img[size] = {}};
                    178:     for (var font in def) {
                    179:       def[font].x = def[font][128]; def[font].y = def[font][129];
                    180:       def[font].wh = def[font][130];
                    181:       delete def[font][128]; delete def[font][129]; delete def[font][130];
                    182:     }
                    183:     jsMath.Add(jsMath.Img[size],def);
                    184:   };
                    185: 
                    186:   /*
                    187:    *  Get URL to directory for given font and size, based on the
                    188:    *  user's alpha/plain setting
                    189:    */
                    190:   jsMath.Img.URL = function (name,size) {
                    191:     if (size == null) {return this.root+name+'/font.js'}
                    192:     var type = (jsMath.Controls.cookie.alpha) ? '/alpha/': '/plain/';
                    193:     return this.root+name+type+size+'.png';
                    194:   };
                    195: 
                    196:   /*
                    197:    *  Laod the data for an image font
                    198:    */
                    199:   jsMath.Img.LoadFont = function (name) {
                    200:     if (jsMath.browser == 'OmniWeb' && !jsMath.Browser.hasInlineBlock) {
                    201:       jsMath.noImgFonts = 1;
                    202:       jsMath.Font.Check();
                    203:       return;
                    204:     }
                    205:     if (!this.loaded) this.Init();
                    206:     jsMath.Setup.Script(this.URL(name));
                    207:   };
                    208:   
                    209:   /*
                    210:    *  Setup for print mode
                    211:    */
                    212:   jsMath.Img.Init = function () {
                    213:     if ((jsMath.Controls.cookie.print || jsMath.Controls.cookie.stayhires) && !jsMath.Browser.operaImgFonts) {
                    214:       jsMath.Controls.cookie.print = jsMath.Controls.cookie.stayhires;
                    215:       this.factor *= 3;
                    216:       if (!jsMath.Controls.isLocalCookie || !jsMath.Global.isLocal) {jsMath.Controls.SetCookie(0)}
                    217:       if (jsMath.Browser.alphaPrintBug) {jsMath.Controls.cookie.alpha = 0}
                    218:     }
                    219:     this.loaded = 1;
                    220:     jsMath.Browser.ImgFontInit();
                    221:     jsMath.Img.root = jsMath.root + "fonts-sprite/";
                    222:   };
                    223: 
                    224: 
                    225: if (!jsMath.Browser) {jsMath.Browser = {}}
                    226:   /*
                    227:    *  These should be part of the regular browser
                    228:    *  test functions
                    229:    */
                    230:   jsMath.Browser.ImgFontInit = function () {
                    231:     this.msieImgFontBBoxFix = '';
                    232:     if (jsMath.browser == 'Mozilla') {
                    233:       jsMath.Box.IMG = jsMath.Box.IMG_mozilla;
                    234:     } else if (jsMath.browser == 'Opera')   {
                    235:       this.operaImageFonts = 1;
                    236:       jsMath.Box.IMG = jsMath.Box.IMG_opera;
                    237:     } else if (jsMath.browser == 'MSIE') {
1.2     ! albertel  238:       if (jsMath.platform == 'mac') {
1.1       albertel  239:         this.msieImgFontBBoxFix = '<span style="display:none">x</span>'
                    240:       } else {
                    241:         jsMath.Parser.prototype.oldTypeset = jsMath.Parser.prototype.Typeset;
                    242:         jsMath.Parser.prototype.Typeset = jsMath.Parser.prototype.msieTypeset;
                    243:         jsMath.Img.mustLoad = [];
                    244:         this.msieImageFonts = 1;
                    245:         jsMath.Controls.defaults.alpha = 0;
                    246:         if (!jsMath.Controls.userSet.alpha) {jsMath.Controls.cookie.alpha = 0}
                    247:         jsMath.Box.IMG = jsMath.Box.IMG_msie;
                    248:       }
                    249:     }
                    250:     jsMath.version += "-sp1.0";
                    251:   };
                    252: 
1.2     ! albertel  253: if (!jsMath.Setup) {jsMath.Setup = {}}
        !           254:   jsMath.Setup.Fonts = function () {
        !           255:     for (var i = 0; i < jsMath.TeX.fam.length; i++) {
        !           256:       var name = jsMath.TeX.fam[i];
        !           257:       if (name) {this.EncodeFont(name)}
        !           258:     }
        !           259:     jsMath.Img.Init();
        !           260:   };
1.1       albertel  261: 
                    262: if (!jsMath.Parser) {jsMath.Parser = {}}
                    263: if (!jsMath.Parser.prototype) {jsMath.Parser.prototype = {}}
                    264:   /*
                    265:    *  Handle loading of image files needed for this equation
                    266:    *  (avoids MSIE bug where it will request the image more
                    267:    *  than once if it is used more than once before it is
                    268:    *  loaded.)
                    269:    */
                    270:   jsMath.Parser.prototype.msieTypeset = function () {
                    271:     var HTML = this.oldTypeset();
                    272:     if (jsMath.Img.mustLoad.length > 0) {
                    273:       for (var i = 0; i < jsMath.Img.mustLoad.length; i++) {
                    274:         var IMG = jsMath.Img.URL(jsMath.Img.mustLoad[i][0],jsMath.Img.mustLoad[i][1]);
                    275:         jsMath.Script.WaitForImage(IMG);
                    276:         jsMath.Img[jsMath.Img.mustLoad[i][1]][jsMath.Img.mustLoad[i][0]].loaded = 1;
                    277:       }
                    278:       jsMath.Img.mustLoad = [];
                    279:       jsMath.Translate.restart = 1;
                    280:       throw "restart";
                    281:     }
                    282:     return HTML;
                    283:   };
                    284: 
                    285: /*
                    286:  *  Override the control panel calls in order to
                    287:  *  disable scaling in Opera.
                    288:  */
                    289: if (!jsMath.Controls) {jsMath.Controls = {}}
                    290:   /*
                    291:    *  Add Opera calls to loading of control panel
                    292:    */
                    293:   jsMath.Controls.Panel = function () {
                    294:     jsMath.Translate.Cancel();
                    295:     if (this.loaded) {
                    296:       this.Main();
                    297:     } else {
                    298:       jsMath.Script.delayedLoad(jsMath.root+"jsMath-controls.html");
                    299:       jsMath.Script.Push(this,"OperaInit");
                    300:     }
                    301:   };
                    302:   
                    303:   /*
                    304:    *  Disable hi-res fonts and image scaling in Opera
                    305:    */
                    306:   jsMath.Controls.OperaMain = function (init) {
                    307:     if (!init) {this.OldMain()}
                    308:     jsMath.Element("_resolution").disabled = true;
                    309:   };
                    310:   
                    311:   jsMath.Controls.OperaOptions = function () {
                    312:     this.OldOptions();
                    313:     jsMath.Element("_scaleImg").disabled = true;
                    314:     jsMath.Element("_scaleImgText").className = "disabled";
                    315:   };
                    316:   
                    317:   jsMath.Controls.OperaInit = function () {
                    318:     if (!jsMath.Browser.operaImageFonts) return;
                    319:     this.OldMain = this.Main; this.Main = this.OperaMain;
                    320:     this.OldOptions = this.Options; this.Options = this.OperaOptions;
                    321:     this.OperaMain(1);
                    322:   };

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>