1;(function(){ 2 3if (BX.date) 4 return; 5 6BX.date = BX.Main.Date; 7 8/************************************** calendar class **********************************/ 9 10var obCalendarSingleton = null; 11 12/* 13params: { 14 node: bind element || document.body 15 16 value - start value in site format (using 'field' param if 'value' does not exist) 17 callback - date check handler. can return false to prevent calendar closing. 18 callback_after - another handler, called after date picking 19 20 field - field to read/write data 21 22 bTime = true - whether to enable time control 23 bHideTime = false - whether to hide time control by default 24 25 currentTime - current UTC time() 26 27} 28*/ 29 30 31BX.calendar = function(params) 32{ 33 return BX.calendar.get().Show(params); 34}; 35 36BX.calendar.get = function() 37{ 38 if (!obCalendarSingleton) 39 obCalendarSingleton = new BX.JCCalendar(); 40 41 return obCalendarSingleton; 42}; 43 44// simple func for compatibility with the oldies 45BX.calendar.InsertDaysBack = function(input, days) 46{ 47 if (days != '') 48 { 49 var d = new Date(); 50 if(days > 0) 51 { 52 d.setTime(d.valueOf() - days*86400000); 53 } 54 55 input.value = BX.date.format(BX.date.convertBitrixFormat(BX.message('FORMAT_DATE')), d, null); 56 } 57 else 58 { 59 input.value = ''; 60 } 61}; 62 63BX.calendar.ValueToString = function(value, bTime, bUTC) 64{ 65 return BX.date.format( 66 BX.date.convertBitrixFormat(BX.message(bTime ? 'FORMAT_DATETIME' : 'FORMAT_DATE')), 67 value, 68 null, 69 !!bUTC 70 ); 71}; 72 73BX.calendar.ValueToStringFormat = function(value, bitrixFormat, bUTC) 74{ 75 return BX.date.format( 76 BX.date.convertBitrixFormat(bitrixFormat), 77 value, 78 null, 79 !!bUTC 80 ); 81}; 82 83 84BX.CalendarPeriod = 85{ 86 Init: function(inputFrom, inputTo, selPeriod) 87 { 88 if((inputFrom.value != "" || inputTo.value != "") && selPeriod.value == "") 89 selPeriod.value = "interval"; 90 91 selPeriod.onchange(); 92 }, 93 94 ChangeDirectOpts: function(peroidValue, selPParent) // "week" || "others" 95 { 96 var selDirect = BX.findChild(selPParent, {'className':'adm-select adm-calendar-direction'}, true); 97 98 if(peroidValue == "week") 99 { 100 selDirect.options[0].text = BX.message('JSADM_CALEND_PREV_WEEK'); 101 selDirect.options[1].text = BX.message('JSADM_CALEND_CURR_WEEK'); 102 selDirect.options[2].text = BX.message('JSADM_CALEND_NEXT_WEEK'); 103 } 104 else 105 { 106 selDirect.options[0].text = BX.message('JSADM_CALEND_PREV'); 107 selDirect.options[1].text = BX.message('JSADM_CALEND_CURR'); 108 selDirect.options[2].text = BX.message('JSADM_CALEND_NEXT'); 109 } 110 }, 111 112 SaveAndClearInput: function(oInput) 113 { 114 if(!window.SavedPeriodValues) 115 window.SavedPeriodValues = {}; 116 117 window.SavedPeriodValues[oInput.id] = oInput.value; 118 oInput.value=""; 119 }, 120 121 RestoreInput: function(oInput) 122 { 123 if(!window.SavedPeriodValues || !window.SavedPeriodValues[oInput.id]) 124 return; 125 126 oInput.value = window.SavedPeriodValues[oInput.id]; 127 delete(window.SavedPeriodValues[oInput.id]); 128 }, 129 130 OnChangeP: function(sel) 131 { 132 var selPParent = sel.parentNode.parentNode; 133 var bShowFrom, bShowTo, bShowDirect, bShowSeparate; 134 bShowFrom = bShowTo = bShowDirect = bShowSeparate = false; 135 136 var inputFromWrap = BX.findChild(selPParent, {'className':'adm-input-wrap adm-calendar-inp adm-calendar-first'}); 137 var inputToWrap = BX.findChild(selPParent, {'className':'adm-input-wrap adm-calendar-second'}); 138 var selDirectWrap = BX.findChild(selPParent, {'className':'adm-select-wrap adm-calendar-direction'}); 139 var separator = BX.findChild(selPParent, {'className':'adm-calendar-separate'}); 140 var inputFrom = BX.findChild(selPParent, {'className':'adm-input adm-calendar-from'},true); 141 var inputTo = BX.findChild(selPParent, {'className':'adm-input adm-calendar-to'},true); 142 143 // define who must be shown 144 switch (sel.value) 145 { 146 case "day": 147 case "week": 148 case "month": 149 case "quarter": 150 case "year": 151 bShowDirect=true; 152 BX.CalendarPeriod.OnChangeD(selDirectWrap.children[0]); 153 break; 154 155 case "before": 156 bShowTo = true; 157 break; 158 159 case "after": 160 bShowFrom = true; 161 break; 162 163 case "exact": 164 bShowFrom= true; 165 break; 166 167 case "interval": 168 bShowFrom = bShowTo = bShowSeparate = true; 169 BX.CalendarPeriod.RestoreInput(inputFrom); 170 BX.CalendarPeriod.RestoreInput(inputTo); 171 172 break; 173 174 case "": 175 BX.CalendarPeriod.SaveAndClearInput(inputFrom); 176 BX.CalendarPeriod.SaveAndClearInput(inputTo); 177 break; 178 179 default: 180 break; 181 182 } 183 184 BX.CalendarPeriod.ChangeDirectOpts(sel.value, selPParent); 185 186 inputFromWrap.style.display = (bShowFrom? 'inline-block':'none'); 187 inputToWrap.style.display = (bShowTo? 'inline-block':'none'); 188 selDirectWrap.style.display = (bShowDirect? 'inline-block':'none'); 189 separator.style.display = (bShowSeparate? 'inline-block':'none'); 190 }, 191 192 193 OnChangeD: function(sel) 194 { 195 var selPParent = sel.parentNode.parentNode; 196 var inputFrom = BX.findChild(selPParent, {'className':'adm-input adm-calendar-from'},true); 197 var inputTo = BX.findChild(selPParent, {'className':'adm-input adm-calendar-to'},true); 198 var selPeriod = BX.findChild(selPParent, {'className':'adm-select adm-calendar-period'},true); 199 200 var offset=0; 201 202 switch (sel.value) 203 { 204 case "previous": 205 offset = -1; 206 break; 207 208 case "next": 209 offset = 1; 210 break; 211 212 case "current": 213 default: 214 break; 215 216 } 217 218 var from = false;
219 var to = false; 220 221 var today = new Date(); 222 var year = today.getFullYear(); 223 var month = today.getMonth(); 224 var day = today.getDate(); 225 var dayW = today.getDay(); 226 227 if (dayW == 0) 228 dayW = 7; 229 230 switch (selPeriod.value) 231 { 232 case "day": 233 from = new Date(year, month, day+offset, 0, 0, 0); 234 to = new Date(year, month, day+offset, 23, 59, 59); 235 break; 236 237 case "week": 238 from = new Date(year, month, day-dayW+1+offset*7, 0, 0, 0); 239 to = new Date(year, month, day+(7-dayW)+offset*7, 23, 59, 59); 240 break; 241 242 case "month": 243 from = new Date(year, month+offset, 1, 0, 0, 0); 244 to = new Date(year, month+1+offset, 0, 23, 59, 59); 245 break; 246 247 case "quarter": 248 var quarterNum = Math.floor((month/3))+offset; 249 from = new Date(year, 3*(quarterNum), 1, 0, 0, 0); 250 to = new Date(year, 3*(quarterNum+1), 0, 23, 59, 59); 251 break; 252 253 case "year": 254 from = new Date(year+offset, 0, 1, 0, 0, 0); 255 to = new Date(year+1+offset, 0, 0, 23, 59, 59); 256 break; 257 258 default: 259 break; 260 } 261 262 var format = window[inputFrom.name+"_bTime"] ? BX.message('FORMAT_DATETIME') : BX.message('FORMAT_DATE'); 263 264 if(from) 265 { 266 inputFrom.value = BX.formatDate(from, format); 267 BX.addClass(inputFrom,"adm-calendar-inp-setted"); 268 } 269 270 if(to) 271 { 272 inputTo.value = BX.formatDate(to, format); 273 BX.addClass(inputTo,"adm-calendar-inp-setted"); 274 } 275 } 276}; 277 278 279BX.JCCalendar = function() 280{ 281 this.params = {}; 282 283 this.bAmPm = BX.isAmPmMode(); 284 285 this.popup = null; 286 this.popup_month = null; 287 this.popup_year = null; 288 this.month_popup_classname = ''; 289 this.year_popup_classname = ''; 290 this.value = null; 291 this._layers = {}; 292 this._current_layer = null; 293 294 this.DIV = null; 295 this.PARTS = {}; 296 297 this.weekStart = 0; 298 this.numRows = 6; 299 300 this._create = function(params) 301 { 302 const paramsForPopupWindow = { 303 closeByEsc: true, 304 autoHide: false, 305 content: this._get_content(), 306 bindOptions: { forceBindPosition: true }, 307 focusTrap: false, 308 }; 309 if (Boolean(params.fixed) && params.fixed) 310 { 311 paramsForPopupWindow.fixed = params.fixed; 312 } 313 314 this.popup = new BX.PopupWindow( 315 'calendar_popup_' + Math.random(), 316 params.node, 317 paramsForPopupWindow, 318 ); 319 320 BX.bind(this.popup.popupContainer, 'click', function(event) { 321 event.stopPropagation(); 322 }); 323 }; 324 325 this._auto_hide_disable = function() 326 { 327 BX.unbind(document, 'click', BX.proxy(this._auto_hide, this)); 328 }; 329 330 this._auto_hide_enable = function() 331 { 332 BX.bind(document, 'click', BX.proxy(this._auto_hide, this)); 333 }; 334 335 this._auto_hide = function(e) 336 { 337 this._auto_hide_disable(); 338 this.popup.close(); 339 }; 340 341 this._get_content = function() 342 { 343 var _layer_onclick = BX.delegate(function(e) { 344 e = e||window.event; 345 this.SetDate( 346 new Date(parseInt(BX.proxy_context.getAttribute('data-date'))), 347 (e.type === 'dblclick' || (this.params.bCompatibility && !this.params.bTimeVisibility)) 348 ) 349 }, this); 350 351 this.DIV = BX.create('DIV', { 352 props: {className: 'bx-calendar'}, 353 children: [ 354 BX.create('DIV', { 355 props: { 356 className: 'bx-calendar-header' 357 }, 358 children: [ 359 BX.create('A', { 360 attrs: {href: 'javascript:void(0)'}, 361 props: {className: 'bx-calendar-left-arrow'}, 362 events: {click: BX.proxy(this._prev, this)} 363 }), 364 365 BX.create('SPAN', { 366 props: {className: 'bx-calendar-header-content'}, 367 children: [ 368 (this.PARTS.MONTH = BX.create('A', { 369 attrs: {href: 'javascript:void(0)'}, 370 props: {className: 'bx-calendar-top-month'}, 371 events: {click: BX.proxy(this._menu_month, this)} 372 })), 373 374 (this.PARTS.YEAR = BX.create('A', { 375 attrs: {href: 'javascript:void(0)'}, 376 props: {className: 'bx-calendar-top-year'}, 377 events: {click: BX.proxy(this._menu_year, this)} 378 })) 379 ] 380 }), 381 382 BX.create('A', { 383 attrs: {href: 'javascript:void(0)'}, 384 props: {className: 'bx-calendar-right-arrow'}, 385 events: {click: BX.proxy(this._next, this)} 386 }) 387 ] 388 }), 389 390 (this.PARTS.WEEK = BX.create('DIV', { 391 props: { 392 className: 'bx-calendar-name-day-wrap' 393 } 394 })), 395 396 (this.PARTS.LAYERS = BX.create('DIV', { 397 props: { 398 className: 'bx-calendar-cell-block' 399 }, 400 events: { 401 click: BX.delegateEvent({className: 'bx-calendar-cell'}, _layer_onclick), 402 dblclick: BX.delegateEvent({className: 'bx-calendar-cell'}, _layer_onclick) 403 } 404 })), 405 406 (this.PARTS.TIME = BX.create('DIV', { 407 props: { 408 className: 'bx-calendar-set-time-wrap' 409 }, 410 events: { 411 click: BX.delegateEvent( 412 {attr: 'data-action'}, 413 BX.delegate(this._time_actions, this) 414 ) 415 }, 416 html: '<a href="javascript:void(0)" data-action="time_show" class="bx-calendar-set-time"><i></i>'+BX.message('CAL_TIME_SET')+'</a><div class="bx-calendar-form-block"><span class="bx-calendar-form-text">'+BX.message('CAL_TIME')+'</span><span class="bx-calendar-form"><input type="text" class="bx-calendar-form-input" maxwidth="2" onkeyup="BX.calendar.get()._check_time()" /><span class="bx-calendar-form-separator"></span><input type="text" class="bx-calendar-form-input" maxwidth="2" onkeyup="BX.calendar.get()._check_time()" />'+(this.bAmPm?'<span class="bx-calendar-AM-PM-block"><span class="bx-calendar-AM-PM-text" data-action="time_ampm"></span><span class="bx-calendar-form-arrow-r"><a href="javascript:void(0)" class="bx-calendar-form-arrow-top" data-action="time_ampm_up"><i></i></a><a href="javascript:void(0)" class="bx-calendar-form-arrow-bottom" data-action="time_ampm_down"><i></i></a></span></span>':'')+'</span><a href="javascript:void(0)" data-action="time_hide" class="bx-calendar-form-close"><i></i></a></div>' 417 })), 418 419 (this.PARTS.BUTTONS = BX.create('DIV', { 420 props: {className: 'bx-calendar-button-block'}, 421 events: { 422 click: BX.delegateEvent( 423 {attr: 'data-action'}, 424 BX.delegate(this._button_actions, this) 425 ) 426 }, 427 html: '<a href="javascript:void(0)" class="bx-calendar-button bx-calendar-button-select" data-action="submit"><span class="bx-calendar-button-left"></span><span class="bx-calendar-button-text">'+BX.message('CAL_BUTTON')+'</span><span class="bx-calendar-button-right"></span></a><a href="javascript:void(0)" class="bx-calendar-button bx-calendar-button-cancel" data-action="cancel"><span class="bx-calendar-button-left"></span><span class="bx-calendar-button-text">'+BX.message('JS_CORE_WINDOW_CLOSE')+'</span><span class="bx-calendar-button-right"></span></a>' 428 })) 429 ] 430 }); 431 432 this.PARTS.TIME_INPUT_H = BX.findChild(this.PARTS.TIME, {tag: 'INPUT'}, true); 433 this.PARTS.TIME_INPUT_M = this.PARTS.TIME_INPUT_H.nextSibling.nextSibling; 434 435 if (this.bAmPm) 436 this.PARTS.TIME_AMPM = this.PARTS.TIME_INPUT_M.nextSibling.firstChild; 437 438 var spinner = (new BX.JCSpinner({
439 input: this.PARTS.TIME_INPUT_H, 440 callback_change: BX.proxy(this._check_time, this), 441 bSaveValue: false 442 })).Show(); 443 spinner.className = 'bx-calendar-form-arrow-l'; 444 this.PARTS.TIME_INPUT_H.parentNode.insertBefore(spinner, this.PARTS.TIME_INPUT_H); 445 446 spinner = (new BX.JCSpinner({ 447 input: this.PARTS.TIME_INPUT_M, 448 callback_change: BX.proxy(this._check_time, this), 449 bSaveValue: true 450 })).Show(); 451 spinner.className = 'bx-calendar-form-arrow-r'; 452 if (!this.PARTS.TIME_INPUT_M.nextSibling) 453 this.PARTS.TIME_INPUT_M.parentNode.appendChild(spinner); 454 else 455 this.PARTS.TIME_INPUT_M.parentNode.insertBefore(spinner, this.PARTS.TIME_INPUT_M.nextSibling); 456 457 for (var i = 0; i < 7; i++) 458 { 459 this.PARTS.WEEK.appendChild(BX.create('SPAN', { 460 props: { 461 className: 'bx-calendar-name-day' 462 }, 463 text: BX.message('DOW_' + ((i + this.weekStart) % 7)) 464 })); 465 } 466 467 return this.DIV; 468 }; 469 470 this._time_actions = function() 471 { 472 switch (BX.proxy_context.getAttribute('data-action')) 473 { 474 case 'time_show': 475 BX.addClass(this.PARTS.TIME, 'bx-calendar-set-time-opened'); 476 if (this.params.bCompatibility) 477 { 478 BX.removeClass(this.PARTS.BUTTONS, 'bx-calendar-buttons-disabled'); 479 } 480 this.popup.adjustPosition(); 481 break; 482 case 'time_hide': 483 BX.removeClass(this.PARTS.TIME, 'bx-calendar-set-time-opened'); 484 if (this.params.bCompatibility) 485 { 486 this._saveChoice('hide'); 487 BX.addClass(this.PARTS.BUTTONS, 'bx-calendar-buttons-disabled'); 488 } 489 this.popup.adjustPosition(); 490 break; 491 case 'time_ampm': 492 this.PARTS.TIME_AMPM.innerHTML = this.PARTS.TIME_AMPM.innerHTML == 'AM' ? 'PM' : 'AM'; 493 break; 494 case 'time_ampm_up': 495 this._check_time({bSaveValue: false}, null, 12); 496 return; 497 break; 498 case 'time_ampm_down': 499 this._check_time({bSaveValue: false}, null, -12); 500 return; 501 break; 502 } 503 504 this._check_time(); 505 }; 506 507 this._button_actions = function() 508 { 509 switch (BX.proxy_context.getAttribute('data-action')) 510 { 511 case 'submit': 512 if (this.params.bCompatibility) 513 { 514 this._saveChoice('show'); 515 } 516 this.SaveValue(); 517 break; 518 case 'cancel': 519 this.Close(); 520 break; 521 } 522 }; 523 524 this._saveChoice = function(state) 525 { 526 if (this.params.bCategoryTimeVisibilityOption) 527 { 528 BX.userOptions.save( 529 this.params.bCategoryTimeVisibilityOption, 530 this.params.bNameTimeVisibilityOption, 531 'visibility', 532 (state === 'show' ? 'Y' : 'N') 533 ); 534 } 535 536 this._bTimeVisibility = (state === 'show'); 537 this.params.bTimeVisibility = this._bTimeVisibility; 538 }; 539 540 this._check_time = function(params, value, direction) 541 { 542 var h = parseInt(this.PARTS.TIME_INPUT_H.value.substring(0,5),10)||0, 543 m = parseInt(this.PARTS.TIME_INPUT_M.value.substring(0,5),10)||0, 544 bChanged = false; 545 546 if (!!params && !params.bSaveValue) 547 { 548 this.value.setUTCHours(this.value.getUTCHours() + direction); 549 } 550 else if (!isNaN(h)) 551 { 552 if (this.bAmPm) 553 { 554 if (h != 12 && this.PARTS.TIME_AMPM.innerHTML == 'PM') 555 { 556 h += 12; 557 } 558 } 559 560 bChanged = true; 561 this.value.setUTCHours(h % 24); 562 } 563 564 if (!isNaN(m)) 565 { 566 bChanged = true; 567 this.value.setUTCMinutes(m % 60); 568 } 569 570 if (bChanged) 571 { 572 this.SetValue(this.value); 573 } 574 }; 575 576 this._set_layer = function() 577 { 578 var layerId = parseInt(this.value.getUTCFullYear() + '' + BX.util.str_pad_left(this.value.getUTCMonth()+'', 2, "0")); 579 580 if (!this._layers[layerId]) 581 { 582 this._layers[layerId] = this._create_layer(); 583 this._layers[layerId].BXLAYERID = layerId; 584 } 585 586 if (this._current_layer) 587 { 588 var v = new Date(this.value.valueOf()); 589 v.setUTCHours(0); v.setUTCMinutes(0); 590 591 var cur_value = BX.findChild(this._layers[layerId], { 592 tag: 'A', 593 className: 'bx-calendar-active' 594 }, true), 595 new_value = BX.findChild(this._layers[layerId], { 596 tag: 'A', 597 attr: { 598 'data-date' : v.valueOf() + '' 599 } 600 }, true); 601 602 if (cur_value) 603 { 604 BX.removeClass(cur_value, 'bx-calendar-active'); 605 } 606 607 if (new_value) 608 { 609 BX.addClass(new_value, 'bx-calendar-active'); 610 } 611 612 this._replace_layer(this._current_layer, this._layers[layerId]); 613 } 614 else 615 { 616 this.PARTS.LAYERS.appendChild(this._layers[layerId]); 617 } 618 619 this._current_layer = this._layers[layerId]; 620 }; 621 622 this._replace_layer = function(old_layer, new_layer) 623 { 624 if (old_layer != new_layer) 625 { 626 if (!BX.browser.IsIE() || BX.browser.IsDoctype()) 627 { 628 var dir = old_layer.BXLAYERID > new_layer.BXLAYERID ? 1 : -1; 629 630 var old_top = 0; 631 var new_top = -dir * old_layer.offsetHeight; 632 633 old_layer.style.position = 'relative'; 634 old_layer.style.top = "0px"; 635 old_layer.style.zIndex = 5; 636 637 new_layer.style.position = 'absolute'; 638 new_layer.style.top = new_top + 'px'; 639 new_layer.style.zIndex = 6; 640 641 this.PARTS.LAYERS.appendChild(new_layer); 642 643 var delta = 15; 644 645 var f; 646 (f = function() { 647 new_top += dir * delta; 648 old_top += dir * delta; 649 650 if (dir * new_top < 0) 651 { 652 old_layer.style.top = old_top + 'px'; 653 new_layer.style.top = new_top + 'px'; 654 setTimeout(f, 10); 655 } 656 else 657 { 658 old_layer.parentNode.removeChild(old_layer); 659 660 new_layer.style.top = "0px"; 661 new_layer.style.position = 'static'; 662 new_layer.style.zIndex = 0; 663 } 664 })(); 665 } 666 else 667 {
668 this.PARTS.LAYERS.replaceChild(new_layer, old_layer); 669 } 670 } 671 }; 672 673 this._create_layer = function() 674 { 675 var l = BX.create('DIV', { 676 props: { 677 className: 'bx-calendar-layer' 678 } 679 }); 680 681 var month_start = new Date(this.value); 682 month_start.setUTCHours(0); 683 month_start.setUTCMinutes(0); 684 685 month_start.setUTCDate(1); 686 687 if (month_start.getUTCDay() != this.weekStart) 688 { 689 var d = month_start.getUTCDay() - this.weekStart; 690 d += d < 0 ? 7 : 0; 691 month_start.setUTCDate(month_start.getUTCDate()-d); 692 } 693 694 var cur_month = this.value.getUTCMonth(), 695 cur_day = this.value.getUTCDate(), 696 s = ''; 697 for (var i = 0; i < this.numRows; i++) 698 { 699 s += '<div class="bx-calendar-range' 700 +(i == this.numRows-1 ? ' bx-calendar-range-noline' : '') 701 +'">'; 702 703 for (var j = 0; j < 7; j++) 704 { 705 d = month_start.getUTCDate(); 706 var wd = month_start.getUTCDay(); 707 var className = 'bx-calendar-cell'; 708 709 if (cur_month != month_start.getUTCMonth()) 710 className += ' bx-calendar-date-hidden'; 711 else if (cur_day == d) 712 className += ' bx-calendar-active'; 713 714 715 if (wd == 0 || wd == 6) 716 className += ' bx-calendar-weekend'; 717 718 s += '<a href="javascript:void(0)" class="'+className+'" data-date="' + month_start.valueOf() + '">' + d + '</a>'; 719 720 month_start.setUTCDate(month_start.getUTCDate()+1); 721 } 722 s += '</div>'; 723 } 724 725 l.innerHTML = s; 726 727 return l; 728 }; 729 730 this._prev = function() 731 { 732 this.SetMonth(this.value.getUTCMonth()-1); 733 }; 734 735 this._next = function() 736 { 737 this.SetMonth(this.value.getUTCMonth()+1); 738 }; 739 740 this._menu_month_content = function() 741 { 742 var months = '', cur_month = this.value.getMonth(), i; 743 for (i = 0; i < 12; i++) 744 { 745 months += '<span class="bx-calendar-month'+(i == cur_month ? ' bx-calendar-month-active' : '')+'" data-bx-month="' + i + '">' + BX.message('MONTH_' + (i + 1)) + '</span>'; 746 } 747 748 return '<div class="bx-calendar-month-popup"><div class="bx-calendar-month-title" data-bx-month="' + this.value.getUTCMonth() + '">' + BX.message('MONTH_' + (this.value.getUTCMonth() + 1)) + '</div><div class="bx-calendar-month-content">' + months + '</div></div>'; 749 }; 750 751 this._menu_month = function() 752 { 753 if (!this.popup_month) 754 { 755 this.popup_month = new BX.PopupWindow( 756 'calendar_popup_month_' + Math.random(), this.PARTS.MONTH, 757 { 758 content: this._menu_month_content(), 759 closeByEsc: true, 760 autoHide: true, 761 offsetTop: -29, 762 offsetLeft: -1, 763 className: this.month_popup_classname, 764 focusTrap: false, 765 events: { 766 onPopupShow: BX.delegate(function() { 767 if (this.popup_year) 768 { 769 this.popup_year.close(); 770 } 771 }, this) 772 } 773 } 774 ); 775 776 BX.bind(this.popup_month.popupContainer, 'click', BX.proxy(this.month_popup_click, this)); 777 this.popup_month.BXMONTH = this.value.getUTCMonth(); 778 } 779 else if (this.popup_month.BXMONTH != this.value.getUTCMonth()) 780 { 781 this.popup_month.setContent(this._menu_month_content()); 782 this.popup_month.BXMONTH = this.value.getUTCMonth(); 783 } 784 785 this.popup_month.show(); 786 }; 787 788 this.month_popup_click = function(e) 789 { 790 var target = e.target || e.srcElement; 791 if (target && target.getAttribute && target.getAttribute('data-bx-month')) 792 { 793 this.SetMonth(parseInt(target.getAttribute('data-bx-month'))); 794 this.popup_month.close(); 795 } 796 }; 797 798 this._menu_year_content = function() 799 { 800 var s = '<div class="bx-calendar-year-popup"><div class="bx-calendar-year-title" data-bx-year="' + this.value.getUTCFullYear() + '">' + this.value.getUTCFullYear() + '</div><div class="bx-calendar-year-content" id="bx-calendar-year-content">'; 801 802 for (var i=-3; i <= 3; i++) 803 { 804 s += '<span class="bx-calendar-year-number' + (i == 0?' bx-calendar-year-active' : '') + '" data-bx-year="' + (this.value.getUTCFullYear() - i) + '">' + (this.value.getUTCFullYear() - i)+'</span>'; 805 } 806 807 s += '</div><input data-bx-year-input="Y" type="text" class="bx-calendar-year-input" maxlength="4" /></div>'; 808 809 return s; 810 }; 811 812 this._menu_year = function() 813 { 814 if (!this.popup_year) 815 { 816 this.popup_year = new BX.PopupWindow( 817 'calendar_popup_year_' + Math.random(), this.PARTS.YEAR, 818 { 819 content: this._menu_year_content(), 820 closeByEsc: true, 821 autoHide: true, 822 offsetTop: -29, 823 offsetLeft: -1, 824 className: this.year_popup_classname, 825 focusTrap: false, 826 events: { 827 onPopupShow: BX.delegate(function() { 828 if (this.popup_month) 829 { 830 this.popup_month.close(); 831 } 832 }, this) 833 } 834 } 835 ); 836 837 BX.bind(this.popup_year.popupContainer, 'click', BX.proxy(this.year_popup_click, this)); 838 BX.bind(this.popup_year.popupContainer, 'keyup', BX.proxy(this.year_popup_keyup, this)); 839 this.popup_year.BXYEAR = this.value.getUTCFullYear(); 840 } 841 else if (this.popup_year.BXYEAR != this.value.getUTCFullYear()) 842 { 843 this.popup_year.setContent(this._menu_year_content()); 844 this.popup_year.BXYEAR = this.value.getUTCFullYear(); 845 } 846 847 this.popup_year.show(); 848 }; 849 850 this.year_popup_click = function(e) 851 { 852 var target = e.target || e.srcElement; 853 if (target && target.getAttribute && target.getAttribute('data-bx-year')) 854 { 855 this.SetYear(parseInt(target.getAttribute('data-bx-year'))); 856 this.popup_year.close(); 857 } 858 }; 859 this.year_popup_keyup = function(e) 860 { 861 var target = e.target || e.srcElement; 862 if (target && target.getAttribute && target.getAttribute('data-bx-year-input') == 'Y') 863 { 864 var value = parseInt(target.value); 865 if(value >= 1900 && value <= 2100) 866 { 867 this.SetYear(value); 868 this.popup_year.close(); 869 } 870 } 871 }; 872 873 this._check_date = function(v) 874 { 875 var res = v; 876 877 if (BX.type.isString(v)) 878 { 879 res = BX.parseDate(v, true); 880 } 881 882 if (!BX.type.isDate(res) || isNaN(res.valueOf())) 883 { 884 res = BX.date.convertToUTC(new Date()); 885 if (this.params.bHideTime) 886 { 887 res.setUTCHours(0); 888 res.setUTCMinutes(0); 889 } 890 } 891 892 res.setUTCMilliseconds(0); 893 res.setUTCSeconds(0); 894 895 res.BXCHECKED = true; 896 897 return res; 898 }; 899}; 900 901BX.JCCalendar.prototype.Show = function(params) 902{ 903 if (!BX.isReady) 904 { 905 BX.ready(BX.delegate(function() {this.Show(params)}, this)); 906 return; 907 } 908 909 params.node = params.node||document.body; 910 911 if (BX.type.isNotEmptyString(params.node)) 912 { 913 var n = BX(params.node); 914 if (!n) 915 { 916 n = document.getElementsByName(params.node); 917 if (n && n.length > 0) 918 { 919 n = n[0] 920 } 921 } 922 params.node = n; 923 } 924 925 if (!params.node) 926 return; 927 928 if (!!params.field) 929 { 930 if (BX.type.isString(params.field)) 931 { 932 n = BX(params.field); 933 if (!!n) 934 { 935 params.field = n; 936 } 937 else 938 {
939 if (params.form) 940 { 941 if (BX.type.isString(params.form)) 942 { 943 params.form = document.forms[params.form]; 944 } 945 } 946 947 if (BX.type.isDomNode(params.form) && !!params.form[params.field]) 948 { 949 params.field = params.form[params.field]; 950 } 951 else 952 { 953 n = document.getElementsByName(params.field); 954 if (n && n.length > 0) 955 { 956 n = n[0]; 957 params.field = n; 958 } 959 } 960 } 961 962 if (BX.type.isString(params.field)) 963 { 964 params.field = BX(params.field); 965 } 966 } 967 } 968 969 var bShow = !this.popup || !this.popup.isShown() || this.params.node != params.node; 970 971 this.params = params; 972 973 this.params.bCompatibility = (typeof this.params.bCompatibility == 'undefined' ? false : this.params.bCompatibility); 974 this.params.bTimeVisibility = (typeof this.params.bTimeVisibility == 'undefined' ? !this.params.bCompatibility : this.params.bTimeVisibility); 975 if (this.params.bCompatibility) 976 { 977 this.params.bCategoryTimeVisibilityOption = ( 978 this.params.bCategoryTimeVisibilityOption ? this.params.bCategoryTimeVisibilityOption : '' 979 ); 980 this.params.bNameTimeVisibilityOption = ( 981 this.params.bNameTimeVisibilityOption ? this.params.bNameTimeVisibilityOption : 'time_visibility' 982 ); 983 984 if (typeof this._bTimeVisibility !== 'undefined') 985 { 986 this.params.bTimeVisibility = this._bTimeVisibility; 987 } 988 } 989 990 this.params.bTime = typeof this.params.bTime == 'undefined' ? true : !!this.params.bTime; 991 this.params.bHideTime = typeof this.params.bHideTime == 'undefined' ? true : !!this.params.bHideTime; 992 this.params.bUseSecond = typeof this.params.bUseSecond == 'undefined' ? true : !!this.params.bUseSecond; 993 994 this.weekStart = parseInt(this.params.weekStart || this.params.weekStart || BX.message('WEEK_START')); 995 if (isNaN(this.weekStart)) 996 this.weekStart = 1; 997 998 if (!this.popup) 999 { 1000 this._create(this.params); 1001 } 1002 else 1003 { 1004 this.popup.setBindElement(this.params.node); 1005 } 1006 1007 var bHideTime = !!this.params.bHideTime; 1008 if (this.params.value) 1009 { 1010 this.SetValue(this.params.value); 1011 bHideTime = this.value.getUTCHours() <= 0 && this.value.getUTCMinutes() <= 0; 1012 } 1013 else if (this.params.field) 1014 { 1015 this.SetValue(this.params.field.value); 1016 bHideTime = this.value.getUTCHours() <= 0 && this.value.getUTCMinutes() <= 0; 1017 } 1018 else if (!!this.params.currentTime) 1019 { 1020 this.SetValue(this.params.currentTime); 1021 } 1022 else 1023 { 1024 this.SetValue(); 1025 } 1026 1027 if (!!this.params.bTime) 1028 { 1029 this.activateTimeStyle(bHideTime); 1030 } 1031 else 1032 { 1033 this.activateDateStyle(bHideTime); 1034 } 1035 1036 if (bShow) 1037 { 1038 this._auto_hide_disable(); 1039 this.popup.show(); 1040 setTimeout(BX.proxy(this._auto_hide_enable, this), 0); 1041 } 1042 1043 this.params.bSetFocus = typeof this.params.bSetFocus == 'undefined' ? true : !!this.params.bSetFocus; 1044 if(this.params.bSetFocus) 1045 { 1046 params.node.blur(); 1047 } 1048 else 1049 { 1050 BX.bind(params.node, 'keyup', BX.defer(function(){ 1051 this.SetValue(params.node.value); 1052 if(!!this.params.bTime) 1053 { 1054 if(this.value.getUTCHours() <= 0 && this.value.getUTCMinutes() <= 0) 1055 BX.removeClass(this.PARTS.TIME, 'bx-calendar-set-time-opened'); 1056 else 1057 BX.addClass(this.PARTS.TIME, 'bx-calendar-set-time-opened'); 1058 } 1059 }, this)); 1060 } 1061 1062 return this; 1063}; 1064 1065BX.JCCalendar.prototype.activateDateStyle = function(bHideTime) 1066{ 1067 BX.addClass(this.DIV, 'bx-calendar-time-disabled'); 1068 1069 if (!!bHideTime) 1070 BX.removeClass(this.PARTS.TIME, 'bx-calendar-set-time-opened'); 1071 else 1072 BX.addClass(this.PARTS.TIME, 'bx-calendar-set-time-opened'); 1073}; 1074 1075BX.JCCalendar.prototype.activateTimeStyle = function(bHideTime) 1076{ 1077 if (this.params.bCompatibility && !this.params.bTimeVisibility) 1078 { 1079 BX.addClass(this.PARTS.BUTTONS, 'bx-calendar-buttons-disabled'); 1080 BX.addClass(this.PARTS.TIME, 'bx-calendar-set-time-wrap-simple'); 1081 BX.removeClass(this.PARTS.TIME, 'bx-calendar-set-time-opened'); 1082 } 1083 else 1084 { 1085 BX.removeClass(this.DIV, 'bx-calendar-time-disabled'); 1086 1087 if (!!bHideTime) 1088 BX.removeClass(this.PARTS.TIME, 'bx-calendar-set-time-opened'); 1089 else 1090 BX.addClass(this.PARTS.TIME, 'bx-calendar-set-time-opened'); 1091 } 1092}; 1093 1094BX.JCCalendar.prototype.SetDay = function(d) 1095{ 1096 this.value.setUTCDate(d); 1097 return this.SetValue(this.value); 1098}; 1099 1100BX.JCCalendar.prototype.SetMonth = function(m) 1101{ 1102 if (this.popup_month) 1103 this.popup_month.close(); 1104 1105 this.value.setUTCMonth(m); 1106 1107 if(m < 0) 1108 m += 12; 1109 else if (m >= 12) 1110 m -= 12; 1111 1112 while(this.value.getUTCMonth() > m) 1113 { 1114 this.value.setUTCDate(this.value.getUTCDate()-1); 1115 } 1116 1117 return this.SetValue(this.value); 1118}; 1119 1120BX.JCCalendar.prototype.SetYear = function(y) 1121{ 1122 if (this.popup_year) 1123 this.popup_year.close(); 1124 this.value.setUTCFullYear(y); 1125 return this.SetValue(this.value); 1126}; 1127 1128BX.JCCalendar.prototype.SetDate = function(v, bSet) 1129{ 1130 v = this._check_date(v); 1131 v.setUTCHours(this.value.getUTCHours()); 1132 v.setUTCMinutes(this.value.getUTCMinutes()); 1133 v.setUTCSeconds(this.value.getUTCSeconds()); 1134 1135 if (this.params.bTime && !bSet) 1136 { 1137 return this.SetValue(v); 1138 } 1139 else 1140 { 1141 this.SetValue(v); 1142 this.SaveValue(); 1143 } 1144}; 1145 1146BX.JCCalendar.prototype.SetValue = function(v) 1147{ 1148 this.value = (v && v.BXCHECKED) ? v : this._check_date(v); 1149 1150 this.PARTS.MONTH.innerHTML = BX.message('MONTH_' + (this.value.getUTCMonth()+1)); 1151 this.PARTS.YEAR.innerHTML = this.value.getUTCFullYear(); 1152 1153 if (!!this.params.bTime) 1154 {
1155 var h = this.value.getUTCHours(); 1156 if (this.bAmPm) 1157 { 1158 if (h >= 12) 1159 { 1160 this.PARTS.TIME_AMPM.innerHTML = 'PM'; 1161 1162 if (h != 12) 1163 h -= 12; 1164 } 1165 else 1166 { 1167 this.PARTS.TIME_AMPM.innerHTML = 'AM'; 1168 1169 if (h == 0) 1170 h = 12; 1171 } 1172 } 1173 1174 this.PARTS.TIME_INPUT_H.value = BX.util.str_pad_left(h.toString(), 2, "0"); 1175 this.PARTS.TIME_INPUT_M.value = BX.util.str_pad_left(this.value.getUTCMinutes().toString(), 2, "0"); 1176 } 1177 1178 this._set_layer(); 1179 1180 return this; 1181}; 1182 1183BX.JCCalendar.prototype.SaveValue = function() 1184{ 1185 if (this.popup_month) 1186 this.popup_month.close(); 1187 if (this.popup_year) 1188 this.popup_year.close(); 1189 1190 var bSetValue = true; 1191 if (!!this.params.callback) 1192 { 1193 var res = this.params.callback.apply(this, [new Date(this.value.valueOf()+this.value.getTimezoneOffset()*60000)]); 1194 if (res === false) 1195 bSetValue = false; 1196 } 1197 1198 if (bSetValue) 1199 { 1200 var bTime = !!this.params.bTime && BX.hasClass(this.PARTS.TIME, 'bx-calendar-set-time-opened'); 1201 1202 if (this.params.field) 1203 { 1204 var format = BX.message(bTime ? 'FORMAT_DATETIME' : 'FORMAT_DATE'); 1205 1206 if(bTime && !this.params.bUseSecond) 1207 { 1208 format = format.replace(':SS', ''); 1209 } 1210 1211 this.params.field.value = BX.calendar.ValueToStringFormat(this.value, format, true); 1212 BX.fireEvent(this.params.field, 'change'); 1213 } 1214 1215 this.popup.close(); 1216 1217 if (!!this.params.callback_after) 1218 { 1219 this.params.callback_after.apply(this, [new Date(this.value.valueOf()+this.value.getTimezoneOffset()*60000), bTime]); 1220 } 1221 } 1222 1223 return this; 1224}; 1225 1226BX.JCCalendar.prototype.Close = function() 1227{ 1228 if (!!this.popup) 1229 this.popup.close(); 1230 1231 return this; 1232}; 1233 1234BX.JCSpinner = function(params) 1235{ 1236 params = params || {}; 1237 this.params = { 1238 input: params.input || null, 1239 1240 delta: params.delta || 1, 1241 1242 timeout_start: params.timeout_start || 1000, 1243 timeout_cont: params.timeout_cont || 150, 1244 1245 callback_start: params.callback_start || null, 1246 callback_change: params.callback_change || null, 1247 callback_finish: params.callback_finish || null, 1248 1249 bSaveValue: typeof params.bSaveValue == 'undefined' ? !!params.input : !!params.bSaveValue 1250 }; 1251 1252 this.mousedown = false; 1253 this.direction = 1; 1254}; 1255 1256BX.JCSpinner.prototype.Show = function() 1257{ 1258 this.node = BX.create('span', { 1259 events: { 1260 mousedown: BX.delegateEvent( 1261 {attr: 'data-dir'}, 1262 BX.delegate(this.Start, this) 1263 ) 1264 }, 1265 html: '<a href="javascript:void(0)" class="bx-calendar-form-arrow bx-calendar-form-arrow-top" data-dir="1"><i></i></a><a href="javascript:void(0)" class="bx-calendar-form-arrow bx-calendar-form-arrow-bottom" data-dir="-1"><i></i></a>' 1266 }); 1267 return this.node; 1268}; 1269 1270BX.JCSpinner.prototype.Start = function() 1271{ 1272 this.mousedown = true; 1273 this.direction = BX.proxy_context.getAttribute('data-dir') > 0 ? 1 : -1; 1274 BX.bind(document, "mouseup", BX.proxy(this.MouseUp, this)); 1275 this.ChangeValue(true); 1276}; 1277 1278BX.JCSpinner.prototype.ChangeValue = function(bFirst) 1279{ 1280 if(!this.mousedown) 1281 return; 1282 1283 if (this.params.input) 1284 { 1285 var v = parseInt(this.params.input.value, 10) + this.params.delta * this.direction; 1286 1287 if (this.params.bSaveValue) 1288 this.params.input.value = v; 1289 1290 if (!!bFirst && this.params.callback_start) 1291 this.params.callback_start(this.params, v, this.direction); 1292 1293 if (this.params.callback_change) 1294 this.params.callback_change(this.params, v, this.direction); 1295 1296 setTimeout( 1297 BX.proxy(this.ChangeValue, this), 1298 !!bFirst ? this.params.timeout_start : this.params.timeout_cont 1299 ); 1300 } 1301}; 1302 1303BX.JCSpinner.prototype.MouseUp = function() 1304{ 1305 this.mousedown = false; 1306 BX.unbind(document, "mouseup", BX.proxy(this.MouseUp, this)); 1307 1308 if (this.params.callback_finish) 1309 this.params.callback_finish(this.params, this.params.input.value); 1310}; 1311 1312/**************** compatibility hacks ***************************/ 1313 1314window.jsCalendar = { 1315 Show: function(obj, field, fieldFrom, fieldTo, bTime, serverTime, form_name, bHideTimebar) 1316 { 1317 return BX.calendar({ 1318 node: obj, field: field, form: form_name, bTime: !!bTime, currentTime: serverTime, bHideTimebar: !!bHideTimebar 1319 }); 1320 }, 1321 1322 ValueToString: BX.calendar.ValueToString 1323}; 1324 1325 1326/************ clock popup transferred from timeman **************/ 1327 1328BX.CClockSelector = function(params) 1329{ 1330 this.params = params; 1331 1332 this.params.popup_buttons = this.params.popup_buttons || [ 1333 new BX.PopupWindowButton({ 1334 text : BX.message('CAL_BUTTON'), 1335 className : "popup-window-button-create", 1336 events : {click : BX.proxy(this.setValue, this)} 1337 }) 1338 ]; 1339 1340 this.isReady = false;
1341 1342 this.WND = new BX.PopupWindow( 1343 this.params.popup_id || 'clock_selector_popup', 1344 this.params.node, 1345 this.params.popup_config || { 1346 titleBar: BX.message('CAL_TIME'), 1347 offsetLeft: -45, 1348 offsetTop: -135, 1349 autoHide: true, 1350 closeIcon: true, 1351 closeByEsc: true, 1352 focusTrap: false, 1353 }, 1354 ); 1355 1356 this.SHOW = false; 1357 BX.addCustomEvent(this.WND, "onPopupClose", BX.delegate(this.onPopupClose, this)); 1358 1359 this.obClocks = {}; 1360 this.CLOCK_ID = this.params.clock_id || 'clock_selector'; 1361}; 1362 1363BX.CClockSelector.prototype.Show = function() 1364{ 1365 if (!this.isReady) 1366 { 1367 //BX.timeman.showWait(this.parent.DIV); 1368 1369 BX.addCustomEvent('onClockRegister', BX.proxy(this.onClockRegister, this)); 1370 return BX.ajax.get('/bitrix/tools/clock_selector.php', {start_time: this.params.start_time, clock_id: this.CLOCK_ID, sessid: BX.bitrix_sessid()}, BX.delegate(this.Ready, this)); 1371 } 1372 1373 this.WND.setButtons(this.params.popup_buttons); 1374 this.WND.show(); 1375 1376 this.SHOW = true; 1377 1378 if (window['bxClock_' + this.obClocks[this.CLOCK_ID]]) 1379 { 1380 setTimeout("window['bxClock_" + this.obClocks[this.CLOCK_ID] + "'].CalculateCoordinates()", 40); 1381 } 1382 1383 return true; 1384}; 1385 1386BX.CClockSelector.prototype.onClockRegister = function(obClocks) 1387{ 1388 if (obClocks[this.CLOCK_ID]) 1389 { 1390 this.obClocks[this.CLOCK_ID] = obClocks[this.CLOCK_ID]; 1391 BX.removeCustomEvent('onClockRegister', BX.proxy(this.onClockRegister, this)); 1392 } 1393}; 1394 1395BX.CClockSelector.prototype.Ready = function(data) 1396{ 1397 this.content = this.CreateContent(data); 1398 this.WND.setContent(this.content); 1399 1400 this.isReady = true; 1401 //BX.timeman.closeWait(); 1402 1403 setTimeout(BX.proxy(this.Show, this), 30); 1404}; 1405 1406BX.CClockSelector.prototype.CreateContent = function(data) 1407{ 1408 return BX.create('DIV', { 1409 events: {click: BX.PreventDefault}, 1410 html: 1411 '<div class="bx-tm-popup-clock">' + data + '</div>' 1412 }); 1413}; 1414 1415BX.CClockSelector.prototype.setValue = function(e) 1416{ 1417 if (this.params.callback) 1418 { 1419 var input = BX.findChild(this.content, {tagName: 'INPUT'}, true); 1420 this.params.callback.apply(this.params.node, [input.value]); 1421 } 1422 1423 return BX.PreventDefault(e); 1424}; 1425 1426BX.CClockSelector.prototype.closeWnd = function(e) 1427{ 1428 this.WND.close(); 1429 return (e || window.event) ? BX.PreventDefault(e) : true; 1430}; 1431 1432BX.CClockSelector.prototype.setNode = function(node) 1433{ 1434 this.WND.setBindElement(node); 1435}; 1436 1437BX.CClockSelector.prototype.setTime = function(timestamp) 1438{ 1439 this.params.start_time = timestamp; 1440 if (window['bxClock_' + this.obClocks[this.CLOCK_ID]]) 1441 { 1442 window['bxClock_' + this.obClocks[this.CLOCK_ID]].SetTime(parseInt(timestamp/3600), parseInt((timestamp%3600)/60)); 1443 } 1444}; 1445 1446BX.CClockSelector.prototype.setCallback = function(cb) 1447{ 1448 this.params.callback = cb; 1449}; 1450 1451BX.CClockSelector.prototype.onPopupClose = function() 1452{ 1453 this.SHOW = false;
1454}; 1455 1456})(); 1457
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.