MathJax icon indicating copy to clipboard operation
MathJax copied to clipboard

Automatic linebreak of inline math inside shrink-wrap elements

Open kwkbtr opened this issue 7 years ago • 6 comments

Minimal test case: https://jsbin.com/yapulamewo/2/edit?html,output

When automatic linebreak is turned on, an inline math inside a shrink-wrap element (e.g. table cell) is broken to multiple lines even if there is enough horizontal space. I suspect this is caused by #2006 since v2.7.4 does not have the problem.

kwkbtr avatar Nov 12 '18 03:11 kwkbtr

You are correct, the changes for 2006 are the source of the difference. As you can see from that discussion, due to recent changes in WebKit, the mechanism that MathJax used to use to determine the width of the math's container would cause unwanted line breaks at every in-line math expression, so the mechanism had to be changed.

Measuring the width is actually more complicated than one might expect. The main complications are shrink-wrapping elements (like the table cells in your example) and floating content that takes up room within the container on the left or right. The mechanism that MathJax used in 2.7.4 involved inserted a block-level element temporarily that would both expand shrink-wrap elements to their widest allowed size, but not wider than the available room within the container (taking flowing elements into account). Unfortunately, that temporary block-level element would cause a permanent line break in recent versions of WebKit (so in Safari and Chrome).

MathJax still uses this method for finding the size of the container for display math (since that will be on a separate line anyway), but no longer uses that for in-line math. I could not come up with a mechanism that handles both shrink-wrap and floating elements for in-line math. Because it is possible for the page author to handle shrink-wrap elements easier than floating content (see below), MathJax 2.7.5 now uses a method that handles the floating content properly at the expense of shrink-wrapped math.

There are several ways to approach the issue you are facing. One would be to apply a min-width CSS value to one of the cells in the affected column large enough to prevent the expression from breaking. Alternatively, if a shrink-wrapped element contains other text, that text will provide a minimum width, and (if wide enough), will prevent the expression from breaking. (So the issue usually only occurs when in-line math is alone in an otherwise empty cell.)

Another approach would be to use display math rather than in-line math in the table cell. One could use CSS like

td .MJXc-display {
    margin: 0
}

to remove the top and bottom spacing in this case.

Alternatively, one could include an empty display-math element in the table cell, and use a wrapper to hide its height. The block-level element used to measure the width for the display element would force the shrink-wrapper to expand and when the in-line element measures the width, it will be correct (rather than 0). Something like

<div style="height:0; font-size: 1px">\[\]</div>

should do the trick. (One could get fancy about it and use something like <mjx-noshrink></mjx-noshrink> for this, and write a MathJax preprocessor to replace these elements with the <div> above, and remove them after MathJax runs.)

Finally, if you are not using floating content, you could use

  <script type="text/x-mathjax-config">
    MathJax.Hub.Config({
      CommonHTML: {
        styles: {
           ".mjx-test.mjx-test-inline": {
              display: "inline-table!important",
              'margin-right': 0
          },
          ".mjx-test-inline .mjx-left-box": {
              display: "table-cell!important",
              width: "10000em!important",
              "min-width": 0, "max-width": "none",
              padding: 0, border: 0, margin: 0, float: null
          }
        }
      }
    });
  </script>

to convert the in-line measuring to one that does almost what the old measuring did, but with an in-line rather than a block element. (This doesn't work properly if there is floating content, but will handle shrink-wrap elements.)

dpvc avatar Nov 14 '18 15:11 dpvc

Hi @dpvc, is there some generic solution?

Here is my config:

<script type="text/javascript"
  src="https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.5/latest.js?config=TeX-AMS_HTML-full,Safe,https://DOMAIN/config.js">
</script>
MathJax.Hub.Config({
  TeX: {
    extensions: ["autobold.js"],
    equationNumbers: {
      autoNumber: "AMS"
    }
  },
  tex2jax: {
    inlineMath: [["$", "$"], ["\\(", "\\)"]],
    displayMath: [["$$", "$$"], ["\\[", "\\]"]],
    processEscapes: true,
    processRefs: true,
    processEnvironments: true
  },
  "HTML-CSS": {
    linebreaks: {
      automatic: true
    }
  }
});

MathJax.Ajax.loadComplete("https://DOMAIN/config.js");

ivankokan avatar Feb 28 '19 16:02 ivankokan

is there some generic solution?

As I said above, I was not able to find one that handles both shrink-wrapped elements (like table cells) and floating content. The current implementation favors floating elements (but fails for shrink-wrapping). I provided an alternative above that favors shrink-wrapping (but fails for floating content). You can take your pick, but I don't know of one that works for both simultaneously.

dpvc avatar Feb 28 '19 17:02 dpvc

is there some generic solution?

As I said above, I was not able to find one that handles both shrink-wrapped elements (like table cells) and floating content. The current implementation favors floating elements (but fails for shrink-wrapping). I provided an alternative above that favors shrink-wrapping (but fails for floating content). You can take your pick, but I don't know of one that works for both simultaneously.

Thanks! I will dig deeper and hopefully come up with something on this matter.

ivankokan avatar Mar 04 '19 13:03 ivankokan

The MathJax version 3.x is still missing linebreaking - is it due this bug?

mikkorantalainen avatar Mar 18 '21 14:03 mikkorantalainen

@mikkorantalainen:

is it due this bug?

No, it is due to the fact that line-breaking hasn't been ported to v3 yet, so there is no code in v3 to do line breaking yet. it is on the to-do list, but the font update that is currently underway come before that.

dpvc avatar Mar 18 '21 14:03 dpvc

Closed as part of a review of old issues.

dpvc avatar Aug 15 '25 19:08 dpvc