Fix mfenced so that when it contains a line break the delimiters and separators are not lost. Resolves issue #255 (but separators currently aren't able to be breakpoints, so more needs to be done).

This commit is contained in:
Davide P. Cervone 2012-08-29 23:28:20 -04:00
parent 037e5eb895
commit 34a9af5180
10 changed files with 197 additions and 34 deletions

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -12,5 +12,5 @@
* http://www.apache.org/licenses/LICENSE-2.0
*/
MathJax.OutputJax.SVG=MathJax.OutputJax({id:"SVG",version:"2.0.7",directory:MathJax.OutputJax.directory+"/SVG",extensionDir:MathJax.OutputJax.extensionDir+"/SVG",autoloadDir:MathJax.OutputJax.directory+"/SVG/autoload",fontDir:MathJax.OutputJax.directory+"/SVG/fonts",config:{scale:100,minScaleAdjust:50,font:"TeX",blacker:10,mtextFontInherit:false,undefinedFamily:"STIXGeneral,'Arial Unicode MS',serif",addMMLclasses:false,EqnChunk:(MathJax.Hub.Browser.isMobile?10:50),EqnChunkFactor:1.5,EqnChunkDelay:100,linebreaks:{automatic:false,width:"container"},styles:{".MathJax_SVG_Display":{"text-align":"center",margin:"1em 0em"},"#MathJax_SVG_Tooltip":{"background-color":"InfoBackground",color:"InfoText",border:"1px solid black","box-shadow":"2px 2px 5px #AAAAAA","-webkit-box-shadow":"2px 2px 5px #AAAAAA","-moz-box-shadow":"2px 2px 5px #AAAAAA","-khtml-box-shadow":"2px 2px 5px #AAAAAA",padding:"3px 4px"}}}});if(!MathJax.Hub.config.delayJaxRegistration){MathJax.OutputJax.SVG.Register("jax/mml")}MathJax.OutputJax.SVG.loadComplete("config.js");
MathJax.OutputJax.SVG=MathJax.OutputJax({id:"SVG",version:"2.0.8",directory:MathJax.OutputJax.directory+"/SVG",extensionDir:MathJax.OutputJax.extensionDir+"/SVG",autoloadDir:MathJax.OutputJax.directory+"/SVG/autoload",fontDir:MathJax.OutputJax.directory+"/SVG/fonts",config:{scale:100,minScaleAdjust:50,font:"TeX",blacker:10,mtextFontInherit:false,undefinedFamily:"STIXGeneral,'Arial Unicode MS',serif",addMMLclasses:false,EqnChunk:(MathJax.Hub.Browser.isMobile?10:50),EqnChunkFactor:1.5,EqnChunkDelay:100,linebreaks:{automatic:false,width:"container"},styles:{".MathJax_SVG_Display":{"text-align":"center",margin:"1em 0em"},"#MathJax_SVG_Tooltip":{"background-color":"InfoBackground",color:"InfoText",border:"1px solid black","box-shadow":"2px 2px 5px #AAAAAA","-webkit-box-shadow":"2px 2px 5px #AAAAAA","-moz-box-shadow":"2px 2px 5px #AAAAAA","-khtml-box-shadow":"2px 2px 5px #AAAAAA",padding:"3px 4px"}}}});if(!MathJax.Hub.config.delayJaxRegistration){MathJax.OutputJax.SVG.Register("jax/mml")}MathJax.OutputJax.SVG.loadComplete("config.js");

File diff suppressed because one or more lines are too long

View File

@ -22,7 +22,7 @@
*/
MathJax.Hub.Register.StartupHook("HTML-CSS Jax Ready",function () {
var VERSION = "2.0.2";
var VERSION = "2.0.3";
var MML = MathJax.ElementJax.mml,
HTMLCSS = MathJax.OutputJax["HTML-CSS"];
@ -146,10 +146,10 @@ MathJax.Hub.Register.StartupHook("HTML-CSS Jax Ready",function () {
// Get the current breakpoint position and other data
//
var index = info.index.slice(0), i = info.index.shift(),
m = this.data.length, W, scanW = info.W,
broken = (info.index.length > 0), better = false;
m = this.data.length, W, broken = (info.index.length > 0), better = false;
info.scanW = info.W;
if (i == null) {i = -1}; if (!broken) {i++; info.W += info.w};
info.w = 0; info.nest++; info.scanW = scanW;
info.w = 0; info.nest++;
//
// Look through the line for breakpoints,
// (as long as we are not too far past the breaking width)
@ -160,13 +160,7 @@ MathJax.Hub.Register.StartupHook("HTML-CSS Jax Ready",function () {
better = true; index = [i].concat(info.index); W = info.W;
if (info.penalty === PENALTY.newline) {info.index = index; info.nest--; return true}
}
if (!broken) {
var span = this.data[i].HTMLspanElement();
scanW += span.bbox.w;
if (span.style.paddingLeft) {scanW += HTMLCSS.unEm(span.style.paddingLeft)}
if (span.style.paddingRight) {scanW += HTMLCSS.unEm(span.style.paddingRight)}
info.W = info.scanW = scanW;
}
if (!broken) {this.HTMLaddWidth(i,info)}
}
info.index = []; i++; broken = false;
}
@ -174,6 +168,13 @@ MathJax.Hub.Register.StartupHook("HTML-CSS Jax Ready",function () {
if (better) {info.W = W}
return better;
},
HTMLaddWidth: function (i,info) {
var span = this.data[i].HTMLspanElement();
info.scanW += span.bbox.w;
if (span.style.paddingLeft) {info.scanW += HTMLCSS.unEm(span.style.paddingLeft)}
if (span.style.paddingRight) {info.scanW += HTMLCSS.unEm(span.style.paddingRight)}
info.W = info.scanW;
},
/****************************************************************/
//
@ -262,7 +263,7 @@ MathJax.Hub.Register.StartupHook("HTML-CSS Jax Ready",function () {
} else {
//
// Otherwise, move the remainder of the initial item
// and any others up tp the last one
// and any others up to the last one
//
var last = state.last; state.last = false;
while (i < j) {
@ -366,7 +367,84 @@ MathJax.Hub.Register.StartupHook("HTML-CSS Jax Ready",function () {
} else if (state.first) {state.nextIsFirst = true} else {delete state.nextIsFirst}
}
});
/**************************************************************************/
MML.mfenced.Augment({
HTMLbetterBreak: function (info,state) {
//
// Get the current breakpoint position and other data
//
var index = info.index.slice(0), i = info.index.shift(),
m = this.data.length, W, broken = (info.index.length > 0), better = false;
info.scanW = info.W;
if (i == null) {i = -1}; if (!broken) {i++; info.W += info.w};
info.w = 0; info.nest++;
//
// Look through the line for breakpoints, including the open, close, and separators
// (as long as we are not too far past the breaking width)
//
if (!broken && this.data.open) {this.HTMLaddWidth("open",info)}
while (i < m && info.scanW < 1.33*HTMLCSS.linebreakWidth) {
if (this.data[i]) {
if (this.data[i].HTMLbetterBreak(info,state)) {
better = true; index = [i].concat(info.index); W = info.W;
if (info.penalty === PENALTY.newline) {info.index = index; info.nest--; return true}
}
if (!broken) {this.HTMLaddWidth(i,info)}
}
info.index = []; i++; broken = false;
// FIXME: should be able to break at the following (but don't have index for it)
if (this.data["sep"+i]) {this.HTMLaddWidth("sep"+i,info)}
}
if (this.data.close) {this.HTMLaddWidth("close",info)}
info.nest--; info.index = index;
if (better) {info.W = W}
return better;
},
HTMLmoveLine: function (start,end,span,state,values) {
var i = start[0], j = end[0];
if (i == null) {i = -1}; if (j == null) {j = this.data.length-1}
if (i === j && start.length > 1) {
//
// If starting and ending in the same element move the subpiece to the new line
// Add the closing fence, if present
//
this.data[i].HTMLmoveSlice(start.slice(1),end.slice(1),span,state,values,"paddingLeft");
if (i === this.data.length-1 && this.data.close)
{this.data.close.HTMLmoveSpan(span,state,values)}
} else {
//
// Otherwise, move the remainder of the initial item
// and any others (including open and separators) up to the last one
//
var last = state.last; state.last = false;
if (i < 0 && this.data.open) {this.data.open.HTMLmoveSpan(span,state,values)}
while (i < j) {
if (this.data[i]) {
if (start.length <= 1) {this.data[i].HTMLmoveSpan(span,state,values)}
else {this.data[i].HTMLmoveSlice(start.slice(1),[],span,state,values,"paddingLeft")}
}
i++; state.first = false; start = [];
if (this.data["sep"+i]) {this.data["sep"+i].HTMLmoveSpan(span,state,values)}
}
//
// If the last item is complete, move it and the closing fence,
// otherwise move the first part of it up to the split
//
state.last = last;
if (this.data[i]) {
if (end.length <= 1) {
this.data[i].HTMLmoveSpan(span,state,values);
if (this.data.close) {this.data.close.HTMLmoveSpan(span,state,values)}
} else {this.data[i].HTMLmoveSlice([],end.slice(1),span,state,values,"paddingRight")}
}
}
}
});
/**************************************************************************/
MML.mo.Augment({

View File

@ -22,7 +22,7 @@
*/
MathJax.Hub.Register.StartupHook("SVG Jax Ready",function () {
var VERSION = "2.0.1";
var VERSION = "2.0.2";
var MML = MathJax.ElementJax.mml,
SVG = MathJax.OutputJax.SVG,
BBOX = SVG.BBOX;
@ -149,10 +149,10 @@ MathJax.Hub.Register.StartupHook("SVG Jax Ready",function () {
// Get the current breakpoint position and other data
//
var index = info.index.slice(0), i = info.index.shift(),
m = this.data.length, W, scanW = info.W,
broken = (info.index.length > 0), better = false;
m = this.data.length, W, broken = (info.index.length > 0), better = false;
info.scanW = info.W;
if (i == null) {i = -1}; if (!broken) {i++; info.W += info.w};
info.w = 0; info.nest++; info.scanW = scanW;
info.w = 0; info.nest++;
//
// Look through the line for breakpoints,
// (as long as we are not too far past the breaking width)
@ -163,11 +163,7 @@ MathJax.Hub.Register.StartupHook("SVG Jax Ready",function () {
better = true; index = [i].concat(info.index); W = info.W;
if (info.penalty === PENALTY.newline) {info.index = index; info.nest--; return true}
}
if (!broken) {
var svg = this.data[i].SVGdata;
scanW += svg.w + svg.x; if (svg.X) {scanW += svg.X}
info.W = info.scanW = scanW;
}
if (!broken) {this.SVGaddWidth(i,info)}
}
info.index = []; i++; broken = false;
}
@ -175,6 +171,11 @@ MathJax.Hub.Register.StartupHook("SVG Jax Ready",function () {
if (better) {info.W = W}
return better;
},
SVGaddWidth: function (i,info) {
var svg = this.data[i].SVGdata;
info.scanW += svg.w + svg.x; if (svg.X) {info.scanW += svg.X}
info.W = info.scanW;
},
/****************************************************************/
//
@ -303,8 +304,8 @@ MathJax.Hub.Register.StartupHook("SVG Jax Ready",function () {
/****************************************************************/
//
// Move an element from its original span to its new location in
// a split element or the new line's span
// Move an element from its original position to its new location in
// a split element or the new line's position
//
SVGmove: function (line,state,values) {
// FIXME: handle linebreakstyle === "duplicate"
@ -327,6 +328,82 @@ MathJax.Hub.Register.StartupHook("SVG Jax Ready",function () {
/**************************************************************************/
MML.mfenced.Augment({
SVGbetterBreak: function (info,state) {
//
// Get the current breakpoint position and other data
//
var index = info.index.slice(0), i = info.index.shift(),
m = this.data.length, W, broken = (info.index.length > 0), better = false;
info.scanW = info.W;
if (i == null) {i = -1}; if (!broken) {i++; info.W += info.w};
info.w = 0; info.nest++;
//
// Look through the line for breakpoints, including the open, close, and separators
// (as long as we are not too far past the breaking width)
//
if (!broken && this.data.open) {this.SVGaddWidth("open",info)}
while (i < m && info.scanW < 1.33*SVG.linebreakWidth) {
if (this.data[i]) {
if (this.data[i].SVGbetterBreak(info,state)) {
better = true; index = [i].concat(info.index); W = info.W;
if (info.penalty === PENALTY.newline) {info.index = index; info.nest--; return true}
}
if (!broken) {this.SVGaddWidth(i,info)}
}
info.index = []; i++; broken = false;
// FIXME: should be able to break at the following (but don't have index for it)
if (this.data["sep"+i]) {this.SVGaddWidth("sep"+i,info)}
}
if (this.data.close) {this.SVGaddWidth("close",info)}
info.nest--; info.index = index;
if (better) {info.W = W}
return better;
},
SVGmoveLine: function (start,end,svg,state,values) {
var i = start[0], j = end[0];
if (i == null) {i = -1}; if (j == null) {j = this.data.length-1}
if (i === j && start.length > 1) {
//
// If starting and ending in the same element move the subpiece to the new line
// Add the closing fence, if present
//
this.data[i].SVGmoveSlice(start.slice(1),end.slice(1),svg,state,values,"paddingLeft");
if (i === this.data.length-1 && this.data.close) {this.data.close.SVGmove(svg,state,values)}
} else {
//
// Otherwise, move the remainder of the initial item
// and any others (including open and separators) up to the last one
//
var last = state.last; state.last = false;
if (i < 0 && this.data.open) {this.data.open.SVGmove(svg,state,values)}
while (i < j) {
if (this.data[i]) {
if (start.length <= 1) {this.data[i].SVGmove(svg,state,values)}
else {this.data[i].SVGmoveSlice(start.slice(1),[],svg,state,values,"paddingLeft")}
}
i++; state.first = false; start = [];
if (this.data["sep"+i]) {this.data["sep"+i].SVGmove(svg,state,values)}
}
//
// If the last item is complete, move it and the closing fence,
// otherwise move the first part of it up to the split
//
state.last = last;
if (this.data[i]) {
if (end.length <= 1) {
this.data[i].SVGmove(svg,state,values);
if (this.data.close) {this.data.close.SVGmove(svg,state,values)}
} else {this.data[i].SVGmoveSlice([],end.slice(1),svg,state,values,"paddingRight")}
}
}
}
});
/**************************************************************************/
MML.mo.Augment({
//
// Override the method for checking line breaks to properly handle <mo>

View File

@ -24,7 +24,7 @@
MathJax.OutputJax.SVG = MathJax.OutputJax({
id: "SVG",
version: "2.0.7",
version: "2.0.8",
directory: MathJax.OutputJax.directory + "/SVG",
extensionDir: MathJax.OutputJax.extensionDir + "/SVG",
autoloadDir: MathJax.OutputJax.directory + "/SVG/autoload",

View File

@ -837,8 +837,11 @@
Stretch: function () {
for (var i = 0, m = this.svg.length; i < m; i++)
{
var svg = this.svg[i];
if (svg.mml) {svg = svg.mml.SVGstretchV(this.sh,this.sd)}
var svg = this.svg[i], mml = svg.mml;
if (mml) {
svg = mml.SVGstretchV(this.sh,this.sd);
mml.SVGdata.HW = this.sh; mml.SVGdata.D = this.sd;
}
if (svg.ic) {this.ic = svg.ic} else {delete this.ic}
this.Add(svg,this.w,0,true);
}
@ -1243,11 +1246,16 @@
});
MML.mo.Augment({
toSVG: function () {
toSVG: function (HW,D) {
this.SVGgetStyles();
var svg = this.svg = this.SVG(); this.SVGhandleSpace(svg);
if (this.data.length == 0) {svg.Clean(); this.SVGsaveData(svg); return svg}
//
// Stretch the operator, if that is requested
//
if (D != null) {return this.SVGstretchV(HW,D)}
else if (HW != null) {return this.SVG.strechH(HW)}
//
// Get the variant, and check for operator size
//
var scale = this.SVGgetScale(), variant = this.SVGgetVariant();