├── README.md ├── composer.json ├── gantt.css ├── gantt.html ├── ganttDrawerSVG.js ├── ganttGridEditor.js ├── ganttMaster.js ├── ganttPrint.css ├── ganttTask.js ├── ganttTestSuite.js ├── ganttUtilities.js ├── ganttZoom.js ├── libs ├── date.js ├── dialogs.js ├── forms.js ├── i18nJs.js ├── jquery │ ├── JST │ │ └── jquery.JST.js │ ├── dateField │ │ ├── img │ │ │ ├── next.png │ │ │ ├── prev.png │ │ │ └── today.png │ │ ├── jquery.dateField.css │ │ └── jquery.dateField.js │ ├── jquery.livequery.1.1.1.min.js │ ├── jquery.timers.js │ ├── svg │ │ ├── jquery.svg.min.js │ │ ├── jquery.svgdom.1.8.js │ │ └── jquery.svgdom.pack.js │ └── valueSlider │ │ ├── jquery.mb.slider.js │ │ └── mb.slider.css ├── layout.js └── utilities.js ├── license.txt ├── platform.css └── res ├── alert.gif ├── black_70.png ├── closeBig.png ├── ganttSplitterGrip.png ├── hasExternalDeps.png ├── icons.eot ├── icons.svg ├── icons.ttf ├── icons.woff ├── indentIcon.png ├── linkArrow.png ├── milestone.png ├── toggle-expand.png ├── toggle_collapse.png ├── twBanner.jpg ├── twGanttLogo.png └── twproject-badge.png /README.md: -------------------------------------------------------------------------------- 1 | jQueryGantt 2 | =========== 3 | jQuery Gantt editor has been written by Roberto Bicchierai and Silvia Chelazzi 4 | 5 | 6 | Twproject jQuery Gantt 7 | 8 | These are some key features: 9 | * jQuery based 3.2 10 | * MIT licensed: you can reuse everywhere https://opensource.org/licenses/MIT 11 | * JSON import-export 12 | * internationalizable 13 | * manage task status –> project workflow 14 | * manage dependencies 15 | * manage assignments (resources, roles efforts) 16 | * server synchronization ready 17 | * full undo-redo support 18 | * cross browser (at least for recent versions) 19 | * keyboard editing support 20 | * SVG visual editor 21 | * print friendly 22 | * collapsible branches 23 | * critical path 24 | * milestones, progress etc. 25 | * zoom 26 | 27 | Try the online working demo here: https://gantt.twproject.com 28 | 29 | Read here about latest release: https://roberto.twproject.com/2017/04/05/new-gantt-editor-release-the-best-ever/ 30 | 31 | Read the genesis of this component here: http://roberto.twproject.com/2012/06/14/the-javascript-gantt-odyssey/ 32 | 33 | Documentation is here: http://roberto.twproject.com/2012/08/24/jquery-gantt-editor/ 34 | 35 | jQuery Gantt editor is part of Twproject 6 project 36 | 37 | 38 | 39 | -------------------------------------------------------------------------------- /composer.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "robicch/jquery-gantt", 3 | "description": "Twproject Gantt editor is a free online tool for creating and sharing Gantts", 4 | "type": "library", 5 | "license": "MIT", 6 | "keywords": ["jquery","gantt"], 7 | "homepage": "https://github.com/robicch/jQueryGantt", 8 | "require": {} 9 | } 10 | -------------------------------------------------------------------------------- /gantt.css: -------------------------------------------------------------------------------- 1 | 2 | body{ 3 | /*overflow: hidden;*/ 4 | } 5 | 6 | .TWGanttWorkSpace.ganttFullScreen{ 7 | position: fixed; 8 | top:0; 9 | left:0; 10 | bottom:0; 11 | right: 0; 12 | margin: auto; 13 | z-index: 1000; 14 | background-color: #fff; 15 | } 16 | 17 | /* -------------------------------------- GRIDIFY -----------------------------------*/ 18 | .gdfTable { 19 | table-layout: fixed; 20 | border-collapse: separate; 21 | border-spacing: 0; 22 | background-color: #fff; 23 | } 24 | 25 | .gdfTable td, .gdfTable th { 26 | vertical-align: middle; 27 | overflow: hidden; 28 | text-overflow: clip; 29 | white-space: nowrap; 30 | font-size: 14px 31 | } 32 | 33 | .gdfCell { 34 | overflow: hidden; 35 | padding:4px 2px; 36 | border-bottom: 1px solid #eee; 37 | border-right: 1px solid #eee; 38 | font-family: arial, helvetica, sans-serif; 39 | } 40 | 41 | .gdfCell.noClip{ 42 | overflow: visible; 43 | } 44 | 45 | .gdfColHeader { 46 | min-width: 5px; 47 | height: 30px; 48 | background-color: #eee; 49 | border-bottom:2px solid #bbb; 50 | border-right: 1px solid #bbb; 51 | } 52 | 53 | .gdfColHeader:last-of-type { 54 | border-right: none; 55 | } 56 | 57 | .gdfCell:last-of-type { 58 | border-right: none; 59 | } 60 | 61 | 62 | .gdfCellInput { 63 | border: 0 none; 64 | font-size: 12px; 65 | height: 20px; 66 | margin: 0; 67 | padding: 0; 68 | width: 100%; 69 | background-color: #d4fbe8; 70 | } 71 | 72 | .gdfCellWrap { 73 | border: 0 none; 74 | font-size: 12px; 75 | height: 17px; 76 | margin: 0; 77 | padding: 0; 78 | width: 100%; 79 | overflow: hidden; 80 | 81 | background-color: #ffcccc; 82 | } 83 | 84 | .gdfHResizing { 85 | cursor: w-resize; 86 | } 87 | 88 | 89 | /* -------------------------------------- SPLITTER -----------------------------------*/ 90 | .splitterContainer { 91 | width: 100%; 92 | height: 100%; 93 | } 94 | 95 | .splitBox1{ 96 | overflow-x: scroll; 97 | overflow-y: hidden; 98 | } 99 | 100 | .splitBox2 { 101 | overflow-x: scroll; 102 | overflow-y: auto; 103 | } 104 | 105 | 106 | .splitElement { 107 | outline-style: none; 108 | position: absolute; 109 | height: 100%; 110 | background-color: #f3f3f3; 111 | } 112 | 113 | .vSplitBar { 114 | position: relative; 115 | width: 5px; 116 | /*background-color: rgba(170, 170, 170, .2);*/ 117 | cursor: ew-resize; 118 | text-align: center; 119 | color: white; 120 | box-shadow: 0 0 3px rgba(0, 0, 0, .4); 121 | background: rgba(170, 170, 170, .2) url("res/ganttSplitterGrip.png") no-repeat center center; 122 | z-index: 5; 123 | } 124 | 125 | .unselectable .vSplitBar, .vSplitBar:hover { 126 | background-color: rgba(170, 170, 170, .5); 127 | box-shadow: 0 0 5px rgba(0, 0, 0, .5); 128 | 129 | } 130 | 131 | .vSplitBar .toLeft,.vSplitBar .toRight,.vSplitBar .toCenter{ 132 | font-family: icons,TeamworkRegular; 133 | cursor: pointer; 134 | position: absolute; 135 | top: 0; 136 | margin-top: 0; 137 | /*background-color: rgba(170, 170, 170, .2);*/ 138 | /*background-color: rgba(0, 126, 221, 0.3);*/ 139 | background-color: rgba(47, 170, 201, 0.3); 140 | z-index: 2; 141 | font-size: 10px; 142 | width: 15px; 143 | /*box-shadow: 0 0 1px rgba(0, 0, 0, .5);*/ 144 | } 145 | 146 | .unselectable .vSplitBar .toLeft,.unselectable .vSplitBar .toCenter,.unselectable .vSplitBar .toRight, .vSplitBar:hover .toLeft, .vSplitBar:hover .toRight, .vSplitBar:hover .toCenter{ 147 | /*background-color: rgba(170, 170, 170, 1);*/ 148 | /*background-color: rgba(0, 126, 221, 1);*/ 149 | background-color: rgba(47, 170, 201, 1); 150 | 151 | box-shadow: 0 0 1px rgba(0, 0, 0, .4); 152 | } 153 | 154 | .vSplitBar .toLeft { 155 | left: -19px; 156 | text-align: left; 157 | } 158 | .vSplitBar .toCenter{ 159 | left:-4px; 160 | text-align: center; 161 | } 162 | .vSplitBar .toRight{ 163 | left:10px; 164 | text-align: right; 165 | } 166 | 167 | .ganttFixHead{ 168 | position: absolute; 169 | z-index: 2; 170 | top:0; 171 | } 172 | 173 | /* -------------------------------------- GANTT -----------------------------------*/ 174 | 175 | .ganttTable{ 176 | table-layout:fixed; 177 | background-color: #ffffff; 178 | } 179 | 180 | .ganttTable td,.ganttTable th{ 181 | overflow: hidden; 182 | text-overflow: clip; 183 | white-space: nowrap; 184 | } 185 | 186 | .ganttHead1,.ganttHead2{ 187 | height:20px; 188 | } 189 | 190 | .ganttHead1 th{ 191 | border-left:1px solid #b0b0b0; 192 | padding: 0; 193 | margin: 0; 194 | /*border-right: 1px solid #bbb;*/ 195 | border-bottom:1px solid #bbb; 196 | background: #EEEEEE; 197 | white-space: pre-line; 198 | word-break: break-all; 199 | } 200 | 201 | .ganttHead1 th, 202 | .ganttHead2 th{ 203 | white-space: nowrap; 204 | overflow: hidden; 205 | } 206 | 207 | .ganttHead2 th{ 208 | padding: 0; 209 | margin: 0; 210 | border-left:1px solid #b0b0b0; 211 | /*border-right: 1px solid #bbb;*/ 212 | border-bottom:2px solid #bbb; 213 | background: #EEEEEE; 214 | } 215 | 216 | .ganttHead1 th.headSmall,.ganttHead2 th.headSmall{ 217 | font-size: 10px; 218 | } 219 | 220 | .ganttHead1 th.headLeft,.ganttHead2 th.headLeft{ 221 | text-align: left; 222 | } 223 | 224 | .ganttToday{ 225 | position:absolute; 226 | top:0; 227 | width:1px; 228 | height:100%; 229 | border-left:2px dotted #13AFA5; 230 | } 231 | 232 | .ganttTitle img { 233 | max-width: 150px; 234 | } 235 | 236 | .ganttButtonBar{ 237 | position:relative; 238 | z-index: 2; 239 | /*background-color: #fff;*/ 240 | border-bottom: 1px solid #959595; 241 | padding: 5px 0 5px 10px; 242 | } 243 | 244 | .dataTable .ganttButtonBar{ 245 | border-bottom: none; 246 | } 247 | 248 | .ganttButtonBar .buttons { 249 | position: relative; 250 | display:inline-block; 251 | width: 100%; 252 | margin-top: 0; 253 | height: 45px; 254 | } 255 | 256 | .dataTable .ganttButtonBar .buttons { 257 | display:inline-block; 258 | width: 100%; 259 | } 260 | 261 | .ganttButtonBar .buttons button{ 262 | vertical-align: middle; 263 | margin:0; 264 | outline: none; 265 | } 266 | 267 | .ganttButtonBar .buttons .button.textual.icon { 268 | height: 45px; 269 | } 270 | 271 | 272 | .button span.teamworkIcon { 273 | text-indent: -10px; 274 | } 275 | 276 | 277 | .button.textual span.teamworkIcon { 278 | font-size: 140% 279 | } 280 | 281 | #saveGanttButton { 282 | margin-left:20px; 283 | padding: 5px 12px; 284 | margin-bottom: 0; 285 | vertical-align: middle; 286 | } 287 | 288 | 289 | .ganttButtonSeparator{ 290 | border-left:1px solid #dadada; 291 | margin:0 10px; 292 | font-size: 130%; 293 | vertical-align: middle; 294 | } 295 | 296 | .ganttLines{ 297 | position:absolute; 298 | width:100%; 299 | height:1px; 300 | border-top:1px solid #eee; 301 | z-index:1; 302 | } 303 | 304 | .ganttLinks{ 305 | z-index:10; 306 | } 307 | 308 | 309 | .ganttTable td.end{ 310 | border-right: 2px dotted #ddd; 311 | } 312 | 313 | .ganttHead2 th.holy{ 314 | background-color: rgba(236, 195, 176, 0.40); 315 | } 316 | .ganttBodyCell.holy{ 317 | background-color: rgba(255, 245, 230, 0.51); 318 | } 319 | 320 | 321 | /* -------------------------------------- TASK -----------------------------------*/ 322 | 323 | .taskBoxDiv{ 324 | position:absolute; 325 | height:25px; 326 | margin-top:3px; 327 | z-index:100; 328 | } 329 | 330 | .taskBoxDiv .layout { 331 | height:100%; 332 | color:#DB2727; 333 | border-radius:2px; 334 | background: #eee; /* Old browsers */ 335 | border:1px solid #bbb; 336 | } 337 | 338 | .taskBoxDiv .taskStatus { 339 | left:5px; 340 | top:10px; 341 | position:absolute; 342 | width:10px; 343 | height:10px; 344 | } 345 | 346 | .taskBoxDiv .layout .milestone{ 347 | top:0; 348 | position:absolute; 349 | width:18px; 350 | background: url(res/milestone.png) no-repeat; 351 | height:18px; 352 | display:none; 353 | } 354 | .taskBoxDiv .layout .milestone.end{ 355 | right:0; 356 | } 357 | .taskBoxDiv .layout .milestone.active{ 358 | display:block; 359 | } 360 | 361 | .taskBoxDiv.hasChild .layout{ 362 | border-top:2px solid black; 363 | } 364 | 365 | .taskBoxDiv .taskProgress{ 366 | height:5px; 367 | position:absolute; 368 | } 369 | 370 | .taskBoxDiv .layout.extDep{ 371 | background-image:url(res/hasExternalDeps.png); 372 | } 373 | 374 | 375 | .taskLabel{ 376 | position:absolute; 377 | height:28px; 378 | color:black; 379 | text-align:right; 380 | padding-right:5px; 381 | overflow:hidden; 382 | left:-200px; 383 | width:195px; 384 | white-space:nowrap; 385 | } 386 | 387 | 388 | .taskDepLine { 389 | border: 1px solid #9999ff; 390 | overflow: hidden; 391 | position: absolute; 392 | } 393 | 394 | 395 | .taskEditRow,.emptyRow { 396 | height:30px; 397 | } 398 | 399 | .taskEditRow input, .columnWidthTest{ 400 | border: 0 none; 401 | font-size: 14px; 402 | height: 20px; 403 | margin: 0; 404 | padding:0; 405 | outline: 0; 406 | width: 100%; 407 | border-radius: 0; 408 | vertical-align: text-bottom; 409 | } 410 | 411 | .taskEditRow input[type=checkbox]{ 412 | transform:scale(.7); 413 | width:15px; 414 | height: 15px; 415 | } 416 | 417 | .columnWidthTest{ 418 | width: auto; 419 | } 420 | 421 | .taskEditRow input:focus{ 422 | font-weight: bold; 423 | } 424 | 425 | .taskEditRow input{ 426 | background-color: transparent; 427 | } 428 | 429 | .taskEditRow.rowSelected td{ 430 | background-color:rgb(234, 248, 255); 431 | } 432 | 433 | 434 | .isGanttList .taskEditRow:nth-child(odd), .assigEditRow:nth-child(odd){ 435 | background-color: #ffffff; 436 | } 437 | .isGanttList .taskEditRow:nth-child(even), .assigEditRow:nth-child(even){ 438 | background-color: #ffffff; 439 | } 440 | 441 | input[readonly]{ 442 | color: #c0c0c0; 443 | } 444 | 445 | .taskStatusBox{ 446 | position:absolute; 447 | /*width:100px;*/ 448 | height:26px; 449 | border:1px solid #a0a0a0; 450 | background-color:#fff; 451 | margin-top:-21px; 452 | margin-left:-2px; 453 | padding: 4px; 454 | z-index: 100; 455 | } 456 | .taskStatus{ 457 | width:15px; 458 | height:15px; 459 | display:inline-block; 460 | text-indent: 0; 461 | position:relative; 462 | box-shadow: none; 463 | border-radius: 50%; 464 | border:0; 465 | cursor: pointer; 466 | } 467 | .taskStatus[status=STATUS_ACTIVE]{ 468 | background-color: #3BBF67; 469 | color: #fff; 470 | } 471 | .taskStatus[status=STATUS_DONE]{ 472 | background-color: #6EBEF4; 473 | color:#000; 474 | } 475 | .taskStatus[status=STATUS_FAILED]{ 476 | background-color: #763A96; 477 | color: #fff; 478 | } 479 | .taskStatus[status=STATUS_SUSPENDED]{ 480 | background-color: #F9C154; 481 | color:#000; 482 | } 483 | .taskStatus[status=STATUS_WAITING]{ 484 | background-color:#F79136; 485 | color:#000; 486 | } 487 | .taskStatus[status=STATUS_UNDEFINED]{ 488 | background-color: #dededf; 489 | color:#000; 490 | } 491 | .taskStatus.selected{ 492 | border:#666 2px solid; 493 | } 494 | 495 | select.taskStatus{ 496 | width: auto; 497 | height: auto; 498 | border-radius: 2px; 499 | } 500 | 501 | .assigsTableWrapper{ 502 | position: relative; 503 | height: 150px; 504 | overflow: auto; 505 | margin-top: -20px; 506 | } 507 | 508 | .unselectable { 509 | -webkit-user-select: none; 510 | -khtml-user-select: none; 511 | -moz-user-select: none; 512 | -o-user-select: none; 513 | user-select: none; 514 | } 515 | 516 | 517 | .exp-controller{ 518 | display:inline-block; 519 | width:16px; 520 | height:16px; 521 | position: relative; 522 | top: 2px; 523 | margin-left: -18px; 524 | } 525 | 526 | .isParent .exp-controller{ 527 | background-image: url(res/toggle_collapse.png); 528 | } 529 | 530 | .isParent.collapsed .exp-controller{ 531 | cursor: pointer; 532 | background-image: url(res/toggle-expand.png); 533 | } 534 | 535 | .ui-resizable-helper { border: 1px dotted #00F; } 536 | .ui-resizable-e, .ui-resizable-w {width: 5px;} 537 | .ui-draggable{ 538 | cursor:move; 539 | } 540 | 541 | /*--------------------------------------------------- SVG --------------------------------------------------*/ 542 | .ganttSVGBox{ 543 | position: absolute; 544 | top:0; 545 | left: 0; 546 | height: 100%; 547 | background-color: transparent; 548 | width: 100%; 549 | overflow-y: hidden; /*IE11 bug*/ 550 | } 551 | 552 | .taskBoxSVG{ 553 | overflow: visible; 554 | } 555 | 556 | .taskBoxSVG .taskLayout{ 557 | stroke-width:0; 558 | stroke:#999; 559 | } 560 | 561 | .taskLinkPathSVG{ 562 | stroke: rgba(47, 151, 198, 1); 563 | /*stroke:#9999ff;*/ 564 | stroke-width:2.5px; 565 | fill:none; 566 | cursor:pointer; 567 | } 568 | 569 | .ganttLinesSVG{ 570 | fill:transparent; 571 | stroke-width:1; 572 | stroke:#eee; 573 | } 574 | 575 | .isGanttList .ganttLinesSVG:nth-child(even){ 576 | fill:transparent; 577 | stroke-width:1; 578 | stroke:#fff; 579 | 580 | } 581 | .isGanttList .ganttLinesSVG:nth-child(odd){ 582 | fill:transparent; 583 | stroke-width:1; 584 | stroke:#eee; 585 | } 586 | 587 | .ganttLinesSVG.rowSelected{ 588 | fill: rgb(234, 248, 255) !important; 589 | /*fill: rgba(255, 255, 153, 0.50) !important;*/ 590 | } 591 | 592 | .ganttTodaySVG{ 593 | stroke-width:2px; 594 | stroke:#e06671; 595 | stroke-linecap:"round"; 596 | stroke-dasharray:2,2; 597 | } 598 | 599 | .colorByStatus .taskStatusSVG[status=STATUS_ACTIVE]{ 600 | fill: #3BBF67; 601 | } 602 | .colorByStatus .taskStatusSVG[status=STATUS_DONE]{ 603 | fill: #6EBEF4; 604 | } 605 | .colorByStatus .taskStatusSVG[status=STATUS_FAILED]{ 606 | fill: #763A96; 607 | } 608 | .colorByStatus .taskStatusSVG[status=STATUS_SUSPENDED]{ 609 | fill: #f9c154; 610 | } 611 | .colorByStatus .taskStatusSVG[status=STATUS_UNDEFINED]{ 612 | fill: #dededf; 613 | } 614 | .colorByStatus .taskStatusSVG[status=STATUS_UNDEFINED] .taskLayout{ 615 | stroke: #ccc; 616 | stroke-width:1; 617 | } 618 | 619 | .colorByStatus .taskStatusSVG[status=STATUS_DONE] .textPerc, 620 | .colorByStatus .taskStatusSVG[status=STATUS_ACTIVE] .textPerc, 621 | .colorByStatus .taskStatusSVG[status=STATUS_FAILED] .textPerc{ 622 | fill: #fff; 623 | } 624 | 625 | .deSVG.deSVGdrag { 626 | cursor: move; 627 | } 628 | 629 | .deSVG.deSVGhand { 630 | cursor: ew-resize; 631 | } 632 | 633 | .linkHandleSVG{ 634 | display:none; 635 | stroke:transparent; 636 | stroke-width:5; 637 | fill: rgba(47, 151, 198, 0.7); 638 | cursor: pointer; 639 | } 640 | 641 | .linkLineSVG{ 642 | stroke-width:5px; 643 | stroke: rgba(47, 151, 198, 0.7); 644 | stroke-linecap:"round"; 645 | opacity: .5; 646 | } 647 | 648 | .linkOnProgress .deSVG.taskBoxSVG { 649 | cursor:cell; 650 | } 651 | 652 | .taskBoxSVG.linkOver .taskLayout{ 653 | stroke-width:1px; 654 | stroke:rgba(47, 151, 198, 0.7); 655 | opacity: 1; 656 | } 657 | 658 | .taskLabelSVG { 659 | stroke: none; 660 | fill:#999; 661 | font-size: 12px; 662 | } 663 | 664 | .critical .taskLinkPathSVG{ 665 | stroke:red; 666 | } 667 | 668 | .taskBoxSVG.critical .taskLayout{ 669 | stroke:red; 670 | } 671 | 672 | .focused .taskLinkPathSVG{ 673 | stroke-width:5px; 674 | stroke: rgba(47, 151, 198, 0.7); 675 | } 676 | 677 | .taskBoxSVG.focused .taskLayout{ 678 | stroke-width:3px; 679 | stroke: rgba(47, 151, 198, 0.7); 680 | } 681 | 682 | .taskBoxSVG.critical .taskLayout{ 683 | stroke-width:3px; 684 | stroke: rgba(255, 0, 0, 0.7); 685 | } 686 | 687 | 688 | 689 | /*--------------------------------------------------- RESOURCE ADD --------------------------------------------------*/ 690 | .ganttAddResource{ 691 | position: absolute; 692 | width: 660px; 693 | height: 300px; 694 | border: 1px solid red; 695 | background-color: white; 696 | box-shadow: 0 0 5px rgba(0,0,0,0.3); 697 | top:120px; 698 | left:70px; 699 | z-index: 200; 700 | padding: 10px; 701 | } 702 | 703 | .ganttAddResource tr.isCompany{ 704 | display:none; 705 | } 706 | 707 | .ganttAddResource.isCompany tr.isCompany{ 708 | display:table-row; 709 | } 710 | .ganttAddResource.isCompany tr.isPerson{ 711 | display:none; 712 | } 713 | .ganttAddResourceBG { 714 | position: absolute; 715 | width: 100%; 716 | height: 100%; 717 | top: 0; 718 | left: 0; 719 | background-color: rgba(0, 0, 0, .3); 720 | z-index: 200; 721 | } 722 | 723 | 724 | /*---------------------------------#LOG_CHANGES_CONTAINER --------------------------------------------*/ 725 | #LOG_CHANGES_CONTAINER{ 726 | display: none; 727 | width: 300px; 728 | top:-130px; 729 | margin-left: -35px 730 | } 731 | 732 | 733 | .userProfile { 734 | font-size: 16px; 735 | vertical-align: middle; 736 | text-align: right; 737 | margin: 0 5px 0 0; 738 | padding: 5px; 739 | float: right; 740 | position: relative; 741 | z-index: 50; 742 | line-height: 40px; 743 | vertical-align: middle; 744 | position: absolute; 745 | right: 0; 746 | } 747 | 748 | .userLine { 749 | max-width: 150px; 750 | display: inline-block; 751 | text-overflow: ellipsis; 752 | overflow: hidden; 753 | white-space: nowrap; 754 | margin: 0;padding: 0; 755 | vertical-align: middle; 756 | } 757 | 758 | .avatar { 759 | vertical-align: middle; 760 | padding: 1px; 761 | width: 27px; 762 | height: 27px; 763 | border: 1px solid #dedede 764 | } 765 | 766 | /*--------------------------------------------------- Media queries --------------------------------------------------*/ 767 | 768 | /* Large screens */ 769 | 770 | @media only screen and (max-width : 1260px) { 771 | 772 | .ganttButtonBar .button span.teamworkIcon { 773 | font-size: 130%; 774 | } 775 | .userLine { 776 | display: none; 777 | } 778 | 779 | } 780 | 781 | @media only screen and (min-width : 1261px) and (max-width : 1320px) { 782 | 783 | .ganttButtonBar .button span.teamworkIcon { 784 | font-size: 130%; 785 | } 786 | 787 | .button { 788 | font-size: 100%; 789 | padding: 3px 9px 6px; 790 | margin-right: 5px; 791 | margin-bottom: 5px 792 | } 793 | 794 | .userLine { 795 | display: none; 796 | } 797 | 798 | } 799 | 800 | @media only screen and (max-width : 1160px) { 801 | 802 | .userProfile { 803 | float: none; 804 | position: absolute; 805 | top:0; 806 | right: 10px; 807 | } 808 | 809 | .userProfile .teamworkIcon { 810 | color: rgb(255, 255, 255); 811 | } 812 | .userProfile .ganttButtonSeparator, .userProfile .avatar { 813 | border-color: rgb(127, 154, 170); 814 | } 815 | 816 | } 817 | 818 | /* Ipad */ 819 | 820 | @media only screen and (min-width: 768px) and (max-width: 1024px){ 821 | .ganttButtonSeparator { 822 | margin-left: 2px; 823 | padding-right: 6px; 824 | font-size: 100%; 825 | } 826 | .button { 827 | padding: 5px 6px 6px; 828 | } 829 | } 830 | 831 | /* Mobile TODO */ 832 | 833 | @media only screen and (max-width: 767px) { 834 | .button { 835 | font-size: 50%; 836 | } 837 | } 838 | -------------------------------------------------------------------------------- /ganttPrint.css: -------------------------------------------------------------------------------- 1 | .noprint { 2 | display:none !important; 3 | } 4 | 5 | BODY, TBODY { 6 | font-family: arial; 7 | font-size: 12px; 8 | margin: 0; 9 | color: #000; 10 | overflow: visible!important; 11 | } 12 | 13 | .teamworkIcon{ 14 | display:none; 15 | } 16 | 17 | .mainColumn{ 18 | width:98% !important; 19 | } 20 | 21 | 22 | #TWGanttArea{ 23 | overflow-x: visible !important; 24 | overflow-y: visible !important; 25 | width: auto !important; 26 | height: auto !important; 27 | border:none !important; 28 | } 29 | 30 | .splitterContainer{ 31 | width: auto !important; 32 | height: auto !important; 33 | } 34 | .splitElement{ 35 | position: static !important; 36 | width: auto !important; 37 | height: auto !important; 38 | top:0 !important; 39 | left: 0 !important; 40 | overflow-x: visible !important; 41 | overflow-y: visible !important; 42 | } 43 | 44 | .vSplitBar,.emptyRow{ 45 | display: none !important; 46 | } 47 | 48 | .gdfTable{ 49 | width: 0 !important; 50 | } 51 | 52 | .splitBox2{ 53 | page-break-before: always !important; 54 | } 55 | 56 | 57 | .ganttFixHead{ 58 | display: none !important; 59 | } 60 | -------------------------------------------------------------------------------- /ganttUtilities.js: -------------------------------------------------------------------------------- 1 | /* 2 | Copyright (c) 2012-2018 Open Lab 3 | Written by Roberto Bicchierai and Silvia Chelazzi http://roberto.open-lab.com 4 | Permission is hereby granted, free of charge, to any person obtaining 5 | a copy of this software and associated documentation files (the 6 | "Software"), to deal in the Software without restriction, including 7 | without limitation the rights to use, copy, modify, merge, publish, 8 | distribute, sublicense, and/or sell copies of the Software, and to 9 | permit persons to whom the Software is furnished to do so, subject to 10 | the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be 13 | included in all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 16 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 17 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 18 | NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 19 | LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 20 | OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 21 | WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 22 | */ 23 | 24 | $.gridify = function (table, opt) { 25 | var options = { 26 | resizeZoneWidth: 10 27 | }; 28 | 29 | $.extend(options, opt); 30 | 31 | var box = $("
").addClass("gdfWrapper"); 32 | box.append(table); 33 | 34 | var head = table.clone(); 35 | head.addClass("table ganttFixHead"); 36 | //remove non head 37 | head.find("tbody").remove(); 38 | box.append(head); 39 | 40 | box.append(table); 41 | 42 | var hTh = head.find(".gdfColHeader"); 43 | var cTh = table.find(".gdfColHeader"); 44 | for (var i = 0; i < hTh.length; i++) { 45 | hTh.eq(i).data("fTh", cTh.eq(i)); 46 | } 47 | 48 | //--------- set table to 0 to prevent a strange 100% 49 | table.width(0); 50 | head.width(0); 51 | 52 | 53 | //---------------------- header management start 54 | head.find("th.gdfColHeader:not(.gdfied)").mouseover(function () { 55 | $(this).addClass("gdfColHeaderOver"); 56 | 57 | }).on("mouseout.gdf", function () { 58 | $(this).removeClass("gdfColHeaderOver"); 59 | if (!$.gridify.columInResize) { 60 | $("body").removeClass("gdfHResizing"); 61 | } 62 | 63 | }).on("mousemove.gdf", function (e) { 64 | if (!$.gridify.columInResize) { 65 | var colHeader = $(this); 66 | var nextCol = colHeader.next(); 67 | if (nextCol.length > 0 && nextCol.width() < options.resizeZoneWidth) 68 | colHeader = nextCol; 69 | 70 | if (!colHeader.is(".gdfResizable")) 71 | return; 72 | 73 | var mousePos = e.pageX - colHeader.offset().left; 74 | 75 | if (colHeader.width() - mousePos < options.resizeZoneWidth) { 76 | $("body").addClass("gdfHResizing"); 77 | } else { 78 | $("body").removeClass("gdfHResizing"); 79 | } 80 | } 81 | 82 | }).on("mousedown.gdf", function (e) { 83 | //console.debug("mousedown.gdf") 84 | var colHeader = $(this); 85 | 86 | var nextCol = colHeader.next(); 87 | if (nextCol.length > 0 && nextCol.width() < options.resizeZoneWidth) 88 | colHeader = nextCol; 89 | 90 | if (!colHeader.is(".gdfResizable")) 91 | return; 92 | 93 | var mousePos = e.pageX - colHeader.offset().left; 94 | if (colHeader.width() - mousePos < options.resizeZoneWidth) { 95 | $("body").unselectable(); 96 | $.gridify.columInResize = colHeader; 97 | //on event for start resizing 98 | $(document).on("mousemove.gdf", function (e) { 99 | 100 | e.preventDefault(); 101 | $("body").addClass("gdfHResizing"); 102 | 103 | //manage resizing 104 | var w = e.pageX - $.gridify.columInResize.offset().left; 105 | w = w <= 1 ? 1 : w; 106 | $.gridify.columInResize.width(w); 107 | $.gridify.columInResize.data("fTh").width(w); 108 | 109 | 110 | //on mouse up on body to stop resizing 111 | }).on("mouseup.gdf", function () { 112 | //console.debug("mouseup.gdf") 113 | $(this).off("mousemove.gdf").off("mouseup.gdf").clearUnselectable(); 114 | $("body").removeClass("gdfHResizing"); 115 | delete $.gridify.columInResize; 116 | 117 | //save columns dimension 118 | storeGridState(); 119 | 120 | }); 121 | } 122 | 123 | }).on("dblclick.gdf", function () { 124 | //console.debug("dblclick.gdf") 125 | var col = $(this); 126 | 127 | if (!col.is(".gdfResizable")) 128 | return; 129 | 130 | var idx = $("th", col.parents("table")).index(col); 131 | var columnTd = $("td:nth-child(" + (idx + 1) + ")", table); 132 | var w = 0; 133 | columnTd.each(function () { 134 | var td = $(this); 135 | var content = td.children("input").length ? td.children("input").val() : td.html(); 136 | var tmp = $("
").addClass("columnWidthTest").html(content).css({position: "absolute"}); 137 | $("body").append(tmp); 138 | w = Math.max(w, tmp.width() + parseFloat(td.css("padding-left"))); 139 | tmp.remove(); 140 | }); 141 | 142 | w = w + 5; 143 | col.width(w); 144 | col.data("fTh").width(w); 145 | 146 | //save columns dimension 147 | storeGridState(); 148 | return false; 149 | 150 | }).addClass("gdfied unselectable").attr("unselectable", "true"); 151 | 152 | 153 | function storeGridState() { 154 | //console.debug("storeGridState"); 155 | if (localStorage) { 156 | var gridState = {}; 157 | 158 | var colSizes = []; 159 | $(".gdfTable .gdfColHeader").each(function () { 160 | colSizes.push($(this).outerWidth()); 161 | }); 162 | 163 | gridState.colSizes = colSizes; 164 | 165 | localStorage.setObject("TWPGanttGridState", gridState); 166 | } 167 | } 168 | 169 | function loadGridState() { 170 | //console.debug("loadGridState") 171 | if (localStorage) { 172 | if (localStorage.getObject("TWPGanttGridState")) { 173 | var gridState = localStorage.getObject("TWPGanttGridState"); 174 | if (gridState.colSizes) { 175 | box.find(".gdfTable .gdfColHeader").each(function (i) { 176 | $(this).width(gridState.colSizes[i]); 177 | }); 178 | } 179 | } 180 | } 181 | } 182 | 183 | loadGridState(); 184 | return box; 185 | }; 186 | 187 | 188 | 189 | 190 | $.splittify = { 191 | init: function (where, first, second, perc) { 192 | 193 | //perc = perc || 50; 194 | 195 | var element = $("
").addClass("splitterContainer"); 196 | var firstBox = $("
").addClass("splitElement splitBox1"); 197 | var splitterBar = $("
").addClass("splitElement vSplitBar").attr("unselectable", "on").css("padding-top", where.height() / 2 + "px"); 198 | var secondBox = $("
").addClass("splitElement splitBox2"); 199 | 200 | 201 | var splitter = new Splitter(element, firstBox, secondBox, splitterBar); 202 | splitter.perc = perc; 203 | 204 | //override with saved one 205 | loadPosition(); 206 | 207 | var toLeft = $("
").addClass("toLeft").html("{").click(function () {splitter.resize(0.001, 300);}); 208 | splitterBar.append(toLeft); 209 | 210 | var toCenter = $("
").addClass("toCenter").html("©").click(function () {splitter.resize(50, 300);}); 211 | splitterBar.append(toCenter); 212 | 213 | var toRight = $("
").addClass("toRight").html("}").click(function () {splitter.resize(99.9999, 300);}); 214 | splitterBar.append(toRight); 215 | 216 | 217 | firstBox.append(first); 218 | secondBox.append(second); 219 | 220 | element.append(firstBox).append(secondBox).append(splitterBar); 221 | 222 | where.append(element); 223 | 224 | var totalW = where.innerWidth(); 225 | var splW = splitterBar.width(); 226 | var fbw = totalW * perc / 100 - splW; 227 | fbw = fbw > totalW - splW - splitter.secondBoxMinWidth ? totalW - splW - splitter.secondBoxMinWidth : fbw; 228 | firstBox.width(fbw).css({left: 0}); 229 | splitterBar.css({left: firstBox.width()}); 230 | secondBox.width(totalW - fbw - splW).css({left: firstBox.width() + splW}); 231 | 232 | splitterBar.on("mousedown.gdf", function (e) { 233 | 234 | e.preventDefault(); 235 | $("body").addClass("gdfHResizing"); 236 | 237 | $.splittify.splitterBar = $(this); 238 | //on event for start resizing 239 | //console.debug("start splitting"); 240 | $("body").unselectable().on("mousemove.gdf", function (e) { 241 | //manage resizing 242 | e.preventDefault(); 243 | 244 | var sb = $.splittify.splitterBar; 245 | var pos = e.pageX - sb.parent().offset().left; 246 | var w = sb.parent().width(); 247 | var fbw = firstBox; 248 | 249 | pos = pos > splitter.firstBoxMinWidth ? pos : splitter.firstBoxMinWidth; 250 | //pos = pos < realW - 10 ? pos : realW - 10; 251 | pos = pos > totalW - splW - splitter.secondBoxMinWidth ? totalW - splW - splitter.secondBoxMinWidth : pos; 252 | sb.css({left: pos}); 253 | firstBox.width(pos); 254 | secondBox.css({left: pos + sb.width(), width: w - pos - sb.width()}); 255 | splitter.perc = (firstBox.width() / splitter.element.width()) * 100; 256 | 257 | //on mouse up on body to stop resizing 258 | }).on("mouseup.gdf", function () { 259 | //console.debug("stop splitting"); 260 | $(this).off("mousemove.gdf").off("mouseup.gdf").clearUnselectable(); 261 | delete $.splittify.splitterBar; 262 | 263 | $("body").removeClass("gdfHResizing"); 264 | 265 | storePosition(); 266 | }); 267 | }); 268 | 269 | 270 | // keep both side in synch when scroll 271 | var stopScroll = false; 272 | var fs = firstBox.add(secondBox); 273 | var lastScrollTop=0; 274 | fs.scroll(function (e) { 275 | var el = $(this); 276 | var top = el.scrollTop(); 277 | 278 | var firstBoxHeader = firstBox.find(".ganttFixHead"); 279 | var secondBoxHeader = secondBox.find(".ganttFixHead"); 280 | 281 | if (el.is(".splitBox1") && stopScroll != "splitBox2") { 282 | stopScroll = "splitBox1"; 283 | secondBox.scrollTop(top); 284 | } else if (el.is(".splitBox2") && stopScroll != "splitBox1") { 285 | stopScroll = "splitBox2"; 286 | firstBox.scrollTop(top); 287 | } 288 | 289 | 290 | if (Math.abs(top-lastScrollTop)>10) { 291 | firstBoxHeader.css('top', top).hide(); 292 | secondBoxHeader.css('top', top).hide(); 293 | } 294 | lastScrollTop=top; 295 | 296 | where.stopTime("reset").oneTime(100, "reset", function () { 297 | 298 | stopScroll = ""; 299 | top = el.scrollTop(); 300 | 301 | firstBoxHeader.css('top', top).fadeIn(); 302 | secondBoxHeader.css('top', top).fadeIn(); 303 | 304 | }); 305 | 306 | }); 307 | 308 | 309 | firstBox.on('mousewheel MozMousePixelScroll', function (event) { 310 | 311 | event.preventDefault(); 312 | 313 | var deltaY = event.originalEvent.wheelDeltaY; 314 | if (!deltaY) 315 | deltaY = event.originalEvent.wheelDelta; 316 | var deltaX = event.originalEvent.wheelDeltaX; 317 | 318 | if (event.originalEvent.axis) { 319 | deltaY = event.originalEvent.axis == 2 ? -event.originalEvent.detail : null; 320 | deltaX = event.originalEvent.axis == 1 ? -event.originalEvent.detail : null; 321 | } 322 | 323 | deltaY = Math.abs(deltaY) < 40 ? 40 * (Math.abs(deltaY) / deltaY) : deltaY; 324 | deltaX = Math.abs(deltaX) < 40 ? 40 * (Math.abs(deltaX) / deltaX) : deltaX; 325 | 326 | var scrollToY = secondBox.scrollTop() - deltaY; 327 | var scrollToX = firstBox.scrollLeft() - deltaX; 328 | 329 | // console.debug( firstBox.scrollLeft(), Math.abs(deltaX), Math.abs(deltaY)); 330 | 331 | if (deltaY) secondBox.scrollTop(scrollToY); 332 | if (deltaX) firstBox.scrollLeft(scrollToX); 333 | 334 | return false; 335 | }); 336 | 337 | 338 | function Splitter(element, firstBox, secondBox, splitterBar) { 339 | this.element = element; 340 | this.firstBox = firstBox; 341 | this.secondBox = secondBox; 342 | this.splitterBar = splitterBar; 343 | this.perc = 0; 344 | this.firstBoxMinWidth = 0; 345 | this.secondBoxMinWidth = 30; 346 | 347 | this.resize = function (newPerc, anim) { 348 | var animTime = anim ? anim : 0; 349 | this.perc = newPerc ? newPerc : this.perc; 350 | var totalW = this.element.width(); 351 | var splW = this.splitterBar.width(); 352 | var newW = totalW * this.perc / 100; 353 | newW = newW > this.firstBoxMinWidth ? newW : this.firstBoxMinWidth; 354 | newW = newW > totalW - splW - splitter.secondBoxMinWidth ? totalW - splW - splitter.secondBoxMinWidth : newW; 355 | this.firstBox.animate({width: newW}, animTime, function () {$(this).css("overflow-x", "auto")}); 356 | this.splitterBar.animate({left: newW}, animTime); 357 | this.secondBox.animate({left: newW + this.splitterBar.width(), width: totalW - newW - splW}, animTime, function () {$(this).css("overflow", "auto")}); 358 | 359 | storePosition(); 360 | }; 361 | 362 | var self = this; 363 | this.splitterBar.on("dblclick", function () { 364 | self.resize(50, true); 365 | }) 366 | } 367 | 368 | 369 | function storePosition () { 370 | //console.debug("storePosition",splitter.perc); 371 | if (localStorage) { 372 | localStorage.setItem("TWPGanttSplitPos",splitter.perc); 373 | } 374 | } 375 | 376 | function loadPosition () { 377 | //console.debug("loadPosition"); 378 | if (localStorage) { 379 | if (localStorage.getItem("TWPGanttSplitPos")) { 380 | splitter.perc=parseFloat(localStorage.getItem("TWPGanttSplitPos")); 381 | } 382 | } 383 | } 384 | 385 | 386 | 387 | return splitter; 388 | } 389 | 390 | }; 391 | 392 | 393 | //<%------------------------------------------------------------------------ UTILITIES ---------------------------------------------------------------%> 394 | // same dates returns 1 395 | function getDurationInUnits(start,end){ 396 | return start.distanceInWorkingDays(end)+1; // working in days 397 | } 398 | 399 | //con due date uguali ritorna 0: usata per cancolare la distanza effettiva tra due date 400 | function getDistanceInUnits(date1,date2){ 401 | return date1.distanceInWorkingDays(date2); // working in days 402 | } 403 | 404 | function incrementDateByUnits(date,duration){ 405 | date.incrementDateByWorkingDays(duration); // working in days 406 | return date; 407 | } 408 | 409 | 410 | function computeStart(start) { 411 | return computeStartDate(start).getTime(); 412 | } 413 | 414 | /** 415 | * @param start 416 | * @returns {Date} the closes start date 417 | */ 418 | function computeStartDate(start) { 419 | var d; 420 | d = new Date(start + 3600000 * 12); 421 | d.setHours(0, 0, 0, 0); 422 | //move to next working day 423 | while (isHoliday(d)) { 424 | d.setDate(d.getDate() + 1); 425 | } 426 | d.setHours(0, 0, 0, 0); 427 | return d; 428 | } 429 | 430 | function computeEnd(end) { 431 | return computeEndDate(end).getTime() 432 | } 433 | 434 | /** 435 | * @param end 436 | * @returns {Date} the closest end date 437 | */ 438 | function computeEndDate(end) { 439 | var d = new Date(end - 3600000 * 12); 440 | d.setHours(23, 59, 59, 999); 441 | //move to next working day 442 | while (isHoliday(d)) { 443 | d.setDate(d.getDate() + 1); 444 | } 445 | d.setHours(23, 59, 59, 999); 446 | return d; 447 | } 448 | 449 | function computeEndByDuration(start, duration) { 450 | //console.debug("computeEndByDuration start ",d,duration) 451 | var d = new Date(start); 452 | var q = duration - 1; 453 | while (q > 0) { 454 | d.setDate(d.getDate() + 1); 455 | if (!isHoliday(d)) 456 | q--; 457 | } 458 | d.setHours(23, 59, 59, 999); 459 | return d.getTime(); 460 | } 461 | 462 | 463 | function incrementDateByWorkingDays(date, days) { 464 | var d = new Date(date); 465 | d.incrementDateByWorkingDays(days); 466 | return d.getTime(); 467 | } 468 | 469 | 470 | function recomputeDuration(start, end) { 471 | //console.debug("recomputeDuration"); 472 | return getDurationInUnits(new Date(start),new Date(end)); 473 | } 474 | 475 | function resynchDates(leavingField, startField, startMilesField, durationField, endField, endMilesField) { 476 | //console.debug("resynchDates",leavingField.prop("name"), "start. "+startField.val(),"durationField: "+ durationField.val(), "endField: "+endField.val()); 477 | 478 | function resynchDatesSetFields(command) { 479 | //console.debug("resynchDatesSetFields",command); 480 | var duration = stringToDuration(durationField.val()); 481 | var start = computeStart(Date.parseString(startField.val()).getTime()); 482 | 483 | var end = endField.val(); 484 | if (end.length > 0) { 485 | end = Date.parseString(end); 486 | end.setHours(23, 59, 59, 999); //this is necessary because compute end get the closest end, and parseString returns 00:00 487 | end = computeEnd(end.getTime()); 488 | } 489 | 490 | var date = new Date(); 491 | if ("CHANGE_END" == command) { 492 | date.setTime(start); 493 | var workingUnits = duration-1; // if we do not decremet a task lasting two days starting on 10 will end on 12 (at 00:00) instead of on (at 23:59) 494 | incrementDateByUnits(date,workingUnits); 495 | date.setHours(23, 59, 59, 999); //this is necessary because compute end get the closest end, and parseString returns 00:00 496 | end = computeEnd(date.getTime()); // not strictly necessary 497 | } else if ("CHANGE_START" == command) { 498 | date.setTime(end); 499 | var workingUnits = duration - 1; // if we do not decremet a task lasting two days starting on 10 will end on 12 (at 00:00) instead of on (at 23:59) 500 | incrementDateByUnits(date,-workingUnits); 501 | date.setHours(0, 0, 0, 0); //this is necessary because decreasing end we are at 23:50 502 | start = computeStart(date.getTime()); //not strictly necessary 503 | } else if ("CHANGE_DURATION" == command) { 504 | duration = getDurationInUnits(new Date(start),new Date(end)) + 1; 505 | } 506 | 507 | startField.val(new Date(start).format()); 508 | endField.val(new Date(end).format()); 509 | durationField.val(durationToString(duration)); 510 | 511 | return {start: start, end: end, duration: duration}; 512 | } 513 | 514 | var leavingFieldName = leavingField.prop("name"); 515 | var durIsFilled = durationField.val().length > 0; 516 | var startIsFilled = startField.val().length > 0; 517 | var endIsFilled = endField.val().length > 0; 518 | var startIsMilesAndFilled = startIsFilled && (startMilesField.prop("checked") || startField.is("[readOnly]")); 519 | var endIsMilesAndFilled = endIsFilled && (endMilesField.prop("checked") || endField.is("[readOnly]")); 520 | 521 | if (durIsFilled) { 522 | durationField.val(durationToString(stringToDuration(durationField.val()))); 523 | } 524 | 525 | if (leavingFieldName.indexOf("Milestone") > 0) { 526 | if (startIsMilesAndFilled && endIsMilesAndFilled) { 527 | durationField.prop("readOnly", true); 528 | } else { 529 | durationField.prop("readOnly", false); 530 | } 531 | return; 532 | } 533 | 534 | //need at least two values to resynch the third 535 | if ((durIsFilled ? 1 : 0) + (startIsFilled ? 1 : 0) + (endIsFilled ? 1 : 0) < 2) 536 | return; 537 | 538 | var ret; 539 | if (leavingFieldName == 'start' && startIsFilled) { 540 | if (endIsMilesAndFilled && durIsFilled) { 541 | ret = resynchDatesSetFields("CHANGE_DURATION"); 542 | } else if (durIsFilled) { 543 | ret = resynchDatesSetFields("CHANGE_END"); 544 | } 545 | 546 | } else if (leavingFieldName == 'duration' && durIsFilled && !(endIsMilesAndFilled && startIsMilesAndFilled)) { 547 | if (endIsMilesAndFilled && !startIsMilesAndFilled) { 548 | ret = resynchDatesSetFields("CHANGE_START"); 549 | } else if (!endIsMilesAndFilled) { 550 | //document.title=('go and change end!!'); 551 | ret = resynchDatesSetFields("CHANGE_END"); 552 | } 553 | 554 | } else if (leavingFieldName == 'end' && endIsFilled) { 555 | ret = resynchDatesSetFields("CHANGE_DURATION"); 556 | } 557 | return ret; 558 | } 559 | 560 | 561 | //This prototype is provided by the Mozilla foundation and 562 | //is distributed under the MIT license. 563 | //http://www.ibiblio.org/pub/Linux/LICENSES/mit.license 564 | 565 | if (!Array.prototype.filter) { 566 | Array.prototype.filter = function (fun) { 567 | var len = this.length; 568 | if (typeof fun != "function") 569 | throw new TypeError(); 570 | 571 | var res = new Array(); 572 | var thisp = arguments[1]; 573 | for (var i = 0; i < len; i++) { 574 | if (i in this) { 575 | var val = this[i]; // in case fun mutates this 576 | if (fun.call(thisp, val, i, this)) 577 | res.push(val); 578 | } 579 | } 580 | return res; 581 | }; 582 | } 583 | 584 | function durationToString(d) { 585 | return d; 586 | } 587 | 588 | function stringToDuration(durStr) { 589 | var duration = NaN; 590 | duration = daysFromString(durStr, true) || 1; 591 | return duration; 592 | } 593 | 594 | function goToPage(url) { 595 | if (!canILeave()) return; 596 | window.location.href = url; 597 | } 598 | -------------------------------------------------------------------------------- /ganttZoom.js: -------------------------------------------------------------------------------- 1 | /* 2 | Copyright (c) 2012-2018 Open Lab 3 | Written by Roberto Bicchierai and Silvia Chelazzi http://roberto.open-lab.com 4 | Permission is hereby granted, free of charge, to any person obtaining 5 | a copy of this software and associated documentation files (the 6 | "Software"), to deal in the Software without restriction, including 7 | without limitation the rights to use, copy, modify, merge, publish, 8 | distribute, sublicense, and/or sell copies of the Software, and to 9 | permit persons to whom the Software is furnished to do so, subject to 10 | the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be 13 | included in all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 16 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 17 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 18 | NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 19 | LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 20 | OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 21 | WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 22 | 23 | */ 24 | 25 | Ganttalendar.prototype.initZoomlevels = function () { 26 | //console.debug("Ganttalendar.prototype.initZoomlevels"); 27 | 28 | var self = this; 29 | 30 | // define the zoom level arrays 31 | this.zoomLevels = []; 32 | this.zoomDrawers = {}; 33 | 34 | 35 | function _addZoom(zoom,zoomDrawer){ 36 | self.zoomLevels.push(zoom); 37 | self.zoomDrawers[zoom] = zoomDrawer; 38 | 39 | //compute the scale 40 | self.zoomDrawers[zoom].computedScaleX=600/millisFromString(zoom); 41 | } 42 | 43 | 44 | //----------------------------- 3 DAYS 600px----------------------------- 45 | _addZoom("3d", { 46 | adjustDates: function (start, end) { 47 | start.setFirstDayOfThisWeek(); 48 | end.setFirstDayOfThisWeek(); 49 | end.setDate(end.getDate() + 6); 50 | }, 51 | row1: function (date, ctxHead) { 52 | var start = new Date(date.getTime()); 53 | date.setDate(date.getDate() + 6); 54 | self.createHeadCell(1,this,ctxHead,start.format("MMMM d") + " - " + date.format("MMMM d yyyy")+ " ("+start.format("w")+")",7,"", start,date); 55 | date.setDate(date.getDate() + 1); 56 | }, 57 | row2: function (date, ctxHead, ctxBody) { 58 | var start = new Date(date.getTime()); 59 | date.setDate(date.getDate() + 1); 60 | var holyClass = isHoliday(start) ? "holy" : ""; 61 | self.createHeadCell(2,this,ctxHead,start.format("EEE d"), 1, "headSmall "+holyClass, start,date); 62 | self.createBodyCell(this,ctxBody,1, start.getDay() % 7 == (self.master.firstDayOfWeek + 6) % 7, holyClass); 63 | } 64 | }); 65 | 66 | 67 | 68 | //----------------------------- 1 WEEK 600px ----------------------------- 69 | _addZoom("1w", { 70 | adjustDates: function (start, end) { 71 | //reset day of week 72 | start.setFirstDayOfThisWeek(); 73 | start.setDate(start.getDate() - 7); 74 | end.setFirstDayOfThisWeek(); 75 | end.setDate(end.getDate() + 13); 76 | }, 77 | row1: function (date, ctxHead) { 78 | var start = new Date(date.getTime()); 79 | date.setDate(date.getDate() + 6); 80 | self.createHeadCell(1,this,ctxHead,start.format("MMM d") + " - " + date.format("MMM d 'yy")+" (" + GanttMaster.messages["GANTT_WEEK_SHORT"]+date.format("w")+")", 7,"",start,date); 81 | date.setDate(date.getDate() + 1); 82 | }, 83 | row2: function (date, ctxHead, ctxBody) { 84 | var start = new Date(date.getTime()); 85 | date.setDate(date.getDate() + 1); 86 | var holyClass = isHoliday(start) ? "holy" : ""; 87 | self.createHeadCell(2,this,ctxHead,start.format("EEEE").substr(0, 1)+" ("+start.format("dd")+")", 1, "headSmall "+holyClass, start,date); 88 | self.createBodyCell(this,ctxBody,1, start.getDay() % 7 == (self.master.firstDayOfWeek + 6) % 7, holyClass); 89 | } 90 | }); 91 | 92 | 93 | //----------------------------- 2 WEEKS 600px ----------------------------- 94 | _addZoom( "2w",{ 95 | adjustDates: function (start, end) { 96 | start.setFirstDayOfThisWeek(); 97 | start.setDate(start.getDate() - 7); 98 | end.setFirstDayOfThisWeek(); 99 | end.setDate(end.getDate() + 20); 100 | }, 101 | row1: function (date, tr1) { 102 | var start = new Date(date.getTime()); 103 | date.setDate(date.getDate() + 6); 104 | self.createHeadCell(1,this,tr1,start.format("MMM d") + " - " + date.format("MMM d 'yy")+" (" + GanttMaster.messages["GANTT_WEEK_SHORT"]+date.format("w")+")", 7,"",start,date); 105 | date.setDate(date.getDate() + 1); 106 | }, 107 | row2: function (date, tr2, trBody) { 108 | var start = new Date(date.getTime()); 109 | date.setDate(date.getDate() + 1); 110 | var holyClass = isHoliday(start) ? "holy" : ""; 111 | self.createHeadCell(2,this,tr2,start.format("EEEE").substr(0, 1), 1, "headSmall "+holyClass, start,date); 112 | self.createBodyCell(this,trBody,1, start.getDay() % 7 == (self.master.firstDayOfWeek + 6) % 7, holyClass); 113 | } 114 | }); 115 | 116 | 117 | //----------------------------- 1 MONTH 600px ----------------------------- 118 | _addZoom( "1M",{ 119 | adjustDates: function (start, end) { 120 | start.setMonth(start.getMonth()-1); 121 | start.setDate(15); 122 | end.setDate(1); 123 | end.setMonth(end.getMonth() + 1); 124 | end.setDate(end.getDate() + 14); 125 | }, 126 | row1: function (date, tr1) { 127 | var start = new Date(date.getTime()); 128 | date.setDate(1); 129 | date.setMonth(date.getMonth() + 1); 130 | date.setDate(date.getDate() - 1); 131 | var inc=date.getDate()-start.getDate()+1; 132 | date.setDate(date.getDate() + 1); 133 | self.createHeadCell(1,this,tr1,start.format("MMMM yyyy"), inc,"",start,date); //spans mumber of dayn in the month 134 | }, 135 | row2: function (date, tr2, trBody) { 136 | var start = new Date(date.getTime()); 137 | date.setDate(date.getDate() + 1); 138 | var holyClass = isHoliday(start) ? "holy" : ""; 139 | self.createHeadCell(2,this,tr2,start.format("d"), 1, "headSmall "+holyClass, start,date); 140 | var nd = new Date(start.getTime()); 141 | nd.setDate(start.getDate() + 1); 142 | self.createBodyCell(this,trBody,1, nd.getDate() == 1, holyClass); 143 | } 144 | }); 145 | 146 | 147 | 148 | //----------------------------- 1 QUARTERS ----------------------------- 149 | _addZoom( "1Q", { 150 | adjustDates: function (start, end) { 151 | start.setDate(1); 152 | start.setMonth(Math.floor(start.getMonth() / 3) * 3 -1 ); 153 | end.setDate(1); 154 | end.setMonth(Math.floor(end.getMonth() / 3) * 3 + 4); 155 | end.setDate(end.getDate() - 1); 156 | }, 157 | row1: function (date, tr1) { 158 | var start = new Date(date.getTime()); 159 | date.setMonth(Math.floor(date.getMonth() / 3) * 3 + 3); 160 | var inc=(date.getMonth()-start.getMonth()); 161 | inc=inc>0?inc:1; 162 | var q = (Math.floor(start.getMonth() / 3) + 1); 163 | self.createHeadCell(1,this,tr1,GanttMaster.messages["GANTT_QUARTER"]+" "+q+" "+start.format("yyyy"), inc,"",start,date); 164 | }, 165 | row2: function (date, tr2, trBody) { 166 | var start = new Date(date.getTime()); 167 | date.setMonth(date.getMonth() + 1); 168 | self.createHeadCell(2,this,tr2,start.format("MMMM"), 1, "headSmall", start,date); 169 | self.createBodyCell(this,trBody,1, start.getMonth() % 3 == 2); 170 | } 171 | }); 172 | 173 | 174 | //----------------------------- 2 QUARTERS ----------------------------- 175 | _addZoom( "2Q", { 176 | adjustDates: function (start, end) { 177 | start.setDate(1); 178 | start.setMonth(Math.floor(start.getMonth() / 3) * 3 -3); 179 | end.setDate(1); 180 | end.setMonth(Math.floor(end.getMonth() / 3) * 3 + 6); 181 | end.setDate(end.getDate() - 1); 182 | }, 183 | row1: function (date, tr1) { 184 | var start = new Date(date.getTime()); 185 | date.setMonth(date.getMonth() + 3); 186 | var q = (Math.floor(start.getMonth() / 3) + 1); 187 | self.createHeadCell(1,this,tr1,GanttMaster.messages["GANTT_QUARTER"]+" "+q+" "+start.format("yyyy"), 3,"",start,date); 188 | }, 189 | row2: function (date, tr2, trBody) { 190 | var start = new Date(date.getTime()); 191 | date.setMonth(date.getMonth() + 1); 192 | var lbl = start.format("MMMM"); 193 | self.createHeadCell(2,this,tr2,lbl, 1, "headSmall", start,date); 194 | self.createBodyCell(this,trBody,1, start.getMonth() % 3 == 2); 195 | } 196 | }); 197 | 198 | 199 | //----------------------------- 1 YEAR ----------------------------- 200 | _addZoom( "1y", { 201 | adjustDates: function (start, end) { 202 | start.setDate(1); 203 | start.setMonth(Math.floor(start.getMonth() / 6) * 6 -6); 204 | end.setDate(1); 205 | end.setMonth(Math.floor(end.getMonth() / 6) * 6 + 12); 206 | end.setDate(end.getDate() - 1); 207 | }, 208 | row1: function (date, tr1) { 209 | var start = new Date(date.getTime()); 210 | date.setMonth(date.getMonth() + 6); 211 | var sem = (Math.floor(start.getMonth() / 6) + 1); 212 | self.createHeadCell(1,this,tr1,GanttMaster.messages["GANTT_SEMESTER"]+" "+sem+"-"+start.format("yyyy") , 6,"",start,date); 213 | }, 214 | row2: function (date, tr2, trBody) { 215 | var start = new Date(date.getTime()); 216 | date.setMonth(date.getMonth() + 1); 217 | self.createHeadCell(2,this,tr2,start.format("MMM"), 1, "headSmall", start,date); 218 | self.createBodyCell(this,trBody,1, (start.getMonth() + 1) % 6 == 0); 219 | } 220 | }); 221 | 222 | 223 | //----------------------------- 2 YEAR ----------------------------- 224 | _addZoom( "2y", { 225 | adjustDates: function (start, end) { 226 | start.setDate(1); 227 | start.setMonth(-6); 228 | end.setDate(30); 229 | end.setMonth(17); 230 | }, 231 | row1: function (date, tr1) { 232 | var start = new Date(date.getTime()); 233 | var inc=12-start.getMonth(); 234 | date.setMonth(date.getMonth() + inc); 235 | self.createHeadCell(1,this,tr1,start.format("yyyy"), inc/6,"",start,date); 236 | }, 237 | row2: function (date, tr2, trBody) { 238 | var start = new Date(date.getTime()); 239 | date.setMonth(date.getMonth() + 6); 240 | var sem = (Math.floor(start.getMonth() / 6) + 1); 241 | self.createHeadCell(2,this,tr2,GanttMaster.messages["GANTT_SEMESTER"] +" "+ sem, 1, "headSmall", start,date); 242 | self.createBodyCell(this,trBody,1, sem == 2); 243 | } 244 | }); 245 | 246 | 247 | 248 | }; 249 | 250 | -------------------------------------------------------------------------------- /libs/dialogs.js: -------------------------------------------------------------------------------- 1 | /* 2 | Copyright (c) 2012-2017 Open Lab 3 | Permission is hereby granted, free of charge, to any person obtaining 4 | a copy of this software and associated documentation files (the 5 | "Software"), to deal in the Software without restriction, including 6 | without limitation the rights to use, copy, modify, merge, publish, 7 | distribute, sublicense, and/or sell copies of the Software, and to 8 | permit persons to whom the Software is furnished to do so, subject to 9 | the following conditions: 10 | 11 | The above copyright notice and this permission notice shall be 12 | included in all copies or substantial portions of the Software. 13 | 14 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 15 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 16 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 17 | NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 18 | LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 19 | OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 20 | WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 21 | */ 22 | 23 | function centerPopup(url, target, w, h, scroll, resiz) { 24 | var winl = (screen.width - w) / 2; 25 | var wint = (screen.height - h) / 2; 26 | var winprops = 'height=' + h + ',width=' + w + ',top=' + wint + ',left=' + winl + ',scrollbars=' + scroll + ',resizable=' + resiz + ', toolbars=false, status=false, menubar=false'; 27 | var win = window.open(url, target, winprops); 28 | if (!win) 29 | alert("A popup blocker was detected: please allow them for this application (check out the upper part of the browser window)."); 30 | if (parseInt(navigator.appVersion) >= 4) { 31 | win.window.focus(); 32 | } 33 | } 34 | 35 | function openCenteredWindow(url, target, winprops) { 36 | var prop_array = winprops.split(","); 37 | var i = 0; 38 | var w = 800; 39 | var h = 600; 40 | if (winprops && winprops != '') { 41 | while (i < prop_array.length) { 42 | if (prop_array[i].indexOf('width') > -1) { 43 | s = prop_array[i].substring(prop_array[i].indexOf('=') + 1); 44 | w = parseInt(s); 45 | } else if (prop_array[i].indexOf('height') > -1) { 46 | s = prop_array[i].substring(prop_array[i].indexOf('=') + 1); 47 | h = parseInt(s); 48 | } 49 | i += 1; 50 | } 51 | var winl = (screen.width - w) / 2; 52 | var wint = (screen.height - h) / 2; 53 | winprops = winprops + ",top=" + wint + ",left=" + winl; 54 | } 55 | win = window.open(url, target, winprops); 56 | if (!win) 57 | alert("A popup blocker was detected: please allow them for this application (check out the upper part of the browser window)."); 58 | if (parseInt(navigator.appVersion) >= 4) { 59 | win.window.focus(); 60 | } 61 | } 62 | 63 | function showFeedbackMessage(typeOrObject, message, title, autoCloseTime) { 64 | 65 | if(!autoCloseTime) 66 | autoCloseTime = 0; 67 | 68 | //console.debug("showFeedbackMessage",typeOrObject, message, title); 69 | var place = $("#__FEEDBACKMESSAGEPLACE"); 70 | var mess; 71 | if (typeof(typeOrObject)=="object" ) 72 | mess=typeOrObject; 73 | else 74 | mess = {type:typeOrObject, message:message,title:title}; 75 | //if exists append error message 76 | var etm = $(".FFC_"+mess.type+":visible ._errorTemplateMessage"); 77 | if(etm.length>0){ 78 | etm.append("
"+(mess.title?""+mess.title+"
":"")+mess.message+"
"); 79 | }else{ 80 | etm = $.JST.createFromTemplate(mess, "errorTemplate"); 81 | place.append(etm); 82 | place.fadeIn(); 83 | } 84 | 85 | if(autoCloseTime >0) 86 | setTimeout(function(){ 87 | etm.fadeOut(); 88 | },autoCloseTime); 89 | 90 | $(".FFC_OK").stopTime("ffchide").oneTime(1500, "ffchide",function () {$(this).fadeOut(400,function(){$(this)})}); 91 | $(".FFC_WARNING").stopTime("ffchide").oneTime(75000, "ffchide",function () {$(this).fadeOut(400,function(){$(this)})}); 92 | $(".FFC_ERROR").stopTime("ffchide").oneTime(10000, "ffchide",function () {$(this).fadeOut(400,function(){$(this)})}); 93 | } 94 | 95 | function showFeedbackMessageInDiv(type, message, divId) { 96 | var place = $("#" + divId); 97 | var mess = {type:type, message:message}; 98 | place.prepend($.JST.createFromTemplate(mess, "errorTemplate")); 99 | place.fadeIn(); 100 | $("body").oneTime(1200, function () { 101 | $(".FFC_OK").fadeOut(); 102 | }); 103 | } 104 | function hideFeedbackMessages() { 105 | $("#__FEEDBACKMESSAGEPLACE").empty(); 106 | } 107 | 108 | 109 | function submitInBlack(formId, actionHref, w, h) { 110 | 111 | if (!w) 112 | w = $(window).width() - 100; 113 | if (!h) 114 | h = $(window).height() - 50; 115 | 116 | openBlackPopup('', w + "px", h + "px", null, formId + "_ifr"); 117 | var form = $("#" + formId); 118 | var oldAction = form.prop("action"); 119 | var oldTarget = form.prop("target"); 120 | form.prop("action", actionHref); 121 | form.prop("target", formId + "_ifr"); 122 | $(window).data("openerForm", form); 123 | form.submit(); 124 | form.prop("action", oldAction); 125 | if (oldTarget) 126 | form.prop("target", oldTarget); 127 | else 128 | form.removeAttr("target"); 129 | } 130 | 131 | 132 | var __popups = []; 133 | function createModalPopup(width, height, onCloseCallBack, cssClass, element, popupOpener) { 134 | //console.debug("createModalPopup"); 135 | 136 | 137 | if (typeof(disableUploadize)=="function") 138 | disableUploadize(); 139 | 140 | // se non diversamenete specificato l'openere è la window corrente; 141 | popupOpener = popupOpener || window; 142 | 143 | if (!width) 144 | width = "80%"; 145 | 146 | if (!height) 147 | height = "80%"; 148 | 149 | var localWidth=width,localHeight=height; 150 | 151 | if (typeof (width)=="string" && width.indexOf("%")>0 ) { 152 | localWidth = function () {return ($(window).width() * parseFloat(width)) / 100}; 153 | } 154 | 155 | if (typeof (height)=="string" && height.indexOf("%")>0) 156 | localHeight = function(){return ($(window).height() * parseFloat(height)) / 100}; 157 | 158 | var popupWidth = localWidth, popupHeight = localHeight; 159 | 160 | if(typeof localWidth == "function") 161 | popupWidth = localWidth(); 162 | 163 | if(typeof localHeight == "function") 164 | popupHeight = localHeight(); 165 | 166 | popupWidth = parseFloat(popupWidth); 167 | popupHeight = parseFloat(popupHeight); 168 | 169 | if (typeof onCloseCallBack == "string") 170 | cssClass = onCloseCallBack; 171 | 172 | //$("#__popup__").remove(); 173 | 174 | var popupN = __popups.length+1; 175 | __popups.push("__popup__" + popupN); 176 | 177 | var isInIframe = isIframe(); 178 | 179 | var bg = $("
").prop("id", "__popup__" + popupN); 180 | bg.addClass("modalPopup" + (isInIframe ? " inIframe" : "")).hide(); 181 | 182 | if (cssClass) 183 | bg.addClass(cssClass); 184 | 185 | function getMarginTop(){ 186 | var mt = ($(window).height() - popupHeight)/2 - 100; 187 | return mt < 0 ? 10 : mt; 188 | } 189 | 190 | var internalDiv=$("
").addClass("bwinPopupd").css({ width:popupWidth, minHeight:popupHeight, marginTop: getMarginTop(), maxHeight:$(window).height()-20, overflow: "auto" }); 191 | 192 | $(window).off("resize.popup"+popupN).on("resize.popup"+popupN, function(){ 193 | 194 | if(typeof localWidth == "function") 195 | popupWidth = localWidth(); 196 | 197 | if(typeof localHeight == "function") 198 | popupHeight = localHeight(); 199 | 200 | internalDiv.css({ width:popupWidth, minHeight:popupHeight }); 201 | 202 | var w = internalDiv.outerWidth() > $(window).width()-20 ? $(window).width()-20 : popupWidth; 203 | var h = internalDiv.outerHeight() > $(window).height()-20 ? $(window).height()-20 : popupHeight; 204 | 205 | internalDiv.css({ marginTop: getMarginTop(), minHeight: h, maxHeight:$(window).height()-20,minWidth: w }); 206 | 207 | }); 208 | 209 | bg.append(internalDiv); 210 | 211 | var showBG = function(el, time, callback){ 212 | 213 | if (isInIframe) { 214 | internalDiv.css({marginTop: -50 }); 215 | el.show(); 216 | internalDiv.animate({marginTop: 0}, (time/2), callback); 217 | } else { 218 | internalDiv.css({opacity: 0, top: -50}).show(); 219 | el.fadeIn(time, function () { 220 | internalDiv.animate({top: 0, opacity: 1}, time/3, callback); 221 | }); 222 | } 223 | 224 | /* 225 | if(isInIframe) { 226 | internalDiv.css({marginTop: -1000 }); 227 | el.show(); 228 | internalDiv.animate({marginTop: 0}, (time * 2), callback); 229 | }else{ 230 | internalDiv.css({opacity:0, top: -500}).show(); 231 | el.fadeIn(time, function(){ 232 | internalDiv.animate({top: 0, opacity:1}, time, callback); 233 | }); 234 | } 235 | */ 236 | 237 | return this; 238 | }; 239 | 240 | if(!element) 241 | $("#twMainContainer").addClass("blur"); 242 | 243 | showBG(bg, 300, function(){}) 244 | bg.on("click",function(event){ 245 | if ($(event.target).closest(".bwinPopupd").length <= 0) 246 | bg.trigger("close"); 247 | }); 248 | 249 | var close = $("x"); 250 | internalDiv.append(close); 251 | 252 | close.click(function () { 253 | bg.trigger("close"); 254 | }); 255 | 256 | $("body").css({overflowY:"hidden"}); 257 | 258 | if(!element){ 259 | $("body").append(bg); 260 | }else{ 261 | element.after(bg); 262 | } 263 | 264 | //close call callback 265 | bg.on("close", function () { 266 | var callBackdata = $(this).data("callBackdata"); 267 | var ndo=bg; 268 | 269 | if (typeof (enableUploadize)=="function") 270 | enableUploadize(); 271 | 272 | //console.debug("ndo",ndo); 273 | 274 | var alertMsg; 275 | var ifr=bg.find("iframe"); 276 | 277 | if (ifr.length>0){ 278 | try { 279 | alertMsg = ifr.get(0).contentWindow.alertOnUnload(); 280 | }catch (e){} 281 | } else { 282 | alertMsg=alertOnUnload(ndo); 283 | } 284 | 285 | if (alertMsg){ 286 | if (!confirm(alertMsg)) 287 | return; 288 | } 289 | 290 | bg.fadeOut(100, function () { 291 | 292 | $(window).off("resize.popup"+popupN); 293 | bg.remove(); 294 | __popups.pop(); 295 | 296 | if (__popups.length == 0) 297 | $("#twMainContainer").removeClass("blur"); 298 | 299 | if (typeof(onCloseCallBack) == "function") 300 | onCloseCallBack(callBackdata); 301 | 302 | $("body").css({overflowY: "auto"}); 303 | }); 304 | 305 | }); 306 | 307 | //destroy do not call callback 308 | bg.on("destroy", function () { 309 | bg.remove(); 310 | $("body").css({overflowY: "auto"}); 311 | }); 312 | 313 | //rise resize event in order to show buttons 314 | $("body").oneTime(1000,"br",function(){$(this).resize();}); // con meno di 1000 non funziona 315 | 316 | 317 | //si deposita l'popupOpener sul bg. Per riprenderlo si usa getBlackPopupOpener() 318 | bg.data("__opener",popupOpener); 319 | 320 | return internalDiv; 321 | } 322 | 323 | function changeModalSize(w,h){ 324 | var newDim = {}; 325 | if(w) 326 | newDim.width = w; 327 | if(h) 328 | newDim.minHeight = h; 329 | 330 | var isInIframe = isIframe(); 331 | var popUp = isInIframe ? window.parent.$(".bwinPopupd") : $(".bwinPopupd"); 332 | 333 | if(popUp.length) 334 | popUp.delay(300).animate(newDim, 200); 335 | } 336 | 337 | function openBlackPopup(url, width, height, onCloseCallBack, iframeId, cssClass) { 338 | 339 | if (!iframeId) 340 | iframeId = "bwinPopupIframe"; 341 | 342 | //add black only if not already in blackpupup 343 | var color= cssClass ? cssClass + " iframe" : "iframe"; 344 | 345 | var ndo = top.createModalPopup(width, height, onCloseCallBack, color,null,window); 346 | 347 | //ndo.closest(".modalPopup ").data("__opener",window); // si deposita il vero opener 348 | 349 | var isInIframe = isIframe(); 350 | 351 | ndo.append("
"); 352 | ndo.find("iframe:first").prop("src", url).css({width:"100%", height:"100%", backgroundColor: isInIframe ? '#F9F9F9' : '#FFFFFF'}); 353 | } 354 | 355 | function getBlackPopup() { 356 | var ret=$([]); 357 | if (__popups.length>0) { 358 | var id = __popups[__popups.length - 1]; 359 | ret = $("#" + id); 360 | } 361 | if (ret.length==0 && window!=top) { 362 | ret = window.parent.getBlackPopup(); 363 | } 364 | return ret; 365 | } 366 | 367 | 368 | function getBlackPopupOpener(){ 369 | return getBlackPopup().data("__opener") 370 | } 371 | 372 | function closeBlackPopup(callBackdata) { 373 | //console.debug("closeBlackPopup ",callBackdata); 374 | var bp = getBlackPopup(); 375 | 376 | if (callBackdata) 377 | bp.data("callBackdata",callBackdata); 378 | bp.trigger("close"); 379 | } 380 | 381 | function openPopUp(el,width,height){ 382 | var popup=createModalPopup(width,height); 383 | popup.append(el.clone().show()); 384 | } 385 | 386 | //returns a jquery object where to write content 387 | 388 | function isIframe() { 389 | var isIframe = false; 390 | try{ 391 | //try to access the document object 392 | if (self.location.href != top.location.href) 393 | isIframe = true; 394 | }catch(e) { 395 | //We don't have access, it's cross-origin! 396 | isIframe = true; 397 | } 398 | return isIframe; 399 | }; 400 | 401 | 402 | function openBulkAction(bulkDivId){ 403 | var popup=createModalPopup(500,300); 404 | popup.append($("#"+bulkDivId).clone().show()); 405 | } 406 | 407 | 408 | function refreshBulk(el) { 409 | //console.debug("refreshBulk") 410 | 411 | if (el.is(":checked")) 412 | el.closest("tr").addClass("selected"); 413 | else 414 | el.closest("tr").removeClass("selected"); 415 | 416 | var table=el.closest(".dataTable"); 417 | if (table.find(".selected :checked").length > 0) { 418 | 419 | $("#bulkOp #bulkRowSel").html(table.find("tbody > tr.selected").length + "/" + table.children("tbody").children("tr").length); 420 | 421 | var bukOpt = $("#bulkOp").clone().addClass("bulkOpClone"); 422 | bukOpt.fadeIn(200, function(){ 423 | $("#bulkPlace").html(bukOpt); 424 | $.tableHF.refreshTfoot(); 425 | }); 426 | 427 | } else { 428 | $(".bulkOpClone").fadeOut(200, function(){ 429 | $.tableHF.refreshTfoot(); 430 | }); 431 | } 432 | } 433 | 434 | function selUnselAll(el){ 435 | //var bulkCheckbox = $("#multi td [type='checkbox']"); 436 | var bulkCheckbox = el.closest(".dataTable").find("[type='checkbox']"); 437 | if (el.is(":checked")){ 438 | bulkCheckbox.prop("checked", true); 439 | bulkCheckbox.closest("tr").addClass("selected"); 440 | } else { 441 | bulkCheckbox.prop("checked", false); 442 | bulkCheckbox.closest("tr").removeClass("selected"); 443 | } 444 | 445 | refreshBulk(el); 446 | } 447 | -------------------------------------------------------------------------------- /libs/forms.js: -------------------------------------------------------------------------------- 1 | /* 2 | Copyright (c) 2012-2017 Open Lab 3 | Permission is hereby granted, free of charge, to any person obtaining 4 | a copy of this software and associated documentation files (the 5 | "Software"), to deal in the Software without restriction, including 6 | without limitation the rights to use, copy, modify, merge, publish, 7 | distribute, sublicense, and/or sell copies of the Software, and to 8 | permit persons to whom the Software is furnished to do so, subject to 9 | the following conditions: 10 | 11 | The above copyright notice and this permission notice shall be 12 | included in all copies or substantial portions of the Software. 13 | 14 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 15 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 16 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 17 | NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 18 | LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 19 | OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 20 | WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 21 | */ 22 | 23 | var muteAlertOnChange = false; 24 | 25 | 26 | // isRequired ---------------------------------------------------------------------------- 27 | 28 | //return true if every mandatory field is filled and highlight empty ones 29 | jQuery.fn.isFullfilled = function () { 30 | var canSubmit = true; 31 | var firstErrorElement = ""; 32 | 33 | this.each(function () { 34 | var theElement = $(this); 35 | theElement.removeClass("formElementsError"); 36 | //if (theElement.val().trim().length == 0 || theElement.attr("invalid") == "true") { //robicch 13/2/15 37 | if (theElement.is("[required]") && theElement.val().trim().length == 0 || theElement.attr("invalid") == "true") { 38 | if (theElement.attr("type") == "hidden") { 39 | theElement = theElement.prevAll("#" + theElement.prop("id") + "_txt:first"); 40 | } else if (theElement.is("[withTinyMCE]")){ 41 | if (tinymce.activeEditor.getContent()=="") 42 | theElement=$("#"+theElement.attr("name")+"_tbl"); 43 | else 44 | return true;// in order to continue the loop 45 | } 46 | theElement.addClass("formElementsError"); 47 | canSubmit = false; 48 | 49 | if (firstErrorElement == "") 50 | firstErrorElement = theElement; 51 | } 52 | }); 53 | 54 | if (!canSubmit) { 55 | // get the tabdiv 56 | var theTabDiv = firstErrorElement.closest(".tabBox"); 57 | if (theTabDiv.length > 0) 58 | clickTab(theTabDiv.attr("tabId")); 59 | 60 | // highlight element 61 | firstErrorElement.effect("highlight", { color:"red" }, 1500); 62 | } 63 | return canSubmit; 64 | 65 | }; 66 | 67 | function canSubmitForm(formOrId) { 68 | //console.debug("canSubmitForm",formOrId); 69 | if (typeof formOrId != "object") 70 | formOrId=$("#" + formOrId); 71 | return formOrId.find(":input[required],:input[invalid=true]").isFullfilled(); 72 | } 73 | 74 | function showSavingMessage() { 75 | $("#savingMessage:hidden").fadeIn(); 76 | $("body").addClass("waiting"); 77 | $(window).resize(); 78 | } 79 | function hideSavingMessage() { 80 | $("#savingMessage:visible").fadeOut(); 81 | $("body").removeClass("waiting"); 82 | $(window).resize(); 83 | } 84 | 85 | 86 | 87 | /* Types Function */ 88 | 89 | function isValidURL(url) { 90 | var RegExp = /^(([\w]+:)?\/\/)?(([\d\w]|%[a-fA-f\d]{2,2})+(:([\d\w]|%[a-fA-f\d]{2,2})+)?@)?([\d\w][-\d\w]{0,253}[\d\w]\.)+[\w]{2,4}(:[\d]+)?(\/([-+_~.\d\w]|%[a-fA-f\d]{2,2})*)*(\?(&?([-+_~.\d\w]|%[a-fA-f\d]{2,2})=?)*)?(#([-+_~.\d\w]|%[a-fA-f\d]{2,2})*)?$/; 91 | return RegExp.test(url); 92 | } 93 | 94 | function isValidEmail(email) { 95 | //var RegExp = /^((([a-z]|[0-9]|!|#|$|%|&|'|\*|\+|\-|\/|=|\?|\^|_|`|\{|\||\}|~)+(\.([a-z]|[0-9]|!|#|$|%|&|'|\*|\+|\-|\/|=|\?|\^|_|`|\{|\||\}|~)+)*)@((((([a-z]|[0-9])([a-z]|[0-9]|\-){0,61}([a-z]|[0-9])\.))*([a-z]|[0-9])([a-z]|[0-9]|\-){0,61}([a-z]|[0-9])\.)[\w]{2,4}|(((([0-9]){1,3}\.){3}([0-9]){1,3}))|(\[((([0-9]){1,3}\.){3}([0-9]){1,3})\])))$/; 96 | var RegExp = /^.+@\S+\.\S+$/; 97 | return RegExp.test(email); 98 | } 99 | 100 | function isValidInteger(n) { 101 | reg = new RegExp("^[-+]{0,1}[0-9]*$"); 102 | return reg.test(n) || isNumericExpression(n); 103 | } 104 | 105 | function isValidDouble(n) { 106 | var sep = Number.decimalSeparator; 107 | reg = new RegExp("^[-+]{0,1}[0-9]*[" + sep + "]{0,1}[0-9]*$"); 108 | return reg.test(n) || isNumericExpression(n); 109 | } 110 | 111 | function isValidTime(n) { 112 | return !isNaN(millisFromHourMinute(n)); 113 | } 114 | 115 | function isValidDurationDays(n) { 116 | return !isNaN(daysFromString(n)); 117 | } 118 | 119 | function isValidDurationMillis(n) { 120 | return !isNaN(millisFromString(n)); 121 | } 122 | 123 | function isNumericExpression(expr) { 124 | try { 125 | var a = eval(expr); 126 | return typeof(a) == 'number'; 127 | } catch (t) { 128 | return false; 129 | } 130 | 131 | } 132 | 133 | function getNumericExpression(expr) { 134 | var ret; 135 | try { 136 | var a = eval(expr); 137 | if (typeof(a) == 'number') 138 | ret = a; 139 | } catch (t) { 140 | } 141 | return ret; 142 | 143 | } 144 | 145 | /* 146 | supports almost all Java currency format e.g.: ###,##0.00EUR €#,###.00 #,###.00€ -$#,###.00 $-#,###.00 147 | */ 148 | function isValidCurrency(numStr) { 149 | //first try to convert format in a regex 150 | var regex = ""; 151 | var format = Number.currencyFormat + ""; 152 | 153 | var minusFound = false; 154 | var numFound = false; 155 | var currencyString = ""; 156 | var numberRegex = "[0-9\\" + Number.groupingSeparator + "]+[\\" + Number.decimalSeparator + "]?[0-9]*"; 157 | 158 | for (var i = 0; i < format.length; i++) { 159 | var ch = format.charAt(i); 160 | 161 | if (ch == "." || ch == "," || ch == "0") { 162 | //skip it 163 | if (currencyString != "") { 164 | regex = regex + "(?:" + RegExp.quote(currencyString) + ")?"; 165 | currencyString = ""; 166 | } 167 | 168 | } else if (ch == "#") { 169 | if (currencyString != "") { 170 | regex = regex + "(?:" + RegExp.quote(currencyString) + ")?"; 171 | currencyString = ""; 172 | } 173 | 174 | if (!numFound) { 175 | numFound = true; 176 | regex = regex + numberRegex; 177 | } 178 | 179 | } else if (ch == "-") { 180 | if (currencyString != "") { 181 | regex = regex + "(?:" + RegExp.quote(currencyString) + ")?"; 182 | currencyString = ""; 183 | } 184 | if (!minusFound) { 185 | minusFound = true; 186 | regex = regex + "[-]?"; 187 | } 188 | 189 | } else { 190 | currencyString = currencyString + ch; 191 | } 192 | } 193 | if (!minusFound) 194 | regex = "[-]?" + regex; 195 | 196 | if (currencyString != "") 197 | regex = regex + "(?:" + RegExp.quote(currencyString) + ")?"; 198 | 199 | regex = "^" + regex + "$"; 200 | 201 | var rg = new RegExp(regex); 202 | return rg.test(numStr) || isNumericExpression(numStr); 203 | } 204 | 205 | function getCurrencyValue(numStr) { 206 | if (!isValidCurrency(numStr)) 207 | return NaN; 208 | 209 | var ripul = numStr.replaceAll(Number.groupingSeparator, "").replaceAll(Number.decimalSeparator, "."); 210 | return getNumericExpression(ripul) || parseFloat(ripul.replace(/[^-0123456789.]/, "")); 211 | } 212 | 213 | 214 | function formatCurrency(numberString) { 215 | return formatNumber(numberString, Number.currencyFormat); 216 | } 217 | 218 | 219 | function formatNumber(numberString, format) { 220 | if (!format) 221 | format = "##0.00"; 222 | 223 | var dec = Number.decimalSeparator; 224 | var group = Number.groupingSeparator; 225 | var neg = Number.minusSign; 226 | 227 | var round = true; 228 | 229 | var validFormat = "0#-,."; 230 | 231 | // strip all the invalid characters at the beginning and the end 232 | // of the format, and we'll stick them back on at the end 233 | // make a special case for the negative sign "-" though, so 234 | // we can have formats like -$23.32 235 | var prefix = ""; 236 | var negativeInFront = false; 237 | for (var i = 0; i < format.length; i++) { 238 | if (validFormat.indexOf(format.charAt(i)) == -1) { 239 | prefix = prefix + format.charAt(i); 240 | } else { 241 | if (i == 0 && format.charAt(i) == '-') { 242 | negativeInFront = true; 243 | } else { 244 | break; 245 | } 246 | } 247 | } 248 | var suffix = ""; 249 | for (var i = format.length - 1; i >= 0; i--) { 250 | if (validFormat.indexOf(format.charAt(i)) == -1) 251 | suffix = format.charAt(i) + suffix; 252 | else 253 | break; 254 | } 255 | 256 | format = format.substring(prefix.length); 257 | format = format.substring(0, format.length - suffix.length); 258 | 259 | // now we need to convert it into a number 260 | //while (numberString.indexOf(group) > -1) 261 | // numberString = numberString.replace(group, ''); 262 | //var number = new Number(numberString.replace(dec, ".").replace(neg, "-")); 263 | var number = new Number(numberString); 264 | 265 | 266 | var forcedToZero = false; 267 | if (isNaN(number)) { 268 | number = 0; 269 | forcedToZero = true; 270 | } 271 | 272 | // special case for percentages 273 | if (suffix == "%") 274 | number = number * 100; 275 | 276 | var returnString = ""; 277 | if (format.indexOf(".") > -1) { 278 | var decimalPortion = dec; 279 | var decimalFormat = format.substring(format.lastIndexOf(".") + 1); 280 | 281 | // round or truncate number as needed 282 | if (round) 283 | number = new Number(number.toFixed(decimalFormat.length)); 284 | else { 285 | var numStr = number.toString(); 286 | numStr = numStr.substring(0, numStr.lastIndexOf('.') + decimalFormat.length + 1); 287 | number = new Number(numStr); 288 | } 289 | 290 | var decimalValue = number % 1; 291 | var decimalString = new String(decimalValue.toFixed(decimalFormat.length)); 292 | decimalString = decimalString.substring(decimalString.lastIndexOf(".") + 1); 293 | 294 | for (var i = 0; i < decimalFormat.length; i++) { 295 | if (decimalFormat.charAt(i) == '#' && decimalString.charAt(i) != '0') { 296 | decimalPortion += decimalString.charAt(i); 297 | } else if (decimalFormat.charAt(i) == '#' && decimalString.charAt(i) == '0') { 298 | var notParsed = decimalString.substring(i); 299 | if (notParsed.match('[1-9]')) { 300 | decimalPortion += decimalString.charAt(i); 301 | } else { 302 | break; 303 | } 304 | } else if (decimalFormat.charAt(i) == "0") { 305 | decimalPortion += decimalString.charAt(i); 306 | } 307 | } 308 | returnString += decimalPortion; 309 | } else { 310 | number = Math.round(number); 311 | } 312 | var ones = Math.floor(number); 313 | if (number < 0) 314 | ones = Math.ceil(number); 315 | 316 | var onesFormat = ""; 317 | if (format.indexOf(".") == -1) 318 | onesFormat = format; 319 | else 320 | onesFormat = format.substring(0, format.indexOf(".")); 321 | 322 | var onePortion = ""; 323 | if (!(ones == 0 && onesFormat.substr(onesFormat.length - 1) == '#') || forcedToZero) { 324 | // find how many digits are in the group 325 | var oneText = new String(Math.abs(ones)); 326 | var groupLength = 9999; 327 | if (onesFormat.lastIndexOf(",") != -1) 328 | groupLength = onesFormat.length - onesFormat.lastIndexOf(",") - 1; 329 | var groupCount = 0; 330 | for (var i = oneText.length - 1; i > -1; i--) { 331 | onePortion = oneText.charAt(i) + onePortion; 332 | groupCount++; 333 | if (groupCount == groupLength && i != 0) { 334 | onePortion = group + onePortion; 335 | groupCount = 0; 336 | } 337 | } 338 | 339 | // account for any pre-data padding 340 | if (onesFormat.length > onePortion.length) { 341 | var padStart = onesFormat.indexOf('0'); 342 | if (padStart != -1) { 343 | var padLen = onesFormat.length - padStart; 344 | 345 | // pad to left with 0's or group char 346 | var pos = onesFormat.length - onePortion.length - 1; 347 | while (onePortion.length < padLen) { 348 | var padChar = onesFormat.charAt(pos); 349 | // replace with real group char if needed 350 | if (padChar == ',') 351 | padChar = group; 352 | onePortion = padChar + onePortion; 353 | pos--; 354 | } 355 | } 356 | } 357 | } 358 | 359 | if (!onePortion && onesFormat.indexOf('0', onesFormat.length - 1) !== -1) 360 | onePortion = '0'; 361 | 362 | returnString = onePortion + returnString; 363 | 364 | // handle special case where negative is in front of the invalid characters 365 | if (number < 0 && negativeInFront && prefix.length > 0) 366 | prefix = neg + prefix; 367 | else if (number < 0) 368 | returnString = neg + returnString; 369 | 370 | if (returnString.lastIndexOf(dec) == returnString.length - 1) { 371 | returnString = returnString.substring(0, returnString.length - 1); 372 | } 373 | returnString = prefix + returnString + suffix; 374 | return returnString; 375 | } 376 | 377 | 378 | //validation functions - used by textfield and datefield 379 | jQuery.fn.validateField = function () { 380 | var isValid = true; 381 | 382 | this.each(function () { 383 | var el = $(this); 384 | el.clearErrorAlert(); 385 | 386 | var value = el.val(); 387 | if (value) { 388 | var rett = true; 389 | var type = (el.attr('entryType')+"").toUpperCase(); 390 | var errParam; 391 | 392 | if (type == "INTEGER") { 393 | rett = isValidInteger(value); 394 | } else if (type == "DOUBLE") { 395 | rett = isValidDouble(value); 396 | } else if (type == "PERCENTILE") { 397 | rett = isValidDouble(value); 398 | } else if (type == "URL") { 399 | rett = isValidURL(value); 400 | } else if (type == "EMAIL") { 401 | rett = isValidEmail(value); 402 | } else if (type == "DURATIONMILLIS") { 403 | rett = isValidDurationMillis(value); 404 | } else if (type == "DURATIONDAYS") { 405 | rett = isValidDurationDays(value); 406 | } else if (type == "DATE") { 407 | rett = Date.isValid(value, el.attr("format"), true); 408 | if (!rett) 409 | errParam = el.attr("format"); 410 | } else if (type == "TIME") { 411 | rett = isValidTime(value); 412 | } else if (type == "CURRENCY") { 413 | rett = isValidCurrency(value); 414 | } 415 | 416 | if (!rett) { 417 | el.createErrorAlert(i18n.ERROR_ON_FIELD, i18n.INVALID_DATA + (errParam ? " " + errParam : "")); 418 | isValid=false; 419 | } 420 | 421 | 422 | //check limits minValue : maxValue 423 | if (rett && (el.attr("minValue") || el.attr("maxValue"))){ 424 | var val=value; 425 | var min=el.attr("minValue"); 426 | var max=el.attr("maxValue"); 427 | if (type == "INTEGER") { 428 | val=parseInt(value); 429 | min=parseInt(min); 430 | max=parseInt(max); 431 | } else if (type == "DOUBLE" || type == "PERCENTILE") { 432 | val=parseDouble(value); 433 | min=parseDouble(min); 434 | max=parseDouble(max); 435 | } else if (type == "URL") { 436 | val=value; 437 | } else if (type == "EMAIL") { 438 | val=value; 439 | } else if (type == "DURATIONMILLIS") { 440 | val=millisFromString(value); 441 | min=millisFromString(min); 442 | max=millisFromString(max); 443 | 444 | } else if (type == "DURATIONDAYS") { 445 | val=daysFromString(value); 446 | min=daysFromString(min); 447 | max=daysFromString(max); 448 | } else if (type == "DATE") { 449 | val=Date.parseString(value, el.attr("format"),true).getTime(); 450 | min=Date.parseString(min, el.attr("format"),true).getTime(); 451 | max=Date.parseString(max, el.attr("format"),true).getTime(); 452 | } else if (type == "TIME") { 453 | val = millisFromHourMinute(value); 454 | min = millisFromHourMinute(min); 455 | max = millisFromHourMinute(max); 456 | } else if (type == "CURRENCY") { 457 | val=getCurrencyValue(value); 458 | min=getCurrencyValue(min); 459 | max=getCurrencyValue(max); 460 | } 461 | 462 | if (el.attr("minValue") && valmax){ 471 | el.createErrorAlert(i18n.ERROR_ON_FIELD, i18n.OUT_OF_BOUDARIES + " ("+(el.attr("minValue")?el.attr("minValue"):"--")+" : "+el.attr("maxValue")+")"); 472 | rett=false; 473 | isValid=false; 474 | } 475 | 476 | } 477 | 478 | } 479 | 480 | }); 481 | 482 | return isValid; 483 | }; 484 | 485 | jQuery.fn.clearErrorAlert = function () { 486 | this.each(function () { 487 | var el = $(this); 488 | el.removeAttr("invalid").removeClass("formElementsError"); 489 | $("#" + el.prop("id") + "error").remove(); 490 | }); 491 | return this; 492 | }; 493 | 494 | jQuery.fn.createErrorAlert = function (errorCode, message) { 495 | this.each(function () { 496 | var el = $(this); 497 | el.attr("invalid", "true").addClass("formElementsError"); 498 | if ($("#" + el.prop("id") + "error").length <= 0) { 499 | var errMess = (errorCode ? errorCode : "") + ": " + (message ? message : ""); 500 | var err = " "; 502 | err += "\n"; 503 | err = $(err); 504 | err.prop("title", errMess); 505 | el.after(err); 506 | } 507 | }); 508 | return this; 509 | }; 510 | 511 | 512 | // button submit support BEGIN ------------------ 513 | 514 | function saveFormValues(idForm) { 515 | var formx = obj(idForm); 516 | formx.setAttribute("savedAction", formx.action); 517 | formx.setAttribute("savedTarget", formx.target); 518 | var el = formx.elements; 519 | for (i = 0; i < el.length; i++) { 520 | if (el[i].getAttribute("savedValue") != null) { 521 | el[i].setAttribute("savedValue", el[i].value); 522 | } 523 | } 524 | } 525 | 526 | function restoreFormValues(idForm) { 527 | var formx = obj(idForm); 528 | formx.action = formx.getAttribute("savedAction"); 529 | formx.target = formx.getAttribute("savedTarget"); 530 | var el = formx.elements; 531 | for (i = 0; i < el.length; i++) { 532 | if (el[i].getAttribute("savedValue") != null) { 533 | el[i].value = el[i].getAttribute("savedValue"); 534 | } 535 | } 536 | } 537 | 538 | function changeActionAndSubmit(action,command){ 539 | var f=$("form:first"); 540 | f.prop("action",action); 541 | f.find("[name=CM]").val(command); 542 | f.submit(); 543 | } 544 | 545 | 546 | 547 | // textarea limit size ------------------------------------------------- 548 | function limitSize(ob) { 549 | if (ob.getAttribute("maxlength")) { 550 | var ml =parseInt(ob.getAttribute("maxlength")); 551 | var val = ob.value;//.replace(/\r\n/g,"\n"); 552 | if (val.length > ml) { 553 | ob.value = val.substr(0, ml); 554 | $(ob).createErrorAlert("Error",i18n.ERR_FIELD_MAX_SIZE_EXCEEDED); 555 | } else { 556 | $(ob).clearErrorAlert(); 557 | } 558 | } 559 | return true; 560 | } 561 | 562 | 563 | // verify before unload BEGIN ---------------------------------------------------------------------------- 564 | 565 | function alertOnUnload(container) { 566 | //console.debug("alertOnUnload",container,muteAlertOnChange); 567 | if (!muteAlertOnChange) { 568 | 569 | //first try to call a function eventually defined on the page 570 | if (typeof(managePageUnload) == "function") 571 | managePageUnload(); 572 | 573 | container=container||$("body"); 574 | var inps= $("[alertonchange=true]",container).find("[oldValue=1]"); 575 | for (var j = 0; j < inps.length; j++) { 576 | var anInput = inps.eq(j); 577 | //console.debug(j,anInput,anInput.isValueChanged()) 578 | var oldValue = anInput.getOldValue() + ""; 579 | if (!('true' == '' + anInput.attr('excludeFromAlert'))) { 580 | if (anInput.attr("maleficoTiny")) { 581 | if (tinymce.EditorManager.get(anInput.prop("id")).isDirty()) { 582 | return i18n.FORM_IS_CHANGED + " \"" + anInput.prop("name") + "\""; 583 | } 584 | 585 | } else if (anInput.isValueChanged()) { 586 | var inputLabel = $("label[for='" + anInput.prop("id") + "']").text(); //use label element 587 | inputLabel = inputLabel ? inputLabel : anInput.prop("name"); 588 | return i18n.FORM_IS_CHANGED + " \"" + inputLabel + "\""; 589 | } 590 | } 591 | } 592 | } 593 | return undefined; 594 | } 595 | 596 | function canILeave(){ 597 | var ret = window.onbeforeunload(); 598 | if (typeof(ret)!="undefined" && !confirm(ret+" \n"+i18n.PROCEED)) 599 | return false; 600 | else 601 | return true; 602 | } 603 | 604 | // ---------------------------------- oldvalues management 605 | // update all values selected 606 | jQuery.fn.updateOldValue = function () { 607 | this.each(function () { 608 | var el = $(this); 609 | var val=(el.is(":checkbox,:radio")?el.prop("checked"):el.val())+""; 610 | el.data("_oldvalue", val); 611 | }); 612 | return this; 613 | }; 614 | 615 | // return true if at least one element has changed 616 | jQuery.fn.isValueChanged = function () { 617 | var ret = false; 618 | this.each(function () { 619 | var el = $(this); 620 | var val=(el.is(":checkbox,:radio")?el.prop("checked"):el.val())+""; 621 | if (val != el.data("_oldvalue") + "") { 622 | //console.debug("io sono diverso "+el.prop("id")+ " :"+el.val()+" != "+el.data("_oldvalue")); 623 | ret = true; 624 | return false; 625 | } 626 | }); 627 | return ret; 628 | }; 629 | 630 | jQuery.fn.getOldValue = function () { 631 | return $(this).data("_oldvalue"); 632 | }; 633 | 634 | jQuery.fn.fillJsonWithInputValues = function (jsonObject) { 635 | var inputs = this.find(":input"); 636 | $.each(inputs.serializeArray(),function(){ 637 | if (this.name) { 638 | jsonObject[this.name] = this.value; 639 | } 640 | }); 641 | 642 | inputs.filter(":checkbox[name]").each(function () { 643 | var el = $(this); 644 | jsonObject[el.attr("name")] = el.is(":checked") ? "yes" : "no"; 645 | 646 | }) 647 | 648 | return this; 649 | }; 650 | 651 | 652 | 653 | function enlargeTextArea(immediate) { 654 | //console.debug("enlargeTextArea",immediate); 655 | var el = $(this); 656 | 657 | var delay=immediate===true?1:300; 658 | el.stopTime("taResizeApply"); 659 | el.oneTime(delay,"taResizeApply",function(){ 660 | 661 | var miH = el.is("[minHeight]") ? parseInt(el.attr("minHeight")) : 30; 662 | var maH = el.is("[maxHeight]") ? parseInt(el.attr("maxHeight")) : 400; 663 | var inc = el.is("[lineHeight]") ? parseInt(el.attr("lineHeight")) : 30; 664 | 665 | //si copiano nel css per sicurezza 666 | el.css({maxHeight:maH,minHeight:miH}); 667 | 668 | var domEl = el.get(0); 669 | var pad = el.outerHeight()-el.height(); 670 | //devo allargare 671 | if (domEl.scrollHeight>el.outerHeight() && el.outerHeight()maH-pad?maH-pad:nh; 674 | el.height(nh); 675 | } else if (el.height()>miH){ 676 | //devo stringere 677 | el.height(el.height()-inc); 678 | 679 | while(el.outerHeight()-domEl.scrollHeight > 0 && el.height()>miH){ 680 | el.height(el.height()-inc); 681 | } 682 | var newH=domEl.scrollHeight-pad +inc; 683 | //newH=newH -1 || holidays.indexOf(md) > -1; 146 | } 147 | 148 | 149 | 150 | var i18n = { 151 | YES: "Yes", 152 | NO: "No", 153 | FLD_CONFIRM_DELETE: "confirm the deletion?", 154 | INVALID_DATA: "The data inserted are invalid for the field format.", 155 | ERROR_ON_FIELD: "Error on field", 156 | OUT_OF_BOUDARIES: "Out of field admitted values:", 157 | CLOSE_ALL_CONTAINERS:"close all?", 158 | DO_YOU_CONFIRM: "Do you confirm?", 159 | ERR_FIELD_MAX_SIZE_EXCEEDED: "Field max size exceeded", 160 | WEEK_SHORT: "W.", 161 | 162 | FILE_TYPE_NOT_ALLOWED:"File type not allowed.", 163 | FILE_UPLOAD_COMPLETED:"File upload completed.", 164 | UPLOAD_MAX_SIZE_EXCEEDED:"Max file size exceeded", 165 | ERROR_UPLOADING:"Error uploading", 166 | UPLOAD_ABORTED:"Upload aborted", 167 | DROP_HERE:"Drop files here", 168 | 169 | FORM_IS_CHANGED: "You have some unsaved data on the page!", 170 | 171 | PIN_THIS_MENU: "PIN_THIS_MENU", 172 | UNPIN_THIS_MENU: "UNPIN_THIS_MENU", 173 | OPEN_THIS_MENU: "OPEN_THIS_MENU", 174 | CLOSE_THIS_MENU: "CLOSE_THIS_MENU", 175 | PROCEED: "Proceed?", 176 | 177 | PREV: "Previous", 178 | NEXT: "Next", 179 | HINT_SKIP: "Got it, close this hint.", 180 | 181 | WANT_TO_SAVE_FILTER: "save this filter", 182 | NEW_FILTER_NAME: "name of the new filter", 183 | SAVE: "Save", 184 | DELETE: "Delete", 185 | HINT_SKIP: "Got it, close this hint.", 186 | 187 | COMBO_NO_VALUES: "no values available...?", 188 | 189 | FILTER_UPDATED:"Filter updated.", 190 | FILTER_SAVED:"Filter correctly saved." 191 | 192 | }; 193 | 194 | 195 | -------------------------------------------------------------------------------- /libs/jquery/JST/jquery.JST.js: -------------------------------------------------------------------------------- 1 | $.fn.loadTemplates = function() { 2 | $.JST.loadTemplates($(this)); 3 | return this; 4 | }; 5 | 6 | $.JST = { 7 | _templates: new Object(), 8 | _decorators:new Object(), 9 | 10 | loadTemplates: function(elems) { 11 | elems.each(function() { 12 | $(this).find(".__template__").each(function() { 13 | var tmpl = $(this); 14 | var type = tmpl.attr("type"); 15 | 16 | //template may be inside or not in case of ajax loaded templates 17 | var found=false; 18 | var el=tmpl.get(0).firstChild; 19 | while (el && !found) { 20 | if (el.nodeType == 8) { // 8==comment 21 | var templateBody = el.nodeValue; // this is inside the comment 22 | found=true; 23 | break; 24 | } 25 | el=el.nextSibling; 26 | } 27 | if (!found) 28 | var templateBody = tmpl.html(); // this is the whole template 29 | 30 | if (!templateBody.match(/##\w+##/)) { // is Resig' style? e.g. (#=id#) or (# ...some javascript code 'obj' is the alias for the object #) 31 | var strFunc = 32 | "var p=[],print=function(){p.push.apply(p,arguments);};" + 33 | "with(obj){p.push('" + 34 | templateBody.replace(/[\r\t\n]/g, " ") 35 | .replace(/'(?=[^#]*#\))/g, "\t") 36 | .split("'").join("\\'") 37 | .split("\t").join("'") 38 | .replace(/\(#=(.+?)#\)/g, "',$1,'") 39 | .split("(#").join("');") 40 | .split("#)").join("p.push('") 41 | + "');}return p.join('');"; 42 | 43 | try { 44 | $.JST._templates[type] = new Function("obj", strFunc); 45 | } catch (e) { 46 | console.error("JST error: "+type, e,strFunc); 47 | } 48 | 49 | } else { //plain template e.g. ##id## 50 | try { 51 | $.JST._templates[type] = templateBody; 52 | } catch (e) { 53 | console.error("JST error: "+type, e,templateBody); 54 | } 55 | } 56 | 57 | tmpl.remove(); 58 | 59 | }); 60 | }); 61 | }, 62 | 63 | createFromTemplate: function(jsonData, template, transformToPrintable) { 64 | var templates = $.JST._templates; 65 | 66 | var jsData=new Object(); 67 | if (transformToPrintable){ 68 | for (var prop in jsonData){ 69 | var value = jsonData[prop]; 70 | if (typeof(value) == "string") 71 | value = (value + "").replace(/\n/g, "
"); 72 | jsData[prop]=value; 73 | } 74 | } else { 75 | jsData=jsonData; 76 | } 77 | 78 | function fillStripData(strip, data) { 79 | for (var prop in data) { 80 | var value = data[prop]; 81 | 82 | strip = strip.replace(new RegExp("##" + prop + "##", "gi"), value); 83 | } 84 | // then clean the remaining ##xxx## 85 | strip = strip.replace(new RegExp("##\\w+##", "gi"), ""); 86 | return strip; 87 | } 88 | 89 | var stripString = ""; 90 | if (typeof(template) == "undefined") { 91 | alert("Template is required"); 92 | stripString = "
Template is required
"; 93 | 94 | } else if (typeof(templates[template]) == "function") { // resig template 95 | try { 96 | stripString = templates[template](jsData);// create a jquery object in memory 97 | } catch (e) { 98 | console.error("JST error: "+template,e.message); 99 | stripString = "
ERROR: "+template+"
" + e.message + "
"; 100 | } 101 | 102 | } else { 103 | stripString = templates[template]; // recover strip template 104 | if (!stripString || stripString.trim() == "") { 105 | console.error("No template found for type '" + template + "'"); 106 | return $("
"); 107 | 108 | } else { 109 | stripString = fillStripData(stripString, jsData); //replace placeholders with data 110 | } 111 | } 112 | 113 | var ret = $(stripString);// create a jquery object in memory 114 | ret.attr("__template", template); // set __template attribute 115 | 116 | //decorate the strip 117 | var dec = $.JST._decorators[template]; 118 | if (typeof (dec) == "function") 119 | dec(ret, jsData); 120 | 121 | return ret; 122 | }, 123 | 124 | 125 | existsTemplate: function(template) { 126 | return $.JST._templates[template]; 127 | }, 128 | 129 | //decorate function is like function(domElement,jsonData){...} 130 | loadDecorator:function(template, decorator) { 131 | $.JST._decorators[template] = decorator; 132 | }, 133 | 134 | getDecorator:function(template) { 135 | return $.JST._decorators[template]; 136 | }, 137 | 138 | decorateTemplate:function(element) { 139 | var dec = $.JST._decorators[element.attr("__template")]; 140 | if (typeof (dec) == "function") 141 | dec(editor); 142 | }, 143 | 144 | // asynchronous 145 | ajaxLoadAsynchTemplates: function(templateUrl, callback) { 146 | 147 | $.get(templateUrl, function(data) { 148 | 149 | var div = $("
"); 150 | div.html(data); 151 | 152 | $.JST.loadTemplates(div); 153 | 154 | if (typeof(callback == "function")) 155 | callback(); 156 | },"html"); 157 | }, 158 | 159 | ajaxLoadTemplates: function(templateUrl) { 160 | $.ajax({ 161 | async:false, 162 | url: templateUrl, 163 | dataType: "html", 164 | success: function(data) { 165 | var div = $("
"); 166 | div.html(data); 167 | $.JST.loadTemplates(div); 168 | } 169 | }); 170 | 171 | } 172 | 173 | 174 | }; 175 | -------------------------------------------------------------------------------- /libs/jquery/dateField/img/next.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/libs/jquery/dateField/img/next.png -------------------------------------------------------------------------------- /libs/jquery/dateField/img/prev.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/libs/jquery/dateField/img/prev.png -------------------------------------------------------------------------------- /libs/jquery/dateField/img/today.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/libs/jquery/dateField/img/today.png -------------------------------------------------------------------------------- /libs/jquery/dateField/jquery.dateField.css: -------------------------------------------------------------------------------- 1 | .calBox { 2 | background-color: #999; 3 | text-align: center; 4 | color: white; 5 | width:200px; 6 | position:absolute; 7 | padding-bottom: 10px; 8 | } 9 | 10 | .calElement,.calDayHeader { 11 | padding: 1px; 12 | display: inline-block; 13 | overflow:hidden; 14 | } 15 | 16 | .calDayHeader { 17 | padding: 4px; 18 | display: inline-block; 19 | background-color:#55b6c7 20 | } 21 | 22 | .calNav { 23 | height: 20px; 24 | } 25 | 26 | .calNavBar { 27 | padding: 5px; 28 | background-color: rgba(0, 0, 0, 0.25) 29 | } 30 | 31 | 32 | .calDay .calElement, .calDay .calDayHeader { 33 | border: 1px solid transparent; 34 | } 35 | 36 | .calDay .calElement.holy { 37 | /*background-color: rgba(236, 195, 176, 0.40);*/ 38 | color: #81d7e2; 39 | 40 | } 41 | 42 | .calDay .calDayHeader { 43 | font-size: 8px; 44 | text-transform: uppercase; 45 | } 46 | 47 | .calElement.prev, 48 | .calElement.goToday, 49 | .calElement.next { 50 | width: 16px; 51 | height: 18px; 52 | border: none; 53 | margin-top: 0 54 | } 55 | .calElement.prev { 56 | background: transparent url(img/prev.png) no-repeat 5px center; 57 | float:left; 58 | } 59 | 60 | .calElement.goToday { 61 | background: transparent url(img/today.png) no-repeat 5px center; 62 | float:left; 63 | } 64 | 65 | .calElement.next { 66 | background: transparent url(img/next.png) no-repeat 5px center; 67 | float:right; 68 | } 69 | 70 | .calElement:hover{ 71 | background-color: transparent; 72 | border:none; 73 | cursor: pointer; 74 | opacity: 0.6 75 | } 76 | 77 | .calDay .calElement .dayNumber { 78 | font-size: 20px; 79 | } 80 | 81 | .calDay.calFullMonth .dayNumber { 82 | font-size: 14px; 83 | } 84 | .calDay .calOutOfScope{ 85 | color: #b1b0b0; 86 | } 87 | 88 | .calElement.selected { 89 | border: 1px solid #404040; 90 | } 91 | 92 | .calElement:hover { 93 | background-color: #404040; 94 | border: 1px solid #404040; 95 | cursor: pointer; 96 | } 97 | 98 | 99 | .calElement.today { 100 | border: 1px solid #c84e48; 101 | } 102 | 103 | 104 | .shortCuts { 105 | /*border-top: 1px solid rgba(0, 0, 0, 0.25);*/ 106 | padding: 3px 0 6px; 107 | background-color: rgba(97, 215, 232, 0.50) 108 | } 109 | 110 | .shortCuts span{ 111 | font-size: 11px; 112 | border: 1px dotted #617777; 113 | width: 23px; 114 | display: inline-block; 115 | cursor: pointer 116 | } 117 | 118 | .shortCuts span:hover { 119 | background-color: rgba(0, 0, 0, 0.25) 120 | } 121 | 122 | -------------------------------------------------------------------------------- /libs/jquery/dateField/jquery.dateField.js: -------------------------------------------------------------------------------- 1 | /* 2 | Copyright (c) 2009 Open Lab 3 | Written by Roberto Bicchierai http://roberto.open-lab.com 4 | Permission is hereby granted, free of charge, to any person obtaining 5 | a copy of this software and associated documentation files (the 6 | "Software"), to deal in the Software without restriction, including 7 | without limitation the rights to use, copy, modify, merge, publish, 8 | distribute, sublicense, and/or sell copies of the Software, and to 9 | permit persons to whom the Software is furnished to do so, subject to 10 | the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be 13 | included in all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 16 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 17 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 18 | NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 19 | LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 20 | OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 21 | WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 22 | */ 23 | 24 | jQuery.fn.dateField = function(options) { 25 | //console.debug("dateField",options); 26 | //check if the input field is passed correctly 27 | if (!options.inputField){ 28 | console.error("You must supply an input field"); 29 | return false; 30 | } 31 | 32 | // -------------------------- start default option values -------------------------- 33 | 34 | if (typeof(options.firstDayOfWeek) == "undefined") 35 | options.firstDayOfWeek=Date.firstDayOfWeek; 36 | 37 | if (typeof(options.useWheel) == "undefined") 38 | options.useWheel=true; 39 | 40 | if (typeof(options.dateFormat) == "undefined") 41 | options.dateFormat=Date.defaultFormat; 42 | 43 | if (typeof(options.todayLabel) == "undefined") 44 | options.todayLabel=Date.today; 45 | 46 | /* optional 47 | options.notBeforeMillis //disable buttons if before millis 48 | options.notAfterMillis //disable buttons if after millis 49 | options.width // imposta una larghezza al calendario 50 | options.height 51 | options.showToday // show "today" on the year or month bar 52 | options.centerOnScreen //se true centra invece che usa nearBestPosition 53 | options.useYears:0 // se >0 non disegna prev-next ma n anni prima e n anni dopo quello corrente 54 | options.useMonths:0 // se >0 non disegna prev-next ma n mesi prima e n mesi dopo quello corrente 55 | */ 56 | // -------------------------- end default option values -------------------------- 57 | 58 | 59 | 60 | // ------------------ start 61 | if(options.inputField.is("[readonly]") && !options.inputField.is(".noFocus") || options.inputField.is("[disabled]")) 62 | return; 63 | 64 | var calendar = {currentDate: new Date()}; 65 | calendar.options = options; 66 | 67 | //build the calendar on the first element in the set of matched elements. 68 | var theOpener = this.eq(0); 69 | var theDiv=$("
").addClass("calBox"); 70 | 71 | if(options.width) 72 | theDiv.css("width",options.width); 73 | 74 | if(options.height) 75 | theDiv.css("height",options.height); 76 | 77 | 78 | //create calendar elements elements 79 | var divNavBar = $("
").addClass("calNav"); 80 | var divDays = $("
").addClass("calDay"); 81 | 82 | divDays.addClass("calFullMonth"); 83 | theDiv.append(divNavBar).append(divDays); 84 | 85 | if (options.isSearchField){ 86 | var divShortcuts=$("
").addClass("shortCuts").html("LQ LM M LW W Y TTONW NM Q NQ"); 87 | divShortcuts.click(function(ev){ 88 | var el=$(ev.target); 89 | if(el.is("span")){ 90 | if (!options.isSearchField) 91 | options.inputField.val(Date.parseString(el.text().trim(),options.dateFormat,true).format(options.dateFormat)); 92 | else 93 | options.inputField.val(el.text().trim()); 94 | calendar.closeCalendar() 95 | } 96 | }); 97 | theDiv.append(divShortcuts); 98 | } 99 | 100 | //mobile management 101 | if ($("body").is(".mobile")){ 102 | enableComponentOverlay(options.inputField,theDiv); 103 | } 104 | $("body").append(theDiv); 105 | 106 | 107 | if (options.centerOnScreen){ 108 | theDiv.oneTime(10,"ce",function(){$(this).centerOnScreen()}); 109 | } else { 110 | nearBestPosition(theOpener,theDiv); 111 | } 112 | theDiv.css("z-index",10000); 113 | 114 | 115 | //register for click outside. Delayed to avoid it run immediately 116 | $("body").oneTime(100, "regclibodcal", function() { 117 | $("body").bind("click.dateField", function() { 118 | calendar.closeCalendar(); 119 | }); 120 | }); 121 | 122 | 123 | calendar.drawCalendar = function(date) { 124 | calendar.currentDate = date; 125 | //console.debug("drawCalendar",date); 126 | 127 | 128 | var fillNavBar = function(date) { 129 | //console.debug("fillNavBar",date); 130 | var today = new Date();//today 131 | divNavBar.empty(); 132 | 133 | var showToday = options.showToday; 134 | //use the classic prev next bar 135 | if (!options.useYears && !options.useMonths) { 136 | var t = new Date(date.getTime()); 137 | t.setDate(1); 138 | t.setMonth(t.getMonth() - 1); 139 | var spanPrev = $("").addClass("calElement noCallback prev").attr("millis", t.getTime()); 140 | var spanToday = $("").addClass("calElement noCallback goToday").attr("millis", new Date().getTime()).attr("title", "today"); 141 | t.setMonth(t.getMonth() + 1); 142 | var spanMonth = $("").html(t.format("MMMM yyyy")); 143 | t.setMonth(t.getMonth() + 1); 144 | var spanNext = $("").addClass("calElement noCallback next").attr("millis", t.getTime()); 145 | divNavBar.append(spanPrev, spanToday, spanMonth, spanNext); 146 | 147 | // use the year month bar 148 | } else { 149 | if (options.useYears>0){ 150 | options.useMonths=options.useMonths||1; //if shows years -> shows also months 151 | t = new Date(date.getTime()); 152 | var yB= $("
"); 153 | var w=100/(2*options.useYears+1+(showToday?1:0)); 154 | t.setFullYear(t.getFullYear()-options.useYears); 155 | if(showToday){ 156 | var s = $("").addClass("calElement noCallback goToday").attr("millis", today.getTime()).append(options.todayLabel).css("width",w+"%"); 157 | showToday=false; 158 | yB.append(s); 159 | } 160 | for (var i=-options.useYears;i<=options.useYears;i++){ 161 | var s = $("").addClass("calElement noCallback").attr("millis", t.getTime()).append(t.getFullYear()).css("width",w+"%"); 162 | if (today.getFullYear()== t.getFullYear()) //current year 163 | s.addClass("today"); 164 | if (i==0) //selected year 165 | s.addClass("selected"); 166 | 167 | yB.append(s); 168 | t.setFullYear(t.getFullYear()+1); 169 | } 170 | divNavBar.append(yB); 171 | } 172 | if (options.useMonths>0){ 173 | t = new Date(date.getTime()); 174 | t.setDate(1); 175 | var w=100/(2*options.useMonths+1+(showToday?1:0)); 176 | t.setMonth(t.getMonth()-options.useMonths); 177 | var yB= $("
"); 178 | 179 | if(showToday){ 180 | var s = $("").addClass("calElement noCallback goToday").attr("millis", today.getTime()).append(options.todayLabel).css("width",w+"%"); 181 | yB.append(s); 182 | } 183 | 184 | for (var i=-options.useMonths;i<=options.useMonths;i++){ 185 | var s = $("").addClass("calElement noCallback").attr("millis", t.getTime()).append(t.format("MMM")).css("width",w+"%"); 186 | if (today.getFullYear()== t.getFullYear() && today.getMonth()== t.getMonth()) //current year 187 | s.addClass("today"); 188 | if (i==0) //selected month 189 | s.addClass("selected"); 190 | yB.append(s); 191 | t.setMonth(t.getMonth()+1); 192 | } 193 | divNavBar.append(yB); 194 | } 195 | } 196 | 197 | }; 198 | 199 | var fillDaysFullMonth = function(date) { 200 | divDays.empty(); 201 | var today = new Date();//today 202 | var w = 100/7; 203 | // draw day headers 204 | var d = new Date(date); 205 | d.setFirstDayOfThisWeek(options.firstDayOfWeek); 206 | for (var i = 0; i < 7; i++) { 207 | var span = $("").addClass("calDayHeader").attr("day", d.getDay()); 208 | if (d.isHoliday()) 209 | span.addClass("holy"); 210 | span.css("width",w+"%"); 211 | span.html(Date.dayAbbreviations[d.getDay()]); 212 | 213 | //call the dayHeaderRenderer 214 | if (typeof(options.dayHeaderRenderer) == "function") 215 | options.dayHeaderRenderer(span,d.getDay()); 216 | 217 | divDays.append(span); 218 | d.setDate(d.getDate()+1); 219 | } 220 | 221 | //draw cells 222 | d = new Date(date); 223 | d.setDate(1); // set day to start of month 224 | d.setFirstDayOfThisWeek(options.firstDayOfWeek);//go to first day of week 225 | 226 | var i=0; 227 | 228 | while ((d.getMonth()<=date.getMonth() && d.getFullYear()<=date.getFullYear()) || d.getFullYear()").addClass("calElement day").attr("millis", d.getTime()); 230 | 231 | span.html("" + d.getDate() + "").css("width",w+"%"); 232 | if (d.getYear() == today.getYear() && d.getMonth() == today.getMonth() && d.getDate() == today.getDate()) 233 | span.addClass("today"); 234 | if (d.getYear() == date.getYear() && d.getMonth() == date.getMonth() && d.getDate() == date.getDate()) 235 | span.addClass("selected"); 236 | 237 | if (d.isHoliday()) 238 | span.addClass("holy"); 239 | 240 | if(d.getMonth()!=date.getMonth()) 241 | span.addClass("calOutOfScope"); 242 | 243 | //call the dayRenderer 244 | if (typeof(options.dayRenderer) == "function") 245 | options.dayRenderer(span,d); 246 | 247 | divDays.append(span); 248 | d.setDate(d.getDate()+1); 249 | i++; 250 | } 251 | 252 | }; 253 | 254 | fillNavBar(date); 255 | fillDaysFullMonth(date); 256 | 257 | //disable all buttons out of validity period 258 | if (options.notBeforeMillis ||options.notAfterMillis) { 259 | var notBefore = options.notBeforeMillis ? options.notBeforeMillis : Number.MIN_VALUE; 260 | var notAfter = options.notAfterMillis ? options.notAfterMillis : Number.MAX_VALUE; 261 | divDays.find(".calElement[millis]").each(function(){ 262 | var el=$(this); 263 | var m=parseInt(el.attr("millis")); 264 | if (m>notAfter || m 0) { 283 | var millis = parseInt(el.attr("millis")); 284 | var date = new Date(millis); 285 | 286 | if (el.is(".disabled")) { 287 | ev.stopPropagation(); 288 | return; 289 | } 290 | 291 | if (el.hasClass("day")) { 292 | calendar.closeCalendar(); 293 | if (!el.is(".noCallback")) { 294 | options.inputField.val(date.format(options.dateFormat)).attr("millis", date.getTime()).focus(); 295 | if (typeof(options.callback) == "function") 296 | options.callback.apply(options.inputField,[date]); // in callBack you can use "this" that refers to the input 297 | } 298 | } else { 299 | calendar.drawCalendar(date); 300 | } 301 | } 302 | ev.stopPropagation(); 303 | }); 304 | 305 | 306 | //if mousewheel 307 | if ($.event.special.mousewheel && options.useWheel) { 308 | divDays.mousewheel(function(event, delta) { 309 | var d = new Date(calendar.currentDate.getTime()); 310 | d.setMonth(d.getMonth() + delta); 311 | calendar.drawCalendar(d); 312 | return false; 313 | }); 314 | } 315 | 316 | 317 | // start calendar to the date in the input 318 | var dateStr=options.inputField.val(); 319 | 320 | if (!dateStr || !Date.isValid(dateStr,options.dateFormat,true)){ 321 | calendar.drawCalendar(new Date()); 322 | } else { 323 | var date = Date.parseString(dateStr,options.dateFormat,true); 324 | var newDateStr=date.format(options.dateFormat); 325 | //set date string formatted if not equals 326 | if (!options.isSearchField) { 327 | options.inputField.attr("millis", date.getTime()); 328 | if (dateStr != newDateStr) 329 | options.inputField.val(newDateStr); 330 | } 331 | calendar.drawCalendar(date); 332 | } 333 | 334 | return calendar; 335 | }; 336 | -------------------------------------------------------------------------------- /libs/jquery/jquery.livequery.1.1.1.min.js: -------------------------------------------------------------------------------- 1 | (function($){$.extend($.fn,{livequery:function(type,fn,fn2){var self=this,q;if($.isFunction(type))fn2=fn,fn=type,type=undefined;$.each($.livequery.queries,function(i,query){if(self.selector==query.selector&&self.context==query.context&&type==query.type&&(!fn||fn.$lqguid==query.fn.$lqguid)&&(!fn2||fn2.$lqguid==query.fn2.$lqguid))return(q=query)&&false});q=q||new $.livequery(this.selector,this.context,type,fn,fn2);q.stopped=false;q.run();return this},expire:function(type,fn,fn2){var self=this;if($.isFunction(type))fn2= 2 | fn,fn=type,type=undefined;$.each($.livequery.queries,function(i,query){if(self.selector==query.selector&&self.context==query.context&&(!type||type==query.type)&&(!fn||fn.$lqguid==query.fn.$lqguid)&&(!fn2||fn2.$lqguid==query.fn2.$lqguid)&&!this.stopped)$.livequery.stop(query.id)});return this}});$.livequery=function(selector,context,type,fn,fn2){this.selector=selector;this.context=context;this.type=type;this.fn=fn;this.fn2=fn2;this.elements=[];this.stopped=false;this.id=$.livequery.queries.push(this)- 3 | 1;fn.$lqguid=fn.$lqguid||$.livequery.guid++;if(fn2)fn2.$lqguid=fn2.$lqguid||$.livequery.guid++;return this};$.livequery.prototype={stop:function(){var query=this;if(this.type)this.elements.unbind(this.type,this.fn);else if(this.fn2)this.elements.each(function(i,el){query.fn2.apply(el)});this.elements=[];this.stopped=true},run:function(){if(this.stopped)return;var query=this;var oEls=this.elements,els=$(this.selector,this.context),nEls=els.not(oEls);this.elements=els;if(this.type){nEls.bind(this.type, 4 | this.fn);if(oEls.length>0)$.each(oEls,function(i,el){if($.inArray(el,els)<0)$.event.remove(el,query.type,query.fn)})}else{nEls.each(function(){query.fn.apply(this)});if(this.fn2&&oEls.length>0)$.each(oEls,function(i,el){if($.inArray(el,els)<0)query.fn2.apply(el)})}}};$.extend($.livequery,{guid:0,queries:[],queue:[],running:false,timeout:null,checkQueue:function(){if($.livequery.running&&$.livequery.queue.length){var length=$.livequery.queue.length;while(length--)$.livequery.queries[$.livequery.queue.shift()].run()}}, 5 | pause:function(){$.livequery.running=false},play:function(){$.livequery.running=true;$.livequery.run()},registerPlugin:function(){$.each(arguments,function(i,n){if(!$.fn[n])return;var old=$.fn[n];$.fn[n]=function(){var r=old.apply(this,arguments);$.livequery.run();return r}})},run:function(id){if(id!=undefined){if($.inArray(id,$.livequery.queue)<0)$.livequery.queue.push(id)}else $.each($.livequery.queries,function(id){if($.inArray(id,$.livequery.queue)<0)$.livequery.queue.push(id)});if($.livequery.timeout)clearTimeout($.livequery.timeout); 6 | $.livequery.timeout=setTimeout($.livequery.checkQueue,20)},stop:function(id){if(id!=undefined)$.livequery.queries[id].stop();else $.each($.livequery.queries,function(id){$.livequery.queries[id].stop()})}});$.livequery.registerPlugin("append","prepend","after","before","wrap","attr","removeAttr","addClass","removeClass","toggleClass","empty","remove","html");$(function(){$.livequery.play()})})(jQuery); -------------------------------------------------------------------------------- /libs/jquery/jquery.timers.js: -------------------------------------------------------------------------------- 1 | jQuery.fn.extend({ 2 | everyTime: function(interval, label, fn, times, belay) { 3 | return this.each(function() { 4 | jQuery.timer.add(this, interval, label, fn, times, belay); 5 | }); 6 | }, 7 | oneTime: function(interval, label, fn) { 8 | return this.each(function() { 9 | jQuery.timer.add(this, interval, label, fn, 1); 10 | }); 11 | }, 12 | stopTime: function(label, fn) { 13 | return this.each(function() { 14 | jQuery.timer.remove(this, label, fn); 15 | }); 16 | } 17 | }); 18 | 19 | jQuery.extend({ 20 | timer: { 21 | guid: 1, 22 | global: {}, 23 | regex: /^([0-9]+)\s*(.*s)?$/, 24 | powers: { 25 | // Yeah this is major overkill... 26 | 'ms': 1, 27 | 'cs': 10, 28 | 'ds': 100, 29 | 's': 1000, 30 | 'das': 10000, 31 | 'hs': 100000, 32 | 'ks': 1000000 33 | }, 34 | timeParse: function(value) { 35 | if (value == undefined || value == null) 36 | return null; 37 | var result = this.regex.exec(jQuery.trim(value.toString())); 38 | if (result[2]) { 39 | var num = parseInt(result[1], 10); 40 | var mult = this.powers[result[2]] || 1; 41 | return num * mult; 42 | } else { 43 | return value; 44 | } 45 | }, 46 | add: function(element, interval, label, fn, times, belay) { 47 | var counter = 0; 48 | 49 | if (jQuery.isFunction(label)) { 50 | if (!times) 51 | times = fn; 52 | fn = label; 53 | label = interval; 54 | } 55 | 56 | interval = jQuery.timer.timeParse(interval); 57 | 58 | if (typeof interval != 'number' || isNaN(interval) || interval <= 0) 59 | return; 60 | 61 | if (times && times.constructor != Number) { 62 | belay = !!times; 63 | times = 0; 64 | } 65 | 66 | times = times || 0; 67 | belay = belay || false; 68 | 69 | if (!element.$timers) 70 | element.$timers = {}; 71 | 72 | if (!element.$timers[label]) 73 | element.$timers[label] = {}; 74 | 75 | fn.$timerID = fn.$timerID || this.guid++; 76 | 77 | var handler = function() { 78 | if (belay && this.inProgress) 79 | return; 80 | this.inProgress = true; 81 | if ((++counter > times && times !== 0) || fn.call(element, counter) === false) 82 | jQuery.timer.remove(element, label, fn); 83 | this.inProgress = false; 84 | }; 85 | 86 | handler.$timerID = fn.$timerID; 87 | 88 | if (!element.$timers[label][fn.$timerID]) 89 | element.$timers[label][fn.$timerID] = window.setInterval(handler,interval); 90 | 91 | if ( !this.global[label] ) 92 | this.global[label] = []; 93 | this.global[label].push( element ); 94 | 95 | }, 96 | remove: function(element, label, fn) { 97 | var timers = element.$timers, ret; 98 | 99 | if ( timers ) { 100 | 101 | if (!label) { 102 | for ( label in timers ) 103 | this.remove(element, label, fn); 104 | } else if ( timers[label] ) { 105 | if ( fn ) { 106 | if ( fn.$timerID ) { 107 | window.clearInterval(timers[label][fn.$timerID]); 108 | delete timers[label][fn.$timerID]; 109 | } 110 | } else { 111 | for ( var fn in timers[label] ) { 112 | window.clearInterval(timers[label][fn]); 113 | delete timers[label][fn]; 114 | } 115 | } 116 | 117 | for ( ret in timers[label] ) break; 118 | if ( !ret ) { 119 | ret = null; 120 | delete timers[label]; 121 | } 122 | } 123 | 124 | for ( ret in timers ) break; 125 | if ( !ret ) 126 | element.$timers = null; 127 | } 128 | } 129 | } 130 | }); 131 | 132 | jQuery(window).one("unload", function() { 133 | var global = jQuery.timer.global; 134 | for ( var label in global ) { 135 | var els = global[label], i = els.length; 136 | while ( --i ) 137 | jQuery.timer.remove(els[i], label); 138 | } 139 | }); 140 | 141 | 142 | -------------------------------------------------------------------------------- /libs/jquery/svg/jquery.svg.min.js: -------------------------------------------------------------------------------- 1 | /* http://keith-wood.name/svg.html 2 | SVG for jQuery v1.4.5. 3 | Written by Keith Wood (kbwood{at}iinet.com.au) August 2007. 4 | Dual licensed under the GPL (http://dev.jquery.com/browser/trunk/jquery/GPL-LICENSE.txt) and 5 | MIT (http://dev.jquery.com/browser/trunk/jquery/MIT-LICENSE.txt) licenses. 6 | Please attribute the author if you use it. */ 7 | (function($){function SVGManager(){this._settings=[];this._extensions=[];this.regional=[];this.regional['']={errorLoadingText:'Error loading',notSupportedText:'This browser does not support SVG'};this.local=this.regional[''];this._uuid=new Date().getTime();this._renesis=detectActiveX('RenesisX.RenesisCtrl')}function detectActiveX(a){try{return!!(window.ActiveXObject&&new ActiveXObject(a))}catch(e){return false}}var q='svgwrapper';$.extend(SVGManager.prototype,{markerClassName:'hasSVG',svgNS:'http://www.w3.org/2000/svg',xlinkNS:'http://www.w3.org/1999/xlink',_wrapperClass:SVGWrapper,_attrNames:{class_:'class',in_:'in',alignmentBaseline:'alignment-baseline',baselineShift:'baseline-shift',clipPath:'clip-path',clipRule:'clip-rule',colorInterpolation:'color-interpolation',colorInterpolationFilters:'color-interpolation-filters',colorRendering:'color-rendering',dominantBaseline:'dominant-baseline',enableBackground:'enable-background',fillOpacity:'fill-opacity',fillRule:'fill-rule',floodColor:'flood-color',floodOpacity:'flood-opacity',fontFamily:'font-family',fontSize:'font-size',fontSizeAdjust:'font-size-adjust',fontStretch:'font-stretch',fontStyle:'font-style',fontVariant:'font-variant',fontWeight:'font-weight',glyphOrientationHorizontal:'glyph-orientation-horizontal',glyphOrientationVertical:'glyph-orientation-vertical',horizAdvX:'horiz-adv-x',horizOriginX:'horiz-origin-x',imageRendering:'image-rendering',letterSpacing:'letter-spacing',lightingColor:'lighting-color',markerEnd:'marker-end',markerMid:'marker-mid',markerStart:'marker-start',stopColor:'stop-color',stopOpacity:'stop-opacity',strikethroughPosition:'strikethrough-position',strikethroughThickness:'strikethrough-thickness',strokeDashArray:'stroke-dasharray',strokeDashOffset:'stroke-dashoffset',strokeLineCap:'stroke-linecap',strokeLineJoin:'stroke-linejoin',strokeMiterLimit:'stroke-miterlimit',strokeOpacity:'stroke-opacity',strokeWidth:'stroke-width',textAnchor:'text-anchor',textDecoration:'text-decoration',textRendering:'text-rendering',underlinePosition:'underline-position',underlineThickness:'underline-thickness',vertAdvY:'vert-adv-y',vertOriginY:'vert-origin-y',wordSpacing:'word-spacing',writingMode:'writing-mode'},_attachSVG:function(a,b){var c=(a.namespaceURI==this.svgNS?a:null);var a=(c?null:a);if($(a||c).hasClass(this.markerClassName)){return}if(typeof b=='string'){b={loadURL:b}}else if(typeof b=='function'){b={onLoad:b}}$(a||c).addClass(this.markerClassName);try{if(!c){c=document.createElementNS(this.svgNS,'svg');c.setAttribute('version','1.1');if(a.clientWidth>0){c.setAttribute('width',a.clientWidth)}if(a.clientHeight>0){c.setAttribute('height',a.clientHeight)}a.appendChild(c)}this._afterLoad(a,c,b||{})}catch(e){if($.browser.msie){if(!a.id){a.id='svg'+(this._uuid++)}this._settings[a.id]=b;a.innerHTML=''}else{a.innerHTML='

'+this.local.notSupportedText+'

'}}},_registerSVG:function(){for(var i=0;i=0;i--){var d=a.attributes.item(i);if(!(d.nodeName=='onload'||d.nodeName=='version'||d.nodeName.substring(0,5)=='xmlns')){a.attributes.removeNamedItem(d.nodeName)}}}for(var e in b){a.setAttribute($.svg._attrNames[e]||e,b[e])}return this},getElementById:function(a){return this._svg.ownerDocument.getElementById(a)},change:function(a,b){if(a){for(var c in b){if(b[c]==null){a.removeAttribute($.svg._attrNames[c]||c)}else{a.setAttribute($.svg._attrNames[c]||c,b[c])}}}return this},_args:function(b,c,d){c.splice(0,0,'parent');c.splice(c.length,0,'settings');var e={};var f=0;if(b[0]!=null&&b[0].jquery){b[0]=b[0][0]}if(b[0]!=null&&!(typeof b[0]=='object'&&b[0].nodeName)){e['parent']=null;f=1}for(var i=0;i'+d.styles+'')}return e},script:function(a,b,c,d){var e=this._args(arguments,['script','type'],['type']);var f=this._makeNode(e.parent,'script',$.extend({type:e.type||'text/javascript'},e.settings||{}));f.appendChild(this._svg.ownerDocument.createTextNode(e.script));if(!$.browser.mozilla){$.globalEval(e.script)}return f},linearGradient:function(a,b,c,d,e,f,g,h){var i=this._args(arguments,['id','stops','x1','y1','x2','y2'],['x1']);var j=$.extend({id:i.id},(i.x1!=null?{x1:i.x1,y1:i.y1,x2:i.x2,y2:i.y2}:{}));return this._gradient(i.parent,'linearGradient',$.extend(j,i.settings||{}),i.stops)},radialGradient:function(a,b,c,d,e,r,f,g,h){var i=this._args(arguments,['id','stops','cx','cy','r','fx','fy'],['cx']);var j=$.extend({id:i.id},(i.cx!=null?{cx:i.cx,cy:i.cy,r:i.r,fx:i.fx,fy:i.fy}:{}));return this._gradient(i.parent,'radialGradient',$.extend(j,i.settings||{}),i.stops)},_gradient:function(a,b,c,d){var e=this._makeNode(a,b,c);for(var i=0;i/g,'>'))}}}return b},_checkName:function(a){a=(a.substring(0,1)>='A'&&a.substring(0,1)<='Z'?a.toLowerCase():a);return(a.substring(0,4)=='svg:'?a.substring(4):a)},load:function(j,k){k=(typeof k=='boolean'?{addTo:k}:(typeof k=='function'?{onLoad:k}:(typeof k=='string'?{parent:k}:(typeof k=='object'&&k.nodeName?{parent:k}:(typeof k=='object'&&k.jquery?{parent:k}:k||{})))));if(!k.parent&&!k.addTo){this.clear(false)}var l=[this._svg.getAttribute('width'),this._svg.getAttribute('height')];var m=this;var n=function(a){a=$.svg.local.errorLoadingText+': '+a;if(k.onLoad){k.onLoad.apply(m._container||m._svg,[m,a])}else{m.text(null,10,20,a)}};var o=function(a){var b=new ActiveXObject('Microsoft.XMLDOM');b.validateOnParse=false;b.resolveExternals=false;b.async=false;b.loadXML(a);if(b.parseError.errorCode!=0){n(b.parseError.reason);return null}return b};var p=function(a){if(!a){return}if(a.documentElement.nodeName!='svg'){var b=a.getElementsByTagName('parsererror');var c=(b.length?b[0].getElementsByTagName('div'):[]);n(!b.length?'???':(c.length?c[0]:b[0]).firstChild.nodeValue);return}var d=(k.parent?$(k.parent)[0]:m._svg);var f={};for(var i=0;i'}else{b='<'+a.nodeName;if(a.attributes){for(var i=0;i';var d=a.firstChild;while(d){b+=this._toSVG(d);d=d.nextSibling}b+=''}else{b+='/>'}}return b}});function SVGPath(){this._path=''}$.extend(SVGPath.prototype,{reset:function(){this._path='';return this},move:function(x,y,a){a=(isArray(x)?y:a);return this._coords((a?'m':'M'),x,y)},line:function(x,y,a){a=(isArray(x)?y:a);return this._coords((a?'l':'L'),x,y)},horiz:function(x,a){this._path+=(a?'h':'H')+(isArray(x)?x.join(' '):x);return this},vert:function(y,a){this._path+=(a?'v':'V')+(isArray(y)?y.join(' '):y);return this},curveC:function(a,b,c,d,x,y,e){e=(isArray(a)?b:e);return this._coords((e?'c':'C'),a,b,c,d,x,y)},smoothC:function(a,b,x,y,c){c=(isArray(a)?b:c);return this._coords((c?'s':'S'),a,b,x,y)},curveQ:function(a,b,x,y,c){c=(isArray(a)?b:c);return this._coords((c?'q':'Q'),a,b,x,y)},smoothQ:function(x,y,a){a=(isArray(x)?y:a);return this._coords((a?'t':'T'),x,y)},_coords:function(a,b,c,d,e,f,g){if(isArray(b)){for(var i=0;i= 0) { 97 | className = className.replace(" " + classNames[ c ] + " ", " "); 98 | } 99 | } 100 | 101 | className = jQuery.trim(className); 102 | } else { 103 | className = ""; 104 | } 105 | 106 | if ($.svg.isSVGElem(elem)) { 107 | (elem.className ? elem.className.baseVal = className 108 | : elem.setAttribute('class', className)); 109 | } else { 110 | elem.className = className; 111 | } 112 | } 113 | } 114 | } 115 | 116 | return this; 117 | }; 118 | }($.fn.removeClass); 119 | 120 | /* Support toggling class names on SVG nodes. */ 121 | $.fn.toggleClass = function (origToggleClass) { 122 | return function (className, state) { 123 | return this.each(function () { 124 | if ($.svg.isSVGElem(this)) { 125 | if (typeof state !== 'boolean') { 126 | state = !$(this).hasClass(className); 127 | } 128 | $(this)[(state ? 'add' : 'remove') + 'Class'](className); 129 | } 130 | else { 131 | origToggleClass.apply($(this), [className, state]); 132 | } 133 | }); 134 | }; 135 | }($.fn.toggleClass); 136 | 137 | /* Support checking class names on SVG nodes. */ 138 | $.fn.hasClass = function (origHasClass) { 139 | return function (selector) { 140 | 141 | var className = " " + selector + " ", 142 | i = 0, 143 | l = this.length, 144 | elem, classes; 145 | 146 | for (; i < l; i++) { 147 | elem = this[i]; 148 | if (elem.nodeType === 1) { 149 | classes = !$.svg.isSVGElem(elem) ? elem.className : 150 | elem.className ? elem.className.baseVal : 151 | elem.getAttribute('class'); 152 | if ((" " + classes + " ").replace(rclass, " ").indexOf(className) > -1) { 153 | return true; 154 | } 155 | } 156 | } 157 | 158 | return false; 159 | }; 160 | }($.fn.hasClass); 161 | 162 | /* Support attributes on SVG nodes. */ 163 | $.fn.attr = function (origAttr) { 164 | return function (name, value, type) { 165 | var origArgs = arguments; 166 | if (typeof name === 'string' && value === undefined) { 167 | var val = origAttr.apply(this, origArgs); 168 | if (val && val.baseVal && val.baseVal.numberOfItems != null) { // Multiple values 169 | value = ''; 170 | val = val.baseVal; 171 | if (name == 'transform') { 172 | for (var i = 0; i < val.numberOfItems; i++) { 173 | var item = val.getItem(i); 174 | switch (item.type) { 175 | case 1: 176 | value += ' matrix(' + item.matrix.a + ',' + item.matrix.b + ',' + 177 | item.matrix.c + ',' + item.matrix.d + ',' + 178 | item.matrix.e + ',' + item.matrix.f + ')'; 179 | break; 180 | case 2: 181 | value += ' translate(' + item.matrix.e + ',' + item.matrix.f + ')'; 182 | break; 183 | case 3: 184 | value += ' scale(' + item.matrix.a + ',' + item.matrix.d + ')'; 185 | break; 186 | case 4: 187 | value += ' rotate(' + item.angle + ')'; 188 | break; // Doesn't handle new origin 189 | case 5: 190 | value += ' skewX(' + item.angle + ')'; 191 | break; 192 | case 6: 193 | value += ' skewY(' + item.angle + ')'; 194 | break; 195 | } 196 | } 197 | val = value.substring(1); 198 | } 199 | else { 200 | val = val.getItem(0).valueAsString; 201 | } 202 | } 203 | return (val && val.baseVal ? val.baseVal.valueAsString : val); 204 | } 205 | 206 | var options = name; 207 | if (typeof name === 'string') { 208 | options = {}; 209 | options[name] = value; 210 | } 211 | return $(this).each(function () { 212 | if ($.svg.isSVGElem(this)) { 213 | for (var n in options) { 214 | var val = ($.isFunction(options[n]) ? options[n]() : options[n]); 215 | (type ? this.style[n] = val : this.setAttribute(n, val)); 216 | } 217 | } 218 | else { 219 | origAttr.apply($(this), origArgs); 220 | } 221 | }); 222 | }; 223 | }($.fn.attr); 224 | 225 | /* Support removing attributes on SVG nodes. */ 226 | $.fn.removeAttr = function (origRemoveAttr) { 227 | return function (name) { 228 | return this.each(function () { 229 | if ($.svg.isSVGElem(this)) { 230 | (this[name] && this[name].baseVal ? this[name].baseVal.value = '' : 231 | this.setAttribute(name, '')); 232 | } 233 | else { 234 | origRemoveAttr.apply($(this), [name]); 235 | } 236 | }); 237 | }; 238 | }($.fn.removeAttr); 239 | 240 | /* Add numeric only properties. */ 241 | $.extend($.cssNumber, { 242 | 'stopOpacity': true, 243 | 'strokeMitrelimit':true, 244 | 'strokeOpacity': true 245 | }); 246 | 247 | /* Support retrieving CSS/attribute values on SVG nodes. */ 248 | if ($.cssProps) { 249 | $.css = function (origCSS) { 250 | return function (elem, name, numeric, extra) { 251 | var value = (name.match(/^svg.*/) ? $(elem).attr($.cssProps[name] || name) : ''); 252 | return value || origCSS(elem, name, numeric, extra); 253 | }; 254 | }($.css); 255 | } 256 | 257 | $.find.isXML = function (origIsXml) { 258 | return function (elem) { 259 | return $.svg.isSVGElem(elem) || origIsXml(elem); 260 | } 261 | }($.find.isXML) 262 | 263 | var div = document.createElement('div'); 264 | div.appendChild(document.createComment('')); 265 | if (div.getElementsByTagName('*').length > 0) { // Make sure no comments are found 266 | $.expr.find.TAG = function (match, context) { 267 | var results = context.getElementsByTagName(match[1]); 268 | if (match[1] === '*') { // Filter out possible comments 269 | var tmp = []; 270 | for (var i = 0; results[i] || results.item(i); i++) { 271 | if ((results[i] || results.item(i)).nodeType === 1) { 272 | tmp.push(results[i] || results.item(i)); 273 | } 274 | } 275 | results = tmp; 276 | } 277 | return results; 278 | }; 279 | } 280 | 281 | $.expr.filter.CLASS = function (className) { 282 | var pattern = new RegExp("(^|" + rwhitespace + ")" + className + "(" + rwhitespace + "|$)"); 283 | return function (elem) { 284 | var elemClass = (!$.svg.isSVGElem(elem) ? elem.className || (typeof elem.getAttribute !== "undefined" && elem.getAttribute("class")) || "" : 285 | (elem.className ? elem.className.baseVal : elem.getAttribute('class'))); 286 | 287 | return pattern.test(elemClass); 288 | }; 289 | }; 290 | 291 | /* 292 | In the removeData function (line 1881, v1.7.2): 293 | 294 | if ( jQuery.support.deleteExpando ) { 295 | delete elem[ internalKey ]; 296 | } else { 297 | try { // SVG 298 | elem.removeAttribute( internalKey ); 299 | } catch (e) { 300 | elem[ internalKey ] = null; 301 | } 302 | } 303 | 304 | In the event.add function (line 2985, v1.7.2): 305 | 306 | if ( !special.setup || special.setup.call( elem, data, namespaces, eventHandle ) === false ) { 307 | // Bind the global event handler to the element 308 | try { // SVG 309 | elem.addEventListener( type, eventHandle, false ); 310 | } catch(e) { 311 | if ( elem.attachEvent ) { 312 | elem.attachEvent( "on" + type, eventHandle ); 313 | } 314 | } 315 | } 316 | 317 | In the event.remove function (line 3074, v1.7.2): 318 | 319 | if ( !special.teardown || special.teardown.call( elem, namespaces ) === false ) { 320 | try { // SVG 321 | elem.removeEventListener(type, elemData.handle, false); 322 | } 323 | catch (e) { 324 | if (elem.detachEvent) { 325 | elem.detachEvent("on" + type, elemData.handle); 326 | } 327 | } 328 | } 329 | 330 | In the event.fix function (line 3394, v1.7.2): 331 | 332 | if (event.target.namespaceURI == 'http://www.w3.org/2000/svg') { // SVG 333 | event.button = [1, 4, 2][event.button]; 334 | } 335 | 336 | // Add which for click: 1 === left; 2 === middle; 3 === right 337 | // Note: button is not normalized, so don't use it 338 | if ( !event.which && button !== undefined ) { 339 | event.which = ( button & 1 ? 1 : ( button & 2 ? 3 : ( button & 4 ? 2 : 0 ) ) ); 340 | } 341 | 342 | In the Sizzle function (line 4083, v1.7.2): 343 | 344 | if ( toString.call(checkSet) === "[object Array]" ) { 345 | if ( !prune ) { 346 | results.push.apply( results, checkSet ); 347 | 348 | } else if ( context && context.nodeType === 1 ) { 349 | for ( i = 0; checkSet[i] != null; i++ ) { 350 | if ( checkSet[i] && (checkSet[i] === true || checkSet[i].nodeType === 1 && Sizzle.contains(context, checkSet[i])) ) { 351 | results.push( set[i] || set.item(i) ); // SVG 352 | } 353 | } 354 | 355 | } else { 356 | for ( i = 0; checkSet[i] != null; i++ ) { 357 | if ( checkSet[i] && checkSet[i].nodeType === 1 ) { 358 | results.push( set[i] || set.item(i) ); // SVG 359 | } 360 | } 361 | } 362 | } else {... 363 | 364 | In the fallback for the Sizzle makeArray function (line 4877, v1.7.2): 365 | 366 | if ( toString.call(array) === "[object Array]" ) { 367 | Array.prototype.push.apply( ret, array ); 368 | 369 | } else { 370 | if ( typeof array.length === "number" ) { 371 | for ( var l = array.length; i < l; i++ ) { 372 | ret.push( array[i] || array.item(i) ); // SVG 373 | } 374 | 375 | } else { 376 | for ( ; array[i]; i++ ) { 377 | ret.push( array[i] ); 378 | } 379 | } 380 | } 381 | 382 | In the jQuery.cleandata function (line 6538, v1.7.2): 383 | 384 | if ( deleteExpando ) { 385 | delete elem[ jQuery.expando ]; 386 | 387 | } else { 388 | try { // SVG 389 | elem.removeAttribute( jQuery.expando ); 390 | } catch (e) { 391 | // Ignore 392 | } 393 | } 394 | 395 | In the fallback getComputedStyle function (line 6727, v1.7.2): 396 | 397 | defaultView = (elem.ownerDocument ? elem.ownerDocument.defaultView : elem.defaultView); // SVG 398 | if ( defaultView && 399 | (computedStyle = defaultView.getComputedStyle( elem, null )) ) { 400 | 401 | ret = computedStyle.getPropertyValue( name ); 402 | ... 403 | 404 | */ 405 | 406 | })(jQuery); -------------------------------------------------------------------------------- /libs/jquery/svg/jquery.svgdom.pack.js: -------------------------------------------------------------------------------- 1 | /* http://keith-wood.name/svg.html 2 | jQuery DOM compatibility for jQuery SVG v1.4.5. 3 | Written by Keith Wood (kbwood{at}iinet.com.au) April 2009. 4 | Dual licensed under the GPL (http://dev.jquery.com/browser/trunk/jquery/GPL-LICENSE.txt) and 5 | MIT (http://dev.jquery.com/browser/trunk/jquery/MIT-LICENSE.txt) licenses. 6 | Please attribute the author if you use it. */ 7 | eval(function(p,a,c,k,e,r){e=function(c){return(c35?String.fromCharCode(c+29):c.toString(36))};if(!''.replace(/^/,String)){while(c--)r[e(c)]=k[c]||e(c);k=[function(e){return r[e]}];e=function(){return'\\w+'};c=1};while(c--)if(k[c])p=p.replace(new RegExp('\\b'+e(c)+'\\b','g'),k[c]);return p}('(7($){$.q.S=7(e){8 7(d){d=d||\'\';8 9.w(7(){k($.r.v(9)){l c=9;$.w(d.E(/\\s+/),7(i,a){l b=(c.o?c.o.p:c.B(\'z\'));k($.T(a,b.E(/\\s+/))==-1){b+=(b?\' \':\'\')+a;(c.o?c.o.p=b:c.H(\'z\',b))}})}x{e.A($(9),[d])}})}}($.q.S);$.q.U=7(e){8 7(d){d=d||\'\';8 9.w(7(){k($.r.v(9)){l c=9;$.w(d.E(/\\s+/),7(i,a){l b=(c.o?c.o.p:c.B(\'z\'));b=$.1d(b.E(/\\s+/),7(n,i){8 n!=a}).1e(\' \');(c.o?c.o.p=b:c.H(\'z\',b))})}x{e.A($(9),[d])}})}}($.q.U);$.q.V=7(c){8 7(a,b){8 9.w(7(){k($.r.v(9)){k(M b!==\'1f\'){b=!$(9).N(a)}$(9)[(b?\'1g\':\'1h\')+\'1i\'](a)}x{c.A($(9),[a,b])}})}}($.q.V);$.q.N=7(d){8 7(b){b=b||\'\';l c=I;9.w(7(){k($.r.v(9)){l a=(9.o?9.o.p:9.B(\'z\')).E(/\\s+/);c=($.T(b,a)>-1)}x{c=(d.A($(9),[b]))}8!c});8 c}}($.q.N);$.q.O=7(h){8 7(b,c,d){k(M b===\'W\'&&c===1j){l e=h.A(9,[b]);k(e&&e.p&&e.p.X!=J){c=\'\';e=e.p;k(b==\'1k\'){F(l i=0;i\']=7(d){8 7(a,b,c){d(a,b,c||G(a))}}($.m.y[\'>\']);$.m.y[\'\']=7(d){8 7(a,b,c){d(a,b,c||G(a))}}($.m.y[\'\']);$.m.y[\'~\']=7(d){8 7(a,b,c){d(a,b,c||G(a))}}($.m.y[\'~\']);$.m.Q.15=7(d){8 7(a,b,c){8($.r.v(b)?[b.1F.1G(a[1])]:d(a,b,c))}}($.m.Q.15);l j=16.1H(\'1I\');j.1J(16.1K(\'\'));k(j.17(\'*\').13>0){$.m.Q.1L=7(a,b){l c=b.17(a[1]);k(a[1]===\'*\'){l d=[];F(l i=0;c[i]||c.L(i);i++){k((c[i]||c.L(i)).14===1){d.18(c[i]||c.L(i))}}c=d}8 c}}$.m.1M.19=7(a,b,c,d,f,g){a=\' \'+a[1].1N(/\\\\/g,\'\')+\' \';k(g){8 a}F(l i=0,t={};t!=J;i++){t=b[i];k(!t){1O{t=b.L(i)}1P(e){}}k(t){l h=(!$.r.v(t)?t.o:(t.o?t.o.p:\'\')||t.B(\'z\'));k(f^(h&&(\' \'+h+\' \').1a(a)>-1)){k(!c)d.18(t)}x k(c){b[i]=I}}}8 I};$.m.R.19=7(a,b){l c=(!$.r.v(a)?a.o:(a.o?a.o.p:a.B(\'z\')));8(\' \'+c+\' \').1a(b)>-1};$.m.R.1b=7(g){8 7(c,d){l e=J;k($.r.v(c)){e=d[1];$.m.1c[e]=7(a){l b=a.B(e);8 b&&b.p||b}}l f=g(c,d);k(e){$.m.1c[e]=J}8 f}}($.m.R.1b)})(1Q);',62,115,'|||||||function|return|this|||||||||||if|var|expr||className|baseVal|fn|svg||elem|matrix|isSVGElem|each|else|relative|class|apply|getAttribute|case|break|split|for|anySVG|setAttribute|false|null|true|item|typeof|hasClass|attr|angle|find|filter|addClass|inArray|removeClass|toggleClass|string|numberOfItems|getItem|valueAsString|removeAttr|cssProps|css|length|nodeType|ID|document|getElementsByTagName|push|CLASS|indexOf|ATTR|attrHandle|grep|join|boolean|add|remove|Class|undefined|transform|switch|type|translate|scale|rotate|skewX|skewY|substring|in|isFunction|style|value|extend|cssNumber|stopOpacity|strokeMitrelimit|strokeOpacity|match|namespaceURI|svgNS|ownerDocument|getElementById|createElement|div|appendChild|createComment|TAG|preFilter|replace|try|catch|jQuery'.split('|'),0,{})) -------------------------------------------------------------------------------- /libs/jquery/valueSlider/jquery.mb.slider.js: -------------------------------------------------------------------------------- 1 | /******************************************************************************* 2 | * jquery.mb.components 3 | * file: jquery.mb.slider.js 4 | * last modified: 18/11/17 18.21 5 | * Version: {{ version }} 6 | * Build: {{ buildnum }} 7 | * 8 | * Open Lab s.r.l., Florence - Italy 9 | * email: matteo@open-lab.com 10 | * site: http://pupunzi.com 11 | * http://open-lab.com 12 | * blog: http://pupunzi.open-lab.com 13 | * 14 | * Licences: MIT, GPL 15 | * http://www.opensource.org/licenses/mit-license.php 16 | * http://www.gnu.org/licenses/gpl.html 17 | * 18 | * Copyright (c) 2001-2017. Matteo Bicocchi (Pupunzi) 19 | ******************************************************************************/ 20 | 21 | (function ($) { 22 | 23 | $.mbSlider = { 24 | name : "mb.slider", 25 | author : "Matteo Bicocchi", 26 | version: "1.6.0", 27 | 28 | defaults: { 29 | minVal : 0, 30 | maxVal : 100, 31 | grid : 0, 32 | showVal : true, 33 | labelPos : "top", 34 | rangeColor : "#000", 35 | negativeColor: "#e20000", 36 | formatValue : function (val) {return parseFloat(val)}, 37 | onSlideLoad : function (o) {}, 38 | onStart : function (o) {}, 39 | onSlide : function (o) {}, 40 | onStop : function (o) {} 41 | }, 42 | 43 | buildSlider: function (options) { 44 | return this.each(function () { 45 | var slider = this; 46 | var $slider = $(slider); 47 | $slider.addClass("mb_slider"); 48 | 49 | slider.options = {}; 50 | slider.metadata = $slider.data("property") && typeof $slider.data("property") == "string" ? eval('(' + $slider.data("property") + ')') : $slider.data("property"); 51 | $.extend(slider.options, $.mbSlider.defaults, options, this.metadata); 52 | slider.options.element = slider; 53 | 54 | if (slider.options.grid == 0) 55 | slider.options.grid = 1; 56 | 57 | if (this.options.startAt < 0 && this.options.startAt < slider.options.minVal) 58 | slider.options.minVal = parseFloat(this.options.startAt); 59 | 60 | slider.actualPos = this.options.startAt; 61 | 62 | /** 63 | * Slider UI builder 64 | */ 65 | slider.sliderStart = $("
"); 66 | slider.sliderEnd = $("
"); 67 | slider.sliderValue = $("
").css({color: this.options.rangeColor}); 68 | slider.sliderZeroLabel = $("
0
").css({position: "absolute", top: (slider.options.labelPos == "top" ? -18 : 29)}); 69 | slider.sliderValueLabel = $("
").css({position: "absolute", borderTop: "2px solid " + slider.options.rangeColor}); 70 | 71 | slider.sliderBar = $("
").css({position: "relative", display: "block"}); 72 | slider.sliderRange = $("
").css({background: slider.options.rangeColor}); 73 | slider.sliderZero = $("
").css({}); 74 | slider.sliderHandler = $("
"); 75 | 76 | $(slider).append(slider.sliderBar); 77 | slider.sliderBar.append(slider.sliderValueLabel); 78 | 79 | if (slider.options.showVal) $(slider).append(slider.sliderEnd); 80 | if (slider.options.showVal) $(slider).prepend(slider.sliderStart); 81 | slider.sliderBar.append(slider.sliderRange); 82 | slider.sliderBar.append(slider.sliderRange); 83 | 84 | if (slider.options.minVal < 0) { 85 | slider.sliderBar.append(slider.sliderZero); 86 | slider.sliderBar.append(slider.sliderZeroLabel); 87 | } 88 | 89 | slider.sliderBar.append(slider.sliderHandler); 90 | slider.rangeVal = slider.options.maxVal - slider.options.minVal; 91 | slider.zero = slider.options.minVal < 0 ? (slider.sliderBar.outerWidth() * Math.abs(slider.options.minVal)) / slider.rangeVal : 0; 92 | slider.sliderZero.css({left: 0, width: slider.zero}); 93 | slider.sliderZeroLabel.css({left: slider.zero - 5}); 94 | 95 | $(slider).find("div").css({display: "inline-block", clear: "left"}); 96 | 97 | $(slider).attr("unselectable", "on"); 98 | $(slider).find("div").attr("unselectable", "on"); 99 | 100 | var sliderVal = parseFloat(this.options.startAt) >= slider.options.minVal ? parseFloat(this.options.startAt) : slider.options.minVal; 101 | slider.sliderValue.html(sliderVal); 102 | slider.sliderValueLabel.html(slider.options.formatValue(sliderVal)); 103 | 104 | slider.sliderStart.html(slider.options.formatValue(slider.options.minVal)); 105 | slider.sliderEnd.html(slider.options.formatValue(slider.options.maxVal)); 106 | 107 | if (slider.options.startAt < slider.options.minVal || !slider.options.startAt) 108 | this.options.startAt = slider.options.minVal; 109 | 110 | slider.evalPosGrid = parseFloat(slider.actualPos); 111 | $(slider).mbsetVal(slider.evalPosGrid); 112 | 113 | function setNewPosition(e) { 114 | 115 | e.preventDefault(); 116 | e.stopPropagation(); 117 | 118 | var mousePos = e.clientX - slider.sliderBar.offset().left; 119 | var grid = (slider.options.grid * slider.sliderBar.outerWidth()) / slider.rangeVal; 120 | var posInGrid = grid * Math.round(mousePos / grid); 121 | var evalPos = ((slider.options.maxVal - slider.options.minVal) * posInGrid) / (slider.sliderBar.outerWidth() - (slider.sliderHandler.outerWidth() / 2)) + parseFloat(slider.options.minVal); 122 | 123 | slider.evalPosGrid = Math.max(slider.options.minVal, Math.min(slider.options.maxVal, slider.options.grid * Math.round(evalPos / slider.options.grid))); 124 | 125 | if (typeof slider.options.onSlide == "function" && slider.gridStep != posInGrid) { 126 | slider.gridStep = posInGrid; 127 | slider.options.onSlide(slider); 128 | } 129 | 130 | $(slider).mbsetVal(slider.evalPosGrid); 131 | 132 | } 133 | 134 | /** 135 | * Slider Events 136 | * 137 | * Add start event both on slider bar and on slider handler 138 | */ 139 | var sliderElements = slider.sliderBar.add(slider.sliderHandler); 140 | 141 | sliderElements.on("mousedown.mb_slider", function (e) { 142 | 143 | if (!$(e.target).is(slider.sliderHandler)) 144 | setNewPosition(e); 145 | 146 | if (typeof slider.options.onStart == "function") 147 | slider.options.onStart(slider); 148 | 149 | $(document).on("mousemove.mb_slider", function (e) { 150 | setNewPosition(e); 151 | }); 152 | 153 | $(document).on("mouseup.mb_slider", function () { 154 | $(document).off("mousemove.mb_slider").off("mouseup.mb_slider"); 155 | if (typeof slider.options.onStop == "function") 156 | slider.options.onStop(slider); 157 | }); 158 | 159 | }); 160 | 161 | $(window).on("resize", function() { 162 | $(slider).mbsetVal(slider.evalPosGrid); 163 | }) 164 | 165 | if (typeof slider.options.onSlideLoad == "function") 166 | slider.options.onSlideLoad(slider); 167 | }); 168 | }, 169 | 170 | setVal: function (val) { 171 | var slider = $(this).get(0); 172 | if (val > slider.options.maxVal) val = slider.options.maxVal; 173 | if (val < slider.options.minVal) val = slider.options.minVal; 174 | var startPos = val == slider.options.minVal ? 0 : Math.round(((val - slider.options.minVal) * slider.sliderBar.outerWidth()) / slider.rangeVal); 175 | startPos = startPos >= 0 ? startPos : slider.zero + val; 176 | var grid = (slider.options.grid * slider.sliderBar.outerWidth()) / slider.rangeVal; 177 | var posInGrid = grid * Math.round(startPos / grid); 178 | 179 | slider.evalPosGrid = slider.options.grid * Math.round(val / slider.options.grid); 180 | slider.sliderHandler.css({left: posInGrid - slider.sliderHandler.outerWidth()/2}); 181 | slider.sliderValueLabel.css({left: posInGrid - (slider.sliderHandler.outerWidth() / 2) - (slider.sliderValueLabel.outerWidth() - slider.sliderHandler.outerWidth()) / 2}); 182 | 183 | if (slider.evalPosGrid >= 0) { 184 | slider.sliderValueLabel.css({borderTop: "2px solid " + slider.options.rangeColor}); 185 | slider.sliderRange.css({left: 0, width: posInGrid, background: slider.options.rangeColor}).removeClass("negative"); 186 | slider.sliderZero.css({width: slider.zero}); 187 | } else { 188 | slider.sliderValueLabel.css({borderTop: "2px solid " + slider.options.negativeColor}); 189 | slider.sliderRange.css({left: 0, width: slider.zero, background: slider.options.negativeColor}).addClass("negative"); 190 | slider.sliderZero.css({width: posInGrid + (slider.sliderHandler.outerWidth() / 2)}); 191 | } 192 | 193 | if (startPos >= slider.sliderBar.outerWidth() && slider.sliderValueLabel.outerWidth() > 40) 194 | slider.sliderValueLabel.addClass("right"); 195 | 196 | else if (startPos <= 0 && slider.sliderValueLabel.outerWidth() > 40) 197 | slider.sliderValueLabel.addClass("left"); 198 | 199 | else 200 | slider.sliderValueLabel.removeClass("left right"); 201 | 202 | 203 | slider.sliderValue.html(val >= slider.options.minVal ? slider.evalPosGrid : slider.options.minVal); 204 | slider.sliderValueLabel.html(slider.options.formatValue(val >= slider.options.minVal ? slider.evalPosGrid : slider.options.minVal)); 205 | }, 206 | 207 | getVal: function () { 208 | var slider = $(this).get(0); 209 | return slider.evalPosGrid; 210 | } 211 | }; 212 | 213 | $.fn.mbSlider = $.mbSlider.buildSlider; 214 | $.fn.mbsetVal = $.mbSlider.setVal; 215 | $.fn.mbgetVal = $.mbSlider.getVal; 216 | 217 | })(jQuery); 218 | 219 | -------------------------------------------------------------------------------- /libs/jquery/valueSlider/mb.slider.css: -------------------------------------------------------------------------------- 1 | .mb_slider{ 2 | position:relative; 3 | padding:10px; 4 | padding-bottom: 40px; 5 | z-index:0; 6 | font-family:Arial, Helvetica, sans-serif; 7 | } 8 | 9 | .mb_sliderBar{ 10 | background-color:#fafafa; 11 | height: 6px; 12 | width:100%; 13 | box-shadow: rgba(0, 0, 0, 0.1) 0 0 0 1px; 14 | cursor:default; 15 | } 16 | 17 | .mb_sliderHandler { 18 | width: 14px; 19 | height: 14px; 20 | background-color: #266b8d; 21 | position: absolute; 22 | top: -4px; 23 | left: 0; 24 | border-radius: 100%; 25 | border: 3px solid white; 26 | box-shadow: #2F97C6 0 0 0 2px; 27 | cursor: default; 28 | } 29 | 30 | .mb_sliderEnd, .mb_sliderStart, .mb_sliderValue{ 31 | padding:7px; 32 | position:absolute; 33 | margin: 3px; 34 | min-width: 50px; 35 | color:#AAA; 36 | white-space: nowrap; 37 | cursor:default; 38 | } 39 | 40 | .mb_sliderStart{ 41 | left:0; 42 | bottom: 0; 43 | text-align: right; 44 | margin-top: 20px; 45 | } 46 | 47 | .mb_sliderEnd{ 48 | text-align: left; 49 | right: 0; 50 | bottom: 0; 51 | margin-top: 20px; 52 | } 53 | 54 | .mb_sliderRange { 55 | position: absolute; 56 | height: 2px; 57 | margin: auto; 58 | bottom: 0; 59 | top: 0; 60 | background: #ffcc00; 61 | cursor: default; 62 | } 63 | 64 | .mb_sliderZero{ 65 | background-color: #fafafa; 66 | position:absolute; 67 | height:100%; 68 | margin:0; 69 | top:0; 70 | cursor:default; 71 | } 72 | 73 | .mb_sliderZeroLabel{ 74 | font: 12px/12px Arial, sans-serif; 75 | color: #AAA; 76 | padding: 5px; 77 | background-color: #fff; 78 | margin-left: -4px; 79 | z-index: -2; 80 | margin-top: -5px; 81 | } 82 | 83 | .mb_sliderValueLabel{ 84 | font:12px/12px Arial, sans-serif; 85 | padding: 3px 5px; 86 | background-color: #2F97C6; 87 | color: #fff; 88 | top: -24px; 89 | margin-left:0; 90 | z-index:-1; 91 | border: none; 92 | border-radius: 4px; 93 | margin-top: -10px; 94 | white-space: nowrap; 95 | } 96 | 97 | .mb_sliderValueLabel:after{ 98 | content: ""; 99 | position: absolute; 100 | bottom: -5px; 101 | width: 0; 102 | height: 0; 103 | left:0; 104 | right: 0; 105 | margin: auto; 106 | border-style: solid; 107 | border-width: 5px 5px 0 5px; 108 | border-color: #2F97C6 transparent transparent transparent; 109 | } 110 | 111 | .mb_sliderValueLabel.right{ 112 | left: auto!important; 113 | right: -15px!important; 114 | } 115 | 116 | .mb_sliderValueLabel.left{ 117 | left: -15px!important; 118 | right: auto!important; 119 | } 120 | 121 | .mb_sliderValueLabel.right:after{ 122 | left:auto; 123 | right: 10px; 124 | margin: auto; 125 | } 126 | 127 | .mb_sliderValueLabel.left:after{ 128 | right:auto; 129 | left: 10px; 130 | margin: auto; 131 | } 132 | -------------------------------------------------------------------------------- /libs/layout.js: -------------------------------------------------------------------------------- 1 | /* 2 | Copyright (c) 2012-2017 Open Lab 3 | Permission is hereby granted, free of charge, to any person obtaining 4 | a copy of this software and associated documentation files (the 5 | "Software"), to deal in the Software without restriction, including 6 | without limitation the rights to use, copy, modify, merge, publish, 7 | distribute, sublicense, and/or sell copies of the Software, and to 8 | permit persons to whom the Software is furnished to do so, subject to 9 | the following conditions: 10 | 11 | The above copyright notice and this permission notice shall be 12 | included in all copies or substantial portions of the Software. 13 | 14 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 15 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 16 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 17 | NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 18 | LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 19 | OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 20 | WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 21 | */ 22 | 23 | //----------------------------------positioning----------------------------------------------- 24 | jQuery.fn.centerOnScreen = function () { 25 | return this.each(function () { 26 | var container = $(this); 27 | //console.debug($(window).height(), container.outerHeight(),(($(window).height() - container.outerHeight()) / 2)) 28 | container.css("position", "fixed"); 29 | container.css("top", (($(window).height() - container.outerHeight()) / 2) + 'px'); 30 | container.css("left", (($(window).width() - container.outerWidth()) / 2) + 'px'); 31 | }); 32 | }; 33 | 34 | 35 | function nearBestPosition(whereId, theObjId, centerOnEl) { 36 | 37 | var el = whereId; 38 | var target = theObjId; 39 | 40 | if (typeof whereId != "object") { 41 | el = $("#" + whereId); 42 | } 43 | if (typeof theObjId != "object") { 44 | target = $("#" + theObjId); 45 | } 46 | 47 | if (el) { 48 | target.css("visibility", "hidden"); 49 | var hasContainment = false; 50 | 51 | target.parents().each(function () { 52 | if ($(this).css("position") == "static") 53 | return; 54 | 55 | hasContainment = true; 56 | }); 57 | 58 | var trueX = hasContainment ? el.position().left : el.offset().left; 59 | var trueY = hasContainment ? el.position().top : el.offset().top; 60 | var h = el.outerHeight(); 61 | var elHeight = parseFloat(h); 62 | 63 | if (centerOnEl) { 64 | var elWidth = parseFloat(el.outerWidth()); 65 | var targetWidth = parseFloat(target.outerWidth()); 66 | trueX += (elWidth - targetWidth) / 2; 67 | } 68 | 69 | trueY += parseFloat(elHeight); 70 | 71 | var left = trueX; 72 | var top = trueY; 73 | var barHeight = 45 ; 74 | var barWidth = 20 ; 75 | 76 | if (trueX && trueY) { 77 | target.css("left", left); 78 | target.css("top", top); 79 | } 80 | 81 | if (target.offset().left >= ( ($(window).width() + $(window).scrollLeft()) - target.outerWidth())) { 82 | 83 | left = ( ($(window).width() + $(window).scrollLeft()) - target.outerWidth() - 10 ); 84 | target.css({left:left, marginTop: 0}); 85 | } 86 | 87 | if (target.offset().left < 0) { 88 | left = 10; 89 | target.css("left", left); 90 | } 91 | 92 | if ((target.offset().top + target.outerHeight() >= ( ($(window).height() + $(window).scrollTop()) - barHeight)) && (target.outerHeight() < $(window).height())) { 93 | var marginTop = -(target.outerHeight() + el.outerHeight()); 94 | target.css("margin-top", marginTop); 95 | } 96 | 97 | if (target.offset().top < 0) { 98 | top = 0; 99 | target.css("top", top); 100 | } 101 | 102 | 103 | target.css("visibility", "visible"); 104 | } 105 | } 106 | 107 | $.fn.keepItVisible = function (ref) { 108 | var thisTop = $(this).offset().top; 109 | var thisLeft = $(this).offset().left; 110 | var fromTop =0; 111 | var fromLeft =0; 112 | 113 | var windowH = $(window).height() + $(window).scrollTop(); 114 | var windowW = $(window).width() + $(window).scrollLeft(); 115 | 116 | if (ref){ 117 | fromTop = windowH - (ref.offset().top); 118 | fromLeft = windowW - (ref.offset().left + ref.outerWidth()); 119 | } 120 | 121 | if (thisTop + $(this).outerHeight() > windowH){ 122 | var mt = (thisTop + $(this).outerHeight()) - windowH; 123 | // $(this).css("margin-top", -$(this).outerHeight() - fromTop); 124 | $(this).css("margin-top", -mt - fromTop); 125 | } 126 | if (thisLeft + $(this).outerWidth() > windowW){ 127 | var mL = (thisLeft + $(this).outerWidth()) - windowW; 128 | // $(this).css("margin-left", -$(this).outerWidth() - fromLeft); 129 | $(this).css("margin-left", -mL - fromLeft); 130 | } 131 | $(this).css("visibility", "visible"); 132 | }; 133 | 134 | //END positioning 135 | 136 | 137 | /* Caret Functions 138 | Use setSelection with start = end to set caret 139 | */ 140 | function setSelection(input, start, end) { 141 | input.setSelectionRange(start, end); 142 | } 143 | 144 | $.fn.setCursorPosition = function(pos) { 145 | this.each(function(index, elem) { 146 | if (elem.setSelectionRange) { 147 | elem.setSelectionRange(pos, pos); 148 | } else if (elem.createTextRange) { 149 | var range = elem.createTextRange(); 150 | range.collapse(true); 151 | range.moveEnd('character', pos); 152 | range.moveStart('character', pos); 153 | range.select(); 154 | } 155 | }); 156 | return this; 157 | }; 158 | 159 | //-- Caret Functions END ---------------------------------------------------------------------------- -- 160 | 161 | 162 | 163 | /*----------------------------------------------------------------- manage bbButtons*/ 164 | $.buttonBar = { 165 | defaults: {}, 166 | 167 | init: function(){ 168 | setTimeout(function(){ 169 | $.buttonBar.manageButtonBar(); 170 | },100); 171 | 172 | $(window).on("scroll.ButtonBar",function(){ 173 | $.buttonBar.manageButtonBar(); 174 | }); 175 | $(window).on("resize.ButtonBar",function(){ 176 | $.buttonBar.manageButtonBar(); 177 | }); 178 | }, 179 | 180 | manageButtonBar: function(anim) { 181 | 182 | $(".buttonArea").not(".bbCloned").not(".notFix").each(function(){ 183 | var bb = this; 184 | 185 | //se usiamo questi si rompe la button bar flottante del save sulla issue list 186 | //bb.originalHeigh=bb.originalHeigh || $(bb).height(); 187 | //bb.originalOffsetTop=bb.originalOffsetTop||$(bb).offset().top; 188 | 189 | bb.originalHeigh= $(bb).height(); 190 | bb.originalOffsetTop=$(bb).offset().top; 191 | 192 | bb.isOut = $(window).scrollTop() + $(window).height() - bb.originalHeigh < bb.originalOffsetTop; 193 | 194 | if (bb.bbHolder) 195 | bb.bbHolder.css({width: $(bb).outerWidth(),left:$(bb).offset().left}); 196 | 197 | if (bb.isOut && !bb.isCloned){ 198 | if (bb.bbHolder) 199 | bb.bbHolder.remove(); 200 | bb.isCloned = true; 201 | bb.bbHolder = $(bb).clone().addClass("bbCloned clone bottom").css({width: $(bb).outerWidth(), marginTop:0,left:$(bb).offset().left}); 202 | bb.bbHolder.hide(); 203 | bb.bbHolder.css({position:"fixed", bottom:0, left:$(bb).offset().left}); 204 | $(bb).after(bb.bbHolder); 205 | bb.bbHolder.show(); 206 | $(bb).css("visibility","hidden"); 207 | 208 | } else if (!bb.isOut && bb.isCloned) { 209 | //} else { 210 | bb.isCloned = false; 211 | bb.bbHolder.remove(); 212 | $(bb).css("visibility","visible"); 213 | } 214 | }); 215 | }, 216 | 217 | refreshButtonBar: function() { 218 | $(".bbCloned").remove(); 219 | $(".buttonArea").not(".bbCloned").each(function(){ 220 | var bb = this; 221 | bb.isCloned = false; 222 | }); 223 | 224 | $.buttonBar.manageButtonBar(false); 225 | } 226 | }; 227 | -------------------------------------------------------------------------------- /libs/utilities.js: -------------------------------------------------------------------------------- 1 | /* 2 | Copyright (c) 2012-2017 Open Lab 3 | Permission is hereby granted, free of charge, to any person obtaining 4 | a copy of this software and associated documentation files (the 5 | "Software"), to deal in the Software without restriction, including 6 | without limitation the rights to use, copy, modify, merge, publish, 7 | distribute, sublicense, and/or sell copies of the Software, and to 8 | permit persons to whom the Software is furnished to do so, subject to 9 | the following conditions: 10 | 11 | The above copyright notice and this permission notice shall be 12 | included in all copies or substantial portions of the Software. 13 | 14 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 15 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 16 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 17 | NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 18 | LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 19 | OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 20 | WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 21 | */ 22 | 23 | 24 | 25 | // works also for IE8 beta 26 | var isExplorer = navigator.userAgent.toUpperCase().indexOf("MSIE") >= 0 || !!navigator.userAgent.match(/Trident.*rv\:11\./); 27 | var isMozilla = navigator.userAgent.toUpperCase().indexOf("FIREFOX") >= 0; 28 | var isSafari = navigator.userAgent.toLowerCase().indexOf("safari") != -1 && navigator.userAgent.toLowerCase().indexOf('chrome') < 0; 29 | 30 | //Version detection 31 | var version = navigator.appVersion.substring(0, 1); 32 | var inProduction = false; 33 | if (inProduction) { 34 | window.console = undefined; 35 | } 36 | 37 | // deprecated use $("#domid")... 38 | function obj(element) { 39 | if (arguments.length > 1) { 40 | alert("invalid use of obj with multiple params:" + element) 41 | } 42 | var el = document.getElementById(element); 43 | if (!el) 44 | console.error("element not found: " + element); 45 | return el; 46 | } 47 | 48 | if (!window.console) { 49 | window.console = new function () { 50 | this.log = function (str) {/*alert(str)*/}; 51 | this.debug = function (str) {/*alert(str)*/}; 52 | this.error = function (str) {/*alert(str)*/}; 53 | }; 54 | } 55 | if (!window.console.debug || !window.console.error || !window.console.log) { 56 | window.console = new function () { 57 | this.log = function (str) {/*alert(str)*/}; 58 | this.debug = function (str) {/*alert(str)*/}; 59 | this.error = function (str) {/*alert(str)*/}; 60 | }; 61 | } 62 | 63 | 64 | 65 | String.prototype.trim = function () { 66 | return this.replace(/^\s*(\S*(\s+\S+)*)\s*$/, "$1"); 67 | }; 68 | 69 | String.prototype.startsWith = function (t, i) { 70 | if (!i) { 71 | return (t == this.substring(0, t.length)); 72 | } else { 73 | return (t.toLowerCase() == this.substring(0, t.length).toLowerCase()); 74 | } 75 | }; 76 | 77 | String.prototype.endsWith = function (t, i) { 78 | if (!i) { 79 | return (t == this.substring(this.length - t.length)); 80 | } else { 81 | return (t.toLowerCase() == this.substring(this.length - t.length).toLowerCase()); 82 | } 83 | }; 84 | 85 | // leaves only char from A to Z, numbers, _ -> valid ID 86 | String.prototype.asId = function () { 87 | return this.replace(/[^a-zA-Z0-9_]+/g, ''); 88 | }; 89 | 90 | String.prototype.replaceAll = function (from, to) { 91 | return this.replace(new RegExp(RegExp.quote(from), 'g'), to); 92 | }; 93 | 94 | 95 | if (!Array.prototype.indexOf) { 96 | Array.prototype.indexOf = function (searchElement, fromIndex) { 97 | if (this == null) { 98 | throw new TypeError(); 99 | } 100 | var t = Object(this); 101 | var len = t.length >>> 0; 102 | if (len === 0) { 103 | return -1; 104 | } 105 | var n = 0; 106 | if (arguments.length > 0) { 107 | n = Number(arguments[1]); 108 | if (n != n) { // shortcut for verifying if it's NaN 109 | n = 0; 110 | } else if (n != 0 && n != Infinity && n != -Infinity) { 111 | n = (n > 0 || -1) * Math.floor(Math.abs(n)); 112 | } 113 | } 114 | if (n >= len) { 115 | return -1; 116 | } 117 | var k = n >= 0 ? n : Math.max(len - Math.abs(n), 0); 118 | for (; k < len; k++) { 119 | if (k in t && t[k] === searchElement) { 120 | return k; 121 | } 122 | } 123 | return -1; 124 | }; 125 | } 126 | 127 | 128 | Object.size = function (obj) { 129 | var size = 0, key; 130 | for (key in obj) { 131 | if (obj.hasOwnProperty(key)) size++; 132 | } 133 | return size; 134 | }; 135 | 136 | 137 | // transform string values to printable: \n in
138 | function transformToPrintable(data) { 139 | for (var prop in data) { 140 | var value = data[prop]; 141 | if (typeof(value) == "string") 142 | data[prop] = (value + "").replace(/\n/g, "
"); 143 | } 144 | return data; 145 | } 146 | 147 | 148 | RegExp.quote = function (str) { 149 | return str.replace(/([.?*+^$[\]\\(){}-])/g, "\\$1"); 150 | }; 151 | 152 | 153 | /* Object Functions */ 154 | 155 | function stopBubble(e) { 156 | e.stopPropagation(); 157 | e.preventDefault(); 158 | return false; 159 | } 160 | 161 | 162 | // ------ ------- -------- wraps http://www.mysite.com/....... with 163 | jQuery.fn.activateLinks = function (showImages) { 164 | var httpRE = /(['"]\s*)?(http[s]?:[\d]*\/\/[^"<>\s]*)/g; 165 | var wwwRE = /(['"/]\s*)?(www\.[^"<>\s]+)/g; 166 | var imgRE = /(['"]\s*)?(http[s]?:[\d]*\/\/[^"<>\s]*\.(?:gif|jpg|png|jpeg|bmp))/g; 167 | 168 | 169 | this.each(function () { 170 | var el = $(this); 171 | var html = el.html(); 172 | 173 | if (showImages) { 174 | // workaround for negative look ahead 175 | html = html.replace(imgRE, function ($0, $1) { 176 | return $1 ? $0 : "
"; 177 | }); 178 | } 179 | 180 | html = html.replace(httpRE, function ($0, $1) { 181 | return $1 ? $0 : "
" + $0 + ""; 182 | }); 183 | 184 | html = html.replace(wwwRE, function ($0, $1) { 185 | return $1 ? $0 : "" + $0 + ""; 186 | }); 187 | 188 | el.empty().append(html); 189 | 190 | if (showImages) { 191 | //inject expand capability on images 192 | el.find("div.imgWrap").each(function () { 193 | var imageDiv = $(this); 194 | 195 | 196 | imageDiv.click(function (e) { 197 | if (e.ctrlKey || e.metaKey) { 198 | window.open(imageDiv.find("img").prop("src"), "_blank"); 199 | } else { 200 | var imageClone = imageDiv.find("img").clone(); 201 | imageClone.mouseout(function () { 202 | $(this).remove(); 203 | }); 204 | imageClone.addClass("imageClone").css({"position":"absolute", "display":"none", "top":imageDiv.position().top, "left":imageDiv.position().left, "z-index":1000000}); 205 | imageDiv.after(imageClone); 206 | imageClone.fadeIn(); 207 | } 208 | }); 209 | }); 210 | } 211 | 212 | }); 213 | return this; 214 | }; 215 | 216 | jQuery.fn.emoticonize = function () { 217 | function convert(text) { 218 | var faccRE = /(:\))|(:-\))|(:-])|(:-\()|(:\()|(:-\/)|(:-\\)|(:-\|)|(;-\))|(:-D)|(:-P)|(:-p)|(:-0)|(:-o)|(:-O)|(:'-\()|(\(@\))/g; 219 | return text.replace(faccRE, function (str) { 220 | var ret = {":)":"smile", 221 | ":-)":"smile", 222 | ":-]":"polite_smile", 223 | ":-(":"frown", 224 | ":(":"frown", 225 | ":-/":"skepticism", 226 | ":-\\":"skepticism", 227 | ":-|":"sarcasm", 228 | ";-)":"wink", 229 | ":-D":"grin", 230 | ":-P":"tongue", 231 | ":-p":"tongue", 232 | ":-o":"surprise", 233 | ":-O":"surprise", 234 | ":-0":"surprise", 235 | ":'-(":"tear", 236 | "(@)":"angry"}[str]; 237 | if (ret) { 238 | ret = ""; 239 | return ret; 240 | } else 241 | return str; 242 | }); 243 | } 244 | 245 | function addBold(text) { 246 | var returnedValue; 247 | var faccRE = /\*\*[^*]*\*\*/ig; 248 | return text.replace(faccRE, function (str) { 249 | var temp = str.substr(2); 250 | var temp2 = temp.substr(0, temp.length - 2); 251 | return "" + temp2 + ""; 252 | }); 253 | } 254 | 255 | this.each(function () { 256 | var el = $(this); 257 | var html = convert(el.html()); 258 | html = addBold(html); 259 | el.html(html); 260 | }); 261 | return this; 262 | }; 263 | 264 | 265 | $.fn.unselectable = function () { 266 | this.each(function () { 267 | $(this).addClass("unselectable").attr("unselectable", "on"); 268 | }); 269 | return $(this); 270 | }; 271 | 272 | $.fn.clearUnselectable = function () { 273 | this.each(function () { 274 | $(this).removeClass("unselectable").removeAttr("unselectable"); 275 | }); 276 | return $(this); 277 | }; 278 | 279 | // ---------------------------------- initialize management 280 | var __initedComponents = new Object(); 281 | 282 | function initialize(url, type, ndo) { 283 | //console.debug("initialize before: " + url); 284 | var normUrl = url.asId(); 285 | var deferred = $.Deferred(); 286 | 287 | if (!__initedComponents[normUrl]) { 288 | __initedComponents[normUrl] = deferred; 289 | 290 | if ("CSS" == (type + "").toUpperCase()) { 291 | var link = $("").prop("href", url); 292 | $("head").append(link); 293 | deferred.resolve(); 294 | 295 | } else if ("SCRIPT" == (type + "").toUpperCase()) { 296 | $.ajax({type: "GET", 297 | url: url + "?" + buildNumber, 298 | dataType: "script", 299 | cache: true, 300 | success: function () { 301 | //console.debug("initialize loaded:" + url); 302 | deferred.resolve() 303 | }, 304 | error: function () { 305 | //console.debug("initialize failed:" + url); 306 | deferred.reject(); 307 | } 308 | }); 309 | 310 | 311 | } else { 312 | //console.debug(url+" as DOM"); 313 | //var text = getContent(url); 314 | url = url + (url.indexOf("?") > -1 ? "&" : "?") + buildNumber; 315 | var text = $.ajax({ 316 | type: "GET", 317 | url: url, 318 | dataType: "html", 319 | cache: true, 320 | success: function (text) { 321 | //console.debug("initialize loaded:" + url); 322 | ndo = ndo || $("body"); 323 | ndo.append(text); 324 | deferred.resolve() 325 | }, 326 | error: function () { 327 | //console.debug("initialize failed:" + url); 328 | deferred.reject(); 329 | } 330 | }); 331 | } 332 | } 333 | 334 | return __initedComponents[normUrl].promise(); 335 | } 336 | 337 | 338 | /** 339 | * callback receive event, data 340 | * data.response contiene la response json arrivata dal controller 341 | * E.G.: 342 | * $("body").trigger("worklogEvent",[{type:"delete",response:response}]) 343 | * 344 | * in caso di delete di solito c'è il response.deletedId 345 | */ 346 | function registerEvent(eventName,callback) { 347 | $("body").off(eventName).on(eventName, callback); 348 | } 349 | 350 | 351 | function openPersistentFile(file) { 352 | //console.debug("openPersistentFile",file); 353 | var t=window.self; 354 | try{ 355 | if(window.top != window.self) 356 | t=window.top; 357 | } catch(e) {} 358 | 359 | if (file.mime.indexOf("image") >= 0) { 360 | var img = $("").prop("src", file.url).css({position: "absolute", top: "-10000px", left: "-10000px"}).one("load", function () { 361 | //console.debug("image loaded"); 362 | var img = $(this); 363 | var w = img.width(); 364 | var h = img.height(); 365 | //console.debug("image loaded",w,h); 366 | var f=w/h; 367 | var ww = $(t).width()*.8; 368 | var wh = $(t).height()*.8; 369 | if (w>ww){ 370 | w=ww; 371 | h=w/f; 372 | } 373 | if (h>wh){ 374 | h=wh; 375 | w=h*f; 376 | } 377 | 378 | var hasTop=false; 379 | img.width(w).height(h).css({position: "static", top: 0, left: 0}); 380 | 381 | t.createModalPopup(w+100,h+100).append(img); 382 | }); 383 | t.$("body").append(img); 384 | } else if (file.mime.indexOf("pdf") >= 0) { 385 | t.openBlackPopup(file.url, $(t).width()*.8, $(t).height()*.8); 386 | } else { 387 | window.open(file.url + "&TREATASATTACH=yes"); 388 | } 389 | } 390 | 391 | 392 | function wrappedEvaluer(toEval){ 393 | eval(toEval); 394 | } 395 | 396 | function evalInContext(stringToEval,context){ 397 | wrappedEvaluer.apply(context,[stringToEval]); 398 | } 399 | 400 | 401 | Storage.prototype.setObject = function(key, value) { 402 | this.setItem(key, JSON.stringify(value)); 403 | }; 404 | 405 | Storage.prototype.getObject = function(key) { 406 | return this.getItem(key) && JSON.parse(this.getItem(key)); 407 | }; 408 | 409 | function objectSize(size) { 410 | var divisor = 1; 411 | var unit = "bytes"; 412 | if (size >= 1024 * 1024) { 413 | divisor = 1024 * 1024; 414 | unit = "MB"; 415 | } else if (size >= 1024) { 416 | divisor = 1024; 417 | unit = "KB"; 418 | } 419 | if (divisor == 1) 420 | return size + " " + unit; 421 | 422 | return (size / divisor).toFixed(2) + ' ' + unit; 423 | } 424 | 425 | 426 | function htmlEncode(value){ 427 | //create a in-memory div, set it's inner text(which jQuery automatically encodes) 428 | //then grab the encoded contents back out. The div never exists on the page. 429 | return $('
').text(value).html(); 430 | } 431 | 432 | function htmlLinearize(value, length){ 433 | value = value.replace(/(\r\n|\n|\r)/gm,"").replace(/
/g, " - "); 434 | value = value.replace(/- -/g, "-"); 435 | 436 | var ret = $('
').text(value).text(); 437 | 438 | if(length){ 439 | var ellips = ret.length > length ? "..." : ""; 440 | ret = ret.substring(0,length) + ellips; 441 | } 442 | 443 | return ret; 444 | } 445 | 446 | function htmlDecode(value){ 447 | return $('
').html(value).text(); 448 | } 449 | 450 | 451 | 452 | function createCookie(name,value,days) { 453 | if (days) { 454 | var date = new Date(); 455 | date.setTime(date.getTime()+(days*24*60*60*1000)); 456 | var expires = "; expires="+date.toGMTString(); 457 | } 458 | else var expires = ""; 459 | document.cookie = name+"="+value+expires+"; path=/"; 460 | } 461 | 462 | function readCookie(name) { 463 | var nameEQ = name + "="; 464 | var ca = document.cookie.split(';'); 465 | for(var i=0;i < ca.length;i++) { 466 | var c = ca[i]; 467 | while (c.charAt(0)==' ') c = c.substring(1,c.length); 468 | if (c.indexOf(nameEQ) == 0) return c.substring(nameEQ.length,c.length); 469 | } 470 | return null; 471 | } 472 | 473 | function eraseCookie(name) { 474 | createCookie(name,"",-1); 475 | } 476 | 477 | 478 | 479 | function getParameterByName(name, url) { 480 | if (!url) url = window.location.href; 481 | name = name.replace(/[\[\]]/g, "\\$&"); 482 | var regex = new RegExp("[?&]" + name + "(=([^&#]*)|&|#|$)"), 483 | results = regex.exec(url); 484 | if (!results) return null; 485 | if (!results[2]) return ''; 486 | return decodeURIComponent(results[2].replace(/\+/g, " ")); 487 | } 488 | 489 | $.fn.isEmptyElement = function( ){ 490 | return !$.trim($(this).html()) 491 | }; 492 | 493 | //workaround for jquery 3.x 494 | if (typeof ($.fn.size)!="funcion") 495 | $.fn.size=function(){return this.length}; -------------------------------------------------------------------------------- /license.txt: -------------------------------------------------------------------------------- 1 | Copyright (c) 2019-2020 Twproject https://twproject.com 2 | Copyright (c) 2012-2018 Open Lab http://open-lab.com 3 | Written by Roberto Bicchierai and Silvia Chelazzi http://roberto.twproject.com 4 | Permission is hereby granted, free of charge, to any person obtaining 5 | a copy of this software and associated documentation files (the 6 | "Software"), to deal in the Software without restriction, including 7 | without limitation the rights to use, copy, modify, merge, publish, 8 | distribute, sublicense, and/or sell copies of the Software, and to 9 | permit persons to whom the Software is furnished to do so, subject to 10 | the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be 13 | included in all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 16 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 17 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 18 | NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 19 | LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 20 | OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 21 | WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 22 | -------------------------------------------------------------------------------- /platform.css: -------------------------------------------------------------------------------- 1 | @font-face { 2 | font-family: 'TeamworkRegular'; 3 | src: url('res/icons.eot?5qjga5'); 4 | src: url('res/icons.eot?#iefix5qjga5') format('embedded-opentype'), 5 | url('res/icons.woff?5qjga5') format('woff'), 6 | url('res/icons.ttf?5qjga5') format('truetype'), 7 | url('res/icons.svg?5qjga5#icons') format('svg'); 8 | font-weight: normal !important; 9 | font-style: normal; 10 | } 11 | 12 | * { 13 | -webkit-box-sizing: border-box; 14 | -moz-box-sizing: border-box; 15 | -o-box-sizing: border-box; 16 | box-sizing: border-box; 17 | } 18 | 19 | /* 20 | ------------------------------------------------------- 21 | body styles 22 | ------------------------------------------------------- 23 | */ 24 | BODY, TBODY { 25 | font-family: "HelveticaNeue-Light", "Helvetica Neue Light", "Helvetica Neue", Helvetica, Arial, "Lucida Grande", sans-serif; 26 | /*font-family: 'Open Sans', sans-serif;*/ 27 | font-size: 14px; 28 | margin: 0; 29 | color: #1e2f41; 30 | text-decoration: none; 31 | } 32 | 33 | a { 34 | text-decoration: none; 35 | font-weight: bold; 36 | /*color: #16ABDD;*/ 37 | color: #2b9af3; 38 | text-rendering: optimizelegibility; 39 | -webkit-font-smoothing: antialiased; 40 | -moz-font-smoothing: antialiased; 41 | 42 | } 43 | 44 | a:hover, a.aHover { 45 | color: #0C85AD; 46 | color: #2575be; 47 | text-decoration: underline; 48 | } 49 | 50 | h1 { 51 | font-size: 32px; 52 | line-height: 34px; 53 | color: #91B4B7; 54 | font-weight: normal; 55 | margin: 0 0 10px 0 56 | } 57 | 58 | h2 { 59 | font-size: 28px; 60 | color: #34495e; 61 | font-weight: normal; 62 | margin: 0 0 10px 0 63 | } 64 | 65 | h3 { 66 | text-decoration: none; 67 | color: #1e2f41; 68 | font-size: 16px; 69 | margin: 0; 70 | } 71 | 72 | h4 { 73 | font-size: 16px; 74 | padding: 5px 0; 75 | color: #617777; 76 | margin: 0 77 | } 78 | 79 | #savingMessage { 80 | background-color: #E3EDED; 81 | display: none; 82 | color: #617777; 83 | font-weight: bolder; 84 | position: fixed; 85 | top: 0; 86 | left: 50%; 87 | width: 200px; 88 | text-align: center; 89 | margin-left: -100px; 90 | padding: 5px 0; 91 | z-index: 1000000; 92 | box-shadow: 0 3px 2px rgba(0, 0, 0, 0.4); 93 | -moz-box-shadow: 0 3px 2px rgba(0, 0, 0, 0.4); 94 | -webkit-box-shadow: 0 3px 2px rgba(0, 0, 0, 0.4); 95 | -o-box-shadow: 0 3px 2px rgba(0, 0, 0, 0.4); 96 | } 97 | 98 | .waiting { 99 | cursor: progress; 100 | } 101 | 102 | /* 103 | ------------------------------------------------------- 104 | teamwork icon 105 | ------------------------------------------------------- 106 | */ 107 | 108 | .teamworkIcon { 109 | font-family: 'TeamworkRegular' !important; 110 | color: #34495e; 111 | font-weight: normal; 112 | font-size: 120%; 113 | font-style: normal !important; 114 | text-rendering: optimizelegibility; 115 | -webkit-font-smoothing: antialiased; 116 | -moz-font-smoothing: antialiased; 117 | 118 | } 119 | 120 | .teamworkIcon:hover { 121 | opacity: .8 122 | } 123 | 124 | .teamworkIcon.withLabel { 125 | padding-right: 5px; 126 | } 127 | 128 | .button:hover .teamworkIcon { 129 | opacity: 0.8 130 | } 131 | 132 | .teamworkIcon.alert { 133 | color: #B61E2D; 134 | } 135 | 136 | .del { 137 | color: #ff7271 138 | } 139 | 140 | .cvcColorSquare { 141 | display: inline-block; 142 | text-align: left; 143 | border: #fff 0px solid; 144 | box-shadow: 0px 0px 5px #999; 145 | -moz-box-shadow: 2px 2px 2px #999; 146 | -webkit-box-shadow: 0px 0px 5px #999; 147 | -o-box-shadow: 0px 0px 5px #999; 148 | text-indent: 10px; 149 | border-radius: 5px; 150 | cursor: pointer; 151 | } 152 | 153 | .cvcColorSquare:hover { 154 | opacity: .7; 155 | } 156 | 157 | .unselectable { 158 | -webkit-user-select: none; 159 | -khtml-user-select: none; 160 | -moz-user-select: none; 161 | -o-user-select: none; 162 | user-select: none; 163 | } 164 | 165 | .ui-resizable { 166 | position: relative; 167 | } 168 | 169 | .ui-resizable-handle { 170 | position: absolute; 171 | font-size: 0.1px; 172 | z-index: 99999; 173 | display: block; 174 | } 175 | 176 | .ui-resizable-disabled .ui-resizable-handle, .ui-resizable-autohide .ui-resizable-handle { 177 | display: none; 178 | } 179 | 180 | .ui-resizable-n { 181 | cursor: n-resize; 182 | height: 7px; 183 | width: 100%; 184 | top: -5px; 185 | left: 0; 186 | } 187 | 188 | .ui-resizable-s { 189 | cursor: s-resize; 190 | height: 7px; 191 | width: 100%; 192 | bottom: -5px; 193 | left: 0; 194 | } 195 | 196 | .ui-resizable-e { 197 | cursor: e-resize; 198 | width: 7px; 199 | right: -5px; 200 | top: 0; 201 | height: 100%; 202 | } 203 | 204 | .ui-resizable-w { 205 | cursor: w-resize; 206 | width: 7px; 207 | left: -5px; 208 | top: 0; 209 | height: 100%; 210 | } 211 | 212 | .ui-resizable-se { 213 | cursor: se-resize; 214 | width: 12px; 215 | height: 12px; 216 | right: 1px; 217 | bottom: 1px; 218 | } 219 | 220 | .ui-resizable-sw { 221 | cursor: sw-resize; 222 | width: 9px; 223 | height: 9px; 224 | left: -5px; 225 | bottom: -5px; 226 | } 227 | 228 | .ui-resizable-nw { 229 | cursor: nw-resize; 230 | width: 9px; 231 | height: 9px; 232 | left: -5px; 233 | top: -5px; 234 | } 235 | 236 | .ui-resizable-ne { 237 | cursor: ne-resize; 238 | width: 9px; 239 | height: 9px; 240 | right: -5px; 241 | top: -5px; 242 | } 243 | 244 | /* 245 | ------------------------------------------------------- 246 | table styles 247 | ------------------------------------------------------- 248 | */ 249 | 250 | .table { 251 | width: 100%; 252 | } 253 | 254 | TH, .tableHeader { 255 | font-weight: normal; 256 | color: #555; 257 | border: none; 258 | background-color: #f0f0f0; 259 | padding: 2px 260 | } 261 | 262 | .list td{ 263 | border-bottom: 1px solid #dedede; 264 | padding: 5px 0; 265 | } 266 | 267 | .list th { 268 | padding: 5px 2px 269 | } 270 | 271 | .row em {font-style: normal;color: #a2a2a2} 272 | 273 | 274 | .ganttTaskEditor h2 { 275 | text-transform: capitalize 276 | 277 | } 278 | 279 | .ganttTaskEditor .formElements, 280 | .resourceEditor .formElements { 281 | background-color: #F5F5F5; 282 | border-color: #CECECE 283 | } 284 | 285 | table .resRow td, table .assigEditRow td { 286 | border-bottom: 1px solid #cecece; 287 | padding: 5px 0 288 | } 289 | 290 | 291 | 292 | 293 | /* 294 | ------------------------------------------------------- 295 | Gantt Online 296 | ------------------------------------------------------- 297 | */ 298 | 299 | 300 | .servicesEnroll h2 { 301 | margin-bottom: 20px 302 | } 303 | 304 | .heading { 305 | text-align: center; 306 | } 307 | .heading img { 308 | display:block; 309 | margin: -20px auto 30px; 310 | } 311 | 312 | 313 | .twAds { 314 | height: 38px; 315 | background-color: #5ACADF; 316 | width: 100%; 317 | /*background-image: url("../../img/twAdBg.png");*/ 318 | text-align: center; 319 | color: #fff; 320 | z-index: 1000; 321 | } 322 | 323 | .twAds.light { 324 | padding-top: 8px 325 | } 326 | 327 | .twAds .twitterButton { 328 | vertical-align: middle; 329 | display: inline-block; 330 | margin-left: 15px 331 | } 332 | 333 | .twAds .remove { 334 | display: inline-block; 335 | line-height: 38px; 336 | color: #fff; 337 | cursor: pointer; 338 | position: absolute; 339 | top:0; 340 | right: 12px 341 | } 342 | 343 | .twAds a { 344 | color: #fff; 345 | border-bottom: 1px solid rgba(255, 255, 255, 0.40) 346 | } 347 | 348 | .twAds a:hover { 349 | text-decoration: none 350 | } 351 | 352 | .servicesEnroll .oauth { 353 | width: 90px; 354 | height: auto; 355 | } 356 | 357 | .servicesEnroll .oauth:hover { 358 | opacity: .8 359 | } 360 | 361 | .errImg img { 362 | width: 25px; 363 | height: auto; 364 | vertical-align: middle; 365 | } 366 | 367 | #__FEEDBACKMESSAGEPLACE { 368 | position: absolute; 369 | background-color: #fafad2; 370 | } 371 | 372 | .adminLogin .formElements { 373 | width: 120px; 374 | } 375 | 376 | .adminLogin { 377 | width: 350px; 378 | margin: 0 auto; 379 | position: absolute; 380 | bottom: 10px; 381 | left: 20px; 382 | } 383 | 384 | .lastMod { 385 | font-style: italic; 386 | margin-right: 10px; 387 | vertical-align: middle; 388 | display: block; 389 | color: #D37E00; 390 | font-size: 12px; 391 | position: fixed; 392 | bottom: 25px; 393 | z-index: 20; 394 | padding: 5px 10px; 395 | background-color: rgba(255, 255, 0, 0.16); 396 | } 397 | 398 | .lastMod .teamworkIcon { 399 | color: #34495e; 400 | font-size: 160%; 401 | vertical-align: middle; 402 | } 403 | 404 | .button.textual, 405 | .button.buttonImg, 406 | .ganttButtonSeparator { 407 | vertical-align: middle; 408 | } 409 | 410 | .button span.teamworkIcon { 411 | font-size: .95em; 412 | } 413 | 414 | .clearfix:after { 415 | visibility: hidden; 416 | display: block; 417 | font-size: 0; 418 | content: " "; 419 | clear: both; 420 | height: 0; 421 | } 422 | 423 | 424 | .embedCode { 425 | font-family: Consolas,monospace!important; 426 | font-size: 100%; 427 | width: 100%; 428 | color: #2792E6; 429 | padding: 10px; 430 | border: 4px solid #d0d0d0 431 | } 432 | 433 | .ruler { 434 | width: 100%; 435 | display: block; 436 | padding: 35px 0 35px; 437 | height: 1px; 438 | } 439 | 440 | .ruler.short span { 441 | width: 100px; 442 | height: 1px; 443 | display: block; 444 | margin: 0 auto; 445 | border-bottom:1px solid #ccc 446 | } 447 | 448 | 449 | .clearfix { display: inline-block; } 450 | /* start commented backslash hack \*/ 451 | * html .clearfix { height: 1%; } 452 | .clearfix { display: block; } 453 | /* close commented backslash hack */ 454 | 455 | 456 | 457 | /* 458 | ------------------------------------------------------- 459 | Buttons 460 | ------------------------------------------------------- 461 | */ 462 | 463 | .buttonBar { 464 | } 465 | 466 | .buttonBar.centered { 467 | text-align: center 468 | } 469 | 470 | .buttonBar.block .button { 471 | margin: 0 0 20px 472 | } 473 | 474 | 475 | .button { 476 | display: inline-block; 477 | font-size: 110%; 478 | color: #fff; 479 | cursor: pointer; 480 | background-color: #34495e; 481 | -moz-border-radius: 5px; 482 | -webkit-border-radius: 5px; 483 | -o-border-radius: 5px; 484 | border-radius: 5px; 485 | border: 1px solid rgba(0, 0, 0, 0.2); 486 | padding: 5px 12px 8px; 487 | margin-bottom: 10px; 488 | margin-right: 10px; 489 | text-align: center; 490 | -webkit-transition: background-color 500ms ease-out 1s; 491 | -moz-transition: background-color 500ms ease-out 1s; 492 | -o-transition: background-color 500ms ease-out 1s; 493 | transition: background-color 500ms ease-out 1s; 494 | } 495 | 496 | .button.first { 497 | background-color: #75a800; 498 | font-weight: bold; 499 | } 500 | 501 | .button.small { 502 | font-size: 100%; 503 | padding: 2px 7px 4px; 504 | margin-bottom: 0 505 | 506 | } 507 | 508 | .large { 509 | font-size: 160%; 510 | padding: 5px 14px 8px; 511 | border-radius: 6px 512 | } 513 | 514 | 515 | 516 | .button.first:hover { 517 | background-color: #2F2F2F; 518 | } 519 | 520 | .button[disabled] { 521 | cursor: default; 522 | opacity: 0.4 523 | } 524 | 525 | .button:hover[disabled] { 526 | background-color: #BABABA 527 | } 528 | 529 | .button.textual, .button.buttonImg { 530 | border: none; 531 | background-color: transparent; 532 | color: #68979B; 533 | -moz-border-radius: 0; 534 | -webkit-border-radius: 0; 535 | -o-border-radius: 0; 536 | border-radius: 0; 537 | padding: 0; 538 | margin: 0; 539 | text-align: left 540 | } 541 | 542 | .button.opt { 543 | background-color: #009E94; 544 | background-color: #2792E6; 545 | } 546 | 547 | .button.edit { 548 | color: #009E94; 549 | padding: 0; 550 | margin: 0 551 | } 552 | 553 | .button.delete { 554 | color: #B61E2D; 555 | padding: 0; 556 | margin: 0 557 | } 558 | 559 | .button:hover { 560 | background-color: #506b84; 561 | color: rgba(255, 255, 255, 0.75); 562 | } 563 | 564 | a.button:hover { 565 | text-decoration: none 566 | } 567 | 568 | .button.textual:hover, .button.buttonImg:hover { 569 | background-color: transparent; 570 | } 571 | 572 | span.separator { 573 | display: inline-block; 574 | } 575 | 576 | .button.add { 577 | color: #009E94; 578 | } 579 | 580 | .button.add .teamworkIcon { 581 | color: #009E94; 582 | } 583 | 584 | form { 585 | margin: 0; 586 | padding: 0; 587 | } 588 | 589 | select { 590 | border: 1px solid #91B4B7; 591 | padding: 4px; 592 | font-size: 16px; 593 | font-family: "HelveticaNeue-Light", "Helvetica Neue Light", "Helvetica Neue", Helvetica, Arial, "Lucida Grande", sans-serif; 594 | } 595 | 596 | .formElements { 597 | background-color: white; 598 | padding: 4px; 599 | font-size: 16px; 600 | border: 1px solid #91B4B7; 601 | -moz-border-radius: 3px; 602 | -webkit-border-radius: 3px; 603 | -o-border-radius: 3px; 604 | border-radius: 3px; 605 | font-family: "HelveticaNeue-Light", "Helvetica Neue Light", "Helvetica Neue", Helvetica, Arial, "Lucida Grande", sans-serif; 606 | } 607 | 608 | .formElementsError { 609 | border: 1px solid #ff0000; 610 | } 611 | 612 | .formElementExclamation { 613 | width: 15px; 614 | height: 25px; 615 | margin-left: -20px; 616 | position: absolute; 617 | background: url("../../applications/gantt/distrib/res/alert.gif") no-repeat; 618 | } 619 | 620 | span#FLD_LOGIN_NAMEerror, span#FLD_PWDerror { 621 | margin-left: -23px; 622 | margin-top: 2px; 623 | } 624 | 625 | input { 626 | background-color: white; 627 | padding: 4px; 628 | font-size: 16px; 629 | border: 1px solid #91B4B7; 630 | -moz-border-radius: 3px; 631 | -webkit-border-radius: 3px; 632 | -o-border-radius: 3px; 633 | border-radius: 3px; 634 | font-family: "HelveticaNeue-Light", "Helvetica Neue Light", "Helvetica Neue", Helvetica, Arial, "Lucida Grande", sans-serif; 635 | } 636 | 637 | .confirmBox { 638 | display: inline; 639 | z-index: 10000; 640 | vertical-align: middle; 641 | text-align: center; 642 | font-style: italic; 643 | color: #777; 644 | background: #fff; 645 | position: absolute; 646 | margin: 0 auto 647 | } 648 | 649 | 650 | 651 | .confirmBox .confirmNo { 652 | color: #e06060; 653 | cursor: pointer; 654 | font-weight: bolder; 655 | } 656 | 657 | .confirmBox .confirmYes { 658 | color: #68af6c; 659 | cursor: pointer; 660 | font-weight: bolder; 661 | } 662 | 663 | .blackpopup { 664 | padding: 20px; 665 | border-radius: 10px; 666 | } 667 | 668 | .smallPopUp { 669 | top:0!important; 670 | margin-top:0!important; 671 | } 672 | 673 | iframe#bwinPopup { 674 | border-radius: 10px; 675 | } 676 | 677 | .mainWrap { 678 | padding: 20px 679 | } 680 | 681 | .mainWrap > h2:first-of-type { 682 | text-transform: capitalize 683 | } 684 | 685 | 686 | /******** SHARE BOX *********/ 687 | 688 | .shareBar { 689 | position: absolute; 690 | right: 100px; 691 | top: 0; 692 | } 693 | 694 | .shareBar img:hover { 695 | opacity: 0.8; 696 | } 697 | 698 | .shareBtn { 699 | background: none repeat scroll 0 0 #F9F7F7; 700 | border: 1px solid rgba(0, 0, 0, 0.24); 701 | border-radius: 3px; 702 | color: #878686; 703 | display: inline-block; 704 | font-family: sans-serif; 705 | font-size: 12px; 706 | padding: 4px 8px 4px 14px; 707 | text-decoration: none; 708 | } 709 | 710 | .shareBtn { 711 | cursor: pointer; 712 | } 713 | 714 | .shareBtn:hover { 715 | border: 1px solid rgba(0, 0, 0, 0.24); 716 | color: #878686; 717 | opacity: .7; 718 | } 719 | 720 | .shareBtn img { 721 | border: 0 none; 722 | padding-right: 5px; 723 | vertical-align: middle; 724 | } 725 | 726 | .shareBtn a { 727 | color: #888; 728 | text-decoration: none; 729 | } 730 | 731 | #shareBox { 732 | text-align: center 733 | } 734 | 735 | #shareBox h2 { 736 | margin-bottom: 30px; 737 | } 738 | 739 | 740 | #shareBox .shareBtn { 741 | padding: 15px 20px; 742 | font-size: 30px; 743 | } 744 | 745 | #shareBox .shareBtn.icon-facebook { 746 | background-color:#3b5998; 747 | color: #fff; 748 | } 749 | 750 | #shareBox .shareBtn.icon-twitter { 751 | background-color:#00aced; 752 | color: #fff; 753 | } 754 | 755 | #shareBox .shareBtn.icon-linkedin { 756 | background-color:#007bb6; 757 | color: #fff; 758 | } 759 | #shareBox .shareBtn.icon-gplus { 760 | background-color:#dd4b39; 761 | color: #fff; 762 | } 763 | 764 | #shareBox .shareBtn span { 765 | display: none; 766 | } 767 | 768 | 769 | /*------------------------------------------------- MODAL POPUP (ex blackPopup) ------------------------------------------------------*/ 770 | .modalPopup { 771 | position:fixed; 772 | top:0; 773 | left:0; 774 | width:100%; 775 | height:100%; 776 | background-color:rgba(255,255,255,.8); 777 | z-index: 100; 778 | } 779 | 780 | .modalPopup.upgradeMessage { 781 | top:40px; 782 | text-align: center; 783 | } 784 | 785 | .modalPopup.upgradeMessage p { 786 | margin-bottom: 20px; 787 | line-height: 1.6em; 788 | } 789 | 790 | .modalPopup.inIframe { 791 | background-color:rgba(255,255,255,0); 792 | } 793 | 794 | .modalPopup.black { 795 | background-color: rgba(75, 75, 75, 0.6); 796 | } 797 | 798 | .modalPopup .bwinPopupd{ 799 | position: relative; 800 | box-shadow: 0 0 0 4px rgba(46, 186, 255, 0.3); 801 | border: 1px solid rgba(127, 127, 127, 0.3); 802 | background-color:#fff; 803 | margin:auto; 804 | padding: 30px 30px; 805 | border-radius: 5px; 806 | } 807 | 808 | .modalPopup .popUpClose{ 809 | z-index: 9; 810 | color: #2f2f2f; 811 | width: 20px; 812 | height: 20px; 813 | text-align: center; 814 | line-height: 20px; 815 | right: 15px; 816 | top:15px; 817 | } 818 | 819 | .modalPopup.black .bwinPopupd .popUpClose{ 820 | color: #ffffff; 821 | } 822 | 823 | .modalPopup.iframe .bwinPopupd { 824 | overflow: hidden; 825 | padding: 0; 826 | } 827 | 828 | .modalPopup.iframe .bwinPopupd iframe { 829 | position: absolute; 830 | border-radius: 5px; 831 | } 832 | 833 | .modalPopup.inIframe .bwinPopupd { 834 | background-color: #f9f9f9; 835 | border-radius: 0 0 5px 5px; 836 | } 837 | 838 | .offScreen { 839 | position: absolute; 840 | left: -5000px; 841 | } 842 | 843 | -------------------------------------------------------------------------------- /res/alert.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/alert.gif -------------------------------------------------------------------------------- /res/black_70.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/black_70.png -------------------------------------------------------------------------------- /res/closeBig.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/closeBig.png -------------------------------------------------------------------------------- /res/ganttSplitterGrip.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/ganttSplitterGrip.png -------------------------------------------------------------------------------- /res/hasExternalDeps.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/hasExternalDeps.png -------------------------------------------------------------------------------- /res/icons.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/icons.eot -------------------------------------------------------------------------------- /res/icons.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/icons.ttf -------------------------------------------------------------------------------- /res/icons.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/icons.woff -------------------------------------------------------------------------------- /res/indentIcon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/indentIcon.png -------------------------------------------------------------------------------- /res/linkArrow.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/linkArrow.png -------------------------------------------------------------------------------- /res/milestone.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/milestone.png -------------------------------------------------------------------------------- /res/toggle-expand.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/toggle-expand.png -------------------------------------------------------------------------------- /res/toggle_collapse.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/toggle_collapse.png -------------------------------------------------------------------------------- /res/twBanner.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/twBanner.jpg -------------------------------------------------------------------------------- /res/twGanttLogo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/twGanttLogo.png -------------------------------------------------------------------------------- /res/twproject-badge.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/robicch/jQueryGantt/6b45a9c5041b3a72a8815fa5e8fb866714bf7d29/res/twproject-badge.png --------------------------------------------------------------------------------