From 7b85cd06962c184f74f5ca54328739df26d6d832 Mon Sep 17 00:00:00 2001 From: FAJ-Munich <60485740+FAJ-Munich@users.noreply.github.com> Date: Thu, 28 Mar 2024 17:40:48 +0100 Subject: [PATCH] JavaScript backbone for GABC chant display Enabling #1375 (GABC files are not retrieved from GregoBase though) --- web/cgi-bin/horas/horasjs.pl | 305 +- web/cgi-bin/horas/js/exsurge.js | 8928 +++++++++++++++++++++++++++ web/cgi-bin/horas/js/exsurge.min.js | 8 + web/cgi-bin/horas/js/jquery.min.js | 4 + web/cgi-bin/horas/js/util.js | 1758 ++++++ web/cgi-bin/horas/officium_html.pl | 2 + web/cgi-bin/horas/webdia.pl | 110 +- 7 files changed, 10970 insertions(+), 145 deletions(-) create mode 100644 web/cgi-bin/horas/js/exsurge.js create mode 100644 web/cgi-bin/horas/js/exsurge.min.js create mode 100644 web/cgi-bin/horas/js/jquery.min.js create mode 100644 web/cgi-bin/horas/js/util.js diff --git a/web/cgi-bin/horas/horasjs.pl b/web/cgi-bin/horas/horasjs.pl index 4c7f6790888..8df4a4573e5 100644 --- a/web/cgi-bin/horas/horasjs.pl +++ b/web/cgi-bin/horas/horasjs.pl @@ -1,7 +1,6 @@ #*** Javascript functions # the sub is called from htmlhead sub horasjs { - my($output); # $caller in principle might not be defined. my $caller_flag = $caller || 0; @@ -16,70 +15,70 @@ sub horasjs { var day = d.getDate(); document.forms[0].browsertime.value = (d.getMonth() + 1) + "-" + day + "-" + d.getFullYear(); if (!"$date1") { - var a = (day > $day) ? "-+" : (day < $day) ? "--" : ""; - document.forms[0].date.value = document.forms[0].browsertime.value + a; - if (a) document.forms[0].submit(); - } - } - var i = 1; - while (i <= $searchvalue) { + var a = (day > $day) ? "-+" : (day < $day) ? "--" : ""; + document.forms[0].date.value = document.forms[0].browsertime.value + a; + if (a) document.forms[0].submit(); + } + } + var i = 1; + while (i <= $searchvalue) { a = document.getElementById('L' + i); i++; if (a) a.scrollIntoView(); - } -} - -//call a setup table -function pset(p) { - var pc = document.createElement("input"); - pc.setAttribute("type", "hidden"); - pc.setAttribute("name", "pcommand"); - pc.setAttribute("value", "pray" + document.forms[0].command.value); - document.forms[0].appendChild(pc); - document.forms[0].command.value = "setup" + p; - document.forms[0].submit(); -} - -//call an individual hora -function hset(p, d) { - clearradio(); - - if (p != 'Laudes' && d) { + } + } + + //call a setup table + function pset(p) { + var pc = document.createElement("input"); + pc.setAttribute("type", "hidden"); + pc.setAttribute("name", "pcommand"); + pc.setAttribute("value", "pray" + document.forms[0].command.value); + document.forms[0].appendChild(pc); + document.forms[0].command.value = "setup" + p; + document.forms[0].submit(); + } + + //call an individual hora + function hset(p, d) { + clearradio(); + + if (p != 'Laudes' && d) { document.forms[0].date.value = d; document.forms[0].caller.value = 1; - } - if ($caller_flag) {document.forms[0].caller.value = 1;} - document.forms[0].command.value = "pray" + p; - document.forms[0].action = "$officium"; - document.forms[0].target = "_self" - document.forms[0].submit(); -} - -// call appendix -function appendix(a) { - document.forms[0].command.value = "Appendix " + a; - console.log(document.forms[0].command.value); - document.forms[0].submit(); -} - -// Jump straight to an hour of the Office for the Dead. -function defunctorum(hour) { - clearradio(); - - document.forms[0].caller.value = 1; - document.forms[0].votive.value = "C9"; - document.forms[0].command.value = "pray" + hour; - document.forms[0].action = "$officium"; - document.forms[0].target = "_self" - document.forms[0].submit(); -} - -//calls compare -function callcompare() { - document.forms[0].action = "Cofficium.pl"; - document.forms[0].target = "_self" - document.forms[0].submit(); -} + } + if ($caller_flag) {document.forms[0].caller.value = 1;} + document.forms[0].command.value = "pray" + p; + document.forms[0].action = "$officium"; + document.forms[0].target = "_self" + document.forms[0].submit(); + } + + // call appendix + function appendix(a) { + document.forms[0].command.value = "Appendix " + a; + console.log(document.forms[0].command.value); + document.forms[0].submit(); + } + + // Jump straight to an hour of the Office for the Dead. + function defunctorum(hour) { + clearradio(); + + document.forms[0].caller.value = 1; + document.forms[0].votive.value = "C9"; + document.forms[0].command.value = "pray" + hour; + document.forms[0].action = "$officium"; + document.forms[0].target = "_self" + document.forms[0].submit(); + } + + //calls compare + function callcompare() { + document.forms[0].action = "Cofficium.pl"; + document.forms[0].target = "_self" + document.forms[0].submit(); + } PrintTag } $output .= << "PrintTag"; @@ -90,64 +89,64 @@ sub horasjs { document.forms[0].action = "$officium"; document.forms[0].target = "_self" return; -} - -// set a popup tab -function linkit(name,ind,lang) { + } + + // set a popup tab + function linkit(name,ind,lang) { document.forms[0].popup.value = name; document.forms[0].popuplang.value=lang; document.forms[0].expandnum.value=ind; if (ind == 0) { - document.forms[0].action = 'popup.pl'; - document.forms[0].target = '_BLANK'; - } else { - var c = document.forms[0].command.value; - if (!c.match('pray')) document.forms[0].command.value = "pray" + c; - } + document.forms[0].action = 'popup.pl'; + document.forms[0].target = '_BLANK'; + } else { + var c = document.forms[0].command.value; + if (!c.match('pray')) document.forms[0].command.value = "pray" + c; + } document.forms[0].submit(); -} - -//finishing horas back to main page -function okbutton() { + } + + //finishing horas back to main page + function okbutton() { document.forms[0].action = "$officium"; document.forms[0].target = "_self" document.forms[0].command.value = ''; document.forms[0].submit(); -} - -//restart the programlet if parameter change -function parchange() { - var c = document.forms[0].command.value; - if (c && !c.match("change")) { - clearradio(); - } - if (c && !c.match("pray")) document.forms[0].command.value = "pray" + c; - document.forms[0].submit(); -} - -//calls kalendar -function callkalendar() { - document.forms[0].action = 'kalendar.pl'; - document.forms[0].target = "_self" - document.forms[0].submit(); -} - -// for Cofficium -function callbrevi(date) { - document.forms[0].date.value = date; - document.forms[0].action = 'officium.pl' - document.forms[0].target = "_self" - document.forms[0].submit(); -} - -//calls missa -function callmissa() { - document.forms[0].action = "../missa/missa.pl"; - document.forms[0].target = "_self" - document.forms[0].submit(); -} - -function prevnext(ch) { + } + + //restart the programlet if parameter change + function parchange() { + var c = document.forms[0].command.value; + if (c && !c.match("change")) { + clearradio(); + } + if (c && !c.match("pray")) document.forms[0].command.value = "pray" + c; + document.forms[0].submit(); + } + + //calls kalendar + function callkalendar() { + document.forms[0].action = 'kalendar.pl'; + document.forms[0].target = "_self" + document.forms[0].submit(); + } + + // for Cofficium + function callbrevi(date) { + document.forms[0].date.value = date; + document.forms[0].action = 'officium.pl' + document.forms[0].target = "_self" + document.forms[0].submit(); + } + + //calls missa + function callmissa() { + document.forms[0].action = "../missa/missa.pl"; + document.forms[0].target = "_self" + document.forms[0].submit(); + } + + function prevnext(ch) { var dat = document.forms[0].date.value; var adat = dat.split('-'); var mtab = new Array(31,28,31,30,31,30,31,31,30,31,30,31); @@ -155,7 +154,7 @@ sub horasjs { var d = eval(adat[1]); var y = eval(adat[2]); var c = eval(ch); - + var leapyear = 0; if ((y % 4) == 0) leapyear = 1; if ((y % 100) == 0) leapyear = 0; @@ -163,15 +162,15 @@ sub horasjs { if (leapyear) mtab[1] = 29; d = d + c; if (d < 1) { - m--; - if (m < 1) {y--; m = 12;} - d = mtab[m-1]; - } + m--; + if (m < 1) {y--; m = 12;} + d = mtab[m-1]; + } if (d > mtab[m-1]) { - m++; - d = 1; - if (m > 12) {y++; m = 1;} - } + m++; + d = 1; + if (m > 12) {y++; m = 1;} + } document.forms[0].date.value = m + "-" + d + "-" + y; } PrintTag @@ -179,4 +178,74 @@ sub horasjs { $output } +#to convert gabc into chant svg +sub horasjsend { + + print "\n +PrintTag +} + 1; diff --git a/web/cgi-bin/horas/js/exsurge.js b/web/cgi-bin/horas/js/exsurge.js new file mode 100644 index 00000000000..9007a2aa940 --- /dev/null +++ b/web/cgi-bin/horas/js/exsurge.js @@ -0,0 +1,8928 @@ +(function webpackUniversalModuleDefinition(root, factory) { + if(typeof exports === 'object' && typeof module === 'object') + module.exports = factory(); + else if(typeof define === 'function' && define.amd) + define("exsurge", [], factory); + else if(typeof exports === 'object') + exports["exsurge"] = factory(); + else + root["exsurge"] = factory(); +})(this, function() { +return /******/ (function(modules) { // webpackBootstrap +/******/ // The module cache +/******/ var installedModules = {}; +/******/ +/******/ // The require function +/******/ function __webpack_require__(moduleId) { +/******/ +/******/ // Check if module is in cache +/******/ if(installedModules[moduleId]) +/******/ return installedModules[moduleId].exports; +/******/ +/******/ // Create a new module (and put it into the cache) +/******/ var module = installedModules[moduleId] = { +/******/ exports: {}, +/******/ id: moduleId, +/******/ loaded: false +/******/ }; +/******/ +/******/ // Execute the module function +/******/ modules[moduleId].call(module.exports, module, module.exports, __webpack_require__); +/******/ +/******/ // Flag the module as loaded +/******/ module.loaded = true; +/******/ +/******/ // Return the exports of the module +/******/ return module.exports; +/******/ } +/******/ +/******/ +/******/ // expose the modules object (__webpack_modules__) +/******/ __webpack_require__.m = modules; +/******/ +/******/ // expose the module cache +/******/ __webpack_require__.c = installedModules; +/******/ +/******/ // __webpack_public_path__ +/******/ __webpack_require__.p = ""; +/******/ +/******/ // Load entry module and return exports +/******/ return __webpack_require__(0); +/******/ }) +/************************************************************************/ +/******/ ([ +/* 0 */ +/***/ function(module, exports, __webpack_require__) { + + // + // Author(s): + // Fr. Matthew Spencer, OSJ + // + // Copyright (c) 2008-2016 Fr. Matthew Spencer, OSJ + // + // Permission is hereby granted, free of charge, to any person obtaining a copy + // of this software and associated documentation files (the "Software"), to deal + // in the Software without restriction, including without limitation the rights + // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + // copies of the Software, and to permit persons to whom the Software is + // furnished to do so, subject to the following conditions: + // + // The above copyright notice and this permission notice shall be included in + // all copies or substantial portions of the Software. + // + // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + // THE SOFTWARE. + // + + 'use strict'; + + Object.defineProperty(exports, "__esModule", { + value: true + }); + + var _Exsurge = __webpack_require__(1); + + Object.keys(_Exsurge).forEach(function (key) { + if (key === "default") return; + Object.defineProperty(exports, key, { + enumerable: true, + get: function get() { + return _Exsurge[key]; + } + }); + }); + + var _Exsurge2 = __webpack_require__(2); + + Object.keys(_Exsurge2).forEach(function (key) { + if (key === "default") return; + Object.defineProperty(exports, key, { + enumerable: true, + get: function get() { + return _Exsurge2[key]; + } + }); + }); + + var _Exsurge3 = __webpack_require__(3); + + Object.keys(_Exsurge3).forEach(function (key) { + if (key === "default") return; + Object.defineProperty(exports, key, { + enumerable: true, + get: function get() { + return _Exsurge3[key]; + } + }); + }); + + var _Exsurge4 = __webpack_require__(4); + + Object.keys(_Exsurge4).forEach(function (key) { + if (key === "default") return; + Object.defineProperty(exports, key, { + enumerable: true, + get: function get() { + return _Exsurge4[key]; + } + }); + }); + + var _Exsurge5 = __webpack_require__(6); + + Object.keys(_Exsurge5).forEach(function (key) { + if (key === "default") return; + Object.defineProperty(exports, key, { + enumerable: true, + get: function get() { + return _Exsurge5[key]; + } + }); + }); + + var _ExsurgeChant = __webpack_require__(9); + + Object.keys(_ExsurgeChant).forEach(function (key) { + if (key === "default") return; + Object.defineProperty(exports, key, { + enumerable: true, + get: function get() { + return _ExsurgeChant[key]; + } + }); + }); + + var _ExsurgeChant2 = __webpack_require__(8); + + Object.keys(_ExsurgeChant2).forEach(function (key) { + if (key === "default") return; + Object.defineProperty(exports, key, { + enumerable: true, + get: function get() { + return _ExsurgeChant2[key]; + } + }); + }); + + var _ExsurgeChant3 = __webpack_require__(11); + + Object.keys(_ExsurgeChant3).forEach(function (key) { + if (key === "default") return; + Object.defineProperty(exports, key, { + enumerable: true, + get: function get() { + return _ExsurgeChant3[key]; + } + }); + }); + + var _Exsurge6 = __webpack_require__(10); + + Object.keys(_Exsurge6).forEach(function (key) { + if (key === "default") return; + Object.defineProperty(exports, key, { + enumerable: true, + get: function get() { + return _Exsurge6[key]; + } + }); + }); + + + // client side support + + if (typeof document !== 'undefined') { + var ChantVisualElementPrototype = Object.create(HTMLElement.prototype); + + ChantVisualElementPrototype.createdCallback = function () { + var ctxt = new _Exsurge4.ChantContext(); + + ctxt.lyricTextFont = "'Crimson Text', serif"; + ctxt.lyricTextSize *= 1.2; + ctxt.dropCapTextFont = ctxt.lyricTextFont; + ctxt.annotationTextFont = ctxt.lyricTextFont; + + var useDropCap = true; + var useDropCapAttr = this.getAttribute("use-drop-cap"); + if (useDropCapAttr === 'false') useDropCap = false; + + var score = _Exsurge6.Gabc.loadChantScore(ctxt, this.innerText, useDropCap); + + var annotationAttr = this.getAttribute("annotation"); + if (annotationAttr) { + // add an annotation + score.annotation = new _Exsurge4.Annotation(ctxt, annotationAttr); + } + + var _element = this; + + var width = 0; + var doLayout = function doLayout() { + var newWidth = _element.parentElement.clientWidth; + if (width === newWidth) return; + width = newWidth; + // perform layout on the chant + score.performLayout(ctxt, function () { + score.layoutChantLines(ctxt, width, function () { + // render the score to svg code + _element.innerHTML = score.createSvgFragment(ctxt); + }); + }); + }; + doLayout(); + if (window.addEventListener) window.addEventListener('resize', doLayout, false);else if (window.attachEvent) window.attachEvent('onresize', doLayout); + }; + + ChantVisualElementPrototype.attachedCallback = function () {}; + + document.registerElement = document.registerElement || function () {}; + // register the custom element + var ChantVisualElement = document.registerElement('chant-visual', { + prototype: ChantVisualElementPrototype + }); + } + +/***/ }, +/* 1 */ +/***/ function(module, exports) { + + "use strict"; + + Object.defineProperty(exports, "__esModule", { + value: true + }); + + var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }(); + + exports.DeviceIndependent = DeviceIndependent; + exports.Centimeters = Centimeters; + exports.Millimeters = Millimeters; + exports.Inches = Inches; + exports.ToCentimeters = ToCentimeters; + exports.ToMillimeters = ToMillimeters; + exports.ToInches = ToInches; + exports.generateRandomGuid = generateRandomGuid; + + function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } + + // + // Author(s): + // Fr. Matthew Spencer, OSJ + // + // Copyright (c) 2008-2016 Fr. Matthew Spencer, OSJ + // + // Permission is hereby granted, free of charge, to any person obtaining a copy + // of this software and associated documentation files (the "Software"), to deal + // in the Software without restriction, including without limitation the rights + // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + // copies of the Software, and to permit persons to whom the Software is + // furnished to do so, subject to the following conditions: + // + // The above copyright notice and this permission notice shall be included in + // all copies or substantial portions of the Software. + // + // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + // THE SOFTWARE. + // + + var Units = exports.Units = { + // enums + DeviceIndepenedent: 0, // device independent units: 96/inch + Centimeters: 1, + Millimeters: 2, + Inches: 3, + + // constants for device independent units (diu) + DIU_PER_INCH: 96, + DIU_PER_CENTIMETER: 96 / 2.54, + + ToDeviceIndependent: function ToDeviceIndependent(n, inputUnits) { + switch (inputUnits) { + case Centimeters: + return n * DIU_PER_CENTIMETER; + case Millimeters: + return n * DIU_PER_CENTIMETER / 10; + case Inches: + return n * DIU_PER_INCH; + default: + return n; + } + }, + + FromDeviceIndependent: function FromDeviceIndependent(n, outputUnits) { + switch (outputUnits) { + case Centimeters: + return n / DIU_PER_CENTIMETER; + case Millimeters: + return n / DIU_PER_CENTIMETER * 10; + case Inches: + return n / DIU_PER_INCH; + default: + return n; + } + }, + + StringToUnitsType: function StringToUnitsType(s) { + switch (s.ToLower()) { + case "in": + case "inches": + return Inches; + + case "cm": + case "centimeters": + return Centimeters; + + case "mm": + case "millimeters": + return Millimeters; + + case "di": + case "device-independent": + return DeviceIndepenedent; + + default: + return DeviceIndepenedent; + } + }, + + UnitsTypeToString: function UnitsTypeToString(units) { + switch (units) { + case Inches: + return "in"; + case Centimeters: + return "cm"; + case Millimeters: + return "mm"; + case DeviceIndepenedent: + return "device-independent"; + default: + return "device-independent"; + } + } + }; + + function DeviceIndependent(n) { + return n; + } + + function Centimeters(n) { + return Units.ToDeviceIndependent(n, Units.Centimeters); + } + + function Millimeters(n) { + return Units.ToDeviceIndependent(n, Units.Millimeters); + } + + function Inches(n) { + return Units.ToDeviceIndependent(n, Units.Inches); + } + + function ToCentimeters(n) { + return Units.FromDeviceIndependent(n, Units.Centimeters); + } + + function ToMillimeters(n) { + return Units.FromDeviceIndependent(n, Units.Millimeters); + } + + function ToInches(n) { + return Units.FromDeviceIndependent(n, Units.Inches); + } + + /* + * Point + */ + + var Point = exports.Point = function () { + function Point(x, y) { + _classCallCheck(this, Point); + + this.x = typeof x !== 'undefined' ? x : 0; + this.y = typeof y !== 'undefined' ? y : 0; + } + + _createClass(Point, [{ + key: "clone", + value: function clone() { + return new Point(this.x, this.y); + } + }, { + key: "equals", + value: function equals(point) { + return this.x === point.x && this.y === point.y; + } + }]); + + return Point; + }(); + + /* + * Rect + */ + + + var Rect = exports.Rect = function () { + function Rect(x, y, width, height) { + _classCallCheck(this, Rect); + + this.x = typeof x !== 'undefined' ? x : Infinity; + this.y = typeof y !== 'undefined' ? y : Infinity; + this.width = typeof width !== 'undefined' ? width : -Infinity; + this.height = typeof height !== 'undefined' ? height : -Infinity; + } + + _createClass(Rect, [{ + key: "clone", + value: function clone() { + return new Rect(this.x, this.y, this.width, this.height); + } + }, { + key: "isEmpty", + value: function isEmpty() { + return this.x === Infinity && this.y === Infinity && this.width === -Infinity && this.height === -Infinity; + } + + // convenience method + + }, { + key: "right", + value: function right() { + return this.x + this.width; + } + }, { + key: "bottom", + value: function bottom() { + return this.y + this.height; + } + }, { + key: "equals", + value: function equals(rect) { + return this.x === rect.x && this.y === rect.y && this.width === rect.width && this.height === rect.height; + } + + // other can be a Point or a Rect + + }, { + key: "contains", + value: function contains(other) { + if (other instanceof Point) { + return other.x >= this.x && other.x <= this.x + this.width && other.y >= this.y && other.y <= this.y + this.height; + } else { + // better be instance of Rect + return this.x <= other.x && this.x + this.width >= other.x + other.width && this.y <= other.y && this.y + this.height >= other.y + other.height; + } + } + }, { + key: "union", + value: function union(rect) { + + var right = Math.max(this.x + this.width, rect.x + rect.width); + var bottom = Math.max(this.y + this.height, rect.y + rect.height); + + this.x = Math.min(this.x, rect.x); + this.y = Math.min(this.y, rect.y); + + this.width = right - this.x; + this.height = bottom - this.y; + } + }]); + + return Rect; + }(); + + /** + * Margins + * + * @class + */ + + + var Margins = exports.Margins = function () { + function Margins(left, top, right, bottom) { + _classCallCheck(this, Margins); + + this.left = typeof left !== 'undefined' ? left : 0; + this.top = typeof top !== 'undefined' ? top : 0; + this.right = typeof right !== 'undefined' ? right : 0; + this.bottom = typeof bottom !== 'undefined' ? bottom : 0; + } + + _createClass(Margins, [{ + key: "clone", + value: function clone() { + return new Margins(this.left, this.top, this.right, this.bottom); + } + }, { + key: "equals", + value: function equals(margins) { + return this.left === margins.left && this.top === margins.top && this.right === margins.right && this.bottom === margins.bottom; + } + }]); + + return Margins; + }(); + + /** + * Size + * + * @class + */ + + + var Size = exports.Size = function () { + function Size(width, height) { + _classCallCheck(this, Size); + + this.width = typeof width !== 'undefined' ? width : 0; + this.height = typeof height !== 'undefined' ? height : 0; + } + + _createClass(Size, [{ + key: "clone", + value: function clone() { + return new Size(this.width, this.height); + } + }, { + key: "equals", + value: function equals(size) { + return this.width === size.width && this.height === size.height; + } + }]); + + return Size; + }(); + + /* + * Pitches, notes + */ + + + var Step = exports.Step = { + Do: 0, + Du: 1, + Re: 2, + Me: 3, + Mi: 4, + Fa: 5, + Fu: 6, + So: 7, + La: 9, + Te: 10, + Ti: 11 + }; + + // this little array helps map step values to staff positions. The numeric values of steps + // correspond to whole step increments (2) or half step increments (1). This gives us the ability + // to compare pitches precisely, but makes it challenging to place steps on the staff. this little + // array maps the steps to an incremental position the steps take on the staff line. This works + // so simply because chant only uses do and fa clefs, and only has a flatted ti (te), making + // for relatively easy mapping to staff line locations. + // Do Du Re Me Mi Fa Fu So La Te Ti + var __StepToStaffPosition = [0, 0, 1, 1, 2, 3, 3, 4, 4, 5, 6, 6]; + var __StaffOffsetToStep = [Step.Do, Step.Re, Step.Mi, Step.Fa, Step.So, Step.La, Step.Ti]; // no accidentals in this one + + var Pitch = exports.Pitch = function () { + function Pitch(step, octave) { + _classCallCheck(this, Pitch); + + this.step = step; + this.octave = octave; + } + + _createClass(Pitch, [{ + key: "toInt", + value: function toInt() { + return this.octave * 12 + this.step; + } + }, { + key: "isHigherThan", + value: function isHigherThan(pitch) { + return this.toInt() > pitch.toInt(); + } + }, { + key: "isLowerThan", + value: function isLowerThan(pitch) { + return this.toInt() < pitch.toInt(); + } + }, { + key: "equals", + value: function equals(pitch) { + return this.toInt() === pitch.toInt(); + } + }], [{ + key: "stepToStaffOffset", + value: function stepToStaffOffset(step) { + return __StepToStaffPosition[step]; + } + }, { + key: "staffOffsetToStep", + value: function staffOffsetToStep(offset) { + while (offset < 0) { + offset = __StaffOffsetToStep.length + offset; + }return __StaffOffsetToStep[offset % __StaffOffsetToStep.length]; + } + }]); + + return Pitch; + }(); + + function generateRandomGuid() { + function s4() { + return Math.floor((1 + Math.random()) * 0x10000).toString(16).substring(1); + } + return s4() + s4(); + } + +/***/ }, +/* 2 */ +/***/ function(module, exports, __webpack_require__) { + + 'use strict'; + + Object.defineProperty(exports, "__esModule", { + value: true + }); + exports.Spanish = exports.Latin = exports.Language = undefined; + + var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }(); // + // Author(s): + // Fr. Matthew Spencer, OSJ + // + // Copyright (c) 2008-2016 Fr. Matthew Spencer, OSJ + // + // Permission is hereby granted, free of charge, to any person obtaining a copy + // of this software and associated documentation files (the "Software"), to deal + // in the Software without restriction, including without limitation the rights + // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + // copies of the Software, and to permit persons to whom the Software is + // furnished to do so, subject to the following conditions: + // + // The above copyright notice and this permission notice shall be included in + // all copies or substantial portions of the Software. + // + // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + // THE SOFTWARE. + // + + var _Exsurge = __webpack_require__(1); + + var Exsurge = _interopRequireWildcard(_Exsurge); + + function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key]; } } newObj.default = obj; return newObj; } } + + function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; } + + function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; } + + function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } + + /** + * @class + */ + + var Language = exports.Language = function () { + function Language(name) { + _classCallCheck(this, Language); + + this.name = typeof name !== 'undefined' ? name : ""; + } + + /** + * @param {String} text The string to parsed into words. + * @return {Word[]} the resulting parsed words from syllabification + */ + + + _createClass(Language, [{ + key: 'syllabify', + value: function syllabify(text) { + + var parsedWords = []; + + if (typeof text === 'undefined' || text === "") return parsedWords; + + // Divide the text into words separated by whitespace + var words = text.split(/[\s]+/); + + for (var i = 0, end = words.length; i < end; i++) { + parsedWords.push(this.syllabifyWord(words[i])); + }return parsedWords; + } + }]); + + return Language; + }(); + + /** + * @class + */ + + + var Latin = exports.Latin = function (_Language) { + _inherits(Latin, _Language); + + /** + * @constructs + */ + + function Latin() { + _classCallCheck(this, Latin); + + // fixme: ui is only diphthong in the exceptional cases below (according to Wheelock's Latin) + + var _this = _possibleConstructorReturn(this, Object.getPrototypeOf(Latin).call(this, "Latin")); + + _this.diphthongs = ["ae", "au", "oe", "aé", "áu", "oé"]; + // for centering over the vowel, we will need to know any combinations that might be diphthongs: + _this.possibleDiphthongs = _this.diphthongs.concat(["ei", "eu", "ui", "éi", "éu", "úi"]); + + // some words that are simply exceptions to standard syllabification rules! + var wordExceptions = new Object(); + + // ui combos pronounced as diphthongs + wordExceptions["huius"] = ["hui", "us"]; + wordExceptions["cuius"] = ["cui", "us"]; + wordExceptions["huic"] = ["huic"]; + wordExceptions["cui"] = ["cui"]; + wordExceptions["hui"] = ["hui"]; + + // eu combos pronounced as diphthongs + wordExceptions["euge"] = ["eu", "ge"]; + wordExceptions["seu"] = ["seu"]; + + _this.vowels = ['a', 'e', 'i', 'o', 'u', 'á', 'é', 'í', 'ó', 'ú', 'æ', 'œ', 'ǽ', // no accented œ in unicode? + 'y']; // y is treated as a vowel; not native to Latin but useful for words borrowed from Greek + + _this.vowelsThatMightBeConsonants = ['i', 'u']; + + _this.muteConsonantsAndF = ['b', 'c', 'd', 'g', 'p', 't', 'f']; + + _this.liquidConsonants = ['l', 'r']; + return _this; + } + + // c must be lowercase! + + + _createClass(Latin, [{ + key: 'isVowel', + value: function isVowel(c) { + for (var i = 0, end = this.vowels.length; i < end; i++) { + if (this.vowels[i] === c) return true; + }return false; + } + }, { + key: 'isVowelThatMightBeConsonant', + value: function isVowelThatMightBeConsonant(c) { + for (var i = 0, end = this.vowelsThatMightBeConsonants.length; i < end; i++) { + if (this.vowelsThatMightBeConsonants[i] === c) return true; + }return false; + } + + // substring should be a vowel and the character following + + }, { + key: 'isVowelActingAsConsonant', + value: function isVowelActingAsConsonant(substring) { + return this.isVowelThatMightBeConsonant(substring[0]) && this.isVowel(substring[1]); + } + + /** + * f is not a mute consonant, but we lump it together for syllabification + * since it is syntactically treated the same way + * + * @param {String} c The character to test; must be lowercase + * @return {boolean} true if c is an f or a mute consonant + */ + + }, { + key: 'isMuteConsonantOrF', + value: function isMuteConsonantOrF(c) { + for (var i = 0, end = this.muteConsonantsAndF.length; i < end; i++) { + if (this.muteConsonantsAndF[i] === c) return true; + }return false; + } + + /** + * + * @param {String} c The character to test; must be lowercase + * @return {boolean} true if c is a liquid consonant + */ + + }, { + key: 'isLiquidConsonant', + value: function isLiquidConsonant(c) { + for (var i = 0, end = this.liquidConsonants.length; i < end; i++) { + if (this.liquidConsonants[i] === c) return true; + }return false; + } + + /** + * + * @param {String} s The string to test; must be lowercase + * @return {boolean} true if s is a diphthong + */ + + }, { + key: 'isDiphthong', + value: function isDiphthong(s) { + for (var i = 0, end = this.diphthongs.length; i < end; i++) { + if (this.diphthongs[i] === s) return true; + }return false; + } + + /** + * + * @param {String} s The string to test; must be lowercase + * @return {boolean} true if s is a diphthong + */ + + }, { + key: 'isPossibleDiphthong', + value: function isPossibleDiphthong(s) { + for (var i = 0, end = this.possibleDiphthongs.length; i < end; i++) { + if (this.possibleDiphthongs[i] === s) return true; + }return false; + } + + /** + * Rules for Latin syllabification (from Collins, "A Primer on Ecclesiastical Latin") + * + * Divisions occur when: + * 1. After open vowels (those not followed by a consonant) (e.g., "pi-us" and "De-us") + * 2. After vowels followed by a single consonant (e.g., "vi-ta" and "ho-ra") + * 3. After the first consonant when two or more consonants follow a vowel + * (e.g., "mis-sa", "minis-ter", and "san-ctus"). + * + * Exceptions: + * 1. In compound words the consonants stay together (e.g., "de-scribo"). + * 2. A mute consonant (b, c, d, g, p, t) or f followed by a liquid consonant (l, r) + * go with the succeeding vowel: "la-crima", "pa-tris" + * + * In addition to these rules, Wheelock's Latin provides this sound exception: + * - Also counted as single consonants are qu and the aspirates ch, ph, + * th, which should never be separated in syllabification: + * architectus, ar-chi-tec-tus; loquacem, lo-qua-cem. + * + */ + + }, { + key: 'syllabifyWord', + value: function syllabifyWord(word) { + var syllables = []; + var haveCompleteSyllable = false; + var previousWasVowel = false; + var workingString = word.toLowerCase(); + var startSyllable = 0; + + var c, lookahead, haveLookahead; + + // a helper function to create syllables + var makeSyllable = function makeSyllable(length) { + if (haveCompleteSyllable) { + syllables.push(word.substr(startSyllable, length)); + startSyllable += length; + } + + haveCompleteSyllable = false; + }; + + for (var i = 0, wordLength = workingString.length; i < wordLength; i++) { + + c = workingString[i]; + + // get our lookahead in case we need them... + lookahead = '*'; + haveLookahead = i + 1 < wordLength; + + if (haveLookahead) lookahead = workingString[i + 1]; + + var cIsVowel = this.isVowel(c); + + // i is a special case for a vowel. when i is at the beginning + // of the word (Iesu) or i is between vowels (alleluia), + // then the i is treated as a consonant (y) + if (c === 'i') { + if (i === 0 && haveLookahead && this.isVowel(lookahead)) cIsVowel = false;else if (previousWasVowel && haveLookahead && this.isVowel(lookahead)) { + cIsVowel = false; + } + } + + if (c === '-') { + + // a hyphen forces a syllable break, which effectively resets + // the logic... + + haveCompleteSyllable = true; + previousWasVowel = false; + makeSyllable(i - startSyllable); + startSyllable++; + } else if (cIsVowel) { + + // once we get a vowel, we have a complete syllable + haveCompleteSyllable = true; + + if (previousWasVowel && !this.isDiphthong(workingString[i - 1] + "" + c)) { + makeSyllable(i - startSyllable); + haveCompleteSyllable = true; + } + + previousWasVowel = true; + } else if (haveLookahead) { + + if (c === 'q' && lookahead === 'u' || lookahead === 'h' && (c === 'c' || c === 'p' || c === 't')) { + // handle wheelock's exceptions for qu, ch, ph and th + makeSyllable(i - startSyllable); + i++; // skip over the 'h' or 'u' + } else if (previousWasVowel && this.isVowel(lookahead)) { + // handle division rule 2 + makeSyllable(i - startSyllable); + } else if (this.isMuteConsonantOrF(c) && this.isLiquidConsonant(lookahead)) { + // handle exception 2 + makeSyllable(i - startSyllable); + } else if (haveCompleteSyllable) { + // handle division rule 3 + makeSyllable(i + 1 - startSyllable); + } + + previousWasVowel = false; + } + } + + // if we have a complete syllable, we can add it as a new one. Otherwise + // we tack the remaining characters onto the last syllable. + if (haveCompleteSyllable) syllables.push(word.substr(startSyllable));else if (startSyllable > 0) syllables[syllables.length - 1] += word.substr(startSyllable); + + return syllables; + } + + /** + * @param {String} s the string to search + * @param {Number} startIndex The index at which to start searching for a vowel in the string + * @retuns a custom class with three properties: {found: (true/false) startIndex: (start index in s of vowel segment) length ()} + */ + + }, { + key: 'findVowelSegment', + value: function findVowelSegment(s, startIndex) { + + var i, end, index; + var workingString = s.toLowerCase(); + + // do we have a diphthong? + for (i = 0, end = this.possibleDiphthongs.length; i < end; i++) { + var d = this.possibleDiphthongs[i]; + index = workingString.indexOf(d, startIndex); + + if (index >= 0) return { found: true, startIndex: index, length: d.length }; + } + + // no diphthongs. Let's look for single vowels then... + for (i = 0, end = this.vowels.length; i < end; i++) { + index = workingString.indexOf(this.vowels[i], startIndex); + + if (index >= 0) { + // if the first vowel found might also be a consonant (U or I), and it is immediately followed by another vowel, (e.g., sanguis, quis), the first u counts as a consonant: + // (in practice, this only affects words such as equus that contain a uu, since the alphabetically earlier vowel would be found before the U) + if (this.isVowelActingAsConsonant(workingString.substr(index, 2))) { + ++index; + } + return { found: true, startIndex: index, length: 1 }; + } + } + + // no vowels sets found after startIndex! + return { found: false, startIndex: -1, length: -1 }; + } + }]); + + return Latin; + }(Language); + + /** + * @class + */ + + + var Spanish = exports.Spanish = function (_Language2) { + _inherits(Spanish, _Language2); + + function Spanish() { + _classCallCheck(this, Spanish); + + var _this2 = _possibleConstructorReturn(this, Object.getPrototypeOf(Spanish).call(this, "Spanish")); + + _this2.vowels = ['a', 'e', 'i', 'o', 'u', 'y', 'á', 'é', 'í', 'ó', 'ú', 'ü']; + + _this2.weakVowels = ['i', 'u', 'ü', 'y']; + + _this2.strongVowels = ['a', 'e', 'o', 'á', 'é', 'í', 'ó', 'ú']; + + _this2.diphthongs = ["ai", "ei", "oi", "ui", "ia", "ie", "io", "iu", "au", "eu", "ou", "ua", "ue", "uo", "ái", "éi", "ói", "úi", "iá", "ié", "ió", "iú", "áu", "éu", "óu", "uá", "ué", "uó", "üe", "üi"]; + + _this2.uDiphthongExceptions = ["gue", "gui", "qua", "que", "qui", "quo"]; + return _this2; + } + + // c must be lowercase! + + + _createClass(Spanish, [{ + key: 'isVowel', + value: function isVowel(c) { + for (var i = 0, end = this.vowels.length; i < end; i++) { + if (this.vowels[i] === c) return true; + }return false; + } + + /** + * @param {String} c The character to test; must be lowercase + * @return {boolean} true if c is an f or a mute consonant + */ + + }, { + key: 'isWeakVowel', + value: function isWeakVowel(c) { + for (var i = 0, end = this.weakVowels.length; i < end; i++) { + if (this.weakVowels[i] === c) return true; + }return false; + } + + /** + * @param {String} c The character to test; must be lowercase + * @return {boolean} true if c is an f or a mute consonant + */ + + }, { + key: 'isStrongVowel', + value: function isStrongVowel(c) { + for (var i = 0, end = this.strongVowels.length; i < end; i++) { + if (this.strongVowels[i] === c) return true; + }return false; + } + + /** + * + * @param {String} s The string to test; must be lowercase + * @return {boolean} true if s is a diphthong + */ + + }, { + key: 'isDiphthong', + value: function isDiphthong(s) { + for (var i = 0, end = this.diphthongs.length; i < end; i++) { + if (this.diphthongs[i] === s) return true; + }return false; + } + }, { + key: 'createSyllable', + value: function createSyllable(text) { + + /* + var accented = false; + var ellidesToNext = false; + + if (text.length > 0) { + + if (text[0] == '`') { + accented = true; + text = text.substr(1); + } + + if (text[text.length - 1] == '_') { + ellidesToNext = true; + text = text.substr(0, text.length - 1); + } + } + + var s = new Syllable(text); + + s.isMusicalAccent = accented; + s.elidesToNext = ellidesToNext;*/ + + return text; + } + + /** + */ + + }, { + key: 'syllabifyWord', + value: function syllabifyWord(word) { + + var syllables = []; + + var haveCompleteSyllable = false; + var previousIsVowel = false; + var previousIsStrongVowel = false; // only valid if previousIsVowel == true + var startSyllable = 0; + + // fixme: first check for prefixes + + for (i = 0; i < word.length; i++) { + + var c = word[i].toLowerCase(); + + if (this.isVowel(c)) { + + // we have a complete syllable as soon as we have a vowel + haveCompleteSyllable = true; + + var cIsStrongVowel = this.isStrongVowel(c); + + if (previousIsVowel) { + // if we're at a strong vowel, then we finish out the last syllable + if (cIsStrongVowel) { + if (previousIsStrongVowel) { + syllables.push(this.createSyllable(word.substr(startSyllable, i - startSyllable))); + startSyllable = i; + } + } + } + + previousIsVowel = true; + previousIsStrongVowel = cIsStrongVowel; + } else { + if (!haveCompleteSyllable) { + // do nothing since we don't have a complete syllable yet... + } else { + + // handle explicit syllable breaks + if (word[i] === '-') { + // start new syllable + syllables.push(this.createSyllable(word.substr(startSyllable, i - startSyllable))); + startSyllable = ++i; + } else { + + var numberOfConsonants = 1, + consonant2; + + // count how many more consonants there are + for (j = i + 1; j < word.length; j++) { + if (this.isVowel(word[j])) break; + numberOfConsonants++; + } + + if (numberOfConsonants === 1) { + // start new syllable + syllables.push(this.createSyllable(word.substr(startSyllable, i - startSyllable))); + startSyllable = i; + } else if (numberOfConsonants === 2) { + consonant2 = word[i + 1].toLowerCase(); + if (consonant2 === 'l' || consonant2 === 'r' || c === 'c' && consonant2 === 'h') { + // split before the consonant pair + syllables.push(this.createSyllable(word.substr(startSyllable, i - startSyllable))); + startSyllable = i++; + } else { + //split the consonants + syllables.push(this.createSyllable(word.substr(startSyllable, ++i - startSyllable))); + startSyllable = i; + } + } else if (numberOfConsonants === 3) { + consonant2 = word[i + 1].toLowerCase(); + + // if second consonant is s, divide cc-c, otherwise divide c-cc + if (consonant2 === 's') { + i += 2; + syllables.push(this.createSyllable(word.substr(startSyllable, i - startSyllable))); + } else syllables.push(this.createSyllable(word.substr(startSyllable, ++i - startSyllable))); + + startSyllable = i; + } else if (numberOfConsonants === 4) { + // four always get split cc-cc + syllables.push(this.createSyllable(word.substr(startSyllable, i - startSyllable + 2))); + startSyllable = i + 2; + i += 3; + } + } + + haveCompleteSyllable = false; + } + + previousIsVowel = false; + } + } + + // if we have a complete syllable, we can add it as a new one. Otherwise + // we tack the remaining characters onto the last syllable. + if (haveCompleteSyllable) syllables.push(word.substr(startSyllable));else if (startSyllable > 0) syllables[syllables.length - 1] += word.substr(startSyllable);else if (syllables.length === 0) syllables.push(this.createSyllable(word)); + + return syllables; + } + + /** + * @param {String} s the string to search + * @param {Number} startIndex The index at which to start searching for a vowel in the string + * @retuns a custom class with three properties: {found: (true/false) startIndex: (start index in s of vowel segment) length ()} + */ + + }, { + key: 'findVowelSegment', + value: function findVowelSegment(s, startIndex) { + + var i, end, index; + var workingString = s.toLowerCase(); + + // do we have a diphthongs? + for (i = 0, end = this.diphthongs.length; i < end; i++) { + var d = this.diphthongs[i]; + index = workingString.indexOf(d, startIndex); + + if (index >= 0) { + + // check the exceptions... + if (d[0] === 'u' && index > 0) { + var tripthong = s.substr(index - 1, 3).toLowerCase(); + + for (j = 0, endj = this.uDiphthongExceptions.length; i < endj; j++) { + if (tripthong === this.uDiphthongExceptions[j]) { + // search from after the u... + return this.findVowelSegment(s, index + 1); + } + } + } + + return { found: true, startIndex: index, length: d.length }; + } + } + + // no diphthongs. Let's look for single vowels then... + for (i = 0, end = this.vowels.length; i < end; i++) { + index = workingString.indexOf(this.vowels[i], startIndex); + + if (index >= 0) return { found: true, startIndex: index, length: 1 }; + } + + // no vowels sets found after startIndex! + return { found: false, startIndex: -1, length: -1 }; + } + }]); + + return Spanish; + }(Language); + +/***/ }, +/* 3 */ +/***/ function(module, exports) { + + "use strict"; + + Object.defineProperty(exports, "__esModule", { + value: true + }); + // + // Author(s): + // Fr. Matthew Spencer, OSJ + // + // Copyright (c) 2008-2016 Fr. Matthew Spencer, OSJ + // + // Permission is hereby granted, free of charge, to any person obtaining a copy + // of this software and associated documentation files (the "Software"), to deal + // in the Software without restriction, including without limitation the rights + // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + // copies of the Software, and to permit persons to whom the Software is + // furnished to do so, subject to the following conditions: + // + // The above copyright notice and this permission notice shall be included in + // all copies or substantial portions of the Software. + // + // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + // THE SOFTWARE. + // + + // generated based on the svg data + var Glyphs = exports.Glyphs = { + "None": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 0, + "height": 0 + }, + "origin": { + "x": 0, + "y": 0 + }, + "align": "left" + }, + "AcuteAccent": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M4 0C-.614.52-.614.52-.803-3.182l60.768-108.422c4.52-7.182 10.543-13.67 18.075-13.67 5.27 0 14.31 1.264 23.346 7.793 7.53 5.223 8.803 11.752 8.803 16.975 0 3.917-.52 11.1-8.05 17.628L4 0z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 110.99200439453125, + "height": 125.79399108886719 + }, + "origin": { + "x": 0.8030000329017639, + "y": 125.27399444580078 + }, + "align": "left" + }, + "Stropha": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M1.22-73.438c4.165 13.02 12.238 27.084 24.217 42.188L49.657 0 34.812 27.344C18.666 55.47-.084 72.396-21.438 78.124c4.687-3.645 7.03-8.593 7.03-14.843 0-8.853-4.947-20.572-14.843-35.155L-48 0 1.22-73.438z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 97.65699768066406, + "height": 151.56201171875 + }, + "origin": { + "x": 48, + "y": 73.43800354003906 + }, + "align": "left" + }, + "BeginningAscLiquescent": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M-50 43.688V-61c4.167 7.292 12.76 10.938 25.78 10.938 9.376 0 20.053-1.563 32.032-4.688C31.773-60.48 45.833-71.677 50-88.344v117.97C43.75 42.645 32.812 51.5 17.187 56.186-.52 61.398-15.886 64-28.906 64-42.97 64-50 57.23-50 43.687z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 152.343994140625 + }, + "origin": { + "x": 50, + "y": 88.34400177001953 + }, + "align": "left" + }, + "BeginningDesLiquescent": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M-50-56.03c0-13.022 7.03-19.532 21.094-19.532 13.02 0 28.385 2.604 46.093 7.812C32.813-63.583 43.75-54.73 50-41.187V76C45.833 59.854 31.77 48.656 7.812 42.406c-11.98-3.125-22.656-4.687-32.03-4.687-13.022 0-21.615 3.905-25.782 11.718v-105.47z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 151.56199645996094 + }, + "origin": { + "x": 50, + "y": 75.56199645996094 + }, + "align": "left" + }, + "CustosDescLong": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M39.063 273.472c5.73.52 7.29-6.25 4.687-20.312V-65.59c-13.542 2.083-24.22 5.468-32.03 10.156C3.905-50.226 0-43.714 0-35.904V71.91c5.73-5.21 10.677-8.594 14.844-10.157 5.73-1.562 12.24-2.343 19.53-2.343v196.875c0 11.458 1.563 17.187 4.688 17.187" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 46.35300064086914, + "height": 339.58197021484375 + }, + "origin": { + "x": 0, + "y": 65.58999633789062 + }, + "align": "left" + }, + "CustosDescShort": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M34.375 191.923c0 8.333 1.563 12.24 4.688 11.72 3.125-.522 4.687-7.033 4.687-19.533v-250c-13.542 2.084-24.22 5.47-32.03 10.157C3.905-50.525 0-44.015 0-36.203V71.61c5.73-5.208 10.677-8.593 14.844-10.156 5.73-1.562 12.24-2.344 19.53-2.344v132.813z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 43.75, + "height": 270.0530090332031 + }, + "origin": { + "x": 0, + "y": 65.88999938964844 + }, + "align": "left" + }, + "CustosLong": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M39.063-269.562c5.73-.52 7.29 6.25 4.687 20.312V69.5c-13.542-2.083-24.22-5.47-32.03-10.156C3.905 54.134 0 47.624 0 39.812V-68c5.73 5.208 10.677 8.594 14.844 10.156 5.73 1.563 12.24 2.344 19.53 2.344v-196.875c0-11.458 1.563-17.187 4.688-17.187z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 46.35300064086914, + "height": 339.5820007324219 + }, + "origin": { + "x": 0, + "y": 270.0820007324219 + }, + "align": "left" + }, + "CustosShort": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M34.375-188.125c0-8.333 1.563-12.24 4.688-11.72 3.125.522 4.687 7.033 4.687 19.532v250c-13.542-2.083-24.22-5.468-32.03-10.156C3.905 54.324 0 47.813 0 40V-67.813c5.73 5.21 10.677 8.594 14.844 10.157 5.73 1.562 12.24 2.344 19.53 2.343v-132.812z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 43.75, + "height": 270.052001953125 + }, + "origin": { + "x": 0, + "y": 200.36500549316406 + }, + "align": "left" + }, + "DoClef": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M0 98.406V-97.688C0-118 5.99-134.275 17.97-146.516c11.978-12.24 27.603-18.36 46.874-18.36 10.937 0 19.53 3.126 25.78 9.376s9.376 14.583 9.376 25v107.813l-6.25-5.47c-4.167-3.645-10.287-7.42-18.36-11.327-8.072-3.907-16.796-5.86-26.17-5.86-11.46 0-21.486 4.427-30.08 13.282-8.593 8.854-12.89 19.53-12.89 32.03s4.297 23.308 12.89 32.423c8.594 9.115 18.62 13.672 30.08 13.672 9.374 0 18.098-1.822 26.17-5.468 8.073-3.646 14.193-7.292 18.36-10.938l6.25-6.25V132c0 9.896-3.125 18.1-9.375 24.61-6.25 6.51-14.844 9.765-25.78 9.765-19.272 0-34.897-6.25-46.876-18.75C5.99 135.125 0 118.72 0 98.405z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 331.2510070800781 + }, + "origin": { + "x": 0, + "y": 164.87600708007812 + }, + "align": "left" + }, + "FaClef": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M85.156-32v193.75c0 9.375-1.562 14.323-4.687 14.844-1.564 0-2.605-.52-3.126-1.563-.52-1.04-.782-2.603-.78-4.686V56.28c-8.335-8.332-19.793-12.5-34.376-12.5-17.71 0-31.77 3.907-42.188 11.72V-32c0-18.23 14.193-27.344 42.578-27.344 28.385 0 42.578 9.115 42.578 27.344zM98.438 93V-92.156c0-19.27 5.73-34.896 17.187-46.875 11.458-11.98 26.562-17.97 45.313-17.97 10.937 0 19.14 2.865 24.61 8.594 5.467 5.73 8.202 13.542 8.202 23.437v103.126l-5.47-4.687c-3.645-3.647-9.374-7.293-17.186-10.94-7.813-3.645-15.886-5.467-24.22-5.468-11.978 0-22.004 4.167-30.077 12.5-8.073 8.334-12.11 18.36-12.11 30.08 0 11.717 4.037 22.004 12.11 30.858s18.1 13.28 30.078 13.28c8.333 0 16.406-1.822 24.22-5.468 7.81-3.645 13.54-7.03 17.186-10.156l5.47-5.468V125.81c0 9.896-2.865 17.84-8.594 23.83-5.73 5.988-13.802 8.983-24.22 8.983-18.75 0-33.853-6.12-45.31-18.36-11.46-12.24-17.19-27.994-17.19-47.265z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 193.75201416015625, + "height": 333.5950012207031 + }, + "origin": { + "x": 0.001003265380859375, + "y": 157.00100708007812 + }, + "align": "left" + }, + "Flat": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M7.813-204.406c4.166 0 6.25 5.208 6.25 15.625L12.5-10.657C33.854 13.302 54.167 25.28 73.438 25.28c9.374 0 14.062-4.686 14.062-14.06 0-6.25-1.042-11.72-3.125-16.407-2.083-4.688-7.03-9.766-14.844-15.235-7.81-5.47-13.02-8.984-15.624-10.547L27.344-45.81V-80.97c17.187 0 33.073 4.82 47.656 14.454C89.583-56.88 96.875-47.376 96.875-38c0 67.708-.26 101.562-.78 101.563-38.543 0-69.532-12.24-92.97-36.72C0-52.322-1.042-123.936 0-188c0-10.937 2.604-16.406 7.813-16.406z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 97.91699981689453, + "height": 267.968994140625 + }, + "origin": { + "x": 1.0420000553131104, + "y": 204.406005859375 + }, + "align": "left" + }, + "Mora": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M47.478-24c6.957 0 12.793 2.288 17.49 6.883C69.662-12.52 72-6.904 72-.267c0 6.64-2.337 12.352-7.033 17.118C60.27 21.618 54.435 24 47.477 24c-6.26 0-11.748-2.383-16.444-7.15C26.337 12.086 24 6.374 24-.265c0-6.638 2.337-12.255 7.033-16.85C35.73-21.713 41.217-24 47.478-24z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 48, + "height": 48 + }, + "origin": { + "x": -24, + "y": 24 + }, + "align": "left" + }, + "Natural": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M7.906-166.563c-2.864 0-5.614.52-8.218 1.563v13.28l.78 56.25.782 78.907v85.157c.52 3.646 2.604 5.73 6.25 6.25l23.438-3.906 23.437-3.907v29.69c0 42.186-.26 63.54-.78 64.06l6.25 2.345c1.04.52 2.082.78 3.124.78 2.603 0 4.947-1.3 7.03-3.905L67.656-71.25c-.52-2.604-2.083-3.906-4.687-3.906-7.814 0-17.19 1.04-28.126 3.125l-19.53 3.124.78-38.28V-165c-2.604-1.042-5.323-1.562-8.188-1.563zM55.938-40v71.875l-41.407 7.03c0-48.436.262-72.655.783-72.655L55.938-40z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 70.31100463867188, + "height": 330.468994140625 + }, + "origin": { + "x": 0.3120002746582031, + "y": 166.56300354003906 + }, + "align": "left" + }, + "OriscusAsc": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M50 30.25c0 12.5-3.125 21.354-9.375 26.562-3.125 2.605-7.813 3.907-14.063 3.907-3.125 0-5.99-.522-8.593-1.564-2.605-1.04-5.6-2.474-8.986-4.297C5.6 53.035 2.734 51.603.39 50.56c-2.343-1.04-5.338-2.474-8.984-4.296-3.646-1.823-6.77-3.256-9.375-4.297-2.603-1.043-5.468-1.564-8.593-1.564-6.25 0-10.937 1.563-14.062 4.688C-46.875 50.824-50 59.677-50 71.656v-106.25c0-13.02 3.125-21.875 9.375-26.562 3.125-2.604 7.813-3.906 14.063-3.907 3.125 0 5.99.52 8.593 1.563 2.605 1.042 5.73 2.474 9.376 4.297 3.646 1.823 6.51 2.995 8.594 3.516l10.938 5.468c6.25 3.126 11.458 4.69 15.624 4.69 6.25 0 10.938-1.564 14.063-4.69C46.875-55.426 50-64.02 50-76V30.25z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 147.656005859375 + }, + "origin": { + "x": 50, + "y": 76 + }, + "align": "left" + }, + "OriscusDes": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M-50 30.844v-106.25c0 11.458 3.125 20.052 9.375 25.78 3.125 3.126 7.813 4.69 14.063 4.688 4.687 0 13.41-3.255 26.17-9.765 12.762-6.51 21.746-9.766 26.954-9.766 6.25 0 10.938 1.303 14.063 3.907C46.875-55.874 50-47.02 50-34V72.25c0-11.98-3.125-20.833-9.375-26.563C37.5 42.563 32.812 41 26.562 41 21.875 41 13.023 44.385 0 51.156c-4.167 2.604-8.594 4.948-13.28 7.032-4.69 2.083-9.116 3.124-13.283 3.124-6.25 0-10.937-1.302-14.062-3.906C-46.875 52.198-50 43.344-50 30.844z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 147.656005859375 + }, + "origin": { + "x": 50, + "y": 75.40599822998047 + }, + "align": "left" + }, + "OriscusLiquescent": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M 19.05539,78.886528 C 20.242277,78.486807 21.532179,77.890297 22.925106,77.09701 24.317891,76.303653 26.700882,74.417241 30.074091,71.437777 33.447144,68.45824 36.523539,64.985185 39.303286,61.018598 42.082855,57.051975 44.562739,51.395765 46.742952,44.049969 48.922975,36.704172 50.01304,28.671032 50.013135,19.950525 L 50.013135,-34.225545 C 50.01304,-54.464261 42.07377,-64.583661 26.195289,-64.583768 20.248326,-64.583661 11.518758,-61.410372 0.00656131,-55.06389 -11.505742,-48.717218 -20.23531,-45.543929 -26.182179,-45.544024 -34.515109,-45.543929 -40.567968,-48.520405 -44.340791,-54.473441 -48.113613,-60.426286 -50.000025,-67.369373 -50.000025,-75.302702 L -50.000025,30.069925 C -50.000025,49.909039 -42.060754,59.828603 -26.182179,59.828615 -21.022584,59.828603 -12.38991,56.455465 -0.28412107,49.709203 11.821549,42.96294 20.648023,39.589803 26.195289,39.589803 29.368506,40.776762 30.361665,44.249817 29.17479,50.00897 27.987759,55.768122 26.00143,62.020829 23.215789,68.767116 z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 147.656005859375 + }, + "origin": { + "x": 50, + "y": 75.40599822998047 + }, + "align": "left" + }, + "PodatusLower": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M-4.688-30.28c22.396 0 34.636-.262 36.72-.782 5.728-1.563 8.593-5.21 8.593-10.938H50v97.656c0 2.604-1.302 4.167-3.906 4.688-5.21.52-21.355.78-48.438.78-23.958 0-38.54-.26-43.75-.78-2.604 0-3.906-1.302-3.906-3.906v-82.032c0-3.646 1.302-5.468 3.906-5.468h2.344c2.604.52 15.625.78 39.063.78z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 103.12399291992188 + }, + "origin": { + "x": 50, + "y": 42 + }, + "align": "left" + }, + "PodatusUpper": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M-46.094-63.78c13.542 0 24.61 2.473 33.203 7.42C-4.298-51.41 0-43.99 0-34.093V62h-9.375c0-10.938-2.604-19.14-7.812-24.61-5.21-5.468-14.844-8.203-28.907-8.202-18.23 0-33.333 4.166-45.312 12.5v-75.782c0-19.79 15.104-29.687 45.312-29.687z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 91.406005859375, + "height": 125.78099822998047 + }, + "origin": { + "x": 91.406005859375, + "y": 63.78099822998047 + }, + "align": "right" + }, + "Porrectus1": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M233.594 162.875c-58.855 0-107.032-6.25-144.53-18.75C34.895 125.895-11.46 99.855-50 66V-52.75C-21.354-24.625 26.302 6.885 92.97 41.78 123.697 57.928 163.54 66 212.5 66c21.354 0 34.635-9.896 39.844-29.688V151.94c0 7.29-6.25 10.937-18.75 10.937z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 302.343994140625, + "height": 215.6269989013672 + }, + "origin": { + "x": 50, + "y": 52.75 + }, + "align": "left" + }, + "Porrectus2": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M309.375 259.375c-50.52 0-110.938-22.396-181.25-67.188C48.437 141.667-10.938 94.272-50 50V-68.75C0-3.125 60.417 52.083 131.25 96.875c58.333 36.98 110.677 58.854 157.03 65.625h7.033c16.145 0 26.822-9.896 32.03-29.688v114.844c0 7.812-5.99 11.72-17.968 11.72z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 377.3429870605469, + "height": 328.1260070800781 + }, + "origin": { + "x": 50, + "y": 68.75 + }, + "align": "left" + }, + "Porrectus3": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M309.375 355.78c-48.96-16.666-109.115-55.468-180.47-116.405C79.428 198.23 19.793 134.687-50 48.75V-70C20 40 94.104 103.79 135.25 148.063 190 200 230 230 288.28 258.906c4.168 2.083 8.334 3.125 12.5 3.125 12.5 0 21.355-10.937 26.564-32.81v114.06c0 9.376-3.386 14.063-10.156 14.064-2.084 0-4.688-.522-7.813-1.563z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 377.343994140625, + "height": 427.3450012207031 + }, + "origin": { + "x": 50, + "y": 70 + }, + "align": "left" + }, + "Porrectus4": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M350 453.438c-52.754-22.397-120-77.345-201.74-164.844C90.87 227.656 24.784 147.708-50 48.75V-70C-8.84-1.25 58.406 86.51 151.74 193.28c60.868 69.793 119.13 124.22 174.782 163.282 5.797 3.646 11.014 5.47 15.652 5.47 12.173 0 21.45-11.72 27.826-35.157V441.72c0 9.373-3.19 14.06-9.565 14.06-2.9 0-6.377-.78-10.435-2.342z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 420, + "height": 525.780029296875 + }, + "origin": { + "x": 50, + "y": 70 + }, + "align": "left" + }, + "PunctumCavum": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M0-60.906c33.333 0 50 9.635 50 28.906v94.53C39.062 51.595 22.396 46.126 0 46.126s-39.063 5.47-50 16.406V-32c0-19.27 16.667-28.906 50-28.906z" + }, { + "type": "negative", + "data": "M.08-42.56c9.585.206 20.126.53 27.954 6.822 4.96 3.9 4.71 10.792 4.574 16.482v51.278C22.09 27.066 7.283 26.072.168 26.01c-7.72.23-21.895.935-32.616 4.674.04-19.197-.083-38.395.064-57.59.567-7.5 7.834-12.33 14.62-13.774 5.818-1.498 11.857-1.86 17.844-1.88z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 123.43799591064453 + }, + "origin": { + "x": 50, + "y": 60.90599822998047 + }, + "align": "left" + }, + "PunctumQuadratum": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M0-60.906c33.333 0 50 9.635 50 28.906v94.53C39.062 51.595 22.396 46.126 0 46.126s-39.063 5.47-50 16.406V-32c0-19.27 16.667-28.906 50-28.906z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 123.43799591064453 + }, + "origin": { + "x": 50, + "y": 60.90599822998047 + }, + "align": "left" + }, + "PunctumQuadratumAscLiquescent": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M-50 43.688V-61c4.167 7.292 12.76 10.938 25.78 10.938 9.376 0 20.053-1.563 32.032-4.688C31.773-60.48 45.833-71.677 50-88.344v117.97C43.75 42.645 32.812 51.5 17.187 56.186-.52 61.398-15.886 64-28.906 64-42.97 64-50 57.23-50 43.687z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 152.343994140625 + }, + "origin": { + "x": 50, + "y": 88.34400177001953 + }, + "align": "left" + }, + "PunctumQuadratumDesLiquescent": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M-50-56.03c0-13.022 7.03-19.532 21.094-19.532 13.02 0 28.385 2.604 46.093 7.812C32.813-63.583 43.75-54.73 50-41.187V76C45.833 59.854 31.77 48.656 7.812 42.406c-11.98-3.125-22.656-4.687-32.03-4.687-13.022 0-21.615 3.905-25.782 11.718v-105.47z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 151.56199645996094 + }, + "origin": { + "x": 50, + "y": 75.56199645996094 + }, + "align": "left" + }, + "PunctumInclinatum": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M0-75.78L50 0 0 75-50 0 0-75.78z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 150.77999877929688 + }, + "origin": { + "x": 50, + "y": 75.77999877929688 + }, + "align": "left" + }, + "PunctumInclinatumLiquescent": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M 0,-53.164062 35,-0.1171875 0,52.382812 -35,-0.1171875 0,-53.164062 z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 70, + "height": 105.546 + }, + "origin": { + "x": 35, + "y": 53.164062 + }, + "align": "left" + }, + "Quilisma": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M-50 34.938V-51c5.73 20.833 13.02 31.25 21.875 31.25 7.813 0 12.5-15.625 14.063-46.875 3.645 12.5 6.9 21.224 9.765 26.172s6.9 7.422 12.11 7.422c5.208 0 9.374-14.324 12.5-42.97 5.73 22.917 10.677 34.375 14.843 34.375 5.73 0 10.677-15.885 14.844-47.656v100c0 17.707-3.125 26.56-9.375 26.56-4.688 0-9.115-5.988-13.28-17.968-2.085 21.875-8.074 32.813-17.97 32.813-7.813 0-16.146-7.292-25-21.875-4.688 20.312-10.677 30.47-17.97 30.47-5.207 0-9.244-2.605-12.108-7.814C-48.568 47.698-50 41.708-50 34.938z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 150 + }, + "origin": { + "x": 50, + "y": 89.28199768066406 + }, + "align": "left" + }, + "TerminatingAscLiquescent": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M-9.375 40.22c0-11.98-4.948-17.97-14.844-17.97-10.936 0-19.53 3.646-25.78 10.938v-53.126c0-6.77 2.604-12.76 7.813-17.968 5.208-5.21 10.677-8.594 16.406-10.157 2.603-.52 5.207-.78 7.81-.78 3.647 0 7.032.78 10.157 2.343C-2.603-43.896 0-39.73 0-34V73.03h-9.375V40.22z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 49.999000549316406, + "height": 121.87299346923828 + }, + "origin": { + "x": 49.999000549316406, + "y": 48.842994689941406 + }, + "align": "right" + }, + "TerminatingDesLiquescent": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M-9.375-48.156V-80.97H0V26.845c0 5.73-2.604 9.896-7.813 12.5-3.125 1.562-6.51 2.343-10.156 2.343-2.603 0-5.207-.26-7.81-.78-5.73-1.563-11.2-4.95-16.407-10.157C-47.398 25.542-50 19.292-50 12v-52.344c6.25 7.292 14.844 10.938 25.78 10.938 9.897 0 14.845-6.25 14.845-18.75z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 50, + "height": 122.65800476074219 + }, + "origin": { + "x": 50, + "y": 80.97000122070312 + }, + "align": "right" + }, + "VerticalEpisemaAbove": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M-8-80H8L4 0h-8l-4-80z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 16, + "height": 80 + }, + "origin": { + "x": 8, + "y": 80 + }, + "align": "left" + }, + "VerticalEpisemaBelow": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M-8 80H8L4 0h-8l-4 80z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 16, + "height": 80 + }, + "origin": { + "x": 8, + "y": 0 + }, + "align": "left" + }, + "VirgaLong": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M50-38v285.156c0 6.77-2.344 10.937-7.03 12.5-1.564 0-2.605-.78-3.126-2.344-.52-1.562-.782-10.156-.782-25.78V54.186C29.168 45.334 16.146 40.907 0 40.907c-22.917 0-39.583 5.208-50 15.624V-38c0-19.27 16.667-28.906 50-28.906S50-57.27 50-38z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 326.56201171875 + }, + "origin": { + "x": 50, + "y": 66.90599822998047 + }, + "align": "left" + }, + "VirgaShort": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M50-38v211.72c0 7.29-2.344 11.457-7.03 12.5-1.564 0-2.606-.783-3.126-2.345-.52-1.563-.782-10.156-.782-25.78V54.187C29.167 45.332 16.146 40.906 0 40.906c-22.917 0-39.583 5.21-50 15.625V-38c0-19.27 16.667-28.906 50-28.906S50-57.27 50-38z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 100, + "height": 253.12600708007812 + }, + "origin": { + "x": 50, + "y": 66.90599822998047 + }, + "align": "left" + }, + "Virgula": { + "svgSrc": "", + "paths": [{ + "type": "positive", + "data": "M8.178-55.66c0-22.137 12.092-33.2 36.287-33.2 11.835 0 23.53 5.66 35.108 16.98C91.15-60.547 96.94-41.766 96.94-15.534c0 53.515-31.646 87.487-94.937 101.895-2.048-2.06-3.077-5.146-3.077-9.273 0-1.03.247-1.8.76-2.316 42.71-19.027 64.075-41.678 64.075-67.92 0-11.322-2.325-20.326-6.945-27.016-4.62-6.69-9.52-11.052-14.676-13.11-5.147-2.048-11.836-3.85-20.07-5.403C12.81-39.707 8.18-45.37 8.18-55.66z" + }], + "bounds": { + "x": 0, + "y": 0, + "width": 98.01399993896484, + "height": 175.2209930419922 + }, + "origin": { + "x": 1.0739939212799072, + "y": 88.86000061035156 + }, + "align": "left" + } + }; + +/***/ }, +/* 4 */ +/***/ function(module, exports, __webpack_require__) { + + 'use strict'; + + Object.defineProperty(exports, "__esModule", { + value: true + }); + exports.ChantNotationElement = exports.Annotation = exports.DropCap = exports.Lyric = exports.LyricType = exports.TextElement = exports.CurlyBraceVisualizer = exports.RoundBraceVisualizer = exports.GlyphVisualizer = exports.VirgaLineVisualizer = exports.NeumeLineVisualizer = exports.DividerLineVisualizer = exports.ChantLayoutElement = exports.ChantContext = exports.TextMeasuringStrategy = exports.QuickSvg = exports.GlyphCode = undefined; + + var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } }; + + var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }(); // + // Author(s): + // Fr. Matthew Spencer, OSJ + // + // Copyright (c) 2008-2016 Fr. Matthew Spencer, OSJ + // + // Permission is hereby granted, free of charge, to any person obtaining a copy + // of this software and associated documentation files (the "Software"), to deal + // in the Software without restriction, including without limitation the rights + // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + // copies of the Software, and to permit persons to whom the Software is + // furnished to do so, subject to the following conditions: + // + // The above copyright notice and this permission notice shall be included in + // all copies or substantial portions of the Software. + // + // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + // THE SOFTWARE. + // + + var _Exsurge = __webpack_require__(1); + + var _Exsurge2 = __webpack_require__(3); + + var _Exsurge3 = __webpack_require__(2); + + function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; } + + function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; } + + function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } + + // load in the web font for special chant characters here: + var __exsurgeCharactersFont = __webpack_require__(5); + + var GlyphCode = exports.GlyphCode = { + + None: "None", + + AcuteAccent: "AcuteAccent", + Stropha: "Stropha", + StrophaLiquescent: "StrophaLiquescent", + + BeginningAscLiquescent: "BeginningAscLiquescent", + BeginningDesLiquescent: "BeginningDesLiquescent", + + CustosDescLong: "CustosDescLong", + CustosDescShort: "CustosDescShort", + CustosLong: "CustosLong", + CustosShort: "CustosShort", + + // clefs and other markings + DoClef: "DoClef", + FaClef: "FaClef", + Flat: "Flat", + Mora: "Mora", + Natural: "Natural", + OriscusAsc: "OriscusAsc", + OriscusDes: "OriscusDes", + OriscusLiquescent: "OriscusLiquescent", + + PodatusLower: "PodatusLower", + PodatusUpper: "PodatusUpper", + + Porrectus1: "Porrectus1", // 1 staff line difference, + Porrectus2: "Porrectus2", // 2 lines difference, etc... + Porrectus3: "Porrectus3", + Porrectus4: "Porrectus4", + + PunctumCavum: "PunctumCavum", + PunctumQuadratum: "PunctumQuadratum", + PunctumQuadratumAscLiquescent: "PunctumQuadratumAscLiquescent", + PunctumQuadratumDesLiquescent: "PunctumQuadratumDesLiquescent", + PunctumInclinatum: "PunctumInclinatum", + PunctumInclinatumLiquescent: "PunctumInclinatumLiquescent", + Quilisma: "Quilisma", + + TerminatingAscLiquescent: "TerminatingAscLiquescent", + TerminatingDesLiquescent: "TerminatingDesLiquescent", + VerticalEpisemaAbove: "VerticalEpisemaAbove", + VerticalEpisemaBelow: "VerticalEpisemaBelow", + VirgaLong: "VirgaLong", + VirgaShort: "VirgaShort", + Virgula: "Virgula", + + UpperBrace: "UpperBrace" + }; // GlyphCode + + var QuickSvg = exports.QuickSvg = { + + // namespaces + ns: 'http://www.w3.org/2000/svg', + xmlns: 'http://www.w3.org/2000/xmlns/', + xlink: 'http://www.w3.org/1999/xlink', + + // create the root level svg object + svg: function svg(width, height) { + var node = document.createElementNS(this.ns, 'svg'); + + node.setAttribute('xmlns', this.ns); + node.setAttribute('version', '1.1'); + node.setAttributeNS(this.xmlns, 'xmlns:xlink', this.xlink); + + node.setAttribute('width', width); + node.setAttribute('height', height); + + // create the defs element + var defs = document.createElementNS(this.ns, 'defs'); + node.appendChild(defs); + + node.defs = defs; + + node.clearNotations = function () { + // clear out all children except defs + node.removeChild(defs); + + while (node.hasChildNodes()) { + node.removeChild(node.lastChild); + }node.appendChild(defs); + }; + + return node; + }, + + rect: function rect(width, height) { + var node = document.createElementNS(this.ns, 'rect'); + + node.setAttribute('width', width); + node.setAttribute('height', height); + + return node; + }, + + line: function line(x1, y1, x2, y2) { + var node = document.createElementNS(this.ns, 'line'); + + node.setAttribute('x1', x1); + node.setAttribute('y1', y1); + node.setAttribute('x2', x2); + node.setAttribute('y2', y2); + + return node; + }, + + g: function g() { + var node = document.createElementNS(this.ns, 'g'); + + return node; + }, + + text: function text() { + var node = document.createElementNS(this.ns, 'text'); + + return node; + }, + + tspan: function tspan(str) { + var node = document.createElementNS(this.ns, 'tspan'); + node.textContent = str; + + return node; + }, + + // nodeRef should be the id of the object in defs (without the #) + use: function use(nodeRef) { + var node = document.createElementNS(this.ns, 'use'); + node.setAttributeNS(this.xlink, "xlink:href", '#' + nodeRef); + + return node; + }, + + createFragment: function createFragment(name, attributes, child) { + if (child === undefined || child === null) child = ''; + + var fragment = '<' + name + ' '; + + for (var attr in attributes) { + if (attributes.hasOwnProperty(attr)) fragment += attr + '="' + attributes[attr] + '" '; + } + + fragment += '>' + child + ''; + + return fragment; + }, + + parseFragment: function parseFragment(fragment) { + + // create temporary holder + var well = document.createElement('svg'); + + // act as a setter if svg is given + if (fragment) { + + var container = this.g(); + + // dump raw svg + // do this to allow the browser to automatically create svg nodes? + well.innerHTML = '' + fragment.replace(/\n/, '').replace(/<(\w+)([^<]+?)\/>/g, '<$1$2>') + ''; + + // transplant nodes + for (var i = 0, il = well.firstChild.childNodes.length; i < il; i++) { + container.appendChild(well.firstChild.firstChild); + }return container; + } + }, + + translate: function translate(node, x, y) { + node.setAttribute('transform', 'translate(' + x + ',' + y + ')'); + return node; + }, + + scale: function scale(node, sx, sy) { + node.setAttribute('transform', 'scale(' + sx + ',' + sy + ')'); + return node; + } + }; + + var TextMeasuringStrategy = exports.TextMeasuringStrategy = { + // shapes + Svg: 0, + Canvas: 1 + }; + + /* + * ChantContext + */ + + var ChantContext = exports.ChantContext = function () { + function ChantContext() { + var textMeasuringStrategy = arguments.length <= 0 || arguments[0] === undefined ? TextMeasuringStrategy.Svg : arguments[0]; + + _classCallCheck(this, ChantContext); + + this.textMeasuringStrategy = textMeasuringStrategy; + this.defs = {}; + + // font styles + this.lyricTextSize = 16; // in points? + this.lyricTextFont = "'Palatino Linotype', 'Book Antiqua', Palatino, serif"; + this.lyricTextColor = "#000"; + + this.dropCapTextSize = 64; + this.dropCapTextFont = this.lyricTextFont; + this.dropCapTextColor = this.lyricTextColor; + + this.annotationTextSize = 13; + this.annotationTextFont = this.lyricTextFont; + this.annotationTextColor = this.lyricTextColor; + + // everything depends on the scale of the punctum + this.glyphPunctumWidth = _Exsurge2.Glyphs.PunctumQuadratum.bounds.width; + this.glyphPunctumHeight = _Exsurge2.Glyphs.PunctumQuadratum.bounds.height; + + // fixme: for now, we just set these using the glyph scales as noted above, presuming a + // staff line size of 0.5 in. Really what we should do is scale the punctum size based + // on the text metrics, right? 1 punctum ~ x height size? + this.glyphScaling = 1.0 / 16.0; + + this.staffInterval = this.glyphPunctumWidth * this.glyphScaling; + + // setup the line weights for the various elements. + // we + this.staffLineWeight = Math.round(this.glyphPunctumWidth * this.glyphScaling / 8); + this.neumeLineWeight = this.staffLineWeight; // the weight of connecting lines in the glyphs. + this.dividerLineWeight = this.neumeLineWeight; // of quarter bar, half bar, etc. + this.episemaLineWeight = this.neumeLineWeight; // of horizontal episemae + + // for keeping track of the clef + this.activeClef = null; + + this.neumeLineColor = "#000"; + this.staffLineColor = "#000"; + this.dividerLineColor = "#000"; + + this.defaultLanguage = new _Exsurge3.Latin(); + + this.canvas = document.createElement("canvas"); + this.canvasCtxt = this.canvas.getContext("2d"); + + // calculate the pixel ratio for drawing to a canvas + var dpr = window.devicePixelRatio || 1.0; + var bsr = this.canvasCtxt.webkitBackingStorePixelRatio || this.canvasCtxt.mozBackingStorePixelRatio || this.canvasCtxt.msBackingStorePixelRatio || this.canvasCtxt.oBackingStorePixelRatio || this.canvasCtxt.backingStorePixelRatio || 1.0; + + this.pixelRatio = dpr / bsr; + + this.canvasCtxt.setTransform(this.pixelRatio, 0, 0, this.pixelRatio, 0, 0); + + if (textMeasuringStrategy === TextMeasuringStrategy.Svg) { + this.svgTextMeasurer = QuickSvg.svg(1, 1); + this.svgTextMeasurer.setAttribute('id', "TextMeasurer"); + document.querySelector('body').appendChild(this.svgTextMeasurer); + } + + // measure the size of a hyphen for the lyrics + var hyphen = new Lyric(this, "-", LyricType.SingleSyllable); + this.hyphenWidth = hyphen.bounds.width; + + this.minLyricWordSpacing = this.hyphenWidth; + + this.intraNeumeSpacing = this.staffInterval / 2.0; + + // for connecting neume syllables... + this.syllableConnector = '-'; + + this.drawGuides = false; + this.drawDebuggingBounds = true; + + // we keep track of where we are in processing notations, so that + // we can maintain the context for notations to know about. + // + // these are only gauranteed to be valid during the performLayout phase! + this.activeNotations = null; + this.currNotationIndex = -1; + + // chant notation elements are normally separated by a minimum fixed amount of space + // on the staff line. It can happen, however, that two text elements are almost close + // enough to merge, only to be separated much more by the required hyphen (or other + // connecting string). + // + // This tolerance value allows a little bit of flexibility to merge two close lyrical + // elements, thus bringing the chant notation elements a bit closer than otherwise + // would be normally allowed. + // + // condensing tolerance is a percentage value (0.0-1.0, inclusive) that indicates + // how much the default spacing can shrink. E.g., a value of 0.80 allows the layout + // engine to separate two glyphs by only 80% of the normal inter-neume spacing value. + // + // fixme: condensing tolerance is not implemented yet! + this.condensingTolerance = 0.9; + + // if auto color is true, then exsurge tries to automatically colorize + // some elements of the chant (directives become rubric color, etc.) + this.autoColor = true; + + this.insertFontsInDoc(); + } + + _createClass(ChantContext, [{ + key: 'calculateHeightFromStaffPosition', + value: function calculateHeightFromStaffPosition(staffPosition) { + return -staffPosition * this.staffInterval; + } + }, { + key: 'insertFontsInDoc', + value: function insertFontsInDoc() { + + var styleElement = document.getElementById('exsurge-fonts'); + + if (styleElement === null) { + // create it since it doesn't exist yet. + styleElement = document.createElement('style'); + styleElement.id = 'exsurge-fonts'; + + styleElement.appendChild(document.createTextNode("@font-face{font-family: 'Exsurge Characters';font-weight: normal;font-style: normal;src: url(" + __exsurgeCharactersFont + ") format('opentype');}")); + + document.head.appendChild(styleElement); + } + } + + // returns the next neume starting at this.currNotationIndex, or null + // if there isn't a neume after this one... + + }, { + key: 'findNextNeume', + value: function findNextNeume() { + + if (typeof this.currNotationIndex === 'undefined') throw "findNextNeume() called without a valid currNotationIndex set"; + + for (var i = this.currNotationIndex + 1; i < this.notations.length; i++) { + var notation = this.notations[i]; + + if (notation.isNeume) return notation; + } + + return null; + } + }, { + key: 'setCanvasSize', + value: function setCanvasSize(width, height) { + this.canvas.width = width * this.pixelRatio; + this.canvas.height = height * this.pixelRatio; + this.canvas.style.width = width + "px"; + this.canvas.style.height = height + "px"; + + this.canvasCtxt.setTransform(this.pixelRatio, 0, 0, this.pixelRatio, 0, 0); + } + }]); + + return ChantContext; + }(); + + /* + * ChantLayoutElement + */ + + + var ChantLayoutElement = exports.ChantLayoutElement = function () { + function ChantLayoutElement() { + _classCallCheck(this, ChantLayoutElement); + + this.bounds = new _Exsurge.Rect(); + this.origin = new _Exsurge.Point(0, 0); + + this.selected = false; + this.highlighted = false; + } + + // draws the element on an html5 canvas + + + _createClass(ChantLayoutElement, [{ + key: 'draw', + value: function draw(ctxt) {} + + // returns svg code for the element, used for printing support + + }, { + key: 'createSvgFragment', + value: function createSvgFragment(ctxt) { + throw "ChantLayout Elements must implement createSvgFragment(ctxt)"; + } + }]); + + return ChantLayoutElement; + }(); + + var DividerLineVisualizer = exports.DividerLineVisualizer = function (_ChantLayoutElement) { + _inherits(DividerLineVisualizer, _ChantLayoutElement); + + function DividerLineVisualizer(ctxt, staffPosition0, staffPosition1) { + _classCallCheck(this, DividerLineVisualizer); + + var _this = _possibleConstructorReturn(this, Object.getPrototypeOf(DividerLineVisualizer).call(this)); + + var y0 = ctxt.calculateHeightFromStaffPosition(staffPosition0); + var y1 = ctxt.calculateHeightFromStaffPosition(staffPosition1); + + if (y0 > y1) { + var temp = y0; + y0 = y1; + y1 = temp; + } + + _this.bounds.x = 0; + _this.bounds.y = y0; + _this.bounds.width = ctxt.dividerLineWeight; + _this.bounds.height = y1 - y0; + + _this.origin.x = _this.bounds.width / 2; + _this.origin.y = y0; + return _this; + } + + _createClass(DividerLineVisualizer, [{ + key: 'draw', + value: function draw(ctxt) { + var canvasCtxt = ctxt.canvasCtxt; + + canvasCtxt.lineWidth = this.bounds.width; + canvasCtxt.strokeStyle = ctxt.dividerLineColor; + + canvasCtxt.beginPath(); + canvasCtxt.moveTo(this.bounds.x - this.origin.x, this.bounds.y); + canvasCtxt.lineTo(this.bounds.x - this.origin.x, this.bounds.y + this.bounds.height); + canvasCtxt.stroke(); + } + }, { + key: 'createSvgFragment', + value: function createSvgFragment(ctxt) { + + return QuickSvg.createFragment('rect', { + 'x': this.bounds.x, + 'y': this.bounds.y, + 'width': ctxt.dividerLineWeight, + 'height': this.bounds.height, + 'fill': ctxt.dividerLineColor, + 'class': 'dividerLine' + }); + } + }]); + + return DividerLineVisualizer; + }(ChantLayoutElement); + + var NeumeLineVisualizer = exports.NeumeLineVisualizer = function (_ChantLayoutElement2) { + _inherits(NeumeLineVisualizer, _ChantLayoutElement2); + + function NeumeLineVisualizer(ctxt, note0, note1, hanging) { + _classCallCheck(this, NeumeLineVisualizer); + + var _this2 = _possibleConstructorReturn(this, Object.getPrototypeOf(NeumeLineVisualizer).call(this)); + + var staffPosition0 = note0.staffPosition; + var staffPosition1 = note1.staffPosition; + + // note0 should be the upper one for our calculations here + if (staffPosition0 < staffPosition1) { + var temp = staffPosition0; + staffPosition0 = staffPosition1; + staffPosition1 = temp; + } + + var y0 = ctxt.calculateHeightFromStaffPosition(staffPosition0); + var y1 = 0; + + if (hanging) { + + // if the difference between the notes is only one, and the upper + // note is on a line, and the lower note is within the four staff lines, + // then our hanging line goes past the lower note by a whole + // staff interval + if (staffPosition0 - staffPosition1 === 1 && Math.abs(staffPosition0) % 2 === 1 && staffPosition1 > -3) staffPosition1--; + + y1 += ctxt.glyphPunctumHeight * ctxt.glyphScaling / 2.2; + } + + y1 += ctxt.calculateHeightFromStaffPosition(staffPosition1); + + _this2.bounds.x = 0; + _this2.bounds.y = y0; + _this2.bounds.width = ctxt.neumeLineWeight; + _this2.bounds.height = y1 - y0; + + _this2.origin.x = 0; + _this2.origin.y = 0; + return _this2; + } + + _createClass(NeumeLineVisualizer, [{ + key: 'draw', + value: function draw(ctxt) { + var canvasCtxt = ctxt.canvasCtxt; + + canvasCtxt.lineWidth = this.bounds.width; + canvasCtxt.strokeStyle = ctxt.neumeLineColor; + + canvasCtxt.beginPath(); + + // since the canvas context draws strokes centered on the path + // and neume lines are supposed to be draw left aligned, + // we need to offset the line by half the line width. + var x = this.bounds.x + this.bounds.width / 2; + + canvasCtxt.moveTo(x, this.bounds.y); + canvasCtxt.lineTo(x, this.bounds.y + this.bounds.height); + canvasCtxt.stroke(); + } + }, { + key: 'createSvgFragment', + value: function createSvgFragment(ctxt) { + + return QuickSvg.createFragment('rect', { + 'x': this.bounds.x, + 'y': this.bounds.y, + 'width': ctxt.neumeLineWeight, + 'height': this.bounds.height, + 'fill': ctxt.neumeLineColor, + 'class': 'neumeLine' + }); + } + }]); + + return NeumeLineVisualizer; + }(ChantLayoutElement); + + var VirgaLineVisualizer = exports.VirgaLineVisualizer = function (_ChantLayoutElement3) { + _inherits(VirgaLineVisualizer, _ChantLayoutElement3); + + function VirgaLineVisualizer(ctxt, note) { + _classCallCheck(this, VirgaLineVisualizer); + + var _this3 = _possibleConstructorReturn(this, Object.getPrototypeOf(VirgaLineVisualizer).call(this)); + + var staffPosition = note.staffPosition; + + var y0 = ctxt.calculateHeightFromStaffPosition(staffPosition); + var y1; + + if (Math.abs(staffPosition % 2) === 0) y1 = y0 + ctxt.staffInterval * 1.8;else y1 = y0 + ctxt.staffInterval * 2.7; + + _this3.bounds.x = 0; + _this3.bounds.y = y0; + _this3.bounds.width = ctxt.neumeLineWeight; + _this3.bounds.height = y1 - y0; + + _this3.origin.x = 0; + _this3.origin.y = 0; + return _this3; + } + + _createClass(VirgaLineVisualizer, [{ + key: 'draw', + value: function draw(ctxt) { + var canvasCtxt = ctxt.canvasCtxt; + + canvasCtxt.lineWidth = this.bounds.width; + canvasCtxt.strokeStyle = ctxt.neumeLineColor; + + canvasCtxt.beginPath(); + canvasCtxt.moveTo(this.bounds.x, this.bounds.y); + canvasCtxt.lineTo(this.bounds.x, this.bounds.y + this.bounds.height); + canvasCtxt.stroke(); + } + }, { + key: 'createSvgFragment', + value: function createSvgFragment(ctxt) { + + return QuickSvg.createFragment('rect', { + 'x': this.bounds.x, + 'y': this.bounds.y, + 'width': ctxt.neumeLineWeight, + 'height': this.bounds.height, + 'fill': ctxt.neumeLineColor, + 'class': 'neumeLine' + }); + } + }]); + + return VirgaLineVisualizer; + }(ChantLayoutElement); + + var GlyphVisualizer = exports.GlyphVisualizer = function (_ChantLayoutElement4) { + _inherits(GlyphVisualizer, _ChantLayoutElement4); + + function GlyphVisualizer(ctxt, glyphCode) { + _classCallCheck(this, GlyphVisualizer); + + var _this4 = _possibleConstructorReturn(this, Object.getPrototypeOf(GlyphVisualizer).call(this)); + + _this4.glyph = null; + + _this4.setGlyph(ctxt, glyphCode); + return _this4; + } + + _createClass(GlyphVisualizer, [{ + key: 'setGlyph', + value: function setGlyph(ctxt, glyphCode) { + + if (this.glyphCode === glyphCode) return; + + if (typeof glyphCode === 'undefined' || glyphCode === null || glyphCode === "") this.glyphCode = GlyphCode.None;else this.glyphCode = glyphCode; + + this.glyph = _Exsurge2.Glyphs[this.glyphCode]; + + // if this glyph hasn't been used yet, then load it up in the defs section for sharing + if (!ctxt.defs.hasOwnProperty(this.glyphCode)) { + var glyphSrc = this.glyph.svgSrc; + + // create the ref + ctxt.defs[this.glyphCode] = QuickSvg.createFragment('g', { + id: this.glyphCode, + 'class': 'glyph', + transform: 'scale(' + ctxt.glyphScaling + ')' + }, glyphSrc); + } + + this.align = this.glyph.align; + + this.origin.x = this.glyph.origin.x * ctxt.glyphScaling; + this.origin.y = this.glyph.origin.y * ctxt.glyphScaling; + + this.bounds.x = 0; + this.bounds.y = -this.origin.y; + this.bounds.width = this.glyph.bounds.width * ctxt.glyphScaling; + this.bounds.height = this.glyph.bounds.height * ctxt.glyphScaling; + } + }, { + key: 'setStaffPosition', + value: function setStaffPosition(ctxt, staffPosition) { + this.bounds.y += ctxt.calculateHeightFromStaffPosition(staffPosition); + } + }, { + key: 'draw', + value: function draw(ctxt) { + var canvasCtxt = ctxt.canvasCtxt; + + var x = this.bounds.x + this.origin.x; + var y = this.bounds.y + this.origin.y; + canvasCtxt.translate(x, y); + canvasCtxt.scale(ctxt.glyphScaling, ctxt.glyphScaling); + + for (var i = 0; i < this.glyph.paths.length; i++) { + var path = this.glyph.paths[i]; + canvasCtxt.fillStyle = ctxt.neumeLineColor; + canvasCtxt.fill(new Path2D(path.data)); + } + + canvasCtxt.scale(1.0 / ctxt.glyphScaling, 1.0 / ctxt.glyphScaling); + canvasCtxt.translate(-x, -y); + } + }, { + key: 'createSvgFragment', + value: function createSvgFragment(ctxt) { + + return QuickSvg.createFragment('use', { + 'xlink:href': '#' + this.glyphCode, + x: this.bounds.x + this.origin.x, + y: this.bounds.y + this.origin.y + }); + } + }]); + + return GlyphVisualizer; + }(ChantLayoutElement); + + var RoundBraceVisualizer = exports.RoundBraceVisualizer = function (_ChantLayoutElement5) { + _inherits(RoundBraceVisualizer, _ChantLayoutElement5); + + function RoundBraceVisualizer(ctxt, x1, x2, y, isAbove) { + _classCallCheck(this, RoundBraceVisualizer); + + var _this5 = _possibleConstructorReturn(this, Object.getPrototypeOf(RoundBraceVisualizer).call(this)); + + if (x1 > x2) { + // swap the xs + var temp = x1; + x1 = x2; + x2 = temp; + } + + _this5.isAbove = isAbove; + _this5.braceHeight = ctxt.staffInterval / 2; + + _this5.bounds = new _Exsurge.Rect(x1, y, x2 - x1, _this5.braceHeight); + + _this5.origin.x = 0; + _this5.origin.y = 0; + return _this5; + } + + _createClass(RoundBraceVisualizer, [{ + key: 'createSvgFragment', + value: function createSvgFragment(ctxt) { + var fragment = QuickSvg.createFragment('path', { + 'd': this.generatePathString(), + 'stroke': ctxt.neumeLineColor, + 'stroke-width': ctxt.staffLineWeight + 'px', + 'fill': 'none', + 'class': 'brace' + }); + + if (this.acuteAccent) { + + fragment += this.acuteAccent.createSvgFragment(ctxt); + + return QuickSvg.createFragment('g', { + 'class': 'accentedBrace' + }, fragment); + } else return fragment; + } + + // returns svg path d string + + }, { + key: 'generatePathString', + value: function generatePathString() { + + var x1 = this.bounds.x; + var x2 = this.bounds.right(); + var width = this.bounds.width; + var y, dx, dy; + + if (this.isAbove) { + y = this.bounds.bottom(); + dx = width / 6; + dy = -width / 6; + } else { + y = this.bounds.y; + dx = width / 6; + dy = width / 6; + } + + //Calculate Control Points of path, + var cx1 = x1 + dx; + var cy = y + dy; + var cx2 = x2 - dx; + + // two decimal points should be enough, but if we need more precision, we can + // up it here. + var dp = 2; + return "M " + x1.toFixed(dp) + " " + y.toFixed(dp) + " C " + cx1.toFixed(dp) + " " + cy.toFixed(dp) + " " + cx2.toFixed(dp) + " " + cy.toFixed(dp) + " " + x2.toFixed(dp) + " " + y.toFixed(dp); + } + }]); + + return RoundBraceVisualizer; + }(ChantLayoutElement); + + var CurlyBraceVisualizer = exports.CurlyBraceVisualizer = function (_ChantLayoutElement6) { + _inherits(CurlyBraceVisualizer, _ChantLayoutElement6); + + function CurlyBraceVisualizer(ctxt, x1, x2, y) { + var isAbove = arguments.length <= 4 || arguments[4] === undefined ? true : arguments[4]; + var addAcuteAccent = arguments.length <= 5 || arguments[5] === undefined ? false : arguments[5]; + + _classCallCheck(this, CurlyBraceVisualizer); + + var _this6 = _possibleConstructorReturn(this, Object.getPrototypeOf(CurlyBraceVisualizer).call(this)); + + if (x1 > x2) { + // swap the xs + var temp = x1; + x1 = x2; + x2 = temp; + } + + _this6.isAbove = isAbove; + _this6.braceHeight = ctxt.staffInterval / 2; + + // y is the actual vertical start of the brace (left hand side) + // thus for a brace over notes, bounds.y is the bottom of brace, + // but for a brace under the notes, y is simply the y passed in. + if (isAbove) y -= _this6.braceHeight; + + var bounds = new _Exsurge.Rect(x1, y, x2 - x1, _this6.braceHeight); + + if (addAcuteAccent && isAbove) { + + _this6.acuteAccent = new GlyphVisualizer(ctxt, GlyphCode.AcuteAccent); + _this6.acuteAccent.bounds.x += bounds.x + (x2 - x1) / 2; + _this6.acuteAccent.bounds.y += bounds.y - ctxt.staffInterval / 4; + + bounds.union(_this6.acuteAccent.bounds); + } + + _this6.bounds = bounds; + + _this6.origin.x = 0; + _this6.origin.y = 0; + return _this6; + } + + _createClass(CurlyBraceVisualizer, [{ + key: 'createSvgFragment', + value: function createSvgFragment(ctxt) { + var fragment = QuickSvg.createFragment('path', { + 'd': this.generatePathString(), + 'stroke': ctxt.neumeLineColor, + 'stroke-width': ctxt.staffLineWeight + 'px', + 'fill': 'none', + 'class': 'brace' + }); + + if (this.acuteAccent) { + + fragment += this.acuteAccent.createSvgFragment(ctxt); + + return QuickSvg.createFragment('g', { + 'class': 'accentedBrace' + }, fragment); + } else return fragment; + } + + // code below inspired by: https://gist.github.com/alexhornbake + // optimized for braces that are only drawn horizontally. + // returns svg path d string + + }, { + key: 'generatePathString', + value: function generatePathString() { + + var q = 0.6; // .5 is normal, higher q = more expressive bracket + + var x1 = this.bounds.x; + var x2 = this.bounds.right(); + var width = this.bounds.width; + var y, h; + + if (this.isAbove) { + y = this.bounds.bottom(); + h = -this.braceHeight; + } else { + y = this.bounds.y; + h = this.braceHeight; + } + + // calculate Control Points of path + var qy1 = y + q * h; + var qx2 = x1 + .25 * width; + var qy2 = y + (1 - q) * h; + var tx1 = x1 + .5 * width; + var ty1 = y + h; + var qy3 = y + q * h; + var qx4 = x1 + .75 * width; + var qy4 = y + (1 - q) * h; + + // two decimal points should be enough, but if we need more precision, we can + // up it here. + var dp = 2; + return "M " + x1.toFixed(dp) + " " + y.toFixed(dp) + " Q " + x1.toFixed(dp) + " " + qy1.toFixed(dp) + " " + qx2.toFixed(dp) + " " + qy2.toFixed(dp) + " T " + tx1.toFixed(dp) + " " + ty1.toFixed(dp) + " M " + x2.toFixed(dp) + " " + y.toFixed(dp) + " Q " + x2.toFixed(dp) + " " + qy3.toFixed(dp) + " " + qx4.toFixed(dp) + " " + qy4.toFixed(dp) + " T " + tx1.toFixed(dp) + " " + ty1.toFixed(dp); + } + }]); + + return CurlyBraceVisualizer; + }(ChantLayoutElement); + + var TextSpan = function TextSpan(text, properties) { + if (typeof properties === 'undefined' || properties === null) properties = ""; + + this.text = text; + this.properties = properties; + }; + + var boldMarkup = "*"; + var italicMarkup = "_"; + var redMarkup = "^"; + var smallCapsMarkup = "%"; + + function MarkupStackFrame(symbol, startIndex, properties) { + this.symbol = symbol; + this.startIndex = startIndex; + this.properties = properties; + } + + MarkupStackFrame.createStackFrame = function (symbol, startIndex) { + + var properties = ""; + + switch (symbol) { + case boldMarkup: + properties = 'font-weight:bold;'; + break; + case italicMarkup: + properties = 'font-style:italic;'; + break; + case redMarkup: + properties = 'fill:#f00;'; // SVG text color is set by the fill property + break; + case smallCapsMarkup: + properties = "font-variant:small-caps;font-feature-settings:'smcp';-webkit-font-feature-settings:'smcp';"; + break; + } + + return new MarkupStackFrame(symbol, startIndex, properties); + }; + + // for escaping html strings before they go into the svgs + // adapted from http://stackoverflow.com/a/12034334/5720160 + var __subsForTspans = { + "&": "&", + "<": "<", + ">": ">" + }; + + var TextElement = exports.TextElement = function (_ChantLayoutElement7) { + _inherits(TextElement, _ChantLayoutElement7); + + function TextElement(ctxt, text, fontFamily, fontSize, textAnchor) { + _classCallCheck(this, TextElement); + + // set these to some sane values for now... + + var _this7 = _possibleConstructorReturn(this, Object.getPrototypeOf(TextElement).call(this)); + + _this7.bounds.x = 0; + _this7.bounds.y = 0; + _this7.bounds.width = 0; + _this7.bounds.height = 0; + _this7.origin.x = 0; + _this7.origin.y = 0; + + _this7.fontFamily = fontFamily; + _this7.fontSize = fontSize; + _this7.textAnchor = textAnchor; + _this7.dominantBaseline = 'baseline'; // default placement + + _this7.generateSpansFromText(ctxt, text); + + _this7.recalculateMetrics(ctxt); + return _this7; + } + + _createClass(TextElement, [{ + key: 'generateSpansFromText', + value: function generateSpansFromText(ctxt, text) { + + this.text = ""; + this.spans = []; + + // save ourselves a lot of grief for a very common text: + if (text === "*" || text === "†") { + this.spans.push(new TextSpan(text)); + return; + } + + var markupStack = []; + var spanStartIndex = 0; + + var filterFrames = function filterFrames(frame, symbol) { + return frame.Symbol === symbol; + }; + + var that = this; + var closeSpan = function closeSpan(spanText, extraProperties) { + if (spanText === "") return; + + that.text += spanText; + + var properties = ""; + for (var i = 0; i < markupStack.length; i++) { + properties += markupStack[i].properties; + }if (extraProperties) properties = properties + extraProperties; + + that.spans.push(new TextSpan(spanText, properties)); + }; + + var markupRegex = /(\*|_|\^|%|[ARVarv]\/\.)/g; + + var match = null; + while (match = markupRegex.exec(text)) { + + var markupSymbol = match[0]; + + // non-matching symbols first + if (markupSymbol === "A/." || markupSymbol === "R/." || markupSymbol === "V/." || markupSymbol === "a/." || markupSymbol === "r/." || markupSymbol === "v/.") { + closeSpan(text[match.index] + ".", "font-family:'Exsurge Characters';fill:#f00;"); + } else if (markupStack.length === 0) { + // otherwise we're dealing with matching markup delimeters + // if this is our first markup frame, then just create an inline for preceding text and push the stack frame + closeSpan(text.substring(spanStartIndex, match.index)); + markupStack.push(MarkupStackFrame.createStackFrame(markupSymbol, match.index)); + } else { + + if (markupStack[markupStack.length - 1].symbol === markupSymbol) { + // group close + closeSpan(text.substring(spanStartIndex, match.index)); + markupStack.pop(); + } else if (markupStack.filter(filterFrames).length > 0) { + // trying to open a recursive group (or forgot to close a previous group) + // in either case, we just unwind to the previous stack frame + spanStartIndex = markupStack[markupStack.length - 1].startIndex; + markupStack.pop(); + continue; + } else { + // group open + closeSpan(text.substring(spanStartIndex, match.index)); + markupStack.push(MarkupStackFrame.createStackFrame(markupSymbol, match.index)); + } + } + + // advance the start index past the current markup + spanStartIndex = match.index + markupSymbol.length; + } + + // if we finished matches, and there is still some text left, create one final run + if (spanStartIndex < text.length) closeSpan(text.substring(spanStartIndex, text.length)); + + // if after all of that we still didn't create any runs, then just add the entire text + // string itself as a run + if (this.spans.length === 0) closeSpan(text); + } + }, { + key: 'measureSubstring', + value: function measureSubstring(ctxt, length) { + if (length === 0) return 0; + if (!length) length = Infinity; + var canvasCtxt = ctxt.canvasCtxt; + var baseFont = this.fontSize + "px " + this.fontFamily; + var width = 0; + var subStringLength = 0; + for (var i = 0; i < this.spans.length; i++) { + var font = '', + span = this.spans[i], + myText = span.text.slice(0, length - subStringLength); + if (span.properties.indexOf('font-style:italic;') >= 0) font += 'italic '; + if (span.properties.indexOf("font-variant:small-caps;") >= 0) font += 'small-caps '; + if (span.properties.indexOf('font-weight:bold;') >= 0) font += 'bold '; + font += baseFont; + canvasCtxt.font = font; + var metrics = canvasCtxt.measureText(myText, this.bounds.x, this.bounds.y); + width += metrics.width; + subStringLength += myText.length; + if (subStringLength === length) break; + } + return width; + } + }, { + key: 'recalculateMetrics', + value: function recalculateMetrics(ctxt) { + + this.bounds.x = 0; + this.bounds.y = 0; + + this.bounds.x = 0; + this.bounds.y = 0; + + this.origin.x = 0; + + if (ctxt.textMeasuringStrategy === TextMeasuringStrategy.Svg) { + var xml = '' + this.createSvgFragment(ctxt) + ''; + var doc = new DOMParser().parseFromString(xml, 'application/xml'); + + while (ctxt.svgTextMeasurer.firstChild) { + ctxt.svgTextMeasurer.firstChild.remove(); + }ctxt.svgTextMeasurer.appendChild(ctxt.svgTextMeasurer.ownerDocument.importNode(doc.documentElement, true).firstChild); + + var bbox = ctxt.svgTextMeasurer.firstChild.getBBox(); + this.bounds.width = bbox.width; + this.bounds.height = bbox.height; + this.origin.y = -bbox.y; // offset to baseline from top + } else if (ctxt.textMeasuringStrategy === TextMeasuringStrategy.Canvas) { + this.bounds.width = this.measureSubstring(ctxt); + this.bounds.height = this.fontSize * 1.2; + this.origin.y = this.fontSize; + } + } + }, { + key: 'getCssClasses', + value: function getCssClasses() { + return ""; + } + }, { + key: 'getExtraStyleProperties', + value: function getExtraStyleProperties(ctxt) { + return ""; + } + }, { + key: 'draw', + value: function draw(ctxt) { + + var canvasCtxt = ctxt.canvasCtxt; + + if (this.textAnchor === 'middle') canvasCtxt.textAlign = 'center';else canvasCtxt.textAlign = 'start'; + + canvasCtxt.font = this.fontSize + "px " + this.fontFamily; + + for (var i = 0; i < this.spans.length; i++) { + canvasCtxt.fillText(this.spans[i].text, this.bounds.x, this.bounds.y); + } + } + }, { + key: 'createSvgFragment', + value: function createSvgFragment(ctxt) { + + var spans = ""; + + for (var i = 0; i < this.spans.length; i++) { + var options = {}; + + if (this.spans[i].properties) options['style'] = this.spans[i].properties; + + spans += QuickSvg.createFragment('tspan', options, TextElement.escapeForTspan(this.spans[i].text)); + } + + var styleProperties = "font-family:" + this.fontFamily + ";font-size:" + this.fontSize + "px" + ";font-kerning:normal;" + this.getExtraStyleProperties(ctxt); + + return QuickSvg.createFragment('text', { + 'x': this.bounds.x, + 'y': this.bounds.y, + 'class': this.getCssClasses().trim(), + 'text-anchor': this.textAnchor, + 'dominant-baseline': this.dominantBaseline, + 'style': styleProperties + }, spans); + } + }], [{ + key: 'escapeForTspan', + value: function escapeForTspan(string) { + return String(string).replace(/[&<>]/g, function (s) { + return __subsForTspans[s]; + }); + } + }]); + + return TextElement; + }(ChantLayoutElement); + + var LyricType = exports.LyricType = { + SingleSyllable: 0, + BeginningSyllable: 1, + MiddleSyllable: 2, + EndingSyllable: 3, + + Directive: 4 // for asterisks, "ij." elements, or other performance notes. + }; + + var Lyric = exports.Lyric = function (_TextElement) { + _inherits(Lyric, _TextElement); + + function Lyric(ctxt, text, lyricType) { + _classCallCheck(this, Lyric); + + // save the original text in case we need to later use the lyric + // in a dropcap... + + var _this8 = _possibleConstructorReturn(this, Object.getPrototypeOf(Lyric).call(this, ctxt, text, ctxt.lyricTextFont, ctxt.lyricTextSize, 'start')); + + _this8.originalText = text; + + if (typeof lyricType === 'undefined' || lyricType === null || lyricType === "") _this8.lyricType = LyricType.SingleSyllable;else _this8.lyricType = lyricType; + + // Lyrics keep track of how to center them on notation elements. + // centerTextIndex is the index in this.text where the centering starts, + // centerLength is how many characters comprise the center point. + // performLayout will do the processing + _this8.centerStartIndex = -1; + _this8.centerLength = text.length; + + _this8.needsConnector = false; + + // Lyrics can have their own language defined, which affects the alignment + // of the text with the notation element + _this8.language = null; + return _this8; + } + + _createClass(Lyric, [{ + key: 'allowsConnector', + value: function allowsConnector() { + return this.lyricType === LyricType.BeginningSyllable || this.lyricType === LyricType.MiddleSyllable; + } + }, { + key: 'setNeedsConnector', + value: function setNeedsConnector(needs) { + if (needs === true) { + this.needsConnector = true; + this.bounds.width = this.widthWithConnector; + + if (this.spans.length > 0) this.spans[this.spans.length - 1].text = this.lastSpanTextWithConnector; + } else { + this.needsConnector = false; + this.bounds.width = this.widthWithoutConnector; + + if (this.spans.length > 0) this.spans[this.spans.length - 1].text = this.lastSpanText; + } + } + }, { + key: 'generateSpansFromText', + value: function generateSpansFromText(ctxt, text) { + _get(Object.getPrototypeOf(Lyric.prototype), 'generateSpansFromText', this).call(this, ctxt, text); + + if (this.spans.length > 0) { + this.lastSpanText = this.spans[this.spans.length - 1].text; + this.lastSpanTextWithConnector = this.lastSpanText + ctxt.syllableConnector; + } else { + this.lastSpanText = ""; + this.lastSpanTextWithConnector = ""; + } + } + }, { + key: 'recalculateMetrics', + value: function recalculateMetrics(ctxt) { + _get(Object.getPrototypeOf(Lyric.prototype), 'recalculateMetrics', this).call(this, ctxt); + + this.widthWithoutConnector = this.bounds.width; + this.textWithConnector = this.text + ctxt.syllableConnector; + + this.widthWithConnector = this.bounds.width + ctxt.hyphenWidth; + + var activeLanguage = this.language || ctxt.defaultLanguage; + + // calculate the point where the text lines up to the staff notation + // and offset the rect that much. By default we just center the text, + // but the logic below allows for smarter lyric alignment based + // on manual override or language control. + var offset = this.widthWithoutConnector / 2, + x1, + x2; + + // some simple checks for sanity, and disable manual centering if the numbers are bad + if (this.centerStartIndex >= 0 && (this.centerStartIndex >= this.text.length || this.centerLength < 0 || this.centerStartIndex + this.centerLength > this.text.length)) this.centerStartIndex = -1; + + if (this.text.length === 0) { + // if we have no text to work with, then there's nothing to do! + } else if (this.centerStartIndex >= 0) { + // if we have manually overriden the centering logic for this lyric, + // then always use that. + if (ctxt.textMeasuringStrategy === TextMeasuringStrategy.Svg) { + // svgTextMeasurer still has the current lyric in it... + x1 = ctxt.svgTextMeasurer.firstChild.getSubStringLength(0, this.centerStartIndex); + x2 = ctxt.svgTextMeasurer.firstChild.getSubStringLength(0, this.centerStartIndex + this.centerLength); + } else if (ctxt.textMeasuringStrategy === TextMeasuringStrategy.Canvas) { + x1 = this.measureSubstring(ctxt, this.centerStartIndex); + x2 = this.measureSubstring(ctxt, this.centerStartIndex + this.centerLength); + } + offset = x1 + (x2 - x1) / 2; + } else { + + // if it's a directive with no manual centering override, then + // just center the text. + if (this.lyricType !== LyricType.Directive) { + + // Non-directive elements are lined up to the chant notation based on vowel segments, + var result = activeLanguage.findVowelSegment(this.text, 0); + + if (result.found === true) { + if (ctxt.textMeasuringStrategy === TextMeasuringStrategy.Svg) { + // svgTextMeasurer still has the current lyric in it... + x1 = ctxt.svgTextMeasurer.firstChild.getSubStringLength(0, result.startIndex); + x2 = ctxt.svgTextMeasurer.firstChild.getSubStringLength(0, result.startIndex + result.length); + } else if (ctxt.textMeasuringStrategy === TextMeasuringStrategy.Canvas) { + x1 = this.measureSubstring(ctxt, result.startIndex); + x2 = this.measureSubstring(ctxt, result.startIndex + result.length); + } + offset = x1 + (x2 - x1) / 2; + } + } + } + + this.bounds.x = -offset; + this.bounds.y = 0; + + this.origin.x = offset; + + this.bounds.width = this.widthWithoutConnector; + this.bounds.height = ctxt.lyricTextSize; + } + }, { + key: 'generateDropCap', + value: function generateDropCap(ctxt) { + + var dropCap = new DropCap(ctxt, this.originalText.substring(0, 1)); + + // if the dropcap is a single character syllable (vowel) that is the + // beginning of the word, then we use a hyphen in place of the lyric text + // and treat it as a single syllable. + if (this.originalText.length === 1) { + this.generateSpansFromText(ctxt, ctxt.syllableConnector); + this.centerStartIndex = -1; + this.lyricType = LyricType.SingleSyllable; + } else { + this.generateSpansFromText(ctxt, this.originalText.substring(1)); + this.centerStartIndex--; // lost a letter, so adjust centering accordingly + } + + return dropCap; + } + }, { + key: 'getCssClasses', + value: function getCssClasses() { + + var classes = "lyric "; + + if (this.lyricType === LyricType.Directive) classes += "directive "; + + return classes + _get(Object.getPrototypeOf(Lyric.prototype), 'getCssClasses', this).call(this); + } + }, { + key: 'getExtraStyleProperties', + value: function getExtraStyleProperties(ctxt) { + var props = _get(Object.getPrototypeOf(Lyric.prototype), 'getExtraStyleProperties', this).call(this); + + if (this.lyricType === LyricType.Directive && ctxt.autoColor === true) props += "fill:#f00;"; + + return props; + } + }, { + key: 'createSvgFragment', + value: function createSvgFragment(ctxt) { + if (this.spans.length > 0) { + if (this.needsConnector) this.spans[this.spans.length - 1].text = this.lastSpanTextWithConnector;else this.spans[this.spans.length - 1].text = this.lastSpanText; + } + + return _get(Object.getPrototypeOf(Lyric.prototype), 'createSvgFragment', this).call(this, ctxt); + } + }]); + + return Lyric; + }(TextElement); + + var DropCap = exports.DropCap = function (_TextElement2) { + _inherits(DropCap, _TextElement2); + + /** + * @param {String} text + */ + + function DropCap(ctxt, text) { + _classCallCheck(this, DropCap); + + var _this9 = _possibleConstructorReturn(this, Object.getPrototypeOf(DropCap).call(this, ctxt, text, ctxt.dropCapTextFont, ctxt.dropCapTextSize, 'middle')); + + _this9.padding = ctxt.staffInterval * 2; + return _this9; + } + + _createClass(DropCap, [{ + key: 'getCssClasses', + value: function getCssClasses() { + return "dropCap " + _get(Object.getPrototypeOf(DropCap.prototype), 'getCssClasses', this).call(this); + } + }]); + + return DropCap; + }(TextElement); + + var Annotation = exports.Annotation = function (_TextElement3) { + _inherits(Annotation, _TextElement3); + + /** + * @param {String} text + */ + + function Annotation(ctxt, text) { + _classCallCheck(this, Annotation); + + var _this10 = _possibleConstructorReturn(this, Object.getPrototypeOf(Annotation).call(this, ctxt, text, ctxt.annotationTextFont, ctxt.annotationTextSize, 'middle')); + + _this10.padding = ctxt.staffInterval; + _this10.dominantBaseline = 'hanging'; // so that annotations can be aligned at the top. + return _this10; + } + + _createClass(Annotation, [{ + key: 'getCssClasses', + value: function getCssClasses() { + return "annotation " + _get(Object.getPrototypeOf(Annotation.prototype), 'getCssClasses', this).call(this); + } + }]); + + return Annotation; + }(TextElement); + + var ChantNotationElement = exports.ChantNotationElement = function (_ChantLayoutElement8) { + _inherits(ChantNotationElement, _ChantLayoutElement8); + + function ChantNotationElement() { + _classCallCheck(this, ChantNotationElement); + + //double + + var _this11 = _possibleConstructorReturn(this, Object.getPrototypeOf(ChantNotationElement).call(this)); + + _this11.leadingSpace = 0.0; + _this11.trailingSpace = -1; // if less than zero, this is automatically calculated at layout time + _this11.keepWithNext = false; + _this11.needsLayout = true; + + _this11.lyrics = []; + + _this11.score = null; // the ChantScore + _this11.line = null; // the ChantLine + + _this11.visualizers = []; + return _this11; + } + + _createClass(ChantNotationElement, [{ + key: 'hasLyrics', + value: function hasLyrics() { + if (this.lyrics.length !== 0) return true;else return false; + } + }, { + key: 'getLyricLeft', + value: function getLyricLeft(index) { + // warning: no error checking on index or on whether lyric[index] is valid + return this.bounds.x + this.lyrics[index].bounds.x; + } + }, { + key: 'getAllLyricsLeft', + value: function getAllLyricsLeft() { + if (this.lyrics.length === 0) return this.bounds.right(); + + var x = Number.MAX_VALUE; + for (var i = 0; i < this.lyrics.length; i++) { + if (this.lyrics[i]) x = Math.min(x, this.lyrics[i].bounds.x); + } + + return this.bounds.x + x; + } + }, { + key: 'getLyricRight', + value: function getLyricRight(index) { + // warning: no error checking on index or on whether lyric[index] is valid + return this.bounds.x + this.lyrics[index].bounds.x + this.lyrics[index].bounds.width; + } + }, { + key: 'getAllLyricsRight', + value: function getAllLyricsRight() { + if (this.lyrics.length === 0) return this.bounds.x; + + var x = Number.MIN_VALUE; + for (var i = 0; i < this.lyrics.length; i++) { + if (this.lyrics[i]) x = Math.max(x, this.lyrics[i].bounds.x + this.lyrics[i].bounds.width); + } + + return this.bounds.x + x; + } + + // used by subclasses while building up the chant notations. + + }, { + key: 'addVisualizer', + value: function addVisualizer(chantLayoutElement) { + if (this.bounds.isEmpty()) this.bounds = chantLayoutElement.bounds.clone();else this.bounds.union(chantLayoutElement.bounds); + + this.visualizers.push(chantLayoutElement); + } + + // same as addVisualizer, except the element is unshifted to the front + // of the visualizer array rather than the end. This way, some + // visualizers can be placed behind the others...ledger lines for example. + + }, { + key: 'prependVisualizer', + value: function prependVisualizer(chantLayoutElement) { + if (this.bounds.isEmpty()) this.bounds = chantLayoutElement.bounds.clone();else this.bounds.union(chantLayoutElement.bounds); + + this.visualizers.unshift(chantLayoutElement); + } + + // chant notation elements are given an opportunity to perform their layout via this function. + // subclasses should call this function first in overrides of this function. + // on completion, exsurge presumes that the bounds, the origin, and the fragment objects are + // all valid and prepared for higher level layout. + + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + + if (this.trailingSpace < 0) this.trailingSpace = ctxt.intraNeumeSpacing * 4; + + // reset the bounds and the staff notations before doing a layout + this.visualizers = []; + this.bounds = new _Exsurge.Rect(Infinity, Infinity, -Infinity, -Infinity); + + for (var i = 0; i < this.lyrics.length; i++) { + this.lyrics[i].recalculateMetrics(ctxt); + } + } + + // some subclasses have internal dependencies on other notations (for example, + // a custos can depend on a later neume which it uses to set its height). + // subclasses can override this function so that when the notations are + // altered, the subclass can correctly invalidate (and later restore) its own + // depedencies + + }, { + key: 'resetDependencies', + value: function resetDependencies() {} + + // a helper function for subclasses to call after they are done performing layout... + + }, { + key: 'finishLayout', + value: function finishLayout(ctxt) { + + this.bounds.x = 0; + + for (var i = 0; i < this.lyrics.length; i++) { + this.lyrics[i].bounds.x = this.origin.x - this.lyrics[i].origin.x; + }this.needsLayout = false; + } + }, { + key: 'draw', + value: function draw(ctxt) { + + var canvasCtxt = ctxt.canvasCtxt; + canvasCtxt.translate(this.bounds.x, 0); + + for (var i = 0; i < this.visualizers.length; i++) { + this.visualizers[i].draw(ctxt); + }for (i = 0; i < this.lyrics.length; i++) { + this.lyrics[i].draw(ctxt); + }canvasCtxt.translate(-this.bounds.x, 0); + } + }, { + key: 'createSvgFragment', + value: function createSvgFragment(ctxt) { + var inner = ""; + + for (var i = 0; i < this.visualizers.length; i++) { + inner += this.visualizers[i].createSvgFragment(ctxt); + }for (i = 0; i < this.lyrics.length; i++) { + inner += this.lyrics[i].createSvgFragment(ctxt); + }return QuickSvg.createFragment('g', { + // this.constructor.name will not be the same after being mangled by UglifyJS + 'class': 'ChantNotationElement ' + this.constructor.name, + 'transform': 'translate(' + this.bounds.x + ',' + 0 + ')' + }, inner); + } + }]); + + return ChantNotationElement; + }(ChantLayoutElement); + +/***/ }, +/* 5 */ +/***/ function(module, exports) { + + module.exports = "data:font/opentype;base64,AAEAAAATAQAABAAwRFNJRwAAAAEAAENkAAAACEdERUYAbgADAABDbAAAABhHUE9TTxtiswAAQ4QAAAE8R1NVQjtgWB4AAETAAAAAlk9TLzJKLTibAAABuAAAAGBjbWFwCRIK1gAAA4gAAAEEY3Z0IAGGB0cAAAZ0AAAAGmZwZ20GWZw3AAAEjAAAAXNnYXNwABcACAAAQ1QAAAAQZ2x5ZhRQNO4AAAdQAAAEzGhlYWQKMl2QAAABPAAAADZoaGVhDC0CmQAAAXQAAAAkaG10eB67AO4AAAIYAAABbmtlcm4E1wS9AAAMHAAAAMZsb2NhLQ4u0gAABpAAAADAbWF4cAJtAJoAAAGYAAAAIG5hbWUmgJC3AAAM5AAANY5wb3N0CJUJxAAAQnQAAADgcHJlcNTHuIYAAAYAAAAAcgABAAAAAQAArr24P18PPPUAGwgAAAAAANLrfC8AAAAA0uuXUgAA/vAFLAYhAAAACQACAAAAAAAAAAEAAAb+/bwAAAUzAAD/UQUsAAEAAAAAAAAAAAAAAAAAAABYAAEAAABfAE4AAwAAAAAAAQAAAAAACgAAAgAASwAAAAAAAwNBAZAABQAAA1gDWAAABLADWANYAAAEsABkAfQAAAIABQMGAAACAAQAAAABAAAAAAAAAAAAAAAAICAgIABAACEAfgb+/bwAAAb+AkQAAAABAAAAAAOiBOwAAAAgAAIDMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAHVAIMDMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAMzAAAEwwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAR9ACkDMwAAAzMAAAMzAAAFMwAUAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAO6AAADMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAAzMAAAMzAAADMwAAA4kAHwMzAAADMwAAAzMAAAQNAA8DMwAAAAAAAAAAAAAAAAAAAAAAAAAAAAMAAAADAAAAHAABAAAAAAA8AAMAAQAAABwABAAgAAAABAAEAAEAAAB+//8AAAAg////4AABAAAAAAAGAMgAAAAgAF8AAAABAAIAAwAEAAUABgAHAAgACQAKAAsADAANAA4ADwAQABEAEgATABQAFQAWABcAGAAZABoAGwAcAB0AHgAfACAAIQAiACMAJAAlACYAJwAoACkAKgArACwALQAuAC8AMAAxADIAMwA0ADUANgA3ADgAOQA6ADsAPAA9AD4APwBAAEEAQgBDAEQARQBGAEcASABJAEoASwBMAE0ATgBPAFAAUQBSAFMAVABVAFYAVwBYAFkAWgBbAFwAXQBeuAAALEu4AAlQWLEBAY5ZuAH/hbgARB25AAkAA19eLbgAASwgIEVpRLABYC24AAIsuAABKiEtuAADLCBGsAMlRlJYI1kgiiCKSWSKIEYgaGFksAQlRiBoYWRSWCNlilkvILAAU1hpILAAVFghsEBZG2kgsABUWCGwQGVZWTotuAAELCBGsAQlRlJYI4pZIEYgamFksAQlRiBqYWRSWCOKWS/9LbgABSxLILADJlBYUViwgEQbsEBEWRshISBFsMBQWLDARBshWVktuAAGLCAgRWlEsAFgICBFfWkYRLABYC24AAcsuAAGKi24AAgsSyCwAyZTWLBAG7AAWYqKILADJlNYIyGwgIqKG4ojWSCwAyZTWCMhuADAioobiiNZILADJlNYIyG4AQCKihuKI1kgsAMmU1gjIbgBQIqKG4ojWSC4AAMmU1iwAyVFuAGAUFgjIbgBgCMhG7ADJUUjISMhWRshWUQtuAAJLEtTWEVEGyEhWS0AuAAAKwC6AAEAAgACKwG6AAMAAgACKwG/AAMATAA8AC8AIgAUAAAACCu/AAQARwA8AC8AIgAUAAAACCsAvwABAIAAZgBQADkAIgAAAAgrvwACAHgAZgBQADkAIgAAAAgrALoABQAEAAcruAAAIEV9aRhEAAAAKgArAFAAbgCCAAAAHv4gABQDogAeBOwAOQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEIAQgBCAEIAQgBCAEIAQgBCAEIAQgBCAEIAQgBCAEIAQgBCAEIAlACUAJQAlACUAJQAlACUAJQAlACUAJQAlACUAJQAlACUAQwBDAEMAQwBWAFYAVgBWAFYAVgBWAFYAVgBWAFYAagBqAGoAagBqAGoAagBqAGoAagBqAGoAagBqAGoAagBqAIcAhwCHAIcAmYCZgJmAmYCZgJmAmYCZgJmAAEAg//YAXEA7AAPAEu7AAAABAAIAAQrQRMABgAAABYAAAAmAAAANgAAAEYAAABWAAAAZgAAAHYAAACGAAAACV1BBQCVAAAApQAAAAJdALoADQAFAAMrMDElFA4CIyImNTQ+AjMyFgFxFSUzHTYuFiYzHDIxeyM7LBk6NiI7LRo7AAAAAAMAAP72BK4GIQACAB4ALAAAAQsBBwMGFhcVITU+ATcBPgE3AR4DFxUhNT4BJwMCFjcGJjcBLgEHNhYDAQL2sKsebwpKUv5gRFAKAXQXRBoBpAUSHi4g/lpOPAtyoi1ecrRIAdcBRVR70VX+OQIXAgL9/lr+sh8cCSsrDBoeBGYZKQ77Sg4WEAwEKysFHiEBTv3MDQSKE+8FHkMMCsZJ/vn7AwAAAwAp/vAFLAYbADEAPwBNAAAzNT4BNREOAQcnPgMzMh4CFRQOAgcBHgM3Fw4BIyImJwEGKwEiJicRFBYXFQMiBxEeATMyNjU0LgISFjcGJjcBLgEHNhYDATJETSNJJQkvYGhzQnSscjgpS2g+AS8PIys1IgtCdycdNw7+0Q0NGxo0HEhJRCYnGygWnqonU4HtLV5ytEgB1wFFVHvRVf45Kw4hDgQ9BQsFPgwVEQouUm9ASHVaQBP+GhYaDQEDKxYdIBcCMQIFBv4FDCMOKwS2A/4ABQKLhTdcQiX6zQ0EihPvBR5DDArGSf75+wMAAAAAAgAU/vYFCgYhABoAKAAAAQ4BBwEOAwcBLgEnNSEVDgEXCQE2Jic1IQAWNwYmNwEuAQc2FgMBBQpETQr+gQgnLiwN/kgKRT8Bs1A7CwFhAVALR1IBoPxdLV5ytEgB1wFFVHvRVf45BMENGRz7vBYfFQwDBJ0aIAgrKwYdHfxKA7QdGwor+p0NBIoT7wUeQwwKxkn++fsDAAADAAD/LwOrBOUAAgAeACwAAAELAQ8BBhYXFSE1PgE3AT4BNwEeAxcVITU+AS8BAhY3BiY3ATQmBzYWBwECNGtpHlAFKEv+oEAxBgEXFTYtAUIDCxAeJ/6bRx8GU3oOZGuBOQFhIV1xlUL+qgG5AUf+uV76ERAJNzYMEREDcBciGfw+CQ4JCAU3OAUQFPr+WwUFhxPFA/0rBgy8RNX8HAAAAwAf/y8D6wTlADEAPwBNAAAzNT4BNREiBgcnPgMzMh4CFRQOAgcTHgM3Fw4BIyImJwM2KwEiJhcRFBYXFQMiBxEeATMyNjU0LgISFjcGJjcBNCYHNhYHASc+LgI3MQoxSk9ZM1uIXCwfO1Mi3goVGCIsDT9eIR0zDN4GDBQVKgMrQkcbCwQbEG11HDhYqw5ka4E5AWEhXXGVQv6qNg0VBQM/CQdHDRENCCZFWjM5Xkk1C/6ODxEHAQQ1FhgfFQGqAQQB/oYEFg02A60B/oQBAWNlKkQuG/wJBQWHE8UD/SsGDLxE1fwcAAIAD/8vA/AE5QAaACgAAAEOAQcBDgMHAS4BJzUhFQ4BFxsBNiYnNSEAFjcGJjcBNCYHNhYHAQPwQDAF/uEHIickH/6xBio7AW5IHgb16AYmSgFg/TIOZGuBOQFhIV1xlUL+qgO5DRAQ/KwTHRIKCAOoEBQINzgGDxH9UwKrEA8KN/vHBQWHE8UD/SsGDLxE1fwcAAAAAAEAAADCAAEAHgBgAAQAVAAhAA7/nAAhACEANgAhADIADQAhADb/8gAhAEEANgAhAFIAFwAhAFb/pQAyAA7/nAAyACEAWAAyADIAoQAyADYAvQAyAEEAWAAyAFIATwAyAFYAaQA2AA7+cAA2ACH+kwA2ADL/+QA2ADYADgA2AEH+kwA2AFL/YQA2AFb/fABBAA7/nABBAFIAFwBBAFb/1QBSAA7/nABSAFIANgBSAFYATABWAA7+cABWAFIACQBWAFYAGQAAAAAAFAD2AAEAAAAAAAAALgAAAAEAAAAAAAEAEgA1AAEAAAAAAAIABwAuAAEAAAAAAAMAHwA1AAEAAAAAAAQAEgA1AAEAAAAAAAUALwBUAAEAAAAAAAYAEQCDAAEAAAAAAA0Q9ACUAAEAAAAAAA4AGgEkAAEAAAAAABIAEgA1AAMAAQQJAAAAXBGIAAMAAQQJAAEAJBHyAAMAAQQJAAIADhHkAAMAAQQJAAMAPhHyAAMAAQQJAAQAJBHyAAMAAQQJAAUAXhIwAAMAAQQJAAYAIhKOAAMAAQQJAA0h6BKwAAMAAQQJAA4ANBPQAAMAAQQJABIAJBHyQ29weXJpZ2h0IChjKSAyMDE2IEZyLiBNYXR0aGV3IFNwZW5jZXIsIE8uUy5KLlJlZ3VsYXJFeHN1cmdlIENoYXJhY3RlcnM6VmVyc2lvbiAxLjAwVmVyc2lvbiAxLjAwIEZlYnJ1YXJ5IDE4LCAyMDE2LCBpbml0aWFsIHJlbGVhc2VFeHN1cmdlQ2hhcmFjdGVyc1RoaXMgRm9udCBTb2Z0d2FyZSBpcyBsaWNlbnNlZCB1bmRlciB0aGUgU0lMIE9wZW4gRm9udCBMaWNlbnNlLCBWZXJzaW9uIDEuMS4gVGhpcyBsaWNlbnNlIGlzIGNvcGllZCBiZWxvdywgYW5kIGlzIGFsc28gYXZhaWxhYmxlIHdpdGggYSBGQVEgYXQ6IGh0dHA6Ly9zY3JpcHRzLnNpbC5vcmcvT0ZMDQoNCg0KLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0NClNJTCBPUEVOIEZPTlQgTElDRU5TRSBWZXJzaW9uIDEuMSAtIDI2IEZlYnJ1YXJ5IDIwMDcNCi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tDQoNClBSRUFNQkxFDQpUaGUgZ29hbHMgb2YgdGhlIE9wZW4gRm9udCBMaWNlbnNlIChPRkwpIGFyZSB0byBzdGltdWxhdGUgd29ybGR3aWRlIGRldmVsb3BtZW50IG9mIGNvbGxhYm9yYXRpdmUgZm9udCBwcm9qZWN0cywgdG8gc3VwcG9ydCB0aGUgZm9udCBjcmVhdGlvbiBlZmZvcnRzIG9mIGFjYWRlbWljIGFuZCBsaW5ndWlzdGljIGNvbW11bml0aWVzLCBhbmQgdG8gcHJvdmlkZSBhIGZyZWUgYW5kIG9wZW4gZnJhbWV3b3JrIGluIHdoaWNoIGZvbnRzIG1heSBiZSBzaGFyZWQgYW5kIGltcHJvdmVkIGluIHBhcnRuZXJzaGlwIHdpdGggb3RoZXJzLg0KDQpUaGUgT0ZMIGFsbG93cyB0aGUgbGljZW5zZWQgZm9udHMgdG8gYmUgdXNlZCwgc3R1ZGllZCwgbW9kaWZpZWQgYW5kIHJlZGlzdHJpYnV0ZWQgZnJlZWx5IGFzIGxvbmcgYXMgdGhleSBhcmUgbm90IHNvbGQgYnkgdGhlbXNlbHZlcy4gVGhlIGZvbnRzLCBpbmNsdWRpbmcgYW55IGRlcml2YXRpdmUgd29ya3MsIGNhbiBiZSBidW5kbGVkLCBlbWJlZGRlZCwgcmVkaXN0cmlidXRlZCBhbmQvb3Igc29sZCB3aXRoIGFueSBzb2Z0d2FyZSBwcm92aWRlZCB0aGF0IGFueSByZXNlcnZlZCBuYW1lcyBhcmUgbm90IHVzZWQgYnkgZGVyaXZhdGl2ZSB3b3Jrcy4gVGhlIGZvbnRzIGFuZCBkZXJpdmF0aXZlcywgaG93ZXZlciwgY2Fubm90IGJlIHJlbGVhc2VkIHVuZGVyIGFueSBvdGhlciB0eXBlIG9mIGxpY2Vuc2UuIFRoZSByZXF1aXJlbWVudCBmb3IgZm9udHMgdG8gcmVtYWluIHVuZGVyIHRoaXMgbGljZW5zZSBkb2VzIG5vdCBhcHBseSB0byBhbnkgZG9jdW1lbnQgY3JlYXRlZCB1c2luZyB0aGUgZm9udHMgb3IgdGhlaXIgZGVyaXZhdGl2ZXMuDQoNCkRFRklOSVRJT05TDQoiRm9udCBTb2Z0d2FyZSIgcmVmZXJzIHRvIHRoZSBzZXQgb2YgZmlsZXMgcmVsZWFzZWQgYnkgdGhlIENvcHlyaWdodCBIb2xkZXIocykgdW5kZXIgdGhpcyBsaWNlbnNlIGFuZCBjbGVhcmx5IG1hcmtlZCBhcyBzdWNoLiBUaGlzIG1heSBpbmNsdWRlIHNvdXJjZSBmaWxlcywgYnVpbGQgc2NyaXB0cyBhbmQgZG9jdW1lbnRhdGlvbi4NCg0KIlJlc2VydmVkIEZvbnQgTmFtZSIgcmVmZXJzIHRvIGFueSBuYW1lcyBzcGVjaWZpZWQgYXMgc3VjaCBhZnRlciB0aGUgY29weXJpZ2h0IHN0YXRlbWVudChzKS4NCg0KIk9yaWdpbmFsIFZlcnNpb24iIHJlZmVycyB0byB0aGUgY29sbGVjdGlvbiBvZiBGb250IFNvZnR3YXJlIGNvbXBvbmVudHMgYXMgZGlzdHJpYnV0ZWQgYnkgdGhlIENvcHlyaWdodCBIb2xkZXIocykuDQoNCiJNb2RpZmllZCBWZXJzaW9uIiByZWZlcnMgdG8gYW55IGRlcml2YXRpdmUgbWFkZSBieSBhZGRpbmcgdG8sIGRlbGV0aW5nLCBvciBzdWJzdGl0dXRpbmcgLS0gaW4gcGFydCBvciBpbiB3aG9sZSAtLSBhbnkgb2YgdGhlIGNvbXBvbmVudHMgb2YgdGhlIE9yaWdpbmFsIFZlcnNpb24sIGJ5IGNoYW5naW5nIGZvcm1hdHMgb3IgYnkgcG9ydGluZyB0aGUgRm9udCBTb2Z0d2FyZSB0byBhIG5ldyBlbnZpcm9ubWVudC4NCg0KIkF1dGhvciIgcmVmZXJzIHRvIGFueSBkZXNpZ25lciwgZW5naW5lZXIsIHByb2dyYW1tZXIsIHRlY2huaWNhbCB3cml0ZXIgb3Igb3RoZXIgcGVyc29uIHdobyBjb250cmlidXRlZCB0byB0aGUgRm9udCBTb2Z0d2FyZS4NCg0KUEVSTUlTU0lPTiAmIENPTkRJVElPTlMNClBlcm1pc3Npb24gaXMgaGVyZWJ5IGdyYW50ZWQsIGZyZWUgb2YgY2hhcmdlLCB0byBhbnkgcGVyc29uIG9idGFpbmluZyBhIGNvcHkgb2YgdGhlIEZvbnQgU29mdHdhcmUsIHRvIHVzZSwgc3R1ZHksIGNvcHksIG1lcmdlLCBlbWJlZCwgbW9kaWZ5LCByZWRpc3RyaWJ1dGUsIGFuZCBzZWxsIG1vZGlmaWVkIGFuZCB1bm1vZGlmaWVkIGNvcGllcyBvZiB0aGUgRm9udCBTb2Z0d2FyZSwgc3ViamVjdCB0byB0aGUgZm9sbG93aW5nIGNvbmRpdGlvbnM6DQoNCjEpIE5laXRoZXIgdGhlIEZvbnQgU29mdHdhcmUgbm9yIGFueSBvZiBpdHMgaW5kaXZpZHVhbCBjb21wb25lbnRzLCBpbiBPcmlnaW5hbCBvciBNb2RpZmllZCBWZXJzaW9ucywgbWF5IGJlIHNvbGQgYnkgaXRzZWxmLg0KDQoyKSBPcmlnaW5hbCBvciBNb2RpZmllZCBWZXJzaW9ucyBvZiB0aGUgRm9udCBTb2Z0d2FyZSBtYXkgYmUgYnVuZGxlZCwgcmVkaXN0cmlidXRlZCBhbmQvb3Igc29sZCB3aXRoIGFueSBzb2Z0d2FyZSwgcHJvdmlkZWQgdGhhdCBlYWNoIGNvcHkgY29udGFpbnMgdGhlIGFib3ZlIGNvcHlyaWdodCBub3RpY2UgYW5kIHRoaXMgbGljZW5zZS4gVGhlc2UgY2FuIGJlIGluY2x1ZGVkIGVpdGhlciBhcyBzdGFuZC1hbG9uZSB0ZXh0IGZpbGVzLCBodW1hbi1yZWFkYWJsZSBoZWFkZXJzIG9yIGluIHRoZSBhcHByb3ByaWF0ZSBtYWNoaW5lLXJlYWRhYmxlIG1ldGFkYXRhIGZpZWxkcyB3aXRoaW4gdGV4dCBvciBiaW5hcnkgZmlsZXMgYXMgbG9uZyBhcyB0aG9zZSBmaWVsZHMgY2FuIGJlIGVhc2lseSB2aWV3ZWQgYnkgdGhlIHVzZXIuDQoNCjMpIE5vIE1vZGlmaWVkIFZlcnNpb24gb2YgdGhlIEZvbnQgU29mdHdhcmUgbWF5IHVzZSB0aGUgUmVzZXJ2ZWQgRm9udCBOYW1lKHMpIHVubGVzcyBleHBsaWNpdCB3cml0dGVuIHBlcm1pc3Npb24gaXMgZ3JhbnRlZCBieSB0aGUgY29ycmVzcG9uZGluZyBDb3B5cmlnaHQgSG9sZGVyLiBUaGlzIHJlc3RyaWN0aW9uIG9ubHkgYXBwbGllcyB0byB0aGUgcHJpbWFyeSBmb250IG5hbWUgYXMgcHJlc2VudGVkIHRvIHRoZSB1c2Vycy4NCg0KNCkgVGhlIG5hbWUocykgb2YgdGhlIENvcHlyaWdodCBIb2xkZXIocykgb3IgdGhlIEF1dGhvcihzKSBvZiB0aGUgRm9udCBTb2Z0d2FyZSBzaGFsbCBub3QgYmUgdXNlZCB0byBwcm9tb3RlLCBlbmRvcnNlIG9yIGFkdmVydGlzZSBhbnkgTW9kaWZpZWQgVmVyc2lvbiwgZXhjZXB0IHRvIGFja25vd2xlZGdlIHRoZSBjb250cmlidXRpb24ocykgb2YgdGhlIENvcHlyaWdodCBIb2xkZXIocykgYW5kIHRoZSBBdXRob3Iocykgb3Igd2l0aCB0aGVpciBleHBsaWNpdCB3cml0dGVuIHBlcm1pc3Npb24uDQoNCjUpIFRoZSBGb250IFNvZnR3YXJlLCBtb2RpZmllZCBvciB1bm1vZGlmaWVkLCBpbiBwYXJ0IG9yIGluIHdob2xlLCBtdXN0IGJlIGRpc3RyaWJ1dGVkIGVudGlyZWx5IHVuZGVyIHRoaXMgbGljZW5zZSwgYW5kIG11c3Qgbm90IGJlIGRpc3RyaWJ1dGVkIHVuZGVyIGFueSBvdGhlciBsaWNlbnNlLiBUaGUgcmVxdWlyZW1lbnQgZm9yIGZvbnRzIHRvIHJlbWFpbiB1bmRlciB0aGlzIGxpY2Vuc2UgZG9lcyBub3QgYXBwbHkgdG8gYW55IGRvY3VtZW50IGNyZWF0ZWQgdXNpbmcgdGhlIEZvbnQgU29mdHdhcmUuDQoNClRFUk1JTkFUSU9ODQpUaGlzIGxpY2Vuc2UgYmVjb21lcyBudWxsIGFuZCB2b2lkIGlmIGFueSBvZiB0aGUgYWJvdmUgY29uZGl0aW9ucyBhcmUgbm90IG1ldC4NCg0KRElTQ0xBSU1FUg0KVEhFIEZPTlQgU09GVFdBUkUgSVMgUFJPVklERUQgIkFTIElTIiwgV0lUSE9VVCBXQVJSQU5UWSBPRiBBTlkgS0lORCwgRVhQUkVTUyBPUiBJTVBMSUVELCBJTkNMVURJTkcgQlVUIE5PVCBMSU1JVEVEIFRPIEFOWSBXQVJSQU5USUVTIE9GIE1FUkNIQU5UQUJJTElUWSwgRklUTkVTUyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UgQU5EIE5PTklORlJJTkdFTUVOVCBPRiBDT1BZUklHSFQsIFBBVEVOVCwgVFJBREVNQVJLLCBPUiBPVEhFUiBSSUdIVC4gSU4gTk8gRVZFTlQgU0hBTEwgVEhFIENPUFlSSUdIVCBIT0xERVIgQkUgTElBQkxFIEZPUiBBTlkgQ0xBSU0sIERBTUFHRVMgT1IgT1RIRVIgTElBQklMSVRZLCBJTkNMVURJTkcgQU5ZIEdFTkVSQUwsIFNQRUNJQUwsIElORElSRUNULCBJTkNJREVOVEFMLCBPUiBDT05TRVFVRU5USUFMIERBTUFHRVMsIFdIRVRIRVIgSU4gQU4gQUNUSU9OIE9GIENPTlRSQUNULCBUT1JUIE9SIE9USEVSV0lTRSwgQVJJU0lORyBGUk9NLCBPVVQgT0YgVEhFIFVTRSBPUiBJTkFCSUxJVFkgVE8gVVNFIFRIRSBGT05UIFNPRlRXQVJFIE9SIEZST00gT1RIRVIgREVBTElOR1MgSU4gVEhFIEZPTlQgU09GVFdBUkUuAEMAbwBwAHkAcgBpAGcAaAB0ACAAKABjACkAIAAyADAAMQA2ACAARgByAC4AIABNAGEAdAB0AGgAZQB3ACAAUwBwAGUAbgBjAGUAcgAsACAATwAuAFMALgBKAC4AUgBlAGcAdQBsAGEAcgBFAHgAcwB1AHIAZwBlACAAQwBoAGEAcgBhAGMAdABlAHIAcwA6AFYAZQByAHMAaQBvAG4AIAAxAC4AMAAwAFYAZQByAHMAaQBvAG4AIAAxAC4AMAAwACAARgBlAGIAcgB1AGEAcgB5ACAAMQA4ACwAIAAyADAAMQA2ACwAIABpAG4AaQB0AGkAYQBsACAAcgBlAGwAZQBhAHMAZQBFAHgAcwB1AHIAZwBlAEMAaABhAHIAYQBjAHQAZQByAHMAVABoAGkAcwAgAEYAbwBuAHQAIABTAG8AZgB0AHcAYQByAGUAIABpAHMAIABsAGkAYwBlAG4AcwBlAGQAIAB1AG4AZABlAHIAIAB0AGgAZQAgAFMASQBMACAATwBwAGUAbgAgAEYAbwBuAHQAIABMAGkAYwBlAG4AcwBlACwAIABWAGUAcgBzAGkAbwBuACAAMQAuADEALgAgAFQAaABpAHMAIABsAGkAYwBlAG4AcwBlACAAaQBzACAAYwBvAHAAaQBlAGQAIABiAGUAbABvAHcALAAgAGEAbgBkACAAaQBzACAAYQBsAHMAbwAgAGEAdgBhAGkAbABhAGIAbABlACAAdwBpAHQAaAAgAGEAIABGAEEAUQAgAGEAdAA6ACAAaAB0AHQAcAA6AC8ALwBzAGMAcgBpAHAAdABzAC4AcwBpAGwALgBvAHIAZwAvAE8ARgBMAA0ACgANAAoADQAKAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQANAAoAUwBJAEwAIABPAFAARQBOACAARgBPAE4AVAAgAEwASQBDAEUATgBTAEUAIABWAGUAcgBzAGkAbwBuACAAMQAuADEAIAAtACAAMgA2ACAARgBlAGIAcgB1AGEAcgB5ACAAMgAwADAANwANAAoALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAC0ALQAtAA0ACgANAAoAUABSAEUAQQBNAEIATABFAA0ACgBUAGgAZQAgAGcAbwBhAGwAcwAgAG8AZgAgAHQAaABlACAATwBwAGUAbgAgAEYAbwBuAHQAIABMAGkAYwBlAG4AcwBlACAAKABPAEYATAApACAAYQByAGUAIAB0AG8AIABzAHQAaQBtAHUAbABhAHQAZQAgAHcAbwByAGwAZAB3AGkAZABlACAAZABlAHYAZQBsAG8AcABtAGUAbgB0ACAAbwBmACAAYwBvAGwAbABhAGIAbwByAGEAdABpAHYAZQAgAGYAbwBuAHQAIABwAHIAbwBqAGUAYwB0AHMALAAgAHQAbwAgAHMAdQBwAHAAbwByAHQAIAB0AGgAZQAgAGYAbwBuAHQAIABjAHIAZQBhAHQAaQBvAG4AIABlAGYAZgBvAHIAdABzACAAbwBmACAAYQBjAGEAZABlAG0AaQBjACAAYQBuAGQAIABsAGkAbgBnAHUAaQBzAHQAaQBjACAAYwBvAG0AbQB1AG4AaQB0AGkAZQBzACwAIABhAG4AZAAgAHQAbwAgAHAAcgBvAHYAaQBkAGUAIABhACAAZgByAGUAZQAgAGEAbgBkACAAbwBwAGUAbgAgAGYAcgBhAG0AZQB3AG8AcgBrACAAaQBuACAAdwBoAGkAYwBoACAAZgBvAG4AdABzACAAbQBhAHkAIABiAGUAIABzAGgAYQByAGUAZAAgAGEAbgBkACAAaQBtAHAAcgBvAHYAZQBkACAAaQBuACAAcABhAHIAdABuAGUAcgBzAGgAaQBwACAAdwBpAHQAaAAgAG8AdABoAGUAcgBzAC4ADQAKAA0ACgBUAGgAZQAgAE8ARgBMACAAYQBsAGwAbwB3AHMAIAB0AGgAZQAgAGwAaQBjAGUAbgBzAGUAZAAgAGYAbwBuAHQAcwAgAHQAbwAgAGIAZQAgAHUAcwBlAGQALAAgAHMAdAB1AGQAaQBlAGQALAAgAG0AbwBkAGkAZgBpAGUAZAAgAGEAbgBkACAAcgBlAGQAaQBzAHQAcgBpAGIAdQB0AGUAZAAgAGYAcgBlAGUAbAB5ACAAYQBzACAAbABvAG4AZwAgAGEAcwAgAHQAaABlAHkAIABhAHIAZQAgAG4AbwB0ACAAcwBvAGwAZAAgAGIAeQAgAHQAaABlAG0AcwBlAGwAdgBlAHMALgAgAFQAaABlACAAZgBvAG4AdABzACwAIABpAG4AYwBsAHUAZABpAG4AZwAgAGEAbgB5ACAAZABlAHIAaQB2AGEAdABpAHYAZQAgAHcAbwByAGsAcwAsACAAYwBhAG4AIABiAGUAIABiAHUAbgBkAGwAZQBkACwAIABlAG0AYgBlAGQAZABlAGQALAAgAHIAZQBkAGkAcwB0AHIAaQBiAHUAdABlAGQAIABhAG4AZAAvAG8AcgAgAHMAbwBsAGQAIAB3AGkAdABoACAAYQBuAHkAIABzAG8AZgB0AHcAYQByAGUAIABwAHIAbwB2AGkAZABlAGQAIAB0AGgAYQB0ACAAYQBuAHkAIAByAGUAcwBlAHIAdgBlAGQAIABuAGEAbQBlAHMAIABhAHIAZQAgAG4AbwB0ACAAdQBzAGUAZAAgAGIAeQAgAGQAZQByAGkAdgBhAHQAaQB2AGUAIAB3AG8AcgBrAHMALgAgAFQAaABlACAAZgBvAG4AdABzACAAYQBuAGQAIABkAGUAcgBpAHYAYQB0AGkAdgBlAHMALAAgAGgAbwB3AGUAdgBlAHIALAAgAGMAYQBuAG4AbwB0ACAAYgBlACAAcgBlAGwAZQBhAHMAZQBkACAAdQBuAGQAZQByACAAYQBuAHkAIABvAHQAaABlAHIAIAB0AHkAcABlACAAbwBmACAAbABpAGMAZQBuAHMAZQAuACAAVABoAGUAIAByAGUAcQB1AGkAcgBlAG0AZQBuAHQAIABmAG8AcgAgAGYAbwBuAHQAcwAgAHQAbwAgAHIAZQBtAGEAaQBuACAAdQBuAGQAZQByACAAdABoAGkAcwAgAGwAaQBjAGUAbgBzAGUAIABkAG8AZQBzACAAbgBvAHQAIABhAHAAcABsAHkAIAB0AG8AIABhAG4AeQAgAGQAbwBjAHUAbQBlAG4AdAAgAGMAcgBlAGEAdABlAGQAIAB1AHMAaQBuAGcAIAB0AGgAZQAgAGYAbwBuAHQAcwAgAG8AcgAgAHQAaABlAGkAcgAgAGQAZQByAGkAdgBhAHQAaQB2AGUAcwAuAA0ACgANAAoARABFAEYASQBOAEkAVABJAE8ATgBTAA0ACgAiAEYAbwBuAHQAIABTAG8AZgB0AHcAYQByAGUAIgAgAHIAZQBmAGUAcgBzACAAdABvACAAdABoAGUAIABzAGUAdAAgAG8AZgAgAGYAaQBsAGUAcwAgAHIAZQBsAGUAYQBzAGUAZAAgAGIAeQAgAHQAaABlACAAQwBvAHAAeQByAGkAZwBoAHQAIABIAG8AbABkAGUAcgAoAHMAKQAgAHUAbgBkAGUAcgAgAHQAaABpAHMAIABsAGkAYwBlAG4AcwBlACAAYQBuAGQAIABjAGwAZQBhAHIAbAB5ACAAbQBhAHIAawBlAGQAIABhAHMAIABzAHUAYwBoAC4AIABUAGgAaQBzACAAbQBhAHkAIABpAG4AYwBsAHUAZABlACAAcwBvAHUAcgBjAGUAIABmAGkAbABlAHMALAAgAGIAdQBpAGwAZAAgAHMAYwByAGkAcAB0AHMAIABhAG4AZAAgAGQAbwBjAHUAbQBlAG4AdABhAHQAaQBvAG4ALgANAAoADQAKACIAUgBlAHMAZQByAHYAZQBkACAARgBvAG4AdAAgAE4AYQBtAGUAIgAgAHIAZQBmAGUAcgBzACAAdABvACAAYQBuAHkAIABuAGEAbQBlAHMAIABzAHAAZQBjAGkAZgBpAGUAZAAgAGEAcwAgAHMAdQBjAGgAIABhAGYAdABlAHIAIAB0AGgAZQAgAGMAbwBwAHkAcgBpAGcAaAB0ACAAcwB0AGEAdABlAG0AZQBuAHQAKABzACkALgANAAoADQAKACIATwByAGkAZwBpAG4AYQBsACAAVgBlAHIAcwBpAG8AbgAiACAAcgBlAGYAZQByAHMAIAB0AG8AIAB0AGgAZQAgAGMAbwBsAGwAZQBjAHQAaQBvAG4AIABvAGYAIABGAG8AbgB0ACAAUwBvAGYAdAB3AGEAcgBlACAAYwBvAG0AcABvAG4AZQBuAHQAcwAgAGEAcwAgAGQAaQBzAHQAcgBpAGIAdQB0AGUAZAAgAGIAeQAgAHQAaABlACAAQwBvAHAAeQByAGkAZwBoAHQAIABIAG8AbABkAGUAcgAoAHMAKQAuAA0ACgANAAoAIgBNAG8AZABpAGYAaQBlAGQAIABWAGUAcgBzAGkAbwBuACIAIAByAGUAZgBlAHIAcwAgAHQAbwAgAGEAbgB5ACAAZABlAHIAaQB2AGEAdABpAHYAZQAgAG0AYQBkAGUAIABiAHkAIABhAGQAZABpAG4AZwAgAHQAbwAsACAAZABlAGwAZQB0AGkAbgBnACwAIABvAHIAIABzAHUAYgBzAHQAaQB0AHUAdABpAG4AZwAgAC0ALQAgAGkAbgAgAHAAYQByAHQAIABvAHIAIABpAG4AIAB3AGgAbwBsAGUAIAAtAC0AIABhAG4AeQAgAG8AZgAgAHQAaABlACAAYwBvAG0AcABvAG4AZQBuAHQAcwAgAG8AZgAgAHQAaABlACAATwByAGkAZwBpAG4AYQBsACAAVgBlAHIAcwBpAG8AbgAsACAAYgB5ACAAYwBoAGEAbgBnAGkAbgBnACAAZgBvAHIAbQBhAHQAcwAgAG8AcgAgAGIAeQAgAHAAbwByAHQAaQBuAGcAIAB0AGgAZQAgAEYAbwBuAHQAIABTAG8AZgB0AHcAYQByAGUAIAB0AG8AIABhACAAbgBlAHcAIABlAG4AdgBpAHIAbwBuAG0AZQBuAHQALgANAAoADQAKACIAQQB1AHQAaABvAHIAIgAgAHIAZQBmAGUAcgBzACAAdABvACAAYQBuAHkAIABkAGUAcwBpAGcAbgBlAHIALAAgAGUAbgBnAGkAbgBlAGUAcgAsACAAcAByAG8AZwByAGEAbQBtAGUAcgAsACAAdABlAGMAaABuAGkAYwBhAGwAIAB3AHIAaQB0AGUAcgAgAG8AcgAgAG8AdABoAGUAcgAgAHAAZQByAHMAbwBuACAAdwBoAG8AIABjAG8AbgB0AHIAaQBiAHUAdABlAGQAIAB0AG8AIAB0AGgAZQAgAEYAbwBuAHQAIABTAG8AZgB0AHcAYQByAGUALgANAAoADQAKAFAARQBSAE0ASQBTAFMASQBPAE4AIAAmACAAQwBPAE4ARABJAFQASQBPAE4AUwANAAoAUABlAHIAbQBpAHMAcwBpAG8AbgAgAGkAcwAgAGgAZQByAGUAYgB5ACAAZwByAGEAbgB0AGUAZAAsACAAZgByAGUAZQAgAG8AZgAgAGMAaABhAHIAZwBlACwAIAB0AG8AIABhAG4AeQAgAHAAZQByAHMAbwBuACAAbwBiAHQAYQBpAG4AaQBuAGcAIABhACAAYwBvAHAAeQAgAG8AZgAgAHQAaABlACAARgBvAG4AdAAgAFMAbwBmAHQAdwBhAHIAZQAsACAAdABvACAAdQBzAGUALAAgAHMAdAB1AGQAeQAsACAAYwBvAHAAeQAsACAAbQBlAHIAZwBlACwAIABlAG0AYgBlAGQALAAgAG0AbwBkAGkAZgB5ACwAIAByAGUAZABpAHMAdAByAGkAYgB1AHQAZQAsACAAYQBuAGQAIABzAGUAbABsACAAbQBvAGQAaQBmAGkAZQBkACAAYQBuAGQAIAB1AG4AbQBvAGQAaQBmAGkAZQBkACAAYwBvAHAAaQBlAHMAIABvAGYAIAB0AGgAZQAgAEYAbwBuAHQAIABTAG8AZgB0AHcAYQByAGUALAAgAHMAdQBiAGoAZQBjAHQAIAB0AG8AIAB0AGgAZQAgAGYAbwBsAGwAbwB3AGkAbgBnACAAYwBvAG4AZABpAHQAaQBvAG4AcwA6AA0ACgANAAoAMQApACAATgBlAGkAdABoAGUAcgAgAHQAaABlACAARgBvAG4AdAAgAFMAbwBmAHQAdwBhAHIAZQAgAG4AbwByACAAYQBuAHkAIABvAGYAIABpAHQAcwAgAGkAbgBkAGkAdgBpAGQAdQBhAGwAIABjAG8AbQBwAG8AbgBlAG4AdABzACwAIABpAG4AIABPAHIAaQBnAGkAbgBhAGwAIABvAHIAIABNAG8AZABpAGYAaQBlAGQAIABWAGUAcgBzAGkAbwBuAHMALAAgAG0AYQB5ACAAYgBlACAAcwBvAGwAZAAgAGIAeQAgAGkAdABzAGUAbABmAC4ADQAKAA0ACgAyACkAIABPAHIAaQBnAGkAbgBhAGwAIABvAHIAIABNAG8AZABpAGYAaQBlAGQAIABWAGUAcgBzAGkAbwBuAHMAIABvAGYAIAB0AGgAZQAgAEYAbwBuAHQAIABTAG8AZgB0AHcAYQByAGUAIABtAGEAeQAgAGIAZQAgAGIAdQBuAGQAbABlAGQALAAgAHIAZQBkAGkAcwB0AHIAaQBiAHUAdABlAGQAIABhAG4AZAAvAG8AcgAgAHMAbwBsAGQAIAB3AGkAdABoACAAYQBuAHkAIABzAG8AZgB0AHcAYQByAGUALAAgAHAAcgBvAHYAaQBkAGUAZAAgAHQAaABhAHQAIABlAGEAYwBoACAAYwBvAHAAeQAgAGMAbwBuAHQAYQBpAG4AcwAgAHQAaABlACAAYQBiAG8AdgBlACAAYwBvAHAAeQByAGkAZwBoAHQAIABuAG8AdABpAGMAZQAgAGEAbgBkACAAdABoAGkAcwAgAGwAaQBjAGUAbgBzAGUALgAgAFQAaABlAHMAZQAgAGMAYQBuACAAYgBlACAAaQBuAGMAbAB1AGQAZQBkACAAZQBpAHQAaABlAHIAIABhAHMAIABzAHQAYQBuAGQALQBhAGwAbwBuAGUAIAB0AGUAeAB0ACAAZgBpAGwAZQBzACwAIABoAHUAbQBhAG4ALQByAGUAYQBkAGEAYgBsAGUAIABoAGUAYQBkAGUAcgBzACAAbwByACAAaQBuACAAdABoAGUAIABhAHAAcAByAG8AcAByAGkAYQB0AGUAIABtAGEAYwBoAGkAbgBlAC0AcgBlAGEAZABhAGIAbABlACAAbQBlAHQAYQBkAGEAdABhACAAZgBpAGUAbABkAHMAIAB3AGkAdABoAGkAbgAgAHQAZQB4AHQAIABvAHIAIABiAGkAbgBhAHIAeQAgAGYAaQBsAGUAcwAgAGEAcwAgAGwAbwBuAGcAIABhAHMAIAB0AGgAbwBzAGUAIABmAGkAZQBsAGQAcwAgAGMAYQBuACAAYgBlACAAZQBhAHMAaQBsAHkAIAB2AGkAZQB3AGUAZAAgAGIAeQAgAHQAaABlACAAdQBzAGUAcgAuAA0ACgANAAoAMwApACAATgBvACAATQBvAGQAaQBmAGkAZQBkACAAVgBlAHIAcwBpAG8AbgAgAG8AZgAgAHQAaABlACAARgBvAG4AdAAgAFMAbwBmAHQAdwBhAHIAZQAgAG0AYQB5ACAAdQBzAGUAIAB0AGgAZQAgAFIAZQBzAGUAcgB2AGUAZAAgAEYAbwBuAHQAIABOAGEAbQBlACgAcwApACAAdQBuAGwAZQBzAHMAIABlAHgAcABsAGkAYwBpAHQAIAB3AHIAaQB0AHQAZQBuACAAcABlAHIAbQBpAHMAcwBpAG8AbgAgAGkAcwAgAGcAcgBhAG4AdABlAGQAIABiAHkAIAB0AGgAZQAgAGMAbwByAHIAZQBzAHAAbwBuAGQAaQBuAGcAIABDAG8AcAB5AHIAaQBnAGgAdAAgAEgAbwBsAGQAZQByAC4AIABUAGgAaQBzACAAcgBlAHMAdAByAGkAYwB0AGkAbwBuACAAbwBuAGwAeQAgAGEAcABwAGwAaQBlAHMAIAB0AG8AIAB0AGgAZQAgAHAAcgBpAG0AYQByAHkAIABmAG8AbgB0ACAAbgBhAG0AZQAgAGEAcwAgAHAAcgBlAHMAZQBuAHQAZQBkACAAdABvACAAdABoAGUAIAB1AHMAZQByAHMALgANAAoADQAKADQAKQAgAFQAaABlACAAbgBhAG0AZQAoAHMAKQAgAG8AZgAgAHQAaABlACAAQwBvAHAAeQByAGkAZwBoAHQAIABIAG8AbABkAGUAcgAoAHMAKQAgAG8AcgAgAHQAaABlACAAQQB1AHQAaABvAHIAKABzACkAIABvAGYAIAB0AGgAZQAgAEYAbwBuAHQAIABTAG8AZgB0AHcAYQByAGUAIABzAGgAYQBsAGwAIABuAG8AdAAgAGIAZQAgAHUAcwBlAGQAIAB0AG8AIABwAHIAbwBtAG8AdABlACwAIABlAG4AZABvAHIAcwBlACAAbwByACAAYQBkAHYAZQByAHQAaQBzAGUAIABhAG4AeQAgAE0AbwBkAGkAZgBpAGUAZAAgAFYAZQByAHMAaQBvAG4ALAAgAGUAeABjAGUAcAB0ACAAdABvACAAYQBjAGsAbgBvAHcAbABlAGQAZwBlACAAdABoAGUAIABjAG8AbgB0AHIAaQBiAHUAdABpAG8AbgAoAHMAKQAgAG8AZgAgAHQAaABlACAAQwBvAHAAeQByAGkAZwBoAHQAIABIAG8AbABkAGUAcgAoAHMAKQAgAGEAbgBkACAAdABoAGUAIABBAHUAdABoAG8AcgAoAHMAKQAgAG8AcgAgAHcAaQB0AGgAIAB0AGgAZQBpAHIAIABlAHgAcABsAGkAYwBpAHQAIAB3AHIAaQB0AHQAZQBuACAAcABlAHIAbQBpAHMAcwBpAG8AbgAuAA0ACgANAAoANQApACAAVABoAGUAIABGAG8AbgB0ACAAUwBvAGYAdAB3AGEAcgBlACwAIABtAG8AZABpAGYAaQBlAGQAIABvAHIAIAB1AG4AbQBvAGQAaQBmAGkAZQBkACwAIABpAG4AIABwAGEAcgB0ACAAbwByACAAaQBuACAAdwBoAG8AbABlACwAIABtAHUAcwB0ACAAYgBlACAAZABpAHMAdAByAGkAYgB1AHQAZQBkACAAZQBuAHQAaQByAGUAbAB5ACAAdQBuAGQAZQByACAAdABoAGkAcwAgAGwAaQBjAGUAbgBzAGUALAAgAGEAbgBkACAAbQB1AHMAdAAgAG4AbwB0ACAAYgBlACAAZABpAHMAdAByAGkAYgB1AHQAZQBkACAAdQBuAGQAZQByACAAYQBuAHkAIABvAHQAaABlAHIAIABsAGkAYwBlAG4AcwBlAC4AIABUAGgAZQAgAHIAZQBxAHUAaQByAGUAbQBlAG4AdAAgAGYAbwByACAAZgBvAG4AdABzACAAdABvACAAcgBlAG0AYQBpAG4AIAB1AG4AZABlAHIAIAB0AGgAaQBzACAAbABpAGMAZQBuAHMAZQAgAGQAbwBlAHMAIABuAG8AdAAgAGEAcABwAGwAeQAgAHQAbwAgAGEAbgB5ACAAZABvAGMAdQBtAGUAbgB0ACAAYwByAGUAYQB0AGUAZAAgAHUAcwBpAG4AZwAgAHQAaABlACAARgBvAG4AdAAgAFMAbwBmAHQAdwBhAHIAZQAuAA0ACgANAAoAVABFAFIATQBJAE4AQQBUAEkATwBOAA0ACgBUAGgAaQBzACAAbABpAGMAZQBuAHMAZQAgAGIAZQBjAG8AbQBlAHMAIABuAHUAbABsACAAYQBuAGQAIAB2AG8AaQBkACAAaQBmACAAYQBuAHkAIABvAGYAIAB0AGgAZQAgAGEAYgBvAHYAZQAgAGMAbwBuAGQAaQB0AGkAbwBuAHMAIABhAHIAZQAgAG4AbwB0ACAAbQBlAHQALgANAAoADQAKAEQASQBTAEMATABBAEkATQBFAFIADQAKAFQASABFACAARgBPAE4AVAAgAFMATwBGAFQAVwBBAFIARQAgAEkAUwAgAFAAUgBPAFYASQBEAEUARAAgACIAQQBTACAASQBTACIALAAgAFcASQBUAEgATwBVAFQAIABXAEEAUgBSAEEATgBUAFkAIABPAEYAIABBAE4AWQAgAEsASQBOAEQALAAgAEUAWABQAFIARQBTAFMAIABPAFIAIABJAE0AUABMAEkARQBEACwAIABJAE4AQwBMAFUARABJAE4ARwAgAEIAVQBUACAATgBPAFQAIABMAEkATQBJAFQARQBEACAAVABPACAAQQBOAFkAIABXAEEAUgBSAEEATgBUAEkARQBTACAATwBGACAATQBFAFIAQwBIAEEATgBUAEEAQgBJAEwASQBUAFkALAAgAEYASQBUAE4ARQBTAFMAIABGAE8AUgAgAEEAIABQAEEAUgBUAEkAQwBVAEwAQQBSACAAUABVAFIAUABPAFMARQAgAEEATgBEACAATgBPAE4ASQBOAEYAUgBJAE4ARwBFAE0ARQBOAFQAIABPAEYAIABDAE8AUABZAFIASQBHAEgAVAAsACAAUABBAFQARQBOAFQALAAgAFQAUgBBAEQARQBNAEEAUgBLACwAIABPAFIAIABPAFQASABFAFIAIABSAEkARwBIAFQALgAgAEkATgAgAE4ATwAgAEUAVgBFAE4AVAAgAFMASABBAEwATAAgAFQASABFACAAQwBPAFAAWQBSAEkARwBIAFQAIABIAE8ATABEAEUAUgAgAEIARQAgAEwASQBBAEIATABFACAARgBPAFIAIABBAE4AWQAgAEMATABBAEkATQAsACAARABBAE0AQQBHAEUAUwAgAE8AUgAgAE8AVABIAEUAUgAgAEwASQBBAEIASQBMAEkAVABZACwAIABJAE4AQwBMAFUARABJAE4ARwAgAEEATgBZACAARwBFAE4ARQBSAEEATAAsACAAUwBQAEUAQwBJAEEATAAsACAASQBOAEQASQBSAEUAQwBUACwAIABJAE4AQwBJAEQARQBOAFQAQQBMACwAIABPAFIAIABDAE8ATgBTAEUAUQBVAEUATgBUAEkAQQBMACAARABBAE0AQQBHAEUAUwAsACAAVwBIAEUAVABIAEUAUgAgAEkATgAgAEEATgAgAEEAQwBUAEkATwBOACAATwBGACAAQwBPAE4AVABSAEEAQwBUACwAIABUAE8AUgBUACAATwBSACAATwBUAEgARQBSAFcASQBTAEUALAAgAEEAUgBJAFMASQBOAEcAIABGAFIATwBNACwAIABPAFUAVAAgAE8ARgAgAFQASABFACAAVQBTAEUAIABPAFIAIABJAE4AQQBCAEkATABJAFQAWQAgAFQATwAgAFUAUwBFACAAVABIAEUAIABGAE8ATgBUACAAUwBPAEYAVABXAEEAUgBFACAATwBSACAARgBSAE8ATQAgAE8AVABIAEUAUgAgAEQARQBBAEwASQBOAEcAUwAgAEkATgAgAFQASABFACAARgBPAE4AVAAgAFMATwBGAFQAVwBBAFIARQAuAAAAAgAAAAAAAP8GAGQAAAAAAAAAAAAAAAAAAAAAAAAAAABfAAMABAAFAAYABwAIAAkACgALAAwADQAOAA8AEAARABIAEwAUABUAFgAXABgAGQAaABsAHAAdAB4AHwAgACEAIgAjACQAJQAmACcAKAApACoAKwAsAC0ALgAvADAAMQAyADMANAA1ADYANwA4ADkAOgA7ADwAPQA+AD8AQABBAEIAQwBEAEUARgBHAEgASQBKAEsATABNAE4ATwBQAFEAUgBTAFQAVQBWAFcAWABZAFoAWwBcAF0AXgBfAGAAYQAAAAMACAACABAAAf//AAIAAAABAAAAAAABAAAADgAAAAAAAAAAAAIAAQAAAF4AAQABAAAACgBKAGQAAmN5cmwADmxhdG4AGAAEAAAAAP//AAAAEAACSVBBIAAaVklUIAAiAAD//wACAAEAAAAA//8AAQABAAD//wAAAAJrZXJuAA5tYXJrABQAAAABAAEAAAABAAAAAgAGAA4ABAAEAAEAEAACAAAAAQAsAAEADAAQAAAAIAAiAAIAAAABAAYAIQAyADYAQQBSAFYAAAAGAAEAjgAEAAAABgAWADAASgBkAHIAgAAGAA7/nAAhADYAQQA2ADIADQA2//IAUgAXAAYADv+cACEAWABBAFgAMgChADYAvQBSAE8ABgAO/nAAIf6TAEH+kwAy//kANgAOAFL/YQADAA7/nABSABcAVv/VAAMADv+cAFIANgBWAEwAAwAO/nAAUgAJAFYAGQABAAYAIQAyADYAQQBSAFYAAQAAAAoATgBoAAJjeXJsAA5sYXRuABoABAAAAAD//wABAAAAEAACSVBBIAAaVklUIAAiAAD//wACAAAAAQAA//8AAQAAAAD//wABAAAAAmFhbHQADnNtY3AAFAAAAAEAAAAAAAEAAAABAAQAAwAAAAEACAABABgAAwAMABAAFAABAEEAAQBSAAEAVgABAAMAIQAyADYAAA==" + +/***/ }, +/* 6 */ +/***/ function(module, exports, __webpack_require__) { + + 'use strict'; + + Object.defineProperty(exports, "__esModule", { + value: true + }); + exports.ChantDocument = exports.ChantScore = exports.ChantMapping = exports.ChantLineBreak = exports.TextOnly = exports.FaClef = exports.DoClef = exports.Clef = exports.Note = exports.NoteShapeModifiers = exports.NoteShape = exports.LiquescentType = undefined; + + var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } }; + + var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }(); + + var _Exsurge = __webpack_require__(1); + + var Exsurge = _interopRequireWildcard(_Exsurge); + + var _Exsurge2 = __webpack_require__(4); + + var _ExsurgeChant = __webpack_require__(7); + + var _ExsurgeChant2 = __webpack_require__(8); + + var _ExsurgeChant3 = __webpack_require__(9); + + var _Exsurge3 = __webpack_require__(10); + + function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key]; } } newObj.default = obj; return newObj; } } + + function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } + + function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; } + + function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; } // + // Author(s): + // Fr. Matthew Spencer, OSJ + // + // Copyright (c) 2008-2016 Fr. Matthew Spencer, OSJ + // + // Permission is hereby granted, free of charge, to any person obtaining a copy + // of this software and associated documentation files (the "Software"), to deal + // in the Software without restriction, including without limitation the rights + // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + // copies of the Software, and to permit persons to whom the Software is + // furnished to do so, subject to the following conditions: + // + // The above copyright notice and this permission notice shall be included in + // all copies or substantial portions of the Software. + // + // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + // THE SOFTWARE. + // + + var LiquescentType = exports.LiquescentType = { + None: 0, + + // flags that can be combined, though of course it + // it doesn't make sense to combine some! + Large: 1 << 0, + Small: 1 << 1, + Ascending: 1 << 2, + Descending: 1 << 3, + InitioDebilis: 1 << 4, + + // handy liquescent types + LargeAscending: 1 << 0 | 1 << 2, + LargeDescending: 1 << 0 | 1 << 3, + SmallAscending: 1 << 1 | 1 << 2, + SmallDescending: 1 << 1 | 1 << 3 + }; + + var NoteShape = exports.NoteShape = { + // shapes + Default: 0, + Virga: 1, + Inclinatum: 2, + Quilisma: 3, + Stropha: 4, + Oriscus: 5 + }; + + var NoteShapeModifiers = exports.NoteShapeModifiers = { + + // flags which modify the shape + // not all of them apply to every shape of course + None: 0, + Ascending: 1 << 0, + Descending: 1 << 1, + Cavum: 1 << 2, + Stemmed: 1 << 3 + }; + + /** + * @class + */ + + var Note = exports.Note = function (_ChantLayoutElement) { + _inherits(Note, _ChantLayoutElement); + + /** + * @para {Pitch} pitch + */ + + function Note(pitch) { + _classCallCheck(this, Note); + + var _this = _possibleConstructorReturn(this, Object.getPrototypeOf(Note).call(this)); + + if (typeof pitch !== 'undefined') _this.pitch = pitch;else _this.pitch = null; + + _this.glyphVisualizer = null; + + // The staffPosition on a note is an integer that indicates the vertical position on the staff. + // 0 is the center space on the staff (equivalent to gabc 'g'). Positive numbers go up + // the staff, and negative numbers go down, i.e., 1 is gabc 'h', 2 is gabc 'i', -1 is gabc 'f', etc. + _this.staffPosition = 0; + _this.liquescent = LiquescentType.None; + _this.shape = NoteShape.Default; + _this.shapeModifiers = NoteShapeModifiers.None; + + // notes keep track of the neume they belong to in order to facilitate layout + // this.neume gets set when a note is added to a neume via Neume.addNote() + _this.neume = null; + + // various markings that can exist on a note, organized by type + // for faster access and simpler code logic + _this.epismata = []; + _this.morae = []; // silly to have an array of these, but gabc allows multiple morae per note! + + // these are set on the note when they are needed, otherwise, they're undefined + // this.ictus + // this.accuteAccent + // this.braceStart + // this.braceEnd + return _this; + } + + _createClass(Note, [{ + key: 'setGlyph', + value: function setGlyph(ctxt, glyphCode) { + if (this.glyphVisualizer) this.glyphVisualizer.setGlyph(ctxt, glyphCode);else this.glyphVisualizer = new _Exsurge2.GlyphVisualizer(ctxt, glyphCode); + + this.glyphVisualizer.setStaffPosition(ctxt, this.staffPosition); + + // assign glyphvisualizer metrics to this note + this.bounds.x = this.glyphVisualizer.bounds.x; + this.bounds.y = this.glyphVisualizer.bounds.y; + this.bounds.width = this.glyphVisualizer.bounds.width; + this.bounds.height = this.glyphVisualizer.bounds.height; + + this.origin.x = this.glyphVisualizer.origin.x; + this.origin.y = this.glyphVisualizer.origin.y; + } + + // a utility function for modifiers + + }, { + key: 'shapeModifierMatches', + value: function shapeModifierMatches(shapeModifier) { + if (shapeModifier === NoteShapeModifiers.None) return this.shapeModifier === NoteShapeModifiers.None;else return this.shapeModifier & shapeModifier !== 0; + } + }, { + key: 'draw', + value: function draw(ctxt) { + + this.glyphVisualizer.bounds.x = this.bounds.x; + this.glyphVisualizer.bounds.y = this.bounds.y; + + this.glyphVisualizer.draw(ctxt); + } + }, { + key: 'createSvgFragment', + value: function createSvgFragment(ctxt) { + + this.glyphVisualizer.bounds.x = this.bounds.x; + this.glyphVisualizer.bounds.y = this.bounds.y; + return this.glyphVisualizer.createSvgFragment(ctxt); + } + }]); + + return Note; + }(_Exsurge2.ChantLayoutElement); + + var Clef = exports.Clef = function (_ChantNotationElement) { + _inherits(Clef, _ChantNotationElement); + + function Clef(staffPosition, octave) { + var defaultAccidental = arguments.length <= 2 || arguments[2] === undefined ? null : arguments[2]; + + _classCallCheck(this, Clef); + + var _this2 = _possibleConstructorReturn(this, Object.getPrototypeOf(Clef).call(this)); + + _this2.isClef = true; + _this2.staffPosition = staffPosition; + _this2.octave = octave; + _this2.defaultAccidental = defaultAccidental; + _this2.activeAccidental = defaultAccidental; + return _this2; + } + + _createClass(Clef, [{ + key: 'resetAccidentals', + value: function resetAccidentals() { + this.activeAccidental = this.defaultAccidental; + } + }, { + key: 'pitchToStaffPosition', + value: function pitchToStaffPosition(pitch) {} + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + + ctxt.activeClef = this; + + if (this.defaultAccidental) this.defaultAccidental.performLayout(ctxt); + + _get(Object.getPrototypeOf(Clef.prototype), 'performLayout', this).call(this, ctxt); + } + }, { + key: 'finishLayout', + value: function finishLayout(ctxt) { + + // if we have a default accidental, then add a glyph for it now + if (this.defaultAccidental) { + var accidentalGlyph = this.defaultAccidental.createGlyphVisualizer(ctxt); + accidentalGlyph.bounds.x += this.visualizers[0].bounds.right() + ctxt.intraNeumeSpacing; + this.addVisualizer(accidentalGlyph); + } + + _get(Object.getPrototypeOf(Clef.prototype), 'finishLayout', this).call(this, ctxt); + } + }], [{ + key: 'default', + value: function _default() { + return __defaultDoClef; + } + }]); + + return Clef; + }(_Exsurge2.ChantNotationElement); + + var DoClef = exports.DoClef = function (_Clef) { + _inherits(DoClef, _Clef); + + function DoClef(staffPosition, octave) { + var defaultAccidental = arguments.length <= 2 || arguments[2] === undefined ? null : arguments[2]; + + _classCallCheck(this, DoClef); + + var _this3 = _possibleConstructorReturn(this, Object.getPrototypeOf(DoClef).call(this, staffPosition, octave, defaultAccidental)); + + _this3.leadingSpace = 0.0; + return _this3; + } + + _createClass(DoClef, [{ + key: 'pitchToStaffPosition', + value: function pitchToStaffPosition(pitch) { + return (pitch.octave - this.octave) * 7 + this.staffPosition + _Exsurge.Pitch.stepToStaffOffset(pitch.step) - _Exsurge.Pitch.stepToStaffOffset(_Exsurge.Step.Do); + } + }, { + key: 'staffPositionToPitch', + value: function staffPositionToPitch(staffPosition) { + var offset = staffPosition - this.staffPosition; + var octaveOffset = Math.floor(offset / 7); + + var step = _Exsurge.Pitch.staffOffsetToStep(offset); + + if (this.defaultAccidental !== null && step === this.defaultAccidental.step) step += this.defaultAccidental.accidentalType; + + return new _Exsurge.Pitch(step, this.octave + octaveOffset); + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(DoClef.prototype), 'performLayout', this).call(this, ctxt); + + var glyph = new _Exsurge2.GlyphVisualizer(ctxt, _Exsurge2.GlyphCode.DoClef); + glyph.setStaffPosition(ctxt, this.staffPosition); + this.addVisualizer(glyph); + + this.finishLayout(ctxt); + } + }, { + key: 'clone', + value: function clone() { + return new DoClef(this.staffPosition, this.octave, this.defaultAccidental); + } + }]); + + return DoClef; + }(Clef); + + var __defaultDoClef = new DoClef(1, 2); + + var FaClef = exports.FaClef = function (_Clef2) { + _inherits(FaClef, _Clef2); + + function FaClef(staffPosition, octave) { + var defaultAccidental = arguments.length <= 2 || arguments[2] === undefined ? null : arguments[2]; + + _classCallCheck(this, FaClef); + + var _this4 = _possibleConstructorReturn(this, Object.getPrototypeOf(FaClef).call(this, staffPosition, octave, defaultAccidental)); + + _this4.octave = octave; + + _this4.leadingSpace = 0; + return _this4; + } + + _createClass(FaClef, [{ + key: 'pitchToStaffPosition', + value: function pitchToStaffPosition(pitch) { + return (pitch.octave - this.octave) * 7 + this.staffPosition + _Exsurge.Pitch.stepToStaffOffset(pitch.step) - _Exsurge.Pitch.stepToStaffOffset(_Exsurge.Step.Fa); + } + }, { + key: 'staffPositionToPitch', + value: function staffPositionToPitch(staffPosition) { + var offset = staffPosition - this.staffPosition + 3; // + 3 because it's a fa clef (3 == offset from Do) + var octaveOffset = Math.floor(offset / 7); + + var step = _Exsurge.Pitch.staffOffsetToStep(offset); + + if (step === _Exsurge.Step.Ti && this.defaultAccidental === _ExsurgeChant2.AccidentalType.Flat) step = _Exsurge.Step.Te; + + return new _Exsurge.Pitch(step, this.octave + octaveOffset); + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(FaClef.prototype), 'performLayout', this).call(this, ctxt); + + var glyph = new _Exsurge2.GlyphVisualizer(ctxt, _Exsurge2.GlyphCode.FaClef); + glyph.setStaffPosition(ctxt, this.staffPosition); + this.addVisualizer(glyph); + + this.finishLayout(ctxt); + } + }, { + key: 'clone', + value: function clone() { + return new FaClef(this.staffPosition, this.octave, this.defaultAccidental); + } + }]); + + return FaClef; + }(Clef); + + /* + * TextOnly + */ + + + var TextOnly = exports.TextOnly = function (_ChantNotationElement2) { + _inherits(TextOnly, _ChantNotationElement2); + + function TextOnly() { + _classCallCheck(this, TextOnly); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(TextOnly).call(this)); + } + + _createClass(TextOnly, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(TextOnly.prototype), 'performLayout', this).call(this, ctxt); + + // add an empty glyph as a placeholder + this.addVisualizer(new _Exsurge2.GlyphVisualizer(ctxt, _Exsurge2.GlyphCode.None)); + + this.origin.x = 0; + this.origin.y = 0; + + this.finishLayout(ctxt); + } + }]); + + return TextOnly; + }(_Exsurge2.ChantNotationElement); + + var ChantLineBreak = exports.ChantLineBreak = function (_ChantNotationElement3) { + _inherits(ChantLineBreak, _ChantNotationElement3); + + function ChantLineBreak(justify) { + _classCallCheck(this, ChantLineBreak); + + var _this6 = _possibleConstructorReturn(this, Object.getPrototypeOf(ChantLineBreak).call(this)); + + _this6.justify = justify; + return _this6; + } + + _createClass(ChantLineBreak, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + + // reset the bounds before doing a layout + this.bounds = new _Exsurge.Rect(0, 0, 0, 0); + } + }, { + key: 'clone', + value: function clone() { + var lb = new ChantLineBreak(); + lb.justify = this.justify; + + return lb; + } + }]); + + return ChantLineBreak; + }(_Exsurge2.ChantNotationElement); + + // a chant mapping is a lightweight format independent way of + // tracking how a chant language (e.g., gabc) has been + // mapped to exsurge notations. + + + var ChantMapping = + + // source can be any object type. in the case of gabc, source is a text + // string that maps to a gabc word (e.g.: "no(g)bis(fg)"). + // notations is an array of ChantNotationElements + exports.ChantMapping = function ChantMapping(source, notations) { + _classCallCheck(this, ChantMapping); + + this.source = source; + this.notations = notations; + }; + + /* + * Score, document + */ + + + var ChantScore = exports.ChantScore = function () { + + // mappings is an array of ChantMappings. + + function ChantScore(ctxt) { + var mappings = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1]; + var useDropCap = arguments[2]; + + _classCallCheck(this, ChantScore); + + this.mappings = mappings; + + this.lines = []; + this.notes = []; + + this.startingClef = null; + + this.useDropCap = useDropCap; + this.dropCap = null; + + this.annotation = null; + + this.compiled = false; + + this.autoColoring = true; + this.needsLayout = true; + + // valid after chant lines are created... + this.bounds = new _Exsurge.Rect(); + + this.updateNotations(ctxt); + } + + _createClass(ChantScore, [{ + key: 'updateNotations', + value: function updateNotations(ctxt) { + + var i; + + // flatten all mappings into one array for N(0) access to notations + this.notations = []; + for (i = 0; i < this.mappings.length; i++) { + this.notations = this.notations.concat(this.mappings[i].notations); + } // find the starting clef... + // start with a default clef in case the notations don't provide one. + this.startingClef = null; + var defaultClef = new DoClef(1, 2); + + for (i = 0; i < this.notations.length; i++) { + + // if there are neumes before the clef, then we just keep the default clef above + if (this.notations[i].isNeume) { + this.startingClef = defaultClef; + break; + } + + // otherwise, if we find a clef, before neumes then we use that as our default + if (this.notations[i].isClef) { + this.startingClef = this.notations[i]; + + // the clef is taken out of the notations... + this.notations.splice(i, 1); // remove a single notation + + break; + } + } + + // if we've reached this far and we *still* don't have a clef, then there aren't even + // any neumes in the score. still, set the default clef just for good measure + if (!this.startingClef) this.startingClef = defaultClef; + + // update drop cap + if (this.useDropCap) this.recreateDropCap(ctxt); + + this.needsLayout = true; + } + }, { + key: 'recreateDropCap', + value: function recreateDropCap(ctxt) { + + // find the first notation with lyrics to use + for (var i = 0; i < this.notations.length; i++) { + if (this.notations[i].hasLyrics() && this.notations[i].lyrics[0] !== null) { + this.dropCap = this.notations[i].lyrics[0].generateDropCap(ctxt); + return; + } + } + } + + // this is the the synchronous version of performLayout that + // process everything without yielding to any other workers/threads. + // good for server side processing or very small chant pieces. + + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + + if (this.needsLayout === false) return; // nothing to do here! + + // setup the context + ctxt.activeClef = this.startingClef; + ctxt.notations = this.notations; + ctxt.currNotationIndex = 0; + + if (this.dropCap) this.dropCap.recalculateMetrics(ctxt); + + if (this.annotation) this.annotation.recalculateMetrics(ctxt); + + for (var i = 0; i < this.notations.length; i++) { + this.notations[i].performLayout(ctxt); + ctxt.currNotationIndex++; + } + + this.needsLayout = false; + } + + // for web applications, probably performLayoutAsync would be more + // apppropriate that the above performLayout, since it will process + // the notations without locking up the UI thread. + + }, { + key: 'performLayoutAsync', + value: function performLayoutAsync(ctxt, finishedCallback) { + var _this7 = this; + + if (this.needsLayout === false) { + if (finishedCallback) setTimeout(function () { + return finishedCallback(); + }, 0); + + return; // nothing to do here! + } + + // setup the context + ctxt.activeClef = this.startingClef; + ctxt.notations = this.notations; + ctxt.currNotationIndex = 0; + + if (this.dropCap) this.dropCap.recalculateMetrics(ctxt); + + if (this.annotation) this.annotation.recalculateMetrics(ctxt); + + setTimeout(function () { + return _this7.layoutElementsAsync(ctxt, 0, finishedCallback); + }, 0); + } + }, { + key: 'layoutElementsAsync', + value: function layoutElementsAsync(ctxt, index, finishedCallback) { + var _this8 = this; + + if (index >= this.notations.length) { + this.needsLayout = false; + + if (finishedCallback) setTimeout(function () { + return finishedCallback(); + }, 0); + + return; + } + + if (index === 0) ctxt.activeClef = this.startingClef; + + var timeout = new Date().getTime() + 50; // process for fifty milliseconds + do { + var notation = this.notations[index]; + if (notation.needsLayout) { + ctxt.currNotationIndex = index; + notation.performLayout(ctxt); + } + + index++; + } while (index < this.notations.length && new Date().getTime() < timeout); + + // schedule the next block of processing + setTimeout(function () { + return _this8.layoutElementsAsync(ctxt, index, finishedCallback); + }, 0); + } + }, { + key: 'layoutChantLines', + value: function layoutChantLines(ctxt, width, finishedCallback) { + + this.lines = []; + + var y = 0; + var currIndex = 0; + + ctxt.activeClef = this.startingClef; + + do { + + var line = new _ExsurgeChant.ChantLine(this); + + line.buildFromChantNotationIndex(ctxt, currIndex, width); + currIndex = line.notationsStartIndex + line.numNotationsOnLine; + line.performLayout(ctxt); + this.lines.push(line); + + line.bounds.y = -line.bounds.y + y; + y += line.bounds.height + ctxt.staffInterval * 1.5; + } while (currIndex < this.notations.length); + + var lastLine = this.lines[this.lines.length - 1]; + + this.bounds.x = 0; + this.bounds.y = 0; + this.bounds.width = lastLine.bounds.width; + this.bounds.height = y; + + if (finishedCallback) finishedCallback(this); + } + }, { + key: 'draw', + value: function draw(ctxt) { + + var canvasCtxt = ctxt.canvasCtxt; + + canvasCtxt.clearRect(0, 0, ctxt.canvas.width, ctxt.canvas.height); + + canvasCtxt.translate(this.bounds.x, this.bounds.y); + + for (var i = 0; i < this.lines.length; i++) { + this.lines[i].draw(ctxt); + }canvasCtxt.translate(-this.bounds.x, -this.bounds.y); + } + }, { + key: 'createSvg', + value: function createSvg(ctxt) { + + var fragment = ""; + + // create defs section + for (var def in ctxt.defs) { + if (ctxt.defs.hasOwnProperty(def)) fragment += ctxt.defs[def]; + }fragment = _Exsurge2.QuickSvg.createFragment('defs', {}, fragment); + + for (var i = 0; i < this.lines.length; i++) { + fragment += this.lines[i].createSvgFragment(ctxt); + }fragment = _Exsurge2.QuickSvg.createFragment('g', {}, fragment); + + fragment = _Exsurge2.QuickSvg.createFragment('svg', { + 'xmlns': 'http://www.w3.org/2000/svg', + 'version': '1.1', + 'xmlns:xlink': 'http://www.w3.org/1999/xlink', + 'class': 'ChantScore', + 'width': this.bounds.width, + 'height': this.bounds.height + }, fragment); + + return fragment; + } + }, { + key: 'unserializeFromJson', + value: function unserializeFromJson(data) { + this.autoColoring = data['auto-coloring']; + + if (data.annotation !== null && data.annotation !== "") { + // create the annotation + this.annotation = new _Exsurge2.Annotation(ctxt, data.annotation); + } else this.annotation = null; + + var createDropCap = data['drop-cap'] === 'auto' ? true : false; + + _Exsurge3.Gabc.parseChantNotations(data.notations, this, createDropCap); + } + }, { + key: 'serializeToJson', + value: function serializeToJson() { + var data = {}; + + data['type'] = "score"; + data['auto-coloring'] = true; + + if (this.annotation !== null) data.annotation = this.annotation.unsanitizedText;else data.annotation = ""; + + return data; + } + }]); + + return ChantScore; + }(); + + var ChantDocument = exports.ChantDocument = function () { + function ChantDocument() { + _classCallCheck(this, ChantDocument); + + var defaults = { + layout: { + units: "mm", + 'default-font': { + 'font-family': "Crimson", + 'font-size': 14 + }, + page: { + width: 8.5, + height: 11, + 'margin-left': 0, + 'margin-top': 0, + 'margin-right': 0, + 'margin-bottom': 0 + } + }, + scores: [] + }; + + // default layout + this.copyLayout(this, defaults); + + this.scores = defaults.scores; + } + + _createClass(ChantDocument, [{ + key: 'copyLayout', + value: function copyLayout(to, from) { + + to.layout = { + units: from.layout.units, + 'default-font': { + 'font-family': from.layout['default-font']['font-family'], + 'font-size': from.layout['default-font']['font-size'] + }, + page: { + width: from.layout.page.width, + height: from.layout.page.height, + 'margin-left': from.layout.page['margin-left'], + 'margin-top': from.layout.page['margin-top'], + 'margin-right': from.layout.page['margin-right'], + 'margin-bottom': from.layout.page['margin-bottom'] + } + }; + } + }, { + key: 'unserializeFromJson', + value: function unserializeFromJson(data) { + + this.copyLayout(this, data); + + this.scores = []; + + // read in the scores + for (var i = 0; i < data.scores.length; i++) { + var score = new ChantScore(); + + score.unserializeFromJson(data.scores[i]); + this.scores.push(score); + } + } + }, { + key: 'serializeToJson', + value: function serializeToJson() { + var data = {}; + + this.copyLayout(data, this); + + data.scores = []; + + // save scores... + for (var i = 0; i < this.scores.length; i++) { + data.scores.push(this.scores[i].serializeToJson()); + }return data; + } + }]); + + return ChantDocument; + }(); + +/***/ }, +/* 7 */ +/***/ function(module, exports, __webpack_require__) { + + 'use strict'; + + Object.defineProperty(exports, "__esModule", { + value: true + }); + exports.ChantLine = undefined; + + var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }(); + + var _Exsurge = __webpack_require__(1); + + var Exsurge = _interopRequireWildcard(_Exsurge); + + var _Exsurge2 = __webpack_require__(4); + + var _Exsurge3 = __webpack_require__(6); + + var _Exsurge4 = __webpack_require__(3); + + var _ExsurgeChant = __webpack_require__(8); + + var _ExsurgeChant2 = __webpack_require__(9); + + function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key]; } } newObj.default = obj; return newObj; } } + + function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } + + function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; } + + function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; } // + // Author(s): + // Fr. Matthew Spencer, OSJ + // + // Copyright (c) 2008-2016 Fr. Matthew Spencer, OSJ + // + // Permission is hereby granted, free of charge, to any person obtaining a copy + // of this software and associated documentation files (the "Software"), to deal + // in the Software without restriction, including without limitation the rights + // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + // copies of the Software, and to permit persons to whom the Software is + // furnished to do so, subject to the following conditions: + // + // The above copyright notice and this permission notice shall be included in + // all copies or substantial portions of the Software. + // + // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + // THE SOFTWARE. + // + + // a chant line represents one staff line on the page. ChantLines are created by the score + // and laid out by the page + + var ChantLine = exports.ChantLine = function (_ChantLayoutElement) { + _inherits(ChantLine, _ChantLayoutElement); + + function ChantLine(score) { + _classCallCheck(this, ChantLine); + + var _this = _possibleConstructorReturn(this, Object.getPrototypeOf(ChantLine).call(this)); + + _this.score = score; + + _this.notationsStartIndex = 0; + _this.numNotationsOnLine = 0; + _this.notationBounds = null; // Rect + + _this.staffLeft = 0; + _this.staffRight = 0; + + _this.startingClef = null; // necessary for the layout process + _this.custos = null; + + _this.justify = true; + + // these are markings that exist at the chant line level rather than at the neume level. + _this.ledgerLines = []; + _this.braces = []; + + _this.nextLine = null; + _this.previousLine = null; // for layout assistance + + _this.lyricLineHeights = []; // height of each text line + _this.lyricLineBaselines = []; // offsets from the top of the text line to the baseline + + // fixme: make these configurable values from the score + _this.spaceAfterNotations = 0; // the space between the notation bounds and the first text track + _this.spaceBetweenTextTracks = 0; // spacing between each text track + return _this; + } + + _createClass(ChantLine, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + + // start off with a rectangle that holds at least the four staff lines + // we fudge the 3 to 3.1 so that the svg doesn't crop off the upper/lower staff lines... + this.notationBounds = new _Exsurge.Rect(this.staffLeft, -3.1 * ctxt.staffInterval, this.staffRight - this.staffLeft, 6.2 * ctxt.staffInterval); + + // run through all the elements of the line and calculate the bounds of the notations, + // as well as the bounds of each text track we will use + var i; + var notations = this.score.notations; + var lastIndex = this.notationsStartIndex + this.numNotationsOnLine; + var notation = null; + + this.notationBounds.union(this.startingClef.bounds); + + // reset the lyric line offsets before we [re]calculate them now + this.lyricLineHeights = []; + this.lyricLineBaselines = []; + + for (i = this.notationsStartIndex; i < lastIndex; i++) { + notation = notations[i]; + + this.notationBounds.union(notation.bounds); + + // keep track of lyric line offsets + for (j = 0; j < notation.lyrics.length; j++) { + if (this.lyricLineHeights.length < j + 1) { + this.lyricLineHeights.push(0); + this.lyricLineBaselines.push(0); + } + + this.lyricLineHeights[j] = Math.max(this.lyricLineHeights[j], notation.lyrics[j].bounds.height); + this.lyricLineBaselines[j] = Math.max(this.lyricLineBaselines[j], notation.lyrics[j].origin.y); + } + } + + if (this.custos) this.notationBounds.union(this.custos.bounds); + + // finalize the lyrics placement + for (i = this.notationsStartIndex; i < lastIndex; i++) { + notation = notations[i]; + + var offset = this.notationBounds.y + this.notationBounds.height; + + for (var j = 0; j < notation.lyrics.length; j++) { + notation.lyrics[j].bounds.y = offset + this.lyricLineBaselines[j]; + offset += this.lyricLineHeights[j]; + } + } + + // add any braces to the notationBounds as well + for (i = 0; i < this.braces.length; i++) { + this.notationBounds.union(this.braces[i].bounds); + }var totalHeight = this.notationBounds.height; + + // add up the lyric line heights to get the total height of the chant line + for (i = 0; i < this.lyricLineHeights.length; i++) { + totalHeight += this.lyricLineHeights[i]; + } // dropCap and the annotations + if (this.notationsStartIndex === 0) { + + if (this.score.dropCap !== null) { + + var dropCapY; + if (this.lyricLineHeights.length > 0) { + dropCapY = this.notationBounds.y + this.notationBounds.height + this.lyricLineBaselines[0]; + } else dropCapY = this.notationBounds.y + this.notationBounds.height; + + // drop caps and annotations are drawn from their center, so aligning them + // horizontally is as easy as this.staffLeft / 2 + this.score.dropCap.bounds.x = this.staffLeft / 2; + this.score.dropCap.bounds.y = dropCapY; + } + + if (this.score.annotation !== null) { + // annotations use dominant-baseline to align text to the top + this.score.annotation.bounds.x = this.staffLeft / 2; + this.score.annotation.bounds.y = -ctxt.staffInterval * 3; + } + } + + this.notationBounds.height += ctxt.lyricTextSize; + + this.bounds.x = 0; + this.bounds.y = this.notationBounds.y; + this.bounds.width = this.notationBounds.right(); + this.bounds.height = totalHeight; + + // the origin of the chant line's coordinate space is at the center line of the left extremity of the staff + this.origin = new _Exsurge.Point(this.staffLeft, -this.notationBounds.y); + } + }, { + key: 'draw', + value: function draw(ctxt) { + + var canvasCtxt = ctxt.canvasCtxt; + + canvasCtxt.translate(this.bounds.x, this.bounds.y); + + // draw the chant lines + var i, + x1 = this.staffLeft, + x2 = this.staffRight, + y; + + canvasCtxt.lineWidth = Math.round(ctxt.staffLineWeight); + canvasCtxt.strokeStyle = ctxt.staffLineWeight; + + for (i = -3; i <= 3; i += 2) { + + y = Math.round(ctxt.staffInterval * i) + 0.5; + + canvasCtxt.beginPath(); + canvasCtxt.moveTo(x1, y); + canvasCtxt.lineTo(x2, y); + canvasCtxt.stroke(); + } + + // draw the ledger lines + for (i = 0; i < this.ledgerLines.length; i++) { + + var ledgerLine = this.ledgerLines[i]; + y = ctxt.calculateHeightFromStaffPosition(ledgerLine.staffPosition); + + canvasCtxt.beginPath(); + canvasCtxt.moveTo(ledgerLine.x1, y); + canvasCtxt.lineTo(ledgerLine.x2, y); + canvasCtxt.stroke(); + } + + // fixme: draw the braces + + // draw the dropCap and the annotations + if (this.notationsStartIndex === 0) { + + if (this.score.dropCap !== null) this.score.dropCap.draw(ctxt); + + if (this.score.annotation !== null) this.score.annotation.draw(ctxt); + } + + // draw the notations + var notations = this.score.notations; + var lastIndex = this.notationsStartIndex + this.numNotationsOnLine; + + for (i = this.notationsStartIndex; i < lastIndex; i++) { + notations[i].draw(ctxt); + }this.startingClef.draw(ctxt); + + if (this.custos) this.custos.draw(ctxt); + + canvasCtxt.translate(-this.bounds.x, -this.bounds.y); + } + }, { + key: 'createSvgFragment', + value: function createSvgFragment(ctxt) { + var inner = ""; + + // add the chant lines + var i, + x1 = this.staffLeft, + x2 = this.staffRight; + + // create the staff lines + for (i = -3; i <= 3; i += 2) { + + inner += _Exsurge2.QuickSvg.createFragment('line', { + 'x1': x1, + 'y1': ctxt.staffInterval * i, + 'x2': x2, + 'y2': ctxt.staffInterval * i, + 'stroke': ctxt.staffLineColor, + 'stroke-width': ctxt.staffLineWeight, + 'class': 'staffLine' + }); + } + + // create the ledger lines + for (i = 0; i < this.ledgerLines.length; i++) { + + var ledgerLine = this.ledgerLines[i]; + var y = ctxt.calculateHeightFromStaffPosition(ledgerLine.staffPosition); + + inner += _Exsurge2.QuickSvg.createFragment('line', { + 'x1': ledgerLine.x1, + 'y1': y, + 'x2': ledgerLine.x2, + 'y2': y, + 'stroke': ctxt.staffLineColor, + 'stroke-width': ctxt.staffLineWeight, + 'class': 'ledgerLine' + }); + } + + // add any braces + for (i = 0; i < this.braces.length; i++) { + inner += this.braces[i].createSvgFragment(ctxt); + } // dropCap and the annotations + if (this.notationsStartIndex === 0) { + + if (this.score.dropCap !== null) inner += this.score.dropCap.createSvgFragment(ctxt); + + if (this.score.annotation !== null) inner += this.score.annotation.createSvgFragment(ctxt); + } + + inner += this.startingClef.createSvgFragment(ctxt); + + var notations = this.score.notations; + var lastIndex = this.notationsStartIndex + this.numNotationsOnLine; + + // add all of the notations + for (i = this.notationsStartIndex; i < lastIndex; i++) { + inner += notations[i].createSvgFragment(ctxt); + }if (this.custos) inner += this.custos.createSvgFragment(ctxt); + + return _Exsurge2.QuickSvg.createFragment('g', { + 'class': 'chantLine', + 'transform': 'translate(' + this.bounds.x + ',' + this.bounds.y + ')' + }, inner); + } + + // code below based on code by: https://gist.github.com/alexhornbake + // + // optimized for braces that are only drawn horizontally. + // returns svg path string ready to insert into svg doc + + }, { + key: 'generateCurlyBraceDrawable', + value: function generateCurlyBraceDrawable(ctxt, x1, x2, y, isAbove) { + + var h; + + if (isAbove) h = -ctxt.staffInterval / 2;else h = ctxt.staffInterval / 2; + + // and q factor, .5 is normal, higher q = more expressive bracket + var q = 0.6; + + var dx = -1; + var len = x2 - x1; + + //Calculate Control Points of path, + var qx1 = x1; + var qy1 = y + q * h; + var qx2 = x1 + .25 * len; + var qy2 = y + (1 - q) * h; + var tx1 = x1 + .5 * len; + var ty1 = y + h; + var qx3 = x2; + var qy3 = y + q * h; + var qx4 = x1 + .75 * len; + var qy4 = y + (1 - q) * h; + var d = "M " + x1 + " " + y + " Q " + qx1 + " " + qy1 + " " + qx2 + " " + qy2 + " T " + tx1 + " " + ty1 + " M " + x2 + " " + y + " Q " + qx3 + " " + qy3 + " " + qx4 + " " + qy4 + " T " + tx1 + " " + ty1; + + return _Exsurge2.QuickSvg.createFragment('path', { + 'd': d, + 'stroke': ctxt.neumeLineColor, + 'stroke-width': ctxt.neumeLineWeight + 'px', + 'fill': 'none' + }); + } + }, { + key: 'buildFromChantNotationIndex', + value: function buildFromChantNotationIndex(ctxt, newElementStart, width) { + + // todo: reset / clear the children we have in case they have data + var notations = this.score.notations; + this.notationsStartIndex = newElementStart; + this.numNotationsOnLine = 0; + + this.staffLeft = 0; + + if (width > 0) this.staffRight = width;else this.staffRight = 99999999; // no limit to staff size + + // If this is the first chant line, then we have to make room for a + // drop cap and/or annotation, if present + if (this.notationsStartIndex === 0) { + + var padding = 0; + + if (this.score.dropCap !== null) padding = this.score.dropCap.bounds.width + this.score.dropCap.padding * 2; + + if (this.score.annotation !== null) padding = Math.max(padding, this.score.annotation.bounds.width + this.score.annotation.padding * 4); + + this.staffLeft += padding; + } + + // set up the clef... + // if the first notation on the line is a starting clef, then we treat it a little differently... + // the clef becomes this line's starting clef and we skip over the clef in the notations array + if (notations[newElementStart].isClef) { + ctxt.activeClef = notations[newElementStart].clone(); + newElementStart++; + this.notationsStartIndex++; + } + + // make a copy for this line to use at the beginning + this.startingClef = ctxt.activeClef.clone(); + this.startingClef.performLayout(ctxt); + this.startingClef.bounds.x = this.staffLeft; + + var curr = this.startingClef, + prev = null, + prevWithLyrics = null; + + // estimate how much space we have available to us + var rightNotationBoundary = this.staffRight - _Exsurge4.Glyphs.CustosLong.bounds.width * ctxt.glyphScaling - ctxt.intraNeumeSpacing * 4; // possible custos on the line + + // iterate through the notations, fittng what we can on this line + var i, + j, + lastNotationIndex = notations.length - 1; + + for (i = newElementStart; i <= lastNotationIndex; i++) { + + if (curr.hasLyrics()) prevWithLyrics = curr; + + prev = curr; + curr = notations[i]; + + var actualRightBoundary; + if (i === lastNotationIndex) { + // on the last notation of the score, we don't need a custos or trailing space, so we use staffRight as the + // right boundary. + actualRightBoundary = this.staffRight; + } else if (i === lastNotationIndex - 1) { + // on the penultimate notation, make sure there is at least enough room for whichever takes up less space, + // between the final notation and a custos: + actualRightBoundary = Math.max(rightNotationBoundary, this.staffRight - notations[lastNotationIndex].bounds.width); + } else { + // Otherwise, we use rightNotationBoundary, which leaves room for a custos... + actualRightBoundary = rightNotationBoundary; + } + + // try to fit the curr element on this line. + // if it doesn't fit, we finish up here. + var fitsOnLine = this.positionNotationElement(ctxt, prevWithLyrics, prev, curr, actualRightBoundary); + if (fitsOnLine === false) { + + // check for an end brace in the curr element + var braceEndIndex = curr.notes && curr.notes.reduce(function (result, n, i) { + return result || n.braceEnd && i + 1 || 0; + }, 0); + var braceStartIndex = curr.notes && curr.notes.reduce(function (result, n, i) { + return result || n.braceStart && i + 1 || 0; + }, 0); + // if there is not a start brace earlier in the element than the end brace, we need to find the earlier start brace + // to keep the entire brace together on the next line + if (braceEndIndex && (!braceStartIndex || braceStartIndex > braceEndIndex)) { + // find last index of start brace + var index = notations.slice(this.notationsStartIndex, i).reduceRight(function (accum, cne, index) { + if (accum === -1 && cne.notes) { + var braceStart = cne.notes.filter(function (n) { + return n.braceStart; + }).length; + var braceEnd = cne.notes.filter(function (n) { + return n.braceEnd; + }).length; + // if we see another end brace before we get to a start brace, short circuit + if (braceEnd) return -2; + if (braceStart) return index; + } + return accum; + }, -1); + // if the start brace was found, this line needs to end just before it: + if (index > 0) { + this.numNotationsOnLine = index; + i = index + this.notationsStartIndex; + } + } + + // check if the prev elements want to be kept with this one + for (j = i - 1; j > this.notationsStartIndex; j--) { + var cne = notations[j]; + + if (cne.keepWithNext === true || j === i - 1 && curr.isDivider) this.numNotationsOnLine--;else break; + } + + // we are at the end of the line! + break; + } + + curr.chantLine = this; + this.numNotationsOnLine++; + + if (curr.isClef) ctxt.activeClef = curr; + + // line breaks are a special case indicating to stop processing here + if (curr.constructor === _Exsurge3.ChantLineBreak && width > 0) { + this.justify = curr.justify; + break; + } + } + + // create the automatic custos at the end of the line if there are neumes left in the notations + for (i = this.notationsStartIndex + this.numNotationsOnLine; i < notations.length; i++) { + var notation = notations[i]; + + if (notation.isNeume) { + + this.custos = new _ExsurgeChant.Custos(true); + ctxt.currNotationIndex = i - 1; // make sure the context knows where the custos is + this.custos.performLayout(ctxt); + + // Put the custos at the very end of the line + this.custos.bounds.x = this.staffRight - this.custos.bounds.width - this.custos.leadingSpace; + + // nothing more to see here... + break; + } + } + + // if the provided width is less than zero, then set the width of the line + // based on the last notation + var last = notations[this.notationsStartIndex + this.numNotationsOnLine - 1]; + if (width <= 0) { + this.staffRight = last.bounds.right(); + this.justify = false; + } else if (this.notationsStartIndex + this.numNotationsOnLine === notations.length) { + // this is the last chant line. + this.justify = true; + this.justify = last.isDivider && (this.staffRight - last.bounds.right()) / this.staffRight < .1; + } + + // Justify the line if we need to + if (this.justify === true) this.justifyElements(); + + this.finishLayout(ctxt); + } + }, { + key: 'justifyElements', + value: function justifyElements() { + + var i; + var toJustify = []; + var notations = this.score.notations; + var lastIndex = this.notationsStartIndex + this.numNotationsOnLine; + + // first step of justification is to determine how much space we have to use up + var extraSpace = 0; + + if (this.numNotationsOnLine > 0) { + var last = notations[lastIndex - 1], + lastWithLyrics = null; + + for (i = lastIndex - 1; i >= this.notationsStartIndex; i--) { + if (notations[i].hasLyrics()) { + lastWithLyrics = notations[i]; + break; + } + } + + if (lastWithLyrics) extraSpace = this.staffRight - Math.max(lastWithLyrics.getAllLyricsRight(), last.bounds.right() + last.trailingSpace);else extraSpace = this.staffRight - (last.bounds.right() + last.trailingSpace); + } + + if (this.custos) extraSpace -= this.custos.bounds.width + this.custos.leadingSpace; + + if (extraSpace <= 0) return; + + var prev = null, + curr = null, + prevWithLyrics = null; + + // first pass: determine the neumes we can space apart + for (i = this.notationsStartIndex; i < lastIndex; i++) { + + if (curr !== null && curr.hasLyrics()) prevWithLyrics = curr; + + prev = curr; + curr = notations[i]; + + if (prev !== null && prev.keepWithNext === true) continue; + + if (prevWithLyrics !== null && prevWithLyrics.lyrics[0].allowsConnector() && !prevWithLyrics.lyrics[0].needsConnector) continue; + + if (curr.constructor === _Exsurge3.ChantLineBreak) continue; + + // otherwise, we can add space before this element + toJustify.push(curr); + } + + if (toJustify.length === 0) return; + + var offset = 0; + var increment = extraSpace / toJustify.length; + var toJustifyIndex = 0; + for (i = this.notationsStartIndex; i < lastIndex; i++) { + + curr = notations[i]; + + if (toJustifyIndex < toJustify.length && toJustify[toJustifyIndex] === curr) { + offset += increment; + toJustifyIndex++; + } + + curr.bounds.x += offset; + } + } + }, { + key: 'finishLayout', + value: function finishLayout(ctxt) { + var _this2 = this; + + this.ledgerLines = []; // clear any existing ledger lines + + var notations = this.score.notations; + var lastIndex = this.notationsStartIndex + this.numNotationsOnLine; + + // an element needs to have a staffPosition property, as well as the standard + // bounds property. so it could be a note, or it could be a custos + // offsetX and offsetY can be used to add to the position info for the element, + // useful in the case of notes. + var processElementForLedgerLine = function processElementForLedgerLine(element) { + var offsetX = arguments.length <= 1 || arguments[1] === undefined ? 0 : arguments[1]; + var offsetY = arguments.length <= 2 || arguments[2] === undefined ? 0 : arguments[2]; + + + // do we need a ledger line for this note? + var staffPosition = element.staffPosition; + + if (staffPosition >= 5 || staffPosition <= -5) { + + var x1 = offsetX + element.bounds.x - ctxt.intraNeumeSpacing; + var x2 = offsetX + element.bounds.x + element.bounds.width + ctxt.intraNeumeSpacing; + + // round the staffPosition to the nearest line + if (staffPosition > 0) staffPosition = staffPosition - (staffPosition - 1) % 2;else staffPosition = staffPosition - (staffPosition + 1) % 2; + + // if we have a ledger line close by, then average out the distance between the two + var minLedgerSeperation = ctxt.staffInterval * 5; + + if (_this2.ledgerLines.length > 0 && _this2.ledgerLines[_this2.ledgerLines.length - 1].x2 + minLedgerSeperation >= x1) { + + // average out the distance + var half = (x1 - _this2.ledgerLines[_this2.ledgerLines.length - 1].x2) / 2; + _this2.ledgerLines[_this2.ledgerLines.length - 1].x2 += half; + x1 -= half; + } + + // never let a ledger line extend past the staff width + if (x2 > _this2.staffRight) x2 = _this2.staffRight; + + // finally, add the ledger line + _this2.ledgerLines.push({ + x1: x1, + x2: x2, + staffPosition: staffPosition + }); + } + }; + + var epismata = []; // keep track of epismata in case we can connect some + var startBrace = null, + startBraceNotationIndex = 0; + var minY = Number.MAX_VALUE, + maxY = Number.MIN_VALUE; // for braces + + // make a final pass over all of the notes to add any necessary + // ledger lines and to smooth out epismata + for (var i = this.notationsStartIndex; i < lastIndex; i++) { + + minY = Math.min(minY, notations[i].bounds.y); + maxY = Math.max(maxY, notations[i].bounds.bottom()); + + if (notations[i].constructor === _ExsurgeChant.Custos) { + processElementForLedgerLine(notations[i]); + continue; + } + + // if it's not a neume then just skip here + if (!notations[i].isNeume) continue; + + var neume = notations[i]; + + for (var j = 0; j < neume.notes.length; j++) { + var k, + note = neume.notes[j]; + + processElementForLedgerLine(note, neume.bounds.x, neume.bounds.y); + + // blend epismata as we're able + for (k = 0; k < note.epismata.length; k++) { + + var episema = note.epismata[k]; + + var spaceBetweenEpismata = 0; + + // calculate the distance between the last epismata and this one... + // lots of code for a simple: currEpismata.left - prevEpismata.right + if (epismata.length > 0) spaceBetweenEpismata = neume.bounds.x + episema.bounds.x - (epismata[epismata.length - 1].note.neume.bounds.x + epismata[epismata.length - 1].bounds.right()); + + // we try to blend the episema if we're able. + if (epismata.length === 0 || epismata[epismata.length - 1].positionHint !== episema.positionHint || epismata[epismata.length - 1].terminating === true || epismata[epismata.length - 1].alignment === _ExsurgeChant2.HorizontalEpisemaAlignment.Left || episema.alignment === _ExsurgeChant2.HorizontalEpisemaAlignment.Right || spaceBetweenEpismata > ctxt.intraNeumeSpacing * 2) { + + // start a new set of epismata to potentially blend + epismata = []; + epismata.push(episema); + } else { + // blend all previous with this one + var newY; + + if (episema.positionHint === _ExsurgeChant2.MarkingPositionHint.Below) newY = Math.max(episema.bounds.y, epismata[epismata.length - 1].bounds.y);else newY = Math.min(episema.bounds.y, epismata[epismata.length - 1].bounds.y); + + if (episema.bounds.y !== newY) episema.bounds.y = newY;else { + for (var l = 0; l < epismata.length; l++) { + epismata[l].bounds.y = newY; + } + } + + // extend the last episema to meet the new one + var newWidth = neume.bounds.x + episema.bounds.x - (epismata[epismata.length - 1].note.neume.bounds.x + epismata[epismata.length - 1].bounds.x); + epismata[epismata.length - 1].bounds.width = newWidth; + + epismata.push(episema); + } + } + + if (note.braceEnd) { + + // calculate the y value of the brace by iterating over all notations + // under/over the brace. + var y; + var dy = ctxt.intraNeumeSpacing / 2; // some safe space between brace and notes. + if (startBrace === null) { + // fixme: this brace must have started on the previous line...what to do here, draw half a brace? + } else { + if (startBrace.isAbove) { + y = ctxt.calculateHeightFromStaffPosition(4); + for (k = startBraceNotationIndex; k <= i; k++) { + y = Math.min(y, notations[k].bounds.y - dy); + } + } else { + y = ctxt.calculateHeightFromStaffPosition(-4); + for (k = startBraceNotationIndex; k <= i; k++) { + y = Math.max(y, notations[k].bounds.y + dy); + } + } + + var addAcuteAccent = false; + + if (startBrace.shape === _ExsurgeChant2.BraceShape.RoundBrace) { + + this.braces.push(new _Exsurge2.RoundBraceVisualizer(ctxt, startBrace.getAttachmentX(), note.braceEnd.getAttachmentX(), y, startBrace.isAbove)); + } else { + + if (startBrace.shape === _ExsurgeChant2.BraceShape.AccentedCurlyBrace) addAcuteAccent = true; + + this.braces.push(new _Exsurge2.CurlyBraceVisualizer(ctxt, startBrace.getAttachmentX(), note.braceEnd.getAttachmentX(), y, startBrace.isAbove, addAcuteAccent)); + } + } + } + + if (note.braceStart) { + startBrace = note.braceStart; + startBraceNotationIndex = i; + } + + // update the active brace y position if there is one + if (startBrace !== null) { + if (startBrace.isAbove) startBrace.bounds.y = Math.min(startBrace.bounds.y, note.bounds.y);else startBrace.bounds.y = Math.max(startBrace.bounds.y, note.bounds.bottom()); + } + } + } + + // if we still have an active brace, that means it spands two chant lines! + if (startBrace !== null) { + startBrace = startBrace; + } + + // don't forget to also include the final custos, which may need a ledger line too + if (this.custos) processElementForLedgerLine(this.custos); + } + + // this is where the real core of positioning neumes takes place + // returns true if positioning was able to fit the neume before rightNotationBoundary. + // returns false if cannot fit before given right margin. + // fixme: if this returns false, shouldn't we set the connectors on prev to be activated?! + + }, { + key: 'positionNotationElement', + value: function positionNotationElement(ctxt, prevWithLyrics, prev, curr, rightNotationBoundary) { + + var i; + + // To begin we just place the current notation right after the previous, + // irrespective of lyrics. + curr.bounds.x = prev.bounds.right() + prev.trailingSpace; + + // if the previous notation has no lyrics, then we simply make sure the + // current notation with lyrics is in the bounds of the line + if (prevWithLyrics === null) { + + var maxRight = curr.bounds.right() + curr.trailingSpace; + + // if the lyric left is negative, then offset the neume appropriately + for (i = 0; i < curr.lyrics.length; i++) { + + curr.lyrics[i].setNeedsConnector(false); // we hope for the best! + + if (curr.getLyricLeft(i) < 0) curr.bounds.x += -curr.getLyricLeft(i); + + maxRight = Math.max(maxRight, curr.getLyricRight(i)); + } + + if (maxRight > rightNotationBoundary) return false;else return true; + } + + // if the curr notation has no lyrics, then we force the prev notation + // with lyrics to have syllable connectors. + if (curr.hasLyrics() === false) { + + for (i = 0; i < prevWithLyrics.lyrics.length; i++) { + + if (prevWithLyrics.lyrics[i] !== null && prevWithLyrics.lyrics[i].allowsConnector()) prevWithLyrics.lyrics[i].setNeedsConnector(true); + } + + if (curr.bounds.right() + curr.trailingSpace < rightNotationBoundary) return true;else return false; + } + + // if we have multiple lyrics on the current or the previous notation, + // then we simplify the process. We don't try to eliminate syllable + // connectors but we require them on every syllable in the previous + // notation that permits a connector. + // + // A nice (but probably tricky) enhancement would be to combine lyrics + // when possible, taking into consideration hyphenation of each syllable! + var lyricCount = Math.max(prevWithLyrics.lyrics.length, curr.lyrics.length); + + if (lyricCount > 1) { + + var prevLyricRightMax = Number.MIN_VALUE; + var currLyricLeftMin = Number.MAX_VALUE; + var currLyricRightMax = Number.MIN_VALUE; + + for (i = 0; i < lyricCount; i++) { + + if (i < prevWithLyrics.lyrics.length && prevWithLyrics.lyrics[i] !== null) { + + var right = prevWithLyrics.getLyricRight(i); + + if (prevWithLyrics.lyrics[i].allowsConnector()) { + prevWithLyrics.lyrics[i].setNeedsConnector(true); + right += prevWithLyrics.lyrics[i].widthWithConnector - prevWithLyrics.lyrics[i].widthWithoutConnector; + } else right += ctxt.minLyricWordSpacing; + + prevLyricRightMax = Math.max(prevLyricRightMax, right); + } + + if (i < curr.lyrics.length && curr.lyrics[i] !== null) { + currLyricLeftMin = Math.min(currLyricLeftMin, curr.getLyricLeft(i)); + currLyricRightMax = Math.max(currLyricRightMax, curr.getLyricRight(i)); + } + } + + // if the lyrics overlap, then we need to shift over the current element a bit + if (prevLyricRightMax > currLyricLeftMin) { + curr.bounds.x += prevLyricRightMax - currLyricLeftMin; + currLyricRightMax += prevLyricRightMax - currLyricLeftMin; + } + + if (curr.bounds.right() < rightNotationBoundary && currLyricRightMax <= this.staffRight) return true;else { + curr.bounds.x = 0; + return false; + } + } + + // handling single lyric lines is a little more nuanced, since we carefully + // eliminate syllable connectors when we're able... + curr.lyrics[0].setNeedsConnector(false); // we hope for the best! + + var currLyricLeft = curr.getLyricLeft(0); + var prevLyricRight = prevWithLyrics.getLyricRight(0); + + if (prevWithLyrics.lyrics[0].allowsConnector() === false) { + + // No connector needed, but include space between words if necessary! + if (prevLyricRight + ctxt.minLyricWordSpacing > currLyricLeft) { + // push the current element over a bit. + curr.bounds.x += prevLyricRight + ctxt.minLyricWordSpacing - currLyricLeft; + } + } else { + + // we may need a connector yet... + + if (prevLyricRight > currLyricLeft) { + // in this case, the lyric elements actually overlap. + // so nope, no connector needed. instead, we just place the lyrics together + // fixme: for better text layout, we could actually use the kerning values + // between the prev and curr lyric elements! + curr.bounds.x += prevLyricRight - currLyricLeft; + } else { + + // bummer, looks like we couldn't merge the syllables together. Better add a connector... + prevWithLyrics.lyrics[0].setNeedsConnector(true); + prevLyricRight = prevWithLyrics.getLyricRight(0); + + if (prevLyricRight > currLyricLeft) curr.bounds.x += prevLyricRight - currLyricLeft; + } + } + + if (curr.bounds.right() + curr.trailingSpace < rightNotationBoundary && curr.getLyricRight(0) <= this.staffRight) return true; + + // if we made it this far, then the element won't fit on this line. + // set the position of the current element to the beginning of a chant line, + // and mark the previous lyric as connecting if needed. + // curr.bounds.x = this.startingClef.bounds.right(); + + if (prevWithLyrics.hasLyrics() && prevWithLyrics.lyrics[0].allowsConnector()) prevWithLyrics.lyrics[0].setNeedsConnector(true); + + return false; + } + }]); + + return ChantLine; + }(_Exsurge2.ChantLayoutElement); + +/***/ }, +/* 8 */ +/***/ function(module, exports, __webpack_require__) { + + 'use strict'; + + Object.defineProperty(exports, "__esModule", { + value: true + }); + exports.Virgula = exports.Accidental = exports.AccidentalType = exports.DoubleBar = exports.FullBar = exports.HalfBar = exports.QuarterBar = exports.Divider = exports.Custos = undefined; + + var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }(); + + var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } }; + + var _Exsurge = __webpack_require__(1); + + var Exsurge = _interopRequireWildcard(_Exsurge); + + var _Exsurge2 = __webpack_require__(4); + + function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key]; } } newObj.default = obj; return newObj; } } + + function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } + + function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; } + + function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; } // + // Author(s): + // Fr. Matthew Spencer, OSJ + // + // Copyright (c) 2008-2016 Fr. Matthew Spencer, OSJ + // + // Permission is hereby granted, free of charge, to any person obtaining a copy + // of this software and associated documentation files (the "Software"), to deal + // in the Software without restriction, including without limitation the rights + // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + // copies of the Software, and to permit persons to whom the Software is + // furnished to do so, subject to the following conditions: + // + // The above copyright notice and this permission notice shall be included in + // all copies or substantial portions of the Software. + // + // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + // THE SOFTWARE. + // + + /* + * + */ + + var Custos = exports.Custos = function (_ChantNotationElement) { + _inherits(Custos, _ChantNotationElement); + + // if auto is true, then the custos will automatically try to determine it's height based on + // subsequent notations + + function Custos() { + var auto = arguments.length <= 0 || arguments[0] === undefined ? false : arguments[0]; + + _classCallCheck(this, Custos); + + var _this = _possibleConstructorReturn(this, Object.getPrototypeOf(Custos).call(this)); + + _this.auto = auto; + _this.staffPosition = 0; // default sane value + return _this; + } + + _createClass(Custos, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Custos.prototype), 'performLayout', this).call(this, ctxt); + + var glyphCode; + + if (this.auto) { + + var neume = ctxt.findNextNeume(); + + if (neume) this.staffPosition = ctxt.activeClef.pitchToStaffPosition(neume.notes[0].pitch); + } + + var glyph = new _Exsurge2.GlyphVisualizer(ctxt, Custos.getGlyphCode(this.staffPosition)); + glyph.setStaffPosition(ctxt, this.staffPosition); + this.addVisualizer(glyph); + + this.finishLayout(ctxt); + } + + // called when layout has changed and our dependencies are no longer good + + }, { + key: 'resetDependencies', + value: function resetDependencies() { + + // we only need to resolve new dependencies if we're an automatic custos + if (this.auto) this.needsLayout = true; + } + }], [{ + key: 'getGlyphCode', + value: function getGlyphCode(staffPosition) { + + if (staffPosition <= 2) { + + // ascending custodes + if (Math.abs(staffPosition) % 2 === 1) return _Exsurge2.GlyphCode.CustosLong;else return _Exsurge2.GlyphCode.CustosShort; + } else { + + // descending custodes + if (Math.abs(staffPosition) % 2 === 1) return _Exsurge2.GlyphCode.CustosDescLong;else return _Exsurge2.GlyphCode.CustosDescShort; + } + } + }]); + + return Custos; + }(_Exsurge2.ChantNotationElement); + + /* + * Divider + */ + + + var Divider = exports.Divider = function (_ChantNotationElement2) { + _inherits(Divider, _ChantNotationElement2); + + function Divider() { + _classCallCheck(this, Divider); + + var _this2 = _possibleConstructorReturn(this, Object.getPrototypeOf(Divider).call(this)); + + _this2.isDivider = true; + _this2.resetsAccidentals = true; + return _this2; + } + + return Divider; + }(_Exsurge2.ChantNotationElement); + + /* + * QuarterBar + */ + + + var QuarterBar = exports.QuarterBar = function (_Divider) { + _inherits(QuarterBar, _Divider); + + function QuarterBar() { + _classCallCheck(this, QuarterBar); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(QuarterBar).apply(this, arguments)); + } + + _createClass(QuarterBar, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(QuarterBar.prototype), 'performLayout', this).call(this, ctxt); + this.addVisualizer(new _Exsurge2.DividerLineVisualizer(ctxt, 2, 4)); + + this.origin.x = this.bounds.width / 2; + + this.finishLayout(ctxt); + } + }]); + + return QuarterBar; + }(Divider); + + /* + * HalfBar + */ + + + var HalfBar = exports.HalfBar = function (_Divider2) { + _inherits(HalfBar, _Divider2); + + function HalfBar() { + _classCallCheck(this, HalfBar); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(HalfBar).apply(this, arguments)); + } + + _createClass(HalfBar, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(HalfBar.prototype), 'performLayout', this).call(this, ctxt); + + this.addVisualizer(new _Exsurge2.DividerLineVisualizer(ctxt, -2, 2)); + + this.origin.x = this.bounds.width / 2; + + this.finishLayout(ctxt); + } + }]); + + return HalfBar; + }(Divider); + + /* + * FullBar + */ + + + var FullBar = exports.FullBar = function (_Divider3) { + _inherits(FullBar, _Divider3); + + function FullBar() { + _classCallCheck(this, FullBar); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(FullBar).apply(this, arguments)); + } + + _createClass(FullBar, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(FullBar.prototype), 'performLayout', this).call(this, ctxt); + + this.addVisualizer(new _Exsurge2.DividerLineVisualizer(ctxt, -3, 3)); + + this.origin.x = this.bounds.width / 2; + + this.finishLayout(ctxt); + } + }]); + + return FullBar; + }(Divider); + + /* + * DoubleBar + */ + + + var DoubleBar = exports.DoubleBar = function (_Divider4) { + _inherits(DoubleBar, _Divider4); + + function DoubleBar() { + _classCallCheck(this, DoubleBar); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(DoubleBar).apply(this, arguments)); + } + + _createClass(DoubleBar, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(DoubleBar.prototype), 'performLayout', this).call(this, ctxt); + + var line0 = new _Exsurge2.DividerLineVisualizer(ctxt, -3, 3); + line0.bounds.x = 0; + this.addVisualizer(line0); + + var line1 = new _Exsurge2.DividerLineVisualizer(ctxt, -3, 3); + line1.bounds.x = ctxt.intraNeumeSpacing * 2; + this.addVisualizer(line1); + + this.origin.x = this.bounds.width / 2; + + this.finishLayout(ctxt); + } + }]); + + return DoubleBar; + }(Divider); + + var AccidentalType = exports.AccidentalType = { + Flat: -1, + Natural: 0, + Sharp: 1 + }; + + /* + * Accidental + */ + + var Accidental = exports.Accidental = function (_ChantNotationElement3) { + _inherits(Accidental, _ChantNotationElement3); + + function Accidental(staffPosition, accidentalType) { + _classCallCheck(this, Accidental); + + var _this7 = _possibleConstructorReturn(this, Object.getPrototypeOf(Accidental).call(this)); + + _this7.isAccidental = true; + _this7.keepWithNext = true; // accidentals should always stay connected... + + _this7.staffPosition = staffPosition; + _this7.accidentalType = accidentalType; + return _this7; + } + + _createClass(Accidental, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Accidental.prototype), 'performLayout', this).call(this, ctxt); + + this.addVisualizer(this.createGlyphVisualizer(ctxt)); + + this.finishLayout(ctxt); + } + + // creation of the glyph visualizer is refactored out or performLayout + // so that clefs can use the same logic for their accidental glyph + + }, { + key: 'createGlyphVisualizer', + value: function createGlyphVisualizer(ctxt) { + + var glyphCode = _Exsurge2.GlyphCode.Flat; + + switch (this.accidentalType) { + case AccidentalType.Natural: + glyphCode = _Exsurge2.GlyphCode.Natural; + break; + case AccidentalType.Sharp: + glyphCode = _Exsurge2.GlyphCode.Sharp; + break; + default: + glyphCode = _Exsurge2.GlyphCode.Flat; + break; + } + + var glyph = new _Exsurge2.GlyphVisualizer(ctxt, glyphCode); + glyph.setStaffPosition(ctxt, this.staffPosition); + + return glyph; + } + }, { + key: 'adjustStep', + value: function adjustStep(step) { + switch (this.accidentalType) { + case AccidentalType.Flat: + if (step === Step.Ti) return Step.Te; + if (step === Step.Mi) return Step.Me; + break; + case AccidentalType.Sharp: + if (step === Step.Do) return Step.Du; + if (step === Step.Fa) return Step.Fu; + break; + case AccidentalType.Natural: + if (step === Step.Te) return Step.Ti; + if (step === Step.Me) return Step.Mi; + if (step === Step.Du) return Step.Do; + if (step === Step.Fu) return Step.Fa; + break; + } + + // no adjustment needed + return step; + } + }, { + key: 'applyToPitch', + value: function applyToPitch(pitch) { + + // fixme: this is broken since we changed to staff positions + + // no adjusment needed + if (this.octave !== pitch.octave) return; + + pitch.step = this.adjustStep(pitch.step); + } + }]); + + return Accidental; + }(_Exsurge2.ChantNotationElement); + + /* + * Virgula + */ + + + var Virgula = exports.Virgula = function (_Divider5) { + _inherits(Virgula, _Divider5); + + function Virgula() { + _classCallCheck(this, Virgula); + + // unlike other dividers a virgula does not reset accidentals + + var _this8 = _possibleConstructorReturn(this, Object.getPrototypeOf(Virgula).call(this)); + + _this8.resetsAccidentals = false; + + // the staff position of the virgula is customizable, so that it + // can be placed on different lines (top or bottom) depending on the + // notation tradition of what is being notated (e.g., Benedictine has it + // on top line, Norbertine at the bottom) + _this8.staffPosition = 3; + return _this8; + } + + _createClass(Virgula, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Virgula.prototype), 'performLayout', this).call(this, ctxt); + + var glyph = new _Exsurge2.GlyphVisualizer(ctxt, _Exsurge2.GlyphCode.Virgula); + glyph.setStaffPosition(ctxt, this.staffPosition); + + this.addVisualizer(glyph); + + this.origin.x = this.bounds.width / 2; + + this.finishLayout(ctxt); + } + }]); + + return Virgula; + }(Divider); + +/***/ }, +/* 9 */ +/***/ function(module, exports, __webpack_require__) { + + 'use strict'; + + Object.defineProperty(exports, "__esModule", { + value: true + }); + exports.BracePoint = exports.BraceAttachment = exports.BraceShape = exports.Mora = exports.Ictus = exports.HorizontalEpisema = exports.HorizontalEpisemaAlignment = exports.AcuteAccent = exports.MarkingPositionHint = undefined; + + var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }(); + + var _Exsurge = __webpack_require__(1); + + var Exsurge = _interopRequireWildcard(_Exsurge); + + var _Exsurge2 = __webpack_require__(4); + + var _Exsurge3 = __webpack_require__(6); + + function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key]; } } newObj.default = obj; return newObj; } } + + function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } + + function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; } + + function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; } // + // Author(s): + // Fr. Matthew Spencer, OSJ + // + // Copyright (c) 2008-2016 Fr. Matthew Spencer, OSJ + // + // Permission is hereby granted, free of charge, to any person obtaining a copy + // of this software and associated documentation files (the "Software"), to deal + // in the Software without restriction, including without limitation the rights + // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + // copies of the Software, and to permit persons to whom the Software is + // furnished to do so, subject to the following conditions: + // + // The above copyright notice and this permission notice shall be included in + // all copies or substantial portions of the Software. + // + // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + // THE SOFTWARE. + // + + // for positioning markings on notes + var MarkingPositionHint = exports.MarkingPositionHint = { + Default: 0, + Above: 1, + Below: 2 + }; + + var AcuteAccent = exports.AcuteAccent = function (_GlyphVisualizer) { + _inherits(AcuteAccent, _GlyphVisualizer); + + function AcuteAccent(ctxt, note) { + _classCallCheck(this, AcuteAccent); + + var _this = _possibleConstructorReturn(this, Object.getPrototypeOf(AcuteAccent).call(this, ctxt, _Exsurge2.GlyphCode.AcuteAccent)); + + _this.note = note; + _this.positionHint = MarkingPositionHint.Above; + return _this; + } + + _createClass(AcuteAccent, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + + this.bounds.x += this.bounds.width / 2; // center on the note itself + + // this puts the acute accent either over the staff lines, or over the note if the + // note is above the staff lines + this.setStaffPosition(ctxt, Math.max(this.note.staffPosition + 1, 4)); + } + }]); + + return AcuteAccent; + }(_Exsurge2.GlyphVisualizer); + + // for positioning markings on notes + + + var HorizontalEpisemaAlignment = exports.HorizontalEpisemaAlignment = { + Default: 0, + Left: 1, + Center: 2, + Right: 3 + }; + + /* + * HorizontalEpisema + * + * A horizontal episema marking is it's own visualizer (that is, it implements createSvgFragment) + */ + + var HorizontalEpisema = exports.HorizontalEpisema = function (_ChantLayoutElement) { + _inherits(HorizontalEpisema, _ChantLayoutElement); + + function HorizontalEpisema(note) { + _classCallCheck(this, HorizontalEpisema); + + var _this2 = _possibleConstructorReturn(this, Object.getPrototypeOf(HorizontalEpisema).call(this)); + + _this2.note = note; + + _this2.positionHint = MarkingPositionHint.Default; + _this2.terminating = false; // indicates if this episema should terminate itself or not + _this2.alignment = HorizontalEpisemaAlignment.Default; + return _this2; + } + + _createClass(HorizontalEpisema, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + + // following logic helps to keep the episemae away from staff lines if they get too close + // the placement is based on a review of the Vatican and solesmes editions, which + // seem to always place the epismata centered between staff lines. Probably helps + // for visual layout, rather than letting epismata be at various heights. + + var y = 0, + step; + var minDistanceAway = ctxt.staffInterval * 0.4; // min distance from neume + + if (this.positionHint === MarkingPositionHint.Below) { + y = this.note.bounds.bottom() + minDistanceAway; // the highest the line could be at + step = Math.floor(y / ctxt.staffInterval); + + // if it's an odd step, that means we're on a staff line, + // so we shift to between the staff line + if (Math.abs(step % 2) === 1) step = step + 1; + } else { + y = this.note.bounds.y - minDistanceAway; // the lowest the line could be at + step = Math.ceil(y / ctxt.staffInterval); + + // if it's an odd step, that means we're on a staff line, + // so we shift to between the staff line + if (Math.abs(step % 2) === 1) step = step - 1; + } + + y = step * ctxt.staffInterval; + + var glyphCode = this.note.glyphVisualizer.glyphCode; + var width; + + // The porrectus requires special handling of the note width, + // otherwise the width is just that of the note itself + if (glyphCode === _Exsurge2.GlyphCode.Porrectus1 || glyphCode === _Exsurge2.GlyphCode.Porrectus2 || glyphCode === _Exsurge2.GlyphCode.Porrectus3 || glyphCode === _Exsurge2.GlyphCode.Porrectus4) width = ctxt.staffInterval;else width = this.note.bounds.width; + + var x = this.note.bounds.x; + + // also, the position hint can affect the x/width of the episema + if (this.alignment === HorizontalEpisemaAlignment.Left) { + width *= .80; + } else if (this.alignment === HorizontalEpisemaAlignment.Center) { + x += width * .20; + width *= .60; + } else if (this.alignment === HorizontalEpisemaAlignment.Right) { + x += width * .20; + width *= .80; + } + + this.bounds.x = x; + this.bounds.y = y; + this.bounds.width = width; + this.bounds.height = ctxt.episemaLineWeight; + + this.origin.x = 0; + this.origin.y = 0; + } + }, { + key: 'createSvgFragment', + value: function createSvgFragment(ctxt) { + + return _Exsurge2.QuickSvg.createFragment('rect', { + 'x': this.bounds.x, + 'y': this.bounds.y, + 'width': this.bounds.width, + 'height': this.bounds.height, + 'fill': ctxt.neumeLineColor, + 'class': 'horizontalEpisema' + }); + } + }]); + + return HorizontalEpisema; + }(_Exsurge2.ChantLayoutElement); + + /* + * Ictus + */ + + + var Ictus = exports.Ictus = function (_GlyphVisualizer2) { + _inherits(Ictus, _GlyphVisualizer2); + + function Ictus(ctxt, note) { + _classCallCheck(this, Ictus); + + var _this3 = _possibleConstructorReturn(this, Object.getPrototypeOf(Ictus).call(this, ctxt, _Exsurge2.GlyphCode.VerticalEpisemaAbove)); + + _this3.note = note; + _this3.positionHint = MarkingPositionHint.Default; + return _this3; + } + + _createClass(Ictus, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + + var glyphCode; + + // fixme: this positioning logic doesn't work for the ictus on a virga apparently...? + + if (this.positionHint === MarkingPositionHint.Above) { + glyphCode = _Exsurge2.GlyphCode.VerticalEpisemaAbove; + } else { + glyphCode = _Exsurge2.GlyphCode.VerticalEpisemaBelow; + } + + var staffPosition = this.note.staffPosition; + + var horizontalOffset = this.note.bounds.width / 2; + var verticalOffset = 0; + + switch (glyphCode) { + case _Exsurge2.GlyphCode.VerticalEpisemaAbove: + if (staffPosition % 2 === 0) verticalOffset -= ctxt.staffInterval * 1.5;else verticalOffset -= ctxt.staffInterval * .9; + break; + + case _Exsurge2.GlyphCode.VerticalEpisemaBelow: + default: + if (staffPosition % 2 === 0) verticalOffset += ctxt.staffInterval * 1.5;else verticalOffset += ctxt.staffInterval * .8; + break; + } + + this.setGlyph(ctxt, glyphCode); + this.setStaffPosition(ctxt, staffPosition); + + this.bounds.x = this.note.bounds.x + horizontalOffset - this.origin.x; + this.bounds.y += verticalOffset; + } + }]); + + return Ictus; + }(_Exsurge2.GlyphVisualizer); + + /* + * Mora + */ + + + var Mora = exports.Mora = function (_GlyphVisualizer3) { + _inherits(Mora, _GlyphVisualizer3); + + function Mora(ctxt, note) { + _classCallCheck(this, Mora); + + var _this4 = _possibleConstructorReturn(this, Object.getPrototypeOf(Mora).call(this, ctxt, _Exsurge2.GlyphCode.Mora)); + + _this4.note = note; + _this4.positionHint = MarkingPositionHint.Default; + return _this4; + } + + _createClass(Mora, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + + var staffPosition = this.note.staffPosition; + + this.setStaffPosition(ctxt, staffPosition); + + var verticalOffset = 0; + if (this.positionHint === MarkingPositionHint.Above) { + if (staffPosition % 2 === 0) verticalOffset -= ctxt.staffInterval + ctxt.staffInterval * .75;else verticalOffset -= ctxt.staffInterval * .75; + } else if (this.positionHint === MarkingPositionHint.Below) { + if (staffPosition % 2 === 0) verticalOffset += ctxt.staffInterval + ctxt.staffInterval * .75;else verticalOffset += ctxt.staffInterval * .75; + } else { + if (Math.abs(staffPosition) % 2 === 1) verticalOffset -= ctxt.staffInterval * .75; + } + + this.bounds.x += this.note.bounds.right() + ctxt.staffInterval / 4.0; + this.bounds.y += verticalOffset; + } + }]); + + return Mora; + }(_Exsurge2.GlyphVisualizer); + + // indicates the shape of the brace + + + var BraceShape = exports.BraceShape = { + RoundBrace: 0, + CurlyBrace: 1, + AccentedCurlyBrace: 2 + }; + + // indicates how the brace is alignerd to the note to which it's connected + var BraceAttachment = exports.BraceAttachment = { + Left: 0, + Right: 1 + }; + + var BracePoint = exports.BracePoint = function (_ChantLayoutElement2) { + _inherits(BracePoint, _ChantLayoutElement2); + + function BracePoint(note, isAbove, shape, attachment) { + _classCallCheck(this, BracePoint); + + var _this5 = _possibleConstructorReturn(this, Object.getPrototypeOf(BracePoint).call(this)); + + _this5.note = note; + _this5.isAbove = isAbove; + _this5.shape = shape; + _this5.attachment = attachment; + return _this5; + } + + _createClass(BracePoint, [{ + key: 'getAttachmentX', + value: function getAttachmentX() { + if (this.attachment === BraceAttachment.Left) return this.note.neume.bounds.x + this.note.bounds.x;else return this.note.neume.bounds.x + this.note.bounds.right(); + } + }]); + + return BracePoint; + }(_Exsurge2.ChantLayoutElement); + +/***/ }, +/* 10 */ +/***/ function(module, exports, __webpack_require__) { + + 'use strict'; + + Object.defineProperty(exports, "__esModule", { + value: true + }); + exports.Gabc = undefined; + + var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }(); + // + // Author(s): + // Fr. Matthew Spencer, OSJ + // + // Copyright (c) 2008-2016 Fr. Matthew Spencer, OSJ + // + // Permission is hereby granted, free of charge, to any person obtaining a copy + // of this software and associated documentation files (the "Software"), to deal + // in the Software without restriction, including without limitation the rights + // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + // copies of the Software, and to permit persons to whom the Software is + // furnished to do so, subject to the following conditions: + // + // The above copyright notice and this permission notice shall be included in + // all copies or substantial portions of the Software. + // + // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + // THE SOFTWARE. + // + + var _Exsurge = __webpack_require__(1); + + var _Exsurge2 = __webpack_require__(4); + + var _Exsurge3 = __webpack_require__(6); + + var _ExsurgeChant = __webpack_require__(9); + + var Markings = _interopRequireWildcard(_ExsurgeChant); + + var _ExsurgeChant2 = __webpack_require__(8); + + var Signs = _interopRequireWildcard(_ExsurgeChant2); + + var _ExsurgeChant3 = __webpack_require__(11); + + var Neumes = _interopRequireWildcard(_ExsurgeChant3); + + function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key]; } } newObj.default = obj; return newObj; } } + + function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } + + // reusable reg exps + var __syllablesRegex = /(?=.)((?:[^(])*)(?:\(?([^)]*)\)?)?/g; + var __notationsRegex = /z0|z|Z|::|:|;|,|`|c1|c2|c3|c4|f3|f4|cb3|cb4|\/\/|\/| |\!|-?[a-mA-M][oOwWvVrRsxy#~\+><_\.'012345]*(?:\[[^\]]*\]?)*/g; + + // for the brace string inside of [ and ] in notation data + // the capturing groups are: + // 1. o or u, to indicate over or under + // 2. b, cb, or cba, to indicate the brace type + // 3. 0 or 1 to indicate the attachment point + // 4. {}( or ) to indicate opening/closing (this group will be null if the metric version is used) + // 5. a float indicating the millimeter length of the brace (not supported yet) + var __braceSpecRegex = /([ou])(b|cb|cba):([01])(?:([{}])|;(\d*(?:\.\d+)?)mm)/; + + var Gabc = exports.Gabc = function () { + function Gabc() { + _classCallCheck(this, Gabc); + } + + _createClass(Gabc, null, [{ + key: 'createMappingsFromSource', + + + // takes gabc source code (without the header info) and returns an array + // of ChantMappings describing the chant. A chant score can then be created + // fron the chant mappings and later updated via updateMappings() if need + // be... + value: function createMappingsFromSource(ctxt, gabcSource) { + + var words = this.splitWords(gabcSource); + + // set the default clef + ctxt.activeClef = _Exsurge3.Clef.default(); + + var mappings = this.createMappingsFromWords(ctxt, words, function (clef) { + return ctxt.activeClef = clef; + }); + + // always set the last notation to have a trailingSpace of 0. This makes layout for the last chant line simpler + if (mappings.length > 0 && mappings[mappings.length - 1].notations.length > 0) mappings[mappings.length - 1].notations[mappings[mappings.length - 1].notations.length - 1].trailingSpace = 0; + + return mappings; + } + + // A simple general purpose diff algorithm adapted here for comparing + // an array of existing mappings with an updated list of gabc words. + // note before is an array of mappings, and after is an array of strings + // (gabc words). + // + // This is definitely not the most effecient diff algorithm, but for our + // limited needs and source size it seems to work just fine... + // + // code is adapted from: https://github.com/paulgb/simplediff + // + // Returns: + // A list of pairs, with the first part of the pair being one of three + // strings ('-', '+', '=') and the second part being a list of values from + // the original before and/or after lists. The first part of the pair + // corresponds to whether the list of values is a deletion, insertion, or + // unchanged, respectively. + + }, { + key: 'diffDescriptorsAndNewWords', + value: function diffDescriptorsAndNewWords(before, after) { + + // Create a map from before values to their indices + var oldIndexMap = {}, + i; + for (i = 0; i < before.length; i++) { + oldIndexMap[before[i].source] = oldIndexMap[before[i].source] || []; + oldIndexMap[before[i].source].push(i); + } + + var overlap = [], + startOld, + startNew, + subLength, + inew; + + startOld = startNew = subLength = 0; + + for (inew = 0; inew < after.length; inew++) { + var _overlap = []; + oldIndexMap[after[inew]] = oldIndexMap[after[inew]] || []; + for (i = 0; i < oldIndexMap[after[inew]].length; i++) { + var iold = oldIndexMap[after[inew]][i]; + // now we are considering all values of val such that + // `before[iold] == after[inew]` + _overlap[iold] = (iold && overlap[iold - 1] || 0) + 1; + if (_overlap[iold] > subLength) { + // this is the largest substring seen so far, so store its indices + subLength = _overlap[iold]; + startOld = iold - subLength + 1; + startNew = inew - subLength + 1; + } + } + overlap = _overlap; + } + + if (subLength === 0) { + // If no common substring is found, we return an insert and delete... + var result = []; + + if (before.length) result.push(['-', before]); + + if (after.length) result.push(['+', after]); + + return result; + } + + // ...otherwise, the common substring is unchanged and we recursively + // diff the text before and after that substring + return [].concat(this.diffDescriptorsAndNewWords(before.slice(0, startOld), after.slice(0, startNew)), [['=', after.slice(startNew, startNew + subLength)]], this.diffDescriptorsAndNewWords(before.slice(startOld + subLength), after.slice(startNew + subLength))); + } + + // this function essentially performs and applies a rudimentary diff between a + // previously parsed set of mappings and between a new gabc source text. + // the mappings array passed in is changed in place to be updated from the + // new source + + }, { + key: 'updateMappingsFromSource', + value: function updateMappingsFromSource(ctxt, mappings, newGabcSource) { + + // always remove the last old mapping since it's spacing/trailingSpace is handled specially + mappings.pop(); + + var newWords = this.splitWords(newGabcSource); + + var results = this.diffDescriptorsAndNewWords(mappings, newWords); + + var index = 0, + j, + k; + + ctxt.activeClef = _Exsurge3.Clef.default(); + + // apply the results to the mappings, marking notations that need to be processed + for (var i = 0; i < results.length; i++) { + + var resultCode = results[i][0]; + var resultValues = results[i][1]; + + if (resultCode === '=') { + // skip over ones that haven't changed, but updating the clef as we go + for (j = 0; j < resultValues.length; j++, index++) { + for (k = 0; k < mappings[index].notations.length; k++) { + // notify the notation that its dependencies are no longer valid + mappings[index].notations[k].resetDependencies(); + + if (mappings[index].notations[k].isClef) ctxt.activeClef = mappings[index].notations[k]; + } + } + } else if (resultCode === '-') { + // delete elements that no longer exist, but first notify all + // elements of the change + mappings.splice(index, resultValues.length); + } else if (resultCode === '+') { + // insert new ones + for (j = 0; j < resultValues.length; j++) { + var mapping = this.createMappingFromWord(ctxt, resultValues[j]); + + for (k = 0; k < mapping.notations.length; k++) { + if (mapping.notations[k].isClef) ctxt.activeClef = mapping.notations[k]; + }mappings.splice(index++, 0, mapping); + } + } + } + + // always set the last notation to have a trailingSpace of 0. This makes layout for the last chant line simpler + if (mappings.length > 0 && mappings[mappings.length - 1].notations.length > 0) mappings[mappings.length - 1].notations[mappings[mappings.length - 1].notations.length - 1].trailingSpace = 0; + } + + // takes an array of gabc words (like that returned by splitWords below) + // and returns an array of ChantMapping objects, one for each word. + + }, { + key: 'createMappingsFromWords', + value: function createMappingsFromWords(ctxt, words) { + var mappings = []; + + for (var i = 0; i < words.length; i++) { + var word = words[i].trim(); + + if (word === '') continue; + + var mapping = this.createMappingFromWord(ctxt, word); + + if (mapping) mappings.push(mapping); + } + + return mappings; + } + + // takes a gabc word (like those returned by splitWords below) and returns + // a ChantMapping object that contains the gabc word source text as well + // as the generated notations. + + }, { + key: 'createMappingFromWord', + value: function createMappingFromWord(ctxt, word) { + + var matches = []; + var notations = []; + var currSyllable = 0; + + while (match = __syllablesRegex.exec(word)) { + matches.push(match); + }for (var j = 0; j < matches.length; j++) { + var match = matches[j]; + + var lyricText = match[1].trim(); + var notationData = match[2]; + + var items = this.parseNotations(ctxt, notationData); + + if (items.length === 0) continue; + + notations = notations.concat(items); + + if (lyricText === '') continue; + + // add the lyrics to the first notation that makes sense... + var notationWithLyrics = null; + for (var i = 0; i < items.length; i++) { + var cne = items[i]; + + if (cne.isAccidental || cne.constructor === Signs.Custos) continue; + + notationWithLyrics = cne; + break; + } + + if (notationWithLyrics === null) return notations; + + var proposedLyricType; + + // if it's not a neume or a TextOnly notation, then make the lyrics a directive + if (!cne.isNeume && cne.constructor !== _Exsurge3.TextOnly) proposedLyricType = _Exsurge2.LyricType.Directive; + // otherwise trye to guess the lyricType for the first lyric anyway + else if (currSyllable === 0 && j === matches.length - 1) proposedLyricType = _Exsurge2.LyricType.SingleSyllable;else if (currSyllable === 0 && j < matches.length - 1) proposedLyricType = _Exsurge2.LyricType.BeginningSyllable;else if (j === matches.length - 1) proposedLyricType = _Exsurge2.LyricType.EndingSyllable;else proposedLyricType = _Exsurge2.LyricType.MiddleSyllable; + + currSyllable++; + + // also, new words reset the accidentals, per the Solesmes style (see LU xviij) + if (proposedLyricType === _Exsurge2.LyricType.BeginningSyllable || proposedLyricType === _Exsurge2.LyricType.SingleSyllable) ctxt.activeClef.resetAccidentals(); + + var lyrics = this.createSyllableLyrics(ctxt, lyricText, proposedLyricType); + + if (lyrics === null || lyrics.length === 0) continue; + + notationWithLyrics.lyrics = lyrics; + } + + return new _Exsurge3.ChantMapping(word, notations); + } + + // returns an array of lyrics (an array because each syllable can have multiple lyrics) + + }, { + key: 'createSyllableLyrics', + value: function createSyllableLyrics(ctxt, text, proposedLyricType) { + + var lyrics = []; + + // an extension to gabc: multiple lyrics per syllable can be separated by a | + var lyricTexts = text.split('|'); + + for (var i = 0; i < lyricTexts.length; i++) { + + var lyricText = lyricTexts[i]; + + // gabc allows lyrics to indicate the centering part of the text by + // using braces to indicate how to center the lyric. So a lyric can + // look like "f{i}re" or "{fenced}" to center on the i or on the entire + // word, respectively. Here we determine if the lyric should be spaced + // manually with this method of using braces. + var centerStartIndex = lyricText.indexOf('{'); + var centerLength = 0; + + if (centerStartIndex >= 0) { + var indexClosingBracket = lyricText.indexOf('}'); + + if (indexClosingBracket >= 0 && indexClosingBracket > centerStartIndex) { + centerLength = indexClosingBracket - centerStartIndex - 1; + + // strip out the brackets...is this better than string.replace? + lyricText = lyricText.substring(0, centerStartIndex) + lyricText.substring(centerStartIndex + 1, indexClosingBracket) + lyricText.substring(indexClosingBracket + 1, lyricText.length); + } else centerStartIndex = -1; // if there's no closing bracket, don't enable centering + } + + var lyric = this.makeLyric(ctxt, lyricText, proposedLyricType); + + // if we have manual lyric centering, then set it now + if (centerStartIndex >= 0) { + lyric.centerStartIndex = centerStartIndex; + lyric.centerLength = centerLength; + } + + lyrics.push(lyric); + } + + return lyrics; + } + }, { + key: 'makeLyric', + value: function makeLyric(ctxt, text, lyricType) { + + if (text.length > 1 && text[text.length - 1] === '-') { + if (lyricType === _Exsurge2.LyricType.EndingSyllable) lyricType = _Exsurge2.LyricType.MiddleSyllable;else if (lyricType === _Exsurge2.LyricType.SingleSyllable) lyricType = _Exsurge2.LyricType.BeginningSyllable; + + text = text.substring(0, text.length - 1); + } + + var elides = false; + if (text.length > 1 && text[text.length - 1] === '_') { + // must be an elision + elides = true; + text = text.substring(0, text.length - 1); + } + + if (text === "*" || text === "†") lyricType = _Exsurge2.LyricType.Directive; + + var lyric = new _Exsurge2.Lyric(ctxt, text, lyricType); + lyric.elidesToNext = elides; + + return lyric; + } + + // takes a string of gabc notations and creates exsurge objects out of them. + // returns an array of notations. + + }, { + key: 'parseNotations', + value: function parseNotations(ctxt, data) { + var _this = this; + + // if there is no data, then this must be a text only object + if (!data) return [new _Exsurge3.TextOnly()]; + + var notations = []; + var notes = []; + var trailingSpace = -1; + + var addNotation = function addNotation(notation) { + + // first, if we have any notes left over, we create a neume out of them + if (notes.length > 0) { + + // create neume(s) + var neumes = _this.createNeumesFromNotes(ctxt, notes, trailingSpace); + for (var i = 0; i < neumes.length; i++) { + notations.push(neumes[i]); + } // reset the trailing space + trailingSpace = -1; + + notes = []; + } + + // then, if we're passed a notation, let's add it + // also, perform chant logic here + if (notation !== null) { + + if (notation.isClef) { + ctxt.activeClef = notation; + } else if (notation.isAccidental) ctxt.activeClef.activeAccidental = notation;else if (notation.resetsAccidentals) ctxt.activeClef.resetAccidentals(); + + notations.push(notation); + } + }; + + var atoms = data.match(__notationsRegex); + + if (atoms === null) return notations; + + for (var i = 0; i < atoms.length; i++) { + + var atom = atoms[i]; + + // handle the clefs and dividers here + switch (atom) { + case ",": + addNotation(new Signs.QuarterBar()); + break; + case "`": + addNotation(new Signs.Virgula()); + break; + case ";": + addNotation(new Signs.HalfBar()); + break; + case ":": + addNotation(new Signs.FullBar()); + break; + case "::": + addNotation(new Signs.DoubleBar()); + break; + // other gregorio dividers are not supported yet + + case "c1": + addNotation(ctxt.activeClef = new _Exsurge3.DoClef(-3, 2)); + break; + + case "c2": + addNotation(ctxt.activeClef = new _Exsurge3.DoClef(-1, 2)); + break; + + case "c3": + addNotation(ctxt.activeClef = new _Exsurge3.DoClef(1, 2)); + break; + + case "c4": + addNotation(ctxt.activeClef = new _Exsurge3.DoClef(3, 2)); + break; + + case "f3": + addNotation(ctxt.activeClef = new _Exsurge3.FaClef(1, 2)); + break; + + case "f4": + addNotation(ctxt.activeClef = new _Exsurge3.FaClef(3, 2)); + break; + + case "cb3": + addNotation(ctxt.activeClef = new _Exsurge3.DoClef(1, 2, new Signs.Accidental(0, Signs.AccidentalType.Flat))); + break; + + case "cb4": + addNotation(ctxt.activeClef = new _Exsurge3.DoClef(3, 2, new Signs.Accidental(2, Signs.AccidentalType.Flat))); + break; + + case "z": + addNotation(new _Exsurge3.ChantLineBreak(true)); + break; + case "Z": + addNotation(new _Exsurge3.ChantLineBreak(false)); + break; + case "z0": + addNotation(new Signs.Custos(true)); + break; + + // spacing indicators + case "!": + trailingSpace = 0; + addNotation(null); + break; + case "/": + trailingSpace = ctxt.intraNeumeSpacing; + addNotation(null); + break; + case "//": + trailingSpace = ctxt.intraNeumeSpacing * 2; + addNotation(null); + break; + case ' ': + // fixme: is this correct? logically what is the difference in gabc + // between putting a space between notes vs putting '//' between notes? + trailingSpace = ctxt.intraNeumeSpacing * 2; + addNotation(null); + break; + + default: + // might be a custos, might be an accidental, or might be a note + if (atom.length > 1 && atom[1] === '+') { + // custos + var custos = new Signs.Custos(); + + custos.staffPosition = this.gabcHeightToExsurgeHeight(data[0]); + + addNotation(custos); + } else if (atom.length > 1 && (atom[1] === 'x' || atom[1] === 'y' || atom[1] === '#')) { + + var accidentalType; + + switch (atom[1]) { + case 'y': + accidentalType = Signs.AccidentalType.Natural; + break; + case '#': + accidentalType = Signs.AccidentalType.Sharp; + break; + default: + accidentalType = Signs.AccidentalType.Flat; + break; + } + + var noteArray = []; + this.createNoteFromData(ctxt, ctxt.activeClef, atom, noteArray); + var accidental = new Signs.Accidental(noteArray[0].staffPosition, accidentalType); + accidental.trailingSpace = ctxt.intraNeumeSpacing * 2; + + ctxt.activeClef.activeAccidental = accidental; + + addNotation(accidental); + } else { + + // looks like it's a note + this.createNoteFromData(ctxt, ctxt.activeClef, atom, notes); + } + break; + } + } + + // finish up any remaining notes we have left + addNotation(null); + + return notations; + } + }, { + key: 'createNeumesFromNotes', + value: function createNeumesFromNotes(ctxt, notes, finalTrailingSpace) { + + var neumes = []; + var firstNoteIndex = 0; + var currNoteIndex = 0; + + // here we use a simple finite state machine to create the neumes from the notes + // createNeume is helper function which returns the next state after a neume is created + // (unknownState). Each state object has a neume() function and a handle() function. + // neume() allows us to create the neume of the state in the event that we run out + // of notes. handle() gives the state an opportunity to examine the currNote and + // determine what to do...either transition to a different neume/state, or + // continue building the neume of that state. handle() returns the next state + + var createNeume = function createNeume(neume, includeCurrNote) { + var includePrevNote = arguments.length <= 2 || arguments[2] === undefined ? true : arguments[2]; + + + // add the notes to the neume + var lastNoteIndex; + if (includeCurrNote) lastNoteIndex = currNoteIndex;else if (includePrevNote) lastNoteIndex = currNoteIndex - 1;else lastNoteIndex = currNoteIndex - 2; + + if (lastNoteIndex < 0) return; + + while (firstNoteIndex <= lastNoteIndex) { + neume.addNote(notes[firstNoteIndex++]); + }neumes.push(neume); + + if (includeCurrNote === false) { + currNoteIndex--; + + if (includePrevNote === false) currNoteIndex--; + + neume.keepWithNext = true; + neume.trailingSpace = ctxt.intraNeumeSpacing; + } + + return unknownState; + }; + + var unknownState = { + neume: function neume() { + return new Neumes.Punctum(); + }, + handle: function handle(currNote, prevNote) { + + if (currNote.shape === _Exsurge3.NoteShape.Virga) return virgaState;else if (currNote.shape === _Exsurge3.NoteShape.Stropha) return apostrophaState;else if (currNote.shape === _Exsurge3.NoteShape.Oriscus) return oriscusState;else if (currNote.shape === _Exsurge3.NoteShape.Inclinatum) return punctaInclinataState;else if (currNote.shapeModifiers & _Exsurge3.NoteShapeModifiers.Cavum) return createNeume(new Neumes.Punctum(), true);else return punctumState; + } + }; + + var punctumState = { + neume: function neume() { + return new Neumes.Punctum(); + }, + handle: function handle(currNote, prevNote) { + + if (currNote.staffPosition > prevNote.staffPosition) return podatusState;else if (currNote.staffPosition < prevNote.staffPosition) { + if (currNote.shape === _Exsurge3.NoteShape.Inclinatum) return climacusState;else return clivisState; + } else return distrophaState; + } + }; + + var punctaInclinataState = { + neume: function neume() { + return new Neumes.PunctaInclinata(); + }, + handle: function handle() { + if (currNote.shape !== _Exsurge3.NoteShape.Inclinatum) return createNeume(new Neumes.PunctaInclinata(), false);else return punctaInclinataState; + } + }; + + var oriscusState = { + neume: function neume() { + return new Neumes.Oriscus(); + }, + handle: function handle(currNote, prevNote) { + + if (currNote.shape === _Exsurge3.NoteShape.Default) { + + if (currNote.staffPosition > prevNote.staffPosition) { + prevNote.shapeModifiers |= _Exsurge3.NoteShapeModifiers.Ascending; + return createNeume(new Neumes.PesQuassus(), true); + } else if (currNote.staffPosition < prevNote.staffPosition) { + prevNote.shapeModifiers |= _Exsurge3.NoteShapeModifiers.Descending; + return createNeume(new Neumes.Clivis(), true); + } + } else + // stand alone oriscus + return createNeume(new Neumes.Oriscus(), true); + } + }; + + var podatusState = { + neume: function neume() { + return new Neumes.Podatus(); + }, + handle: function handle(currNote, prevNote) { + + if (currNote.staffPosition > prevNote.staffPosition) { + + if (prevNote.shape === _Exsurge3.NoteShape.Oriscus) return salicusState;else return scandicusState; + } else if (currNote.staffPosition < prevNote.staffPosition) { + if (currNote.shape === _Exsurge3.NoteShape.Inclinatum) return pesSubpunctisState;else return torculusState; + } else return createNeume(new Neumes.Podatus(), false); + } + }; + + var clivisState = { + neume: function neume() { + return new Neumes.Clivis(); + }, + handle: function handle(currNote, prevNote) { + + if (currNote.shape === _Exsurge3.NoteShape.Default && currNote.staffPosition > prevNote.staffPosition) return porrectusState;else return createNeume(new Neumes.Clivis(), false); + } + }; + + var climacusState = { + neume: function neume() { + return new Neumes.Climacus(); + }, + handle: function handle(currNote, prevNote) { + if (currNote.shape !== _Exsurge3.NoteShape.Inclinatum) return createNeume(new Neumes.Climacus(), false);else return state; + } + }; + + var porrectusState = { + neume: function neume() { + return new Neumes.Porrectus(); + }, + handle: function handle(currNote, prevNote) { + + if (currNote.shape === _Exsurge3.NoteShape.Default && currNote.staffPosition < prevNote.staffPosition) return createNeume(new Neumes.PorrectusFlexus(), true);else return createNeume(new Neumes.Porrectus(), false); + } + }; + + var pesSubpunctisState = { + neume: function neume() { + return new Neumes.PesSubpunctis(); + }, + handle: function handle(currNote, prevNote) { + + if (currNote.shape !== _Exsurge3.NoteShape.Inclinatum) return createNeume(new Neumes.PesSubpunctis(), false);else return state; + } + }; + + var salicusState = { + neume: function neume() { + return new Neumes.Salicus(); + }, + handle: function handle(currNote, prevNote) { + + if (currNote.staffPosition < prevNote.staffPosition) return salicusFlexusState;else return createNeume(new Neumes.Salicus(), false); + } + }; + + var salicusFlexusState = { + neume: function neume() { + return new Neumes.SalicusFlexus(); + }, + handle: function handle(currNote, prevNote) { + return createNeume(new Neumes.SalicusFlexus(), false); + } + }; + + var scandicusState = { + neume: function neume() { + return new Neumes.Scandicus(); + }, + handle: function handle(currNote, prevNote) { + + if (prevNote.shape === _Exsurge3.NoteShape.Virga && currNote.shape === _Exsurge3.NoteShape.Inclinatum && currNote.staffPosition < prevNote.staffPosition) { + // if we get here, then it seems we have a podatus, now being followed by a climacus + // rather than a scandicus. react accordingly + return createNeume(new Neumes.Podatus(), false, false); + } else if (currNote.shape === _Exsurge3.NoteShape.Default && currNote.staffPosition < prevNote.staffPosition) return scandicusFlexusState;else return createNeume(new Neumes.Scandicus(), false); + } + }; + + var scandicusFlexusState = { + neume: function neume() { + return new Neumes.ScandicusFlexus(); + }, + handle: function handle(currNote, prevNote) { + return createNeume(new Neumes.ScandicusFlexus(), false); + } + }; + + var virgaState = { + neume: function neume() { + return new Neumes.Virga(); + }, + handle: function handle(currNote, prevNote) { + + if (currNote.shape === _Exsurge3.NoteShape.Inclinatum && currNote.staffPosition < prevNote.staffPosition) return climacusState;else if (currNote.shape === _Exsurge3.NoteShape.Virga && currNote.staffPosition === prevNote.staffPosition) return bivirgaState;else return createNeume(new Neumes.Virga(), false); + } + }; + + var bivirgaState = { + neume: function neume() { + return new Neumes.Bivirga(); + }, + handle: function handle(currNote, prevNote) { + + if (currNote.shape === _Exsurge3.NoteShape.Virga && currNote.staffPosition === prevNote.staffPosition) return createNeume(new Neumes.Trivirga(), true);else return createNeume(new Neumes.Bivirga(), false); + } + }; + + var apostrophaState = { + neume: function neume() { + return new Neumes.Apostropha(); + }, + handle: function handle(currNote, prevNote) { + if (currNote.staffPosition === prevNote.staffPosition) return distrophaState;else return createNeume(new Neumes.Apostropha(), false); + } + }; + + var distrophaState = { + neume: function neume() { + return new Neumes.Distropha(); + }, + handle: function handle(currNote, prevNote) { + if (currNote.staffPosition === prevNote.staffPosition) return tristrophaState;else return createNeume(new Neumes.Apostropha(), false, false); + } + }; + + var tristrophaState = { + neume: function neume() { + return new Neumes.Tristropha(); + }, + handle: function handle(currNote, prevNote) { + // we only create a tristropha when the note run ends after three + // and the neume() function of this state is called. Otherwise + // we always interpret the third note to belong to the next sequence + // of notes. + // + // fixme: gabc allows any number of punctum/stropha in succession... + // is this a valid neume type? Or is it just multiple *stropha neumes + // in succession? Should we simplify the apostropha/distropha/ + // tristropha classes to a generic stropha neume that can have 1 or + // more successive notes? + return createNeume(new Neumes.Distropha(), false, false); + } + }; + + var torculusState = { + neume: function neume() { + return new Neumes.Torculus(); + }, + handle: function handle(currNote, prevNote) { + if (currNote.shape === _Exsurge3.NoteShape.Default && currNote.staffPosition > prevNote.staffPosition) return torculusResupinusState;else return createNeume(new Neumes.Torculus(), false); + } + }; + + var torculusResupinusState = { + neume: function neume() { + return new Neumes.TorculusResupinus(); + }, + handle: function handle(currNote, prevNote) { + if (currNote.shape === _Exsurge3.NoteShape.Default && currNote.staffPosition < prevNote.staffPosition) return createNeume(new Neumes.TorculusResupinusFlexus(), true);else return createNeume(new Neumes.TorculusResupinus(), false); + } + }; + + var state = unknownState; + + while (currNoteIndex < notes.length) { + + var prevNote = currNoteIndex > 0 ? notes[currNoteIndex - 1] : null; + var currNote = notes[currNoteIndex]; + + state = state.handle(currNote, prevNote); + + // if we are on the last note, then try to create a neume if we need to. + if (currNoteIndex === notes.length - 1 && state !== unknownState) createNeume(state.neume(), true); + + currNoteIndex++; + } + + if (neumes.length > 0) { + if (finalTrailingSpace >= 0) { + neumes[neumes.length - 1].trailingSpace = finalTrailingSpace; + + if (finalTrailingSpace > ctxt.intraNeumeSpacing) neumes[neumes.length - 1].keepWithNext = false;else neumes[neumes.length - 1].keepWithNext = true; + } + } + + return neumes; + } + + // appends any notes created to the notes array argument + + }, { + key: 'createNoteFromData', + value: function createNoteFromData(ctxt, clef, data, notes) { + + var note = new _Exsurge3.Note(); + + if (data.length < 1) throw 'Invalid note data: ' + data; + + if (data[0] === '-') { + // liquescent initio debilis + note.liquescent = _Exsurge3.LiquescentType.InitioDebilis; + data = data.substring(1); + } + + if (data.length < 1) throw 'Invalid note data: ' + data; + + // the next char is always the pitch + var pitch = this.gabcHeightToExsurgePitch(clef, data[0]); + + if (data[0] === data[0].toUpperCase()) note.shape = _Exsurge3.NoteShape.Inclinatum; + + note.staffPosition = this.gabcHeightToExsurgeHeight(data[0]); + note.pitch = pitch; + + var mark; + var j; + + var episemaNoteIndex = notes.length; + var episemaNote = note; + + // process the modifiers + for (var i = 1; i < data.length; i++) { + + var c = data[i]; + var lookahead = '\0'; + + var haveLookahead = i + 1 < data.length; + if (haveLookahead) lookahead = data[i + 1]; + + switch (c) { + + // rhythmic markings + case '.': + + mark = null; + + // gabc supports putting up to two morae on each note, by repeating the + // period. here, we check to see if we've already created a mora for the + // note, and if so, we simply force the second one to have an Above + // position hint. if a user decides to try to put position indicators + // on the double morae (such as 1 or 2), then really the behavior is + // not defined by gabc, so it's on the user to figure it out. + if (note.morae.length > 0) { + // if we already have one mora, then create another but force a + // an alternative positionHint + haveLookahead = true; + if (Math.abs(note.staffPosition) % 2 === 0) lookahead = '1';else lookahead = '0'; + } + + mark = new Markings.Mora(ctxt, note); + if (haveLookahead && lookahead === '1') mark.positionHint = Markings.MarkingPositionHint.Above;else if (haveLookahead && lookahead === '0') mark.positionHint = Markings.MarkingPositionHint.Below; + + note.morae.push(mark); + break; + + case '_': + + var episemaHadModifier = false; + + mark = new Markings.HorizontalEpisema(episemaNote); + while (haveLookahead) { + + if (lookahead === '0') mark.positionHint = Markings.MarkingPositionHint.Below;else if (lookahead === '1') mark.positionHint = Markings.MarkingPositionHint.Above;else if (lookahead === '2') mark.terminating = true; // episema terminates + else if (lookahead === '3') mark.alignment = Markings.HorizontalEpisemaAlignment.Left;else if (lookahead === '4') mark.alignment = Markings.HorizontalEpisemaAlignment.Center;else if (lookahead === '5') mark.alignment = Markings.HorizontalEpisemaAlignment.Right;else break; + + // the gabc definition for epismata is so convoluted... + // - double underscores create epismata over multiple notes. + // - unless the _ has a 0, 1, 3, 4, or 5 modifier, which means + // another underscore puts a second epismata on the same note + // - (when there's a 2 lookahead, then this is treated as an + // unmodified underscore, so another underscore would be + // added to previous notes + if (mark.alignment !== Markings.HorizontalEpisemaAlignment.Default && mark.positionHint !== Markings.MarkingPositionHint.Below) episemaHadModifier = true; + + i++; + haveLookahead = i + 1 < data.length; + + if (haveLookahead) lookahead = data[i + 1]; + } + + // since gabc allows consecutive underscores which is a shortcut to + // apply the epismata to previous notes, we keep track of that here + // in order to add the new episema to the correct note. + + if (episemaNote) episemaNote.epismata.push(mark); + + if (episemaNote === note && episemaHadModifier) episemaNote = note;else if (episemaNoteIndex >= 0 && notes.length > 0) episemaNote = notes[--episemaNoteIndex]; + + break; + + case '\'': + mark = new Markings.Ictus(ctxt, note); + if (haveLookahead && lookahead === '1') mark.positionHint = Markings.MarkingPositionHint.Above;else if (haveLookahead && lookahead === '0') mark.positionHint = Markings.MarkingPositionHint.Below; + + note.ictus = mark; + break; + + //note shapes + case 'r': + if (haveLookahead && lookahead === '1') { + note.acuteAccent = new Markings.AcuteAccent(ctxt, note); + i++; + } else note.shapeModifiers |= _Exsurge3.NoteShapeModifiers.Cavum; + break; + + case 's': + + if (note.shape === _Exsurge3.NoteShape.Stropha) { + // if we're already a stropha, that means this is gabc's + // quick stropha feature (e.g., gsss). create a new note + notes.push(note); + note = new _Exsurge3.Note(); + episemaNoteIndex++; // since a new note was added, increase the index here + } + + note.shape = _Exsurge3.NoteShape.Stropha; + break; + + case 'v': + + if (note.shape === _Exsurge3.NoteShape.Virga) { + // if we're already a stropha, that means this is gabc's + // quick virga feature (e.g., gvvv). create a new note + notes.push(note); + note = new _Exsurge3.Note(); + episemaNoteIndex++; // since a new note was added, increase the index here + } + + note.shape = _Exsurge3.NoteShape.Virga; + break; + + case 'w': + note.shape = _Exsurge3.NoteShape.Quilisma; + break; + + case 'o': + note.shape = _Exsurge3.NoteShape.Oriscus; + if (haveLookahead && lookahead === '<') { + note.shapeModifiers |= _Exsurge3.NoteShapeModifiers.Ascending; + i++; + } else if (haveLookahead && lookahead === '>') { + note.shapeModifiers |= _Exsurge3.NoteShapeModifiers.Descending; + i++; + } + break; + + case 'O': + note.shape = _Exsurge3.NoteShape.Oriscus; + if (haveLookahead && lookahead === '<') { + note.shapeModifiers |= _Exsurge3.NoteShapeModifiers.Ascending | _Exsurge3.NoteShapeModifiers.Stemmed; + i++; + } else if (haveLookahead && lookahead === '>') { + note.shapeModifiers |= _Exsurge3.NoteShapeModifiers.Descending | _Exsurge3.NoteShapeModifiers.Stemmed; + i++; + } else note.shapeModifiers |= _Exsurge3.NoteShapeModifiers.Stemmed; + break; + + // liquescents + case '~': + if (note.shape === _Exsurge3.NoteShape.Inclinatum) note.liquescent |= _Exsurge3.LiquescentType.Small;else if (note.shape === _Exsurge3.NoteShape.Oriscus) note.liquescent |= _Exsurge3.LiquescentType.Large;else note.liquescent |= _Exsurge3.LiquescentType.Small; + break; + case '<': + note.liquescent |= _Exsurge3.LiquescentType.Ascending; + break; + case '>': + note.liquescent |= _Exsurge3.LiquescentType.Descending; + break; + + // accidentals + case 'x': + if (note.pitch.step === _Exsurge.Step.Mi) note.pitch.step = _Exsurge.Step.Me;else if (note.pitch.step === _Exsurge.Step.Ti) note.pitch.step = _Exsurge.Step.Te; + break; + case 'y': + if (note.pitch.step === _Exsurge.Step.Te) note.pitch.step = _Exsurge.Step.Ti;else if (note.pitch.step === _Exsurge.Step.Me) note.pitch.step = _Exsurge.Step.Mi;else if (note.pitch.step === _Exsurge.Step.Du) note.pitch.step = _Exsurge.Step.Do;else if (note.pitch.step === _Exsurge.Step.Fu) note.pitch.step = _Exsurge.Step.Fa; + break; + case '#': + if (note.pitch.step === _Exsurge.Step.Do) note.pitch.step = _Exsurge.Step.Du;else if (note.pitch.step === _Exsurge.Step.Fa) note.pitch.step = _Exsurge.Step.Fu; + break; + + // gabc special item groups + case '[': + // read in the whole group and parse it + var startIndex = ++i; + while (i < data.length && data[i] !== ']') { + i++; + }this.processInstructionForNote(ctxt, note, data.substring(startIndex, i)); + break; + } + } + + notes.push(note); + } + + // an instruction in this context is referring to a special gabc coding found after + // notes between ['s and ]'s. choral signs and braces fall into this + // category. + // + // currently only brace instructions are supported here! + + }, { + key: 'processInstructionForNote', + value: function processInstructionForNote(ctxt, note, instruction) { + + var results = instruction.match(__braceSpecRegex); + + if (results === null) return; + + // see the comments at the definition of __braceSpecRegex for the + // capturing groups + var above = results[1] === 'o'; + var shape = Markings.BraceShape.CurlyBrace; // default + + switch (results[2]) { + case 'b': + shape = Markings.BraceShape.RoundBrace; + break; + case 'cb': + shape = Markings.BraceShape.CurlyBrace; + break; + case 'cba': + shape = Markings.BraceShape.AccentedCurlyBrace; + break; + } + + var attachmentPoint = results[3] === '0' ? Markings.BraceAttachment.Left : Markings.BraceAttachment.Right; + var brace = null; + var type; + + if (results[4] === '{') note.braceStart = new Markings.BracePoint(note, above, shape, attachmentPoint);else note.braceEnd = new Markings.BracePoint(note, above, shape, attachmentPoint); + } + + // takes raw gabc text source and parses it into words. For example, passing + // in a string of "me(f.) (,) ma(fff)num(d!ewf) tu(fgF'E)am,(f.)" would return + // an array of four strings: ["me(f.)", "(,)", "ma(fff)num(d!ewf)", "tu(fgF'E)am,(f.)"] + + }, { + key: 'splitWords', + value: function splitWords(gabcNotations) { + // split the notations on whitespace boundaries, as long as the space + // immediately follows a set of parentheses. Prior to doing that, we replace + // all whitespace with spaces, which prevents tabs and newlines from ending + // up in the notation data. + gabcNotations = gabcNotations.trim().replace(/\s/g, ' ').replace(/\) (?=[^\)]*(?:\(|$))/g, ')\n'); + return gabcNotations.split(/\n/g); + } + }, { + key: 'parseSource', + value: function parseSource(gabcSource) { + return this.parseWords(this.splitWords(gabcSource)); + } + + // gabcWords is an array of strings, e.g., the result of splitWords above + + }, { + key: 'parseWords', + value: function parseWords(gabcWords) { + var words = []; + + for (var i = 0; i < gabcWords.length; i++) { + words.push(this.parseWord(gabcWords[i])); + }return words; + } + + // returns an array of objects, each of which has the following properties + // - notations (string) + // - lyrics (array of strings) + + }, { + key: 'parseWord', + value: function parseWord(gabcWord) { + + var syllables = []; + var matches = []; + + while (match = __syllablesRegex.exec(gabcWord)) { + matches.push(match); + }for (var j = 0; j < matches.length; j++) { + var match = matches[j]; + + var lyrics = match[1].trim().split('|'); + var notations = match[2]; + + syllables.push({ + notations: notations, + lyrics: lyrics + }); + } + + return syllables; + } + + // returns pitch + + }, { + key: 'gabcHeightToExsurgeHeight', + value: function gabcHeightToExsurgeHeight(gabcHeight) { + return gabcHeight.toLowerCase().charCodeAt(0) - 'a'.charCodeAt(0) - 6; + } + + // returns pitch + + }, { + key: 'gabcHeightToExsurgePitch', + value: function gabcHeightToExsurgePitch(clef, gabcHeight) { + var exsurgeHeight = this.gabcHeightToExsurgeHeight(gabcHeight); + + var pitch = clef.staffPositionToPitch(exsurgeHeight); + + if (clef.activeAccidental !== null) clef.activeAccidental.applyToPitch(pitch); + + return pitch; + } + }]); + + return Gabc; + }(); + +/***/ }, +/* 11 */ +/***/ function(module, exports, __webpack_require__) { + + 'use strict'; + + Object.defineProperty(exports, "__esModule", { + value: true + }); + exports.Virga = exports.Tristropha = exports.TorculusResupinusFlexus = exports.TorculusResupinus = exports.Torculus = exports.ScandicusFlexus = exports.Scandicus = exports.SalicusFlexus = exports.Salicus = exports.Punctum = exports.PunctaInclinata = exports.PorrectusFlexus = exports.Porrectus = exports.Podatus = exports.PesSubpunctis = exports.PesQuassus = exports.Oriscus = exports.Distropha = exports.Clivis = exports.Climacus = exports.Trivirga = exports.Bivirga = exports.Apostropha = exports.Neume = undefined; + + var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } }; + + var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }(); // + // Author(s): + // Fr. Matthew Spencer, OSJ + // + // Copyright (c) 2008-2016 Fr. Matthew Spencer, OSJ + // + // Permission is hereby granted, free of charge, to any person obtaining a copy + // of this software and associated documentation files (the "Software"), to deal + // in the Software without restriction, including without limitation the rights + // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + // copies of the Software, and to permit persons to whom the Software is + // furnished to do so, subject to the following conditions: + // + // The above copyright notice and this permission notice shall be included in + // all copies or substantial portions of the Software. + // + // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + // THE SOFTWARE. + // + + var _Exsurge = __webpack_require__(1); + + var Exsurge = _interopRequireWildcard(_Exsurge); + + var _Exsurge2 = __webpack_require__(4); + + var _Exsurge3 = __webpack_require__(6); + + var _ExsurgeChant = __webpack_require__(9); + + var _Exsurge4 = __webpack_require__(3); + + function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key]; } } newObj.default = obj; return newObj; } } + + function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; } + + function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; } + + function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } + + var NeumeBuilder = function () { + function NeumeBuilder(ctxt, neume) { + var startingX = arguments.length <= 2 || arguments[2] === undefined ? 0 : arguments[2]; + + _classCallCheck(this, NeumeBuilder); + + this.ctxt = ctxt; + this.neume = neume; + this.x = startingX; + this.lastNote = null; + this.lineIsHanging = false; + } + + // used to start a hanging line on the left of the next note + + + _createClass(NeumeBuilder, [{ + key: 'lineFrom', + value: function lineFrom(note) { + this.lastNote = note; + this.lineIsHanging = true; + + return this; + } + + // add a note, with a connecting line on the left if we have one + + }, { + key: 'noteAt', + value: function noteAt(note, glyph) { + var withLineTo = arguments.length <= 2 || arguments[2] === undefined ? true : arguments[2]; + + + if (!note) throw "NeumeBuilder.noteAt: note must be a valid note"; + + if (!glyph) throw "NeumeBuilder.noteAt: glyph must be a valid glyph code"; + + note.setGlyph(this.ctxt, glyph); + var noteAlignsRight = note.glyphVisualizer.align === "right"; + + var needsLine = withLineTo && this.lastNote !== null && (this.lineIsHanging || this.lastNote.glyphVisualizer.align === 'right' || Math.abs(this.lastNote.staffPosition - note.staffPosition) > 1); + + if (needsLine) { + var line = new _Exsurge2.NeumeLineVisualizer(this.ctxt, this.lastNote, note, this.lineIsHanging); + this.neume.addVisualizer(line); + line.bounds.x = Math.max(0, this.x - line.bounds.width); + + if (!noteAlignsRight) this.x = line.bounds.x; + } + + // if this is the first note of a right aligned glyph (probably an initio debilis), + // then there's nothing to worry about. but if it's not then first, then this + // subtraction will right align it visually + if (noteAlignsRight && this.lastNote) note.bounds.x = this.x - note.bounds.width;else { + note.bounds.x = this.x; + this.x += note.bounds.width; + } + + this.neume.addVisualizer(note); + + this.lastNote = note; + this.lineIsHanging = false; + + return this; + } + + // a special form of noteAdd that creates a virga + // uses a punctum cuadratum and a line rather than the virga glyphs + + }, { + key: 'virgaAt', + value: function virgaAt(note) { + var withLineTo = arguments.length <= 1 || arguments[1] === undefined ? true : arguments[1]; + + + // add the punctum for the virga + this.noteAt(note, _Exsurge2.GlyphCode.PunctumQuadratum); + + // add a line for the virga + var line = new _Exsurge2.VirgaLineVisualizer(this.ctxt, note); + this.x -= line.bounds.width; + line.bounds.x = this.x; + this.neume.addVisualizer(line); + + this.lastNote = note; + this.lineIsHanging = false; + + return this; + } + }, { + key: 'advanceBy', + value: function advanceBy(x) { + this.lastNote = null; + this.lineIsHanging = false; + + this.x += x; + + return this; + } + + // for terminating hanging lines with no lower notes + + }, { + key: 'withLineEndingAt', + value: function withLineEndingAt(note) { + + if (this.lastNote === null) return; + + var line = new _Exsurge2.NeumeLineVisualizer(this.ctxt, this.lastNote, note, true); + this.neume.addVisualizer(line); + this.x -= line.bounds.width; + line.bounds.x = this.x; + + this.neume.addVisualizer(line); + + this.lastNote = note; + + return this; + } + }, { + key: 'withPodatus', + value: function withPodatus(lowerNote, upperNote) { + + var upperGlyph; + var lowerGlyph; + + if (lowerNote.liquescent === _Exsurge3.LiquescentType.InitioDebilis) { + + // liquescent upper note or not? + if (upperNote.liquescent === _Exsurge3.LiquescentType.None) upperGlyph = _Exsurge2.GlyphCode.PunctumQuadratum;else upperGlyph = _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent; + + lowerGlyph = _Exsurge2.GlyphCode.TerminatingDesLiquescent; + } else if (upperNote.liquescent & _Exsurge3.LiquescentType.Small) { + lowerGlyph = _Exsurge2.GlyphCode.BeginningAscLiquescent; + upperGlyph = _Exsurge2.GlyphCode.TerminatingAscLiquescent; + } else if (upperNote.liquescent & _Exsurge3.LiquescentType.Ascending) { + lowerGlyph = _Exsurge2.GlyphCode.PunctumQuadratum; + upperGlyph = _Exsurge2.GlyphCode.PunctumQuadratumAscLiquescent; + } else if (upperNote.liquescent & _Exsurge3.LiquescentType.Descending) { + lowerGlyph = _Exsurge2.GlyphCode.PunctumQuadratum; + upperGlyph = _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent; + } else { + // standard shape + lowerGlyph = _Exsurge2.GlyphCode.PodatusLower; + upperGlyph = _Exsurge2.GlyphCode.PodatusUpper; + } + + // allow a quilisma pes + if (lowerNote.shape === _Exsurge3.NoteShape.Quilisma) lowerGlyph = _Exsurge2.GlyphCode.Quilisma; + + this.noteAt(lowerNote, lowerGlyph).noteAt(upperNote, upperGlyph); + + // make sure we don't have lines connected to the podatus + this.lastNote = null; + + return this; + } + }, { + key: 'withClivis', + value: function withClivis(upper, lower) { + + var line; + + var upperGlyph; + var lowerGlyph; + + if (upper.shape === _Exsurge3.NoteShape.Oriscus) this.noteAt(upper, _Exsurge2.GlyphCode.OriscusDes, false);else this.lineFrom(lower).noteAt(upper, _Exsurge2.GlyphCode.PunctumQuadratum); + + if (lower.liquescent & _Exsurge3.LiquescentType.Small) { + lowerGlyph = _Exsurge2.GlyphCode.TerminatingDesLiquescent; + } else if (lower.liquescent === _Exsurge3.LiquescentType.Ascending) lowerGlyph = _Exsurge2.GlyphCode.PunctumQuadratumAscLiquescent;else if (lower.liquescent === _Exsurge3.LiquescentType.Descending) lowerGlyph = _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent;else lowerGlyph = _Exsurge2.GlyphCode.PunctumQuadratum; + + this.noteAt(lower, lowerGlyph); + + // make sure we don't have lines connected to the clivis + this.lastNote = null; + + return this; + } + + // lays out a sequence of notes that are inclinati (e.g., climacus, pes subpunctis) + + }, { + key: 'withInclinati', + value: function withInclinati(notes) { + + var staffPosition = notes[0].staffPosition, + prevStaffPosition = notes[0].staffPosition; + + // it is important to advance by the width of the inclinatum glyph itself + // rather than by individual note widths, so that any liquescents are spaced + // the same as non-liquscents + var advanceWidth = _Exsurge4.Glyphs.PunctumInclinatum.bounds.width * this.ctxt.glyphScaling; + + // now add all the punctum inclinati + for (var i = 0; i < notes.length; i++, prevStaffPosition = staffPosition) { + var note = notes[i]; + + if (note.liquescent & _Exsurge3.LiquescentType.Small) note.setGlyph(this.ctxt, _Exsurge2.GlyphCode.PunctumInclinatumLiquescent);else if (note.liquescent & _Exsurge3.LiquescentType.Large) + // fixme: is the large inclinatum liquescent the same as the apostropha? + note.setGlyph(this.ctxt, _Exsurge2.GlyphCode.Stropha);else + // fixme: some climaci in the new chant books end with a punctum quadratum + // (see, for example, the antiphon "Sancta Maria" for October 7). + note.setGlyph(this.ctxt, _Exsurge2.GlyphCode.PunctumInclinatum); + + staffPosition = note.staffPosition; + + // fixme: how do these calculations look for puncti inclinati based on staff position offsets? + var multiple; + switch (Math.abs(prevStaffPosition - staffPosition)) { + case 0: + multiple = 1.1; + break; + case 1: + multiple = 0.8; + break; + default: + multiple = 1.2; + break; + } + + if (i > 0) this.x += advanceWidth * multiple; + + note.bounds.x = this.x; + + this.neume.addVisualizer(note); + } + + return this; + } + }, { + key: 'withPorrectusSwash', + value: function withPorrectusSwash(start, end) { + + var needsLine = this.lastNote !== null && (this.lineIsHanging || this.lastNote.glyphVisualizer.align === 'right' || Math.abs(this.lastNote.staffPosition - start.staffPosition) > 1); + + if (needsLine) { + var line = new _Exsurge2.NeumeLineVisualizer(this.ctxt, this.lastNote, start, this.lineIsHanging); + this.x = Math.max(0, this.x - line.bounds.width); + line.bounds.x = this.x; + this.neume.addVisualizer(line); + } + + var glyph; + + switch (start.staffPosition - end.staffPosition) { + case 1: + glyph = _Exsurge2.GlyphCode.Porrectus1; + break; + case 2: + glyph = _Exsurge2.GlyphCode.Porrectus2; + break; + case 3: + glyph = _Exsurge2.GlyphCode.Porrectus3; + break; + case 4: + glyph = _Exsurge2.GlyphCode.Porrectus4; + break; + default: + // fixme: should we generate an error here? + glyph = _Exsurge2.GlyphCode.None; + break; + } + + start.setGlyph(this.ctxt, glyph); + start.bounds.x = this.x; + + // the second glyph does not draw anything, but it still has logical importance for the editing + // environment...it can respond to changes which will then change the swash glyph of the first. + end.setGlyph(this.ctxt, _Exsurge2.GlyphCode.None); + + this.x = start.bounds.right(); + end.bounds.x = this.x - end.bounds.width; + + this.neume.addVisualizer(start); + this.neume.addVisualizer(end); + + this.lastNote = end; + this.lineIsHanging = false; + + return this; + } + }]); + + return NeumeBuilder; + }(); + + /* + * Neumes base class + */ + + + var Neume = exports.Neume = function (_ChantNotationElement) { + _inherits(Neume, _ChantNotationElement); + + function Neume() { + var notes = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0]; + + _classCallCheck(this, Neume); + + var _this = _possibleConstructorReturn(this, Object.getPrototypeOf(Neume).call(this)); + + _this.isNeume = true; // poor man's reflection + _this.notes = notes; + + for (var i = 0; i < notes.length; i++) { + notes[i].neume = _this; + }return _this; + } + + _createClass(Neume, [{ + key: 'addNote', + value: function addNote(note) { + note.neume = this; + this.notes.push(note); + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Neume.prototype), 'performLayout', this).call(this, ctxt); + } + }, { + key: 'finishLayout', + value: function finishLayout(ctxt) { + + // allow subclasses an opportunity to position their own markings... + this.positionMarkings(); + + // layout the markings of the notes + for (var i = 0; i < this.notes.length; i++) { + var note = this.notes[i]; + var j; + + for (j = 0; j < note.epismata.length; j++) { + note.epismata[j].performLayout(ctxt); + this.addVisualizer(note.epismata[j]); + } + + for (j = 0; j < note.morae.length; j++) { + note.morae[j].performLayout(ctxt); + this.addVisualizer(note.morae[j]); + } + + // if the note has an ictus, then add it here + if (note.ictus) { + note.ictus.performLayout(ctxt); + this.addVisualizer(note.ictus); + } + + if (note.acuteAccent) { + note.acuteAccent.performLayout(ctxt); + this.addVisualizer(note.acuteAccent); + } + + // braces are handled by the chant line, so we don't mess with them here + // this is because brace size depends on chant line logic (neume spacing, + // justification, etc.) so they are considered chant line level + // markings rather than note level markings + } + + this.origin.x = this.notes[0].origin.x; + this.origin.y = this.notes[0].origin.y; + + _get(Object.getPrototypeOf(Neume.prototype), 'finishLayout', this).call(this, ctxt); + } + }, { + key: 'resetDependencies', + value: function resetDependencies() {} + }, { + key: 'build', + value: function build(ctxt) { + return new NeumeBuilder(ctxt, this); + } + + // subclasses can override this in order to correctly place markings in a neume specific way + + }, { + key: 'positionMarkings', + value: function positionMarkings() {} + }]); + + return Neume; + }(_Exsurge2.ChantNotationElement); + + /* + * Apostropha + */ + + + var Apostropha = exports.Apostropha = function (_Neume) { + _inherits(Apostropha, _Neume); + + function Apostropha() { + _classCallCheck(this, Apostropha); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Apostropha).apply(this, arguments)); + } + + _createClass(Apostropha, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var positionHint = _ExsurgeChant.MarkingPositionHint.Above; + + // logic here is this: if first episema is default position, place it above. + // then place the second one (if there is one) opposite of the first. + for (var i = 0; i < this.notes[0].epismata.length; i++) { + if (this.notes[0].epismata[i].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[0].epismata[i].positionHint = positionHint;else positionHint = this.notes[0].epismata[i].positionHint; + + // now place the next one in the opposite position + positionHint = positionHint === _ExsurgeChant.MarkingPositionHint.Above ? _ExsurgeChant.MarkingPositionHint.Below : _ExsurgeChant.MarkingPositionHint.Above; + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Apostropha.prototype), 'performLayout', this).call(this, ctxt); + + var y = ctxt.calculateHeightFromStaffPosition(4); + + this.build(ctxt).noteAt(this.notes[0], Apostropha.getNoteGlyphCode(this.notes[0])); + + this.finishLayout(ctxt); + } + }], [{ + key: 'getNoteGlyphCode', + value: function getNoteGlyphCode(note) { + + if (note.shape === _Exsurge3.NoteShape.Stropha) return _Exsurge2.GlyphCode.Stropha; + + if (note.liquescent !== _Exsurge3.LiquescentType.None) return _Exsurge2.GlyphCode.StrophaLiquescent; + + if (note.shapeModifiers & _Exsurge3.NoteShapeModifiers.Cavum) return _Exsurge2.GlyphCode.PunctumCavum; + + return _Exsurge2.GlyphCode.PunctumQuadratum; + } + }]); + + return Apostropha; + }(Neume); + + /* + * Bivirga + * + * For simplicity in implementation, Bivirga's have two notes in the object + * structure. These technically must be the same pitch though. + */ + + + var Bivirga = exports.Bivirga = function (_Neume2) { + _inherits(Bivirga, _Neume2); + + function Bivirga() { + _classCallCheck(this, Bivirga); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Bivirga).apply(this, arguments)); + } + + _createClass(Bivirga, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var marking, i, j; + + for (i = 0; i < this.notes.length; i++) { + var positionHint = _ExsurgeChant.MarkingPositionHint.Above; + + // logic here is this: if first episema is default position, place it above. + // then place the second one (if there is one) opposite of the first. + for (j = 0; j < this.notes[i].epismata.length; j++) { + if (this.notes[i].epismata[j].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[i].epismata[j].positionHint = positionHint;else positionHint = this.notes[i].epismata[j].positionHint; + + // now place the next one in the opposite position + positionHint = positionHint === _ExsurgeChant.MarkingPositionHint.Above ? _ExsurgeChant.MarkingPositionHint.Below : _ExsurgeChant.MarkingPositionHint.Above; + } + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Bivirga.prototype), 'performLayout', this).call(this, ctxt); + + this.build(ctxt).virgaAt(this.notes[0]).advanceBy(ctxt.intraNeumeSpacing).virgaAt(this.notes[1]); + + this.finishLayout(ctxt); + } + }]); + + return Bivirga; + }(Neume); + + /* + * Trivirga + * + * For simplicity in implementation, Trivirga's have three notes in the object + * structure. These technically must be the same pitch though. + */ + + + var Trivirga = exports.Trivirga = function (_Neume3) { + _inherits(Trivirga, _Neume3); + + function Trivirga() { + _classCallCheck(this, Trivirga); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Trivirga).apply(this, arguments)); + } + + _createClass(Trivirga, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var marking, i, j; + + for (i = 0; i < this.notes.length; i++) { + var positionHint = _ExsurgeChant.MarkingPositionHint.Above; + + // logic here is this: if first episema is default position, place it above. + // then place the second one (if there is one) opposite of the first. + for (j = 0; j < this.notes[i].epismata.length; j++) { + if (this.notes[i].epismata[j].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[i].epismata[j].positionHint = positionHint;else positionHint = this.notes[i].epismata[j].positionHint; + + // now place the next one in the opposite position + positionHint = positionHint === _ExsurgeChant.MarkingPositionHint.Above ? _ExsurgeChant.MarkingPositionHint.Below : _ExsurgeChant.MarkingPositionHint.Above; + } + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Trivirga.prototype), 'performLayout', this).call(this, ctxt); + + this.build(ctxt).virgaAt(this.notes[0]).advanceBy(ctxt.intraNeumeSpacing).virgaAt(this.notes[1]).advanceBy(ctxt.intraNeumeSpacing).virgaAt(this.notes[2]); + + this.finishLayout(ctxt); + } + }]); + + return Trivirga; + }(Neume); + + /* + * Climacus + */ + + + var Climacus = exports.Climacus = function (_Neume4) { + _inherits(Climacus, _Neume4); + + function Climacus() { + _classCallCheck(this, Climacus); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Climacus).apply(this, arguments)); + } + + _createClass(Climacus, [{ + key: 'positionMarkings', + value: function positionMarkings() { + + for (var i = 0; i < this.notes.length; i++) { + for (var j = 0; j < this.notes[i].epismata.length; j++) { + var mark = this.notes[i].epismata[j]; + + if (mark.positionHint === _ExsurgeChant.MarkingPositionHint.Default) mark.positionHint = _ExsurgeChant.MarkingPositionHint.Above; + } + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Climacus.prototype), 'performLayout', this).call(this, ctxt); + + this.build(ctxt).virgaAt(this.notes[0]).advanceBy(ctxt.intraNeumeSpacing / 2).withInclinati(this.notes.slice(1)); + + this.finishLayout(ctxt); + } + }]); + + return Climacus; + }(Neume); + + /* + * Clivis + */ + + + var Clivis = exports.Clivis = function (_Neume5) { + _inherits(Clivis, _Neume5); + + function Clivis() { + _classCallCheck(this, Clivis); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Clivis).apply(this, arguments)); + } + + _createClass(Clivis, [{ + key: 'positionMarkings', + value: function positionMarkings() { + + var hasLowerMora = false; + var mark, i; + + // 1. morae need to be lined up if both notes have morae + // 2. like the podatus, mora on lower note needs to below + // under certain circumstances + for (i = 0; i < this.notes[1].morae.length; i++) { + mark = this.notes[1].morae[i]; + + if (this.notes[0].staffPosition - this.notes[1].staffPosition === 1 && Math.abs(this.notes[1].staffPosition % 2) === 1) mark.positionHint = _ExsurgeChant.MarkingPositionHint.Below; + } + + for (i = 0; i < this.notes[0].morae.length; i++) { + + if (hasLowerMora) { + mark = this.notes[0].morae[i]; + mark.positionHint = _ExsurgeChant.MarkingPositionHint.Above; + mark.horizontalOffset += this.notes[1].bounds.right() - this.notes[0].bounds.right(); + } + } + + for (i = 0; i < this.notes[0].epismata.length; i++) { + mark = this.notes[0].epismata[i]; + + if (mark.positionHint === _ExsurgeChant.MarkingPositionHint.Default) mark.positionHint = _ExsurgeChant.MarkingPositionHint.Above; + } + + for (i = 0; i < this.notes[1].epismata.length; i++) { + mark = this.notes[1].epismata[i]; + + if (mark.positionHint === _ExsurgeChant.MarkingPositionHint.Default) mark.positionHint = _ExsurgeChant.MarkingPositionHint.Above; + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Clivis.prototype), 'performLayout', this).call(this, ctxt); + + var upper = this.notes[0]; + var lower = this.notes[1]; + + this.build(ctxt).withClivis(upper, lower); + + this.finishLayout(ctxt); + } + }]); + + return Clivis; + }(Neume); + + /* + * Distropha + * + * For simplicity in implementation, Distropha's have two notes in the object + * structure. These technically must be the same pitch though (like Bivirga). + */ + + + var Distropha = exports.Distropha = function (_Neume6) { + _inherits(Distropha, _Neume6); + + function Distropha() { + _classCallCheck(this, Distropha); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Distropha).apply(this, arguments)); + } + + _createClass(Distropha, [{ + key: 'positionMarkings', + value: function positionMarkings() { + + for (var i = 0; i < this.notes.length; i++) { + var positionHint = _ExsurgeChant.MarkingPositionHint.Above; + + // logic here is this: if first episema is default position, place it above. + // then place the second one (if there is one) opposite of the first. + for (var j = 0; j < this.notes[i].epismata.length; j++) { + if (this.notes[i].epismata[j].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[i].epismata[j].positionHint = positionHint;else positionHint = this.notes[i].epismata[j].positionHint; + + // now place the next one in the opposite position + positionHint = positionHint === _ExsurgeChant.MarkingPositionHint.Above ? _ExsurgeChant.MarkingPositionHint.Below : _ExsurgeChant.MarkingPositionHint.Above; + } + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Distropha.prototype), 'performLayout', this).call(this, ctxt); + + this.build(ctxt).noteAt(this.notes[0], Apostropha.getNoteGlyphCode(this.notes[0])).advanceBy(ctxt.intraNeumeSpacing).noteAt(this.notes[1], Apostropha.getNoteGlyphCode(this.notes[1])); + + this.finishLayout(ctxt); + } + }]); + + return Distropha; + }(Neume); + + /* + * Oriscus + */ + + + var Oriscus = exports.Oriscus = function (_Neume7) { + _inherits(Oriscus, _Neume7); + + function Oriscus() { + _classCallCheck(this, Oriscus); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Oriscus).apply(this, arguments)); + } + + _createClass(Oriscus, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var positionHint = _ExsurgeChant.MarkingPositionHint.Above; + + // logic here is this: if first episema is default position, place it above. + // then place the second one (if there is one) opposite of the first. + for (var i = 0; i < this.notes[0].epismata.length; i++) { + if (this.notes[0].epismata[i].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[0].epismata[i].positionHint = positionHint;else positionHint = this.notes[0].epismata[i].positionHint; + + // now place the next one in the opposite position + positionHint = positionHint === _ExsurgeChant.MarkingPositionHint.Above ? _ExsurgeChant.MarkingPositionHint.Below : _ExsurgeChant.MarkingPositionHint.Above; + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Oriscus.prototype), 'performLayout', this).call(this, ctxt); + + // determine the glyph to use + var note = this.notes[0]; + var glyph; + + if (note.liquescent !== _Exsurge3.LiquescentType.None) { + glyph = _Exsurge2.GlyphCode.OriscusLiquescent; + } else { + if (note.shapeModifiers & _Exsurge3.NoteShapeModifiers.Ascending) glyph = _Exsurge2.GlyphCode.OriscusAsc;else if (note.shapeModifiers & _Exsurge3.NoteShapeModifiers.Descending) glyph = _Exsurge2.GlyphCode.OriscusDes;else { + // by default we take the descending form, unless we can figure out by a lookahead here + glyph = _Exsurge2.GlyphCode.OriscusDes; + + // try to find a neume following this one + var neume = ctxt.findNextNeume(); + + if (neume) { + var nextNoteStaffPosition = ctxt.activeClef.pitchToStaffPosition(neume.notes[0].pitch); + + if (nextNoteStaffPosition > note.staffPosition) glyph = _Exsurge2.GlyphCode.OriscusAsc; + } + } + } + + this.build(ctxt).noteAt(note, glyph); + + this.finishLayout(ctxt); + } + }, { + key: 'resetDependencies', + value: function resetDependencies() { + + // a single oriscus tries to automatically use the right direction + // based on the following neumes. if we don't have a manually designated + // direction, then we reset our layout so that we can try to guess it + // at next layout phase. + if (this.notes[0].shapeModifiers & _Exsurge3.NoteShapeModifiers.Ascending || this.notes[0].shapeModifiers & _Exsurge3.NoteShapeModifiers.Descending) return; + + this.needsLayout = true; + } + }]); + + return Oriscus; + }(Neume); + + /* + * PesQuassus + */ + + + var PesQuassus = exports.PesQuassus = function (_Neume8) { + _inherits(PesQuassus, _Neume8); + + function PesQuassus() { + _classCallCheck(this, PesQuassus); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(PesQuassus).apply(this, arguments)); + } + + _createClass(PesQuassus, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(PesQuassus.prototype), 'performLayout', this).call(this, ctxt); + + var lower = this.notes[0]; + var upper = this.notes[1]; + + var lowerGlyph, upperGlyph; + + var lowerStaffPos = lower.staffPosition; + var upperStaffPos = upper.staffPosition; + + if (lower.shape === _Exsurge3.NoteShape.Oriscus) lowerGlyph = _Exsurge2.GlyphCode.OriscusAsc;else lowerGlyph = _Exsurge2.GlyphCode.PunctumQuadratum; + + var builder = this.build(ctxt).noteAt(lower, lowerGlyph); + + if (upperStaffPos - lowerStaffPos === 1) // use a virga glyph in this case + builder.virgaAt(upper);else if (upper.liquescent === _Exsurge3.LiquescentType.LargeDescending) builder.noteAt(upper, _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent).withLineEndingAt(lower);else builder.noteAt(upper, _Exsurge2.GlyphCode.PunctumQuadratum).withLineEndingAt(lower); + + this.finishLayout(ctxt); + } + }]); + + return PesQuassus; + }(Neume); + + /* + * PesSubpunctis + */ + + + var PesSubpunctis = exports.PesSubpunctis = function (_Neume9) { + _inherits(PesSubpunctis, _Neume9); + + function PesSubpunctis() { + _classCallCheck(this, PesSubpunctis); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(PesSubpunctis).apply(this, arguments)); + } + + _createClass(PesSubpunctis, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(PesSubpunctis.prototype), 'performLayout', this).call(this, ctxt); + + // podatus followed by inclinati + this.build(ctxt).withPodatus(this.notes[0], this.notes[1]).advanceBy(ctxt.intraNeumeSpacing / 2).withInclinati(this.notes.slice(2)); + + this.finishLayout(ctxt); + } + }]); + + return PesSubpunctis; + }(Neume); + + /* + * Podatus + * + * This podatus class handles a few neume types actually, depending on the note + * data: Podatus (including various liquescent types on the upper note), + * Podatus initio debilis, and Quilisma-Pes + */ + + + var Podatus = exports.Podatus = function (_Neume10) { + _inherits(Podatus, _Neume10); + + function Podatus() { + _classCallCheck(this, Podatus); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Podatus).apply(this, arguments)); + } + + _createClass(Podatus, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var marking, i; + + // 1. episema on lower note by default be below, upper note above + // 2. morae: + // a. if podatus difference is 1 and lower note is on a line, + // the lower mora should be below + for (i = 0; i < this.notes[0].epismata.length; i++) { + if (this.notes[0].epismata[i].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[0].epismata[i].positionHint = _ExsurgeChant.MarkingPositionHint.Below; + } // if this note has two or more (!?) morae then we just leave them be + // since they have already been assigned position hints. + if (this.notes[0].morae.length < 2) { + for (i = 0; i < this.notes[0].morae.length; i++) { + marking = this.notes[0].morae[i]; + + if (this.notes[1].staffPosition - this.notes[0].staffPosition === 1 && Math.abs(this.notes[0].staffPosition % 2) === 1) marking.positionHint = _ExsurgeChant.MarkingPositionHint.Below; + } + } + + for (i = 0; i < this.notes[1].epismata.length; i++) { + if (this.notes[1].epismata[i].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[1].epismata[i].positionHint = _ExsurgeChant.MarkingPositionHint.Above; + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Podatus.prototype), 'performLayout', this).call(this, ctxt); + + this.build(ctxt).withPodatus(this.notes[0], this.notes[1]); + + this.finishLayout(ctxt); + } + }]); + + return Podatus; + }(Neume); + + /* + * Porrectus + */ + + + var Porrectus = exports.Porrectus = function (_Neume11) { + _inherits(Porrectus, _Neume11); + + function Porrectus() { + _classCallCheck(this, Porrectus); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Porrectus).apply(this, arguments)); + } + + _createClass(Porrectus, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Porrectus.prototype), 'performLayout', this).call(this, ctxt); + + var first = this.notes[0]; + var second = this.notes[1]; + var third = this.notes[2]; + + var thirdGlyph; + + if (third.liquescent & _Exsurge3.LiquescentType.Small) thirdGlyph = _Exsurge2.GlyphCode.TerminatingAscLiquescent;else if (third.liquescent & _Exsurge3.LiquescentType.Descending) thirdGlyph = _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent;else thirdGlyph = _Exsurge2.GlyphCode.PodatusUpper; + + this.build(ctxt).lineFrom(second).withPorrectusSwash(first, second).noteAt(third, thirdGlyph); + + this.finishLayout(ctxt); + } + }]); + + return Porrectus; + }(Neume); + + /* + * PorrectusFlexus + */ + + + var PorrectusFlexus = exports.PorrectusFlexus = function (_Neume12) { + _inherits(PorrectusFlexus, _Neume12); + + function PorrectusFlexus() { + _classCallCheck(this, PorrectusFlexus); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(PorrectusFlexus).apply(this, arguments)); + } + + _createClass(PorrectusFlexus, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(PorrectusFlexus.prototype), 'performLayout', this).call(this, ctxt); + + var first = this.notes[0]; + var second = this.notes[1]; + var third = this.notes[2]; + var fourth = this.notes[3]; + + var thirdGlyph = _Exsurge2.GlyphCode.PunctumQuadratum, + fourthGlyph; + + if (fourth.liquescent & _Exsurge3.LiquescentType.Small) { + thirdGlyph = _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent; + fourthGlyph = _Exsurge2.GlyphCode.TerminatingDesLiquescent; + } else if (fourth.liquescent & _Exsurge3.LiquescentType.Ascending) fourthGlyph = _Exsurge2.GlyphCode.PunctumQuadratumAscLiquescent;else if (fourth.liquescent & _Exsurge3.LiquescentType.Descending) fourthGlyph = _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent;else fourthGlyph = _Exsurge2.GlyphCode.PunctumQuadratum; + + this.build(ctxt).lineFrom(second).withPorrectusSwash(first, second).noteAt(third, thirdGlyph).noteAt(fourth, fourthGlyph); + + this.finishLayout(ctxt); + } + }]); + + return PorrectusFlexus; + }(Neume); + + // this is some type of pseudo nume right? there is no such thing as a neume + // of puncta inclinata, but this will be part of other composite neumes. + + + var PunctaInclinata = exports.PunctaInclinata = function (_Neume13) { + _inherits(PunctaInclinata, _Neume13); + + function PunctaInclinata() { + _classCallCheck(this, PunctaInclinata); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(PunctaInclinata).apply(this, arguments)); + } + + _createClass(PunctaInclinata, [{ + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(PunctaInclinata.prototype), 'performLayout', this).call(this, ctxt); + + this.build(ctxt).withInclinati(this.notes); + + this.finishLayout(ctxt); + } + }]); + + return PunctaInclinata; + }(Neume); + + /* + * Punctum + */ + + + var Punctum = exports.Punctum = function (_Neume14) { + _inherits(Punctum, _Neume14); + + function Punctum() { + _classCallCheck(this, Punctum); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Punctum).apply(this, arguments)); + } + + _createClass(Punctum, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var marking, i; + var positionHint = _ExsurgeChant.MarkingPositionHint.Above; + + // logic here is this: if first episema is default position, place it above. + // then place the second one (if there is one) opposite of the first. + for (i = 0; i < this.notes[0].epismata.length; i++) { + if (this.notes[0].epismata[i].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[0].epismata[i].positionHint = positionHint;else positionHint = this.notes[0].epismata[i].positionHint; + + // now place the next one in the opposite position + positionHint = positionHint === _ExsurgeChant.MarkingPositionHint.Above ? _ExsurgeChant.MarkingPositionHint.Below : _ExsurgeChant.MarkingPositionHint.Above; + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Punctum.prototype), 'performLayout', this).call(this, ctxt); + + var note = this.notes[0]; + var glyph = _Exsurge2.GlyphCode.PunctumQuadratum; + + // determine the glyph to use + if (note.liquescent !== _Exsurge3.LiquescentType.None) { + if (note.shape === _Exsurge3.NoteShape.Inclinatum) glyph = _Exsurge2.GlyphCode.PunctumInclinatumLiquescent;else if (note.shape === _Exsurge3.NoteShape.Oriscus) glyph = _Exsurge2.GlyphCode.OriscusLiquescent;else if (note.liquescent & _Exsurge3.LiquescentType.Ascending) glyph = _Exsurge2.GlyphCode.PunctumQuadratumAscLiquescent;else if (note.liquescent & _Exsurge3.LiquescentType.Descending) glyph = _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent; + } else { + + if (note.shapeModifiers & _Exsurge3.NoteShapeModifiers.Cavum) glyph = _Exsurge2.GlyphCode.PunctumCavum;else if (note.shape === _Exsurge3.NoteShape.Inclinatum) glyph = _Exsurge2.GlyphCode.PunctumInclinatum;else if (note.shape === _Exsurge3.NoteShape.Quilisma) glyph = _Exsurge2.GlyphCode.Quilisma;else glyph = _Exsurge2.GlyphCode.PunctumQuadratum; + } + + this.build(ctxt).noteAt(note, glyph); + + this.finishLayout(ctxt); + } + }]); + + return Punctum; + }(Neume); + + /* + * Salicus + */ + + + var Salicus = exports.Salicus = function (_Neume15) { + _inherits(Salicus, _Neume15); + + function Salicus() { + _classCallCheck(this, Salicus); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Salicus).apply(this, arguments)); + } + + _createClass(Salicus, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var marking, i, j; + + // by default place episema below + // fixme: is this correct? + for (i = 0; i < this.notes.length; i++) { + for (j = 0; j < this.notes[i].epismata.length; j++) { + if (this.notes[i].epismata[j].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[i].epismata[j].positionHint = _ExsurgeChant.MarkingPositionHint.Below; + } + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Salicus.prototype), 'performLayout', this).call(this, ctxt); + + var first = this.notes[0]; + var second = this.notes[1]; + var third = this.notes[2]; + + var builder = this.build(ctxt).noteAt(first, _Exsurge2.GlyphCode.PunctumQuadratum); + + // if the next note doesn't require a stem connector, then add a tad bit + // of spacing here + if (!(second.shapeModifiers & _Exsurge3.NoteShapeModifiers.Stemmed)) builder.advanceBy(ctxt.intraNeumeSpacing); + + // second note is always an oriscus, which may or may not be stemmed + // to the first + builder.noteAt(second, _Exsurge2.GlyphCode.OriscusAsc); + + // third note can be a punctum quadratum or various liquescent forms + if (third.liquescent & _Exsurge3.LiquescentType.Small) builder.noteAt(third, _Exsurge2.GlyphCode.TerminatingAscLiquescent);else if (third.liquescent === _Exsurge3.LiquescentType.Ascending) builder.noteAt(third, _Exsurge2.GlyphCode.PunctumQuadratumAscLiquescent);else if (third.liquescent === _Exsurge3.LiquescentType.Descending) builder.noteAt(third, _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent);else builder.virgaAt(third); + + this.finishLayout(ctxt); + } + }]); + + return Salicus; + }(Neume); + + /* + * Salicus Flexus + */ + + + var SalicusFlexus = exports.SalicusFlexus = function (_Neume16) { + _inherits(SalicusFlexus, _Neume16); + + function SalicusFlexus() { + _classCallCheck(this, SalicusFlexus); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(SalicusFlexus).apply(this, arguments)); + } + + _createClass(SalicusFlexus, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var marking, i, j; + + // by default place episema below + // fixme: is this correct? + for (i = 0; i < this.notes.length; i++) { + for (j = 0; j < this.notes[i].epismata.length; j++) { + if (this.notes[i].epismata[j].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[i].epismata[j].positionHint = _ExsurgeChant.MarkingPositionHint.Below; + } + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(SalicusFlexus.prototype), 'performLayout', this).call(this, ctxt); + + var first = this.notes[0]; + var second = this.notes[1]; + var third = this.notes[2]; + var fourth = this.notes[3]; + + var builder = this.build(ctxt).noteAt(first, _Exsurge2.GlyphCode.PunctumQuadratum); + + // if the next note doesn't require a stem connector, then add a tad bit + // of spacing here + if (!(second.shapeModifiers & _Exsurge3.NoteShapeModifiers.Stemmed)) builder.advanceBy(ctxt.intraNeumeSpacing); + + // second note is always an oriscus, which may or may not be stemmed + // to the first + builder.noteAt(second, _Exsurge2.GlyphCode.OriscusAsc); + + // third note can be a punctum quadratum or various liquescent forms, + // ...based on note four though! + if (fourth.liquescent & _Exsurge3.LiquescentType.Small) builder.noteAt(third, _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent);else builder.noteAt(third, _Exsurge2.GlyphCode.PunctumQuadratum); + + // finally, do the fourth note + if (fourth.liquescent & _Exsurge3.LiquescentType.Small) builder.noteAt(fourth, _Exsurge2.GlyphCode.TerminatingDesLiquescent);else if (fourth.liquescent & _Exsurge3.LiquescentType.Ascending) builder.noteAt(fourth, _Exsurge2.GlyphCode.PunctumQuadratumAscLiquescent);else if (fourth.liquescent & _Exsurge3.LiquescentType.Descending) builder.noteAt(fourth, _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent);else builder.noteAt(fourth, _Exsurge2.GlyphCode.PunctumQuadratum); + + this.finishLayout(ctxt); + } + }]); + + return SalicusFlexus; + }(Neume); + + /* + * Scandicus + */ + + + var Scandicus = exports.Scandicus = function (_Neume17) { + _inherits(Scandicus, _Neume17); + + function Scandicus() { + _classCallCheck(this, Scandicus); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Scandicus).apply(this, arguments)); + } + + _createClass(Scandicus, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var marking, i; + + // by default place first note epismata below + for (i = 0; i < this.notes[0].epismata.length; i++) { + if (this.notes[0].epismata[i].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[0].epismata[i].positionHint = _ExsurgeChant.MarkingPositionHint.Below; + }var positionHint = this.notes[2].shape === _Exsurge3.NoteShape.Virga ? _ExsurgeChant.MarkingPositionHint.Above : _ExsurgeChant.MarkingPositionHint.Below; + for (i = 0; i < this.notes[1].epismata.length; i++) { + if (this.notes[1].epismata[i].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[1].epismata[i].positionHint = positionHint; + } // by default place third note epismata above + for (i = 0; i < this.notes[2].epismata.length; i++) { + if (this.notes[2].epismata[i].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[2].epismata[i].positionHint = _ExsurgeChant.MarkingPositionHint.Above; + } + } + + // if the third note shape is a virga, then the scadicus is rendered + // as a podatus followed by a virga. Otherwise, it's rendered as a + // punctum followed by a podatus... + + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Scandicus.prototype), 'performLayout', this).call(this, ctxt); + + var first = this.notes[0]; + var second = this.notes[1]; + var third = this.notes[2]; + + if (third.shape === _Exsurge3.NoteShape.Virga) { + this.build(ctxt).withPodatus(first, second).virgaAt(third); + } else { + this.build(ctxt).noteAt(first, _Exsurge2.GlyphCode.PunctumQuadratum).withPodatus(second, third); + } + + this.finishLayout(ctxt); + } + }]); + + return Scandicus; + }(Neume); + + /* + * Scandicus Flexus + */ + + + var ScandicusFlexus = exports.ScandicusFlexus = function (_Neume18) { + _inherits(ScandicusFlexus, _Neume18); + + function ScandicusFlexus() { + _classCallCheck(this, ScandicusFlexus); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(ScandicusFlexus).apply(this, arguments)); + } + + _createClass(ScandicusFlexus, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var marking, i; + + // by default place first note epismata below + for (i = 0; i < this.notes[0].epismata.length; i++) { + if (this.notes[0].epismata[i].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[0].epismata[i].positionHint = _ExsurgeChant.MarkingPositionHint.Below; + }var positionHint = this.notes[2].shape === _Exsurge3.NoteShape.Virga ? _ExsurgeChant.MarkingPositionHint.Above : _ExsurgeChant.MarkingPositionHint.Below; + for (i = 0; i < this.notes[1].epismata.length; i++) { + if (this.notes[1].epismata[i].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[1].epismata[i].positionHint = positionHint; + } // by default place third note epismata above + for (i = 0; i < this.notes[2].epismata.length; i++) { + if (this.notes[2].epismata[i].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[2].epismata[i].positionHint = _ExsurgeChant.MarkingPositionHint.Above; + } // by default place fourth note epismata above + for (i = 0; i < this.notes[3].epismata.length; i++) { + if (this.notes[3].epismata[i].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[3].epismata[i].positionHint = _ExsurgeChant.MarkingPositionHint.Above; + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(ScandicusFlexus.prototype), 'performLayout', this).call(this, ctxt); + + var first = this.notes[0]; + var second = this.notes[1]; + var third = this.notes[2]; + var fourth = this.notes[3]; + + if (third.shape === _Exsurge3.NoteShape.Virga) { + this.build(ctxt).withPodatus(first, second).advanceBy(ctxt.intraNeumeSpacing).withClivis(third, fourth); + } else { + var fourthGlyph = _Exsurge2.GlyphCode.PunctumQuadratum; + + if (fourth.liquescent & _Exsurge3.LiquescentType.Ascending) fourthGlyph = _Exsurge2.GlyphCode.PunctumQuadratumAscLiquescent;else if (fourth.liquescent & _Exsurge3.LiquescentType.Descending) fourthGlyph = _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent; + + this.build(ctxt).noteAt(first, _Exsurge2.GlyphCode.PunctumQuadratum).withPodatus(second, third).advanceBy(ctxt.intraNeumeSpacing).noteAt(fourth, fourthGlyph); + } + + this.finishLayout(ctxt); + } + }]); + + return ScandicusFlexus; + }(Neume); + + /* + * Torculus + */ + + + var Torculus = exports.Torculus = function (_Neume19) { + _inherits(Torculus, _Neume19); + + function Torculus() { + _classCallCheck(this, Torculus); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Torculus).apply(this, arguments)); + } + + _createClass(Torculus, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var marking, i; + var hasMiddleEpisema = false; + + // first do the middle note to see if we should try to move + // epismata on the other two lower notes + for (i = 0; i < this.notes[1].epismata.length; i++) { + marking = this.notes[1].epismata[i]; + + if (marking.positionHint === _ExsurgeChant.MarkingPositionHint.Default) { + marking.positionHint = _ExsurgeChant.MarkingPositionHint.Above; + hasMiddleEpisema = true; + } + } + + // 1. episema on lower notes should be below, upper note above + // 2. morae: fixme: implement + for (i = 0; i < this.notes[0].epismata.length; i++) { + marking = this.notes[0].epismata[i]; + + if (marking.positionHint === _ExsurgeChant.MarkingPositionHint.Default) marking.positionHint = hasMiddleEpisema ? _ExsurgeChant.MarkingPositionHint.Above : _ExsurgeChant.MarkingPositionHint.Below; + } + + for (i = 0; i < this.notes[2].epismata.length; i++) { + marking = this.notes[2].epismata[i]; + + if (marking.positionHint === _ExsurgeChant.MarkingPositionHint.Default) marking.positionHint = hasMiddleEpisema ? _ExsurgeChant.MarkingPositionHint.Above : _ExsurgeChant.MarkingPositionHint.Below; + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Torculus.prototype), 'performLayout', this).call(this, ctxt); + + var note1 = this.notes[0]; + var note2 = this.notes[1]; + var note3 = this.notes[2]; + + var glyph1, glyph3; + + if (note1.liquescent === _Exsurge3.LiquescentType.InitioDebilis) glyph1 = _Exsurge2.GlyphCode.TerminatingDesLiquescent;else if (note1.shape === _Exsurge3.NoteShape.Quilisma) glyph1 = _Exsurge2.GlyphCode.Quilisma;else glyph1 = _Exsurge2.GlyphCode.PunctumQuadratum; + + if (note3.liquescent & _Exsurge3.LiquescentType.Small) glyph3 = _Exsurge2.GlyphCode.TerminatingDesLiquescent;else if (note3.liquescent & _Exsurge3.LiquescentType.Ascending) glyph3 = _Exsurge2.GlyphCode.PunctumQuadratumAscLiquescent;else if (note3.liquescent & _Exsurge3.LiquescentType.Descending) glyph3 = _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent;else glyph3 = _Exsurge2.GlyphCode.PunctumQuadratum; + + this.build(ctxt).noteAt(note1, glyph1).noteAt(note2, _Exsurge2.GlyphCode.PunctumQuadratum).noteAt(note3, glyph3); + + this.finishLayout(ctxt); + } + }]); + + return Torculus; + }(Neume); + + /* + * TorculusResupinus + */ + + + var TorculusResupinus = exports.TorculusResupinus = function (_Neume20) { + _inherits(TorculusResupinus, _Neume20); + + function TorculusResupinus() { + _classCallCheck(this, TorculusResupinus); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(TorculusResupinus).apply(this, arguments)); + } + + _createClass(TorculusResupinus, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var marking, i; + var hasMiddleEpisema = false; + + // first do the middle note to see if we should try to move + // epismata on the other two lower notes + for (i = 0; i < this.notes[1].epismata.length; i++) { + marking = this.notes[1].epismata[i]; + + if (marking.positionHint === _ExsurgeChant.MarkingPositionHint.Default) { + marking.positionHint = _ExsurgeChant.MarkingPositionHint.Above; + hasMiddleEpisema = true; + } + } + + // 1. episema on lower notes should be below, upper note above + // 2. morae: fixme: implement + for (i = 0; i < this.notes[0].epismata.length; i++) { + marking = this.notes[0].epismata[i]; + + if (marking.positionHint === _ExsurgeChant.MarkingPositionHint.Default) marking.positionHint = hasMiddleEpisema ? _ExsurgeChant.MarkingPositionHint.Above : _ExsurgeChant.MarkingPositionHint.Below; + } + + for (i = 0; i < this.notes[2].epismata.length; i++) { + marking = this.notes[2].epismata[i]; + + if (marking.positionHint === _ExsurgeChant.MarkingPositionHint.Default) marking.positionHint = hasMiddleEpisema ? _ExsurgeChant.MarkingPositionHint.Above : _ExsurgeChant.MarkingPositionHint.Below; + } + + for (i = 0; i < this.notes[3].epismata.length; i++) { + marking = this.notes[3].epismata[i]; + + if (marking.positionHint === _ExsurgeChant.MarkingPositionHint.Default) marking.positionHint = _ExsurgeChant.MarkingPositionHint.Above; + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(TorculusResupinus.prototype), 'performLayout', this).call(this, ctxt); + + var first = this.notes[0]; + var second = this.notes[1]; + var third = this.notes[2]; + var fourth = this.notes[3]; + + var firstGlyph, fourthGlyph; + + if (first.liquescent === _Exsurge3.LiquescentType.InitioDebilis) { + firstGlyph = _Exsurge2.GlyphCode.TerminatingDesLiquescent; + } else if (first.shape === _Exsurge3.NoteShape.Quilisma) firstGlyph = _Exsurge2.GlyphCode.Quilisma;else firstGlyph = _Exsurge2.GlyphCode.PunctumQuadratum; + + if (fourth.liquescent & _Exsurge3.LiquescentType.Small) fourthGlyph = _Exsurge2.GlyphCode.TerminatingAscLiquescent;else if (third.liquescent & _Exsurge3.LiquescentType.Descending) fourthGlyph = _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent;else fourthGlyph = _Exsurge2.GlyphCode.PodatusUpper; + + this.build(ctxt).noteAt(first, firstGlyph).withPorrectusSwash(second, third).noteAt(fourth, fourthGlyph); + + this.finishLayout(ctxt); + } + }]); + + return TorculusResupinus; + }(Neume); + + /* + * TorculusResupinusFlexus + */ + + + var TorculusResupinusFlexus = exports.TorculusResupinusFlexus = function (_Neume21) { + _inherits(TorculusResupinusFlexus, _Neume21); + + function TorculusResupinusFlexus() { + _classCallCheck(this, TorculusResupinusFlexus); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(TorculusResupinusFlexus).apply(this, arguments)); + } + + _createClass(TorculusResupinusFlexus, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var marking, i; + var hasMiddleEpisema = false; + + // first do the middle note to see if we should try to move + // epismata on the other two lower notes + for (i = 0; i < this.notes[1].epismata.length; i++) { + marking = this.notes[1].epismata[i]; + + if (marking.positionHint === _ExsurgeChant.MarkingPositionHint.Default) { + marking.positionHint = _ExsurgeChant.MarkingPositionHint.Above; + hasMiddleEpisema = true; + } + } + + // 1. episema on lower notes should be below, upper note above + // 2. morae: fixme: implement + for (i = 0; i < this.notes[0].epismata.length; i++) { + marking = this.notes[0].epismata[i]; + + if (marking.positionHint === _ExsurgeChant.MarkingPositionHint.Default) marking.positionHint = hasMiddleEpisema ? _ExsurgeChant.MarkingPositionHint.Above : _ExsurgeChant.MarkingPositionHint.Below; + } + + for (i = 0; i < this.notes[2].epismata.length; i++) { + marking = this.notes[2].epismata[i]; + + if (marking.positionHint === _ExsurgeChant.MarkingPositionHint.Default) marking.positionHint = hasMiddleEpisema ? _ExsurgeChant.MarkingPositionHint.Above : _ExsurgeChant.MarkingPositionHint.Below; + } + + for (i = 0; i < this.notes[3].epismata.length; i++) { + marking = this.notes[3].epismata[i]; + + if (marking.positionHint === _ExsurgeChant.MarkingPositionHint.Default) marking.positionHint = _ExsurgeChant.MarkingPositionHint.Above; + } + + for (i = 0; i < this.notes[4].epismata.length; i++) { + marking = this.notes[4].epismata[i]; + + if (marking.positionHint === _ExsurgeChant.MarkingPositionHint.Default) marking.positionHint = _ExsurgeChant.MarkingPositionHint.Above; + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(TorculusResupinusFlexus.prototype), 'performLayout', this).call(this, ctxt); + + var first = this.notes[0]; + var second = this.notes[1]; + var third = this.notes[2]; + var fourth = this.notes[3]; + var fifth = this.notes[4]; + + var firstGlyph, + fourthGlyph = _Exsurge2.GlyphCode.PunctumQuadratum, + fifthGlyph; + + if (first.liquescent === _Exsurge3.LiquescentType.InitioDebilis) { + firstGlyph = _Exsurge2.GlyphCode.TerminatingDesLiquescent; + } else if (first.shape === _Exsurge3.NoteShape.Quilisma) firstGlyph = _Exsurge2.GlyphCode.Quilisma;else firstGlyph = _Exsurge2.GlyphCode.PunctumQuadratum; + + if (fifth.liquescent & _Exsurge3.LiquescentType.Small) { + fourthGlyph = _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent; + fifthGlyph = _Exsurge2.GlyphCode.TerminatingDesLiquescent; + } else if (fifth.liquescent & _Exsurge3.LiquescentType.Ascending) fifthGlyph = _Exsurge2.GlyphCode.PunctumQuadratumAscLiquescent;else if (fifth.liquescent & _Exsurge3.LiquescentType.Descending) fifthGlyph = _Exsurge2.GlyphCode.PunctumQuadratumDesLiquescent;else fifthGlyph = _Exsurge2.GlyphCode.PunctumQuadratum; + + this.build(ctxt).noteAt(first, firstGlyph).withPorrectusSwash(second, third).noteAt(fourth, fourthGlyph).noteAt(fifth, fifthGlyph); + + this.finishLayout(ctxt); + } + }]); + + return TorculusResupinusFlexus; + }(Neume); + + /* + * Tristropha + * + * For simplicity in implementation, Tristropha's have three notes in the object + * structure. These technically must be the same pitch though (like the + * Distropha and Bivirga). + */ + + + var Tristropha = exports.Tristropha = function (_Neume22) { + _inherits(Tristropha, _Neume22); + + function Tristropha() { + _classCallCheck(this, Tristropha); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Tristropha).apply(this, arguments)); + } + + _createClass(Tristropha, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var marking, i, j; + + for (i = 0; i < this.notes.length; i++) { + var positionHint = _ExsurgeChant.MarkingPositionHint.Above; + + // logic here is this: if first episema is default position, place it above. + // then place the second one (if there is one) opposite of the first. + for (j = 0; j < this.notes[i].epismata.length; j++) { + if (this.notes[i].epismata[j].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[i].epismata[j].positionHint = positionHint;else positionHint = this.notes[i].epismata[j].positionHint; + + // now place the next one in the opposite position + positionHint = positionHint === _ExsurgeChant.MarkingPositionHint.Above ? _ExsurgeChant.MarkingPositionHint.Below : _ExsurgeChant.MarkingPositionHint.Above; + } + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Tristropha.prototype), 'performLayout', this).call(this, ctxt); + + this.build(ctxt).noteAt(this.notes[0], Apostropha.getNoteGlyphCode(this.notes[0])).advanceBy(ctxt.intraNeumeSpacing).noteAt(this.notes[1], Apostropha.getNoteGlyphCode(this.notes[1])).advanceBy(ctxt.intraNeumeSpacing).noteAt(this.notes[2], Apostropha.getNoteGlyphCode(this.notes[2])); + + this.finishLayout(ctxt); + } + }]); + + return Tristropha; + }(Neume); + + /* + * Virga + */ + + + var Virga = exports.Virga = function (_Neume23) { + _inherits(Virga, _Neume23); + + function Virga() { + _classCallCheck(this, Virga); + + return _possibleConstructorReturn(this, Object.getPrototypeOf(Virga).apply(this, arguments)); + } + + _createClass(Virga, [{ + key: 'positionMarkings', + value: function positionMarkings() { + var positionHint = _ExsurgeChant.MarkingPositionHint.Above; + + // logic here is this: if first episema is default position, place it above. + // then place the second one (if there is one) opposite of the first. + for (var i = 0; i < this.notes[0].epismata.length; i++) { + if (this.notes[0].epismata[i].positionHint === _ExsurgeChant.MarkingPositionHint.Default) this.notes[0].epismata[i].positionHint = positionHint;else positionHint = this.notes[0].epismata[i].positionHint; + + // now place the next one in the opposite position + positionHint = positionHint === _ExsurgeChant.MarkingPositionHint.Above ? _ExsurgeChant.MarkingPositionHint.Below : _ExsurgeChant.MarkingPositionHint.Above; + } + } + }, { + key: 'performLayout', + value: function performLayout(ctxt) { + _get(Object.getPrototypeOf(Virga.prototype), 'performLayout', this).call(this, ctxt); + + this.build(ctxt).virgaAt(this.notes[0]); + + this.finishLayout(ctxt); + } + }]); + + return Virga; + }(Neume); + +/***/ } +/******/ ]) +}); +; +//# sourceMappingURL=exsurge.js.map \ No newline at end of file diff --git a/web/cgi-bin/horas/js/exsurge.min.js b/web/cgi-bin/horas/js/exsurge.min.js new file mode 100644 index 00000000000..96072f13474 --- /dev/null +++ b/web/cgi-bin/horas/js/exsurge.min.js @@ -0,0 +1,8 @@ +!function(t,e){"object"==typeof exports&&"object"==typeof module?module.exports=e():"function"==typeof define&&define.amd?define("exsurge",[],e):"object"==typeof exports?exports.exsurge=e():t.exsurge=e()}(this,function(){return function(t){function e(n){if(i[n])return i[n].exports;var s=i[n]={exports:{},id:n,loaded:!1};return t[n].call(s.exports,s,s.exports,e),s.loaded=!0,s.exports}var i={};return e.m=t,e.c=i,e.p="",e(0)}([function(t,e,i){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var n=i(1);Object.keys(n).forEach(function(t){"default"!==t&&"__esModule"!==t&&Object.defineProperty(e,t,{enumerable:!0,get:function(){return n[t]}})});var s=i(2);Object.keys(s).forEach(function(t){"default"!==t&&"__esModule"!==t&&Object.defineProperty(e,t,{enumerable:!0,get:function(){return s[t]}})});var o=i(3);Object.keys(o).forEach(function(t){"default"!==t&&"__esModule"!==t&&Object.defineProperty(e,t,{enumerable:!0,get:function(){return o[t]}})});var r=i(4);Object.keys(r).forEach(function(t){"default"!==t&&"__esModule"!==t&&Object.defineProperty(e,t,{enumerable:!0,get:function(){return r[t]}})});var a=i(8);Object.keys(a).forEach(function(t){"default"!==t&&"__esModule"!==t&&Object.defineProperty(e,t,{enumerable:!0,get:function(){return a[t]}})});var u=i(9);Object.keys(u).forEach(function(t){"default"!==t&&"__esModule"!==t&&Object.defineProperty(e,t,{enumerable:!0,get:function(){return u[t]}})});var h=i(10);Object.keys(h).forEach(function(t){"default"!==t&&"__esModule"!==t&&Object.defineProperty(e,t,{enumerable:!0,get:function(){return h[t]}})});var l=i(11);Object.keys(l).forEach(function(t){"default"!==t&&"__esModule"!==t&&Object.defineProperty(e,t,{enumerable:!0,get:function(){return l[t]}})});var c=i(13);Object.keys(c).forEach(function(t){"default"!==t&&"__esModule"!==t&&Object.defineProperty(e,t,{enumerable:!0,get:function(){return c[t]}})});var f=i(12);Object.keys(f).forEach(function(t){"default"!==t&&"__esModule"!==t&&Object.defineProperty(e,t,{enumerable:!0,get:function(){return f[t]}})});var p=i(14);Object.keys(p).forEach(function(t){"default"!==t&&"__esModule"!==t&&Object.defineProperty(e,t,{enumerable:!0,get:function(){return p[t]}})});var d=i(7);Object.keys(d).forEach(function(t){"default"!==t&&"__esModule"!==t&&Object.defineProperty(e,t,{enumerable:!0,get:function(){return d[t]}})})},function(t,e){"use strict";function i(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function n(t){return t}function s(t){return d.ToDeviceIndependent(t,d.Centimeters)}function o(t){return d.ToDeviceIndependent(t,d.Millimeters)}function r(t){return d.ToDeviceIndependent(t,d.Inches)}function a(t){return d.FromDeviceIndependent(t,d.Centimeters)}function u(t){return d.FromDeviceIndependent(t,d.Millimeters)}function h(t){return d.FromDeviceIndependent(t,d.Inches)}function l(){function t(){return Math.floor(65536*(1+Math.random())).toString(16).substring(1)}return t()+t()}function c(t){return Object.entries(t).map(function(t){var e=f(t,2),i=e[0],n=e[1];return i&&n&&"class"!==i?i+": "+n+";":""}).join("")}Object.defineProperty(e,"__esModule",{value:!0});var f=function(){function t(t,e){var i=[],n=!0,s=!1,o=void 0;try{for(var r,a=t[Symbol.iterator]();!(n=(r=a.next()).done)&&(i.push(r.value),!e||i.length!==e);n=!0);}catch(t){s=!0,o=t}finally{try{!n&&a.return&&a.return()}finally{if(s)throw o}}return i}return function(e,i){if(Array.isArray(e))return e;if(Symbol.iterator in Object(e))return t(e,i);throw new TypeError("Invalid attempt to destructure non-iterable instance")}}(),p=function(){function t(t,e){for(var i=0;i=this.x&&t.x<=this.x+this.width&&t.y>=this.y&&t.y<=this.y+this.height:this.x<=t.x&&this.x+this.width>=t.x+t.width&&this.y<=t.y&&this.y+this.height>=t.y+t.height}},{key:"union",value:function(t){var e=Math.max(this.x+this.width,t.x+t.width),i=Math.max(this.y+this.height,t.y+t.height);this.x=Math.min(this.x,t.x),this.y=Math.min(this.y,t.y),this.width=e-this.x,this.height=i-this.y}}]),t}(),e.Margins=function(){function t(e,n,s,o){i(this,t),this.left="undefined"!=typeof e?e:0,this.top="undefined"!=typeof n?n:0,this.right="undefined"!=typeof s?s:0,this.bottom="undefined"!=typeof o?o:0}return p(t,[{key:"clone",value:function(){return new t(this.left,this.top,this.right,this.bottom)}},{key:"equals",value:function(t){return this.left===t.left&&this.top===t.top&&this.right===t.right&&this.bottom===t.bottom}}]),t}(),e.Size=function(){function t(e,n){i(this,t),this.width="undefined"!=typeof e?e:0,this.height="undefined"!=typeof n?n:0}return p(t,[{key:"clone",value:function(){return new t(this.width,this.height)}},{key:"equals",value:function(t){return this.width===t.width&&this.height===t.height}}]),t}(),e.Step={Do:0,Du:1,Re:2,Me:3,Mi:4,Fa:5,Fu:6,So:7,La:9,Te:10,Ti:11}),v=[0,0,1,1,2,3,3,4,4,5,6,6],m=[y.Do,y.Re,y.Mi,y.Fa,y.So,y.La,y.Ti];e.Pitch=function(){function t(e,n){i(this,t),"undefined"==typeof n&&(n=Math.floor(e/12),e%=12),this.step=e,this.octave=n}return p(t,[{key:"toInt",value:function(){return 12*this.octave+this.step}},{key:"transpose",value:function(e){return new t(this.toInt()+e)}},{key:"isHigherThan",value:function(t){return this.toInt()>t.toInt()}},{key:"isLowerThan",value:function(t){return this.toInt()",this.centerNeume=!1}return o(t,[{key:"syllabify",value:function(t){var e=[];if("undefined"==typeof t||""===t)return e;for(var i=t.split(/[\s]+/),n=0,s=i.length;n0&&(s[s.length-1]+=t.substr(u)),s}},{key:"findVowelSegment",value:function(t,e){var i=this.regexVowel.exec(t.slice(e));return i?(i[1]&&(i.index+=i[1].length),{found:!0,startIndex:e+i.index,length:i[2].length}):{found:!1,startIndex:-1,length:-1}}}]),e}(r),h=e.Spanish=function(t){function e(){s(this,e);var t=i(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,"Spanish"));return t.vowels=["a","e","i","o","u","y","á","é","í","ó","ú","ü"],t.weakVowels=["i","u","ü","y"],t.strongVowels=["a","e","o","á","é","í","ó","ú"],t.diphthongs=["ai","ei","oi","ui","ia","ie","io","iu","au","eu","ou","ua","ue","uo","ái","éi","ói","úi","iá","ié","ió","iú","áu","éu","óu","uá","ué","uó","üe","üi"],t.uDiphthongExceptions=["gue","gui","qua","que","qui","quo"],t}return n(e,t),o(e,[{key:"isVowel",value:function(t){for(var e=0,i=this.vowels.length;e0?e[e.length-1]+=t.substr(o):0===e.length&&e.push(this.createSyllable(t)),e}},{key:"findVowelSegment",value:function(t,e){var i,n,s,o=t.toLowerCase();for(i=0,n=this.diphthongs.length;i=0){if("u"===r[0]&&s>0)for(var a=t.substr(s-1,3).toLowerCase(),u=0,h=this.uDiphthongExceptions.length;i=0)return{found:!0,startIndex:s,length:1};return{found:!1,startIndex:-1,length:-1}}}]),e}(r);e.language={english:new a,latin:new u,spanish:new h}},function(t,e){"use strict";Object.defineProperty(e,"__esModule",{value:!0});e.Glyphs={None:{paths:[{type:"positive",data:""}],bounds:{x:0,y:0,width:0,height:0},origin:{x:0,y:0},align:"left"},AcuteAccent:{paths:[{type:"positive",data:"M4 0C-.614.52-.614.52-.803-3.182l60.768-108.422c4.52-7.182 10.543-13.67 18.075-13.67 5.27 0 14.31 1.264 23.346 7.793 7.53 5.223 8.803 11.752 8.803 16.975 0 3.917-.52 11.1-8.05 17.628L4 0z"}],bounds:{x:0,y:0,width:0,height:125.794},origin:{x:.803,y:125.274},align:"left"},GraveAccent:{paths:[{type:"positive",data:"M105.386.26C110 .78 110 .78 110.189-2.922l-60.768-108.422c-4.52-7.182-10.543-13.67-18.075-13.67-5.27 0-14.31 1.264-23.346 7.793-7.53 5.223-8.803 11.752-8.803 16.975 0 3.917.52 11.1 8.05 17.628L105.386.26z"}],bounds:{x:0,y:0,width:0,height:125.794},origin:{x:0,y:125.274},align:"left"},Circle:{paths:[{type:"positive",data:"M0 -50A50 50 0 0 0 100 -50 50 50 0 0 0 0 -50M10 -50A40 40 0 0 1 90 -50 40 40 0 0 1 10 -50"}],bounds:{x:0,y:0,width:100,height:100},origin:{x:-50,y:100}},Semicircle:{paths:[{type:"positive",data:"M0 -50A50 50 0 0 0 100 -50 5 5 0 0 0 90 -50 40 40 0 0 1 10 -50 5 5 0 0 0 0 -50"}],bounds:{x:0,y:0,width:100,height:55},origin:{x:-50,y:50}},ReversedSemicircle:{paths:[{type:"positive",data:"M0 0A50 50 0 0 1 100 0 5 5 0 0 1 90 0 40 40 0 0 0 10 0 5 5 0 0 1 0 0"}],bounds:{x:0,y:0,width:100,height:55},origin:{x:-50,y:50}},Stropha:{paths:[{type:"positive",data:"M1.22-73.438c4.165 13.02 12.238 27.084 24.217 42.188L49.657 0 34.812 27.344C18.666 55.47-.084 72.396-21.438 78.124c4.687-3.645 7.03-8.593 7.03-14.843 0-8.853-4.947-20.572-14.843-35.155L-48 0 1.22-73.438z"}],bounds:{x:0,y:0,width:97.657,height:151.562},origin:{x:48,y:73.438},align:"left"},BeginningAscLiquescent:{paths:[{type:"positive",data:"M-50 43.688V-61c4.167 7.292 12.76 10.938 25.78 10.938 9.376 0 20.053-1.563 32.032-4.688C31.773-60.48 45.833-71.677 50-88.344v117.97C43.75 42.645 32.812 51.5 17.187 56.186-.52 61.398-15.886 64-28.906 64-42.97 64-50 57.23-50 43.687z"}],bounds:{x:0,y:0,width:100,height:152.344},origin:{x:50,y:88.344},align:"left"},BeginningDesLiquescent:{paths:[{type:"positive",data:"M-50-56.03c0-13.022 7.03-19.532 21.094-19.532 13.02 0 28.385 2.604 46.093 7.812C32.813-63.583 43.75-54.73 50-41.187V76C45.833 59.854 31.77 48.656 7.812 42.406c-11.98-3.125-22.656-4.687-32.03-4.687-13.022 0-21.615 3.905-25.782 11.718v-105.47z"}],bounds:{x:0,y:0,width:100,height:151.562},origin:{x:50,y:75.562},align:"left"},CustosDescLong:{paths:[{type:"positive",data:"M39.063 273.472c5.73.52 7.29-6.25 4.687-20.312V-65.59c-13.542 2.083-24.22 5.468-32.03 10.156C3.905-50.226 0-43.714 0-35.904V71.91c5.73-5.21 10.677-8.594 14.844-10.157 5.73-1.562 12.24-2.343 19.53-2.343v196.875c0 11.458 1.563 17.187 4.688 17.187"}],bounds:{x:0,y:0,width:46.353,height:339.582},origin:{x:0,y:65.59},align:"left"},CustosDescShort:{paths:[{type:"positive",data:"M34.375 191.923c0 8.333 1.563 12.24 4.688 11.72 3.125-.522 4.687-7.033 4.687-19.533v-250c-13.542 2.084-24.22 5.47-32.03 10.157C3.905-50.525 0-44.015 0-36.203V71.61c5.73-5.208 10.677-8.593 14.844-10.156 5.73-1.562 12.24-2.344 19.53-2.344v132.813z"}],bounds:{x:0,y:0,width:43.75,height:270.053},origin:{x:0,y:65.89},align:"left"},CustosLong:{paths:[{type:"positive",data:"M39.063-269.562c5.73-.52 7.29 6.25 4.687 20.312V69.5c-13.542-2.083-24.22-5.47-32.03-10.156C3.905 54.134 0 47.624 0 39.812V-68c5.73 5.208 10.677 8.594 14.844 10.156 5.73 1.563 12.24 2.344 19.53 2.344v-196.875c0-11.458 1.563-17.187 4.688-17.187z"}],bounds:{x:0,y:0,width:46.353,height:339.582},origin:{x:0,y:270.082},align:"left"},CustosShort:{paths:[{type:"positive",data:"M34.375-188.125c0-8.333 1.563-12.24 4.688-11.72 3.125.522 4.687 7.033 4.687 19.532v250c-13.542-2.083-24.22-5.468-32.03-10.156C3.905 54.324 0 47.813 0 40V-67.813c5.73 5.21 10.677 8.594 14.844 10.157 5.73 1.562 12.24 2.344 19.53 2.343v-132.812z"}],bounds:{x:0,y:0,width:43.75,height:270.052},origin:{x:0,y:200.365},align:"left"},DoClef:{paths:[{type:"positive",data:"M0 98.406V-97.688C0-118 5.99-134.275 17.97-146.516c11.978-12.24 27.603-18.36 46.874-18.36 10.937 0 19.53 3.126 25.78 9.376s9.376 14.583 9.376 25v107.813l-6.25-5.47c-4.167-3.645-10.287-7.42-18.36-11.327-8.072-3.907-16.796-5.86-26.17-5.86-11.46 0-21.486 4.427-30.08 13.282-8.593 8.854-12.89 19.53-12.89 32.03s4.297 23.308 12.89 32.423c8.594 9.115 18.62 13.672 30.08 13.672 9.374 0 18.098-1.822 26.17-5.468 8.073-3.646 14.193-7.292 18.36-10.938l6.25-6.25V132c0 9.896-3.125 18.1-9.375 24.61-6.25 6.51-14.844 9.765-25.78 9.765-19.272 0-34.897-6.25-46.876-18.75C5.99 135.125 0 118.72 0 98.405z"}],bounds:{x:0,y:0,width:100,height:331.251},origin:{x:0,y:164.876},align:"left"},FaClef:{paths:[{type:"positive",data:"M85.156-32v193.75c0 9.375-1.562 14.323-4.687 14.844-1.564 0-2.605-.52-3.126-1.563-.52-1.04-.782-2.603-.78-4.686V56.28c-8.335-8.332-19.793-12.5-34.376-12.5-17.71 0-31.77 3.907-42.188 11.72V-32c0-18.23 14.193-27.344 42.578-27.344 28.385 0 42.578 9.115 42.578 27.344zM98.438 93V-92.156c0-19.27 5.73-34.896 17.187-46.875 11.458-11.98 26.562-17.97 45.313-17.97 10.937 0 19.14 2.865 24.61 8.594 5.467 5.73 8.202 13.542 8.202 23.437v103.126l-5.47-4.687c-3.645-3.647-9.374-7.293-17.186-10.94-7.813-3.645-15.886-5.467-24.22-5.468-11.978 0-22.004 4.167-30.077 12.5-8.073 8.334-12.11 18.36-12.11 30.08 0 11.717 4.037 22.004 12.11 30.858s18.1 13.28 30.078 13.28c8.333 0 16.406-1.822 24.22-5.468 7.81-3.645 13.54-7.03 17.186-10.156l5.47-5.468V125.81c0 9.896-2.865 17.84-8.594 23.83-5.73 5.988-13.802 8.983-24.22 8.983-18.75 0-33.853-6.12-45.31-18.36-11.46-12.24-17.19-27.994-17.19-47.265z"}],bounds:{x:0,y:0,width:193.752,height:333.595},origin:{x:.001,y:157.001},align:"left"},Flat:{paths:[{type:"positive",data:"M7.813-204.406c4.166 0 6.25 5.208 6.25 15.625L12.5-10.657C33.854 13.302 54.167 25.28 73.438 25.28c9.374 0 14.062-4.686 14.062-14.06 0-6.25-1.042-11.72-3.125-16.407-2.083-4.688-7.03-9.766-14.844-15.235-7.81-5.47-13.02-8.984-15.624-10.547L27.344-45.81V-80.97c17.187 0 33.073 4.82 47.656 14.454C89.583-56.88 96.875-47.376 96.875-38c0 67.708-.26 101.562-.78 101.563-38.543 0-69.532-12.24-92.97-36.72C0-52.322-1.042-123.936 0-188c0-10.937 2.604-16.406 7.813-16.406z"}],bounds:{x:0,y:0,width:97.917,height:267.969},origin:{x:1.042,y:204.406},align:"left"},Mora:{paths:[{type:"positive",data:"M47.478-24c6.957 0 12.793 2.288 17.49 6.883C69.662-12.52 72-6.904 72-.267c0 6.64-2.337 12.352-7.033 17.118C60.27 21.618 54.435 24 47.477 24c-6.26 0-11.748-2.383-16.444-7.15C26.337 12.086 24 6.374 24-.265c0-6.638 2.337-12.255 7.033-16.85C35.73-21.713 41.217-24 47.478-24z"}],bounds:{x:0,y:0,width:48,height:48},origin:{x:-24,y:24},align:"left"},Natural:{paths:[{type:"positive",data:"M7.906-166.563c-2.864 0-5.614.52-8.218 1.563v13.28l.78 56.25.782 78.907v85.157c.52 3.646 2.604 5.73 6.25 6.25l23.438-3.906 23.437-3.907v29.69c0 42.186-.26 63.54-.78 64.06l6.25 2.345c1.04.52 2.082.78 3.124.78 2.603 0 4.947-1.3 7.03-3.905L67.656-71.25c-.52-2.604-2.083-3.906-4.687-3.906-7.814 0-17.19 1.04-28.126 3.125l-19.53 3.124.78-38.28V-165c-2.604-1.042-5.323-1.562-8.188-1.563zM55.938-40v71.875l-41.407 7.03c0-48.436.262-72.655.783-72.655L55.938-40z"}],bounds:{x:0,y:0,width:70.311,height:330.469},origin:{x:.312,y:166.563},align:"left"},Sharp:{paths:[{type:"positive",data:"m41.725,-73.773c-5.421,-0.241-10.878,5.856-6.549,12.357L67.061,-20.473 61.264,-12.5 13.436,-71.199c-5.634,-5.934-16.988,1.032-11.232,9.783L50.756,0.182 2.203,61.416c-6.745,7.984 3.442,17.859 11.232,9.783L61.264,12.5l5.797,7.973-31.885,40.943c-5.578,6.844 5.588,16.005 11.594,9.783L77.568,33.154 108.367,71.199c4.894,6.717 17.343,-1.575 11.232,-9.783L87.715,20.473 93.873,12.5 141.34,71.199c6.725,7.67 17.509,-2.248 11.596,-9.783L104.02,0.182 152.936,-61.416c5.52,-7.02-5.541,-16.309-11.596,-9.783L93.873,-12.5l-6.158,-7.973 31.884766,-40.943c5.407,-7.045-5.505,-15.924-11.232,-9.783L77.568,-33.154 46.77,-71.199c-1.435,-1.708-3.238,-2.494-5.044922,-2.574zM77.568,-8.516 84.09,0.182 77.568,8.516 70.684,0.182Z"}],bounds:{x:0,y:0,width:154.646,height:147.987},origin:{x:0,y:74.098},align:"left"},OriscusAsc:{paths:[{type:"positive",data:"M50 30.25c0 12.5-3.125 21.354-9.375 26.562-3.125 2.605-7.813 3.907-14.063 3.907-3.125 0-5.99-.522-8.593-1.564-2.605-1.04-5.6-2.474-8.986-4.297C5.6 53.035 2.734 51.603.39 50.56c-2.343-1.04-5.338-2.474-8.984-4.296-3.646-1.823-6.77-3.256-9.375-4.297-2.603-1.043-5.468-1.564-8.593-1.564-6.25 0-10.937 1.563-14.062 4.688C-46.875 50.824-50 59.677-50 71.656v-106.25c0-13.02 3.125-21.875 9.375-26.562 3.125-2.604 7.813-3.906 14.063-3.907 3.125 0 5.99.52 8.593 1.563 2.605 1.042 5.73 2.474 9.376 4.297 3.646 1.823 6.51 2.995 8.594 3.516l10.938 5.468c6.25 3.126 11.458 4.69 15.624 4.69 6.25 0 10.938-1.564 14.063-4.69C46.875-55.426 50-64.02 50-76V30.25z"}],bounds:{x:0,y:0,width:100,height:147.656},origin:{x:50,y:76},align:"left"},OriscusDes:{paths:[{type:"positive",data:"M-50 30.844v-106.25c0 11.458 3.125 20.052 9.375 25.78 3.125 3.126 7.813 4.69 14.063 4.688 4.687 0 13.41-3.255 26.17-9.765 12.762-6.51 21.746-9.766 26.954-9.766 6.25 0 10.938 1.303 14.063 3.907C46.875-55.874 50-47.02 50-34V72.25c0-11.98-3.125-20.833-9.375-26.563C37.5 42.563 32.812 41 26.562 41 21.875 41 13.023 44.385 0 51.156c-4.167 2.604-8.594 4.948-13.28 7.032-4.69 2.083-9.116 3.124-13.283 3.124-6.25 0-10.937-1.302-14.062-3.906C-46.875 52.198-50 43.344-50 30.844z"}],bounds:{x:0,y:0,width:100,height:147.656},origin:{x:50,y:75.406},align:"left"},OriscusLiquescent:{paths:[{type:"positive",data:"M 19.055,78.887 C 20.242,78.487 21.532,77.890 22.925,77.097 24.318,76.304 26.700882,74.417 30.074,71.438 33.447,68.458 36.524,64.985 39.303,61.019 42.083,57.052 44.563,51.396 46.743,44.05 48.923,36.704 50.013,28.671 50.013,19.950525 L 50.013,-34.226 C 50.013,-54.464 42.074,-64.584 26.195,-64.584 20.248,-64.584 11.519,-61.410 0.007,-55.064 -11.506,-48.717 -20.235,-45.544 -26.182,-45.544 -34.515,-45.544 -40.568,-48.520 -44.340791,-54.473 -48.114,-60.426 -50.000,-67.369 -50.000,-75.303 L -50.000,30.07 C -50.000,49.909 -42.060754,59.829 -26.182,59.829 -21.023,59.829 -12.39,56.455 -0.284,49.709 11.822,42.963 20.648,39.59 26.195,39.59 29.369,40.777 30.362,44.25 29.17479,50.009 27.988,55.768 26.001,62.020829 23.216,68.767 z"}],bounds:{x:0,y:0,width:100,height:147.656},origin:{x:50,y:75.406},align:"left"},PodatusLower:{paths:[{type:"positive",data:"M-4.688-30.28c22.396 0 34.636-.262 36.72-.782 5.728-1.563 8.593-5.21 8.593-10.938H50v97.656c0 2.604-1.302 4.167-3.906 4.688-5.21.52-21.355.78-48.438.78-23.958 0-38.54-.26-43.75-.78-2.604 0-3.906-1.302-3.906-3.906v-82.032c0-3.646 1.302-5.468 3.906-5.468h2.344c2.604.52 15.625.78 39.063.78z"}],bounds:{x:0,y:0,width:100,height:103.124},origin:{x:50,y:42},align:"left"},PodatusUpper:{paths:[{type:"positive",data:"M-46.094-63.78c13.542 0 24.61 2.473 33.203 7.42C-4.298-51.41 0-43.99 0-34.093V62h-9.375c0-10.938-2.604-19.14-7.812-24.61-5.21-5.468-14.844-8.203-28.907-8.202-18.23 0-33.333 4.166-45.312 12.5v-75.782c0-19.79 15.104-29.687 45.312-29.687z"}],bounds:{x:0,y:0,width:91.406,height:125.781},origin:{x:91.406,y:63.781},align:"right"},Porrectus1:{paths:[{type:"positive",data:"M233.594 162.875c-58.855 0-107.032-6.25-144.53-18.75C34.895 125.895-11.46 99.855-50 66V-52.75C-21.354-24.625 26.302 6.885 92.97 41.78 123.697 57.928 163.54 66 212.5 66c21.354 0 34.635-9.896 39.844-29.688V151.94c0 7.29-6.25 10.937-18.75 10.937z"}],bounds:{x:0,y:0,width:302.344,height:215.627},origin:{x:50,y:52.75},align:"left"},Porrectus2:{paths:[{type:"positive",data:"M309.375 259.375c-50.52 0-110.938-22.396-181.25-67.188C48.437 141.667-10.938 94.272-50 50V-68.75C0-3.125 60.417 52.083 131.25 96.875c58.333 36.98 110.677 58.854 157.03 65.625h7.033c16.145 0 26.822-9.896 32.03-29.688v114.844c0 7.812-5.99 11.72-17.968 11.72z"}],bounds:{x:0,y:0,width:377.343,height:328.126},origin:{x:50,y:68.75},align:"left"},Porrectus3:{paths:[{type:"positive",data:"M309.375 355.78c-48.96-16.666-109.115-55.468-180.47-116.405C79.428 198.23 19.793 134.687-50 48.75V-70C20 40 94.104 103.79 135.25 148.063 190 200 230 230 288.28 258.906c4.168 2.083 8.334 3.125 12.5 3.125 12.5 0 21.355-10.937 26.564-32.81v114.06c0 9.376-3.386 14.063-10.156 14.064-2.084 0-4.688-.522-7.813-1.563z"}],bounds:{x:0,y:0,width:377.344,height:427.345},origin:{x:50,y:70},align:"left"},Porrectus4:{paths:[{type:"positive",data:"M350 453.438c-52.754-22.397-120-77.345-201.74-164.844C90.87 227.656 24.784 147.708-50 48.75V-70C-8.84-1.25 58.406 86.51 151.74 193.28c60.868 69.793 119.13 124.22 174.782 163.282 5.797 3.646 11.014 5.47 15.652 5.47 12.173 0 21.45-11.72 27.826-35.157V441.72c0 9.373-3.19 14.06-9.565 14.06-2.9 0-6.377-.78-10.435-2.342z"}],bounds:{x:0,y:0,width:420,height:525.78},origin:{x:50,y:70},align:"left"},PunctumCavum:{paths:[{type:"positive",data:"M0-60.906c33.333 0 50 9.635 50 28.906v94.53C39.062 51.595 22.396 46.126 0 46.126s-39.063 5.47-50 16.406V-32c0-19.27 16.667-28.906 50-28.906z"},{type:"negative",data:"M.08-42.56c9.585.206 20.126.53 27.954 6.822 4.96 3.9 4.71 10.792 4.574 16.482v51.278C22.09 27.066 7.283 26.072.168 26.01c-7.72.23-21.895.935-32.616 4.674.04-19.197-.083-38.395.064-57.59.567-7.5 7.834-12.33 14.62-13.774 5.818-1.498 11.857-1.86 17.844-1.88z"}],bounds:{x:0,y:0,width:100,height:123.438},origin:{x:50,y:60.906},align:"left"},PunctumQuadratum:{paths:[{type:"positive",data:"M0-60.906c33.333 0 50 9.635 50 28.906v94.53C39.062 51.595 22.396 46.126 0 46.126s-39.063 5.47-50 16.406V-32c0-19.27 16.667-28.906 50-28.906z"}],bounds:{x:0,y:0,width:100,height:123.438},origin:{x:50,y:60.906},align:"left"},PunctumQuadratumLiquescent:{paths:[{type:"positive",data:"M0-36.5436c19.999799999999997 0 30 5.781 30 17.3436v56.717999999999996C23.437199999999997 30.956999999999997 13.4376 27.6756 0 27.6756s-23.4378 3.2819999999999996-30 9.843599999999999V-19.2c0-11.562 10.000200000000001-17.3436 30-17.3436z"}],bounds:{x:0,y:0,width:100,height:123.438},origin:{x:50,y:60.906},align:"left"},PunctumQuadratumAscLiquescent:{paths:[{type:"positive",data:"M-50 43.688V-61c4.167 7.292 12.76 10.938 25.78 10.938 9.376 0 20.053-1.563 32.032-4.688C31.773-60.48 45.833-71.677 50-88.344v117.97C43.75 42.645 32.812 51.5 17.187 56.186-.52 61.398-15.886 64-28.906 64-42.97 64-50 57.23-50 43.687z"}],bounds:{x:0,y:0,width:100,height:152.344},origin:{x:50,y:88.344},align:"left"},PunctumQuadratumDesLiquescent:{paths:[{type:"positive",data:"M-50-56.03c0-13.022 7.03-19.532 21.094-19.532 13.02 0 28.385 2.604 46.093 7.812C32.813-63.583 43.75-54.73 50-41.187V76C45.833 59.854 31.77 48.656 7.812 42.406c-11.98-3.125-22.656-4.687-32.03-4.687-13.022 0-21.615 3.905-25.782 11.718v-105.47z"}],bounds:{x:0,y:0,width:100,height:151.562},origin:{x:50,y:75.562},align:"left"},PunctumInclinatum:{paths:[{type:"positive",data:"M0-75.78L50 0 0 75-50 0 0-75.78z"}],bounds:{x:0,y:0,width:100,height:150.78},origin:{x:50,y:75.78},align:"left"},PunctumInclinatumLiquescent:{paths:[{type:"positive",data:"M 0,-53.164 35,-0.117 0,52.383 -35,-0.117 0,-53.164 z"}],bounds:{x:0,y:0,width:100,height:105.546},origin:{x:50,y:53.164},align:"left"},Quilisma:{paths:[{type:"positive",data:"M-50 34.938V-51c5.73 20.833 13.02 31.25 21.875 31.25 7.813 0 12.5-15.625 14.063-46.875 3.645 12.5 6.9 21.224 9.765 26.172s6.9 7.422 12.11 7.422c5.208 0 9.374-14.324 12.5-42.97 5.73 22.917 10.677 34.375 14.843 34.375 5.73 0 10.677-15.885 14.844-47.656v100c0 17.707-3.125 26.56-9.375 26.56-4.688 0-9.115-5.988-13.28-17.968-2.085 21.875-8.074 32.813-17.97 32.813-7.813 0-16.146-7.292-25-21.875-4.688 20.312-10.677 30.47-17.97 30.47-5.207 0-9.244-2.605-12.108-7.814C-48.568 47.698-50 41.708-50 34.938z"}],bounds:{x:0,y:0,width:100,height:150},origin:{x:50,y:89.282},align:"left"},TerminatingAscLiquescent:{paths:[{type:"positive",data:"M-9.375 40.22c0-11.98-4.948-17.97-14.844-17.97-10.936 0-19.53 3.646-25.78 10.938v-53.126c0-6.77 2.604-12.76 7.813-17.968 5.208-5.21 10.677-8.594 16.406-10.157 2.603-.52 5.207-.78 7.81-.78 3.647 0 7.032.78 10.157 2.343C-2.603-43.896 0-39.73 0-34V73.03h-9.375V40.22z"}],bounds:{x:0,y:0,width:49.999,height:121.873},origin:{x:49.999,y:48.843},align:"right"},TerminatingDesLiquescent:{paths:[{type:"positive",data:"M-9.375-48.156V-80.97H0V26.845c0 5.73-2.604 9.896-7.813 12.5-3.125 1.562-6.51 2.343-10.156 2.343-2.603 0-5.207-.26-7.81-.78-5.73-1.563-11.2-4.95-16.407-10.157C-47.398 25.542-50 19.292-50 12v-52.344c6.25 7.292 14.844 10.938 25.78 10.938 9.897 0 14.845-6.25 14.845-18.75z"}],bounds:{x:0,y:0,width:50,height:122.658},origin:{x:50,y:80.97},align:"right"},VerticalEpisemaAbove:{paths:[{type:"positive",data:"M-8-4c2 3 6 4 8 4s6-1 8-4v-52c-2-3-6-4-8-4s-6 1-8 4z"}],bounds:{x:0,y:0,width:16,height:60},origin:{x:8,y:60},align:"left"},VerticalEpisemaBelow:{paths:[{type:"positive",data:"M-8 56c2 3 6 4 8 4s6-1 8-4v-52c-2-3-6-4-8-4s-6 1-8 4z"}],bounds:{x:0,y:0,width:16,height:60},origin:{x:8,y:0},align:"left"},VirgaLong:{paths:[{type:"positive",data:"M50-38v285.156c0 6.77-2.344 10.937-7.03 12.5-1.564 0-2.605-.78-3.126-2.344-.52-1.562-.782-10.156-.782-25.78V54.186C29.168 45.334 16.146 40.907 0 40.907c-22.917 0-39.583 5.208-50 15.624V-38c0-19.27 16.667-28.906 50-28.906S50-57.27 50-38z"}],bounds:{x:0,y:0,width:100,height:326.562},origin:{x:50,y:66.906},align:"left"},VirgaShort:{paths:[{type:"positive",data:"M50-38v211.72c0 7.29-2.344 11.457-7.03 12.5-1.564 0-2.606-.783-3.126-2.345-.52-1.563-.782-10.156-.782-25.78V54.187C29.167 45.332 16.146 40.906 0 40.906c-22.917 0-39.583 5.21-50 15.625V-38c0-19.27 16.667-28.906 50-28.906S50-57.27 50-38z"}], +bounds:{x:0,y:0,width:100,height:253.126},origin:{x:50,y:66.906},align:"left"},Virgula:{paths:[{type:"positive",data:"M8.178-55.66c0-22.137 12.092-33.2 36.287-33.2 11.835 0 23.53 5.66 35.108 16.98C91.15-60.547 96.94-41.766 96.94-15.534c0 53.515-31.646 87.487-94.937 101.895-2.048-2.06-3.077-5.146-3.077-9.273 0-1.03.247-1.8.76-2.316 42.71-19.027 64.075-41.678 64.075-67.92 0-11.322-2.325-20.326-6.945-27.016-4.62-6.69-9.52-11.052-14.676-13.11-5.147-2.048-11.836-3.85-20.07-5.403C12.81-39.707 8.18-45.37 8.18-55.66z"}],bounds:{x:0,y:0,width:98.014,height:175.221},origin:{x:1.074,y:88.86},align:"left"}}},function(t,e,i){"use strict";function n(t){if(Array.isArray(t)){for(var e=0,i=Array(t.length);e0&&void 0!==arguments[0]?arguments[0]:{},e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:"{}",i="italic"===t["font-style"]?"Italic":"",n="bold"===t["font-weight"]?"Bold":"";return e.replace("{}",""+(i||n?""+n+i:"Regular"))}function u(t,e){var i=arguments.length>2&&void 0!==arguments[2]?arguments[2]:{},n=arguments[3];this.tagName=t,this.startIndex=e,this.properties=i,n&&(this.symbol=n)}Object.defineProperty(e,"__esModule",{value:!0}),e.ChantNotationElement=e.Annotations=e.Annotation=e.TextLeftRight=e.Subtitle=e.Title=e.Supertitle=e.TitleTextElement=e.DropCap=e.TranslationText=e.AboveLinesText=e.ChoralSign=e.Lyric=e.LyricArray=e.LyricType=e.TextElement=e.TextSpan=e.CurlyBraceVisualizer=e.RoundBraceVisualizer=e.GlyphVisualizer=e.LineaVisualizer=e.VirgaLineVisualizer=e.NeumeLineVisualizer=e.DividerLineVisualizer=e.ChantLayoutElement=e.ChantContext=e.TextMeasuringStrategy=e.QuickSvg=e.GlyphCode=e.DefaultTrailingSpace=e.TextTypesByClass=e.TextTypes=e.MarkingPositionHint=void 0;var h=function t(e,i,n){null===e&&(e=Function.prototype);var s=Object.getOwnPropertyDescriptor(e,i);if(void 0===s){var o=Object.getPrototypeOf(e);return null===o?void 0:t(o,i,n)}if("value"in s)return s.value;var r=s.get;if(void 0!==r)return r.call(n)},l=function(){function t(t,e){for(var i=0;i1&&void 0!==arguments[1]?arguments[1]:"createNode",i=[],n=0;n2?i-2:0),s=2;s"},parseFragment:function(t){var e=document.createElement("svg");if(t){var i=this.g();e.innerHTML=""+t.replace(/\n/,"").replace(/<(\w+)([^<]+?)\/>/g,"<$1$2>")+"";for(var n=0,s=e.firstChild.childNodes.length;n0&&void 0!==arguments[0]?arguments[0]:P.hasDOMAccess()?k.Canvas:k.OpenTypeJS;r(this,t),this.textMeasuringStrategy=i,this.defs={},this.makeDefs=[],P.hasDOMAccess()&&(this.defsNode=P.createNode("defs")),this.textStyles={},this.textColor="#000",this.setFont("'Palatino Linotype', 'Book Antiqua', Palatino, serif",16),this.rubricColor="#d00",this.specialCharProperties={"font-family":"'Exsurge Characters'",fill:this.rubricColor,class:"rubric"},this.textBeforeSpecialChar="",this.textAfterSpecialChar=".",this.specialCharMap={"℣":"v","℟":"r","+":"+","*":"*"},this.plusProperties={},this.asteriskProperties={},this.specialCharText=function(t){return e.specialCharMap[t]||t},this.fontStyleDictionary={b:{"font-weight":"bold"},i:{"font-style":"italic"},u:{"text-decoration":"underline"},ul:{"text-decoration":"underline"},c:{fill:this.rubricColor,class:"rubric"},sc:{"font-variant":"small-caps","font-variant-caps":"small-caps","font-feature-settings":"'smcp'","-webkit-font-feature-settings":"'smcp'"},v:{}},this.markupSymbolDictionary={"*":"b",_:"i","^":"c","%":"sc"},this.textStyles.al.prefix="",this.textStyles.translation.prefix="",this.textStyles.dropCap.padding=1,this.textStyles.annotation.padding=1,this.minLedgerSeparation=2,this.minSpaceAboveStaff=2,this.minSpaceBelowStaff=1,this.spaceBetweenSystems=1.5,this.glyphPunctumWidth=p.Glyphs.PunctumQuadratum.bounds.width,this.glyphPunctumHeight=p.Glyphs.PunctumQuadratum.bounds.height,this.maxExtraSpaceInStaffIntervals=.5,this.activeClef=null,this.neumeLineColor="#000",this.staffLineColor="#000",this.dividerLineColor="#000",this.defaultLanguage=d.language.latin,this.pixelRatio=window.devicePixelRatio||1,i===k.Svg?(this.svgTextMeasurer=P.svg(0,0),this.svgTextMeasurer.setAttribute("id","TextMeasurer"),this.svgTextMeasurer.setAttribute("style","position:absolute"),document.body.insertBefore(this.svgTextMeasurer,document.body.firstChild)):i===k.Canvas&&this.makeCanvasIfNeeded(),this.syllableConnector="-",this.scaleDefs=!0,this.setGlyphScaling(1/16),this.interSyllabicMultiplier=2.5,this.accidentalSpaceMultiplier=2,this.interVerbalMultiplier=1,this.drawGuides=!1,this.drawDebuggingBounds=!0,this.activeNotations=null,this.currNotationIndex=-1,this.minSyllablesLastLine=0,this.minNotesLastLine=0,this.condensingTolerance=.3,this.autoColor=!0,this.useExtraTextOnly=!0,this.noteIdPrefix="note-",this.insertFontsInDoc()}return l(t,[{key:"getFontForProperties",value:function(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:{},e=arguments[1],i=(a(t),a(t,e));return this.fontDictionary&&(this.fontDictionary[i]||this.fontDictionary[e]||this.fontDictionary.Regular)}},{key:"setFont",value:function(t){var e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:16,i=arguments.length>2&&void 0!==arguments[2]?arguments[2]:{},n=arguments[3],s=!0,o=!1,r=void 0;try{for(var a,u=Object.entries(S)[Symbol.iterator]();!(s=(a=u.next()).done);s=!0){var h=c(a.value,2),l=h[0],f=h[1],p=this.textStyles[l]=this.textStyles[l]||{};p.size=f.defaultSize?f.defaultSize(e,this):f.size(this),p.font=t,p.color=this.textColor||"#000"}}catch(t){o=!0,r=t}finally{try{!s&&u.return&&u.return()}finally{if(o)throw r}}this.baseTextStyle=i,n&&(this.textMeasuringStrategy=k.OpenTypeJS,this.fontDictionary=n)}},{key:"setRubricColor",value:function(t){this.rubricColor=t,this.specialCharProperties.fill=t,this.fontStyleDictionary.c.fill=t}},{key:"setScaleDefs",value:function(t){t=!!t,this.scaleDefs!==t&&(this.scaleDefs=t,this.setGlyphScaling(this.glyphScaling))}},{key:"createStyleCss",value:function(){var t="",e=!0,i=!1,n=void 0;try{for(var s,o=Object.entries(S)[Symbol.iterator]();!(e=(s=o.next()).done);e=!0){var r=c(s.value,2),a=r[0],u=r[1],h=u.cssClass,l=this.textStyles[a],f=l.color,p=l.font,d=l.size;t+="svg.Exsurge ."+h+"{fill:"+f+";font-family:"+p+";font-size:"+d+"px;font-kerning:normal}"}}catch(t){i=!0,n=t}finally{try{!e&&o.return&&o.return()}finally{if(i)throw n}}return t}},{key:"createStyleNode",value:function(){var t=P.createNode("style",{});return t.textContent=this.createStyleCss(),t}},{key:"createStyleTree",value:function(){return{name:"style",props:{},children:[this.createStyleCss()]}}},{key:"createStyle",value:function(){return""}},{key:"updateHyphenWidth",value:function(){var t=new I(this,this.syllableConnector,M.SingleSyllable),e=this.minLyricWordSpacing/(this.hyphenWidth||this.minLyricWordSpacing)||1;this.hyphenWidth=t.bounds.width,this.minLyricWordSpacing=e*this.hyphenWidth}},{key:"setStaffHeight",value:function(t){this.setGlyphScaling(t/600)}},{key:"setGlyphScaling",value:function(t){for(this.glyphScaling=t,this.staffInterval=this.glyphPunctumWidth*this.glyphScaling,this.staffLineWeight=Math.ceil(5*this.staffInterval/8)/5,this.neumeLineWeight=this.staffLineWeight,this.dividerLineWeight=this.neumeLineWeight,this.episemaLineWeight=1.25*this.neumeLineWeight,this.intraNeumeSpacing=this.staffInterval/2;this.defsNode&&this.defsNode.firstChild;)this.defsNode.removeChild(this.defsNode.firstChild);for(var e=0;e2&&void 0!==arguments[2]?arguments[2]:1;this.makeCanvasIfNeeded(),this.canvas.style.width=t*i+"px",this.canvas.style.height=e*i+"px",i*=this.pixelRatio,this.canvas.width=t*i,this.canvas.height=e*i,this.canvasCtxt.setTransform(i,0,0,i,0,0)}}]),t}(),e.ChantLayoutElement=function(){function t(){r(this,t),this.bounds=new f.Rect,this.origin=new f.Point(0,0),this.selected=!1,this.highlighted=!1}return l(t,[{key:"draw",value:function(t){throw"ChantLayout Elements must implement draw(ctxt)"}},{key:"createSvgNode",value:function(t){throw"ChantLayout Elements must implement createSvgNode(ctxt)"}},{key:"createSvgFragment",value:function(t){throw"ChantLayout Elements must implement createSvgFragment(ctxt)"}}]),t}()),O=(e.DividerLineVisualizer=function(t){function e(t,i,n,o){r(this,e);var a=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));a.divider=o;var u=t.calculateHeightFromStaffPosition(i),h=t.calculateHeightFromStaffPosition(n);if(u>h){var l=u;u=h,h=l}return a.bounds.x=0,a.bounds.y=u,a.bounds.width=t.dividerLineWeight,a.bounds.height=h-u,a.origin.x=a.bounds.width/2,a.origin.y=u,a}return o(e,t),l(e,[{key:"draw",value:function(t){var e=t.canvasCtxt;e.fillStyle=t.dividerLineColor,e.fillRect(this.bounds.x,this.bounds.y,t.dividerLineWeight,this.bounds.height)}},{key:"getSvgProps",value:function(t){var e={x:this.bounds.x,y:this.bounds.y,width:t.dividerLineWeight,height:this.bounds.height,fill:t.dividerLineColor,class:"dividerLine"};return this.divider&&(this.divider.selected&&(e.class+=" selected"),e["source-index"]=this.divider.sourceIndex,e["element-index"]=this.divider.elementIndex,e.source=this.divider),e}},{key:"createSvgNode",value:function(t){return P.createNode("rect",this.getSvgProps(t))}},{key:"createSvgTree",value:function(t){return P.createSvgTree("rect",this.getSvgProps(t))}},{key:"createSvgFragment",value:function(t){return P.createFragment("rect",this.getSvgProps(t))}}]),e}(T),e.NeumeLineVisualizer=function(t){function e(t,i,n,o){r(this,e);var a=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this)),u=i.staffPosition,h=n.staffPosition;if(u-3&&h--,f+=t.glyphPunctumHeight*t.glyphScaling/2.2),f+=t.calculateHeightFromStaffPosition(h),a.bounds.x=0,a.bounds.y=c,a.bounds.width=t.neumeLineWeight,a.bounds.height=f-c,a.origin.x=0,a.origin.y=0,a}return o(e,t),l(e,[{key:"draw",value:function(t){var e=t.canvasCtxt;e.fillStyle=t.neumeLineColor,e.fillRect(this.bounds.x,this.bounds.y,t.neumeLineWeight,this.bounds.height)}},{key:"getSvgProps",value:function(t){return{x:this.bounds.x,y:this.bounds.y,width:t.neumeLineWeight,height:this.bounds.height,fill:t.neumeLineColor,class:"neumeLine"}}},{key:"createSvgNode",value:function(t){return P.createNode("rect",this.getSvgProps(t))}},{key:"createSvgTree",value:function(t){return P.createSvgTree("rect",this.getSvgProps(t))}},{key:"createSvgFragment",value:function(t){return P.createFragment("rect",this.getSvgProps(t))}}]),e}(T),e.VirgaLineVisualizer=function(t){function e(t,i){r(this,e);var n,o=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this)),a=i.staffPosition,u=t.calculateHeightFromStaffPosition(a);return n=0===Math.abs(a%2)?u+1.8*t.staffInterval:u+2.7*t.staffInterval,o.bounds.x=0,o.bounds.y=u,o.bounds.width=t.neumeLineWeight,o.bounds.height=n-u,o.origin.x=0,o.origin.y=0,o}return o(e,t),l(e,[{key:"draw",value:function(t){var e=t.canvasCtxt;e.fillStyle=t.neumeLineColor,e.fillRect(this.bounds.x,this.bounds.y,t.neumeLineWeight,this.bounds.height)}},{key:"getSvgProps",value:function(t){return{x:this.bounds.x,y:this.bounds.y,width:t.neumeLineWeight,height:this.bounds.height,fill:t.neumeLineColor,class:"neumeLine"}}},{key:"createSvgNode",value:function(t){return P.createNode("rect",this.getSvgProps(t))}},{key:"createSvgTree",value:function(t){return P.createSvgTree("rect",this.getSvgProps(t))}},{key:"createSvgFragment",value:function(t){return P.createFragment("rect",this.getSvgProps(t))}}]),e}(T),e.LineaVisualizer=function(t){function e(t,i){r(this,e);var n=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this)),o=i.staffPosition,a=t.calculateHeightFromStaffPosition(o)-i.origin.y,u=a+i.bounds.height;return n.bounds.x=0,n.bounds.y=a,n.bounds.width=5*t.neumeLineWeight+i.bounds.width,n.bounds.height=u-a,n.origin.x=2.5*t.neumeLineWeight,n.origin.y=0,n}return o(e,t),l(e,[{key:"draw",value:function(t){var e=t.canvasCtxt;e.fillStyle=t.neumeLineColor,e.fillRect(this.bounds.x,this.bounds.y,t.neumeLineWeight,this.bounds.height),e.fillRect(this.bounds.x+this.bounds.width-t.neumeLineWeight,this.bounds.y,t.neumeLineWeight,this.bounds.height)}},{key:"getSvgProps",value:function(t,e){return{x:e,y:this.bounds.y,width:t.neumeLineWeight,height:this.bounds.height,fill:t.neumeLineColor,class:"neumeLine"}}},{key:"createSvgNode",value:function(t){var e=this;return P.createNode("g",null,[this.bounds.x,this.bounds.x+this.bounds.width-t.neumeLineWeight].map(function(i){return P.createNode("rect",e.getSvgProps(t,i))}))}},{key:"createSvgTree",value:function(t){var e=this;return P.createSvgTree.apply(P,["g",{}].concat(n([this.bounds.x,this.bounds.x+this.bounds.width-t.neumeLineWeight].map(function(i){return P.createSvgTree("rect",e.getSvgProps(t,i))}))))}},{key:"createSvgFragment",value:function(t){var e=this;return P.createFragment("g",null,[this.bounds.x,this.bounds.x+this.bounds.width-t.neumeLineWeight].map(function(i){return P.createFragment("rect",e.getSvgProps(t,i))}).join(""))}}]),e}(T),e.GlyphVisualizer=function(t){function e(t,i){r(this,e);var n=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));return n.glyph=null,n.setGlyph(t,i),n}return o(e,t),l(e,[{key:"setGlyph",value:function(t,e){if(this.glyphCode!==e){"undefined"==typeof e||null===e||""===e?e=this.glyphCode=w.None:this.glyphCode=e;var i=this.glyph=p.Glyphs[e];if(!t.defs.hasOwnProperty(e)){var s=function(){var i={id:e,class:"glyph"};return t.scaleDefs===!0&&(i.transform="scale("+t.glyphScaling+")"),i},o=function(){var n=s();t.defs[e]=P.createFragment("g",n,P.svgFragmentForGlyph(i)),t.defsNode&&t.defsNode.appendChild(P.createNode("g",n,P.nodesForGlyph(i)))};o.makeSvgTree=function(){return P.createSvgTree.apply(P,["g",s()].concat(n(P.nodesForGlyph(i,"createSvgTree"))))},o.glyphCode=e,o(),t.makeDefs.push(o)}this.align=this.glyph.align}this.origin.x=this.glyph.origin.x*t.glyphScaling,this.origin.y=this.glyph.origin.y*t.glyphScaling,this.bounds.x=0,this.bounds.y=-this.origin.y,this.bounds.width=this.glyph.bounds.width*t.glyphScaling,this.bounds.height=this.glyph.bounds.height*t.glyphScaling}},{key:"setStaffPosition",value:function(t,e){this.bounds.y=t.calculateHeightFromStaffPosition(e)-this.origin.y}},{key:"draw",value:function(t){var e=t.canvasCtxt,i=this.bounds.x+this.origin.x,n=this.bounds.y+this.origin.y;e.translate(i,n),e.scale(t.glyphScaling,t.glyphScaling);for(var s=0;sn){var h=i;i=n,n=h}return u.isAbove=a,u.braceHeight=3*t.staffInterval/2,u.bounds=new f.Rect(i,a?o-u.braceHeight:o,n-i,u.braceHeight),u.origin.x=0,u.origin.y=0,u}return o(e,t),l(e,[{key:"getSvgPathProps",value:function(t){return{d:this.generatePathString(),stroke:t.neumeLineColor,"stroke-width":t.staffLineWeight+"px",fill:"none",class:"brace"}}},{key:"createSvgNode",value:function(t){var e=P.createNode("path",this.getSvgPathProps(t));return this.accent?P.createNode("g",{class:"accentedBrace"},[e,this.accent.createSvgNode(t)]):e}},{key:"createSvgTree",value:function(t){var e=P.createSvgTree("path",this.getSvgPathProps(t));return this.accent?P.createSvgTree("g",{class:"accentedBrace"},e,this.accent.createSvgTree(t)):e}},{key:"createSvgFragment",value:function(t){var e=P.createFragment("path",this.getSvgPathProps(t));return this.accent?(e+=this.accent.createSvgFragment(t),P.createFragment("g",{class:"accentedBrace"},e)):e}},{key:"generatePathString",value:function(){var t,e,i,n=this.bounds.x,s=this.bounds.right(),o=this.bounds.width;e=o/6,i=this.bounds.height,this.isAbove?(t=this.bounds.bottom(),i=-i):t=this.bounds.y;var r=n+e,a=t+i,u=s-e,h=2;return"M "+n.toFixed(h)+" "+t.toFixed(h)+" C "+r.toFixed(h)+" "+a.toFixed(h)+" "+u.toFixed(h)+" "+a.toFixed(h)+" "+s.toFixed(h)+" "+t.toFixed(h)}}]),e}(T),e.CurlyBraceVisualizer=function(t){function e(t,i,n,o){var a=!(arguments.length>4&&void 0!==arguments[4])||arguments[4],u=arguments.length>5&&void 0!==arguments[5]&&arguments[5];r(this,e);var h=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));if(i>n){var l=i;i=n,n=l}h.isAbove=a,h.braceHeight=t.staffInterval/2,a&&(o-=h.braceHeight);var c=new f.Rect(i,o,n-i,h.braceHeight);return u&&a&&(h.accent=new O(t,w.AcuteAccent),h.accent.bounds.x+=c.x+(n-i)/2,h.accent.bounds.y+=c.y-t.staffInterval/4,c.union(h.accent.bounds)),h.bounds=c,h.origin.x=0,h.origin.y=0,h}return o(e,t),l(e,[{key:"getSvgPathProps",value:function(t){return{d:this.generatePathString(),stroke:t.neumeLineColor,"stroke-width":t.staffLineWeight+"px",fill:"none",class:"brace"}}},{key:"createSvgNode",value:function(t){var e=P.createNode("path",this.getSvgPathProps(t));return this.accent?P.createNode("g",{class:"accentedBrace"},[e,this.accent.createSvgNode(t)]):e}},{key:"createSvgTree",value:function(t){var e=P.createSvgTree("path",this.getSvgPathProps(t));return this.accent?P.createSvgTree("g",{class:"accentedBrace"},e,this.accent.createSvgTree(t)):e}},{key:"createSvgFragment",value:function(t){var e=P.createFragment("path",this.getSvgPathProps(t));return this.accent?(e+=this.accent.createSvgFragment(t),P.createFragment("g",{class:"accentedBrace"},e)):e}},{key:"generatePathString",value:function(){var t,e,i=.6,n=this.bounds.x,s=this.bounds.right(),o=this.bounds.width;this.isAbove?(t=this.bounds.bottom(),e=-this.braceHeight):(t=this.bounds.y,e=this.braceHeight);var r=t+i*e,a=n+.25*o,u=t+(1-i)*e,h=n+.5*o,l=t+e,c=t+i*e,f=n+.75*o,p=t+(1-i)*e,d=2;return"M "+n.toFixed(d)+" "+t.toFixed(d)+" Q "+n.toFixed(d)+" "+r.toFixed(d)+" "+a.toFixed(d)+" "+u.toFixed(d)+" T "+h.toFixed(d)+" "+l.toFixed(d)+" M "+s.toFixed(d)+" "+t.toFixed(d)+" Q "+s.toFixed(d)+" "+c.toFixed(d)+" "+f.toFixed(d)+" "+p.toFixed(d)+" T "+h.toFixed(d)+" "+l.toFixed(d)}}]),e}(T),e.TextSpan=function(){function t(e,i,n){var s=arguments.length>3&&void 0!==arguments[3]?arguments[3]:0;r(this,t),"undefined"!=typeof i&&null!==i||(i={}),this.text=e,this.properties=i,this.activeTags=n||[],this.index=s}return l(t,[{key:"clone",value:function(){return new t(this.text,this.properties,this.activeTags,this.index)}}]),t}());u.createStackFrame=function(t,e,i){var n=arguments.length>3&&void 0!==arguments[3]?arguments[3]:{},s=arguments.length>4&&void 0!==arguments[4]?arguments[4]:"";return new u(e,i,Object.assign({},t.fontStyleDictionary[e],n),s)};var N={"&":"&","<":"<",">":">"},A=e.TextElement=function(t){function e(t,i,n,o,a,u,h){r(this,e);var l=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));return l.bounds.x=0,l.bounds.y=0,l.bounds.width=0,l.bounds.height=0,l.origin.x=0,l.origin.y=0,l.fontFamily=n,l.fontSize=o,l.textAnchor=a,l.sourceIndex=u,l.sourceGabc=h,l.dominantBaseline="baseline",l.generateSpansFromText(t,i),l.recalculateMetrics(t),l}return o(e,t),l(e,[{key:"getFromScore",value:function(t){return this.textType.getFromScore(t,this)}},{key:"generateSpansFromText",value:function(t,e){var i=this;if(e=e.replace(/\s+/g," "),this.text="",this.spans=[],"*"===e||"+"===e||"†"===e){var n="*"===e?t.asteriskProperties:"+"===e?t.plusProperties:null;return e=t.specialCharText(e)||e,void this.spans.push(new _(e,n))}for(var s=[],o=0,r=0,a=function(t,e){return t.Symbol===e},h=function(t,e,n){if(""!==t||i.dropCap){i.text+=t;for(var o={},a=0;a)|([\s\S]*?)(?:<\/v>|$)|(\*)(?=\s*\*|[^*]*(?:$|))|(\+)|(?:(~)|(')?([ao]e|[æœaeiouy])|([arv])\/)<\/sp>|([arv])\/\.|([℣℟])\.?|(?:([*_^%])|<(\/)?([bciuv]|ul|sc|font)(?:\s+(?:family="([^"]+)"|fill="([^"]+)"|class="([^"]+)"))*>)(?=(?:(.+?)(?:\11|<\/\13>))?)/gi,f=/(\\grecross)|\{greextra\}\{([^}]*)\}/g,p=null,d=!1,m=function(){return h(e.substring(o,p.index),o)};p=l.exec(e);){var b=p,x=c(b,18),S=x[1],L=x[2],C=x[3],w=x[4],P=x[5],k=x[6],T=x[7],O=x[8],N=x[9],A=x[10],M=x[11],I=x[12],B=x[13],E=x[14],D=x[15],F=x[16],z=x[17];if(O=O||N||A,S)p.index>o&&m(),r++;else if(L){m();for(var j=void 0,V=0,G=0;j=f.exec(L);){V0&&s[s.length-1].symbol===C?s.pop():h(t.specialCharText(C)||"*",p.index,t.asteriskProperties);else if(w)m(),h(t.specialCharText(w)||"+",p.index,t.plusProperties);else if(P)m(),h("∼",p.index);else if(T){var U=(0,y.makeLigature)(T);k&&(U=(0,g.addAccent)(U)),m(),h(U,p.index)}else if(O)m(),h(t.textBeforeSpecialChar+t.specialCharText(O)+t.textAfterSpecialChar,p.index,t.specialCharProperties);else{if("*"===M)if(z&&/[^\s*]/.test(z))d=!0;else{if(!d)continue;d=!1}if(M&&(B=t.markupSymbolDictionary[M],s.length>0&&s[s.length-1].tagName===B&&s[s.length-1].symbol===M&&(I=!0)),s.length>0&&s[s.length-1].tagName===B)I&&(m(), +s.pop());else{if(s.filter(a).length>0){o=s[s.length-1].startIndex,s.pop();continue}if(m(),I){var J=s.findIndex(function(t){return t.tagName===B});J>=0&&s.splice(J,1)}else{var $={};E&&($["font-family"]=E),D&&($.fill=D),F&&($.class=F),s.push(u.createStackFrame(t,B,p.index,$,M))}}}o=p.index+p[0].length}(o1&&void 0!==arguments[1]?arguments[1]:{},i="";"italic"===e["font-style"]&&(i+="italic "),"small-caps"===e["font-variant"]&&(i+="small-caps "),"bold"===e["font-weight"]&&(i+="bold ");var n=parseFloat(e["font-size"])||this.fontSize(t);return/%$/.test(e["font-size"])&&(n*=this.fontSize(t)/100),i+=n*(this.resize||1)+"px ",i+=e["font-family"]||this.fontFamily(t)}},{key:"measureSubstringBBox",value:function(t,e){return this.measureSubstring(t,e,!0)}},{key:"measureSubstring",value:function(t,e){var i=arguments.length>2&&void 0!==arguments[2]&&arguments[2];if(0===e)return 0;if(e||(e=1/0),e<0){var n=-e;e=1/0}for(var s=t.canvasCtxt,o=0,r=[],a=[this.spans[0]],u=0,h=1,l=this.fontSize(t)*(this.resize||1),c=new f.Rect(0,0,0,0),p=0;p1&&void 0!==arguments[1])||arguments[1];if(e&&(delete this.maxWidth,delete this.firstLineMaxWidth,delete this.rightAligned,delete this.resize,delete this.numLines,this.spans.forEach(function(t){delete t.properties.xOffset,t.properties.newLine===!0&&(delete t.properties.newLine,t.text=" "+t.text)})),this.bounds.x=0,this.bounds.y=0,this.origin.x=0,t.textMeasuringStrategy===k.Svg){for(;t.svgTextMeasurer.firstChild;)t.svgTextMeasurer.removeChild(t.svgTextMeasurer.firstChild);t.svgTextMeasurer.appendChild(this.createSvgNode(t)),t.svgTextMeasurer.appendChild(t.createStyleNode());var i=t.svgTextMeasurer.firstChild.getBBox();this.bounds.width=i.width,this.bounds.height=i.height,this.origin.y=-i.y,this.origin.x=-i.x}else{var n=this.measureSubstringBBox(t);this.bounds.width=n.width,this.bounds.height=n.height,this.origin.y=-n.y,this.origin.x=-n.x}this.numLines=this.spans.reduce(function(t,e){return t+(e.properties.newLine?parseInt(e.properties.newLine)||1:0)},1)}},{key:"setMaxWidth",value:function(t,e){var i=arguments.length>2&&void 0!==arguments[2]?arguments[2]:e;if(this.spans.filter(function(t){return t.properties.newLine===!0}).length&&this.recalculateMetrics(t),this.bounds.width>e){this.maxWidth=e;var n=e/this.bounds.width;if(this instanceof I&&n>=.85)this.resize=n;else{i<0&&(i=e),this.firstLineMaxWidth=i;for(var s,o=0,r=null,a=/\s+|$/g,u=i;(s=a.exec(this.text))&&(!r||s.index>r.index);){var h=this.measureSubstring(t,s.index);if(h>u&&r){for(var l,c=0,f=0;fr.index){var d=this.spans[--c];f-=d.text.length}var g=this.spans[c],y=g.text.slice(0,r.index-f),v=g.text.slice(r.index+r[0].length-f),m=[];if(this.rightAligned=u===i&&i!==e,y&&m.push(new _(y,g.properties,g.activeTags)),v?m.push(new _(v,Object.assign({},g.properties,{newLine:!0}),g.activeTags)):this.spans[c+1]&&(this.spans[c+1].properties.newLine=!0),(l=this.spans).splice.apply(l,[c,1].concat(m)),this.needsLayout=!0,u=e,s.index===this.text.length||this.measureSubstring(t)<=e)break;h=0,s=r=null}o=h,r=s}}this.recalculateMetrics(t,!1)}}},{key:"getCssClasses",value:function(){return this.textType&&this.textType.cssClass||""}},{key:"getExtraStyleProperties",value:function(t){return t.baseTextStyle||{}}},{key:"draw",value:function(t){var e=t.canvasCtxt;"middle"===this.textAnchor?e.textAlign="center":e.textAlign="start";for(var i=0,n=0,s=0;s2&&void 0!==arguments[2]&&arguments[2],n={"source-index":t.index,class:t.properties.class,style:i?Object.assign({},t.properties):(0,f.getCssForProperties)(t.properties)};if(t.properties.newLine){var s=t.properties.xOffset||0;n.dy=1.1*(parseInt(t.properties.newLine)||1)+"em",n.x=this.bounds.x+s}else t.properties.xOffset&&(n.x=this.bounds.x+t.properties.xOffset);return t.properties.textLength&&(n.textLength=t.properties.textLength,n.lengthAdjust="spacingAndGlyphs",n.y=this.bounds.y),this.resize&&(n["font-size"]=t.properties["font-size"]||this.fontSize(e)*this.resize),n}},{key:"createSvgNode",value:function(t){for(var e=[],i=0;i]/g,function(t){return N[t]})}}]),e}(T),M=e.LyricType={SingleSyllable:0,BeginningSyllable:1,MiddleSyllable:2,EndingSyllable:3,Directive:4},I=(e.LyricArray={getLeft:function(t){if(0===t.length)return NaN;for(var e=Number.MAX_VALUE,i=0;i0&&this.spans[this.spans.length-1]!==this.connectorSpan&&this.spans.push(this.connectorSpan);else{this.connectorWidth=0,this.needsConnector=!1,this.bounds.width=this.widthWithoutConnector;var i=this.spans.pop();i&&i!==this.connectorSpan&&this.spans.push(i)}}},{key:"setConnectorWidth",value:function(t){this.connectorWidth=t,this.connectorSpan.properties=Object.assign({},this.connectorSpan.properties,{textLength:t}),this.needsConnector&&(this.bounds.width=this.widthWithoutConnector+this.getConnectorWidth())}},{key:"getConnectorWidth",value:function(){return this.connectorWidth||this.defaultConnectorWidth}},{key:"getLeft",value:function(){return this.notation.bounds.x+this.bounds.x}},{key:"getRight",value:function(){return this.notation.bounds.x+this.bounds.x+this.bounds.width}},{key:"recalculateMetrics",value:function(t){var i=!(arguments.length>1&&void 0!==arguments[1])||arguments[1];this.setNeedsConnector(),h(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"recalculateMetrics",this).call(this,t,i),this.widthWithoutConnector=this.bounds.width,this.connectorWidth=0,this.defaultConnectorWidth=t.hyphenWidth;var n,s,o=this.language||t.defaultLanguage,r=this.widthWithoutConnector/2,a=this.widthWithoutConnector;if(this.centerStartIndex>=0&&(this.centerStartIndex>=this.text.length||this.centerLength<0||this.centerStartIndex+this.centerLength>this.text.length)&&(this.centerStartIndex=-1),0===this.text.length)this.dropCap&&this.originalText&&(r=t.hyphenWidth/2,a=t.hyphenWidth);else if(this.centerStartIndex>=0)t.textMeasuringStrategy===k.Svg?(n=t.svgTextMeasurer.firstChild.getSubStringLength(0,this.centerStartIndex),s=t.svgTextMeasurer.firstChild.getSubStringLength(0,this.centerStartIndex+this.centerLength)):(n=this.measureSubstring(t,this.centerStartIndex),s=this.measureSubstring(t,this.centerStartIndex+this.centerLength)),r=(n+s)/2,a=s-n;else if(this.lyricType!==M.Directive){var u=this.text.lastIndexOf(" ")+1;u>0&&!this.text.slice(u).match(/[a-záéíóúýäëïöüÿàèìòùỳāēīōūȳăĕĭŏŭ]/i)&&(u=0);var l=o.findVowelSegment(this.text,u);if(l.found!==!0){var c=this.text.slice(u).match(/[a-z]+/i);c?(l.startIndex=u+c.index,l.length=c[0].length):(l.startIndex=u,l.length=this.text.length-u)}t.textMeasuringStrategy===k.Svg?(n=t.svgTextMeasurer.firstChild.getSubStringLength(0,l.startIndex),s=t.svgTextMeasurer.firstChild.getSubStringLength(0,l.startIndex+l.length)):(n=this.measureSubstring(t,l.startIndex),s=this.measureSubstring(t,l.startIndex+l.length)),r=(n+s)/2,a=s-n}this.vowelSegmentWidth=a,this.bounds.x=-r,this.bounds.y=0,this.origin.x=r}},{key:"generateDropCap",value:function(t){if(this.dropCap)return this.dropCap;if(this.spans[0].properties["font-family"]===t.specialCharProperties["font-family"])return null;var e=this.spans[0].clone();e.text=e.text.slice(0,1).toUpperCase();var i=e.text.toLowerCase();if(e.text===i)return null;e.activeTags.indexOf("sc")>=0&&(e.text=i);var n=this.dropCap=new B(t,"",this.sourceIndex);n.spans=[e];var s=this.sourceGabc.match(/^(?:<\/?[^>]>)*.?(?:<\/[^>]>)*/)[0].length;return n.sourceGabc=this.sourceGabc.slice(0,s),this.sourceIndex+=n.sourceGabc.length,this.sourceGabc=this.sourceGabc.slice(s),this.spans[0].text=this.spans[0].text.slice(1),this.text=this.text.slice(1),this.centerStartIndex--,n}},{key:"getCssClasses",value:function(){var t=this.lyricType===M.Directive?"directive ":"";return t+h(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"getCssClasses",this).call(this)}},{key:"getExtraStyleProperties",value:function(t){var i=h(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"getExtraStyleProperties",this).call(this,t);return this.lyricType===M.Directive&&t.autoColor===!0&&(i=Object.assign({},i,{fill:t.rubricColor})),i}}]),e}(A)),B=(e.ChoralSign=function(t){function e(t,i,n,o){r(this,e);var a=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,(t.textStyles.choralSign.prefix||"")+i,function(t){return t.textStyles.choralSign.font},S.choralSign.size,"start",o,i));return a.positionHint=x.Default,a.note=n,a.textType=S.choralSign,a}return o(e,t),l(e,[{key:"recalculateMetrics",value:function(t){h(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"recalculateMetrics",this).call(this,t)}},{key:"performLayout",value:function(t){this.recalculateMetrics(t),this.bounds.x=this.note.bounds.x+Math.max(0,(t.staffInterval-this.bounds.width)/2);var e=void 0,i=void 0;this.positionHint===x.Below?(e=-1,i=this.note.staffPosition+2*e,i+=i%2===0?.3:1):(e=1,i=this.note.staffPosition+2*e,i+=i%2===0?.3:-.4),this.bounds.y=t.calculateHeightFromStaffPosition(i)+this.origin.y}}]),e}(A),e.AboveLinesText=function(t){function e(t,i,n,o){r(this,e);var a=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,(t.textStyles.al.prefix||"")+i,function(t){return t.textStyles.al.font},function(t){return t.textStyles.al.size},"start",o,i));return a.notation=n,a.textType=S.al,a.padding=t.staffInterval/2,a}return o(e,t),e}(A),e.TranslationText=function(t){function e(t,i,n,o){r(this,e);var a=i,u="start";"/"===i?(i="",u="end"):i=(t.textStyles.translation.prefix||"")+i;var h=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,i,function(t){return t.textStyles.translation.font},function(t){return t.textStyles.translation.size},u,o,a));return h.notation=n,h.textType=S.translation,h.padding=t.staffInterval/2,h}return o(e,t),e}(A),e.DropCap=function(t){function e(t,i,n){r(this,e);var o=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,(t.textStyles.dropCap.prefix||"")+i,function(t){return t.textStyles.dropCap.font},function(t){return t.textStyles.dropCap.size},"middle",n,i));return o.textType=S.dropCap,o.padding=t.staffInterval*t.textStyles.dropCap.padding,o}return o(e,t),e}(A)),E=e.TitleTextElement=function(t){function e(t,i,n,o,a,u,h){return r(this,e),s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,i,n,o,a,u,h))}return o(e,t),e}(A),D=(e.Supertitle=function(t){function e(t,i,n){r(this,e);var o=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,(t.textStyles.supertitle.prefix||"")+i,function(t){return t.textStyles.supertitle.font},function(t){return t.textStyles.supertitle.size},"middle",n,i));return o.textType=S.supertitle,o.padding=function(t){return(Number(t.textStyles.supertitle.padding)||1)*t.textStyles.supertitle.size/3},o}return o(e,t),e}(E),e.Title=function(t){function e(t,i,n){r(this,e);var o=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,(t.textStyles.title.prefix||"")+i,function(t){return t.textStyles.title.font},function(t){return t.textStyles.title.size},"middle",n,i));return o.textType=S.title,o.padding=function(t){return(Number(t.textStyles.title.padding)||1)*t.textStyles.title.size/3},o}return o(e,t),e}(E),e.Subtitle=function(t){function e(t,i,n){r(this,e);var o=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,(t.textStyles.subtitle.prefix||"")+i,function(t){return t.textStyles.subtitle.font},function(t){return t.textStyles.subtitle.size},"middle",n,i));return o.textType=S.subtitle,o.padding=function(t){return(Number(t.textStyles.subtitle.padding)||1)*t.textStyles.subtitle.size/3},o}return o(e,t),e}(E),e.TextLeftRight=function(t){function e(t,i,n,o){r(this,e);var a=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,(t.textStyles.leftRight.prefix||"")+i,function(t){return t.textStyles.leftRight.font},function(t){return t.textStyles.leftRight.size},"textLeft"===n?"start":"end",o,i));return a.textType=S.leftRight,a.extraClass="textLeft"===n?"textLeft":"textRight",a.headerKey="textLeft"===n?"text-left":"text-right",a.padding=function(t){return(Number(t.textStyles.leftRight.padding)||1)*t.textStyles.leftRight.size/5},a}return o(e,t),l(e,[{key:"getCssClasses",value:function(){return this.extraClass+" "+h(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"getCssClasses",this).call(this)}}]),e}(E),e.Annotation=function(t){function e(t,i){r(this,e);var n=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,(t.textStyles.annotation.prefix||"")+i,function(t){return t.textStyles.annotation.font},function(t){return t.textStyles.annotation.size},"middle"));return n.textType=S.annotation,n.padding=t.staffInterval*t.textStyles.annotation.padding,n.dominantBaseline="hanging",n}return o(e,t),e}(A));e.Annotations=function(t){function e(t){r(this,e);for(var i=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this)),n=arguments.length,o=Array(n>1?n-1:0),a=1;a1&&void 0!==arguments[1]?arguments[1]:"createSvgNode",i=[];for(s=0;s2&&void 0!==arguments[2]?arguments[2]:null;s(this,e);var r=o(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));return r.isClef=!0,r.staffPosition=t,r.octave=i,r.defaultAccidental=n,r.activeAccidental=n,r.keepWithNext=!0,r}return r(e,t),u(e,[{key:"resetAccidentals",value:function(){this.activeAccidental=this.defaultAccidental}},{key:"pitchToStaffPosition",value:function(t){}},{key:"performLayout",value:function(t){t.activeClef=this,this.defaultAccidental&&this.defaultAccidental.performLayout(t),a(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"performLayout",this).call(this,t)}},{key:"finishLayout",value:function(t){if(this.defaultAccidental){var i=this.defaultAccidental.createGlyphVisualizer(t);i.bounds.x+=this.visualizers[0].bounds.right()+t.intraNeumeSpacing,this.addVisualizer(i)}a(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"finishLayout",this).call(this,t)}},{key:"clone",value:function t(){if(this.model)return this.model.clone();var t=new this.constructor(this.staffPosition,this.octave,this.defaultAccidental);return t.sourceGabc=this.sourceGabc,t.sourceIndex=this.sourceIndex,t.elementIndex=this.elementIndex,t.model=this,t}}],[{key:"default",value:function(){return S}}]),e}(f.ChantNotationElement),x=e.DoClef=function(t){function e(t,i){var n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:null;s(this,e);var r=o(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,i,n));return r.leadingSpace=0,r}return r(e,t),u(e,[{key:"pitchToStaffPosition",value:function(t){return 7*(t.octave-this.octave)+this.staffPosition+c.Pitch.stepToStaffOffset(t.step)-c.Pitch.stepToStaffOffset(c.Step.Do)}},{key:"staffPositionToPitch",value:function(t){var e=t-this.staffPosition,i=Math.floor(e/7),n=c.Pitch.staffOffsetToStep(e);return this.activeAccidental&&this.activeAccidental.staffPosition===t&&(n+=this.activeAccidental.accidentalType),new c.Pitch(n,this.octave+i)}},{key:"performLayout",value:function(t){a(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"performLayout",this).call(this,t);var i=new f.GlyphVisualizer(t,f.GlyphCode.DoClef);i.setStaffPosition(t,this.staffPosition),this.addVisualizer(i),this.finishLayout(t)}}]),e}(b),S=new x(3,2),L=(e.FaClef=function(t){function e(t,i){var n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:null;s(this,e);var r=o(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,i,n));return r.octave=i,r.leadingSpace=0,r}return r(e,t),u(e,[{key:"pitchToStaffPosition",value:function(t){return 7*(t.octave-this.octave)+this.staffPosition+c.Pitch.stepToStaffOffset(t.step)-c.Pitch.stepToStaffOffset(c.Step.Fa)}},{key:"staffPositionToPitch",value:function(t){var e=t-this.staffPosition+3,i=Math.floor(e/7),n=c.Pitch.staffOffsetToStep(e);return this.activeAccidental&&this.activeAccidental.staffPosition===t&&(n+=this.activeAccidental.accidentalType),new c.Pitch(n,this.octave+i)}},{key:"performLayout",value:function(t){a(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"performLayout",this).call(this,t); +var i=new f.GlyphVisualizer(t,f.GlyphCode.FaClef);i.setStaffPosition(t,this.staffPosition),this.addVisualizer(i),this.finishLayout(t)}}]),e}(b),e.TextOnly=function(t){function e(t,i){s(this,e);var n=o(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));return n.sourceIndex=t,n.sourceLength=i,n.sourceGabc="",n.trailingSpace=0,n}return r(e,t),u(e,[{key:"performLayout",value:function(t){a(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"performLayout",this).call(this,t),this.addVisualizer(new f.GlyphVisualizer(t,f.GlyphCode.None)),this.origin.x=0,this.origin.y=0,this.finishLayout(t)}}]),e}(f.ChantNotationElement)),C=(e.ChantLineBreak=function(t){function e(t){s(this,e);var i=o(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));return i.calculatedTrailingSpace=i.trailingSpace=0,i.justify=t,i}return r(e,t),u(e,[{key:"performLayout",value:function(t){this.bounds=new c.Rect(0,0,0,0)}},{key:"clone",value:function(){var t=new e;return t.justify=this.justify,t}}]),e}(f.ChantNotationElement),e.ChantMapping=function t(e,i,n){s(this,t),this.source=e,this.notations=i,this.sourceIndex=n},new f.TextSpan(" • ")),w=function(){for(var t=arguments.length,e=Array(t),i=0;i1&&void 0!==arguments[1]?arguments[1]:[],n=arguments[2];s(this,t),this.mappings=i,this.lines=[],this.notes=[],e&&(this.titles=new d.Titles(e,this)),this.startingClef=null,this.useDropCap=n,this.dropCap=null,this.annotation=null,this.compiled=!1,this.autoColoring=!0,this.needsLayout=!0,this.bounds=new c.Rect,this.mergeAnnotationWithTextLeft=w,e&&this.updateNotations(e)}return u(t,[{key:"copyLines",value:function(e,i){var n=new t;n.lines=this.lines.slice(e,i),n.bounds=this.bounds.clone();var s=n.lines.slice(-1)[0];return n.bounds.height=s.bounds.bottom()-s.origin.y,0===e&&(n.titles=this.titles,n.dropCap=this.dropCap,n.annotation=this.annotation),n}},{key:"updateSelection",value:function(t){this.selection=t;var e=t&&t.element||{indices:[]},i=e.indices,n=e.insertion;!n&&1===i.length&&this.notes[i[0]]instanceof L&&(n={afterElementIndex:i[0]});for(var s=0;s.6?void setTimeout(function(){i.performLayoutAsync(t,e)},100):(this.initializeLayout(t),void setTimeout(function(){return i.layoutElementsAsync(t,0,e)},0)))}},{key:"layoutElementsAsync",value:function(t,e,i){var n=this;if(e>=this.notations.length)return this.needsLayout=!1,void(i&&setTimeout(function(){return i()},0));0===e&&(t.activeClef=this.startingClef);var s=(new Date).getTime()+50;do{var o=this.notations[e];o.needsLayout&&(t.currNotationIndex=e,o.performLayout(t)),e++}while(e0?this.titles.layoutTitles(t,e):0,a=0;t.activeClef=this.startingClef;var u=t.staffInterval*t.spaceBetweenSystems;do{var l=new h.ChantLine(this);l.buildFromChantNotationIndex(t,a,e),a=l.notationsStartIndex+l.numNotationsOnLine,l.performLayout(t),l.elementIndex=this.lines.length,this.lines.push(l),l.bounds.y=-l.bounds.y+r,r+=l.bounds.height+u}while(at?(this.pages.push(this.copyLines(i,n)),i=n,e=s.bounds.y-s.origin.y,s.bounds.y=s.origin.y):s.bounds.y-=e}this.pages.push(this.copyLines(i,this.lines.length))}}},{key:"draw",value:function(t){var e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:1;t.setCanvasSize(this.bounds.width,this.bounds.height,e);var i=t.canvasCtxt;i.clearRect(0,0,t.canvas.width,t.canvas.height),i.translate(this.bounds.x,this.bounds.y),this.titles&&this.titles.draw(t);for(var n=0;nthis.lyricLineBaseline&&(this.lyricLineBaseline=o.lyrics[0].origin.y),o.lyrics.length>this.numLyricLines&&(this.numLyricLines=o.lyrics.length)),o.alText&&this.numAltLinesthis.altLineHeight&&(this.altLineHeight=o.alText[0].bounds.height),o.alText[0].origin.y>this.altLineBaseline&&(this.altLineBaseline=o.alText[0].origin.y),o.alText.length>this.numAltLines&&(this.numAltLines=o.alText.length)),o.translationText&&o.translationText[0]&&o.translationText[0].text&&(o.translationText[0].origin.y>this.translationLineBaseline&&(this.translationLineBaseline=o.translationText[0].origin.y),o.translationText.length>this.numTranslationLines&&(this.numTranslationLines=o.translationText.length));for(this.custos&&this.notationBounds.union(this.custos.bounds),e=0;ethis.lyricLineHeight&&(this.extraTextOnlyHeight=this.lyricLineHeight)}else{var p=null,d=0;a=(this.numLyricLines-1)*this.lyricLineHeight,a+=this.numTranslationLines*this.translationLineHeight;var g=0;for(e=this.extraTextOnlyIndex;e0){var v=new c.Rect(0,r,0,this.lyricLineHeight*this.numLyricLines+this.extraTextOnlyHeight+this.translationLineHeight*this.numTranslationLines);this.notationBounds.union(v)}if(this.numAltLines>0){var m=new c.Rect(0,this.notationBounds.y-this.altLineHeight-.5*t.staffInterval-1.1*t.textStyles.al.size*(this.numAltLines-1),0,1.1*t.textStyles.al.size*this.numAltLines);this.notationBounds.union(m)}this.notationBounds.union(new c.Rect(0,0,0,(3+t.staffLineWeight/2+t.minSpaceBelowStaff)*t.staffInterval));var b=this.notationBounds.height;this.bounds.x=0,this.bounds.y=this.notationBounds.y,this.bounds.width=this.notationBounds.right(),this.bounds.height=b,this.origin=new c.Point(this.staffLeft,-this.notationBounds.y)}},{key:"layoutInsertionCursor",value:function(t){return this.insertionCursor&&(this.insertionCursor.performLayout(t),this.insertionCursor.bounds.x=this.score.insertionElement.bounds.right()+(this.score.insertionElement.trailingSpace&&this.score.insertionElement.calculatedTrailingSpace||0)/2-this.insertionCursor.origin.x),this.insertionCursor}},{key:"draw",value:function(t){var e=t.canvasCtxt;e.translate(this.bounds.x,this.bounds.y);var i,n,s=this.staffLeft,o=this.staffRight;for(e.lineWidth=t.staffLineWeight,e.strokeStyle=t.staffLineColor,i=-3;i<=3;i+=2)n=t.staffInterval*i,e.beginPath(),e.moveTo(s,n),e.lineTo(o,n),e.stroke();for(this.layoutInsertionCursor(t)&&this.insertionCursor.draw(t),i=0;i1&&void 0!==arguments[1]?arguments[1]:0,arguments.length>2&&void 0!==arguments[2]?arguments[2]:{quickSvg:"createNode",elements:"createSvgNode"}),n=[],s=this.staffLeft,o=this.staffRight;for(t.editable&&n.push(f.QuickSvg[i.quickSvg]("rect",{key:"insertion",x:s,y:t.staffInterval*-3,width:o-s,height:6*t.staffInterval,fill:"none"})),e=-3;e<=3;e+=2)n.push(f.QuickSvg[i.quickSvg]("line",{key:e,x1:s,y1:t.staffInterval*e,x2:o,y2:t.staffInterval*e,stroke:t.staffLineColor,"stroke-width":t.staffLineWeight,class:"staffLine"}));for(n=[f.QuickSvg[i.quickSvg]("g",{class:"staffLines"},n)],this.layoutInsertionCursor(t)&&n.push(this.insertionCursor[i.elements](t)),e=0;e1&&void 0!==arguments[1]?arguments[1]:0,i=this.getInnerNodes(t,e,{quickSvg:"createNode",elements:"createSvgNode"});return f.QuickSvg.createNode("g",{class:"chantLine",transform:"translate("+this.bounds.x+","+(this.bounds.y-e)+")","element-index":this.elementIndex,source:this},i)}},{key:"createSvgTree",value:function(t){var e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:0,i=this.getInnerNodes(t,e,{quickSvg:"createSvgTree",elements:"createSvgTree"});return f.QuickSvg.createSvgTree.apply(f.QuickSvg,["g",{class:"chantLine",transform:"translate("+this.bounds.x+","+(this.bounds.y-e)+")","element-index":this.elementIndex}].concat(n(i)))}},{key:"createSvgFragment",value:function(t){var e,i=arguments.length>1&&void 0!==arguments[1]?arguments[1]:0,n="",s=this.staffLeft,o=this.staffRight;for(e=-3;e<=3;e+=2)n+=f.QuickSvg.createFragment("line",{x1:s,y1:t.staffInterval*e,x2:o,y2:t.staffInterval*e,stroke:t.staffLineColor,"stroke-width":t.staffLineWeight,class:"staffLine"});for(n=f.QuickSvg.createFragment("g",{class:"staffLines"},n),this.layoutInsertionCursor(t)&&(n+=this.insertionCursor.createSvgFragment(t)),e=0;e0?this.staffRight=i:this.staffRight=1/0,0===this.notationsStartIndex){var c=0;null!==this.score.dropCap&&(c=this.score.dropCap.bounds.width+2*this.score.dropCap.padding),null===this.score.annotation||this.score.mergeAnnotationWithTextLeft&&!this.score.dropCap||(c=Math.max(c,this.score.annotation.bounds.width+2*this.score.annotation.padding)),this.staffLeft+=c,null!==this.score.dropCap&&(this.paddingLeft=(c-this.score.dropCap.bounds.width)/2)}else if(o=n[e-1],o.constructor===l.DoubleBar&&o.hasLyrics()&&(o.lyrics.length>1||!o.lyrics[0].text.match(/^(i\.?)+j\.?/))){s=o.lyrics.map(function(e){var i=new f.Lyric(t,e.originalText,e.lyricType,e.notation,e.notations,e.sourceIndex);return i.elidesToNext=e.elidesToNext,e.bounds.y=Number.MAX_SAFE_INTEGER,i});var d=s.map(function(t){return t.bounds.x}).reduce(function(t,e){return t1&&!r.keepWithNext&&r.bounds.right()>=m;w=w||null!==this.extraTextOnlyIndex&&g.constructor!==u.TextOnly&&g.constructor!==u.ChantLineBreak&&g.constructor!==l.Custos&&g.hasLyrics(),g instanceof u.TextOnly&&o===r&&(S=this.lastLyrics.slice(),L=y),g instanceof u.TextOnly&&n[L]&&!n[L].hasLyrics()&&(L=y),g.hasLyrics()&&g.lyrics[0].needsLayout&&g.lyrics[0].recalculateMetrics(t);var P,k=!w&&this.positionNotationElement(t,this.lastLyrics,r,g,C,this.extraTextOnlyIndex?[]:h),T=t.useExtraTextOnly&&g.constructor===u.TextOnly&&f.LyricArray.hasOnlyOneLyric(g.lyrics)&&(k===!1||null!==this.extraTextOnlyIndex);if(T&&null===this.extraTextOnlyIndex&&(P=f.LyricArray.indexOfLyric(g.lyrics),L===y)){var O=n[y].lyrics[P].text;if(O.length<=1){var _=n[y+1];T=_&&_.constructor===u.TextOnly&&_.lyrics[P]&&_.lyrics[P].text.length>0}}if(T){var N;if(P=this.extraTextOnlyLyricIndex,null===this.extraTextOnlyIndex&&n[L].lyrics.length){if(L===this.notationsStartIndex||!t.startExtraTextOnlyFromFirst){L=y;var A=n.slice(this.notationsStartIndex,y).reverse().find(function(t){return t.hasLyrics()});S=A&&A.lyrics.slice()||[]}this.extraTextOnlyIndex=L,P=this.extraTextOnlyLyricIndex=f.LyricArray.indexOfLyric(g.lyrics),this.lastLyricsBeforeTextOnly=S,this.lastLyrics=[],y=L-1,this.numNotationsOnLine=L-this.notationsStartIndex;continue}if(delete g.lyrics[P].lineWidth,!k||y===this.extraTextOnlyIndex){g.bounds.x=g.lyrics[P].origin.x;var M=t.startExtraTextOnlyFromFirst?f.LyricArray.getRight(this.lastLyrics)+(t.minLyricWordSpacing||0):0;g.lyrics[P].setMaxWidth(t,this.staffRight,this.staffRight-M),N=g}N&&(N.lyrics[P].lineWidth=g.lyrics[P].getRight())}else if(k===!1){for(var I=function(t){var e=n[t];if(e.constructor!==u.TextOnly)return!1;var i=n.slice(t+1).findIndex(function(t){return t.isDivider});return!(i<0)&&n.slice(t+1,t+1+i).every(function(t){return t.constructor===u.TextOnly})};this.numNotationsOnLine>1&&(g.isDivider||g.constructor===l.Custos||I(y));)g=n[--y],this.numNotationsOnLine--,this.lastLyricsBeforeTextOnly&&I(y)&&delete this.lastLyricsBeforeTextOnly;var B=n.slice(y+1),E=0,D=0;for(t.minSyllablesLastLine&&t.minNotesLastLine&&(E=B.filter(function(t){return t.hasLyrics()}).length,D=B.flatMap(function(t){return t.notes}).filter(function(t){return!!t}).length),v=y-1;v>this.notationsStartIndex;v--){var F=n[v];if(g=n[v+1],t.minSyllablesLastLine&&t.minNotesLastLine&&(E+=g.hasLyrics()?1:0,D+=(g.notes||[]).length),F.firstWithNoWidth)this.numNotationsOnLine--;else if(b)this.numNotationsOnLine--,F===b&&(b=null);else if(!g||!g.notes||g.notes[0].shape!==u.NoteShape.Quilisma&&g.notes[0].shape!==u.NoteShape.Inclinatum)if(Et.staffInterval*t.maxExtraSpaceInStaffIntervals&&(f.LyricArray.mergeInArray(a,n.slice(this.notationsStartIndex+this.numNotationsOnLine,this.notationsStartIndex+this.maxNumNotationsOnLine)),this.numNotationsOnLine=this.maxNumNotationsOnLine,delete this.maxNumNotationsOnLine)}var j=this.score.notations[null===this.extraTextOnlyIndex?this.notationsStartIndex+this.numNotationsOnLine:this.extraTextOnlyIndex];if(j&&j.hasLyrics()&&(j.lyrics[0].lyricType===f.LyricType.BeginningSyllable||j.lyrics[0].lyricType===f.LyricType.SingleSyllable)&&this.toJustify.push(this.custos),v>=1&&n[v].isDivider&&n[v-1].constructor===l.Custos){for(a=[],y=v-2;y>=this.notationsStartIndex;y--)if(n[y].hasLyrics()){f.LyricArray.mergeIn(a,n[y].lyrics);break}h.sum-=h.pop().condensable,h.sum-=h.pop().condensable,this.positionNotationElement(t,a,n[v-2],n[v],this.staffRight,h),this.custos=n[v-1],this.custos.bounds.x=this.staffRight-this.custos.bounds.width-this.custos.leadingSpace}break}if(g.hasLyrics()&&f.LyricArray.mergeIn(this.lastLyrics,g.lyrics),b&&g===b.translationText[0].endNeume?b=null:g.translationText&&g.translationText.length&&g.translationText[0].endNeume&&(b=g),g.line=this,this.numNotationsOnLine++,g.isClef&&(t.activeClef=g),g.constructor===u.ChantLineBreak&&i>0){this.justify=g.justify||null!==this.extraTextOnlyIndex||this.getWhitespaceOnRight(t)<0,this.justify&&this.findNeumesToJustify(a);break}g.constructor===l.Custos?this.custos=g:g.isNeume&&(this.custos=null)}for(var V=this.notationsStartIndex+this.numNotationsOnLine-1,G=n[V]||{};V>0&&(G.constructor===u.ChantLineBreak||G.constructor===l.Custos||G.constructor===u.TextOnly);)G=n[--V];var H=this.notationsStartIndex+this.numNotationsOnLine===n.length;if((this.justify&&null!==this.extraTextOnlyIndex||i>0&&H)&&(this.toJustify||this.findNeumesToJustify(a),this.justify=(!H||G.isDivider)&&this.getWhitespaceOnRight(t)/(this.toJustify.length||1)<=t.staffInterval*t.maxExtraSpaceInStaffIntervals),!this.custos)for(y=this.notationsStartIndex+this.numNotationsOnLine;y0){var R=this.getWhitespaceOnRight(),W=this.staffRight;R<0&&(W-=R)}for(y=0;this.lastLyrics&&this.lastLyrics[y];){var Q=this.lastLyrics[y];if(Q.allowsConnector()&&(Q.setNeedsConnector(!0,0),i>0&&t.minLyricWordSpacing1?t.intraNeumeSpacing:t.minLyricWordSpacing);Q.setConnectorWidth(U)}++y}i<=0&&(this.staffRight=n[this.notationsStartIndex+this.numNotationsOnLine-1].bounds.right(),this.justify=!1),this.justifyElements(t,this.justify,h),this.centerDividers(),this.finishLayout(t)}},{key:"centerDividers",value:function(){for(var t,e=null===this.extraTextOnlyIndex?this.notationsStartIndex+this.numNotationsOnLine:this.extraTextOnlyIndex,i=this.notationsStartIndex;i=0;n--)t.lyrics[n].bounds.x+=p,t.lyrics[n].needsLayout=!0}}else i!==e-1||!this.justify||t.constructor!==l.DoubleBar&&t.constructor!==l.FullBar||(t.bounds.x=this.staffRight-t.bounds.width)}}},{key:"findNeumesToJustify",value:function(t){this.toJustify=[];for(var e,i=null,n=null,s=null,o=this.notationsStartIndex+this.numNotationsOnLine,r=this.notationsStartIndex;r=this.extraTextOnlyIndex&&i.constructor===u.TextOnly||null!==e&&(f.LyricArray.mergeIn(t,e.lyrics),e.keepWithNext===!0)||!i.isDivider&&t.length&&t[0].allowsConnector()&&a||s.constructor!==u.ChantLineBreak&&(s!==this.custos||a)&&(0===r&&this.score.useDropCap&&a||this.toJustify.push(i)))}return null!==s&&f.LyricArray.mergeIn(t,s.lyrics),s}},{key:"getWhitespaceOnRight",value:function(t){var e=this.score.notations,i=this.notationsStartIndex+this.numNotationsOnLine,n=e[i-1];null!==this.extraTextOnlyIndex&&n.constructor===u.TextOnly&&(i=this.extraTextOnlyIndex,n=e[i-1]);var s=n?n.bounds.right()+n.calculatedTrailingSpace:0,o=this.lastLyricsBeforeTextOnly||this.lastLyrics,r=o.length?f.LyricArray.getRight(o):0;return this.custos?(s+=this.custos.bounds.width+this.custos.leadingSpace,this.custos.hasLyrics()&&(r=f.LyricArray.getRight(this.custos.lyrics))):t&&i0){for(n=0;this.lastLyrics&&this.lastLyrics[n];){var l=this.lastLyrics[n];if(l.allowsConnector()){var c=l.getConnectorWidth();if(t.minLyricWordSpacing1?t.intraNeumeSpacing:t.minLyricWordSpacing);l.setConnectorWidth(p)}}++n}this.custos.bounds.x=a.bounds.right()+a.calculatedTrailingSpace}var d=this.getWhitespaceOnRight();if(!(Math.abs(d)<.5||d>0&&(e&&0===s.length||!e))){this.condensableSpaces=i;var g,y,v=0,m=d/s.length,b=0,x=0;d<0&&(s=i.filter(function(t){return t.condensable>0}),b=d/i.sum,m=0);var S=s[x++],L=!1;for(n=this.notationsStartIndex;n=this.extraTextOnlyIndex&&g.constructor===u.TextOnly||(b||g!==this.custos?(b?S&&S.notation===g&&(v+=b*S.condensable,S=s[x++]):S===g?(y.hasNoWidth?L=!0:v+=m,S=s[x++]):L&&!y.hasNoWidth&&(L=!1,v+=m),g.bounds.x+=v):g.hasLyrics()?(g.bounds.x=Math.min(g.bounds.x+(this.staffRight-f.LyricArray.getRight(g.lyrics)),this.staffRight-g.bounds.width),v+=m):g.bounds.x=Math.min(g.bounds.x+v,this.staffRight-g.bounds.width));h>0&&(this.custos.bounds.x=a.bounds.right()+a.calculatedTrailingSpace)}}},{key:"handleEndBrace",value:function(t,e,i){var s=t.lastStartBrace;if(s){var o,r=s.notationIndex,a=this.score.notations,u=t.intraNeumeSpacing/2,l=s.note;o=s.isAbove?Math.min.apply(Math,[t.calculateHeightFromStaffPosition(4)].concat(n([l,e].concat(a.slice(r,i+1)).map(function(t){return t.bounds.y-u})))):Math.max.apply(Math,[t.calculateHeightFromStaffPosition(-4)].concat(n([l,e].concat(a.slice(r,i+1)).map(function(t){return t.bounds.bottom()+u}))));var c=!1;s.shape===h.BraceShape.RoundBrace?this.braces.push(new f.RoundBraceVisualizer(t,s.getAttachmentX(l),e.braceEnd.getAttachmentX(e),o,s.isAbove)):(s.shape===h.BraceShape.AccentedCurlyBrace&&(c=!0),this.braces.push(new f.CurlyBraceVisualizer(t,s.getAttachmentX(l),e.braceEnd.getAttachmentX(e),o,s.isAbove,c))),delete t.lastStartBrace}}},{key:"finishLayout",value:function(t){var e=this;this.ledgerLines=[];for(var i=this.score.notations,s=this.notationsStartIndex+this.numNotationsOnLine,o=function(i){var n=arguments.length>1&&void 0!==arguments[1]?arguments[1]:i,s=arguments.length>2&&void 0!==arguments[2]?arguments[2]:i.staffPosition,o=arguments.length>3&&void 0!==arguments[3]?arguments[3]:i.neume?i.neume.bounds.x:0;if(s>=5||s<=-5){var r=o+i.bounds.x-t.intraNeumeSpacing,a=o+n.bounds.x+n.bounds.width+t.intraNeumeSpacing;s-=s>0?(s-1)%2:(s+1)%2;var u=t.staffInterval*t.minLedgerSeparation;if(e.ledgerLines.length>0&&e.ledgerLines[e.ledgerLines.length-1].x2+u>=r){var h=(r-e.ledgerLines[e.ledgerLines.length-1].x2)/2;e.ledgerLines[e.ledgerLines.length-1].x2+=h,r-=h}a>e.staffRight&&(a=e.staffRight),e.ledgerLines.push({x1:r,x2:a,staffPosition:s})}},r=[],a=null,u=Number.MAX_VALUE,c=Number.MIN_VALUE,p=function(i,n,s){i.setMaxWidth(t,e.staffRight),i.bounds.x=0,s&&(i.bounds.x=(i.bounds.x+s-i.bounds.width)/2);var o=n.bounds.x+i.bounds.right()-e.staffRight;o>0&&(i.bounds.x-=o),n.bounds.x+i.bounds.x<0&&(i.bounds.x=-n.bounds.x)},d=this.notationsStartIndex;d0&&(C=g.bounds.x+L.bounds.x-(r[r.length-1].note.neume.bounds.x+r[r.length-1].bounds.right())),0===r.length||r[r.length-1].positionHint!==L.positionHint||r[r.length-1].terminating===!0||r[r.length-1].alignment===h.HorizontalEpisemaAlignment.Left||r[r.length-1].alignment===h.HorizontalEpisemaAlignment.Center||L.alignment===h.HorizontalEpisemaAlignment.Right||L.alignment===h.HorizontalEpisemaAlignment.Center||C>2*t.intraNeumeSpacing&&S.glyphVisualizer.glyphCode!==f.GlyphCode.None)r=[L];else{var w;if(w=L.positionHint===f.MarkingPositionHint.Below?Math.max(L.bounds.y,r[r.length-1].bounds.y):Math.min(L.bounds.y,r[r.length-1].bounds.y),L.bounds.y!==w)L.bounds.y=w;else for(var P=0;P5&&void 0!==arguments[5]?arguments[5]:[];o.hasOwnProperty("sum")||(o.sum=0);var r,a={notation:n},h=!1;if(n.hasNoWidth&&n.firstWithNoWidth!==n||!i.firstWithNoWidth?n.bounds.x=i.bounds.right():(n.bounds.x=i.firstWithNoWidth.bounds.x,h=!0),n.constructor===u.TextOnly&&null===this.extraTextOnlyIndex||!n.hasLyrics()&&i.calculatedTrailingSpace<0?(n.calculatedTrailingSpace=i.calculatedTrailingSpace,n.hasLyrics()&&(n.calculatedTrailingSpace-=n.lyrics[0].bounds.width),n.constructor===u.TextOnly&&1===n.lyrics.length&&n.lyrics[0].setMaxWidth(t,this.staffRight,this.staffRight-f.LyricArray.getRight(e)-t.minLyricWordSpacing)):h||(n.bounds.x+=i.calculatedTrailingSpace),n.hasLyrics()&&!i.isDivider&&!i.isAccidental&&this.numNotationsOnLine>0&&(n.lyrics[0].lyricType===f.LyricType.SingleSyllable||n.lyrics[0].lyricType===f.LyricType.BeginningSyllable)&&(n.bounds.x+=t.intraNeumeSpacing*t.interVerbalMultiplier),n.hasNoWidth||h?a.total=a.condensable=0:null!==this.extraTextOnlyIndex&&n.constructor===u.TextOnly?(n.bounds.x=0,a.total=a.condensable=0):(a.total=n.bounds.x-i.bounds.right(),a.condensable=a.total*t.condensingTolerance),0===e.length){var l=n.bounds.right()+n.calculatedTrailingSpace;for(r=0;rs+o.sum+a.condensable)&&(o.push(a),o.sum+=a.condensable,!0)}if(n.firstOfSyllable&&e.length&&!n.hasLyrics()&&(n.bounds.x=Math.max(n.bounds.x,e[0].getRight()),a.total=n.bounds.x-i.bounds.right(),a.condensable=a.total*t.condensingTolerance),n.hasLyrics()===!1)return!(n.bounds.right()+n.calculatedTrailingSpace>s+o.sum+a.condensable)&&(o.push(a),o.sum+=a.condensable,!0);do{var g=!1,y=!1;for(r=0;r=0?(m=o.slice(x+1),m.sum=m.map(function(t){return t.condensable}).reduce(function(t,e){return t+e},0)):m.sum=0}n.lyrics[r].setNeedsConnector(!1);var S=n.lyrics[r].getLeft();if(e[r]&&e[r].allowsConnector()!==!1)if(v+.1>S-m.sum-a.condensable){var L=v-S;L<-.1&&!function(){var t=L/(m.sum+a.condensable),e=0;m.forEach(function(i){e+=t*i.condensable,i.notation.bounds.x+=e})}(),n.bounds.x+=L,b=0,y=!0,g=L>.5}else{if(t.minLyricWordSpacing1?t.intraNeumeSpacing:t.minLyricWordSpacing;e[r].setConnectorWidth(Math.max(w,C))}}if(e[r].setNeedsConnector(!0),v=e[r].getRight(),v+.1>S){var P=v-S;n.bounds.x+=P,b=0,g=P>.5}else b=S-v}else{var k=S-v-t.minLyricWordSpacing;if(k<0){var T=v+t.minLyricWordSpacing-S;n.bounds.x+=T,b=0,g=T>.5}else b=k}null!==b&&b1&&g&&y);for(r=Math.min(n.lyrics.length,e.length)-1;r>=0;r--){var O=e[r];O.needsConnector&&O.connectorWidth&&(S=n.lyrics[r].getLeft(),v=O.getRight()-O.connectorWidth,C=S-v,C>=t.hyphenWidth&&(C=0),O.setConnectorWidth(C))}if(n.bounds.right()+n.calculatedTrailingSpace.1){var N=o[o.length-1];o.sum-=N.condensable,N.condensable=0}}return o.push(a),o.sum+=a.condensable,!0}return!1}},{key:"bisectNotationAtX",value:function(t){for(var e=!(arguments.length>1&&void 0!==arguments[1])||arguments[1],i=-1,n=Math.min(this.numNotationsOnLine,1/0),s=i+(n-i>>1),o=this.score.notations.slice(this.notationsStartIndex,this.notationsStartIndex+this.numNotationsOnLine);it?n=s:i=s,s=i+(n-i>>1)}var u=o[s];if(e&&u&&0===u.bounds.width&&s+12&&void 0!==arguments[2]?arguments[2]:u.GlyphCode.AcuteAccent;n(this,e);var r=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,o));return r.note=i,r.positionHint=u.MarkingPositionHint.Above,r}return o(e,t),r(e,[{key:"performLayout",value:function(t){this.bounds.x=this.note.bounds.x+this.bounds.width/2,this.setStaffPosition(t,Math.max(this.note.staffPosition+1,4))}}]),e}(u.GlyphVisualizer),e.HorizontalEpisemaAlignment={Default:0,Left:1,Center:2,Right:3}),l=(e.HorizontalEpisema=function(t){function e(t){n(this,e);var i=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));return i.note=t,i.positionHint=u.MarkingPositionHint.Default,i.terminating=!1,i.alignment=h.Default,i}return o(e,t),r(e,[{key:"performLayout",value:function(t){var e,i=0,n=.25*t.staffInterval,s=this.note.glyphVisualizer.glyphCode,o=this.note.neume.ledgerLines[0]||{},r=!1;if(s===u.GlyphCode.PunctumInclinatum){var a=this.note.neume.notes,l=a.indexOf(this.note),c=a[l-1];c&&c.glyphVisualizer.glyphCode===u.GlyphCode.PunctumInclinatum&&c.staffPosition-this.note.staffPosition===1&&(r=!0)}this.positionHint===u.MarkingPositionHint.Below?(i=this.note.bounds.bottom()+n,s===u.GlyphCode.None&&(i+=t.staffInterval/2),e=Math.ceil(i/t.staffInterval),e%2===0?e=(e+.75+(i-n)/t.staffInterval)/2:(e=(2*Math.ceil(1.5*i/t.staffInterval-.5)+1)/3,Math.abs(e)%2===1&&(e+=Math.abs(e)<4||o.staffPosition===-e?2/3:1/3))):(i=this.note.bounds.y-n,e=Math.floor(i/t.staffInterval),e%2===0?e=(e-.75+(i+n)/t.staffInterval)/2:(e=(2*Math.floor(1.5*i/t.staffInterval-.5)+1)/3,Math.abs(e)%2===1&&(e-=Math.abs(e)<4||o.staffPosition===-e?2/3:1/3))),i=e*t.staffInterval;var f=this.note.bounds.width,p=this.note.bounds.x;s===u.GlyphCode.Porrectus1||s===u.GlyphCode.Porrectus2||s===u.GlyphCode.Porrectus3||s===u.GlyphCode.Porrectus4?f=t.staffInterval:s===u.GlyphCode.None?(f=t.staffInterval,p-=f):r?(f*=2/3,p+=.5*f):s===u.GlyphCode.PunctumInclinatumLiquescent&&(f*=2/3,p+=.25*f),this.alignment===h.Left?f*=.8:this.alignment===h.Center?(p+=.1*f,f*=.8):this.alignment===h.Right&&(p+=.2*f,f*=.8),this.bounds.x=p,this.bounds.y=i-t.episemaLineWeight/2,this.bounds.width=f,this.bounds.height=t.episemaLineWeight,this.origin.x=0,this.origin.y=0}},{key:"draw",value:function(t){var e=t.canvasCtxt;e.fillStyle=t.neumeLineColor,e.fillRect(this.bounds.x,this.bounds.y,this.bounds.width,this.bounds.height)}},{key:"getSvgProps",value:function(t){return{x:this.bounds.x,y:this.bounds.y,width:this.bounds.width,height:this.bounds.height,fill:t.neumeLineColor,class:"horizontalEpisema"}}},{key:"createSvgNode",value:function(t){return u.QuickSvg.createNode("rect",this.getSvgProps(t))}},{key:"createSvgTree",value:function(t){return u.QuickSvg.createSvgTree("rect",this.getSvgProps(t))}},{key:"createSvgFragment",value:function(t){return u.QuickSvg.createFragment("rect",this.getSvgProps(t))}}]),e}(u.ChantLayoutElement),e.Ictus=function(t){function e(t,i){n(this,e);var o=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,u.GlyphCode.VerticalEpisemaAbove));return o.note=i,o.positionHint=u.MarkingPositionHint.Default,o}return o(e,t),r(e,[{key:"performLayout",value:function(t){var e,i=this.note.glyphVisualizer.glyphCode,n=this.positionHint||u.MarkingPositionHint.Below,s=this.note.staffPosition+(n===u.MarkingPositionHint.Above?1:-1),o=this.note.episemata.length>0&&(this.note.episemata[0].positionHint||u.MarkingPositionHint.Above)===n,r=1,a=-.2,h=0,l=s%2&&(Math.abs(s)<4||(this.note.neume.ledgerLines[0]||{}).staffPosition===s);i===u.GlyphCode.Porrectus1||i===u.GlyphCode.Porrectus2||i===u.GlyphCode.Porrectus3||i===u.GlyphCode.Porrectus4?e=t.staffInterval/2:i===u.GlyphCode.None?e=-t.staffInterval/2:(e=this.note.bounds.width/2,i!==u.GlyphCode.PunctumInclinatum||l||o||(h=.3)),this.positionHint===u.MarkingPositionHint.Above?(i=u.GlyphCode.VerticalEpisemaAbove,r*=-1):i=u.GlyphCode.VerticalEpisemaBelow,o&&(h=.4),r*=t.staffInterval*(h+(l?.3:a)),this.setGlyph(t,i),this.setStaffPosition(t,s),this.bounds.x=this.note.bounds.x+e-this.origin.x,this.bounds.y+=r}}]),e}(u.GlyphVisualizer),e.Mora=function(t){function e(t,i){n(this,e);var o=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this,t,u.GlyphCode.Mora));return o.note=i,o.positionHint=u.MarkingPositionHint.Default,o.horizontalOffset=t.staffInterval/2+o.origin.x,o}return o(e,t),r(e,[{key:"performLayout",value:function(t){this.setGlyph(t,this.glyphCode),this.horizontalOffset=t.staffInterval/2+this.origin.x;var e=this.note.staffPosition;this.setStaffPosition(t,e);var i,n=0,s=this.note.neume.notes.indexOf(this.note);if(s>=0)if(++s,this.note.neume.notes.length>s)i=this.note.neume.notes[s],i.morae&&i.morae.length&&this.note.neume.notes.length===s+1?this.horizontalOffset+=i.bounds.right()-this.note.bounds.right():i.bounds.right()>this.note.bounds.right()?this.horizontalOffset=(i.bounds.right()-this.note.bounds.right()-this.bounds.right())/2:i=null;else if(this.note.neume.notes.length===s)if(0===this.note.neume.trailingSpace){var o=this.note.neume.score.notations.indexOf(this.note.neume);if(o>=0){var r=this.note.neume.score.notations[o+1];r&&r.notes&&(i=r.notes[0])}}else this.note.shape!==a.NoteShape.Inclinatum&&(this.note.neume.calculatedTrailingSpace+=this.origin.x);this.positionHint===u.MarkingPositionHint.Above?n-=e%2===0?1.75*t.staffInterval:.75*t.staffInterval:this.positionHint===u.MarkingPositionHint.Below?n+=e%2===0?1.75*t.staffInterval:.75*t.staffInterval:e%2===0?i&&i.staffPosition===e-1&&(n-=.25*t.staffInterval):n-=.75*t.staffInterval,this.bounds.x=this.horizontalOffset+this.note.bounds.right(),this.bounds.y+=n}}]),e}(u.GlyphVisualizer),e.BraceShape={RoundBrace:0,CurlyBrace:1,AccentedCurlyBrace:2},e.BraceAttachment={Left:0,Right:1});e.BracePoint=function(t){function e(t,i,o,r){n(this,e);var a=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));return a.note=t,a.isAbove=i,a.shape=o,a.attachment=r,a}return o(e,t),r(e,[{key:"getAttachmentX",value:function(t){return t||(t=this.note),this.attachment===l.Left?(t.neume?t.neume.bounds.x:0)+t.bounds.x:(t.neume?t.neume.bounds.x:0)+t.bounds.right()}}]),e}(u.ChantLayoutElement)},function(t,e,i){"use strict";function n(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function s(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function o(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(e,"__esModule",{value:!0}),e.Virgula=e.Accidental=e.AccidentalType=e.DoubleBar=e.DominicanBar=e.InsertionCursor=e.FullBar=e.HalfBar=e.QuarterBar=e.Divider=e.Custos=void 0;var r=function(){function t(t,e){for(var i=0;i0&&void 0!==arguments[0]&&arguments[0];n(this,e);var i=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));return i.auto=t,i.staffPosition=0,i}return o(e,t),r(e,[{key:"performLayout",value:function(t){if(a(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"performLayout",this).call(this,t),this.auto){var i=t.findNextNeume();for(i&&(this.staffPosition=t.activeClef.pitchToStaffPosition(i.notes[0].pitch));this.staffPosition<-6;)this.staffPosition+=7;for(;this.staffPosition>6;)this.staffPosition-=7}var n=new h.GlyphVisualizer(t,e.getGlyphCode(this.staffPosition));n.setStaffPosition(t,this.staffPosition),this.addVisualizer(n),this.finishLayout(t)}},{key:"resetDependencies",value:function(){this.auto&&(this.needsLayout=!0)}}],[{key:"getGlyphCode",value:function(t){return t<=2?Math.abs(t)%2===1?h.GlyphCode.CustosLong:h.GlyphCode.CustosShort:Math.abs(t)%2===1?h.GlyphCode.CustosDescLong:h.GlyphCode.CustosDescShort}}]),e}(h.ChantNotationElement),e.Divider=function(t){function e(){n(this,e);var t=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));return t.isDivider=!0,t.resetsAccidentals=!0,t}return o(e,t),e}(h.ChantNotationElement)),c=(e.QuarterBar=function(t){function e(){return n(this,e),s(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return o(e,t),r(e,[{key:"performLayout",value:function(t){a(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"performLayout",this).call(this,t),this.addVisualizer(new h.DividerLineVisualizer(t,2,4,this)),this.origin.x=this.bounds.width/2,this.finishLayout(t)}}]),e}(l),e.HalfBar=function(t){function e(){return n(this,e),s(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return o(e,t),r(e,[{key:"performLayout",value:function(t){a(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"performLayout",this).call(this,t),this.addVisualizer(new h.DividerLineVisualizer(t,-2,2,this)),this.origin.x=this.bounds.width/2,this.finishLayout(t)}}]),e}(l),e.FullBar=function(t){function e(){return n(this,e),s(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return o(e,t),r(e,[{key:"performLayout",value:function(t){a(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"performLayout",this).call(this,t),this.addVisualizer(new h.DividerLineVisualizer(t,-3,3,this)),this.origin.x=this.bounds.width/2,this.finishLayout(t)}}]),e}(l),e.InsertionCursor=function(t){function e(){return n(this,e),s(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return o(e,t),r(e,[{key:"performLayout",value:function(t){a(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"performLayout",this).call(this,t),this.addVisualizer(new h.DividerLineVisualizer(t,-4,4)),this.origin.x=this.bounds.width/2,this.bounds.width=0,this.bounds.height=0,this.finishLayout(t)}}]),e}(l),e.DominicanBar=function(t){function e(t){n(this,e);var i=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));t--;var o=t%2;return i.staffPosition=t-2*o,i}return o(e,t),r(e,[{key:"performLayout",value:function(t){a(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"performLayout",this).call(this,t),this.addVisualizer(new h.DividerLineVisualizer(t,this.staffPosition-3,this.staffPosition,this)),this.origin.x=this.bounds.width/2,this.finishLayout(t)}}]),e}(l),e.DoubleBar=function(t){function e(){return n(this,e),s(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return o(e,t),r(e,[{key:"performLayout",value:function(t){a(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"performLayout",this).call(this,t);var i=new h.DividerLineVisualizer(t,-3,3,this);i.bounds.x=0,this.addVisualizer(i);var n=new h.DividerLineVisualizer(t,-3,3,this);n.bounds.x=2*t.intraNeumeSpacing-n.bounds.width,this.addVisualizer(n),this.origin.x=this.bounds.width/2,this.finishLayout(t)}}]),e}(l),e.AccidentalType={Flat:-1,Natural:0,Sharp:1});e.Accidental=function(t){function e(t,i){n(this,e);var o=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));return o.isAccidental=!0,o.keepWithNext=!0,o.staffPosition=t,o.accidentalType=i,o}return o(e,t),r(e,[{key:"performLayout",value:function(t){a(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"performLayout",this).call(this,t),this.addVisualizer(this.createGlyphVisualizer(t)),this.finishLayout(t)}},{key:"createGlyphVisualizer",value:function(t){var e=h.GlyphCode.Flat;switch(this.accidentalType){case c.Natural:e=h.GlyphCode.Natural;break;case c.Sharp:e=h.GlyphCode.Sharp;break;default:e=h.GlyphCode.Flat}var i=new h.GlyphVisualizer(t,e);return i.setStaffPosition(t,this.staffPosition),i}},{key:"adjustStep",value:function(t){switch(this.accidentalType){case c.Flat:if(t===u.Step.Ti)return u.Step.Te;if(t===u.Step.Mi)return u.Step.Me;break;case c.Sharp:if(t===u.Step.Do)return u.Step.Du;if(t===u.Step.Fa)return u.Step.Fu;break;case c.Natural:if(t===u.Step.Te)return u.Step.Ti;if(t===u.Step.Me)return u.Step.Mi;if(t===u.Step.Du)return u.Step.Do;if(t===u.Step.Fu)return u.Step.Fa}return t}},{key:"applyToPitch",value:function(t){this.pitch.octave===t.octave&&(t.step=this.adjustStep(t.step))}}]),e}(h.ChantNotationElement),e.Virgula=function(t){function e(){n(this,e);var t=s(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));return t.resetsAccidentals=!1,t.staffPosition=3,t}return o(e,t),r(e,[{key:"performLayout",value:function(t){a(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"performLayout",this).call(this,t);var i=new h.GlyphVisualizer(t,h.GlyphCode.Virgula);i.setStaffPosition(t,this.staffPosition),this.addVisualizer(i),this.origin.x=this.bounds.width/2,this.finishLayout(t)}}]),e}(l)},function(t,e,i){"use strict";function n(t){if(t&&t.__esModule)return t;var e={};if(null!=t)for(var i in t)Object.prototype.hasOwnProperty.call(t,i)&&(e[i]=t[i]);return e.default=t,e}function s(t){if(Array.isArray(t)){for(var e=0,i=Array(t.length);e[\s\S]*<\/v>|[^(])*)(?:\(?([^)]*)\)?)?/g,v=/(.*?)<\/alt>|\[(alt:)?(.*?)\]/g,m=/z0|z|Z|::|:|[,;][1-6]?|`|[cf][1-4]|cb[1-4]|\/+| |\!|-?[a-mA-M][oOwWvVrRsxy#~\+><_\.'012345]*(?:\[[^\]]*\]?)*|\{([^}]+)\}?/g,b=1,x=/^([a-z]+):(.*)/,S=/([ou])(b|cb|cba):([01])(?:([{}])|;(\d*(?:\.\d+)?)mm)/,L=function(t){return t.intraNeumeSpacing*t.accidentalSpaceMultiplier},C=function(t){return function(e){return e.intraNeumeSpacing*t}},w=/(?:^|\n)%%\s?\n/,P=/^([\w-_.]+):\s*((?:[^;\r\n]|;[ \t])*)(?:;|$)/i,k=/^%.*/,T=e.GabcHeader=function(){function t(e){o(this,t),"string"!=typeof e&&(e=""),this.comments=[],this.cValues={},this.original="";var i=e.match(w);if(i)for(var n=this.original=e.slice(0,i.index+i[0].length),s=n.split(/\r?\n/g),r=0;r0&&s[s.length-1].notations.length>0&&(s[s.length-1].notations[s[s.length-1].notations.length-1].trailingSpace=0),s}},{key:"diffDescriptorsAndNewWords",value:function(t,e){var i,n={};for(i=0;ir&&(r=h[l],s=l-r+1,o=a-r+1)}u=h}if(0===r){var c=[];return t.length&&c.push(["-",t]),e.length&&c.push(["+",e]),c}return[].concat(this.diffDescriptorsAndNewWords(t.slice(0,s),e.slice(0,o)),[["=",e.slice(o,o+r)]],this.diffDescriptorsAndNewWords(t.slice(s+r),e.slice(o+r)))}},{key:"updateMappingsFromSource",value:function(t,e,i){var n=arguments.length>3&&void 0!==arguments[3]?arguments[3]:null,s=arguments.length>4&&void 0!==arguments[4]?arguments[4]:null,o=T.getLength(i);i=i.slice(o),e.pop(),null===n&&(n=NaN),null===s&&(s=NaN);var r,a,l,f,p=this.splitWords(i),d=this.diffDescriptorsAndNewWords(e,p),g=0,y=0,v=0,m=0;t.activeClef=h.Clef.default();for(var b=[],x=0;x0&&(y=e[g-1].sourceIndex+e[g-1].source.length+1),"="===S){var C=y-e[g].sourceIndex;for(r=0;r=m||s>=m){var w=O(f.notations);if(n>=m&&n=m&&s0&&e[e.length-1].notations.length>0&&(e[e.length-1].notations[e[e.length-1].notations.length-1].trailingSpace=0),o}},{key:"createMappingsFromWords",value:function(t,e){for(var i=[],n=0,s=0,o=[],r=0;r)([\s\S]*?)($|)/g,function(t,e,i,n){return""+e+i.replace(/~/g," ")+n}),d=[],g=[],m=f[2];0===l&&/[a-z]/i.test(p)&&/[a-m]/i.test(m)&&t.activeClef.resetAccidentals();var b=this.parseNotations(t,m,i+f.index+f[1].length+1,o);if(0!==b.length){o>=0&&(o-=O(b)),b[0].firstOfSyllable=!!p,b[0].firstOfParentheses=!0,a.push.apply(a,s(b));for(var x=null,S=0;S0&&(f.match(/\s$/)?(f=f.replace(/s+$/,""),i=u.LyricType.EndingSyllable):i=u.LyricType.MiddleSyllable),p=f;for(var e=/[\s\S]*?<\/v>/,l=void 0,v=[];l=e.exec(p);){var m=l.index,b=l[0].length;v[m]=b,p=p.slice(0,m)+p.slice(m+b)}if(d=p.indexOf("{"),g=0,d>=0){var x=p.indexOf("}");if(x>=0&&x>d){var S=function(t){var e=0;for(var i in v){if(!(v.hasOwnProperty(i)&&t>=i))break;e+=v[i]}return t+e};d=S(d),x=S(x),g=x-d-1,f=f.substring(0,d)+f.substring(d+1,x)+f.substring(x+1,f.length)}else d=-1}if(y=r.makeLyric(t,f,i,n,s,o),d>=0){var L=0,C=-1,w=!0,P=!1,k=void 0;try{for(var T,O=y.spans[Symbol.iterator]();!(w=(T=O.next()).done);w=!0){var _=T.value;if(d>=_.index&&d<=_.index+_.text.length&&(C=d+g,d+=L-_.index),C>=0&&C>=_.index&&C<=_.index+_.text.length){C+=L-_.index,g=C-d,C=-1;break}L+=_.text.length}}catch(t){P=!0,k=t}finally{try{!w&&O.return&&O.return()}finally{if(P)throw k}}C>=0&&(C=L,g=C-d)}d>=0&&(y.centerStartIndex=d,y.centerLength=g),y.lyricIndex=a.push(y)-1,o+=f.length+1},c=0;c1&&("-"===e[e.length-1]?(a=!0,i===u.LyricType.EndingSyllable?i=u.LyricType.MiddleSyllable:i===u.LyricType.SingleSyllable&&(i=u.LyricType.BeginningSyllable),e=e.slice(0,-1)):" "===e[e.length-1]?(i===u.LyricType.MiddleSyllable?i=u.LyricType.EndingSyllable:i===u.LyricType.BeginningSyllable&&(i=u.LyricType.SingleSyllable),e=e.slice(0,-1)):/<\/i>$/.test(e)&&(r=!0)),e.match(/^(?:[*†]+|i+j|\d+)\.?$/)&&(i=u.LyricType.Directive);var h=new u.Lyric(t,e,i,n,s,o);return h.elidesToNext=r,a&&h.setForceConnector(!0),h}},{key:"parseNotations",value:function(t,e,i,n){var o=this;if(!e)return[new h.TextOnly(i,0)];for(var r,a=i,l=0,c=[],f=[],d=u.DefaultTrailingSpace,g=function(t){f.length>0&&(f[f.length-1].sourceGabc+=t)},y=function(e){if(f.length>0){for(var n=o.createNeumesFromNotes(t,f,d),s=0;s1&&"+"===x[1]){var S=new p.Custos;S.staffPosition=this.gabcHeightToExsurgeHeight(x[0]),y(S)}else if(x.length>1&&/[xy#]/.test(x[1])){var w;switch(x[1]){case"y":w=p.AccidentalType.Natural;break;case"#":w=p.AccidentalType.Sharp;break;default:w=p.AccidentalType.Flat}var P=[];this.createNoteFromData(t,t.activeClef,x,P,i);var k=new p.Accidental(P[0].staffPosition,w);k.pitch=this.gabcHeightToExsurgePitch(t.activeClef,x[0]),k.sourceIndex=i,k.sourceLength=l,k.trailingSpace=L,t.activeClef.activeAccidental=k,y(k)}else x.length>1&&"{"===x[0]?!function(){d=0,y(null);var e=o.parseNotations(t,r[b],i+1);e.forEach(function(t){t.hasNoWidth=!0,t.firstWithNoWidth=e[0]}),c.push.apply(c,s(e))}():(n===-1&&(d=C(1),y(null)),this.createNoteFromData(t,t.activeClef,x,f,i),--n)}}return y(null),c}},{key:"createNeumesFromNotes",value:function(t,e,i){for(var n=[],s=0,o=0,r=function(t,i){var r,u=!(arguments.length>2&&void 0!==arguments[2])||arguments[2];if(r=i?o:u?o-1:o-2,!(r<0)){for(;s<=r;){var l=e[s++];t.addNote(l),l.alText&&(t.alText||(t.alText=[]),t.alText.push(l.alText),l.alText.noteIndex=s-1)}return n.push(t),i===!1&&(o--,u===!1&&o--,t.keepWithNext=!0,e[o+1].shape===h.NoteShape.Quilisma?t.trailingSpace=0:(t.trailingSpace=C(1),t.allowLineBreakBeforeNext=!0)),a}},a={neume:function(){return new g.Punctum},handle:function(t,e){return t.shape===h.NoteShape.Virga?w:t.shape===h.NoteShape.Stropha?k:t.shape===h.NoteShape.Oriscus?f:t.shape===h.NoteShape.Inclinatum?c:t.shapeModifiers&h.NoteShapeModifiers.Cavum?r(new g.Punctum,!0):l}},l={neume:function(){return new g.Punctum},handle:function(t,e,i){if(t.shape||e.liquescent===h.LiquescentType.Small){var n=new g.Punctum,s=r(n,!1);return t.staffPosition>e.staffPosition&&(t.staffPosition%2===1||e.staffPosition!==t.staffPosition-1||!e.morae||0===e.morae.length)&&(n.trailingSpace=0),s}if(t.staffPosition>e.staffPosition)return t.ictus&&(t.ictus.positionHint=u.MarkingPositionHint.Above),p;if(t.staffPositione.staffPosition)return e.shapeModifiers|=h.NoteShapeModifiers.Ascending,r(new g.PesQuassus,!0);if(t.staffPositione.staffPosition&&(t.staffPosition%2===1||e.staffPosition!==t.staffPosition-1||!e.morae||0===e.morae.length)&&(i.trailingSpace=0),n}},p={neume:function(){return new g.Podatus},handle:function(t,e){return t.staffPosition>e.staffPosition?(t.ictus&&(t.ictus.positionHint=u.MarkingPositionHint.Above),e.ictus&&(e.ictus.positionHint=u.MarkingPositionHint.Below),e.shape===h.NoteShape.Oriscus?b:S):t.staffPositione.staffPosition?(t.ictus&&(t.ictus.positionHint=u.MarkingPositionHint.Above),v):r(new g.Clivis,!1)}},y={neume:function(){return new g.Climacus},handle:function(t,e){return t.shape!==h.NoteShape.Inclinatum?r(new g.Climacus,!1):A}},v={neume:function(){return new g.Porrectus},handle:function(t,e){return t.shape===h.NoteShape.Default&&t.staffPositioni.staffPosition){var n=e[o-2];if(n&&n.staffPosition-i.staffPosition<=4)return t.ictus&&(t.ictus.positionHint=u.MarkingPositionHint.Above),N}return r(new g.Torculus,!1)}},N={neume:function(){return new g.TorculusResupinus},handle:function(t,e){return t.shape===h.NoteShape.Default&&t.staffPosition0?e[o-1]:null,I=e[o];A=A.handle(I,M,e.length-1-o),o===e.length-1&&A!==a&&r(A.neume(),!0),o++}return n.length>0&&(i.isDefault||(n[n.length-1].trailingSpace=i,n[n.length-1].keepWithNext=!0,i>0&&(n[n.length-1].allowLineBreakBeforeNext=n[n.length-1].keepWithNext=!0))),n}},{key:"createNoteFromData",value:function(t,e,i,n,s){var o=new h.Note;if(o.sourceIndex=s,o.sourceGabc=i,i.length<1)throw"Invalid note data: "+i;if("-"===i[0]&&(o.liquescent=h.LiquescentType.InitioDebilis,i=i.substring(1)),i.length<1)throw"Invalid note data: "+i;var r=this.gabcHeightToExsurgePitch(e,i[0]);i[0]===i[0].toUpperCase()&&(o.shape=h.NoteShape.Inclinatum),o.staffPosition=this.gabcHeightToExsurgeHeight(i[0]),o.pitch=r;for(var l,f=n.length,p=o,d=1;d0&&n.length){var m=n.slice(-1)[0],b=o.morae.slice(-1)[0];b.note=m}l=new c.Mora(t,o),v&&"1"===y?l.positionHint=u.MarkingPositionHint.Above:v&&"0"===y&&(l.positionHint=u.MarkingPositionHint.Below),o.morae.push(l);break;case"_":var x=!1;for(l=new c.HorizontalEpisema(p);v;){if("0"===y)l.positionHint=u.MarkingPositionHint.Below;else if("1"===y)l.positionHint=u.MarkingPositionHint.Above;else if("2"===y)l.terminating=!0;else if("3"===y)l.alignment=c.HorizontalEpisemaAlignment.Left;else if("4"===y)l.alignment=c.HorizontalEpisemaAlignment.Center;else{if("5"!==y)break;l.alignment=c.HorizontalEpisemaAlignment.Right}l.alignment!==c.HorizontalEpisemaAlignment.Default&&l.positionHint!==u.MarkingPositionHint.Below&&(x=!0),d++,v=d+1=0&&n.length>0&&(p=n[--f]);break;case"'":l=new c.Ictus(t,o),v&&"1"===y?l.positionHint=u.MarkingPositionHint.Above:v&&"0"===y?l.positionHint=u.MarkingPositionHint.Below:o.shape===h.NoteShape.Virga&&(l.positionHint=u.MarkingPositionHint.Above),o.ictus=l;break;case"r":if(v&&/^[0-5]$/.test(y)){switch(y){case"0":o.shapeModifiers|=h.NoteShapeModifiers.Cavum,o.shapeModifiers|=h.NoteShapeModifiers.Linea;break;case"1":o.accent=new c.Accent(t,o,u.GlyphCode.AcuteAccent);break;case"2":o.accent=new c.Accent(t,o,u.GlyphCode.GraveAccent);break;case"3":o.accent=new c.Accent(t,o,u.GlyphCode.Circle);break;case"4":o.accent=new c.Accent(t,o,u.GlyphCode.Semicircle);break;case"5":o.accent=new c.Accent(t,o,u.GlyphCode.ReversedSemicircle)}d++}else o.shapeModifiers|=h.NoteShapeModifiers.Cavum;break;case"R":o.shapeModifiers|=h.NoteShapeModifiers.Linea;break;case"s":if(o.shape===h.NoteShape.Stropha){var S=new h.Note;S.sourceIndex=s+d,S.sourceGabc="s",S.staffPosition=o.staffPosition,S.pitch=o.pitch,n.push(o),o=S,f++}o.shape=h.NoteShape.Stropha;break;case"v":if(o.shape===h.NoteShape.Virga){var L=new h.Note;L.sourceIndex=s+d,L.sourceGabc="v",L.staffPosition=o.staffPosition,L.pitch=o.pitch,n.push(o),o=L,f++}o.shape=h.NoteShape.Virga;break;case"V":o.shape=h.NoteShape.Virga,o.shapeModifers|=h.NoteShapeModifiers.Reverse;break;case"w":o.shape=h.NoteShape.Quilisma;break;case"o":o.shape=h.NoteShape.Oriscus,v&&"<"===y?(o.shapeModifiers|=h.NoteShapeModifiers.Ascending,d++):v&&">"===y&&(o.shapeModifiers|=h.NoteShapeModifiers.Descending,d++);break;case"O":o.shape=h.NoteShape.Oriscus,v&&"<"===y?(o.shapeModifiers|=h.NoteShapeModifiers.Ascending|h.NoteShapeModifiers.Stemmed,d++):v&&">"===y?(o.shapeModifiers|=h.NoteShapeModifiers.Descending|h.NoteShapeModifiers.Stemmed,d++):o.shapeModifiers|=h.NoteShapeModifiers.Stemmed;break;case"~":o.shape===h.NoteShape.Inclinatum?o.liquescent|=h.LiquescentType.Small:o.shape===h.NoteShape.Oriscus?o.liquescent|=h.LiquescentType.Large:o.liquescent|=h.LiquescentType.Small;break;case"<":o.liquescent|=h.LiquescentType.Ascending;break;case">":o.liquescent|=h.LiquescentType.Descending;break;case"x":o.pitch.step===a.Step.Mi?o.pitch.step=a.Step.Me:o.pitch.step===a.Step.Ti&&(o.pitch.step=a.Step.Te);break;case"y":o.pitch.step===a.Step.Te?o.pitch.step=a.Step.Ti:o.pitch.step===a.Step.Me?o.pitch.step=a.Step.Mi:o.pitch.step===a.Step.Du?o.pitch.step=a.Step.Do:o.pitch.step===a.Step.Fu&&(o.pitch.step=a.Step.Fa);break;case"#":o.pitch.step===a.Step.Do?o.pitch.step=a.Step.Du:o.pitch.step===a.Step.Fa&&(o.pitch.step=a.Step.Fu);break;case"[":for(var C=++d;d2&&void 0!==arguments[2]?arguments[2]:0;o(this,t),this.ctxt=e,this.neume=i,this.x=n,this.lastNote=null,this.lineIsHanging=!1,this.minX=0}return a(t,[{key:"lineFrom",value:function(t){var e=this.ctxt.notations[this.ctxt.currNotationIndex-1];return 0===this.x&&e&&e.notes&&0===e.trailingSpace?(this.lastNote=e.notes.slice(-1)[0],this.minX=-this.ctxt.neumeLineWeight):(this.lastNote=t,this.lineIsHanging=!0),this}},{key:"noteAt",value:function(t,e){var i=!(arguments.length>2&&void 0!==arguments[2])||arguments[2];if(!t)throw"NeumeBuilder.noteAt: note must be a valid note";if(!e)throw"NeumeBuilder.noteAt: glyph must be a valid glyph code";t.setGlyph(this.ctxt,e);var n="right"===t.glyphVisualizer.align,s=i&&null!==this.lastNote&&(this.lineIsHanging||this.lastNote.glyphVisualizer&&"right"===this.lastNote.glyphVisualizer.align||Math.abs(this.lastNote.staffPosition-t.staffPosition)>1);if(s){var o=new h.NeumeLineVisualizer(this.ctxt,this.lastNote,t,this.lineIsHanging);this.neume.addVisualizer(o),o.bounds.x=Math.max(this.minX,this.x-o.bounds.width),n||(this.x=o.bounds.x)}var r=0;if(t.shapeModifiers&u.NoteShapeModifiers.Linea){var a=new h.LineaVisualizer(this.ctxt,t);this.neume.addVisualizer(a),t.origin.x+=a.origin.x,r=a.origin.x}return n&&this.lastNote?t.bounds.x=this.x-t.bounds.width:(t.bounds.x=this.x+r,this.x+=t.bounds.width+r),this.neume.addVisualizer(t),this.lastNote=t,this.lineIsHanging=!1,this}},{key:"virgaAt",value:function(t){!(arguments.length>1&&void 0!==arguments[1])||arguments[1];this.noteAt(t,h.GlyphCode.PunctumQuadratum);var e=new h.VirgaLineVisualizer(this.ctxt,t);return this.x-=e.bounds.width,t.shapeModifers&u.NoteShapeModifiers.Reverse?e.bounds.x=0:e.bounds.x=this.x,this.neume.addVisualizer(e),this.lastNote=t,this.lineIsHanging=!1,this}},{key:"advanceBy",value:function(t){return this.lastNote=null,this.lineIsHanging=!1,this.x+=t,this}},{key:"withLineEndingAt",value:function(t){if(null!==this.lastNote){var e=new h.NeumeLineVisualizer(this.ctxt,this.lastNote,t,!0);return this.neume.addVisualizer(e),this.x-=e.bounds.width,e.bounds.x=this.x,this.neume.addVisualizer(e),this.lastNote=t,this}}},{key:"withPodatus",value:function(t,e){var i,n;return t.liquescent===u.LiquescentType.InitioDebilis?(i=e.liquescent===u.LiquescentType.None?h.GlyphCode.PunctumQuadratum:h.GlyphCode.PunctumQuadratumDesLiquescent,n=h.GlyphCode.TerminatingDesLiquescent):e.liquescent&u.LiquescentType.Small?(n=h.GlyphCode.BeginningAscLiquescent,i=h.GlyphCode.TerminatingAscLiquescent):e.liquescent&u.LiquescentType.Ascending?(n=h.GlyphCode.PunctumQuadratum,i=h.GlyphCode.PunctumQuadratumAscLiquescent):e.liquescent&u.LiquescentType.Descending?(n=h.GlyphCode.PunctumQuadratum,i=h.GlyphCode.PunctumQuadratumDesLiquescent):(n=h.GlyphCode.PodatusLower,i=h.GlyphCode.PodatusUpper),t.shape===u.NoteShape.Quilisma&&(n=h.GlyphCode.Quilisma),this.noteAt(t,n).noteAt(e,i),this.lastNote=null,this}},{key:"withClivis",value:function(t,e){var i;return t.shape===u.NoteShape.Oriscus?this.noteAt(t,h.GlyphCode.OriscusDes,!1):this.lineFrom(e).noteAt(t,h.GlyphCode.PunctumQuadratum),i=e.liquescent&u.LiquescentType.Small?h.GlyphCode.TerminatingDesLiquescent:e.liquescent===u.LiquescentType.Ascending?h.GlyphCode.PunctumQuadratumAscLiquescent:e.liquescent===u.LiquescentType.Descending?h.GlyphCode.PunctumQuadratumDesLiquescent:h.GlyphCode.PunctumQuadratum,this.noteAt(e,i),this.lastNote=null,this}},{key:"withInclinata",value:function(t){for(var e=t[0].staffPosition,i=t[0].staffPosition,n=l.Glyphs.PunctumInclinatum.bounds.width*this.ctxt.glyphScaling,s=0;s0&&(this.x+=n*r),o.bounds.x=this.x,this.neume.addVisualizer(o)}return this}},{key:"withPorrectusSwash",value:function(t,e){var i=null!==this.lastNote&&(this.lineIsHanging||this.lastNote.glyphVisualizer&&"right"===this.lastNote.glyphVisualizer.align||Math.abs(this.lastNote.staffPosition-t.staffPosition)>1);if(i){var n=new h.NeumeLineVisualizer(this.ctxt,this.lastNote,t,this.lineIsHanging);this.x=Math.max(this.minX,this.x-n.bounds.width),n.bounds.x=this.x,this.neume.addVisualizer(n)}var s;switch(t.staffPosition-e.staffPosition){case 1:s=h.GlyphCode.Porrectus1;break;case 2:s=h.GlyphCode.Porrectus2;break;case 3:s=h.GlyphCode.Porrectus3;break;case 4:s=h.GlyphCode.Porrectus4;break;default:s=h.GlyphCode.None}return t.setGlyph(this.ctxt,s),t.bounds.x=this.x,e.setGlyph(this.ctxt,h.GlyphCode.None),this.x=t.bounds.right(),e.bounds.x=this.x-e.bounds.width,this.neume.addVisualizer(t),this.neume.addVisualizer(e),this.lastNote=e,this.lineIsHanging=!1,this}}]),t}(),f=e.Neume=function(t){function e(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:[];o(this,e);var i=n(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));i.isNeume=!0,i.notes=t;for(var s=0;s=4){if(e=e||a>=5,t===!1&&(t=Math.max(0,o-1)),a>=5)continue}else if(a<=-4&&(n=n||a<=-5,i===!1&&(i=Math.max(0,o-1)),a<=-5))continue;if(e||n){var u=o;s.push({element:this.notes[t||i||0],endElem:this.notes[u],staffPosition:e?5:-5}),t=i=e=n=!1}}return(e||n)&&s.push({element:this.notes[t||i||0],endElem:this.notes[this.notes.length-1],staffPosition:e?5:-5}),s}},{key:"resetDependencies",value:function(){}},{key:"build",value:function(t){return new c(t,this)}},{key:"positionEpisemata",value:function(t,e){var i;for(i=0;it[0].staffPosition)){var e,i=t[1],n=t[0];1===Math.abs(i.staffPosition%2)&&n.staffPosition-i.staffPosition===1&&i.morae.length>0&&(e=i.morae.slice(-1)[0],e.positionHint===h.MarkingPositionHint.Default&&(e.positionHint=h.MarkingPositionHint.Below))}}},{key:"positionPodatusMorae",value:function(t,e){var i;1===Math.abs(t.staffPosition%2)&&(1===t.morae.length?i=t.morae[0]:e.morae.length>1&&(i=e.morae[0]),i&&i.positionHint===h.MarkingPositionHint.Default&&(i.positionHint=h.MarkingPositionHint.Below)),t.morae.length>0&&0===e.morae.length&&(t.morae[0].ignoreBounds=!0)}},{key:"positionPodatusMarkings",value:function(t,e){this.positionPodatusEpisemata(t,e),this.positionPodatusMorae(t,e)}},{key:"positionTorculusMarkings",value:function(t,e,i){var n=this.positionClivisMarkings(e,i);return n=this.positionEpisemata(t,n?h.MarkingPositionHint.Above:h.MarkingPositionHint.Below)&&n}},{key:"positionClivisMorae",value:function(t,e){var i=t.morae.concat(e.morae);e.morae.length&&t.staffPosition-e.staffPosition===1&&1===Math.abs(e.staffPosition%2)&&(i.slice(-1)[0].positionHint=h.MarkingPositionHint.Below)}},{key:"positionClivisEpisemata",value:function(t,e){var i=this.positionEpisemataAbove(t);return this.positionEpisemata(e,i?h.MarkingPositionHint.Above:h.MarkingPositionHint.Below),i}},{key:"positionClivisMarkings",value:function(t,e){return this.positionClivisMorae(t,e),this.positionClivisEpisemata(t,e)}},{key:"positionPorrectusMarkings",value:function(t,e,i){this.positionClivisEpisemata(t,e),this.positionPodatusMarkings(e,i)}},{key:"positionPorrectusFlexusMarkings",value:function(t,e,i,n){var s=this.positionEpisemataAbove(t);s=this.positionClivisMarkings(i,n)||s,this.positionEpisemata(e,s?h.MarkingPositionHint.Above:h.MarkingPositionHint.Below)}},{key:"positionMarkings",value:function(){}}]),e}(h.ChantNotationElement),p=e.Apostropha=function(t){function e(){return o(this,e),n(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return s(e,t),a(e,[{key:"positionMarkings",value:function(){for(var t=h.MarkingPositionHint.Above,e=0;en.staffPosition&&(i=h.GlyphCode.OriscusAsc)}}this.build(t).noteAt(n,i),this.finishLayout(t)}},{key:"resetDependencies",value:function(){this.notes[0].shapeModifiers&u.NoteShapeModifiers.Ascending||this.notes[0].shapeModifiers&u.NoteShapeModifiers.Descending||(this.needsLayout=!0)}}]),e}(f),e.PesQuassus=function(t){function e(){return o(this,e),n(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return s(e,t),a(e,[{key:"performLayout",value:function(t){r(e.prototype.__proto__||Object.getPrototypeOf(e.prototype),"performLayout",this).call(this,t);var i,n=this.notes[0],s=this.notes[1],o=n.staffPosition,a=s.staffPosition;i=n.shape===u.NoteShape.Oriscus?h.GlyphCode.OriscusAsc:h.GlyphCode.PunctumQuadratum;var l=this.build(t).noteAt(n,i);a-o===1?l.virgaAt(s):s.liquescent===u.LiquescentType.LargeDescending?l.noteAt(s,h.GlyphCode.PunctumQuadratumDesLiquescent).withLineEndingAt(n):l.noteAt(s,h.GlyphCode.PunctumQuadratum).withLineEndingAt(n),this.finishLayout(t)}}]),e}(f),e.PesSubpunctis=function(t){function e(){return o(this,e),n(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return s(e,t),a(e,[{key:"positionMarkings",value:function(){this.positionPodatusEpisemata(this.notes[0],this.notes[1]);for(var t=2;t2&&void 0!==arguments[2]?arguments[2]:{},r=n.supertitle,a=n.title,u=n.subtitle,h=n.textLeft,l=n.textRight;s(this,e);var c=o(this,(e.__proto__||Object.getPrototypeOf(e)).call(this));return c.score=i,c.setSupertitle(t,r),c.setTitle(t,a),c.setSubtitle(t,u),c.setTextLeft(t,h),c.setTextRight(t,l),c}return r(e,t),a(e,[{key:"setBoundsX",value:function(t,e,i){var n=this[e];switch(t.textStyles[e].alignment){case"left":n.textAnchor="start",n.bounds.x=0;break;case"right":n.textAnchor="end",n.bounds.x=i;break;case"center":default:n.textAnchor="middle",n.bounds.x=i/2}}},{key:"layoutTitles",value:function(t,e){this.bounds=new u.Rect(0,0,0,0);var i=0;this.supertitle&&(this.supertitle.recalculateMetrics(t),this.supertitle.setMaxWidth(t,e),this.setBoundsX(t,"supertitle",e),this.supertitle.bounds.y=i,this.bounds.union(this.supertitle.bounds),this.supertitle.bounds.y+=this.supertitle.origin.y,i+=this.supertitle.bounds.height+this.supertitle.padding(t)),this.title&&(i&&(i+=this.title.padding(t)),this.title.recalculateMetrics(t),this.title.setMaxWidth(t,e),this.setBoundsX(t,"title",e),this.title.bounds.y=i,this.bounds.union(this.title.bounds),this.title.bounds.y+=this.title.origin.y,i+=this.title.bounds.height+this.title.padding(t)),this.subtitle&&(i&&(i+=this.subtitle.padding(t)),this.subtitle.recalculateMetrics(t),this.subtitle.setMaxWidth(t,e),this.setBoundsX(t,"subtitle",e),this.subtitle.bounds.y=i,this.bounds.union(this.subtitle.bounds),this.subtitle.bounds.y+=this.subtitle.origin.y,i+=this.subtitle.bounds.height+this.subtitle.padding(t));var n=i,s=this.score.overrideTextLeft||this.textLeft;return s&&(s.recalculateMetrics(t),s.bounds.y=i,this.bounds.union(s.bounds),s.bounds.y+=s.origin.y,n=i+s.bounds.height+s.padding(t)),this.textRight&&(this.textRight.recalculateMetrics(t),this.textRight.bounds.x=e,this.textRight.bounds.y=i,this.bounds.union(this.textRight.bounds),this.textRight.bounds.y+=this.textRight.origin.y,n=Math.max(n,i+this.textRight.bounds.height+this.textRight.padding(t))),n}},{key:"setSupertitle",value:function(t,e){this.supertitle=e?new h.Supertitle(t,e):null}},{key:"setTitle",value:function(t,e){this.title=e?new h.Title(t,e):null}},{key:"setSubtitle",value:function(t,e){this.subtitle=e?new h.Subtitle(t,e):null}},{key:"setTextLeft",value:function(t,e){this.textLeft=e?new h.TextLeftRight(t,e,"textLeft"):null}},{key:"setTextRight",value:function(t,e){this.textRight=e?new h.TextLeftRight(t,e,"textRight"):null}},{key:"hasSupertitle",value:function(t,e){return!!this.supertitle}},{key:"hasTitle",value:function(t,e){return!!this.title}},{key:"hasSubtitle",value:function(t,e){return!!this.subtitle}},{key:"hasTextLeft",value:function(t,e){return!!this.textLeft}},{key:"hasTextRight",value:function(t,e){return!!this.textRight}},{key:"draw",value:function(t){var e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:1,i=t.canvasCtxt;i.translate(this.bounds.x,this.bounds.y);for(var n=[this.supertitle,this.title,this.subtitle,this.score.overrideTextLeft||this.textLeft,this.textRight],s=0;s1&&void 0!==arguments[1]?arguments[1]:"createSvgNode",i=[],n=[this.supertitle,this.title,this.subtitle,this.score.overrideTextLeft||this.textLeft,this.textRight],s=0;s").appendTo(b),e=d.css("display");d.remove();if(e==="none"||e===""){cn||(cn=c.createElement("iframe"),cn.frameBorder=cn.width=cn.height=0),b.appendChild(cn);if(!co||!cn.createElement)co=(cn.contentWindow||cn.contentDocument).document,co.write((c.compatMode==="CSS1Compat"?"":"")+""),co.close();d=co.createElement(a),co.body.appendChild(d),e=f.css(d,"display"),b.removeChild(cn)}cm[a]=e}return cm[a]}function cw(a,b){var c={};f.each(cs.concat.apply([],cs.slice(0,b)),function(){c[this]=a});return c}function cv(){ct=b}function cu(){setTimeout(cv,0);return ct=f.now()}function cl(){try{return new a.ActiveXObject("Microsoft.XMLHTTP")}catch(b){}}function ck(){try{return new a.XMLHttpRequest}catch(b){}}function ce(a,c){a.dataFilter&&(c=a.dataFilter(c,a.dataType));var d=a.dataTypes,e={},g,h,i=d.length,j,k=d[0],l,m,n,o,p;for(g=1;g0){c!=="border"&&f.each(e,function(){c||(d-=parseFloat(f.css(a,"padding"+this))||0),c==="margin"?d+=parseFloat(f.css(a,c+this))||0:d-=parseFloat(f.css(a,"border"+this+"Width"))||0});return d+"px"}d=bB(a,b,b);if(d<0||d==null)d=a.style[b]||0;d=parseFloat(d)||0,c&&f.each(e,function(){d+=parseFloat(f.css(a,"padding"+this))||0,c!=="padding"&&(d+=parseFloat(f.css(a,"border"+this+"Width"))||0),c==="margin"&&(d+=parseFloat(f.css(a,c+this))||0)});return d+"px"}function br(a,b){b.src?f.ajax({url:b.src,async:!1,dataType:"script"}):f.globalEval((b.text||b.textContent||b.innerHTML||"").replace(bi,"/*$0*/")),b.parentNode&&b.parentNode.removeChild(b)}function bq(a){var b=(a.nodeName||"").toLowerCase();b==="input"?bp(a):b!=="script"&&typeof a.getElementsByTagName!="undefined"&&f.grep(a.getElementsByTagName("input"),bp)}function bp(a){if(a.type==="checkbox"||a.type==="radio")a.defaultChecked=a.checked}function bo(a){return typeof a.getElementsByTagName!="undefined"?a.getElementsByTagName("*"):typeof a.querySelectorAll!="undefined"?a.querySelectorAll("*"):[]}function bn(a,b){var c;if(b.nodeType===1){b.clearAttributes&&b.clearAttributes(),b.mergeAttributes&&b.mergeAttributes(a),c=b.nodeName.toLowerCase();if(c==="object")b.outerHTML=a.outerHTML;else if(c!=="input"||a.type!=="checkbox"&&a.type!=="radio"){if(c==="option")b.selected=a.defaultSelected;else if(c==="input"||c==="textarea")b.defaultValue=a.defaultValue}else a.checked&&(b.defaultChecked=b.checked=a.checked),b.value!==a.value&&(b.value=a.value);b.removeAttribute(f.expando)}}function bm(a,b){if(b.nodeType===1&&!!f.hasData(a)){var c,d,e,g=f._data(a),h=f._data(b,g),i=g.events;if(i){delete h.handle,h.events={};for(c in i)for(d=0,e=i[c].length;d=0===c})}function V(a){return!a||!a.parentNode||a.parentNode.nodeType===11}function N(){return!0}function M(){return!1}function n(a,b,c){var d=b+"defer",e=b+"queue",g=b+"mark",h=f._data(a,d);h&&(c==="queue"||!f._data(a,e))&&(c==="mark"||!f._data(a,g))&&setTimeout(function(){!f._data(a,e)&&!f._data(a,g)&&(f.removeData(a,d,!0),h.fire())},0)}function m(a){for(var b in a){if(b==="data"&&f.isEmptyObject(a[b]))continue;if(b!=="toJSON")return!1}return!0}function l(a,c,d){if(d===b&&a.nodeType===1){var e="data-"+c.replace(k,"-$1").toLowerCase();d=a.getAttribute(e);if(typeof d=="string"){try{d=d==="true"?!0:d==="false"?!1:d==="null"?null:f.isNumeric(d)?parseFloat(d):j.test(d)?f.parseJSON(d):d}catch(g){}f.data(a,c,d)}else d=b}return d}function h(a){var b=g[a]={},c,d;a=a.split(/\s+/);for(c=0,d=a.length;c)[^>]*$|#([\w\-]*)$)/,j=/\S/,k=/^\s+/,l=/\s+$/,m=/\d/,n=/^<(\w+)\s*\/?>(?:<\/\1>)?$/,o=/^[\],:{}\s]*$/,p=/\\(?:["\\\/bfnrt]|u[0-9a-fA-F]{4})/g,q=/"[^"\\\n\r]*"|true|false|null|-?\d+(?:\.\d*)?(?:[eE][+\-]?\d+)?/g,r=/(?:^|:|,)(?:\s*\[)+/g,s=/(webkit)[ \/]([\w.]+)/,t=/(opera)(?:.*version)?[ \/]([\w.]+)/,u=/(msie) ([\w.]+)/,v=/(mozilla)(?:.*? rv:([\w.]+))?/,w=/-([a-z]|[0-9])/ig,x=/^-ms-/,y=function(a,b){return(b+"").toUpperCase()},z=d.userAgent,A,B,C,D=Object.prototype.toString,E=Object.prototype.hasOwnProperty,F=Array.prototype.push,G=Array.prototype.slice,H=String.prototype.trim,I=Array.prototype.indexOf,J={};e.fn=e.prototype={constructor:e,init:function(a,d,f){var g,h,j,k;if(!a)return this;if(a.nodeType){this.context=this[0]=a,this.length=1;return this}if(a==="body"&&!d&&c.body){this.context=c,this[0]=c.body,this.selector=a,this.length=1;return this}if(typeof a=="string"){a.charAt(0)!=="<"||a.charAt(a.length-1)!==">"||a.length<3?g=i.exec(a):g=[null,a,null];if(g&&(g[1]||!d)){if(g[1]){d=d instanceof e?d[0]:d,k=d?d.ownerDocument||d:c,j=n.exec(a),j?e.isPlainObject(d)?(a=[c.createElement(j[1])],e.fn.attr.call(a,d,!0)):a=[k.createElement(j[1])]:(j=e.buildFragment([g[1]],[k]),a=(j.cacheable?e.clone(j.fragment):j.fragment).childNodes);return e.merge(this,a)}h=c.getElementById(g[2]);if(h&&h.parentNode){if(h.id!==g[2])return f.find(a);this.length=1,this[0]=h}this.context=c,this.selector=a;return this}return!d||d.jquery?(d||f).find(a):this.constructor(d).find(a)}if(e.isFunction(a))return f.ready(a);a.selector!==b&&(this.selector=a.selector,this.context=a.context);return e.makeArray(a,this)},selector:"",jquery:"1.7",length:0,size:function(){return this.length},toArray:function(){return G.call(this,0)},get:function(a){return a==null?this.toArray():a<0?this[this.length+a]:this[a]},pushStack:function(a,b,c){var d=this.constructor();e.isArray(a)?F.apply(d,a):e.merge(d,a),d.prevObject=this,d.context=this.context,b==="find"?d.selector=this.selector+(this.selector?" ":"")+c:b&&(d.selector=this.selector+"."+b+"("+c+")");return d},each:function(a,b){return e.each(this,a,b)},ready:function(a){e.bindReady(),B.add(a);return this},eq:function(a){return a===-1?this.slice(a):this.slice(a,+a+1)},first:function(){return this.eq(0)},last:function(){return this.eq(-1)},slice:function(){return this.pushStack(G.apply(this,arguments),"slice",G.call(arguments).join(","))},map:function(a){return this.pushStack(e.map(this,function(b,c){return a.call(b,c,b)}))},end:function(){return this.prevObject||this.constructor(null)},push:F,sort:[].sort,splice:[].splice},e.fn.init.prototype=e.fn,e.extend=e.fn.extend=function(){var a,c,d,f,g,h,i=arguments[0]||{},j=1,k=arguments.length,l=!1;typeof i=="boolean"&&(l=i,i=arguments[1]||{},j=2),typeof i!="object"&&!e.isFunction(i)&&(i={}),k===j&&(i=this,--j);for(;j0)return;B.fireWith(c,[e]),e.fn.trigger&&e(c).trigger("ready").unbind("ready")}},bindReady:function(){if(!B){B=e.Callbacks("once memory");if(c.readyState==="complete")return setTimeout(e.ready,1);if(c.addEventListener)c.addEventListener("DOMContentLoaded",C,!1),a.addEventListener("load",e.ready,!1);else if(c.attachEvent){c.attachEvent("onreadystatechange",C),a.attachEvent("onload",e.ready);var b=!1;try{b=a.frameElement==null}catch(d){}c.documentElement.doScroll&&b&&K()}}},isFunction:function(a){return e.type(a)==="function"},isArray:Array.isArray||function(a){return e.type(a)==="array"},isWindow:function(a){return a&&typeof a=="object"&&"setInterval"in a},isNumeric:function(a){return a!=null&&m.test(a)&&!isNaN(a)},type:function(a){return a==null?String(a):J[D.call(a)]||"object"},isPlainObject:function(a){if(!a||e.type(a)!=="object"||a.nodeType||e.isWindow(a))return!1;try{if(a.constructor&&!E.call(a,"constructor")&&!E.call(a.constructor.prototype,"isPrototypeOf"))return!1}catch(c){return!1}var d;for(d in a);return d===b||E.call(a,d)},isEmptyObject:function(a){for(var b in a)return!1;return!0},error:function(a){throw a},parseJSON:function(b){if(typeof b!="string"||!b)return null;b=e.trim(b);if(a.JSON&&a.JSON.parse)return a.JSON.parse(b);if(o.test(b.replace(p,"@").replace(q,"]").replace(r,"")))return(new Function("return "+b))();e.error("Invalid JSON: "+b)},parseXML:function(c){var d,f;try{a.DOMParser?(f=new DOMParser,d=f.parseFromString(c,"text/xml")):(d=new ActiveXObject("Microsoft.XMLDOM"),d.async="false",d.loadXML(c))}catch(g){d=b}(!d||!d.documentElement||d.getElementsByTagName("parsererror").length)&&e.error("Invalid XML: "+c);return d},noop:function(){},globalEval:function(b){b&&j.test(b)&&(a.execScript||function(b){a.eval.call(a,b)})(b)},camelCase:function(a){return a.replace(x,"ms-").replace(w,y)},nodeName:function(a,b){return a.nodeName&&a.nodeName.toUpperCase()===b.toUpperCase()},each:function(a,c,d){var f,g=0,h=a.length,i=h===b||e.isFunction(a);if(d){if(i){for(f in a)if(c.apply(a[f],d)===!1)break}else for(;g0&&a[0]&&a[j-1]||j===0||e.isArray(a));if(k)for(;i1?i.call(arguments,0):b,j.notifyWith(k,e)}}function l(a){return function(c){b[a]=arguments.length>1?i.call(arguments,0):c,--g||j.resolveWith(j,b)}}var b=i.call(arguments,0),c=0,d=b.length,e=Array(d),g=d,h=d,j=d<=1&&a&&f.isFunction(a.promise)?a:f.Deferred(),k=j.promise();if(d>1){for(;c
a",d=a.getElementsByTagName("*"),e=a.getElementsByTagName("a")[0];if(!d||!d.length||!e)return{};g=c.createElement("select"),h=g.appendChild(c.createElement("option")),i=a.getElementsByTagName("input")[0],k={leadingWhitespace:a.firstChild.nodeType===3,tbody:!a.getElementsByTagName("tbody").length,htmlSerialize:!!a.getElementsByTagName("link").length,style:/top/.test(e.getAttribute("style")),hrefNormalized:e.getAttribute("href")==="/a",opacity:/^0.55/.test(e.style.opacity),cssFloat:!!e.style.cssFloat,unknownElems:!!a.getElementsByTagName("nav").length,checkOn:i.value==="on",optSelected:h.selected,getSetAttribute:a.className!=="t",enctype:!!c.createElement("form").enctype,submitBubbles:!0,changeBubbles:!0,focusinBubbles:!1,deleteExpando:!0,noCloneEvent:!0,inlineBlockNeedsLayout:!1,shrinkWrapBlocks:!1,reliableMarginRight:!0},i.checked=!0,k.noCloneChecked=i.cloneNode(!0).checked,g.disabled=!0,k.optDisabled=!h.disabled;try{delete a.test}catch(v){k.deleteExpando=!1}!a.addEventListener&&a.attachEvent&&a.fireEvent&&(a.attachEvent("onclick",function(){k.noCloneEvent=!1}),a.cloneNode(!0).fireEvent("onclick")),i=c.createElement("input"),i.value="t",i.setAttribute("type","radio"),k.radioValue=i.value==="t",i.setAttribute("checked","checked"),a.appendChild(i),l=c.createDocumentFragment(),l.appendChild(a.lastChild),k.checkClone=l.cloneNode(!0).cloneNode(!0).lastChild.checked,a.innerHTML="",a.style.width=a.style.paddingLeft="1px",m=c.getElementsByTagName("body")[0],o=c.createElement(m?"div":"body"),p={visibility:"hidden",width:0,height:0,border:0,margin:0,background:"none"},m&&f.extend(p,{position:"absolute",left:"-999px",top:"-999px"});for(t in p)o.style[t]=p[t];o.appendChild(a),n=m||b,n.insertBefore(o,n.firstChild),k.appendChecked=i.checked,k.boxModel=a.offsetWidth===2,"zoom"in a.style&&(a.style.display="inline",a.style.zoom=1,k.inlineBlockNeedsLayout=a.offsetWidth===2,a.style.display="",a.innerHTML="
",k.shrinkWrapBlocks=a.offsetWidth!==2),a.innerHTML="
t
",q=a.getElementsByTagName("td"),u=q[0].offsetHeight===0,q[0].style.display="",q[1].style.display="none",k.reliableHiddenOffsets=u&&q[0].offsetHeight===0,a.innerHTML="",c.defaultView&&c.defaultView.getComputedStyle&&(j=c.createElement("div"),j.style.width="0",j.style.marginRight="0",a.appendChild(j),k.reliableMarginRight=(parseInt((c.defaultView.getComputedStyle(j,null)||{marginRight:0}).marginRight,10)||0)===0);if(a.attachEvent)for(t in{submit:1,change:1,focusin:1})s="on"+t,u=s in a,u||(a.setAttribute(s,"return;"),u=typeof a[s]=="function"),k[t+"Bubbles"]=u;f(function(){var a,b,d,e,g,h,i=1,j="position:absolute;top:0;left:0;width:1px;height:1px;margin:0;",l="visibility:hidden;border:0;",n="style='"+j+"border:5px solid #000;padding:0;'",p="
"+""+"
";m=c.getElementsByTagName("body")[0];!m||(a=c.createElement("div"),a.style.cssText=l+"width:0;height:0;position:static;top:0;margin-top:"+i+"px",m.insertBefore(a,m.firstChild),o=c.createElement("div"),o.style.cssText=j+l,o.innerHTML=p,a.appendChild(o),b=o.firstChild,d=b.firstChild,g=b.nextSibling.firstChild.firstChild,h={doesNotAddBorder:d.offsetTop!==5,doesAddBorderForTableAndCells:g.offsetTop===5},d.style.position="fixed",d.style.top="20px",h.fixedPosition=d.offsetTop===20||d.offsetTop===15,d.style.position=d.style.top="",b.style.overflow="hidden",b.style.position="relative",h.subtractsBorderForOverflowNotVisible=d.offsetTop===-5,h.doesNotIncludeMarginInBodyOffset=m.offsetTop!==i,m.removeChild(a),o=a=null,f.extend(k,h))}),o.innerHTML="",n.removeChild(o),o=l=g=h=m=j=a=i=null;return k}(),f.boxModel=f.support.boxModel;var j=/^(?:\{.*\}|\[.*\])$/,k=/([A-Z])/g;f.extend({cache:{},uuid:0,expando:"jQuery"+(f.fn.jquery+Math.random()).replace(/\D/g,""),noData:{embed:!0,object:"clsid:D27CDB6E-AE6D-11cf-96B8-444553540000",applet:!0},hasData:function(a){a=a.nodeType?f.cache[a[f.expando]]:a[f.expando];return!!a&&!m(a)},data:function(a,c,d,e){if(!!f.acceptData(a)){var g,h,i,j=f.expando,k=typeof c=="string",l=a.nodeType,m=l?f.cache:a,n=l?a[f.expando]:a[f.expando]&&f.expando,o=c==="events";if((!n||!m[n]||!o&&!e&&!m[n].data)&&k&&d===b)return;n||(l?a[f.expando]=n=++f.uuid:n=f.expando),m[n]||(m[n]={},l||(m[n].toJSON=f.noop));if(typeof c=="object"||typeof c=="function")e?m[n]=f.extend(m[n],c):m[n].data=f.extend(m[n].data,c);g=h=m[n],e||(h.data||(h.data={}),h=h.data),d!==b&&(h[f.camelCase(c)]=d);if(o&&!h[c])return g.events;k?(i=h[c],i==null&&(i=h[f.camelCase(c)])):i=h;return i}},removeData:function(a,b,c){if(!!f.acceptData(a)){var d,e,g,h=f.expando,i=a.nodeType,j=i?f.cache:a,k=i?a[f.expando]:f.expando;if(!j[k])return;if(b){d=c?j[k]:j[k].data;if(d){f.isArray(b)?b=b:b in d?b=[b]:(b=f.camelCase(b),b in d?b=[b]:b=b.split(" "));for(e=0,g=b.length;e-1)return!0;return!1},val:function(a){var c,d,e,g=this[0];if(!arguments.length){if(g){c=f.valHooks[g.nodeName.toLowerCase()]||f.valHooks[g.type];if(c&&"get"in c&&(d=c.get(g,"value"))!==b)return d;d=g.value;return typeof d=="string"?d.replace(q,""):d==null?"":d}return b}e=f.isFunction(a);return this.each(function(d){var g=f(this),h;if(this.nodeType===1){e?h=a.call(this,d,g.val()):h=a,h==null?h="":typeof h=="number"?h+="":f.isArray(h)&&(h=f.map(h,function(a){return a==null?"":a+""})),c=f.valHooks[this.nodeName.toLowerCase()]||f.valHooks[this.type];if(!c||!("set"in c)||c.set(this,h,"value")===b)this.value=h}})}}),f.extend({valHooks:{option:{get:function(a){var b=a.attributes.value;return!b||b.specified?a.value:a.text}},select:{get:function(a){var b,c,d,e,g=a.selectedIndex,h=[],i=a.options,j=a.type==="select-one";if(g<0)return null;c=j?g:0,d=j?g+1:i.length;for(;c=0}),c.length||(a.selectedIndex=-1);return c}}},attrFn:{val:!0,css:!0,html:!0,text:!0,data:!0,width:!0,height:!0,offset:!0},attr:function(a,c,d,e){var g,h,i,j=a.nodeType;if(!a||j===3||j===8||j===2)return b;if(e&&c in f.attrFn)return f(a)[c](d);if(!("getAttribute"in a))return f.prop(a,c,d);i=j!==1||!f.isXMLDoc(a),i&&(c=c.toLowerCase(),h=f.attrHooks[c]||(u.test(c)?x:w));if(d!==b){if(d===null){f.removeAttr(a,c);return b}if(h&&"set"in h&&i&&(g=h.set(a,d,c))!==b)return g;a.setAttribute(c,""+d);return d}if(h&&"get"in h&&i&&(g=h.get(a,c))!==null)return g;g=a.getAttribute(c);return g===null?b:g},removeAttr:function(a,b){var c,d,e,g,h=0;if(a.nodeType===1){d=(b||"").split(p),g=d.length;for(;h=0}})});var z=/\.(.*)$/,A=/^(?:textarea|input|select)$/i,B=/\./g,C=/ /g,D=/[^\w\s.|`]/g,E=/^([^\.]*)?(?:\.(.+))?$/,F=/\bhover(\.\S+)?/,G=/^key/,H=/^(?:mouse|contextmenu)|click/,I=/^(\w*)(?:#([\w\-]+))?(?:\.([\w\-]+))?$/,J=function(a){var b=I.exec(a);b&& +(b[1]=(b[1]||"").toLowerCase(),b[3]=b[3]&&new RegExp("(?:^|\\s)"+b[3]+"(?:\\s|$)"));return b},K=function(a,b){return(!b[1]||a.nodeName.toLowerCase()===b[1])&&(!b[2]||a.id===b[2])&&(!b[3]||b[3].test(a.className))},L=function(a){return f.event.special.hover?a:a.replace(F,"mouseenter$1 mouseleave$1")};f.event={add:function(a,c,d,e,g){var h,i,j,k,l,m,n,o,p,q,r,s;if(!(a.nodeType===3||a.nodeType===8||!c||!d||!(h=f._data(a)))){d.handler&&(p=d,d=p.handler),d.guid||(d.guid=f.guid++),j=h.events,j||(h.events=j={}),i=h.handle,i||(h.handle=i=function(a){return typeof f!="undefined"&&(!a||f.event.triggered!==a.type)?f.event.dispatch.apply(i.elem,arguments):b},i.elem=a),c=L(c).split(" ");for(k=0;k=0&&(h=h.slice(0,-1),k=!0),h.indexOf(".")>=0&&(i=h.split("."),h=i.shift(),i.sort());if((!e||f.event.customEvent[h])&&!f.event.global[h])return;c=typeof c=="object"?c[f.expando]?c:new f.Event(h,c):new f.Event(h),c.type=h,c.isTrigger=!0,c.exclusive=k,c.namespace=i.join("."),c.namespace_re=c.namespace?new RegExp("(^|\\.)"+i.join("\\.(?:.*\\.)?")+"(\\.|$)"):null,o=h.indexOf(":")<0?"on"+h:"",(g||!e)&&c.preventDefault();if(!e){j=f.cache;for(l in j)j[l].events&&j[l].events[h]&&f.event.trigger(c,d,j[l].handle.elem,!0);return}c.result=b,c.target||(c.target=e),d=d!=null?f.makeArray(d):[],d.unshift(c),p=f.event.special[h]||{};if(p.trigger&&p.trigger.apply(e,d)===!1)return;r=[[e,p.bindType||h]];if(!g&&!p.noBubble&&!f.isWindow(e)){s=p.delegateType||h,n=null;for(m=e.parentNode;m;m=m.parentNode)r.push([m,s]),n=m;n&&n===e.ownerDocument&&r.push([n.defaultView||n.parentWindow||a,s])}for(l=0;l=0:t===b&&(t=o[s]=r.quick?K(m,r.quick):f(m).is(s)),t&&q.push(r);q.length&&j.push({elem:m,matches:q})}d.length>e&&j.push({elem:this,matches:d.slice(e)});for(k=0;k0?this.bind(b,a,c):this.trigger(b)},f.attrFn&&(f.attrFn[b]=!0),G.test(b)&&(f.event.fixHooks[b]=f.event.keyHooks),H.test(b)&&(f.event.fixHooks[b]=f.event.mouseHooks)}),function(){function x(a,b,c,e,f,g){for(var h=0,i=e.length;h0){k=j;break}}j=j[a]}e[h]=k}}}function w(a,b,c,e,f,g){for(var h=0,i=e.length;h+~,(\[\\]+)+|[>+~])(\s*,\s*)?((?:.|\r|\n)*)/g,d="sizcache"+(Math.random()+"").replace(".",""),e=0,g=Object.prototype.toString,h=!1,i=!0,j=/\\/g,k=/\r\n/g,l=/\W/;[0,0].sort(function(){i=!1;return 0});var m=function(b,d,e,f){e=e||[],d=d||c;var h=d;if(d.nodeType!==1&&d.nodeType!==9)return[];if(!b||typeof b!="string")return e;var i,j,k,l,n,q,r,t,u=!0,v=m.isXML(d),w=[],x=b;do{a.exec(""),i=a.exec(x);if(i){x=i[3],w.push(i[1]);if(i[2]){l=i[3];break}}}while(i);if(w.length>1&&p.exec(b))if(w.length===2&&o.relative[w[0]])j=y(w[0]+w[1],d,f);else{j=o.relative[w[0]]?[d]:m(w.shift(),d);while(w.length)b=w.shift(),o.relative[b]&&(b+=w.shift()),j=y(b,j,f)}else{!f&&w.length>1&&d.nodeType===9&&!v&&o.match.ID.test(w[0])&&!o.match.ID.test(w[w.length-1])&&(n=m.find(w.shift(),d,v),d=n.expr?m.filter(n.expr,n.set)[0]:n.set[0]);if(d){n=f?{expr:w.pop(),set:s(f)}:m.find(w.pop(),w.length===1&&(w[0]==="~"||w[0]==="+")&&d.parentNode?d.parentNode:d,v),j=n.expr?m.filter(n.expr,n.set):n.set,w.length>0?k=s(j):u=!1;while(w.length)q=w.pop(),r=q,o.relative[q]?r=w.pop():q="",r==null&&(r=d),o.relative[q](k,r,v)}else k=w=[]}k||(k=j),k||m.error(q||b);if(g.call(k)==="[object Array]")if(!u)e.push.apply(e,k);else if(d&&d.nodeType===1)for(t=0;k[t]!=null;t++)k[t]&&(k[t]===!0||k[t].nodeType===1&&m.contains(d,k[t]))&&e.push(j[t]);else for(t=0;k[t]!=null;t++)k[t]&&k[t].nodeType===1&&e.push(j[t]);else s(k,e);l&&(m(l,h,e,f),m.uniqueSort(e));return e};m.uniqueSort=function(a){if(u){h=i,a.sort(u);if(h)for(var b=1;b0},m.find=function(a,b,c){var d,e,f,g,h,i;if(!a)return[];for(e=0,f=o.order.length;e":function(a,b){var c,d=typeof b=="string",e=0,f=a.length;if(d&&!l.test(b)){b=b.toLowerCase();for(;e=0)?c||d.push(h):c&&(b[g]=!1));return!1},ID:function(a){return a[1].replace(j,"")},TAG:function(a,b){return a[1].replace(j,"").toLowerCase()},CHILD:function(a){if(a[1]==="nth"){a[2]||m.error(a[0]),a[2]=a[2].replace(/^\+|\s*/g,"");var b=/(-?)(\d*)(?:n([+\-]?\d*))?/.exec(a[2]==="even"&&"2n"||a[2]==="odd"&&"2n+1"||!/\D/.test(a[2])&&"0n+"+a[2]||a[2]);a[2]=b[1]+(b[2]||1)-0,a[3]=b[3]-0}else a[2]&&m.error(a[0]);a[0]=e++;return a},ATTR:function(a,b,c,d,e,f){var g=a[1]=a[1].replace(j,"");!f&&o.attrMap[g]&&(a[1]=o.attrMap[g]),a[4]=(a[4]||a[5]||"").replace(j,""),a[2]==="~="&&(a[4]=" "+a[4]+" ");return a},PSEUDO:function(b,c,d,e,f){if(b[1]==="not")if((a.exec(b[3])||"").length>1||/^\w/.test(b[3]))b[3]=m(b[3],null,null,c);else{var g=m.filter(b[3],c,d,!0^f);d||e.push.apply(e,g);return!1}else if(o.match.POS.test(b[0])||o.match.CHILD.test(b[0]))return!0;return b},POS:function(a){a.unshift(!0);return a}},filters:{enabled:function(a){return a.disabled===!1&&a.type!=="hidden"},disabled:function(a){return a.disabled===!0},checked:function(a){return a.checked===!0},selected:function(a){a.parentNode&&a.parentNode.selectedIndex;return a.selected===!0},parent:function(a){return!!a.firstChild},empty:function(a){return!a.firstChild},has:function(a,b,c){return!!m(c[3],a).length},header:function(a){return/h\d/i.test(a.nodeName)},text:function(a){var b=a.getAttribute("type"),c=a.type;return a.nodeName.toLowerCase()==="input"&&"text"===c&&(b===c||b===null)},radio:function(a){return a.nodeName.toLowerCase()==="input"&&"radio"===a.type},checkbox:function(a){return a.nodeName.toLowerCase()==="input"&&"checkbox"===a.type},file:function(a){return a.nodeName.toLowerCase()==="input"&&"file"===a.type},password:function(a){return a.nodeName.toLowerCase()==="input"&&"password"===a.type},submit:function(a){var b=a.nodeName.toLowerCase();return(b==="input"||b==="button")&&"submit"===a.type},image:function(a){return a.nodeName.toLowerCase()==="input"&&"image"===a.type},reset:function(a){var b=a.nodeName.toLowerCase();return(b==="input"||b==="button")&&"reset"===a.type},button:function(a){var b=a.nodeName.toLowerCase();return b==="input"&&"button"===a.type||b==="button"},input:function(a){return/input|select|textarea|button/i.test(a.nodeName)},focus:function(a){return a===a.ownerDocument.activeElement}},setFilters:{first:function(a,b){return b===0},last:function(a,b,c,d){return b===d.length-1},even:function(a,b){return b%2===0},odd:function(a,b){return b%2===1},lt:function(a,b,c){return bc[3]-0},nth:function(a,b,c){return c[3]-0===b},eq:function(a,b,c){return c[3]-0===b}},filter:{PSEUDO:function(a,b,c,d){var e=b[1],f=o.filters[e];if(f)return f(a,c,b,d);if(e==="contains")return(a.textContent||a.innerText||n([a])||"").indexOf(b[3])>=0;if(e==="not"){var g=b[3];for(var h=0,i=g.length;h=0}},ID:function(a,b){return a.nodeType===1&&a.getAttribute("id")===b},TAG:function(a,b){return b==="*"&&a.nodeType===1||!!a.nodeName&&a.nodeName.toLowerCase()===b},CLASS:function(a,b){return(" "+(a.className||a.getAttribute("class"))+" ").indexOf(b)>-1},ATTR:function(a,b){var c=b[1],d=m.attr?m.attr(a,c):o.attrHandle[c]?o.attrHandle[c](a):a[c]!=null?a[c]:a.getAttribute(c),e=d+"",f=b[2],g=b[4];return d==null?f==="!=":!f&&m.attr?d!=null:f==="="?e===g:f==="*="?e.indexOf(g)>=0:f==="~="?(" "+e+" ").indexOf(g)>=0:g?f==="!="?e!==g:f==="^="?e.indexOf(g)===0:f==="$="?e.substr(e.length-g.length)===g:f==="|="?e===g||e.substr(0,g.length+1)===g+"-":!1:e&&d!==!1},POS:function(a,b,c,d){var e=b[2],f=o.setFilters[e];if(f)return f(a,c,b,d)}}},p=o.match.POS,q=function(a,b){return"\\"+(b-0+1)};for(var r in o.match)o.match[r]=new RegExp(o.match[r].source+/(?![^\[]*\])(?![^\(]*\))/.source),o.leftMatch[r]=new RegExp(/(^(?:.|\r|\n)*?)/.source+o.match[r].source.replace(/\\(\d+)/g,q));var s=function(a,b){a=Array.prototype.slice.call(a,0);if(b){b.push.apply(b,a);return b}return a};try{Array.prototype.slice.call(c.documentElement.childNodes,0)[0].nodeType}catch(t){s=function(a,b){var c=0,d=b||[];if(g.call(a)==="[object Array]")Array.prototype.push.apply(d,a);else if(typeof a.length=="number")for(var e=a.length;c",e.insertBefore(a,e.firstChild),c.getElementById(d)&&(o.find.ID=function(a,c,d){if(typeof c.getElementById!="undefined"&&!d){var e=c.getElementById(a[1]);return e?e.id===a[1]||typeof e.getAttributeNode!="undefined"&&e.getAttributeNode("id").nodeValue===a[1]?[e]:b:[]}},o.filter.ID=function(a,b){var c=typeof a.getAttributeNode!="undefined"&&a.getAttributeNode("id");return a.nodeType===1&&c&&c.nodeValue===b}),e.removeChild(a),e=a=null}(),function(){var a=c.createElement("div");a.appendChild(c.createComment("")),a.getElementsByTagName("*").length>0&&(o.find.TAG=function(a,b){var c=b.getElementsByTagName(a[1]);if(a[1]==="*"){var d=[];for(var e=0;c[e];e++)c[e].nodeType===1&&d.push(c[e]);c=d}return c}),a.innerHTML="",a.firstChild&&typeof a.firstChild.getAttribute!="undefined"&&a.firstChild.getAttribute("href")!=="#"&&(o.attrHandle.href=function(a){return a.getAttribute("href",2)}),a=null}(),c.querySelectorAll&&function(){var a=m,b=c.createElement("div"),d="__sizzle__";b.innerHTML="

";if(!b.querySelectorAll||b.querySelectorAll(".TEST").length!==0){m=function(b,e,f,g){e=e||c;if(!g&&!m.isXML(e)){var h=/^(\w+$)|^\.([\w\-]+$)|^#([\w\-]+$)/.exec(b);if(h&&(e.nodeType===1||e.nodeType===9)){if(h[1])return s(e.getElementsByTagName(b),f);if(h[2]&&o.find.CLASS&&e.getElementsByClassName)return s(e.getElementsByClassName(h[2]),f)}if(e.nodeType===9){if(b==="body"&&e.body)return s([e.body],f);if(h&&h[3]){var i=e.getElementById(h[3]);if(!i||!i.parentNode)return s([],f);if(i.id===h[3])return s([i],f)}try{return s(e.querySelectorAll(b),f)}catch(j){}}else if(e.nodeType===1&&e.nodeName.toLowerCase()!=="object"){var k=e,l=e.getAttribute("id"),n=l||d,p=e.parentNode,q=/^\s*[+~]/.test(b);l?n=n.replace(/'/g,"\\$&"):e.setAttribute("id",n),q&&p&&(e=e.parentNode);try{if(!q||p)return s(e.querySelectorAll("[id='"+n+"'] "+b),f)}catch(r){}finally{l||k.removeAttribute("id")}}}return a(b,e,f,g)};for(var e in a)m[e]=a[e];b=null}}(),function(){var a=c.documentElement,b=a.matchesSelector||a.mozMatchesSelector||a.webkitMatchesSelector||a.msMatchesSelector;if(b){var d=!b.call(c.createElement("div"),"div"),e=!1;try{b.call(c.documentElement,"[test!='']:sizzle")}catch(f){e=!0}m.matchesSelector=function(a,c){c=c.replace(/\=\s*([^'"\]]*)\s*\]/g,"='$1']");if(!m.isXML(a))try{if(e||!o.match.PSEUDO.test(c)&&!/!=/.test(c)){var f=b.call(a,c);if(f||!d||a.document&&a.document.nodeType!==11)return f}}catch(g){}return m(c,null,null,[a]).length>0}}}(),function(){var a=c.createElement("div");a.innerHTML="
";if(!!a.getElementsByClassName&&a.getElementsByClassName("e").length!==0){a.lastChild.className="e";if(a.getElementsByClassName("e").length===1)return;o.order.splice(1,0,"CLASS"),o.find.CLASS=function(a,b,c){if(typeof b.getElementsByClassName!="undefined"&&!c)return b.getElementsByClassName(a[1])},a=null}}(),c.documentElement.contains?m.contains=function(a,b){return a!==b&&(a.contains?a.contains(b):!0)}:c.documentElement.compareDocumentPosition?m.contains=function(a,b){return!!(a.compareDocumentPosition(b)&16)}:m.contains=function(){return!1},m.isXML=function(a){var b=(a?a.ownerDocument||a:0).documentElement;return b?b.nodeName!=="HTML":!1};var y=function(a,b,c){var d,e=[],f="",g=b.nodeType?[b]:b;while(d=o.match.PSEUDO.exec(a))f+=d[0],a=a.replace(o.match.PSEUDO,"");a=o.relative[a]?a+"*":a;for(var h=0,i=g.length;h0)for(h=g;h=0:f.filter(a,this).length>0:this.filter(a).length>0)},closest:function(a,b){var c=[],d,e,g=this[0];if(f.isArray(a)){var h=1;while(g&&g.ownerDocument&&g!==b){for(d=0;d-1:f.find.matchesSelector(g,a)){c.push(g);break}g=g.parentNode;if(!g||!g.ownerDocument||g===b||g.nodeType===11)break}}c=c.length>1?f.unique(c):c;return this.pushStack(c,"closest",a)},index:function(a){if(!a)return this[0]&&this[0].parentNode?this.prevAll().length:-1;if(typeof a=="string")return f.inArray(this[0],f(a));return f.inArray(a.jquery?a[0]:a,this)},add:function(a,b){var c=typeof a=="string"?f(a,b):f.makeArray(a&&a.nodeType?[a]:a),d=f.merge(this.get(),c);return this.pushStack(V(c[0])||V(d[0])?d:f.unique(d))},andSelf:function(){return this.add(this.prevObject)}}),f.each({parent:function(a){var b=a.parentNode;return b&&b.nodeType!==11?b:null},parents:function(a){return f.dir(a,"parentNode")},parentsUntil:function(a,b,c){return f.dir(a,"parentNode",c)},next:function(a){return f.nth(a,2,"nextSibling")},prev:function(a){return f.nth(a,2,"previousSibling")},nextAll:function(a){return f.dir(a,"nextSibling")},prevAll:function(a){return f.dir(a,"previousSibling")},nextUntil:function(a,b,c){return f.dir(a,"nextSibling",c)},prevUntil:function(a,b,c){return f.dir(a,"previousSibling",c)},siblings:function(a){return f.sibling(a.parentNode.firstChild,a)},children:function(a){return f.sibling(a.firstChild)},contents:function(a){return f.nodeName(a,"iframe")?a.contentDocument||a.contentWindow.document:f.makeArray(a.childNodes)}},function(a,b){f.fn[a]=function(c,d){var e=f.map(this,b,c),g=S.call(arguments);O.test(a)||(d=c),d&&typeof d=="string"&&(e=f.filter(d,e)),e=this.length>1&&!U[a]?f.unique(e):e,(this.length>1||Q.test(d))&&P.test(a)&&(e=e.reverse());return this.pushStack(e,a,g.join(","))}}),f.extend({filter:function(a,b,c){c&&(a=":not("+a+")");return b.length===1?f.find.matchesSelector(b[0],a)?[b[0]]:[]:f.find.matches(a,b)},dir:function(a,c,d){var e=[],g=a[c];while(g&&g.nodeType!==9&&(d===b||g.nodeType!==1||!f(g).is(d)))g.nodeType===1&&e.push(g),g=g[c];return e},nth:function(a,b,c,d){b=b||1;var e=0;for(;a;a=a[c])if(a.nodeType===1&&++e===b)break;return a},sibling:function(a,b){var c=[];for(;a;a=a.nextSibling)a.nodeType===1&&a!==b&&c.push(a);return c}});var Y="abbr article aside audio canvas datalist details figcaption figure footer header hgroup mark meter nav output progress section summary time video",Z=/ jQuery\d+="(?:\d+|null)"/g,$=/^\s+/,_=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:]+)[^>]*)\/>/ig,ba=/<([\w:]+)/,bb=/",""],legend:[1,"
","
"],thead:[1,"","
"],tr:[2,"","
"],td:[3,"","
"],col:[2,"","
"],area:[1,"",""],_default:[0,"",""]},bk=X(c);bj.optgroup=bj.option,bj.tbody=bj.tfoot=bj.colgroup=bj.caption=bj.thead,bj.th=bj.td,f.support.htmlSerialize||(bj._default=[1,"div
","
"]),f.fn.extend({text:function(a){if(f.isFunction(a))return this.each(function(b){var c=f(this);c.text(a.call(this,b,c.text()))});if(typeof a!="object"&&a!==b)return this.empty().append((this[0]&&this[0].ownerDocument||c).createTextNode(a));return f.text(this)},wrapAll:function(a){if(f.isFunction(a))return this.each(function(b){f(this).wrapAll(a.call(this,b))});if(this[0]){var b=f(a,this[0].ownerDocument).eq(0).clone(!0);this[0].parentNode&&b.insertBefore(this[0]),b.map(function(){var a=this;while(a.firstChild&&a.firstChild.nodeType===1)a=a.firstChild;return a}).append(this)}return this},wrapInner:function(a){if(f.isFunction(a))return this.each(function(b){f(this).wrapInner(a.call(this,b))});return this.each(function(){var b=f(this),c=b.contents();c.length?c.wrapAll(a):b.append(a)})},wrap:function(a){return this.each(function(){f(this).wrapAll(a)})},unwrap:function(){return this.parent().each(function(){f.nodeName(this,"body")||f(this).replaceWith(this.childNodes)}).end()},append:function(){return this.domManip(arguments,!0,function(a){this.nodeType===1&&this.appendChild(a)})},prepend:function(){return this.domManip(arguments,!0,function(a){this.nodeType===1&&this.insertBefore(a,this.firstChild)})},before:function(){if(this[0]&&this[0].parentNode)return this.domManip(arguments,!1,function(a){this.parentNode.insertBefore(a,this)});if(arguments.length){var a=f(arguments[0]);a.push.apply(a,this.toArray());return this.pushStack(a,"before",arguments)}},after:function(){if(this[0]&&this[0].parentNode)return this.domManip(arguments,!1,function(a){this.parentNode.insertBefore(a,this.nextSibling)});if(arguments.length){var a=this.pushStack(this,"after" +,arguments);a.push.apply(a,f(arguments[0]).toArray());return a}},remove:function(a,b){for(var c=0,d;(d=this[c])!=null;c++)if(!a||f.filter(a,[d]).length)!b&&d.nodeType===1&&(f.cleanData(d.getElementsByTagName("*")),f.cleanData([d])),d.parentNode&&d.parentNode.removeChild(d);return this},empty:function(){for(var a=0,b;(b=this[a])!=null;a++){b.nodeType===1&&f.cleanData(b.getElementsByTagName("*"));while(b.firstChild)b.removeChild(b.firstChild)}return this},clone:function(a,b){a=a==null?!1:a,b=b==null?a:b;return this.map(function(){return f.clone(this,a,b)})},html:function(a){if(a===b)return this[0]&&this[0].nodeType===1?this[0].innerHTML.replace(Z,""):null;if(typeof a=="string"&&!bd.test(a)&&(f.support.leadingWhitespace||!$.test(a))&&!bj[(ba.exec(a)||["",""])[1].toLowerCase()]){a=a.replace(_,"<$1>");try{for(var c=0,d=this.length;c1&&l0?this.clone(!0):this).get();f(e[h])[b](j),d=d.concat(j)}return this.pushStack(d,a,e.selector)}}),f.extend({clone:function(a,b,c){var d=a.cloneNode(!0),e,g,h;if((!f.support.noCloneEvent||!f.support.noCloneChecked)&&(a.nodeType===1||a.nodeType===11)&&!f.isXMLDoc(a)){bn(a,d),e=bo(a),g=bo(d);for(h=0;e[h];++h)g[h]&&bn(e[h],g[h])}if(b){bm(a,d);if(c){e=bo(a),g=bo(d);for(h=0;e[h];++h)bm(e[h],g[h])}}e=g=null;return d},clean:function(a,b,d,e){var g;b=b||c,typeof b.createElement=="undefined"&&(b=b.ownerDocument||b[0]&&b[0].ownerDocument||c);var h=[],i;for(var j=0,k;(k=a[j])!=null;j++){typeof k=="number"&&(k+="");if(!k)continue;if(typeof k=="string")if(!bc.test(k))k=b.createTextNode(k);else{k=k.replace(_,"<$1>");var l=(ba.exec(k)||["",""])[1].toLowerCase(),m=bj[l]||bj._default,n=m[0],o=b.createElement("div");b===c?bk.appendChild(o):X(b).appendChild(o),o.innerHTML=m[1]+k+m[2];while(n--)o=o.lastChild;if(!f.support.tbody){var p=bb.test(k),q=l==="table"&&!p?o.firstChild&&o.firstChild.childNodes:m[1]===""&&!p?o.childNodes:[];for(i=q.length-1;i>=0;--i)f.nodeName(q[i],"tbody")&&!q[i].childNodes.length&&q[i].parentNode.removeChild(q[i])}!f.support.leadingWhitespace&&$.test(k)&&o.insertBefore(b.createTextNode($.exec(k)[0]),o.firstChild),k=o.childNodes}var r;if(!f.support.appendChecked)if(k[0]&&typeof (r=k.length)=="number")for(i=0;i=0)return b+"px"}}}),f.support.opacity||(f.cssHooks.opacity={get:function(a,b){return bt.test((b&&a.currentStyle?a.currentStyle.filter:a.style.filter)||"")?parseFloat(RegExp.$1)/100+"":b?"1":""},set:function(a,b){var c=a.style,d=a.currentStyle,e=f.isNumeric(b)?"alpha(opacity="+b*100+")":"",g=d&&d.filter||c.filter||"";c.zoom=1;if(b>=1&&f.trim(g.replace(bs,""))===""){c.removeAttribute("filter");if(d&&!d.filter)return}c.filter=bs.test(g)?g.replace(bs,e):g+" "+e}}),f(function(){f.support.reliableMarginRight||(f.cssHooks.marginRight={get:function(a,b){var c;f.swap(a,{display:"inline-block"},function(){b?c=bB(a,"margin-right","marginRight"):c=a.style.marginRight});return c}})}),c.defaultView&&c.defaultView.getComputedStyle&&(bC=function(a,c){var d,e,g;c=c.replace(bu,"-$1").toLowerCase();if(!(e=a.ownerDocument.defaultView))return b;if(g=e.getComputedStyle(a,null))d=g.getPropertyValue(c),d===""&&!f.contains(a.ownerDocument.documentElement,a)&&(d=f.style(a,c));return d}),c.documentElement.currentStyle&&(bD=function(a,b){var c,d,e,f=a.currentStyle&&a.currentStyle[b],g=a.style;f===null&&g&&(e=g[b])&&(f=e),!bv.test(f)&&bw.test(f)&&(c=g.left,d=a.runtimeStyle&&a.runtimeStyle.left,d&&(a.runtimeStyle.left=a.currentStyle.left),g.left=b==="fontSize"?"1em":f||0,f=g.pixelLeft+"px",g.left=c,d&&(a.runtimeStyle.left=d));return f===""?"auto":f}),bB=bC||bD,f.expr&&f.expr.filters&&(f.expr.filters.hidden=function(a){var b=a.offsetWidth,c=a.offsetHeight;return b===0&&c===0||!f.support.reliableHiddenOffsets&&(a.style&&a.style.display||f.css(a,"display"))==="none"},f.expr.filters.visible=function(a){return!f.expr.filters.hidden(a)});var bF=/%20/g,bG=/\[\]$/,bH=/\r?\n/g,bI=/#.*$/,bJ=/^(.*?):[ \t]*([^\r\n]*)\r?$/mg,bK=/^(?:color|date|datetime|datetime-local|email|hidden|month|number|password|range|search|tel|text|time|url|week)$/i,bL=/^(?:about|app|app\-storage|.+\-extension|file|res|widget):$/,bM=/^(?:GET|HEAD)$/,bN=/^\/\//,bO=/\?/,bP=/)<[^<]*)*<\/script>/gi,bQ=/^(?:select|textarea)/i,bR=/\s+/,bS=/([?&])_=[^&]*/,bT=/^([\w\+\.\-]+:)(?:\/\/([^\/?#:]*)(?::(\d+))?)?/,bU=f.fn.load,bV={},bW={},bX,bY,bZ=["*/"]+["*"];try{bX=e.href}catch(b$){bX=c.createElement("a"),bX.href="",bX=bX.href}bY=bT.exec(bX.toLowerCase())||[],f.fn.extend({load:function(a,c,d){if(typeof a!="string"&&bU)return bU.apply(this,arguments);if(!this.length)return this;var e=a.indexOf(" ");if(e>=0){var g=a.slice(e,a.length);a=a.slice(0,e)}var h="GET";c&&(f.isFunction(c)?(d=c,c=b):typeof c=="object"&&(c=f.param(c,f.ajaxSettings.traditional),h="POST"));var i=this;f.ajax({url:a,type:h,dataType:"html",data:c,complete:function(a,b,c){c=a.responseText,a.isResolved()&&(a.done(function(a){c=a}),i.html(g?f("
").append(c.replace(bP,"")).find(g):c)),d&&i.each(d,[c,b,a])}});return this},serialize:function(){return f.param(this.serializeArray())},serializeArray:function(){return this.map(function(){return this.elements?f.makeArray(this.elements):this}).filter(function(){return this.name&&!this.disabled&&(this.checked||bQ.test(this.nodeName)||bK.test(this.type))}).map(function(a,b){var c=f(this).val();return c==null?null:f.isArray(c)?f.map(c,function(a,c){return{name:b.name,value:a.replace(bH,"\r\n")}}):{name:b.name,value:c.replace(bH,"\r\n")}}).get()}}),f.each("ajaxStart ajaxStop ajaxComplete ajaxError ajaxSuccess ajaxSend".split(" "),function(a,b){f.fn[b]=function(a){return this.bind(b,a)}}),f.each(["get","post"],function(a,c){f[c]=function(a,d,e,g){f.isFunction(d)&&(g=g||e,e=d,d=b);return f.ajax({type:c,url:a,data:d,success:e,dataType:g})}}),f.extend({getScript:function(a,c){return f.get(a,b,c,"script")},getJSON:function(a,b,c){return f.get(a,b,c,"json")},ajaxSetup:function(a,b){b?cb(a,f.ajaxSettings):(b=a,a=f.ajaxSettings),cb(a,b);return a},ajaxSettings:{url:bX,isLocal:bL.test(bY[1]),global:!0,type:"GET",contentType:"application/x-www-form-urlencoded",processData:!0,async:!0,accepts:{xml:"application/xml, text/xml",html:"text/html",text:"text/plain",json:"application/json, text/javascript","*":bZ},contents:{xml:/xml/,html:/html/,json:/json/},responseFields:{xml:"responseXML",text:"responseText"},converters:{"* text":a.String,"text html":!0,"text json":f.parseJSON,"text xml":f.parseXML},flatOptions:{context:!0,url:!0}},ajaxPrefilter:b_(bV),ajaxTransport:b_(bW),ajax:function(a,c){function w(a,c,l,m){if(s!==2){s=2,q&&clearTimeout(q),p=b,n=m||"",v.readyState=a>0?4:0;var o,r,u,w=c,x=l?cd(d,v,l):b,y,z;if(a>=200&&a<300||a===304){if(d.ifModified){if(y=v.getResponseHeader("Last-Modified"))f.lastModified[k]=y;if(z=v.getResponseHeader("Etag"))f.etag[k]=z}if(a===304)w="notmodified",o=!0;else try{r=ce(d,x),w="success",o=!0}catch(A){w="parsererror",u=A}}else{u=w;if(!w||a)w="error",a<0&&(a=0)}v.status=a,v.statusText=""+(c||w),o?h.resolveWith(e,[r,w,v]):h.rejectWith(e,[v,w,u]),v.statusCode(j),j=b,t&&g.trigger("ajax"+(o?"Success":"Error"),[v,d,o?r:u]),i.fireWith(e,[v,w]),t&&(g.trigger("ajaxComplete",[v,d]),--f.active||f.event.trigger("ajaxStop"))}}typeof a=="object"&&(c=a,a=b),c=c||{};var d=f.ajaxSetup({},c),e=d.context||d,g=e!==d&&(e.nodeType||e instanceof f)?f(e):f.event,h=f.Deferred(),i=f.Callbacks("once memory"),j=d.statusCode||{},k,l={},m={},n,o,p,q,r,s=0,t,u,v={readyState:0,setRequestHeader:function(a,b){if(!s){var c=a.toLowerCase();a=m[c]=m[c]||a,l[a]=b}return this},getAllResponseHeaders:function(){return s===2?n:null},getResponseHeader:function(a){var c;if(s===2){if(!o){o={};while(c=bJ.exec(n))o[c[1].toLowerCase()]=c[2]}c=o[a.toLowerCase()]}return c===b?null:c},overrideMimeType:function(a){s||(d.mimeType=a);return this},abort:function(a){a=a||"abort",p&&p.abort(a),w(0,a);return this}};h.promise(v),v.success=v.done,v.error=v.fail,v.complete=i.add,v.statusCode=function(a){if(a){var b;if(s<2)for(b in a)j[b]=[j[b],a[b]];else b=a[v.status],v.then(b,b)}return this},d.url=((a||d.url)+"").replace(bI,"").replace(bN,bY[1]+"//"),d.dataTypes=f.trim(d.dataType||"*").toLowerCase().split(bR),d.crossDomain==null&&(r=bT.exec(d.url.toLowerCase()),d.crossDomain=!(!r||r[1]==bY[1]&&r[2]==bY[2]&&(r[3]||(r[1]==="http:"?80:443))==(bY[3]||(bY[1]==="http:"?80:443)))),d.data&&d.processData&&typeof d.data!="string"&&(d.data=f.param(d.data,d.traditional)),ca(bV,d,c,v);if(s===2)return!1;t=d.global,d.type=d.type.toUpperCase(),d.hasContent=!bM.test(d.type),t&&f.active++===0&&f.event.trigger("ajaxStart");if(!d.hasContent){d.data&&(d.url+=(bO.test(d.url)?"&":"?")+d.data,delete d.data),k=d.url;if(d.cache===!1){var x=f.now(),y=d.url.replace(bS,"$1_="+x);d.url=y+(y===d.url?(bO.test(d.url)?"&":"?")+"_="+x:"")}}(d.data&&d.hasContent&&d.contentType!==!1||c.contentType)&&v.setRequestHeader("Content-Type",d.contentType),d.ifModified&&(k=k||d.url,f.lastModified[k]&&v.setRequestHeader("If-Modified-Since",f.lastModified[k]),f.etag[k]&&v.setRequestHeader("If-None-Match",f.etag[k])),v.setRequestHeader("Accept",d.dataTypes[0]&&d.accepts[d.dataTypes[0]]?d.accepts[d.dataTypes[0]]+(d.dataTypes[0]!=="*"?", "+bZ+"; q=0.01":""):d.accepts["*"]);for(u in d.headers)v.setRequestHeader(u,d.headers[u]);if(d.beforeSend&&(d.beforeSend.call(e,v,d)===!1||s===2)){v.abort();return!1}for(u in{success:1,error:1,complete:1})v[u](d[u]);p=ca(bW,d,c,v);if(!p)w(-1,"No Transport");else{v.readyState=1,t&&g.trigger("ajaxSend",[v,d]),d.async&&d.timeout>0&&(q=setTimeout(function(){v.abort("timeout")},d.timeout));try{s=1,p.send(l,w)}catch(z){s<2?w(-1,z):f.error(z)}}return v},param:function(a,c){var d=[],e=function(a,b){b=f.isFunction(b)?b():b,d[d.length]=encodeURIComponent(a)+"="+encodeURIComponent(b)};c===b&&(c=f.ajaxSettings.traditional);if(f.isArray(a)||a.jquery&&!f.isPlainObject(a))f.each(a,function(){e(this.name,this.value)});else for(var g in a)cc(g,a[g],c,e);return d.join("&").replace(bF,"+")}}),f.extend({active:0,lastModified:{},etag:{}});var cf=f.now(),cg=/(\=)\?(&|$)|\?\?/i;f.ajaxSetup({jsonp:"callback",jsonpCallback:function(){return f.expando+"_"+cf++}}),f.ajaxPrefilter("json jsonp",function(b,c,d){var e=b.contentType==="application/x-www-form-urlencoded"&&typeof b.data=="string";if(b.dataTypes[0]==="jsonp"||b.jsonp!==!1&&(cg.test(b.url)||e&&cg.test(b.data))){var g,h=b.jsonpCallback=f.isFunction(b.jsonpCallback)?b.jsonpCallback():b.jsonpCallback,i=a[h],j=b.url,k=b.data,l="$1"+h+"$2";b.jsonp!==!1&&(j=j.replace(cg,l),b.url===j&&(e&&(k=k.replace(cg,l)),b.data===k&&(j+=(/\?/.test(j)?"&":"?")+b.jsonp+"="+h))),b.url=j,b.data=k,a[h]=function(a){g=[a]},d.always(function(){a[h]=i,g&&f.isFunction(i)&&a[h](g[0])}),b.converters["script json"]=function(){g||f.error(h+" was not called");return g[0]},b.dataTypes[0]="json";return"script"}}),f.ajaxSetup({accepts:{script:"text/javascript, application/javascript, application/ecmascript, application/x-ecmascript"},contents:{script:/javascript|ecmascript/},converters:{"text script":function(a){f.globalEval(a);return a}}}),f.ajaxPrefilter("script",function(a){a.cache===b&&(a.cache=!1),a.crossDomain&&(a.type="GET",a.global=!1)}),f.ajaxTransport("script",function(a){if(a.crossDomain){var d,e=c.head||c.getElementsByTagName("head")[0]||c.documentElement;return{send:function(f,g){d=c.createElement("script"),d.async="async",a.scriptCharset&&(d.charset=a.scriptCharset),d.src=a.url,d.onload=d.onreadystatechange=function(a,c){if(c||!d.readyState||/loaded|complete/.test(d.readyState))d.onload=d.onreadystatechange=null,e&&d.parentNode&&e.removeChild(d),d=b,c||g(200,"success")},e.insertBefore(d,e.firstChild)},abort:function(){d&&d.onload(0,1)}}}});var ch=a.ActiveXObject?function(){for(var a in cj)cj[a](0,1)}:!1,ci=0,cj;f.ajaxSettings.xhr=a.ActiveXObject?function(){return!this.isLocal&&ck()||cl()}:ck,function(a){f.extend(f.support,{ajax:!!a,cors:!!a&&"withCredentials"in a})}(f.ajaxSettings.xhr()),f.support.ajax&&f.ajaxTransport(function(c){if(!c.crossDomain||f.support.cors){var d;return{send:function(e,g){var h=c.xhr(),i,j;c.username?h.open(c.type,c.url,c.async,c.username,c.password):h.open(c.type,c.url,c.async);if(c.xhrFields)for(j in c.xhrFields)h[j]=c.xhrFields[j];c.mimeType&&h.overrideMimeType&&h.overrideMimeType(c.mimeType),!c.crossDomain&&!e["X-Requested-With"]&&(e["X-Requested-With"]="XMLHttpRequest");try{for(j in e)h.setRequestHeader(j,e[j])}catch(k){}h.send(c.hasContent&&c.data||null),d=function(a,e){var j,k,l,m,n;try{if(d&&(e||h.readyState===4)){d=b,i&&(h.onreadystatechange=f.noop,ch&&delete cj[i]);if(e)h.readyState!==4&&h.abort();else{j=h.status,l=h.getAllResponseHeaders(),m={},n=h.responseXML,n&&n.documentElement&&(m.xml=n),m.text=h.responseText;try{k=h.statusText}catch(o){k=""}!j&&c.isLocal&&!c.crossDomain?j=m.text?200:404:j===1223&&(j=204)}}}catch(p){e||g(-1,p)}m&&g(j,k,m,l)},!c.async||h.readyState===4?d():(i=++ci,ch&&(cj||(cj={},f(a).unload(ch)),cj[i]=d),h.onreadystatechange=d)},abort:function(){d&&d(0,1)}}}});var cm={},cn,co,cp=/^(?:toggle|show|hide)$/,cq=/^([+\-]=)?([\d+.\-]+)([a-z%]*)$/i,cr,cs=[["height","marginTop","marginBottom","paddingTop","paddingBottom"],["width","marginLeft","marginRight","paddingLeft","paddingRight"],["opacity"]],ct;f.fn.extend({show:function(a,b,c){var d,e;if(a||a===0)return this.animate(cw("show",3),a,b,c);for(var g=0,h=this.length;g=i.duration+this.startTime){this.now=this.end,this.pos=this.state=1,this.update(),i.animatedProperties[this.prop]=!0;for(b in i.animatedProperties)i.animatedProperties[b]!==!0&&(g=!1);if(g){i.overflow!=null&&!f.support.shrinkWrapBlocks&&f.each(["","X","Y"],function(a,b){h.style["overflow"+b]=i.overflow[a]}),i.hide&&f(h).hide();if(i.hide||i.show)for(b in i.animatedProperties)f.style(h,b,i.orig[b]),f.removeData(h,"fxshow"+b,!0),f.removeData(h,"toggle"+b,!0);d=i.complete,d&&(i.complete=!1,d.call(h))}return!1}i.duration==Infinity?this.now=e:(c=e-this.startTime,this.state=c/i.duration,this.pos=f.easing[i.animatedProperties[this.prop]](this.state,c,0,1,i.duration),this.now=this.start+(this.end-this.start)*this.pos),this.update();return!0}},f.extend(f.fx,{tick:function(){var a,b=f.timers,c=0;for(;c-1,k={},l={},m,n;j?(l=e.position(),m=l.top,n=l.left):(m=parseFloat(h)||0,n=parseFloat(i)||0),f.isFunction(b)&&(b=b.call(a,c,g)),b.top!=null&&(k.top=b.top-g.top+m),b.left!=null&&(k.left=b.left-g.left+n),"using"in b?b.using.call(a,k):e.css(k)}},f.fn.extend({position:function(){if(!this[0])return null;var a=this[0],b=this.offsetParent(),c=this.offset(),d=cz.test(b[0].nodeName)?{top:0,left:0}:b.offset();c.top-=parseFloat(f.css(a,"marginTop"))||0,c.left-=parseFloat(f.css(a,"marginLeft"))||0,d.top+=parseFloat(f.css(b[0],"borderTopWidth"))||0,d.left+=parseFloat(f.css(b[0],"borderLeftWidth"))||0;return{top:c.top-d.top,left:c.left-d.left}},offsetParent:function(){return this.map(function(){var a=this.offsetParent||c.body;while(a&&!cz.test(a.nodeName)&&f.css(a,"position")==="static")a=a.offsetParent;return a})}}),f.each(["Left","Top"],function(a,c){var d="scroll"+c;f.fn[d]=function(c){var e,g;if(c===b){e=this[0];if(!e)return null;g=cA(e);return g?"pageXOffset"in g?g[a?"pageYOffset":"pageXOffset"]:f.support.boxModel&&g.document.documentElement[d]||g.document.body[d]:e[d]}return this.each(function(){g=cA(this),g?g.scrollTo(a?f(g).scrollLeft():c,a?c:f(g).scrollTop()):this[d]=c})}}),f.each(["Height","Width"],function(a,c){var d=c.toLowerCase();f.fn["inner"+c]=function(){var a=this[0];return a?a.style?parseFloat(f.css(a,d,"padding")):this[d]():null},f.fn["outer"+c]=function(a){var b=this[0];return b?b.style?parseFloat(f.css(b,d,a?"margin":"border")):this[d]():null},f.fn[d]=function(a){var e=this[0];if(!e)return a==null?null:this;if(f.isFunction(a))return this.each(function(b){var c=f(this);c[d](a.call(this,b,c[d]()))});if(f.isWindow(e)){var g=e.document.documentElement["client"+c],h=e.document.body;return e.document.compatMode==="CSS1Compat"&&g||h&&h["client"+c]||g}if(e.nodeType===9)return Math.max(e.documentElement["client"+c],e.body["scroll"+c],e.documentElement["scroll"+c],e.body["offset"+c],e.documentElement["offset"+c]);if(a===b){var i=f.css(e,d),j=parseFloat(i);return f.isNumeric(j)?j:i}return this.css(d,typeof a=="string"?a:a+"px")}}),a.jQuery=a.$=f})(window); \ No newline at end of file diff --git a/web/cgi-bin/horas/js/util.js b/web/cgi-bin/horas/js/util.js new file mode 100644 index 00000000000..d01670f96c6 --- /dev/null +++ b/web/cgi-bin/horas/js/util.js @@ -0,0 +1,1758 @@ +String.prototype.repeat = function(num){return new Array(num+1).join(this);}; +String.prototype.reverse = function(){return this.split('').reverse().join('');}; +var regexLatinLongPenult = /([ao]e|au|[aeiouyāēīōūȳăĕĭŏŭäëïöüÿ])(?!([bcdgkpt][rl]|qu|[bcdfghjklmnprstvy])[aeiouyāēīōūȳăĕĭŏŭäëïöüÿ])((?:[bcdfghjklmnprstvy]{2,}|[xz])(?:[ao]e|au|[aeiouyāēīōūȳăĕĭŏŭäëïöüÿ])[bcdfghjklmnprstvxyz]*)$/i; +var linkSelector=""; +var linkDownloadSelector=""; + +var utf8_bom=String.fromCharCode(0xEF)+String.fromCharCode(0xBB)+String.fromCharCode(0xBF); +function encode_utf8( s ) +{ + return utf8_bom+unescape( encodeURIComponent( s ) ); +} +function decode_utf8( s ) +{ + return decodeURIComponent( escape( s ) ); +} + +var mapBooks = { + "Act": "Actus Apostolorum", + "Acts": "Actus Apostolorum", + "Apoc": "Apocalypsis", + "Cant": "Canticum Canticorum", + "Col": "Ad Colossenses", + "Cor": "Ad Corinthios", + "Dan": "Daniel", + "Deut": "Deuteronomium", + "Eccli": "Ecclesiasticus", + "Eph": "Ad Ephesios", + "Ephes": "Ad Ephesios", + "Esth": "Esther", + "Exod": "Exodus", + "Ezech": "Ezechiel", + "Gal": "Ad Galatas", + "Gen": "Genesis", + "Ha": "Habacuc", + "Heb": "Ad Hebræos", + "Hebr": "Ad Hebræos", + "Is": "Isaias", + "Isa": "Isaias", + "Isaiae": "Isaias", + "Jac": "Jacobi", + "Jas": "Jacobi", + "Jer": "Jeremias", + "Joann": "Joannes", + "Joannes": "Joannes", + "Joel": "Joel", + "John": "Joannis", + "Jonæ": "Jonas", + "Jud": "Judæ", + "Judith": "Judith", + "Lev": "Leviticus", + "Luc": "Lucas", + "Mach": "Machabæorum", + "Malach": 'Malachias', + "Marc": "Marcus", + "Matt": "Matthæus", + "Num": "Numeri", + "Par": "Paralipomenon", + "Pet": "Petri", + "Petri": "Petri", + "Phil": "Ad Philippenses", + "Philipp": "Ad Philippenses", + "Prov": "Proverbia", + "Ps": "Psalmi", + "Reg": "Regum", + "Rom": "Ad Romanos", + "Sap": "Sapientia", + "Thess": "Ad Thessalonicenses", + "Tim": "Ad Timotheum", + "Tit": 'Ad Titum', + "Tob": 'Tobiæ', + "Tobias": 'Tobiæ' +}; + +if (typeof Object.assign != 'function') { + // Must be writable: true, enumerable: false, configurable: true + Object.defineProperty(Object, "assign", { + value: function assign(target, varArgs) { // .length of function is 2 + 'use strict'; + if (target == null) { // TypeError if undefined or null + throw new TypeError('Cannot convert undefined or null to object'); + } + + var to = Object(target); + + for (var index = 1; index < arguments.length; index++) { + var nextSource = arguments[index]; + + if (nextSource != null) { // Skip over if undefined or null + for (var nextKey in nextSource) { + // Avoid bugs when hasOwnProperty is shadowed + if (Object.prototype.hasOwnProperty.call(nextSource, nextKey)) { + to[nextKey] = nextSource[nextKey]; + } + } + } + } + return to; + }, + writable: true, + configurable: true + }); +} + +function makeExsurgeChantContext() { + var ctxt = new exsurge.ChantContext(exsurge.TextMeasuringStrategy.Canvas); + ctxt.condenseLineAmount = 1; + ctxt.setGlyphScaling(1/16); + ctxt.setFont("'Crimson Text', serif", 19.2 / 0.9); + ctxt.spaceBetweenSystems = 0; + ctxt.textStyles.dropCap.size = 64; + ctxt.textStyles.annotation.size = 12.8; + ctxt.minLyricWordSpacing *= 0.7; + ctxt.accidentalSpaceMultiplier = 1.5; + + ctxt.specialCharProperties['font-family'] = "'Versiculum'"; + ctxt.specialCharProperties['font-variant'] = 'normal'; + // ctxt.specialCharProperties['font-size'] = (ctxt.lyricTextSize) + 'px'; + ctxt.specialCharProperties['font-weight'] = '400'; + const defaultSpecialCharText = ctxt.specialCharText; + ctxt.specialCharText = function(char) { return defaultSpecialCharText(char).toLowerCase(); }; + ctxt.setRubricColor('#d00'); + return ctxt; +} + +if(typeof HTMLTextAreaElement=='function') { +HTMLTextAreaElement.prototype.selectAndScroll = function(start,end,onlyUp) { + var text = this.value; + var txtBox = this; + setTimeout(function(){ + if(text != txtBox.value) return; + var scrollTop = txtBox.scrollTop; + var extra = '' + if(onlyUp) { + var $txtBox = $(txtBox); + var lineHeight = parseFloat($txtBox.css('line-height')); + if(isNaN(lineHeight)) lineHeight = 1.2 * parseFloat($txtBox.css('font-size')); + var rows = Math.floor($txtBox.height() / lineHeight); + extra = '\n'.repeat(rows-1); + } + txtBox.value = text.slice(0,end) + extra; + txtBox.scrollTop = txtBox.scrollHeight; + + txtBox.value = text; + txtBox.setSelectionRange(start,end); + if(((txtBox.scrollTop - scrollTop) * (onlyUp? -1 : 1)) < 0) txtBox.scrollTop = scrollTop; + }) +}; +} +var regexToneModifiers = /(')|(\.{1,2})|(_{1,4}0?)/g +var regexTones = new RegExp("([/ ,;:`]+)|((?:[fF]|[cC][bB]?)[1-4])|(?:(-)?(([A-M])|([a-m]))(([Vv]{1,3})|(s{1,3})|((<)|(>)|(~))|(w)|(o)|(O)|((x)|(y))|(q)|((R)|(r0)|(r(?![1-5])))|(r[1-5])|(\\+))?((?:" + regexToneModifiers.source.replace(/\((?!\?:)/g,"(?:") + ")*)(?:\\[([^\\]]*)(?:]|$))?|(z0))","g"); +// /([\/ ,;:`]+)|([cfCF][1-4])|(?:(-)?(([A-M])|([a-m]))(([Vv]{1,3})|(s{1,3})|((<)|(>)|(~))|(w)|(o)|(O)|((x)|(y))|(q)|((R)|(r0)|(r(?![1-5])))|(r[1-5]))?((?:(?:')|(?:\.{1,2})|(?:(?:_0?){1,4}))*)|(z0))|\[([^\]]*)(?:\]|$) )*)|(z0))|\[([^\]]*)(?:\]|$) +// /([\/ ,;:`]+)|([cfCF][1-4])|(?:(-)?(([A-M])|([a-m]))(([Vv]{1,3})|(s{1,3})|((<)|(>)|(~))|(w)|(o)|(O)|((x)|(y))|(q)|((R)|(r0)|(r(?![1-5])))|(r[1-5]))?((?:(?:')|(?:\.{1,2})|(?:(?:_0?){1,4}))*)|(z0))|\[([^\]]*)(?:\]|$) +var regexTonesSpliceIndex=27; +var regexToneModifiersCount = 4; +var rtg = { + whitespace: 1, + clef: 2, + initioDebilis: 3, + tone: 4, + toneUpper: 5, // diamond + toneLower: 6, + noteType: 7, // (([Vv]{1,3})|(s{1,3})|((<)|(>)|(~))|(w)|([oO])|([xy])|(q)]|(R|r0|r(?![1-5]))|(r[1-5])|(\+)) + virga: 8, // [Vv]{1,3} + stropha: 9, // s{1,3} + liquescentia: 10, // [<>~] + ascendingLiquescentia: 11, // < + descendingLiquescentia: 12, // > + diminutiveLiquescentia: 13, // ~ + quilisma: 14, // w + oriscus: 15, // o + oriscusReverse: 16, // O + accidental: 17, // [xy] + flat: 18, // x + natural: 19, // y + q: 20, // q + lineaPunctum: 22, // R + lineaPunctumCavum: 23, // r0 + punctumCavum: 24, // r + rNumber: 25, // r[1-5] + custos: 26, // \+ + ictus: 27, // (') + dot: 28, // (\.{1,2}) + episema: 29, // ((?:_0?)){1,4}) + bracketed: 30, // [text] + autoCustos: 31 // z0 +}; + +function setPdfLinkSelector(sel){ + linkSelector=sel; +}; +function onDragStart(e){ + console.info(e); + e.originalEvent.dataTransfer.setData("DownloadURL",this.getAttribute("data-downloadurl")); +}; +function setGabcLinkSelector(sel){ + linkDownloadSelector=sel; + $(sel).bind("dragstart",onDragStart); +}; +function updateLinks(text){ + var header=getHeader(text); + if(header){ + text = text.slice(header.original.length); + } else { + header = '%%\n'; + } + if(linkSelector){ + $(linkSelector).attr("href","http://gregorio.gabrielmass.com/cgi/process.pl?gregtext=" + + window.escape(header+text) + "&gregfontselect=17&gregtextfontselect=12&greginitialselect=43&gregspaceselect=7mm&gregredselect=N&greglinethickselect=10&gregpaperselect=letterpaper&gregfaceselect=libertine&gregcropselect=N"); + } + try { + if(linkDownloadSelector){ + var utf8=encode_utf8(header+text); + var url="data:text/plain;charset=utf8;base64,"+btoa(utf8); + var filename = header.name||"Untitled"; + if(!filename.match(/\.gabc$/))filename += ".gabc"; + $(linkDownloadSelector).attr("charset","UTF-8") + .prop("href",url) + .prop("download",filename) + .attr("data-downloadurl","text/plain:"+filename+":"+url); + } + } catch(e) { + } + return [header,text]; +} + +var rog = { + syl:3, + gabc:5, + whitespace:7 +}; +var regexTag = /<(\/)?(\w+)>/i; +var regexOuter = /((([^\(\r\n]+)($|\())|\()([^\)]*)($|\))(?:(\s+)|(?=(?:\([^\)]*\))+(\s*))|)/g; +var regexHeaderEnd=/(?:^|\n)%%\s?\n/; +var regexHeaderLine = /^([\w-_.]+):\s*((?:[^;\r\n]|;[ \t])*)(?:;|$)/i; +var regexHeaderComment = /^%.*/; +function GabcHeader(text){ + if(typeof(text)!='string') text=''; + this.comments=[]; + this.cValues={}; + this.original=''; + var match=text.match(regexHeaderEnd); + if(match){ + var txtHeader = this.original = text.slice(0,match.index+match[0].length); + var lines = txtHeader.split(/\r?\n/g); + for(var i=0; i < lines.length; ++i){ + var line=lines[i], + match = regexHeaderLine.exec(line); + if(match){ + var key = match[1].replace(/-([a-z])/g,function(a,letter) { return letter.toUpperCase(); }); + if(this[match[1]]) { + var arrayName=match[1]+'Array'; + if(!this[arrayName]){ + this[arrayName] = [this[match[1]]]; + } + this[arrayName].push(match[2]); + } else { + this[match[1]]=match[2]; + } + if(key != match[1]) this[key] = this[match[1]]; + } else if((match = regexHeaderComment.exec(line))){ + if(line!='%%'){ + match = regexHeaderLine.exec(line.slice(1)); + if(match){ + var key = match[1].replace(/-([a-z])/g,function(a,letter) { return letter.toUpperCase(); }); + this.cValues[match[1]]=match[2]; + if(key != match[1]) this.cValues[key] = match[2]; + } else { + this.comments[i]=line; + } + } + } + } + } +} +GabcHeader.prototype.toString = function(){ + var result=[]; + for(key in this){ + if(key=='length' || key=='original' || key=='comments' || key=='cValues' || (typeof this[key])!="string")continue; + var alternateKey = key.replace(/[A-Z]/g,function(letter) { return '-'+letter.toLowerCase(); }); + if(alternateKey != key && alternateKey in this) continue; + var array = this[key+'Array']; + if(array) { + for(var i=0; i < array.length; ++i) { + result.push(key + ': ' + array[i] + ';'); + } + } else { + result.push(key + ': ' + this[key] + ';'); + } + } + for(key in this.cValues){ + if(key.length==0 || !this.cValues.hasOwnProperty(key))continue; + result .push('%'+key + ': ' + this.cValues[key] + ';'); + } + for(i in this.comments){ + if(!this.comments.hasOwnProperty(i)) continue; + try{ + result.splice(i,0,this.comments[i]); + } catch(e){} + } + return result.join('\n') + '\n%%\n'; +}; +function getHeaderLen(text){ + var match=text.match(regexHeaderEnd); + if(match){ + return match.index+match[0].length; + } else { + return 0; + } +} +function getHeader(text){ + return new GabcHeader(text); +} + +function getTagsFrom(txt){ + var tm,r=[]; + while(tm = regexTag.exec(txt)) { + r.push(tm[2]); + var lastIndex = tm.index + tm[0].length; + if(tm.index == 0) + txt = txt.slice(tm[0].length); + else txt = txt.slice(0,tm.index) + txt.slice(lastIndex); + } + return r; +} + +function transposeGabc(gabc,offset,noParens) { + var replaceLetter = function(letter, clef) { + if(clef) return letter; + var newLetter = String.fromCharCode(offset + letter.charCodeAt(0)); + if(!newLetter.match(/[a-m]/i)) throw true; + return newLetter; + }; + var regex = /([cf]b?[1-4])|[a-mA-M]/g; + if(noParens) return gabc.replace(regex, replaceLetter); + return gabc.replace(/\(([^)]+)\)/g, function(whole,gabc) { + return '(' + gabc.replace(regex, replaceLetter) + ')'; + }); +} + +function gabcEditorKeyDown(e) { + var $this = $(this), txt = $this.val(), selStart = this.selectionStart, selEnd = this.selectionEnd; + switch(e.which) { + case 66: //b + if(e.ctrlKey || e.altKey) { + e.preventDefault(); + index = txt.indexOf(' ',this.selectionEnd); + if(index <= 0) index = txt.length; + $this.val(txt.slice(0,index) + ' ()' + txt.slice(index)); + this.selectionEnd = this.selectionStart = index + 2; + } + break; + case 83: //s + if(selStart == selEnd && (e.ctrlKey || e.altKey) && txt[selStart-1]!='(' && txt[selStart]!=')') { + e.preventDefault(); + $this.val(txt.slice(0,selStart) + '()' + txt.slice(selStart)); + this.selectionEnd = this.selectionStart = selStart + 1; + } + break; + case 9: { //tab + var index, indexEnd, headerIndex; + e.preventDefault(); + if(e.shiftKey) { + // go backwards + index = this.selectionStart; + headerIndex = txt.lastIndexOf('\n%%\n',index-1); + index = txt.lastIndexOf(')',index - 1); + if(index <= headerIndex) index = txt.lastIndexOf(')'); + if(index >= 0) { + indexEnd = index; + index = txt.lastIndexOf('(',index); + } + } else { + index = this.selectionEnd; + var regex = /(\()|(-(?!\())|(\s+(?![:;!.]))|([^)\s]$)/g; + regex.lastIndex = index; + var match; + while((match = regex.exec(txt)) && (match[2]||match[3])) { + if(match[3] && (match.index==0 || txt[match.index-1]==')')) continue; + //check if this line is in the header: + index = match.index; + var begIndex = txt.lastIndexOf('\n',index-1)+1, + endIndex = txt.indexOf('\n',index); + if(endIndex < 0) endIndex = txt.length; + if(txt[endIndex]=='\r') endIndex--; + var line = txt.slice(begIndex,endIndex); + if(line.match(/^(?:\s*(?:%.*|[-\w]+:[^;]+;)\s*|%%)$/)) { + continue; + } else { + break; + } + } + if(match) { + if(match[1]) { + index = match.index; + } else if(match[2]||match[3]||match[4]) { + if(match[2]||match[4]) index = match.index+1; + txt = txt.slice(0,index) + '()' + txt.slice(index); + $this.val(txt); + } else { + index = txt.indexOf('('); + } + } else { + index = txt.indexOf('('); + } + index = txt.indexOf('(',index); + + if(index >= 0) { + indexEnd = txt.indexOf(')',index); + } + } + if(index >= 0 && indexEnd >= 0) { + this.selectionStart = index + 1; + this.selectionEnd = indexEnd; + } + break; + } + case 57: + if(e.shiftKey) { //open parenthesis + var rightSide = this.value.slice(selEnd), + firstClose = rightSide.indexOf(')'), + firstOpen = rightSide.indexOf('('); + if(firstClose < 0 || (firstOpen >= 0 && firstOpen < firstClose)) { + this.value=this.value.slice(0,this.selectionStart) + '()' + this.value.slice(selEnd); + this.selectionStart=this.selectionEnd=selStart+1; + e.preventDefault(); + return; + } + } + break; + case 48: + if(e.shiftKey) { //close parenthesis + if(selStart == selEnd && txt[selStart]==')') { + e.preventDefault(); + this.selectionStart = this.selectionEnd = selStart + 1; + } + } + break; + case 8: { + var selEnd = this.selectionEnd; + if(selEnd == this.selectionStart && selEnd > 0 && this.value[selEnd]==')' && this.value[selEnd-1]=='(') { + e.preventDefault(); + this.value=this.value.slice(0,this.selectionStart-1) + this.value.slice(selEnd+1); + this.selectionStart=this.selectionEnd=selEnd-1; + } + break; + } + case 38: // up + case 40: // down + if(e.altKey) { + var up = e.which === 38; + e.preventDefault(); + var allGabc = this.value + header = getHeader(allGabc), + selectionStart = this.selectionStart, + selectionEnd = this.selectionEnd, + gabc = allGabc = allGabc.slice(header.original.length); + if(selectionStart != selectionEnd) { + var startIndex = Math.max(0,selectionStart - header.original.length), + endIndex = Math.max(0,selectionEnd - header.original.length), + lastOpenParen = allGabc.lastIndexOf('(',startIndex), + lastCloseParen = allGabc.lastIndexOf(')',startIndex), + firstOpenParen = allGabc.indexOf('(',endIndex), + firstCloseParen = allGabc.indexOf(')',endIndex); + if(firstOpenParen < 0) firstOpenParen = Infinity; + if(firstCloseParen < 0) firstCloseParen = Infinity; + gabc = gabc.slice(startIndex, endIndex); + if(lastOpenParen > lastCloseParen) gabc = '(' + gabc; + if(firstCloseParen < firstOpenParen) gabc += ')'; + } + var offset = up? 1 : -1; + try { + gabc = transposeGabc(gabc, offset) + } catch(e) { + return; + } + if(selectionStart == selectionEnd) { + this.value = header.original + gabc; + } else { + if(lastOpenParen > lastCloseParen) gabc = gabc.slice(1); + if(firstCloseParen < firstOpenParen) gabc = gabc.slice(0,-1); + this.value = header.original + allGabc.slice(0,startIndex) + gabc + allGabc.slice(endIndex); + } + this.setSelectionRange(selectionStart, selectionEnd); + } + break; + } +} + +function makeInternationalTextBoxKeyDown(convertFlexa){ + var lastKey = 0; + var dictionaries= + {"'": + {"false": + {'a':'á', + 'e':'é', + 'i':'í', + 'o':'ó', + 'u':'ú', + 'y':'ý', + 'A':'Á', + 'E':'É', + 'I':'Í', + 'O':'Ó', + 'U':'Ú', + 'Y':'Ý', + 'æ':"ǽ", + 'œ':"œ́", + 'Æ':"Ǽ", + 'Œ':"Œ́" + }, + "true": + {'a':'ä', + 'e':'ë', + 'i':'ï', + 'o':'ö', + 'u':'ü', + 'y':'ÿ', + 'A':'Ä', + 'E':'Ë', + 'I':'Ï', + 'O':'Ö', + 'U':'Ü', + 'æ':"aë", + 'œ':"oë", + 'Æ':"Aë", + 'Œ':"Oë" + } + }, + "e": + {"false": + {'a':'æ', + 'o':'œ', + 'A':'Æ', + 'O':'Œ' + }, + "true": + {'a':'æ', + 'o':'œ', + 'A':'Æ', + 'O':'Œ' + } + }, + "Backspace": + {"false": + { + '†':"+", + 'æ':"ae", + 'œ':"oe", + 'Æ':"Ae", + 'Œ':"Oe", + 'á':'a', + 'é':'e', + 'í':'i', + 'ó':'o', + 'ú':'u', + 'ý':'y', + 'Á':'A', + 'É':'E', + 'Í':'I', + 'Ó':'O', + 'Ú':'U', + 'Ý':'Y', + 'ä':'a', + 'ë':'e', + 'ï':'i', + 'ö':'o', + 'ü':'u', + 'ÿ':'y', + 'Ä':'A', + 'Ë':'E', + 'Ï':'I', + 'Ö':'O', + 'Ü':'U', + 'Ǽ':"Aé", + 'ǽ':"aé", + 'Œ́':'Oé', + 'œ́':'oé' + }, + "true": + { + } + } + }; + var removeAccent = { + 'á':'a', + 'é':'e', + 'í':'i', + 'ó':'o', + 'ú':'u', + 'ý':'y', + 'Á':'A', + 'É':'E', + 'Í':'I', + 'Ó':'O', + 'Ú':'U', + 'Ý':'Y', + 'Ǽ':"Æ", + 'ǽ':"æ", + "áu": "au", + "oé": "oe", + "aé": "ae" + }; + var accentSyllable = function(syllables,which) { + word = ''; + for(var i = 0; i0) { + // Only process as international textbox if the cursor is not within parentheses: + var lastOpenParen = this.value.lastIndexOf('(',this.selectionStart-1); + var lastCloseParen = this.value.lastIndexOf(')',this.selectionStart-1); + if(lastCloseParen < lastOpenParen) return; + } + if(convertFlexa && e.which == 187 && e.shiftKey) { //if + was entered + var selStart=this.selectionStart; + var len=1; + this.value=this.value.slice(0,selStart) + '†' + this.value.slice(this.selectionEnd); + this.selectionStart=this.selectionEnd=selStart+len; + e.preventDefault(); + return; + } + var isEnglish=$("#cbEnglish")[0] && cbEnglish.checked; + if(e.which == 49 || e.which == 50 || (e.which == 51 && isEnglish)) { + if(e.shiftKey) return; + // swap e.which (49;50;51 => 2;1;0) + var which = 2 - (e.which - 49), + start = this.selectionStart, + end = this.selectionEnd, + wordStart = this.value.lastIndexOf(' ',start) + 1, + wordEnd = this.value.indexOf(' ',end); + if(wordEnd < 0) wordEnd = this.value.length; + if(isEnglish) { + var phrase = this.value.slice(wordStart,end).replace(/\*/g,''), + syllables = Syl.syllabify(phrase), + which = syllables.length - 1 - which; + if(which < 0) return; + var syl = syllables[which]; + phrase = phrase.slice(0,syl.index) + syl.sylnospace + '*' + phrase.slice(phrase.indexOf(syl.sylnospace,syl.index) + syl.sylnospace.length); + this.value = this.value.slice(0, wordStart) + phrase + this.value.slice(end); + // check if this phrase has multiple accents: + var lines = splitSentences(this.value.slice(wordStart)); + if(lines && lines[0] && lines[0].accents > 1 && lines[0][1].length - phrase.length < 4) { + line = lines[0]; + which = syllables.length - 1 - which; + phrase = this.value.slice(0,end); + syllables = Syl.syllabify(phrase); + syllables = syllables.slice(0, syllables.length - 1 - which); + var lastSyl = syllables.slice(-1)[0]; + var last3syl = syllables.slice(-3); + end = last3syl[0].index; + phrase = this.value.slice(end, lastSyl.index + lastSyl.sylnospace.length); + if(phrase.indexOf('*')<0) { + var accentSyl = lastSyl.word.length==1? lastSyl : last3syl[1]; + accentSyl.separator = '*'; + var index = accentSyl.index - end + accentSyl.sylnospace.length; + phrase = phrase.slice(0,index) + '*' + phrase.slice(index); + this.value = this.value.slice(0, end) + phrase + this.value.slice(end + phrase.length - 1); + } + this.selectAndScroll(last3syl[0].index, end + phrase.indexOf(lastSyl.sylnospace,lastSyl.index-end) + lastSyl.sylnospace.length + (lastSyl.separator && lastSyl.separator.length || 0), e.shiftKey); + + } else { + this.selectAndScroll(start, wordStart + phrase.length, e.shiftKey); + } + e.preventDefault(); + return; + } else { + // TODO: expand selection to entire word if it isn't currently on a whole word + var word = this.value.slice(start,end); + var syllables = word.match(regexLatin); + if(!syllables) return; + if(syllables.length>2) { + syllables = syllables.reverse(); + word = accentSyllable(syllables,which); + this.value = this.value.slice(0,start) + word + this.value.slice(end); + this.selectAndScroll(start,end, e.shiftKey); + e.preventDefault(); + } + } + } + if(e.which==9 || (!isEnglish && !e.shiftKey && (e.which == 49 || e.which == 50))) { + if(isEnglish) { + var selectionEnd = this.selectionEnd; + while(/\s/.test(this.value[selectionEnd])) { + ++selectionEnd; + } + if(this.selectionEnd == this.selectionStart) { + selectionEnd = 0; + this.scrollTop = 0; + } + var part, lines, line; + if(e.shiftKey) { + part = this.value.slice(0,this.selectionStart); + lines = splitSentences(part); + if(lines.length<2) return; + line = lines.slice(-2)[0]; + if(line) selectionEnd = part.lastIndexOf(line[1]); + } else { + part = this.value.slice(selectionEnd); + lines = splitSentences(part); + line = lines[0]; + var convertedWhitespace = this.value.slice(0,selectionEnd).replace(/\s/g,' '); + while(line && (line[1].length < 4 || Syl.syllabify(line[1]).length < 3)) { + if(selectionEnd > 0) { + selectionEnd = Math.max(0, convertedWhitespace.lastIndexOf(' ')); + convertedWhitespace = convertedWhitespace.slice(0, selectionEnd); + part = this.value.slice(selectionEnd); + lines = splitSentences(part); + line = lines[0]; + } else { + line = lines[1]; + break; + } + } + if(line) selectionEnd += part.indexOf(line[1]); + } + if(!line) return; + line = line[1]; + var syllables = Syl.syllabify(line); + if(syllables.length<3) return; + var lastSyl = syllables.slice(-1)[0]; + var last3syl = syllables.slice(-3); + if(line.indexOf('*',last3syl[0].index)<0) { + var accentSyl = lastSyl.word.length==1? lastSyl : last3syl[1]; + accentSyl.separator = '*'; + var index = accentSyl.index + accentSyl.sylnospace.length; + line = line.slice(0,index) + '*' + line.slice(index); + this.value = this.value.slice(0, selectionEnd) + line + this.value.slice(selectionEnd + line.length - 1); + } + this.selectAndScroll(selectionEnd + syllables.slice(-3)[0].index, selectionEnd + line.indexOf(lastSyl.sylnospace,lastSyl.index) + lastSyl.sylnospace.length + (lastSyl.separator && lastSyl.separator.length || 0), e.shiftKey); + e.preventDefault(); + return; + } + // else Latin: + var index = e.shiftKey? this.selectionStart : this.selectionEnd; + if(e.which == 9 && this.selectionEnd == this.selectionStart) index = e.shiftKey? this.value.length : 0; + var subIndex; + while(true) { + var slice = e.shiftKey? this.value.slice(0,index).reverse() : this.value.slice(index), + match = slice.match(/[a-zæœ]{3,}(?=$|[\s,.;!\?])/i), + word = match && match[0] || ''; + if(e.shiftKey) word = word.reverse(); + if(e.shiftKey) index -= match.index + word.length; + else index += match.index; + var syllables = word.match(regexLatin); + if(!syllables || syllables.length <= 2) { + if(!e.shiftKey) index += word.length; + continue; + } + var longPenult = word.match(regexLatinLongPenult); + if(longPenult) { + this.value = this.value.slice(0,index) + accentSyllable(syllables.reverse(),1) + this.value.slice((index += word.length)); + this.selectAndScroll(index - word.length, index, e.shiftKey); + continue; + } + this.selectAndScroll(index, index + word.length, e.shiftKey); + e.preventDefault(); + break; + } + } + var dictionary=dictionaries[e.key]; + if(dictionary && this.selectionStart==this.selectionEnd && this.selectionStart>0){ + var previousChar=this.value[this.selectionStart-1]; + var r=dictionary[e.shiftKey][previousChar]; + if(r){ + var selEnd=this.selectionEnd; + var len=r.length - 1; + this.value=this.value.slice(0,--this.selectionStart) + r + this.value.slice(selEnd); + this.selectionStart=this.selectionEnd=selEnd+len; + e.preventDefault(); + return; + } + } + } +}; +var internationalTextBoxKeyDown = makeInternationalTextBoxKeyDown(true); +function calculateDefaultStartPitch(startPitch, lowPitch, highPitch) { + return new exsurge.Pitch(startPitch + ((4 * 12 + 7) - Math.floor((lowPitch + highPitch) / 2))); +} +var Tone; +if(typeof window=='object') (function(window) { + var synth; + if(Tone) { + synth = new Tone.Synth({ + "oscillator" : { + type: "custom", + partials: [0.3,0.03,0.05] + }, + "envelope" : { + "attack" : 0.05, + "decay" : 0.3, + "sustain" : 0.4, + "release" : 0.8, + } + }).toMaster(); + Tone.Transport.bpm.value = 165; + window.setTempo = function(newTempo) { Tone.Transport.bpm.value = newTempo || 165; } + window.setRelativeTempo = function(delta) { + var state = Tone.Transport.state; + Tone.Transport.stop(); + var val = Tone.Transport.bpm.value = Math.round(Math.max(0, Tone.Transport.bpm.value + delta)) || 165; + if(state === 'started') { + Tone.Transport.clear(timeoutNextNote); + Tone.Transport.start(); + timeoutNextNote = Tone.Transport.scheduleOnce(playNextNote, '+8n'); + } + return val; + } + window.setIsUsingSolesmesLengths = function(val) { + localStorage.isUsingSolesmesLengths = val; + } + window.getIsUsingSolesmesLengths = function() { + return (localStorage.isUsingSolesmesLengths !== 'false'); + } + window.toggleIsUsingSolesmesLengths = function() { + return (localStorage.isUsingSolesmesLengths = !getIsUsingSolesmesLengths()); + } + window.playScore = function(score, firstPitch, startNote){ + Tone.Transport.clear(timeoutNextNote); + Tone.Transport.start(); + if($('#mediaControls').length == 0) { + $(document.body).append("
\ +
\ +
\ + \ +
\ +
\ + \ + \ + \ +
\ + 165 BPM
\ + \ + \ +
\ +
\ +
"); + + } + $('#mediaControls').removeClass('offscreen'); + if(syllable) { + syllable.classList.remove('active'); + syllable = null; + } + var originalSvg = score.svg; + var dropCap = !startNote && $('text', originalSvg)[0]; + if(dropCap) + dropCap.classList.add('active'); + var noteId = 0; + var notes = [].concat.apply([],score.notations.map(function(notation) { return notation.notes || notation; })).filter(function(notation) { return !notation.isAccidental; }); + if(startNote) noteId = Math.max(0, notes.indexOf(startNote)); + if(!firstPitch) firstPitch = score.defaultStartPitch; + if(!firstPitch) { + var startPitch = notes[0].pitch.toInt(), + pitches = notes.filter(function(note){return note.pitch;}).map(function(note) { return note.pitch && note.pitch.toInt(); }), + lowPitch = Math.min.apply(null, pitches), + highPitch = Math.max.apply(null, pitches); + firstPitch = score.defaultStartPitch = calculateDefaultStartPitch(startPitch, lowPitch, highPitch); + } + if(firstPitch.toInt) firstPitch = firstPitch.toInt(); + transpose = firstPitch - notes[0].pitch.toInt(); + _isPlaying = true; + + function getArePitchesEqual () { + var pitches = arguments[0] && Array.isArray(arguments[0]) ? arguments[0] : arguments; + if(pitches.length <= 1) return true; + var pitch = pitches[0]; + for (var i=0; i < pitches.length; i++) { + if(pitches[i].step !== pitch.step || pitches[i].octave !== pitch.octave) { + return false; + } + } + return true + } + + function getIsLastNoteInNeume (note) { + return note === note.neume.notes[note.neume.notes.length-1]; + } + function getIsFirstNoteInNeume (note) { + return note === note.neume.notes[0]; + } + + function getNoteIdForNote (notes, note) { + return notes.findIndex(function (n) { return n === note; }); + } + function getIsSalicus (notes, noteId) { + var note = notes[noteId]; + var nextNote = notes[noteId + 1]; + if(nextNote && nextNote.constructor != exsurge.Note) nextNote = null; + var prevNote = notes[noteId - 1]; + if(prevNote && prevNote.constructor != exsurge.Note) prevNote = null; + + if ( + note.ictus && prevNote && + (note.pitch.toInt() - prevNote.pitch.toInt() == 7) && + (nextNote.pitch.toInt() - note.pitch.toInt() == 1) + ) { + return true; + } else if ( + getIsUsingSolesmesLengths() && + note.ictus && note.ictus.glyphCode === "VerticalEpisemaBelow" && + (note.glyphVisualizer.glyphCode === "PodatusLower" || note.glyphVisualizer.glyphCode === "BeginningAscLiquescent") && + (note.pitch.toInt() - prevNote.pitch.toInt() > 0) && + (nextNote.pitch.toInt() - note.pitch.toInt() > 0) + ) { + return true; + } + + return false; + } + + function getNoteDuration (notes, noteId) { + var duration = 1; + var note = notes[noteId]; + var nextNote = notes[noteId + 1]; + if(nextNote && nextNote.constructor != exsurge.Note) nextNote = null; + var prevNote = notes[noteId - 1]; + if(prevNote && prevNote.constructor != exsurge.Note) prevNote = null; + + if(note.morae.length) { + duration = 2; + } else if(nextNote && (nextNote.morae.length > 1 || nextNote.shape == exsurge.NoteShape.Quilisma || getIsSalicus(notes, noteId))) { + duration = 1.8; + } else if(note.episemata.length) { + var episemataCount = 1; + if(prevNote && prevNote.episemata.length) ++ episemataCount; + if(nextNote && nextNote.episemata.length) ++ episemataCount; + duration += 0.9 / episemataCount; + } + + return duration; + } + + function getIsApostropha (note) { + var neume = note.neume; + return neume.isNeume && + neume.notes.length > 1 && + getArePitchesEqual(neume.notes.map(function (n) { return n.pitch; })); + } + + function getPressus (notes, noteId) { + var pressus; + var note = notes[noteId]; + var nextNote = notes[noteId + 1]; + if(nextNote && nextNote.constructor != exsurge.Note) nextNote = null; + var prevNote = notes[noteId - 1]; + if(prevNote && prevNote.constructor != exsurge.Note) prevNote = null; + var noteBeforePrev = notes[noteId - 2]; + if(noteBeforePrev && noteBeforePrev.constructor != exsurge.Note) noteBeforePrev = null; + + if ( + nextNote && nextNote.morae.length === 0 && note.morae.length === 0 && + getIsLastNoteInNeume(note) && getIsFirstNoteInNeume(nextNote) && + getArePitchesEqual(note.pitch, nextNote.pitch) && + (!prevNote || !getPressus(notes, noteId - 1)) && + !getIsApostropha(note) && !getIsApostropha(nextNote) && + nextNote.neume.lyrics.length === 0 + ) { + pressus = [note, nextNote]; + } else if ( + prevNote && prevNote.morae.length === 0 && note.morae.length === 0 && + getIsLastNoteInNeume(prevNote) && getIsFirstNoteInNeume(note) && + getArePitchesEqual(prevNote.pitch, note.pitch) && + (!noteBeforePrev || !getPressus(notes, noteId - 2)) && + !getIsApostropha(prevNote) && !getIsApostropha(note) && + note.neume.lyrics.length === 0 + ) { + pressus = [prevNote, note]; + } + + return pressus; + } + + function playNextNote (time){ + var note = notes[noteId]; + if(noteElem) noteElem.classList.remove('active','porrectus-left','porrectus-right'); + if(originalSvg != score.svg || note == null) { + if(syllable) syllable.classList.remove('active'); + _isPlaying = false; + } + if(!_isPlaying) { + if(dropCap) dropCap.classList.remove('active'); + $('#mediaControls').addClass('offscreen'); + return; + } + var duration = 1; + if(note.constructor != exsurge.Note) { + while(note.constructor != exsurge.Note && (!note.isDivider || note.constructor === exsurge.QuarterBar)) { + if(!(note = notes[++noteId])) return; + } + if(note.isDivider) { + if(syllable) syllable.classList.remove('active'); + if(note.constructor === exsurge.FullBar || note.constructor === exsurge.DoubleBar) { + duration = 2; + } // otherwise (for half bar) duration is default of 1. + } + } + noteElem = note.svgNode; + if(noteElem) { + var href = noteElem.attributes.getNamedItem('href').value; + if(href == '#None') { + noteElem = noteElem.previousSibling; + noteElem.classList.remove('porrectus-left'); + noteElem.classList.add('porrectus-right'); + } else if(/^#Porrectus/.test(href)) { + noteElem.classList.add('porrectus-left'); + } + noteElem.classList.add('active'); + var tmpSyllable = $(noteElem).parent().parent().find('text')[0]; + if(tmpSyllable && tmpSyllable != syllable) { + if(dropCap && syllable) dropCap.classList.remove('active'); + if(syllable) syllable.classList.remove('active'); + syllable = tmpSyllable; + if(syllable) syllable.classList.add('active'); + } + } + if(note.constructor === exsurge.Note) { + duration = getNoteDuration(notes, noteId); + var isUsingSolesmesLengths = getIsUsingSolesmesLengths(); + var isApostropha = getIsApostropha(note); + var pressus = getPressus(notes, noteId); + var noteName = tones.getNoteName(note.pitch, transpose); + if (isApostropha || pressus) { + var totalDuration = 0; + if (isApostropha && note.neume.notes[0] === note) { + note.neume.notes.forEach(function (note) { + totalDuration += getNoteDuration(notes, getNoteIdForNote(notes, note)); + }); + } else if (pressus && pressus[0] === note) { + totalDuration += getNoteDuration(notes, noteId); + totalDuration += getNoteDuration(notes, noteId+1); + } + + if(totalDuration > 0) synth.triggerAttackRelease(noteName, new Tone.Time("4n").toSeconds()*totalDuration, time); + } else { + synth.triggerAttackRelease(noteName, new Tone.Time("4n").toSeconds()*duration, time); + } + } + ++noteId; + if(noteId >= notes.length) _isPlaying = false; + if(Tone.Transport.state != 'started') return; + timeoutNextNote = Tone.Transport.scheduleOnce(playNextNote, '+' + (new Tone.Time("4n").toSeconds()*duration)); + }; + timeoutNextNote = Tone.Transport.scheduleOnce(playNextNote); + window.playNextNote = playNextNote; + window.playPauseScore = function() { + if(timeoutNextNote) { + Tone.Transport.clear(timeoutNextNote); + Tone.Transport.pause(); + timeoutNextNote = null; + } else { + Tone.Transport.start(); + playNextNote(); + return true; + } + } + window.highlightCurrentlyPlayingNote = function() { + if(noteElem) { + noteElem.classList.add('active'); + } + if(syllable) { + syllable.classList.add('active'); + } + } + }; + window.stopScore = function(){ + Tone.Transport.stop(); + _isPlaying=false; + $('#mediaControls').addClass('offscreen'); + } + } else { + Tone = {}; + window.setTempo = window.setRelativeTempo = window.playScore = window.stopScore = function(){}; + } + var timeoutNextNote, transpose = 0; + var _isPlaying=false; + var noteElem, syllable; + window.isPlayingChant = function() { + return _isPlaying; + } + window.removeChantContextMenus = function() { + $('svg.ChantScore use[source-index].active,svg.ChantScore text[source-index].active').each(function(){ this.classList.remove('active','porrectus-left','porrectus-right'); }); + $('.chant-context').remove(); + $('.btn-group.open').removeClass('open'); + if(_isPlaying) window.highlightCurrentlyPlayingNote && window.highlightCurrentlyPlayingNote(); + } + var _getNoteProperties = function(note) { + var neume = note.neume; + var notations = neume.mapping.notations; + var notes = notations.reduce(function(result, notation) { + if(notation.notes) return result.concat(notation.notes); + return result.concat(null); + }, []); + var noteIndex = notes.indexOf(note); + var previousNote = notes[noteIndex-1]; + var nextNote = notes[noteIndex+1]; + var hasPreviousNote = !!previousNote; + var hasNextNote = !!nextNote; + if(previousNote && neume.hasLyrics() && previousNote.neume.lyrics[0] !== neume.lyrics[0]) previousNote = null; + if(nextNote && nextNote.neume.hasLyrics() && nextNote.neume.lyrics[0] !== neume.lyrics[0]) nextNote = null; + var result = {note: note, notes: notes, noteIndex: noteIndex}; + result.isRepeatedNote = (nextNote && nextNote.staffPosition === note.staffPosition) || (previousNote && previousNote.staffPosition === note.staffPosition); + result.hasMorae = note.morae.length > 0 || (nextNote && nextNote.morae.length > 1); + result.hasEpisemata = note.episemata.length > 0; + result.isTorculus = neume.constructor === exsurge.Torculus; + result.isPesSubpunctis = neume.constructor === exsurge.PesSubpunctis && neume.notes.indexOf(note) < 3; + result.isQuilisma = note.shape === exsurge.NoteShape.Quilisma; + result.isLastOfNeume = neume.trailingSpace && neume.notes.slice(-1)[0] == note; + if(result.isTorculus) { + result.torculusNotes = neume.notes; + } else if(result.isPesSubpunctis) { + result.torculusNotes = neume.notes.slice(0,3); + } + result.acceptsBarBefore = !hasPreviousNote; + result.acceptsBarAfter = !hasNextNote; + result.acceptsMora = !result.hasMorae && !result.hasEpisemata && !result.isQuilisma && !result.isRepeatedNote && neume.notes.slice(-1)[0] == note; + result.acceptsEpisema = !result.hasMorae && !result.hasEpisemata && !result.isQuilisma && !result.isRepeatedNote; + if(result.acceptsBarBefore || result.acceptsBarAfter) { + var score = neume.score; + notations = score.notations; + noteIndex = notations.indexOf(neume); + result.prevNotation = notations[noteIndex-1]; + if(result.prevNotation && result.prevNotation.accidentalType) result.prevNotation = notations[noteIndex-2]; + result.nextNotation = notations[noteIndex+1]; + if(!result.prevNotation) result.acceptsBarBefore = false; + if(result.prevNotation && result.prevNotation.isDivider) { + if(result.prevNotation.constructor == exsurge.QuarterBar || result.prevNotation.constructor == exsurge.Virgula || result.prevNotation.constructor == exsurge.HalfBar) result.hasBarBefore = true; + else result.acceptsBarBefore = false; + } + if(result.nextNotation && result.nextNotation.isDivider) { + if(result.nextNotation.constructor == exsurge.QuarterBar || result.nextNotation.constructor == exsurge.Virgula || result.nextNotation.constructor == exsurge.HalfBar) result.hasBarAfter = true; + else result.acceptsBarAfter = result.acceptsBarAfter = false; + } + } + // TODO: allow adding bar after any dotted note: + // if(!result.acceptsBarAfter && result.hasMorae) result.acceptsBarAfter; + return result; + } + // go through s in $notation, and move on to siblings of $notation if they do not have lyrics. + // start at the selected if any + var findNextInterestingNote = function($notation, $selected) { + var $originalNotation = $notation, + $current; + // check to make sure $selected is from the same syllable: + if($selected && $selected.length) { + var selectedNotation = $selected[0].source && $selected[0].source.neume || $selected[0].source, + notations = selectedNotation.score.notations, + index = notations.indexOf(selectedNotation); + while(index > 0 && !selectedNotation.hasLyrics()) { + selectedNotation = notations[--index]; + } + if(!selectedNotation || selectedNotation.lyrics[0] != $notation[0].source.lyrics[0]) $selected = null; + } + if($selected && $selected.length) { + $current = $selected.nextAll('use').first(); + $notation = $selected.parent().parent(); + } + var startingNotation = $notation[0]; + while($notation[0]===startingNotation || !$notation[0].source.hasLyrics()) { + var $current = $current? $current : $notation.find('use').first(); + while($current.length) { + var note = $current[0].source; + if(note && note.neume) { + var properties = _getNoteProperties(note); + if(properties.isRepeatedNote || properties.hasEpisemata || properties.hasMorae || properties.acceptsBarBefore || properties.acceptsBarAfter) { + $current[0].classList.add('active'); + properties.$note = $current; + properties.$neume = $notation; + return properties; + } + } + $current = $current.nextAll('use').first(); + } + $current = null; + var temp = $notation.next(); + if(temp.length === 0) { + temp = $notation.parent().next().find('g').first(); + } + $notation = temp; + if($notation.length == 0) break; + } + if($selected && $selected.length) return findNextInterestingNote($originalNotation); + return null; + } + window.showToolbarForNote = function(element, editorialChange, base) { + var $elem = $(element), + $neume = $elem.parent(), + $svg = $elem.parents('svg'), + $selected = $svg.find('use[source-index].active'), + source = element.source, + isText = false, + note, + noteIndex, + neume, + notations, + noteProperties, + acceptsBarBefore; + + switch(element.nodeName) { + case 'use': + note = source.neume && source; + neume = note? note.neume : source; + notations = neume.mapping.notations; + if(note) { + noteProperties = _getNoteProperties(note); + } else { + noteIndex = notations.indexOf(neume); + noteProperties = { acceptsBarAfter: noteIndex === notations.length - 1 }; + } + acceptsBarBefore = noteIndex === 0; + break; + case 'text': + isText = true; + $neume = $elem; + noteProperties = findNextInterestingNote($neume.parent(), $selected) || {}; + if(noteProperties.acceptsBarAfter) { + neume = noteProperties.note.neume; + } else { + neume = $neume.parent().find('use').prop('source'); + if(!noteProperties.note) noteProperties.note = neume; + neume = neume && neume.neume; + } + break; + } + var $toolbar = noteProperties.toolbar = $('
').addClass('chant-context btn-group-vertical'); + addPitchButtonsToToolbar($toolbar, noteProperties, $svg.prop('source'), [editorialChange, base]); + + if(editorialChange && base) { + base.noteProperties = noteProperties; + if(noteProperties.hasMorae) + $toolbar.prepend($('').click(function(e) { + e.stopPropagation(); + moveToNote(-1); + })); + var playButton = $('').click(function(e) { + e.stopPropagation(); + moveToNote(1); + })); + $toolbar.append(showToolbarForNoteArgs? playButtonGroup : playButton); + if(isFirstPitch) { + $toolbar.append($('').click(function(e) { + e.stopPropagation(); + mouseUpTone(); + changePitch(1); + })); + var mouseDownTone = function() { + if(!stopTone) stopTone = tones.play(new exsurge.Pitch(score.defaultStartPitch.toInt() - startPitch + thisPitch), {start: true, release: 300}); + }; + pitchButtonGroup.append($('').click(function(e) { + e.stopPropagation(); + mouseUpTone(); + changePitch(-1); + })); + $toolbar.append(pitchButtonGroup); + if(isFirstPitch) { + $toolbar.append($('
"; - - if ($notes && $text =~ /\{\:(.*?)\:\}/) { - my $notefile = $1; - $notefile =~ s/^pc/p/; - my $colspan = ($only) ? 1 : 2; - print "\n"; - } - } - print ""; + + if ($notes && $text =~ /\{\:(.*?)\:\}/) { + my $notefile = $1; + $notefile =~ s/^pc/p/; + my $colspan = ($only) ? 1 : 2; + print "\n"; + } + } + print "
\n" - . "
"; - topnext_cell($lang); - - if ($text =~ /%(.*?)%/) { - $text = activate_links(\$text, $lang); - } - } - $text =~ s/wait[0-9]+//ig; - $text =~ s/\_/ /g; - $text =~ s/\{\:.*?\:\}(
)*\s*//g; - $text =~ s/\{\:.*?\:\}//sg; - $text =~ s/\`//g; - + if (!$Ck) { + if (columnsel($lang)) { + $searchind++ if ($text !~ /{omittitur}/); + print "
\n" + . "
"; + topnext_cell($lang); + + if ($lang =~ /gabc/i) { # post process GABC chants + my $dId = 0; + + # retrieve all GABC scores from files + while($text =~ /\{gabc:(.+?)\}/is) { + my $temp = $1; + my $gregFile = "chants/$1.gabc"; + $gregFile = checkfile($lang, $gregFile); + if ($gregFile =~ /\/Latin\/.*gloria\.gabc/i ) { # if second Responsory GABC doesnot exist + $gregFile = "chants/$temp.gabc"; + $gregFile =~ s/\-gloria//; + $gregFile = checkfile($lang, $gregFile); + } + my(@gregScore) = do_read($gregFile); + $text =~ s/gabc:$temp/@gregScore/s; + } + + # identify all GABC sections and post process to be suitable for JavaScript + while($text =~ /\{(\(|name:|initial-style:|centering-scheme:)(.+?)\(\:\:\)\}/is) { + $dId++; + $text =~ s/\{(\(|name:|initial-style:|centering-scheme:)/
$1/s; + $text =~ s/T.\s?P.<\/i>/\_\^T. P.\^\_ /g; + $text =~ s/<\/?i>/\_/g; + $text =~ s/<\/?b>|\\greheightstar<\/v>/*/g; + $text =~ s/<\/?sc>/\%/g; + $text =~ s/<\/?c>/\^/g; + $text =~ s/\'(?:ae|æ)<\/sp>/ǽ/g; + $text =~ s/\'(?:oe|œ)<\/sp>/œ́/g; + $text =~ s/(?:ae|æ)<\/sp>/æ/g; + $text =~ s/(?:oe|œ)<\/sp>/œ/g; + $text =~ s/;
\n/;\n/gi; + $text =~ s/%%
\n/%%\n/gi; + $text =~ s/%%\(/%%\n\(/gi; + $text =~ s/;([a-z\%\(])/;\n$1/gi; + $text =~ s/(\(\:\:\)\}?)
\n/$1 \n/gi; + $text =~ s/\* /\*() /g; + $text =~ s/†\((.+?)\)/($1) † /g; + $text =~ s/\^?†\^?\(?\)?/^†^() /g; + $text =~ s/V\/<\/sp>\.?/V\/\.() /g; + $text =~ s/R\/<\/sp>\.?/R\/\.() /g; + $text =~ s/<\/?nlba>//g; + $text =~ s/\(\:\:\)\}/\(\:\:\)<\/DIV>
<\/DIV>/s; + $text =~ s/\_/\|\|/g; + } + } else { # post process non-GABC + if ($text =~ /%(.*?)%/) { + $text = activate_links(\$text, $lang); + } + } + } + $text =~ s/wait[0-9]+//ig; + $text =~ s/\_/ /g; + $text =~ s/\{\:.*?\:\}(
)*\s*//g; + $text =~ s/\{\:.*?\:\}//sg; + $text =~ s/\`//g; #` #accent grave for editor + + # Remove line breaks from chants + if($lang =~ /gabc/i) { + $text =~ s/\|\|(
)/
/g; + $text =~ s/\|\|/\_/g; + } + if ($Ck) { if ($column == 1) { push(@ctext1, $text);