Dashboard sipadu mbip
您最多选择25个主题 主题必须以字母或数字开头,可以包含连字符 (-),并且长度不得超过35个字符

aui-drawing-base-debug.js 36KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724172517261727172817291730173117321733173417351736173717381739174017411742174317441745174617471748174917501751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784178517861787178817891790179117921793179417951796179717981799180018011802180318041805180618071808180918101811181218131814181518161817181818191820182118221823182418251826182718281829183018311832183318341835183618371838183918401841184218431844184518461847184818491850185118521853185418551856185718581859186018611862186318641865186618671868186918701871187218731874
  1. AUI.add('aui-drawing-base', function(A) {
  2. var Lang = A.Lang,
  3. isArray = Lang.isArray,
  4. isFunction = Lang.isFunction,
  5. isNumber = Lang.isNumber,
  6. isObject = Lang.isObject,
  7. isString = Lang.isString,
  8. isUndefined = Lang.isUndefined,
  9. DOC = A.config.doc,
  10. ColorUtil = A.ColorUtil,
  11. Util,
  12. UA = A.UA,
  13. EMPTY_FN = Lang.emptyFn,
  14. MAP_ATTRS_AVAILABLE = {
  15. blur: 0,
  16. 'clip-rect': '0 0 1e9 1e9',
  17. cursor: 'default',
  18. cx: 0,
  19. cy: 0,
  20. fill: '#fff',
  21. 'fill-opacity': 1,
  22. font: '10px "Arial"',
  23. 'font-family': '"Arial"',
  24. 'font-size': '10',
  25. 'font-style': 'normal',
  26. 'font-weight': 400,
  27. gradient: 0,
  28. height: 0,
  29. href: 'http://alloy.liferay.com/',
  30. opacity: 1,
  31. path: 'M0,0',
  32. r: 0,
  33. rotation: 0,
  34. rx: 0,
  35. ry: 0,
  36. scale: '1 1',
  37. src: '',
  38. stroke: '#000',
  39. 'stroke-dasharray': '',
  40. 'stroke-linecap': 'butt',
  41. 'stroke-linejoin': 'butt',
  42. 'stroke-miterlimit': 0,
  43. 'stroke-opacity': 1,
  44. 'stroke-width': 1,
  45. target: '_blank',
  46. 'text-anchor': 'middle',
  47. title: 'AlloyUI',
  48. translation: '0 0',
  49. width: 0,
  50. x: 0,
  51. y: 0
  52. },
  53. MAP_COMMAND_SVG_QUADRATIC = {
  54. Q: 1,
  55. T: 1
  56. },
  57. MAP_ELEMENTS = {
  58. circle: 1,
  59. ellipse: 1,
  60. image: 1,
  61. path: 1,
  62. rect: 1,
  63. text: 1
  64. },
  65. MAP_TYPES_IMAGE_TEXT = {
  66. image:1,
  67. text: 1
  68. },
  69. MAP_TYPES_CIRCLE_ELLIPSE = {
  70. circle: 1,
  71. ellipse: 1
  72. },
  73. MATH = Math,
  74. MATH_MAX = MATH.max,
  75. MATH_MIN = MATH.min,
  76. MATH_POW = MATH.pow,
  77. NAME = 'drawing',
  78. REGEX_GRADIENT_VALUES = /^([^:]*):?([\d\.]*)/,
  79. REGEX_ISURL = /^url\(['"]?([^\)]+?)['"]?\)$/i,
  80. REGEX_PATH_COMMAND = /([achlmqstvz])[\s,]*((-?\d*\.?\d*(?:e[-+]?\d+)?\s*,?\s*)+)/ig,
  81. REGEX_PATH_TO_STRING = /,?([achlmqrstvxz]),?/gi,
  82. REGEX_PATH_VALUES = /(-?\d*\.?\d*(?:e[-+]?\d+)?)\s*,?\s*/ig,
  83. REGEX_RADIAL_GRADIENT = /^r(?:\(([^,]+?)\s*,\s*([^\)]+?)\))?/,
  84. REGEX_SEPARATOR = /[, ]+/,
  85. REGEX_SEPARATOR_GRADIENT = /\s*\-\s*/,
  86. STR_EMPTY = '',
  87. STR_FILL = 'fill',
  88. STR_MS_PROG_ID_PREFIX = ' progid:DXImageTransform.Microsoft',
  89. STR_SPACE = ' ',
  90. TO_LOWER_CASE = String.prototype.toLowerCase,
  91. TO_UPPER_CASE = String.prototype.toUpperCase;
  92. var Drawing = A.Component.create(
  93. {
  94. ATTRS: {
  95. height: {
  96. value: 342
  97. },
  98. width: {
  99. value: 512
  100. },
  101. x: {
  102. value: null
  103. },
  104. y: {
  105. value: null
  106. }
  107. },
  108. UI_ATTRS: ['x', 'y'],
  109. create: function(config) {
  110. var args = arguments;
  111. var firstArg = args[0];
  112. if (isArray(firstArg)) {
  113. args = args[0];
  114. config = Util.getConfig(args);
  115. var paper = new Drawing(config).render();
  116. var set = paper.createSet();
  117. var element;
  118. for (var i = 0, length = args.length; i < length; i++) {
  119. element = args[i] || {};
  120. if (MAP_ELEMENTS.hasOwnProperty(element.type)) {
  121. set.push(
  122. paper[element.type]().attr(element)
  123. );
  124. }
  125. }
  126. return paper;
  127. }
  128. else if (isObject(firstArg) && !(firstArg.nodeName || firstArg instanceof A.Node)) {
  129. config = firstArg;
  130. }
  131. else {
  132. config = Util.getConfig(args);
  133. }
  134. return new Drawing(config).render();
  135. },
  136. NAME: NAME,
  137. prototype: {
  138. CONTENT_TEMPLATE: null,
  139. renderUI: function() {
  140. var instance = this;
  141. instance.customAttributes = {};
  142. Drawing.Impl.createCanvas.call(instance);
  143. },
  144. circle: function(x, y, r) {
  145. var instance = this;
  146. return Drawing.Impl.createCircle.call(instance, x || 0, y || 0, r || 0);
  147. },
  148. clear: function() {
  149. var instance = this;
  150. return Drawing.Impl.clear.call(instance);
  151. },
  152. createSet: function(itemsArray) {
  153. var instance = this;
  154. if (arguments.length > 1) {
  155. itemsArray = Array.prototype.splice.call(arguments, 0, arguments.length);
  156. }
  157. return new Set(itemsArray);
  158. },
  159. ellipse: function(x, y, rx, ry) {
  160. var instance = this;
  161. return Drawing.Impl.createEllipse.call(instance, x || 0, y || 0, rx || 0, ry || 0);
  162. },
  163. image: function(src, x, y, w, h) {
  164. var instance = this;
  165. return Drawing.Impl.createImage.call(instance, src || 'about:blank', x || 0, y || 0, w || 0, h || 0);
  166. },
  167. path: function(pathString) {
  168. var instance = this;
  169. if (isString(pathString)) {
  170. pathString = Lang.sub.apply(A, arguments);
  171. }
  172. else if (!isUndefined(pathString) && !isArray(pathString)) {
  173. pathString += STR_EMPTY;
  174. }
  175. return Drawing.Impl.createPath.call(instance, pathString);
  176. },
  177. rect: function(x, y, w, h, r) {
  178. var instance = this;
  179. return Drawing.Impl.createRectangle.call(instance, x || 0, y || 0, w || 0, h || 0, r || 0);
  180. },
  181. remove: function() {
  182. var instance = this;
  183. return Drawing.Impl.remove.call(instance);
  184. },
  185. safari: EMPTY_FN,
  186. text: function(x, y, text) {
  187. var instance = this;
  188. return Drawing.Impl.createText.call(instance, x || 0, y || 0, text || STR_EMPTY);
  189. },
  190. _uiSetX: function(value) {
  191. var instance = this;
  192. instance.get('boundingBox').setXY([value, instance.get('y')]);
  193. },
  194. _uiSetY: function(value) {
  195. var instance = this;
  196. instance.get('boundingBox').setXY([instance.get('x'), value]);
  197. }
  198. }
  199. }
  200. );
  201. Util = {
  202. getConfig: function(args) {
  203. var config = {};
  204. var firstArg = args[0];
  205. var firstConfigArg = 'boundingBox';
  206. var indexHeight = 2;
  207. var indexWidth = 1;
  208. var indexY = -1;
  209. if (isNumber(firstArg)) {
  210. firstConfigArg = 'x';
  211. indexHeight = 3;
  212. indexWidth = 2;
  213. indexY = 1;
  214. }
  215. config[firstConfigArg] = firstArg;
  216. config.height = args[indexHeight];
  217. config.width = args[indexWidth];
  218. config.y = args[indexY];
  219. return config;
  220. },
  221. translate: function(x, y) {
  222. if (x == null) {
  223. return {
  224. x: this._.tx,
  225. y: this._.ty,
  226. toString: Util.XYToString
  227. };
  228. }
  229. this._.tx += +x;
  230. this._.ty += +y;
  231. switch (this.type) {
  232. case 'circle':
  233. case 'ellipse':
  234. this.attr(
  235. {
  236. cx: +x + this.attrs.cx,
  237. cy: +y + this.attrs.cy
  238. }
  239. );
  240. break;
  241. case 'rect':
  242. case 'image':
  243. case 'text':
  244. this.attr(
  245. {
  246. x: +x + this.attrs.x,
  247. y: +y + this.attrs.y
  248. }
  249. );
  250. break;
  251. case 'path':
  252. var path = Util.pathToRelative(this.attrs.path);
  253. path[0][1] += +x;
  254. path[0][2] += +y;
  255. this.attr(
  256. {
  257. path: path
  258. }
  259. );
  260. break;
  261. }
  262. return this;
  263. }
  264. };
  265. Drawing.getColor = function(value) {
  266. var start = Drawing.getColor.start = Drawing.getColor.start || {
  267. h: 0,
  268. s: 1,
  269. b: value || 0.75
  270. };
  271. var rgb = ColorUtil.hsb2rgb(start.h, start.s, start.b);
  272. start.h += 0.075;
  273. if (start.h > 1) {
  274. start.h = 0;
  275. start.s -= 0.2;
  276. if (start.s <= 0) {
  277. Drawing.getColor.start = {
  278. h: 0,
  279. s: 1,
  280. b: start.b
  281. }
  282. }
  283. }
  284. return rgb.hex;
  285. };
  286. Drawing.getColor.reset = function() {
  287. delete Drawing.start;
  288. };
  289. Util.tear = function(el, drawing) {
  290. el == drawing.top && (drawing.top = el.prev);
  291. el == drawing.bottom && (drawing.bottom = el.next);
  292. el.next && (el.next.prev = el.prev);
  293. el.prev && (el.prev.next = el.next);
  294. };
  295. Util.toFront = function(el, drawing) {
  296. if (drawing.top === el) {
  297. return;
  298. }
  299. Util.tear(el, drawing);
  300. el.next = null;
  301. el.prev = drawing.top;
  302. drawing.top.next = el;
  303. drawing.top = el;
  304. };
  305. Util.toBack = function(el, drawing) {
  306. if (drawing.bottom === el) {
  307. return;
  308. }
  309. Util.tear(el, drawing);
  310. el.next = drawing.bottom;
  311. el.prev = null;
  312. drawing.bottom.prev = el;
  313. drawing.bottom = el;
  314. };
  315. Util.insertAfter = function(el, el2, drawing) {
  316. Util.tear(el, drawing);
  317. el2 == drawing.top && (drawing.top = el);
  318. el2.next && (el2.next.prev = el);
  319. el.next = el2.next;
  320. el.prev = el2;
  321. el2.next = el;
  322. };
  323. Util.insertBefore = function(el, el2, drawing) {
  324. Util.tear(el, drawing);
  325. el2 == drawing.bottom && (drawing.bottom = el);
  326. el2.prev && (el2.prev.next = el);
  327. el.prev = el2.prev;
  328. el2.prev = el;
  329. el.next = el2;
  330. };
  331. var Element = function(node, drawing) {
  332. var instance = this;
  333. instance.createElement.apply(instance, arguments);
  334. };
  335. Util.removed = function(methodname) {
  336. return function() {
  337. throw new Error('AlloyUI: you are calling to method "' + methodname + '" of removed object');
  338. };
  339. };
  340. Util._path2string = function() {
  341. return this.join(',').replace(REGEX_PATH_TO_STRING, '$1');
  342. };
  343. Util.parsePathString = A.cached(
  344. function(pathString) {
  345. if (!pathString) {
  346. return null;
  347. }
  348. var paramCounts = {
  349. a: 7,
  350. c: 6,
  351. h: 1,
  352. l: 2,
  353. m: 2,
  354. q: 4,
  355. s: 4,
  356. t: 2,
  357. v: 1,
  358. z: 0
  359. };
  360. var data = [];
  361. if (isArray(pathString) && isArray(pathString[0])) { // rough assumption
  362. data = pathClone(pathString);
  363. }
  364. if (!data.length) {
  365. String(pathString).replace(REGEX_PATH_COMMAND, function(a, b, c) {
  366. var params = [];
  367. var name = TO_LOWER_CASE.call(b);
  368. c.replace(
  369. REGEX_PATH_VALUES,
  370. function(a, b) {
  371. b && params.push(+b);
  372. }
  373. );
  374. if (name == 'm' && params.length > 2) {
  375. data.push([b].concat(params.splice(0, 2)));
  376. name = 'l';
  377. b = b == 'm' ? 'l' : 'L';
  378. }
  379. while (params.length >= paramCounts[name]) {
  380. data.push([b].concat(params.splice(0, paramCounts[name])));
  381. if (!paramCounts[name]) {
  382. break;
  383. }
  384. }
  385. });
  386. }
  387. data.toString = Util._path2string;
  388. return data;
  389. }
  390. );
  391. Util.findDotsAtSegment = function(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, t) {
  392. var t1 = 1 - t;
  393. var x = MATH_POW(t1, 3) * p1x + MATH_POW(t1, 2) * 3 * t * c1x + t1 * 3 * t * t * c2x + MATH_POW(t, 3) * p2x;
  394. var y = MATH_POW(t1, 3) * p1y + MATH_POW(t1, 2) * 3 * t * c1y + t1 * 3 * t * t * c2y + MATH_POW(t, 3) * p2y;
  395. var mx = p1x + 2 * t * (c1x - p1x) + t * t * (c2x - 2 * c1x + p1x);
  396. var my = p1y + 2 * t * (c1y - p1y) + t * t * (c2y - 2 * c1y + p1y);
  397. var nx = c1x + 2 * t * (c2x - c1x) + t * t * (p2x - 2 * c2x + c1x);
  398. var ny = c1y + 2 * t * (c2y - c1y) + t * t * (p2y - 2 * c2y + c1y);
  399. var ax = (1 - t) * p1x + t * c1x;
  400. var ay = (1 - t) * p1y + t * c1y;
  401. var cx = (1 - t) * c2x + t * p2x;
  402. var cy = (1 - t) * c2y + t * p2y;
  403. var alpha = (90 - MATH.atan((mx - nx) / (my - ny)) * 180 / MATH.PI);
  404. if (mx > nx || my < ny) {
  405. alpha += 180;
  406. }
  407. return {
  408. x: x,
  409. y: y,
  410. m: {
  411. x: mx,
  412. y: my
  413. },
  414. n: {
  415. x: nx,
  416. y: ny
  417. },
  418. start: {
  419. x: ax,
  420. y: ay
  421. },
  422. end: {
  423. x: cx,
  424. y: cy
  425. },
  426. alpha: alpha
  427. };
  428. };
  429. Util.pathDimensions = A.cached(
  430. function(path) {
  431. if (!path) {
  432. return {x: 0, y: 0, width: 0, height: 0};
  433. }
  434. path = Util.path2curve(path);
  435. var x = 0;
  436. var y = 0;
  437. var X = [];
  438. var Y = [];
  439. var p;
  440. for (var i = 0, length = path.length; i < length; i++) {
  441. p = path[i];
  442. if (p[0] == "M") {
  443. x = p[1];
  444. y = p[2];
  445. X.push(x);
  446. Y.push(y);
  447. }
  448. else {
  449. var dim = Util.curveDim(x, y, p[1], p[2], p[3], p[4], p[5], p[6]);
  450. X = X.concat(dim.min.x, dim.max.x);
  451. Y = Y.concat(dim.min.y, dim.max.y);
  452. x = p[5];
  453. y = p[6];
  454. }
  455. }
  456. var xmin = MATH_MIN.apply(0, X);
  457. var ymin = MATH_MIN.apply(0, Y);
  458. return {
  459. x: xmin,
  460. y: ymin,
  461. width: MATH_MAX.apply(0, X) - xmin,
  462. height: MATH_MAX.apply(0, Y) - ymin
  463. };
  464. }
  465. );
  466. Util.pathClone = function(pathArray) {
  467. var res = [];
  468. if (!isArray(pathArray) || !isArray(pathArray && pathArray[0])) { // rough assumption
  469. pathArray = Util.parsePathString(pathArray);
  470. }
  471. for (var i = 0, length = pathArray.length; i < length; i++) {
  472. res[i] = [];
  473. for (var j = 0, jLength = pathArray[i].length; j < jLength; j++) {
  474. res[i][j] = pathArray[i][j];
  475. }
  476. }
  477. res.toString = Util._path2string;
  478. return res;
  479. };
  480. Util._pathToRelative = A.cached(
  481. function(pathArray) {
  482. if (!isArray(pathArray) || !isArray(pathArray && pathArray[0])) { // rough assumption
  483. pathArray = Util.parsePathString(pathArray);
  484. }
  485. var res = [];
  486. var x = 0;
  487. var y = 0;
  488. var mx = 0;
  489. var my = 0;
  490. var start = 0;
  491. if (pathArray[0][0] == 'M') {
  492. x = pathArray[0][1];
  493. y = pathArray[0][2];
  494. mx = x;
  495. my = y;
  496. start++;
  497. res.push(['M', x, y]);
  498. }
  499. for (var i = start, length = pathArray.length; i < length; i++) {
  500. var r = res[i] = [];
  501. var pa = pathArray[i];
  502. if (pa[0] != TO_LOWER_CASE.call(pa[0])) {
  503. r[0] = TO_LOWER_CASE.call(pa[0]);
  504. switch (r[0]) {
  505. case 'a':
  506. r[1] = pa[1];
  507. r[2] = pa[2];
  508. r[3] = pa[3];
  509. r[4] = pa[4];
  510. r[5] = pa[5];
  511. r[6] = +(pa[6] - x).toFixed(3);
  512. r[7] = +(pa[7] - y).toFixed(3);
  513. break;
  514. case 'v':
  515. r[1] = +(pa[1] - y).toFixed(3);
  516. break;
  517. case 'm':
  518. mx = pa[1];
  519. my = pa[2];
  520. default:
  521. for (var j = 1, jLength = pa.length; j < jLength; j++) {
  522. r[j] = +(pa[j] - ((j % 2) ? x : y)).toFixed(3);
  523. }
  524. }
  525. }
  526. else {
  527. r = res[i] = [];
  528. if (pa[0] == 'm') {
  529. mx = pa[1] + x;
  530. my = pa[2] + y;
  531. }
  532. for (var k = 0, kLength = pa.length; k < kLength; k++) {
  533. res[i][k] = pa[k];
  534. }
  535. }
  536. var len = res[i].length;
  537. switch (res[i][0]) {
  538. case 'z':
  539. x = mx;
  540. y = my;
  541. break;
  542. case 'h':
  543. x += +res[i][len - 1];
  544. break;
  545. case 'v':
  546. y += +res[i][len - 1];
  547. break;
  548. default:
  549. x += +res[i][len - 2];
  550. y += +res[i][len - 1];
  551. }
  552. }
  553. res.toString = Util._path2string;
  554. return res;
  555. }
  556. );
  557. Util.pathToRelative = function(pathArray) {
  558. return Util.pathClone(Util._pathToRelative(pathArray));
  559. };
  560. Util._pathToAbsolute = A.cached(
  561. function(pathArray) {
  562. if (!isArray(pathArray) || !isArray(pathArray && pathArray[0])) { // rough assumption
  563. pathArray = Util.parsePathString(pathArray);
  564. }
  565. var res = [];
  566. var x = 0;
  567. var y = 0;
  568. var mx = 0;
  569. var my = 0;
  570. var start = 0;
  571. if (pathArray[0][0] == 'M') {
  572. x = +pathArray[0][1];
  573. y = +pathArray[0][2];
  574. mx = x;
  575. my = y;
  576. start++;
  577. res[0] = ['M', x, y];
  578. }
  579. for (var i = start, length = pathArray.length; i < length; i++) {
  580. var r = res[i] = [];
  581. var pa = pathArray[i];
  582. if (pa[0] != TO_UPPER_CASE.call(pa[0])) {
  583. r[0] = TO_UPPER_CASE.call(pa[0]);
  584. switch (r[0]) {
  585. case 'A':
  586. r[1] = pa[1];
  587. r[2] = pa[2];
  588. r[3] = pa[3];
  589. r[4] = pa[4];
  590. r[5] = pa[5];
  591. r[6] = +(pa[6] + x);
  592. r[7] = +(pa[7] + y);
  593. break;
  594. case 'V':
  595. r[1] = +pa[1] + y;
  596. break;
  597. case 'H':
  598. r[1] = +pa[1] + x;
  599. break;
  600. case 'M':
  601. mx = +pa[1] + x;
  602. my = +pa[2] + y;
  603. default:
  604. for (var j = 1, jLength = pa.length; j < jLength; j++) {
  605. r[j] = +pa[j] + ((j % 2) ? x : y);
  606. }
  607. }
  608. }
  609. else {
  610. for (var k = 0, kLength = pa.length; k < kLength; k++) {
  611. res[i][k] = pa[k];
  612. }
  613. }
  614. switch (r[0]) {
  615. case 'Z':
  616. x = mx;
  617. y = my;
  618. break;
  619. case 'H':
  620. x = r[1];
  621. break;
  622. case 'V':
  623. y = r[1];
  624. break;
  625. case 'M':
  626. mx = res[i][res[i].length - 2];
  627. my = res[i][res[i].length - 1];
  628. default:
  629. x = res[i][res[i].length - 2];
  630. y = res[i][res[i].length - 1];
  631. }
  632. }
  633. res.toString = Util._path2string;
  634. return res;
  635. }
  636. );
  637. Util.pathToAbsolute = function(pathArray) {
  638. return Util.pathClone(Util._pathToAbsolute(pathArray));
  639. };
  640. Util.lineToCubicCurve = function(x1, y1, x2, y2) {
  641. return [x1, y1, x2, y2, x2, y2];
  642. };
  643. Util.quadraticToCubicCurve = function(x1, y1, ax, ay, x2, y2) {
  644. var _13 = 1 / 3;
  645. var _23 = 2 / 3;
  646. return [
  647. _13 * x1 + _23 * ax,
  648. _13 * y1 + _23 * ay,
  649. _13 * x2 + _23 * ax,
  650. _13 * y2 + _23 * ay,
  651. x2,
  652. y2
  653. ];
  654. };
  655. Util.arcToCubicCurve = function(x1, y1, rx, ry, angle, large_arc_flag, sweep_flag, x2, y2, recursive) {
  656. // for more information of where this math came from visit:
  657. // http://www.w3.org/TR/SVG11/implnote.html#ArcImplementationNotes
  658. var PI = MATH.PI;
  659. var _120 = PI * 120 / 180;
  660. var rad = PI / 180 * (+angle || 0);
  661. var res = [];
  662. var xy;
  663. var rotate = A.cached(
  664. function(x, y, rad) {
  665. var X = x * MATH.cos(rad) - y * MATH.sin(rad),
  666. Y = x * MATH.sin(rad) + y * MATH.cos(rad);
  667. return {x: X, y: Y};
  668. }
  669. );
  670. if (!recursive) {
  671. xy = rotate(x1, y1, -rad);
  672. x1 = xy.x;
  673. y1 = xy.y;
  674. xy = rotate(x2, y2, -rad);
  675. x2 = xy.x;
  676. y2 = xy.y;
  677. var cos = MATH.cos(PI / 180 * angle);
  678. var sin = MATH.sin(PI / 180 * angle);
  679. var x = (x1 - x2) / 2;
  680. var y = (y1 - y2) / 2;
  681. var h = (x * x) / (rx * rx) + (y * y) / (ry * ry);
  682. if (h > 1) {
  683. h = MATH.sqrt(h);
  684. rx = h * rx;
  685. ry = h * ry;
  686. }
  687. var rx2 = rx * rx;
  688. var ry2 = ry * ry;
  689. var k = (large_arc_flag == sweep_flag ? -1 : 1) *
  690. MATH.sqrt(MATH.abs((rx2 * ry2 - rx2 * y * y - ry2 * x * x) / (rx2 * y * y + ry2 * x * x)));
  691. var cx = k * rx * y / ry + (x1 + x2) / 2;
  692. var cy = k * -ry * x / rx + (y1 + y2) / 2;
  693. var f1 = MATH.asin(((y1 - cy) / ry).toFixed(7));
  694. var f2 = MATH.asin(((y2 - cy) / ry).toFixed(7));
  695. f1 = x1 < cx ? PI - f1 : f1;
  696. f2 = x2 < cx ? PI - f2 : f2;
  697. f1 < 0 && (f1 = PI * 2 + f1);
  698. f2 < 0 && (f2 = PI * 2 + f2);
  699. if (sweep_flag && f1 > f2) {
  700. f1 = f1 - PI * 2;
  701. }
  702. if (!sweep_flag && f2 > f1) {
  703. f2 = f2 - PI * 2;
  704. }
  705. }
  706. else {
  707. f1 = recursive[0];
  708. f2 = recursive[1];
  709. cx = recursive[2];
  710. cy = recursive[3];
  711. }
  712. var df = f2 - f1;
  713. if (MATH.abs(df) > _120) {
  714. var f2old = f2;
  715. var x2old = x2;
  716. var y2old = y2;
  717. f2 = f1 + _120 * (sweep_flag && f2 > f1 ? 1 : -1);
  718. x2 = cx + rx * MATH.cos(f2);
  719. y2 = cy + ry * MATH.sin(f2);
  720. res = Util.arcToCubicCurve(x2, y2, rx, ry, angle, 0, sweep_flag, x2old, y2old, [f2, f2old, cx, cy]);
  721. }
  722. df = f2 - f1;
  723. var c1 = MATH.cos(f1);
  724. var s1 = MATH.sin(f1);
  725. var c2 = MATH.cos(f2);
  726. var s2 = MATH.sin(f2);
  727. var t = MATH.tan(df / 4);
  728. var hx = 4 / 3 * rx * t;
  729. var hy = 4 / 3 * ry * t;
  730. var m1 = [x1, y1];
  731. var m2 = [x1 + hx * s1, y1 - hy * c1];
  732. var m3 = [x2 + hx * s2, y2 - hy * c2];
  733. var m4 = [x2, y2];
  734. m2[0] = 2 * m1[0] - m2[0];
  735. m2[1] = 2 * m1[1] - m2[1];
  736. if (recursive) {
  737. return [m2, m3, m4].concat(res);
  738. }
  739. else {
  740. res = [m2, m3, m4].concat(res).join().split(',');
  741. var newres = [];
  742. for (var i = 0, length = res.length; i < length; i++) {
  743. newres[i] = i % 2 ? rotate(res[i - 1], res[i], rad).y : rotate(res[i], res[i + 1], rad).x;
  744. }
  745. return newres;
  746. }
  747. };
  748. Util.findDotAtSegment = function(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, t) {
  749. var t1 = 1 - t;
  750. return {
  751. x: MATH_POW(t1, 3) * p1x + MATH_POW(t1, 2) * 3 * t * c1x + t1 * 3 * t * t * c2x + MATH_POW(t, 3) * p2x,
  752. y: MATH_POW(t1, 3) * p1y + MATH_POW(t1, 2) * 3 * t * c1y + t1 * 3 * t * t * c2y + MATH_POW(t, 3) * p2y
  753. };
  754. };
  755. Util.curveDim = A.cached(
  756. function(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y) {
  757. var a = (c2x - 2 * c1x + p1x) - (p2x - 2 * c2x + c1x);
  758. var b = 2 * (c1x - p1x) - 2 * (c2x - c1x);
  759. var c = p1x - c1x;
  760. var t1 = (-b + MATH.sqrt(b * b - 4 * a * c)) / 2 / a;
  761. var t2 = (-b - MATH.sqrt(b * b - 4 * a * c)) / 2 / a;
  762. var y = [p1y, p2y];
  763. var x = [p1x, p2x];
  764. var dot;
  765. MATH.abs(t1) > 1e12 && (t1 = 0.5);
  766. MATH.abs(t2) > 1e12 && (t2 = 0.5);
  767. if (t1 > 0 && t1 < 1) {
  768. dot = Util.findDotAtSegment(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, t1);
  769. x.push(dot.x);
  770. y.push(dot.y);
  771. }
  772. if (t2 > 0 && t2 < 1) {
  773. dot = Util.findDotAtSegment(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, t2);
  774. x.push(dot.x);
  775. y.push(dot.y);
  776. }
  777. a = (c2y - 2 * c1y + p1y) - (p2y - 2 * c2y + c1y);
  778. b = 2 * (c1y - p1y) - 2 * (c2y - c1y);
  779. c = p1y - c1y;
  780. t1 = (-b + MATH.sqrt(b * b - 4 * a * c)) / 2 / a;
  781. t2 = (-b - MATH.sqrt(b * b - 4 * a * c)) / 2 / a;
  782. MATH.abs(t1) > 1e12 && (t1 = 0.5);
  783. MATH.abs(t2) > 1e12 && (t2 = 0.5);
  784. if (t1 > 0 && t1 < 1) {
  785. dot = Util.findDotAtSegment(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, t1);
  786. x.push(dot.x);
  787. y.push(dot.y);
  788. }
  789. if (t2 > 0 && t2 < 1) {
  790. dot = Util.findDotAtSegment(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, t2);
  791. x.push(dot.x);
  792. y.push(dot.y);
  793. }
  794. return {
  795. min: {
  796. x: MATH_MIN.apply(0, x),
  797. y: MATH_MIN.apply(0, y)
  798. },
  799. max: {
  800. x: MATH_MAX.apply(0, x),
  801. y: MATH_MAX.apply(0, y)
  802. }
  803. };
  804. }
  805. );
  806. Util._path2curve = A.cached(
  807. function(path, path2) {
  808. var p = Util.pathToAbsolute(path);
  809. var p2 = path2 && Util.pathToAbsolute(path2);
  810. var attrs = {
  811. x: 0,
  812. y: 0,
  813. bx: 0,
  814. by: 0,
  815. X: 0,
  816. Y: 0,
  817. qx: null,
  818. qy: null
  819. };
  820. var attrs2 = {
  821. x: 0,
  822. y: 0,
  823. bx: 0,
  824. by: 0,
  825. X: 0,
  826. Y: 0,
  827. qx: null,
  828. qy: null
  829. };
  830. var processPath = function(path, d) {
  831. var nx;
  832. var ny;
  833. if (!path) {
  834. return ['C', d.x, d.y, d.x, d.y, d.x, d.y];
  835. }
  836. if (!(path[0] in MAP_COMMAND_SVG_QUADRATIC)) {
  837. d.qx = d.qy = null
  838. }
  839. switch (path[0]) {
  840. case 'M':
  841. d.X = path[1];
  842. d.Y = path[2];
  843. break;
  844. case 'A':
  845. path = ['C'].concat(Util.arcToCubicCurve.apply(0, [d.x, d.y].concat(path.slice(1))));
  846. break;
  847. case 'S':
  848. nx = d.x + (d.x - (d.bx || d.x));
  849. ny = d.y + (d.y - (d.by || d.y));
  850. path = ['C', nx, ny].concat(path.slice(1));
  851. break;
  852. case 'T':
  853. d.qx = d.x + (d.x - (d.qx || d.x));
  854. d.qy = d.y + (d.y - (d.qy || d.y));
  855. path = ['C'].concat(Util.quadraticToCubicCurve(d.x, d.y, d.qx, d.qy, path[1], path[2]));
  856. break;
  857. case 'Q':
  858. d.qx = path[1];
  859. d.qy = path[2];
  860. path = ['C'].concat(Util.quadraticToCubicCurve(d.x, d.y, path[1], path[2], path[3], path[4]));
  861. break;
  862. case 'L':
  863. path = ['C'].concat(Util.lineToCubicCurve(d.x, d.y, path[1], path[2]));
  864. break;
  865. case 'H':
  866. path = ['C'].concat(Util.lineToCubicCurve(d.x, d.y, path[1], d.y));
  867. break;
  868. case 'V':
  869. path = ['C'].concat(Util.lineToCubicCurve(d.x, d.y, d.x, path[1]));
  870. break;
  871. case 'Z':
  872. path = ['C'].concat(Util.lineToCubicCurve(d.x, d.y, d.X, d.Y));
  873. break;
  874. }
  875. return path;
  876. };
  877. var fixArc = function(pp, i) {
  878. if (pp[i].length > 7) {
  879. pp[i].shift();
  880. var pi = pp[i];
  881. while (pi.length) {
  882. pp.splice(i++, 0, ['C'].concat(pi.splice(0, 6)));
  883. }
  884. pp.splice(i, 1);
  885. length = MATH_MAX(p.length, p2 && p2.length || 0);
  886. }
  887. };
  888. var fixM = function(path1, path2, a1, a2, i) {
  889. if (path1 && path2 && path1[i][0] == 'M' && path2[i][0] != 'M') {
  890. path2.splice(i, 0, ['M', a2.x, a2.y]);
  891. a1.bx = 0;
  892. a1.by = 0;
  893. a1.x = path1[i][1];
  894. a1.y = path1[i][2];
  895. length = MATH_MAX(p.length, p2 && p2.length || 0);
  896. }
  897. };
  898. for (var i = 0, length = MATH_MAX(p.length, p2 && p2.length || 0); i < length; i++) {
  899. p[i] = processPath(p[i], attrs);
  900. fixArc(p, i);
  901. p2 && (p2[i] = processPath(p2[i], attrs2));
  902. p2 && fixArc(p2, i);
  903. fixM(p, p2, attrs, attrs2, i);
  904. fixM(p2, p, attrs2, attrs, i);
  905. var seg = p[i];
  906. var seg2 = p2 && p2[i];
  907. var seglen = seg.length;
  908. var seg2len = p2 && seg2.length;
  909. attrs.x = seg[seglen - 2];
  910. attrs.y = seg[seglen - 1];
  911. attrs.bx = parseFloat(seg[seglen - 4]) || attrs.x;
  912. attrs.by = parseFloat(seg[seglen - 3]) || attrs.y;
  913. attrs2.bx = p2 && (parseFloat(seg2[seg2len - 4]) || attrs2.x);
  914. attrs2.by = p2 && (parseFloat(seg2[seg2len - 3]) || attrs2.y);
  915. attrs2.x = p2 && seg2[seg2len - 2];
  916. attrs2.y = p2 && seg2[seg2len - 1];
  917. }
  918. return p2 ? [p, p2] : p;
  919. }
  920. );
  921. Util.path2curve = function(path1, path2) {
  922. return Util.pathClone(Util._path2curve(path1, path2));
  923. };
  924. Util.parseDots = A.cached(
  925. function(gradient) {
  926. var dots = [];
  927. for (var i = 0, length = gradient.length; i < length; i++) {
  928. var dot = {};
  929. var par = gradient[i].match(REGEX_GRADIENT_VALUES);
  930. dot.color = ColorUtil.getRGB(par[1]);
  931. if (dot.color.error) {
  932. return null;
  933. }
  934. dot.color = dot.color.hex;
  935. par[2] && (dot.offset = par[2] + '%');
  936. dots.push(dot);
  937. }
  938. for (i = 1, length = dots.length - 1; i < length; i++) {
  939. if (!dots[i].offset) {
  940. var start = parseFloat(dots[i - 1].offset || 0);
  941. var end = 0;
  942. for (var j = i + 1; j < length; j++) {
  943. if (dots[j].offset) {
  944. end = dots[j].offset;
  945. break;
  946. }
  947. }
  948. if (!end) {
  949. end = 100;
  950. j = length;
  951. }
  952. end = parseFloat(end);
  953. var d = (end - start) / (j - i + 1);
  954. for (; i < j; i++) {
  955. start += d;
  956. dots[i].offset = start + '%';
  957. }
  958. }
  959. }
  960. return dots;
  961. }
  962. );
  963. Util.XYToString = function() {
  964. return this.x + STR_SPACE + this.y;
  965. };
  966. Util.getPointAtSegmentLength = A.cached(
  967. function(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, length) {
  968. var len = 0;
  969. var old;
  970. for (var i = 0; i < 1.01; i+=.01) {
  971. var dot = Util.findDotAtSegment(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, i);
  972. i && (len += MATH_POW(MATH_POW(old.x - dot.x, 2) + MATH_POW(old.y - dot.y, 2), 0.5));
  973. if (len >= length) {
  974. return dot;
  975. }
  976. old = dot;
  977. }
  978. }
  979. );
  980. var curvesLengths = {};
  981. Util.getPointAtSegmentLength = function(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, length) {
  982. var len = 0;
  983. var precision = 100;
  984. var name = [p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y].join();
  985. var cache = curvesLengths[name];
  986. var old;
  987. var dot;
  988. if (!cache) {
  989. cache = {
  990. data: []
  991. };
  992. curvesLengths[name] = cache;
  993. }
  994. if (cache.timer) {
  995. clearTimeout(cache.timer);
  996. }
  997. cache.timer = setTimeout(
  998. function() {
  999. delete curvesLengths[name];
  1000. },
  1001. 2000
  1002. );
  1003. if (length != null) {
  1004. var total = getPointAtSegmentLength(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y);
  1005. precision = ~~total * 10;
  1006. }
  1007. for (var i = 0; i < precision + 1; i++) {
  1008. if (cache.data[length] > i) {
  1009. dot = cache.data[i * precision];
  1010. }
  1011. else {
  1012. dot = Util.findDotsAtSegment(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, i / precision);
  1013. cache.data[i] = dot;
  1014. }
  1015. if (i) {
  1016. len += MATH_POW(MATH_POW(old.x - dot.x, 2) + MATH_POW(old.y - dot.y, 2), 0.5);
  1017. }
  1018. if (length != null && len >= length) {
  1019. return dot;
  1020. }
  1021. if (length == null) {
  1022. return len;
  1023. }
  1024. }
  1025. };
  1026. Util.getLengthFactory = function(istotal, subpath) {
  1027. return function(path, length, onlystart) {
  1028. path = Util.path2curve(path);
  1029. var x;
  1030. var y;
  1031. var p;
  1032. var l;
  1033. var sp = '';
  1034. var subpaths = {};
  1035. var point;
  1036. var len = 0;
  1037. for (var i = 0, length = path.length; i < length; i++) {
  1038. p = path[i];
  1039. if (p[0] == 'M') {
  1040. x = +p[1];
  1041. y = +p[2];
  1042. }
  1043. else {
  1044. l = Util.getPointAtSegmentLength(x, y, p[1], p[2], p[3], p[4], p[5], p[6]);
  1045. if (len + l > length) {
  1046. if (subpath && !subpaths.start) {
  1047. point = Util.getPointAtSegmentLength(x, y, p[1], p[2], p[3], p[4], p[5], p[6], length - len);
  1048. sp += [
  1049. 'C',
  1050. point.start.x,
  1051. point.start.y,
  1052. point.m.x,
  1053. point.m.y,
  1054. point.x,
  1055. point.y
  1056. ];
  1057. if (onlystart) {
  1058. return sp;
  1059. }
  1060. subpaths.start = sp;
  1061. sp = [
  1062. 'M',
  1063. point.x,
  1064. point.y + 'C',
  1065. point.n.x,
  1066. point.n.y,
  1067. point.end.x,
  1068. point.end.y,
  1069. p[5],
  1070. p[6]
  1071. ].join();
  1072. len += l;
  1073. x = +p[5];
  1074. y = +p[6];
  1075. continue;
  1076. }
  1077. if (!istotal && !subpath) {
  1078. point = Util.getPointAtSegmentLength(x, y, p[1], p[2], p[3], p[4], p[5], p[6], length - len);
  1079. return {
  1080. x: point.x,
  1081. y: point.y,
  1082. alpha: point.alpha
  1083. };
  1084. }
  1085. }
  1086. len += l;
  1087. x = +p[5];
  1088. y = +p[6];
  1089. }
  1090. sp += p;
  1091. }
  1092. subpaths.end = sp;
  1093. point = istotal ? len : subpath ? subpaths : Util.findDotsAtSegment(x, y, p[1], p[2], p[3], p[4], p[5], p[6], 1);
  1094. point.alpha && (point = {
  1095. x: point.x,
  1096. y: point.y,
  1097. alpha: point.alpha
  1098. });
  1099. return point;
  1100. };
  1101. };
  1102. Util.getTotalLength = Util.getLengthFactory(1);
  1103. Util.getPointAtLength = Util.getLengthFactory();
  1104. Util.getSubpathsAtLength = Util.getLengthFactory(0, 1);
  1105. Util.applyAttributes = function(element, name, value) {
  1106. var params;
  1107. if (value != null) {
  1108. params = {};
  1109. params[name] = value;
  1110. }
  1111. else if (name != null && isObject(name)) {
  1112. params = name;
  1113. }
  1114. var customAttributes = element.paper.customAttributes;
  1115. for (var key in customAttributes) {
  1116. if (
  1117. customAttributes.hasOwnProperty(key) &&
  1118. params.hasOwnProperty(key) &&
  1119. isFunction(customAttributes[key])
  1120. ) {
  1121. var subParams = customAttributes[key].apply(element, [].concat(params[key]));
  1122. element.attrs[key] = params[key];
  1123. for (var subKey in subParams) {
  1124. if (subParams.hasOwnProperty(subKey)) {
  1125. params[subKey] = subParams[subKey];
  1126. }
  1127. }
  1128. }
  1129. }
  1130. return params;
  1131. };
  1132. Element.prototype = {
  1133. attr: EMPTY_FN,
  1134. blur: EMPTY_FN,
  1135. clone: function() {
  1136. if (this.removed) {
  1137. return null;
  1138. }
  1139. var attr = this.attr();
  1140. delete attr.scale;
  1141. delete attr.translation;
  1142. return this.paper[this.type]().attr(attr);
  1143. },
  1144. createElement: EMPTY_FN,
  1145. detach: function(type, fn) {
  1146. var instance = this;
  1147. A.detach(Element._getEventType(type), fn, (instance.shape || instance.node || DOC));
  1148. return instance;
  1149. },
  1150. getRegion: EMPTY_FN,
  1151. getPointAtLength: function(length) {
  1152. if (this.type != 'path') {
  1153. return;
  1154. }
  1155. return Util.getPointAtLength(this.attrs.path, length);
  1156. },
  1157. getSubpath: function(from, to) {
  1158. if (this.type != 'path') {
  1159. return;
  1160. }
  1161. if (MATH.abs(this.getTotalLength() - to) < '1e-6') {
  1162. return Util.getSubpathsAtLength(this.attrs.path, from).end;
  1163. }
  1164. var a = Util.getSubpathsAtLength(this.attrs.path, to, 1);
  1165. return from ? Util.getSubpathsAtLength(a, from).end : a;
  1166. },
  1167. getTotalLength: function() {
  1168. if (this.type != 'path') {
  1169. return;
  1170. }
  1171. if (this.node.getTotalLength) {
  1172. return this.node.getTotalLength();
  1173. }
  1174. return Util.getTotalLength(this.attrs.path);
  1175. },
  1176. hide: EMPTY_FN,
  1177. hover: function(overFn, outFn) {
  1178. return this.on('mouseover', overFn).on('mouseout', outFn);
  1179. },
  1180. insertAfter: EMPTY_FN,
  1181. insertBefore: EMPTY_FN,
  1182. on: function(type, fn, context) {
  1183. var instance = this;
  1184. var realType = Element._getEventType(type);
  1185. A.on(realType, A.bind(fn, context || instance), instance.shape || instance.node || DOC, Element._getEventConfig(realType, type));
  1186. return instance;
  1187. },
  1188. remove: EMPTY_FN,
  1189. resetScale: function() {
  1190. if (this.removed) {
  1191. return this;
  1192. }
  1193. this._.sx = 1;
  1194. this._.sy = 1;
  1195. this.attrs.scale = '1 1';
  1196. },
  1197. rotate: EMPTY_FN,
  1198. scale: function(x, y, cx, cy) {
  1199. if (this.removed) {
  1200. return this;
  1201. }
  1202. if (x == null && y == null) {
  1203. return {
  1204. x: this._.sx,
  1205. y: this._.sy,
  1206. toString: Util.XYToString
  1207. };
  1208. }
  1209. y = y || x;
  1210. !+y && (y = x);
  1211. var dx;
  1212. var dy;
  1213. var dcx;
  1214. var dcy;
  1215. var a = this.attrs;
  1216. if (x != 0) {
  1217. var bb = this.getRegion();
  1218. var rcx = bb.x + bb.width / 2;
  1219. var rcy = bb.y + bb.height / 2;
  1220. var kx = MATH.abs(x / this._.sx);
  1221. var ky = MATH.abs(y / this._.sy);
  1222. cx = (+cx || cx == 0) ? cx : rcx;
  1223. cy = (+cy || cy == 0) ? cy : rcy;
  1224. var posx = ~~(this._.sx > 0);
  1225. var posy = ~~(this._.sy > 0);
  1226. var dirx = ~~(x / MATH.abs(x));
  1227. var diry = ~~(y / MATH.abs(y));
  1228. var dkx = kx * dirx;
  1229. var dky = ky * diry;
  1230. var s = this.node.style;
  1231. var ncx = cx + MATH.abs(rcx - cx) * dkx * (rcx > cx == posx ? 1 : -1);
  1232. var ncy = cy + MATH.abs(rcy - cy) * dky * (rcy > cy == posy ? 1 : -1);
  1233. var fr = (x * dirx > y * diry ? ky : kx);
  1234. switch (this.type) {
  1235. case 'rect':
  1236. case 'image':
  1237. var neww = a.width * kx;
  1238. var newh = a.height * ky;
  1239. this.attr({
  1240. height: newh,
  1241. r: a.r * fr,
  1242. width: neww,
  1243. x: ncx - neww / 2,
  1244. y: ncy - newh / 2
  1245. });
  1246. break;
  1247. case 'circle':
  1248. case 'ellipse':
  1249. this.attr({
  1250. rx: a.rx * dirx * kx,
  1251. ry: a.ry * diry * ky,
  1252. r: a.r * MATH_MIN(dirx * kx, diry * ky),
  1253. cx: ncx,
  1254. cy: ncy
  1255. });
  1256. break;
  1257. case 'text':
  1258. this.attr({
  1259. x: ncx,
  1260. y: ncy
  1261. });
  1262. break;
  1263. case 'path':
  1264. var path = Util.pathToRelative(a.path);
  1265. var skip = true;
  1266. var fx = posx ? dkx : kx;
  1267. var fy = posy ? dky : ky;
  1268. for (var i = 0, length = path.length; i < length; i++) {
  1269. var p = path[i];
  1270. var P0 = TO_UPPER_CASE.call(p[0]);
  1271. if (P0 == 'M' && skip) {
  1272. continue;
  1273. }
  1274. else {
  1275. skip = false;
  1276. }
  1277. if (P0 == 'A') {
  1278. p[path[i].length - 2] *= fx;
  1279. p[path[i].length - 1] *= fy;
  1280. p[1] *= kx;
  1281. p[2] *= ky;
  1282. p[5] = +(dirx + diry ? !!+p[5] : !+p[5]);
  1283. }
  1284. else if (P0 == 'H') {
  1285. for (var j = 1, jLength = p.length; j < jLength; j++) {
  1286. p[j] *= fx;
  1287. }
  1288. }
  1289. else if (P0 == 'V') {
  1290. for (j = 1, jLength = p.length; j < jLength; j++) {
  1291. p[j] *= fy;
  1292. }
  1293. }
  1294. else {
  1295. for (j = 1, jLength = p.length; j < jLength; j++) {
  1296. p[j] *= (j % 2) ? fx : fy;
  1297. }
  1298. }
  1299. }
  1300. var dim2 = Util.pathDimensions(path);
  1301. dx = ncx - dim2.x - dim2.width / 2;
  1302. dy = ncy - dim2.y - dim2.height / 2;
  1303. path[0][1] += dx;
  1304. path[0][2] += dy;
  1305. this.attr({path: path});
  1306. break;
  1307. }
  1308. if (this.type in MAP_TYPES_IMAGE_TEXT && (dirx != 1 || diry != 1)) {
  1309. if (this.transformations) {
  1310. this.transformations[2] = 'scale('.concat(dirx, ',', diry, ')');
  1311. this.node.setAttribute('transform', this.transformations.join(STR_SPACE));
  1312. dx = (dirx == -1) ? -a.x - (neww || 0) : a.x;
  1313. dy = (diry == -1) ? -a.y - (newh || 0) : a.y;
  1314. this.attr(
  1315. {
  1316. x: dx,
  1317. y: dy
  1318. }
  1319. );
  1320. a.fx = dirx - 1;
  1321. a.fy = diry - 1;
  1322. }
  1323. else {
  1324. this.node.filterMatrix = STR_MS_PROG_ID_PREFIX + '.Matrix(M11='.concat(dirx,
  1325. ', M12=0, M21=0, M22=', diry,
  1326. ', Dx=0, Dy=0, sizingmethod="auto expand", filtertype="bilinear")');
  1327. s.filter = (this.node.filterMatrix || STR_EMPTY) + (this.node.filterOpacity || STR_EMPTY);
  1328. }
  1329. }
  1330. else {
  1331. if (this.transformations) {
  1332. this.transformations[2] = STR_EMPTY;
  1333. this.node.setAttribute('transform', this.transformations.join(STR_SPACE));
  1334. a.fx = 0;
  1335. a.fy = 0;
  1336. }
  1337. else {
  1338. this.node.filterMatrix = STR_EMPTY;
  1339. s.filter = (this.node.filterMatrix || STR_EMPTY) + (this.node.filterOpacity || STR_EMPTY);
  1340. }
  1341. }
  1342. a.scale = [x, y, cx, cy].join(STR_SPACE);
  1343. this._.sx = x;
  1344. this._.sy = y;
  1345. }
  1346. return this;
  1347. },
  1348. show: EMPTY_FN,
  1349. toBack: EMPTY_FN,
  1350. toFront: EMPTY_FN,
  1351. toString: function() {
  1352. return '"' + TO_UPPER_CASE.call(this.type) + '": AlloyUI Drawing Element';
  1353. },
  1354. translate: EMPTY_FN,
  1355. unhover: function(overFn, outFn) {
  1356. return this.detach('mouseover', overFn).detach('mouseout', outFn);
  1357. }
  1358. };
  1359. Element._getEventConfig = EMPTY_FN;
  1360. Element._getEventType = function(eventType) {
  1361. return eventType;
  1362. };
  1363. Drawing.Element = Element;
  1364. var Set = A.Component.create(
  1365. {
  1366. NAME: 'set',
  1367. EXTENDS: A.ArrayList,
  1368. prototype: {
  1369. pop: function() {
  1370. var instance = this;
  1371. return instance._items.pop();
  1372. },
  1373. push: function() {
  1374. var instance = this;
  1375. var items = instance._items;
  1376. var args = arguments;
  1377. var length = args.length;
  1378. var item;
  1379. for (var i = 0; i < length; i++) {
  1380. item = args[i];
  1381. if (item && item instanceof Element || item instanceof Set) {
  1382. items[items.length] = args[i];
  1383. }
  1384. }
  1385. return instance;
  1386. },
  1387. clone: function() {
  1388. var instance = this;
  1389. var setList = new Set();
  1390. setList._items = instance._items;
  1391. return setList;
  1392. },
  1393. invoke: function(methodName) {
  1394. var instance = this;
  1395. var args = Array.prototype.slice.call(arguments, 1);
  1396. var item;
  1397. var items = instance._items;
  1398. for (var i = 0, length = items.length; i < length; i++) {
  1399. item = items[i];
  1400. if (methodName in item) {
  1401. item[methodName].apply(items[i], args);
  1402. }
  1403. }
  1404. return instance;
  1405. }
  1406. }
  1407. }
  1408. );
  1409. Drawing.Set = Set;
  1410. Set.addMethod = function(method) {
  1411. return A.ArrayList.addMethod(Drawing.Set.prototype, method);
  1412. };
  1413. var setListMethods = A.Object.keys(Element.prototype);
  1414. Set.addMethod(setListMethods);
  1415. Set.prototype.getRegion = Set.prototype.getBBox = function() {
  1416. var instance = this;
  1417. var x = [];
  1418. var y = [];
  1419. var w = [];
  1420. var h = [];
  1421. var items = instance._items;
  1422. for (var i = items.length; i--;) {
  1423. var box = items[i].getRegion();
  1424. x.push(box.x);
  1425. y.push(box.y);
  1426. w.push(box.x + box.width);
  1427. h.push(box.y + box.height);
  1428. }
  1429. x = MATH_MIN.apply(0, x);
  1430. y = MATH_MIN.apply(0, y);
  1431. return {
  1432. x: x,
  1433. y: y,
  1434. width: MATH_MAX.apply(0, w) - x,
  1435. height: MATH_MAX.apply(0, h) - y
  1436. };
  1437. };
  1438. Set.prototype.attr = function(name, value) {
  1439. var instance = this;
  1440. var items = instance._items;
  1441. if (name && isArray(name) && isObject(name[0])) {
  1442. for (var i = 0, length = name.length; i < length; i++) {
  1443. items[i].attr(name[i]);
  1444. }
  1445. }
  1446. else {
  1447. for (var i = 0, length = items.length; i < length; i++) {
  1448. items[i].attr(name, value);
  1449. }
  1450. }
  1451. return instance;
  1452. };
  1453. Set.prototype.toString = function() {
  1454. return this._items.join(',');
  1455. };
  1456. // Expose shared object/common constants
  1457. Drawing.REGEX_ISURL = REGEX_ISURL;
  1458. Drawing.REGEX_SEPARATOR = REGEX_SEPARATOR;
  1459. Drawing.REGEX_SEPARATOR_GRADIENT = REGEX_SEPARATOR_GRADIENT;
  1460. Drawing.REGEX_RADIAL_GRADIENT = REGEX_RADIAL_GRADIENT;
  1461. Drawing.MAP_ATTRS_AVAILABLE = MAP_ATTRS_AVAILABLE;
  1462. Drawing.MAP_TYPES_IMAGE_TEXT = MAP_TYPES_IMAGE_TEXT;
  1463. Drawing.MAP_TYPES_CIRCLE_ELLIPSE = MAP_TYPES_CIRCLE_ELLIPSE;
  1464. Drawing.STR_EMPTY = STR_EMPTY;
  1465. Drawing.STR_FILL = STR_FILL;
  1466. Drawing.STR_SPACE = STR_SPACE;
  1467. Drawing.STR_MS_PROG_ID_PREFIX = STR_MS_PROG_ID_PREFIX;
  1468. Drawing.Util = Util;
  1469. Drawing.Element = Element;
  1470. A.Drawing = Drawing;
  1471. }, '@VERSION@' ,{requires:['aui-base','aui-color-util','substitute']});