[HOME] jsMath (Authors) [Prev][Up][Skip][Next]

Overriding jsMath Functions with Your Own Versions

Advanced authors may find it desirable to modify the way that jsMath operates and feel the need to adjust some of the functions that are part of the jsMath package. It is important, however, not to modify the jsMath.js file itself; jsMath provides other means for managing its functions and default values. While it may seem easier to just edit the code directly, in the long run this will make it more difficult for you to upgrade jsMath in the future. The procedure described below will allow you to keep your modifications separate from the original jsMath code, which will make it much easier for you to check the changes you have made when you install a new version of jsMath.

Changing jsMath before it is loaded

All the values and code for jsMath are collected in an object stored in a global variable jsMath. When jsMath.js is first loaded, it looks to see if there is already a variable called jsMath, and if so, it uses the values stored there to override the standard values from jsMath.js. This is why the customization examples suggest setting the jsMath variable.

The jsMath variable contains not just values (e.g., the default style definitions), but also all the code used by jsMath, so you can override functions as easily as you can values. Some functions have been designed to be overridden by the author (e.g., the one that creates the font warning messages), but most have not, so be careful about replacing them; you can cause jsMath to fail quite easily by replacing the wrong thing.

After jsMath has set up its own version of the jsMath variable, it copies any values from your version of jsMath into its own, thereby replacing the defaults with your modifications. It is also possible to add new functions or values to jsMath in this way (some of the plugins do this, for example).

Some of the routines and data stored in jsMath are collected into sub-objects within the jsMath object. For example, all the setup code is in the jsMath.Setup object. You could override one of these values by setting

    jsMath = {Setup: {name: value}}
where name is the item to be overridden, and value is its new value. The way this works is that jsMath will replace the items in jsMath with your values unless the value is an object, in which case it will merge the contents of your object into the existing one (not replace it). So in the example above, Setup will not be replaced by an object with only one entry; instead, that entry will be added to the default Setup object. This merging is done recursively, so you can insert entries into objects at any level of the jsMath hierarchy.

You will, of course, need to look through the jsMath.js file in order to see what routines or data you want to replace; however, this file is compressed so that it can be downloaded faster, so you will need to look at the copy in the uncompressed folder instead.

If you are using easy/load.js, you can include changes to the jsMath variable there as well. In fact, the options set in that file are stored in jsMath.Easy, and you could modify other settings in a similar way.

Changing jsMath after it is loaded

The process described above allows you to modify jsMath by defining values before you load the jsMath.js file. You can also modify jsMath after loading jsMath.js by simply setting the values in the jsMath variable directly. For example, you could replace the jsMath.Process() function by setting
    jsMath.Process = function () {your code here}
after loading jsMath.js. (You might want to save the old function first, for example jsMath.OldProcess = jsMath.Process, so you can call the original from your new version.) Note, however, that after jsMath.js has been loaded, some processing has already been done, so your changes might be made too late to have their intended effect. For example, the font warning message will have been created already, so setting jsMath.Font.Message after loading jsMath.js will not have the desired effect.

Changes made to jsMath after loading jsMath.js are best used for additions to jsMath; overriding the values in jsMath is best handled by setting jsMath before loading jsMath.js.

As of version 3.0, there may be synchronization issues that you need to be aware of when you make modifications to jsMath after it is loaded. For example, even when a SCRIPT follows the one that loads jsMath.js, it may be that jsMath is not yet fully loaded and set up (e.g., a fallback file could be loading asynchronously). So if you plan to modify jsMath after loading it, you should be sure to use jsMath.Synchronize() to make sure that your modifications coordinate with the jsMath event queue properly. The same applies to calling any jsMath function other than the ones specifically designed to be called by the user (such as jsMath.Process(), jsMath.ConcertTeX(), jsMath.Setup.Script() and jsMath.Setup.Styles()). See the documentation on synchronizing with jsMath for more details.

Inserting your code into the initialization sequence

The initialization sequence for jsMath is rather complex, and involves a number of checks (to see what fonts are available, for example), and may include loading of browser-specific code, or fallback support code. The initialization inserts some HTML into the document (e.g., the floating jsMath button) and sets up the styles needed for jsMath.

There are three main phases of initialization: setting up the jsMath variable (which contains all the data and code used by jsMath, and can be done in either the HEAD or the BODY of the document), initializing the BODY elements needed by jsMath (which must be done after the BODY is available), and checking for the TeX fonts and loading the fallback method if necessary (which must be performed after the other initialization is complete).

The first of these is done by loading the jsMath.js file, and the second and third are performed by jsMath.Setup.Body(). When jsMath.js is loaded in the BODY of the document, jsMath.Setup.Body() is called automatically, but when it is loaded in the HEAD, this is put off until the first call to jsMath.Process() or jsMath.ProcessBeforeShowing(). If you need to do processing between loading jsMath and the body setup function, be sure to load jsMath.js in the document HEAD, and then do your processing, and finally make a call to jsMath.Setup.Body() yourself (or let jsMath.Process() take care of it). This allows you to insert processing between the first two phases of initialization.

It is possible to insert your own code between the second and third phases as well, even though they are part of the same routine, by overriding the definition of jsMath.Setup.UserEvent object. This object holds functions that are called at particular times in the initialization process. The jsMath.Setup.UserEvent["pre-font"] function is called after the BODY has been set up but before the font check is performed, and is initially empty (i.e., it does nothing). When this routine is called, the jsMath.BBoxFor() routine (but not jsMath.EmBoxFor()) is be available, the user's browser has been determined and any browser-specific code has been loaded, the cookie values have been read, and the styles have been set.

If you need to run code after the browser-specific code has been loaded but before the font check, you can use

    jsMath = {Setup: {UserEvent: {
      "pre-font": function () {
to accomplish this.

Three is also a user event called onload that is called after jsMath.js has loaded and finished running. So if you need to do some processing after you are sure jsMath.js is loaded and ready to go, you can use

    jsMath = {Setup: {UserEvent: {
      onload: function () {
to perform your code.

Additional user events may be defined in future releases of jsMath.

Get jsMath at SourceForge.net. Fast, secure and Free Open Source software downloads [HOME] jsMath web pages
Created: 02 Aug 2005
Last modified: 13 Sep 2008 10:47:38
Comments to: dpvc@union.edu
[Next] Synchronizing with jsMath
[Skip] Browser Support for jsMath
[Up] Information for jsMath Authors
[Prev] Adding jsMath to a BLOG or Bulletin-Board System