-
-
Notifications
You must be signed in to change notification settings - Fork 1.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Performance problem with custom elements when there are many equations #2263
Comments
Because Javascript is single threaded, user interaction can't occur if Javascript is running. MathJax v2 would voluntarily give up the CPU temporarily during its typesetting so that screen updates and user interaction could occur. Your code above doesn't do that, and so all the expressions must be typeset before the screen updates or user interaction occurs. One possible work-around is to use
instead of
in the There is a trade-off with this approach, which is that screen updates take time, and so refreshing the window in between each equation will mean that it will take longer to get all the equations rendered this way, but the browser will respond to interaction, and you will see the initial equations earlier. MathJax v2 would typeset more than one equation at at time before allowing a screen update, which tried to balance responsiveness with update speed. It would take some additional work to make this approach typeset several before updating. |
Thanks so much Davide, I will give your suggestion a try. |
Your work-around gives a much better user experience. (Hooray!) I'll test a bit more when I get home next week & then close this issue. |
I did a little more testing of the code, and it doesn't seem to work in Safari or Chrome. This is due to the fact that the content doesn't seem to be available during the I did some exploring, and it looks like MutationObservers are the only way to handle accessing the contents in a cross-browser way. This also has the side advantage of handling changes to the contents after the element has been added to the page (though you don't use that yourself). While reading about custom elements, it looks like the recommendation is to set up the shadow DOM in the constructor rather than the Here is the updated math-text.js:
I also made a few changes to the MathJax configuration. The first is to use Here is the modified custom-element-config.js file:
There are some issues you may want to consider. First, there is no guarantee that the expressions will be typeset in the order in which they appear on the page, and that can have consequences on the results. For example, if one expression includes a macro definition that is used later, the order of evaluation is important. If you were to use automatic equation numbering (e.g., AMS equation numbers), then the order is important in order to have the numbering be sequential. Even without automatic numbering, there may be problems with Personally, I'm not sure what using the shadow DOM for this really buys you. It is an interesting experiment, and I'm glad that MathJax v3 can be made to handle it, but there are a number of problems that make me wonder if it is worth using it. |
Hi Davide, thanks for all the work on this -- and sorry for the late reply. I've been out of touch electronically, which I must say has given me great peace for an extended period! I'm really anxious to try out the new code, which I'll do tomorrow. Re the shadow DOM, I do need to use custom elements because of the way Elm code interacts with the browser. Is there a way of using them without the shadow DOM? I've made two optimizations/hacks which help quite a bit. The first I believe I already mentioned -- render the first page or two of the text while the user is reacting to it so that he has the illusion that all is very fast. The second is that I use the timeout > 0 only when loading the doc or when completely re-rendering it at the user's request. During editing, re-rendering is very fast because I diff the new text against the old and only have to-parse-render a tiny bit of the document. The MathJax 3 rendering is really good here because there is no "jittering" of the output as it is re-rendered. Re labels and refs, I handle these myself, so the out-of order rendering is not a problem as far as visual display is concerned. I did not try to make my handrolled \eqrefs clickable-followable now that you mention this — and so the question is: can I? Maybe so, using the fact that I can make the renderer enclose the math-text element in a div with the correct target for the link. I will give it a try. This is how text-mode links work in MiniLaTeX. One question — maybe this is related to the out of order problem. Before I could insert macros between double dollar signs and they would be used throughout the document. Is there a way around this? I really appreciate your help on all of this. PS. Did you find a good reference for custom elements? I need to improve my understanding of them. |
I haven't been able to make the new custom element code work. When I inspect the rendered text in the browser, the math elements have no content. I think that this is related to capturing the input to the custom element -- see for example custom element code . In this file I have commented out the old version. The new version is below the old. In the old version there is the paragraph
If this paragraph is deleted, using the old code, the DOM node for the custom element is empty of content. For a working instance of the old code, see text editor demo. Click on the L1 button at the bottom to get an example with lots of math. For an instance with the new code, do the same with this link: text editor demo-x |
re my question above about math-mode macros – I've found a way around this that works quite well, so it is no longer an issue. (The parser reads the macro definitions and applies the substitutions they define to math elements before passing them off to MathJax). |
I've played around a little more with the math-text custom element code, putting |
Here is a link to a fairly simple app using the old math-text custom elements and with And here is the buggy version, where https://jxxcarlson.github.io/app/bug.demo.minilatex.io/index.html |
Create a worker may be a good idea to reduce the computed in render @dpvc |
Thanks! will think about that. |
Hi -- I've been using the custom element code you provided (Thanks!!!) (see attached at bottom). It works very well when there are not too many math elements, but I run into problems with more complex pages. There is a significant delay -- several seconds -- in rendering such pages. That is, the page does not display until all the rendering is complete.
Here is an example from https://math-markdown.netlify.com, the latest iteration of my Elm + MathJax app:
Example
I've tried to get around this by parsing and rendering the first 4000 characters of the document, then rendering the whole document, so that the user has the illusion of snappiness. However, this is not a great solution, as you will see in the example.
For another view of the problem, go to QFT Notes and click back and forth between the sections
listed in the left-hand table of contents.
Is there a way to improve the performance of the custom elements? I don't know enough about how they work, but here are some possibilities:
All the elements have to complete their rendering before the page displays. If that is the case, maybe a placeholder could be displayed until the actual text is rendered.
Perhaps there is a large amount of set up work that each element has to perform. If so, is there a way that this could be done once, so that all elements could benefit?
NOTE. These performance problems are largely absent during editing because only logical paragraphs that have changed need to be reparsed and rerendered. Moreover -- and this is a huge win -- the jittering that was present during editing with MathJax 2.7 is gone. Bravo!
Two pieces of code attached:
1. custom-element-config.js
2. math-text.js
The text was updated successfully, but these errors were encountered: