1/** 2 * Rosetta 3 */ 4 5var Site = Site || { }; 6 7// Cache 8Site.$el = { 9 10 setup : function() { 11 this.window = $(window); 12 this.index = $('#index'); 13 } 14 15}; 16 17// Run the setup & events methods on all Site namespaces 18$(function() { 19 20 var key, namespace; 21 22 for (key in Site) { 23 namespace = Site[key]; 24 if ( namespace.hasOwnProperty('setup') && typeof namespace.setup === "function" ) { 25 namespace.setup(); 26 } 27 if ( namespace.hasOwnProperty('events') && typeof namespace.events === "function" ) { 28 namespace.events(); 29 } 30 } 31 32}); 33 34 35var Design = { 36 37 data : { 38 stageHeight: 0, 39 stageWidth: 0, 40 textBodyStartHeight :0, 41 allThumbWidth: 0, 42 allMediaWidth: 0, 43 titleHeight: 0, 44 intextImageHeight: 0, 45 entryWidth: 0, 46 bottomMarginAdjust: 0 47 }, 48 49 bindKeys : function() { 50 Cargo.Core.KeyboardShortcut.Add("Left", 37, function() { 51 Action.Project.Prev(); 52 return false; 53 }); 54 55 Cargo.Core.KeyboardShortcut.Add("Right", 39, function() { 56 Action.Project.Next(); 57 return false; 58 }); 59 }, 60 61 hoverProject: function() { 62 63 // add hover class for project thumbs, if no titles or tagsâadd a separate class for separate styling 64 65 if (!Cargo.Model.DisplayOptions.get('title_in_thumb') && !Cargo.Model.DisplayOptions.get('tags_in_thumb')) { 66 67 hoverClass = 'hovering-no-info'; 68 69 $('.thumb_info').remove(); 70 71 } else { 72 73 hoverClass = 'hovering'; 74 75 } 76 77 // Thumbnail hover 78 if (!Cargo.Helper.isMobile()) { 79 80 $(".thumbnails") 81 .on("mouseenter", ".project_thumb", function(e) { 82 $(this).addClass(hoverClass); 83 }) 84 .on("mouseleave", ".project_thumb", function(e) { 85 $(this).removeClass(hoverClass); 86 }); 87 88 } 89 90 }, 91 92 setFormatting: function() { 93 94 // group sets in navigation 95 96 var navGroups = []; 97 98 $(".navigation div[data-type]").each(function() { 99 100 var type = this.getAttribute("data-type"); 101 102 if ($.inArray(type, navGroups) == -1) { 103 104 // first unwrap if already wrapped 105 if ($(this).parent().hasClass("group")) { 106 $(this).unwrap(); 107 } 108 109 if (type == "link" || type == "page") { 110 var items = $(".navigation div[data-type='link'], .navigation div[data-type='page']"); 111 navGroups.push("link", "page"); 112 } else { 113 var items = $(".navigation div[data-type='" + type + "']"); 114 navGroups.push(type); 115 } 116 117 items.wrapAll("<div class='group' />"); 118 119 } 120 121 }); 122 123 }, 124 125 captionFormatting: function() { 126 127 // formatting for captions on media images, and slideshows 128 129 // if slideshow nav is on topâ(not slideshow images') captions go on bototm, else they are on top 130 if ( Cargo.Model.DisplayOptions.get("slide_nav_position") == "top" ){ 131 captionClass = 'on_bottom'; 132 } else { 133 captionClass = 'on_top'; 134 } 135 136 137 // slideshow captions 138 $('.slideshow_caption').each(function(i){ 139 140 $(this).addClass(captionClass); 141 142 }); 143 144 // take caption from the img caption attribute, and put content in an absolute position div 145 if (Cargo.Model.DisplayOptions.get('captions_view') == true) { 146 147 $('.project_media .img_holder img').each(function(i){ 148 149 var caption = $(this).attr('caption'); 150 151 if ( typeof caption !== typeof undefined && caption !== false ) { 152 153 $(this).after('<div class="caption on_bottom">' + caption + '</div>'); 154 155 } 156 157 }); 158 159 } 160 161 }, 162 163 columnizeText: function() { 164 165 // columnize text on projects 166 167 var stage = $('.entry'), 168 titleHeight = $('.project_title').height() + parseInt($('.project_title').css('padding-bottom')), 169 footerHeight = $('.project_footer').outerHeight(true), 170 hasText = $('.project_content > .textcolumns').length > 0, 171 minWidth = parseInt($('.project_content').css('min-width')), 172 projectPadding = parseInt($('.project').css('padding-bottom')) + parseInt($('.project').css('padding-top')),
173 adjustedHeight = Design.data.stageHeight + -Design.data.titleHeight + -projectPadding + -Design.data.bottomMarginAdjust, 174 calcColumns = Design.data.textBodyStartHeight / adjustedHeight, 175 columnsNeeded = Math.ceil(calcColumns); 176 177 // add a marker to see if there is overflow 178 if ($('.column-marker').length < 1) { 179 $('.textcolumns').append('<div class="column-marker" />'); 180 } 181 182 // Set height of columns subtracting height of title from stage 183 $('.project_content .textcolumns').height(adjustedHeight); 184 185 // if there is no text, set a hard width on project_content instead of min-width 186 if (hasText == false) { 187 $('.project_content').width(minWidth); 188 } 189 190 //if text is taller than window stage, columnize 191 if (Design.data.textBodyStartHeight > adjustedHeight) { 192 193 $('.project_content .textcolumns').addClass('columnized'); 194 $('.project_content .textcolumns').attr('columns', columnsNeeded); 195 196 columnWidth = parseInt($('.columnized').css('column-width')), 197 columnGutter = parseInt($('.columnized').css('column-gap')), 198 columnTotalWidth = columnGutter + columnWidth, 199 oneMoreColumn = 0; 200 201 // if we have a column parker past the width of columns, add another column 202 if ($('.column-marker').position().left > (columnTotalWidth * columnsNeeded) - columnGutter) { 203 oneMoreColumn = 1; 204 } 205 206 // set the column container width, and column count 207 $('.columnized').css({ 208 'width' : (columnTotalWidth * (columnsNeeded + oneMoreColumn)) - columnGutter, 209 '-webkit-column-count' : columnsNeeded + oneMoreColumn, 210 '-moz-column-count' : columnsNeeded + oneMoreColumn, 211 'column-count': columnsNeeded + oneMoreColumn 212 }); 213 214 } else { 215 216 // get rid of any column attributes that were added 217 $('.project_content').removeAttr('columns'); 218 $('.project_content .textcolumns').removeAttr('style'); 219 $('.project_content .textcolumns').removeClass('columnized'); 220 221 } 222 223 Cargo.Event.trigger("column_complete", "Cargo"); 224 225 }, 226 227 noBreaksOnTop: function() { 228 229 // visually remove breaks at the top of columns, add them to the end of the content 230 231 var brAtTop = $('.break_span'), 232 spanHeight = parseInt($('.project_content').css('line-height')); 233 footer = $('.project_footer'); 234 235 // determine where to add breaks that have been visually removed 236 if (footer.length > 0 && footer.is(':visible')){ 237 endPlace = '.project_footer'; 238 } else { 239 endPlace = 'p'; 240 } 241 242 // clear top and last breaks before they are set 243 brAtTop.removeClass('top-br'); 244 $('.last_span').remove(); 245 246 247 $(brAtTop).each( function(el){ 248 249 // set a height to each span 250 $(this).css('height', spanHeight); 251 252 // if a break is at the top of the container, remove its height, add that height to the end place 253 if (($(this).position().top - $('.project_title').outerHeight(true)) <= 1) { 254 255 $(this).addClass('top-br').css('height', '0'); 256 $('.project_content ' + endPlace).append('<span class="last_span" style=" height: ' + spanHeight + 'px' + '"></span>'); 257 258 } 259 260 }); 261 262 }, 263 264 setProjectMediaSize: function() { 265 266 // set a hard width on project media based on the combined width of its children 267 268 slideshowGutter = ($('.slideshow').length > 0) ? $('.slideshow').length * parseInt($('.slideshow').css('margin-right')): 0; 269 projContPad = parseInt($('.project_media').css('padding-right')), 270 mediaCount = parseInt($('.project_media > *').length); 271 272 if ($('.project_media > *:not(.slideshow)').length > 0) { 273 Design.data.allMediaWidth = 0; 274 $('.project_media > *').each(function() { 275 Design.data.allMediaWidth += $(this).outerWidth(true); 276 }); 277 } 278 279 $('.project_media').width(Design.data.allMediaWidth + projContPad + slideshowGutter); 280 281 }, 282 283 setStageProperties: function() { 284 285 // set the height and width of the stage 286 287 var stagePadding = parseInt($('.thumbnails').css('padding-top')) + parseInt($('.thumbnails').css('padding-bottom')); 288 289 Design.data.stageHeight = $('#index > div:visible').last().height(); 290 291 Design.data.stageWidth = $(window).width(); 292 293 }, 294 295 titleHeight: function() { 296 297 // find the height of the project title 298 299 if (Cargo.Model.DisplayOptions.get('title_in_project') && Cargo.Model.Project.GetShowTitle()) { 300 301 Design.data.titleHeight = $('.project_title').height() + parseInt($('.project_title').css('padding-bottom')); 302 303 } else { 304 305 Design.data.titleHeight = 0; 306 307 } 308 309 }, 310 311 intextImageHeight: function() { 312 313 // FOR FUTURE USE (if browsers advance CSS3 columns) 314 // find the height of images inside of columns 315 316 if ($('.textcolumns p').has('span img')) { 317 318 Design.data.intextImageHeight = 0; 319 320 $('.textcolumns p span img').each(function(){ 321 322 Design.data.intextImageHeight += $(this).outerHeight(true); 323 324 }); 325 326 } else { Design.data.intextImageHeight = 0; } 327 328 }, 329 330 setThumbSize: function() { 331 332 // set the size of thumbnails 333 334 var thumbMargin = parseInt($('.project_thumb').css('margin-bottom')), 335 marginPerc = (Design.data.stageHeight / thumbMargin) / 100, 336 thumbSize = parseInt(Cargo.Model.DisplayOptions.get('thumb_size').h) + thumbMargin, 337 rowCount = (Design.data.stageHeight + thumbMargin) / thumbSize, 338 rowsNeeded = Math.ceil(rowCount), 339 rowHeightpx = Design.data.stageHeight / rowsNeeded, 340 rowHeight = Math.floor(rowHeightpx), 341 leftover = Design.data.stageHeight - (rowHeight * rowsNeeded); 342 343 if (rowsNeeded > rowCount) { 344 345 // Set percentage height for each row depending on user's thumb height 346 $('.project_thumb').css('height', rowHeight - thumbMargin + 'px'); 347 348 // Set width of each thumb based on amount of rows 349 $('.project_thumb').each(function() { 350 $(this).width(parseInt($(this).find('.thumb_image img').css('width'))); 351 }); 352 353 // pixels leftover if rows are an odd number 354 Design.data.bottomMarginAdjust = leftover; 355 356 } 357 358 Cargo.Event.trigger("thumbsize_complete", "Cargo"); 359 360 }, 361 362 setThumbSizeAfterFirstLoad: function() { 363 364 // Run setThumbSize and horizontalIsotope functions for the first time 365 366 // tell Cargo that pagination is occuring so it will not fire twice 367 if (typeof Cargo.View.Autopaginate == 'object') { 368 Cargo.View.Autopaginate.Data.is_updating = true; 369 } 370 371 var elems = $(".project_thumb[data-rowed!='true']"); 372 373 // hide thumbs before until they have loaded 374 elems.css('visibility', 'hidden'); 375 376 // once images have loaded 377 elems.imagesLoaded( function() { 378 379 elems.css('visibility', 'hidden'); 380 Design.setThumbSize(); 381 Design.horizontalIsotope(); 382 383 }); 384 385 }, 386 387 thumbInfoClick: function() { 388 389 // make sure clicking thumb_info works in the inspector, and when in the active project thumb 390 391 var clickEvent = 'click'; 392
393 // if inspector is open, clickEvent occurs on double click 394 if (location.href.match(/[\?|\&]inspecting/) !== null || parent.editor !== undefined) { 395 396 clickEvent = 'dblclick'; 397 398 } 399 400 // Make thumb_info clickable 401 $(".project_thumb .thumb_info").on(clickEvent, function(){ 402 403 if ($(this).find("a").length){ 404 405 Cargo.Event.trigger("add_history", $(this).find("a:first").attr("href")); 406 407 } 408 409 }); 410 411 // if is the active project thumb, go back to start of project 412 $(".project_thumb.active .thumb_info").on(clickEvent, function(){ 413 414 setTimeout(function() { 415 Cargo.Helper.ScrollToLeft( $('#slide_container') ); 416 }, 10) 417 418 }); 419 420 }, 421 422 horizontalIsotope: function() { 423 424 imagesLoaded( '#thumbnails', function() { 425 426 $('#thumbnails').isotope({ 427 428 layoutMode: 'masonryHorizontal', 429 itemSelector: '.project_thumb', 430 sortBy: 'number', 431 transitionDuration: 0, 432 masonryHorizontal: {}, 433 434 }); 435 436 // for testing purposes, add class first-isotope, so we only run it once depending on whether or not 'doc ready' or 'show index' fires first 437 $('#thumbnails').addClass('first-isotope'); 438 439 setTimeout( function() { 440 441 // if we are on the first page, force check for pagination 442 if (Cargo.API.Config.current_page == 1) { 443 444 if (typeof Cargo.View.Autopaginate == 'object') { 445 Cargo.View.Autopaginate.CheckForPagination(); 446 } 447 448 } 449 450 }, 50); 451 452 }); 453 454 // once isotope has run, add the 'data-rowed' attribute 455 $("#thumbnails .project_thumb").attr('data-rowed', 'true'); 456 457 Design.firstImageIsLoaded(); 458 459 }, 460 461 firstImageIsLoaded: function() { 462 463 // if the first image has been loaded, show the project thumbnials, and tell pagination it is not firing 464 465 var imgLoad = imagesLoaded('#thumbnails'); 466 467 imgLoad.on( 'always', function() { 468 469 var is_loaded = false; 470 471 // find out if one image has been loaded (if one image is loaded we can assume we have the height / width info for the rest of the images) 472 for ( var i = 0, len = imgLoad.images.length; i < len; i++ ) { 473 474 image = imgLoad.images[i]; 475 476 if (typeof image == "object" && image.isLoaded) { 477 478 is_loaded = true; 479 480 } 481 482 } 483 484 // if one image is loaded: 485 if (is_loaded == true) { 486 487 // fade in the new projects 488 $(".project_thumb[data-rowed='true']").css({opacity: 0, visibility: 'visible'}).animate({opacity: 1}, 400); 489 490 // move the autopagination loader to the middle of the screen, and right of the projects already loaded 491 $('#autopaginate_loader').css('display', 'none').addClass('after-load'); 492 493 // tell Cargo pagination it is no longer firing 494 if (typeof Cargo.View.Autopaginate == 'object') { 495 Cargo.View.Autopaginate.Data.is_updating = false; 496 } 497 498 } 499 500 }); 501 502 }, 503 504 isotopeOnPagination: function() { 505 506 // append new thumbnails to isotope 507 if (typeof Cargo.View.Autopaginate == 'object') { 508 Cargo.View.Autopaginate.Data.is_updating = true; 509 } 510 511 // hide thumbnails that have not been data-rowed 512 var elems = $(".project_thumb[data-rowed!='true']"); 513 elems.css('visibility', 'hidden'); 514 515 var imgLoad = imagesLoaded(elems); 516 517 imgLoad.on( 'always', function() { 518 519 var is_loaded = false; 520 521 // find out if one image has been loaded (if one image is loaded we can assume we have the height / width info for the rest of the images) 522 for ( var i = 0, len = imgLoad.images.length; i < len; i++ ) { 523 524 image = imgLoad.images[i]; 525 526 if (typeof image == "object" && image.isLoaded) { 527 528 is_loaded = true; 529 530 } 531 532 } 533 534 // if one image has been loaded: 535 if (is_loaded == true) { 536 537 // set new thumbnails size 538 Design.setThumbSize(); 539 540 // append the new thumbnails 541 $('#thumbnails').isotope( 'appended', elems); 542 543 // Add 'data-rowed' attribute and display loaded thumbs 544 elems.attr('data-rowed', 'true'); 545 elems.css({opacity: 0, visibility: 'visible'}).animate({opacity: 1}, 400); 546 547 // if we've already paginated and thumbnails is not wide enough to trigger pagination again 548 if ($('#thumbnails').width() < $(window).width() + 300) { 549 550 setTimeout(function() { 551 552 if (typeof Cargo.View.Autopaginate == 'object') { 553 Cargo.View.Autopaginate.CheckForPagination(); 554 } 555 556 }, 100) 557 558 } 559 560 // tell Cargo pagination it is no longer firing 561 if (typeof Cargo.View.Autopaginate == 'object') { 562 Cargo.View.Autopaginate.Data.is_updating = false;
563 } 564 565 } 566 567 }); 568 569 }, 570 571 dataRows: function() { 572 573 // Add attribute of data-rowed, once thumbnails have been isotoped 574 575 thumbs = $(".project_thumb[data-rowed!='true']"); 576 577 thumbs.attr('data-rowed', 'true'); 578 579 }, 580 581 adjustStage: function() { 582 583 // Adjust the stage height of projects after thumbnail rows have been calculated so project_media aligns with thumbnails 584 585 var currentPad = parseInt($('.project').css('padding-bottom')); 586 587 Cargo.Plugins.elementResizer.setOptions({ 588 589 forceVerticalMargin: $(window).height() - Design.data.stageHeight + Design.data.bottomMarginAdjust + currentPad 590 591 }); 592 593 $('.project').addClass('adjust_stage'); 594 595 Cargo.Plugins.elementResizer.refresh(); 596 597 $('.project_media').css('visibility', 'visible'); 598 599 Design.setResizerOptions(); 600 601 }, 602 603 setResizerOptions: function() { 604 605 // set vertical & horizontal margins on element resizer 606 607 if (Cargo.Helper.isPhone()) { 608 609 var container = screen.width; 610 var extra = 40; 611 var parent = $('.entry').width(); 612 613 if (Cargo.Model.DisplayOptions.get('captions_view') == true) { 614 615 var containerBottom = parseInt($('.container').css('bottom')); 616 617 } else { 618 619 var containerBottom = 0; 620 621 } 622 623 } else { 624 625 var container = 0; 626 var parent = 0; 627 var extra = 0; 628 containerBottom = 0; 629 630 } 631 632 Cargo.Plugins.elementResizer.setOptions({ 633 forceVerticalMargin: $(window).height() - $('.entry').height() + containerBottom, 634 forceHorizontalMargin: parent - container + extra 635 }); 636 637 }, 638 639 imageScroll: function() { 640 641 // scroll project_media image based on location in the window 642 643 var media = $('.project_media .img_holder img'), 644 moreThanOne = $(media).length > 1, 645 scrollContainer = $('#slide_container'), 646 projectContent = $('.project_content').width() + $('.project_content').css('margin-right'), 647 projectLeftMargin = parseInt($('.project').css('margin-left')), 648 entryWidth = $('.entry').width(), 649 stageWidthHalf = Design.data.stageWidth / 2, 650 thumbnailLocation = $('#thumbnails').position().left, 651 thumbnailPadding = parseInt($('#thumbnails').css('margin-left')), 652 noThumbsProj = Cargo.Model.DisplayOptions.get('thumbs_below_projects') && Cargo.Helper.GetCurrentPageType() == "project", 653 noThumbsPage = Cargo.Model.DisplayOptions.get('thumbs_below_pages') && Cargo.Helper.GetCurrentPageType() == "page", 654 imgPadding = parseInt($('.project_media img').css('margin-right')); 655 656 657 if (moreThanOne) { 658 // if more than 1 image, identify first image 659 660 $(media).first().addClass('first'); 661 662 } else if (!moreThanOne && (!noThumbsProj && !noThumbsPage)) { 663 // else, if only one image and no thumbs to the right, identify as loner 664 665 $(media).first().addClass('loner'); 666 667 } 668 669 // identify last image 670 $(media).last().addClass('last'); 671 672 673 // for each image 674 media.each(function() { 675 676 var lonerImg = $(this).hasClass('loner'), 677 distanceRightH = this.getBoundingClientRect().right; 678 679 // hover conditions 680 $(this).on('mouseenter', function(e) { 681 682 e.preventDefault(); 683 684 // if the image is a loner and is completely in view, don't use pointer 685 if (lonerImg && (distanceRightH < $(window).width())) { 686 $(this).css('cursor', 'default'); 687 } else { 688 $(this).css('cursor', 'pointer'); 689 } 690 691 }).on('mouseleave', function(e) { 692 693 $(this).css('cursor', 'default'); 694 695 }); 696 697 698 // click conditions 699 $(this).on('click', function(e) { 700 701 e.preventDefault(); 702 703 // image properties 704 var imgWidth = $(this).width(), 705 imgLeft = $(this).closest('.img_holder').position().left + projectLeftMargin, 706 inView = $(this).is(':in-viewport'), 707 lastImg = $(this).hasClass('last'), 708 firstImg = $(this).hasClass('first'), 709 imgRight = imgLeft + imgWidth, 710 distanceLeft = this.getBoundingClientRect().left, 711 distanceRight = this.getBoundingClientRect().right, 712 distFromRight = Design.data.stageWidth - distanceRight, 713 transitionFlag = false; 714 715 // image position conditions 716 windowLeft = $(scrollContainer).scrollLeft(), 717 windowRight = windowLeft + Design.data.stageWidth, 718 isOffRight = inView && (Design.data.stageWidth < distanceRight), 719 isOffLeft = inView && (0 > distanceLeft), 720 isOff = isOffLeft || isOffRight, 721 inFullView = inView && !isOffRight && !isOffLeft, 722 isCenter = inView && (distanceLeft < stageWidthHalf) && (distanceRight > stageWidthHalf); 723 724 // next image properties 725 if (!lastImg) { 726 727 nextImg = $(this).closest('.img_holder').next(), 728 prevImg = $(this).closest('.img_holder').prev(), 729 nextImgPos = $(nextImg).position().left + projectLeftMargin, 730 nextImgPosMid = ((Design.data.stageWidth - $(nextImg).width() + imgPadding) / 2); 731 732 } 733 734 // go to this image 735 if ((transitionFlag == false) && 736 ( (!inFullView && !isCenter && !firstImg && !lastImg && (!nextImg.is(':in-viewport')) && (!prevImg.is(':in-viewport'))) 737 || (isOffRight && !lastImg && !firstImg && !isCenter) 738 || (isOffLeft && !lastImg && !firstImg && !isCenter) 739 || ((firstImg && isOffRight && !isOffLeft) || (firstImg && isOffLeft && !isOffRight)) 740 || (!inFullView && !firstImg && ((nextImg.is(':in-viewport')) || (prevImg.is(':in-viewport')))) 741 || (firstImg && (distanceRight < stageWidthHalf) && inFullView) 742 || (lastImg && isOff) 743 || (inFullView && (distanceRight < stageWidthHalf) && !lastImg && !isCenter && !firstImg) 744 || (inFullView && (distanceLeft > stageWidthHalf) && !lastImg && !isCenter) 745 || (inFullView && !isOff && !lastImg && !firstImg && isCenter && (nextImg == lastImg)) 746 )) { 747 748 transitionFlag = true; 749 $(scrollContainer).animate({ 750 scrollLeft: imgLeft - ((Design.data.stageWidth - imgWidth) / 2) 751 }, 300, 'easeInOutCubic', function() { 752 transitionFlag = false;
753 }); 754 755 756 // go to the next image 757 } else if ((transitionFlag == false) && 758 ( (inFullView && firstImg && !lastImg) 759 || (inFullView && !isOff && !lastImg && !firstImg && isCenter && (nextImg !== lastImg)) 760 || (inFullView && firstImg && !lastImg && !isCenter && (distanceRight < stageWidthHalf)) 761 || (isOff && !lastImg && !firstImg && isCenter && (!nextImg.is(':in-viewport')) && (!prevImg.is(':in-viewport'))) 762 || (!isOff && !lastImg /* && !firstImg */ && isCenter && (nextImg.is(':in-viewport')) && (prevImg.is(':in-viewport'))) 763 || (firstImg && isOffRight && isOffLeft) 764 )) { 765 766 transitionFlag = true; 767 $(scrollContainer).animate({ 768 scrollLeft: nextImgPos - nextImgPosMid 769 }, 300, 'easeInOutCubic', function() { 770 transitionFlag = false; 771 }); 772 773 // if is the last image 774 } else if ((transitionFlag == false) && 775 (inFullView && lastImg && isCenter && !lonerImg) 776 || (!isOff && lastImg && isCenter && lonerImg && (windowLeft > 0)) 777 || (inFullView && lastImg && !lonerImg && !isCenter && (distanceLeft > stageWidthHalf) && (!noThumbsPage || !noThumbsProj)) 778 ) { 779 780 // if thumbnails are visible next to project / pages, animate to them 781 if (!noThumbsPage || !noThumbsProj) { 782 783 transitionFlag = true; 784 $(scrollContainer).animate({ 785 scrollLeft: (thumbnailLocation + thumbnailPadding) - stageWidthHalf 786 }, 400, 'easeOutExpo', function() { 787 transitionFlag = false; 788 }); 789 790 // or animate to beginning of the project / page 791 } else { 792 793 transitionFlag = true; 794 $(scrollContainer).animate({ 795 scrollLeft: 0 796 }, 250, 'easeInOutCubic', function() { 797 transitionFlag = false; 798 }); 799 } 800 801 // if is a loner (completely in viewport and there is no content to the right) 802 } else if ((transitionFlag == false) && 803 (lonerImg && inFullView && (windowLeft <= 0) && (!noThumbsPage || !noThumbsProj)) 804 ) { 805 806 // do nothing 807 808 } 809 810 }); 811 812 }); 813 814 }, 815 816 Mobile : { 817 init: function() { 818 819 if ( Cargo.Helper.isPhone() ){ 820 821 $('body').addClass('phone'); 822 823 $('head').append('<meta name="viewport" content="width=device-width">'); 824 825 // add max-width to slide 826 $('#slide_container').css("max-width", screen.width + "px"); 827 828 $('.header_text a, .navigation_toggle').bind( "touchstart", function(){ 829 return true; 830 }); 831 832 $('.navigation_toggle').bind("click", function(){ 833 834 Design.Mobile.toggleNav(); 835 836 }); 837 838 $('.navigation').bind( "touchstart", function(e){ 839 840 var touchtarget = $(e.target); 841 842 if ( !touchtarget.is('a') ) { 843 844 Design.Mobile.toggleNav(); 845 846 } 847 848 }); 849 850 Cargo.Event.on("project_load_complete", function(pid) { 851 852 Design.Mobile.toggleNav(true); 853 854 }); 855 856 } else if ( Cargo.Helper.isTablet() ) { 857 858 ratio = window.devicePixelRatio; 859 860 $('body').addClass('tablet'); 861 $('.container').css("max-width", (screen.width * ratio) + "px"); 862 863 } else { 864 865 $('body').addClass('desktop'); 866 867 } 868 869 // Add attribute once this is done 870 $('body').attr('data-mobileload', 'true'); 871 }, 872 873 toggleNav: function(closeNav){ 874 875 if ( $('.navigation_toggle').is(".active") || closeNav ){ 876 877 $(".navigation, .navigation_toggle").removeClass("active"); 878 879 } else { 880 881 $(".navigation, .navigation_toggle").addClass("active"); 882 883 } 884 885 } 886 } 887}; 888 889 890/********************************************* 891 * 892 * Helpers 893 * 894 *********************************************/ 895 896 Site.Helper = { 897 898 formatText : function(node, includeWhitespaceNodes) { 899
900 var validTags = ['img', 'object', 'video', 'audio', 'iframe', 'div'], 901 keepClass = ['in-text'], 902 nodeContents = node.contents(), 903 newPageFromCache = true, 904 textPages = {}, 905 pageCache = [], 906 pageCount = 0; 907 908 // inline helper functions 909 var _isValidText = function(txt, strict) { 910 911 if (txt !== undefined) { 912 txt = txt.replace(/<!--([\s\S]*?)-->/mig, ""); 913 txt = txt.replace(/(\r\n|\n|\r|\t| )/gm, ""); 914 txt = txt.replace(/[^A-Za-z0-9\s!?\.,-\/#!$%\^&\*;:{}=\-_`~()[[\]]/g, ""); 915 916 if (txt.length > 0) { 917 return true; 918 } 919 } else { 920 if (strict) { 921 return false; 922 } else { 923 return true; 924 } 925 } 926 927 return false; 928 929 } 930 931 var _getTag = function(el) { 932 933 if (typeof el !== "undefined") { 934 var tag = el.tagName; 935 936 if (typeof tag === "undefined") { 937 tag = 'text'; 938 } 939 940 return tag.toLowerCase(); 941 } 942 943 } 944 945 nodeContents.each(function(key, val) { 946 947 if ($.inArray(_getTag(val), validTags) >= 0) { 948 // Don't do anything here 949 if($.inArray($(val).attr('class'), keepClass) >= 0) { 950 pageCache.push(val); 951 } 952 953 } else { 954 if (_isValidText(val.data) && val.nodeType != 8) { 955 pageCache.push(val); 956 } 957 } 958 959 }); 960 961 // Still some stuff left in cache 962 if (pageCache.length > 0) { 963 964 // Check if it needs a new page 965 for (var i = 0; i < pageCache.length; i++) { 966 if (pageCache[i].nodeType == 8 || pageCache[i].nodeName == "SCRIPT" || pageCache[i].nodeName == "STYLE") { 967 // Contains text, create new page 968 newPageFromCache = false; 969 } 970 } 971 972 if (newPageFromCache) { 973 // Create new page 974 textPages[pageCount] = pageCache; 975 pageCache = []; 976 pageCount++; 977 } else { 978 for (var i = 0; i < pageCache.length; i++) { 979 // Dump and hide remaining elements 980 $(pageCache[i]).hide().appendTo($('.project_footer')); 981 } 982 } 983 984 } 985 986 $.each(textPages, function(key, arr) { 987 988 var breaks = 0; 989 $.each(arr, function(key, el) { 990 if (el.nodeName == "BR") { 991 breaks++; 992 } 993 994 }); 995 996 if (breaks < arr.length) { 997 var first = arr[0], 998 parent = $('<p />'); 999 1000 $(first).before(parent); 1001 1002 $.each(arr, function(key, el) { 1003 $(el).appendTo(parent); 1004 }); 1005 1006 1007 1008 } else { 1009 1010 $.each(arr, function(key, el) { 1011 $(el).remove(); 1012 }); 1013 } 1014 1015 }); 1016 1017 $('.project_content p').each(function(key) { 1018 1019 // Strip leading <br> 1020 var found_text = false; 1021 $(this) 1022 .contents() 1023 .filter(function() { 1024 if(this.nodeName != "br") { 1025 found_text = true; 1026 } 1027 return (!found_text); 1028 }) 1029 .remove(); 1030 1031 }); 1032 1033 } 1034 1035 }; 1036 1037 Site.Project = { 1038 1039 Data : { 1040 1041 'file_name' : 'thumb_size.json', 1042 'size_var' : 'thumb_size_list', 1043 'thumb_size_list' : false, 1044 'open' : false 1045 1046 }, 1047 1048 loadComplete : function() { 1049 1050 setTimeout(function(){ 1051 Site.Project.Data.open = true; 1052 }, 100); 1053 1054 // Cache 1055 var self = Site.Project, 1056 data = { }, 1057 ignoreList = '.project_title, .project_footer, span img, .in-text, .in-text *', 1058 mediaElements = 'img, video, iframe, object, audio, embed, div'; 1059 1060 // Cache 1061 Site.$el.entry = $('.entry'); 1062 Site.$el.projectContent = $('.project_content'); 1063 Site.$el.projectMedia = $('.project_media'); 1064 1065 // Only split on projects 1066 if ( Cargo.Helper.GetCurrentPageType() =="project" || Cargo.Helper.GetCurrentPageType() =="page" ){ 1067 // Split the content into blocks 1068 Site.Helper.formatText(Site.$el.projectContent); 1069 1070 // Move elements into containers 1071 Site.$el.projectContent 1072 .children(mediaElements) 1073 .not(ignoreList) 1074 .appendTo(Site.$el.projectMedia); 1075 }; 1076 1077 Site.$el.projectMedia.append('<img src="/_gfx/spacer.gif" class="spacer" width="1" height="2000" style="pointer-events:none; margin: 0; padding: 0; position: absolute; z-index: -99">'); 1078 1079 if ($('.project_content p').length > 0) { 1080 // Make double <br> into single 1081 $(".project_content p").html($(".project_content p").html().replace(/(<br\s*\/?>){2,2}/gi,'<br>')); 1082 // Strip the first <br> if it is first 1083 $(".project_content p").html($(".project_content p").html().replace(/^(<br\s*\/?>)/,'')); 1084 // Wrap everything 1085 $('.project_content p').wrap('<div class="textcolumns"></div>'); 1086 } 1087 1088 // Wrap all breaks in spans to measure their position 1089 $('.project_content p br').wrap('<span class="break_span" />'); 1090 1091 // If embedded objects have 100%, give them a max width of the user's max image width 1092 var embeddedMedia = $('.project_media > iframe, .project_media > object, .project_media > video, .project_media > audio, .project_media > embed'); 1093 1094 $(embeddedMedia).each(function() { 1095 if ($(this).attr('width') == '100%') { 1096 $(this).attr('width', parseInt(Cargo.Model.DisplayOptions.GetImageWidth())); 1097 } 1098 }); 1099 1100 // Prepend the title to the project content container, set width to text column width 1101 columnWidth = parseInt($('.project_content .textcolumns').css('width')); 1102 $('.project_title').prependTo('.project_content').css('maxWidth', columnWidth + 'px'); 1103 1104 // If there is no title and no content, remove the content div 1105 1106 var title_exists = Cargo.Model.DisplayOptions.get('title_in_project') && Cargo.Model.Project.get("show_title") && $('.project_title').css("display") != "none"; 1107 var content_exists = $.trim( $('.project_content').html()).length > 0 && $('.project_content').css("display") != "none"; 1108 var footer_exists = $('.project_footer').css("display") != "none" && $.trim( $('.project_footer > *').not('.editlink').html()).length > 0; 1109 1110 if ( !title_exists && !content_exists && !footer_exists){ 1111 $('.project_content, .project_footer').hide(); 1112 } 1113 1114 // Remove project media if no content 1115 if ((!$.trim( $('.project_media').html() ).length )) { 1116 $('.project_media').remove(); 1117 } 1118 1119 // Remove footer if no content 1120 if ((!$.trim( $('.project_footer').html() ).length )) { 1121 $('.project_footer').remove(); 1122 } 1123 1124 //Remove classes before adding them conditionally 1125 $('body #thumbnails').removeClass('inline-block'); 1126 1127 // If thumbs are set next to projects make them inline block 1128 if ((Cargo.Model.DisplayOptions.get('thumbs_below_pages') && Cargo.Helper.GetCurrentPageType() == "page") || (Cargo.Model.DisplayOptions.get('thumbs_below_projects') && Cargo.Helper.GetCurrentPageType() == "project")) { 1129 $('body #thumbnails').addClass('inline-block'); 1130 } else { 1131 $('.project_media > *:last-child').css('margin-right', '0'); 1132 } 1133 1134 // if no project media, no margin right 1135 if ($('.project_media').length <= 0) { 1136 $('.project_content').css('margin-right', '0'); 1137 } 1138 1139 // Append the footer if there is text to the text container, or append it to project_content 1140 if ($('.textcolumns').length > 0) { 1141 $('.project_footer').appendTo('.project_content .textcolumns'); 1142 } else { 1143 $('.project_footer').appendTo('.project_content'); 1144 } 1145 1146 // add img_holder around each project media img 1147 $('.project_media > img').not('.spacer').wrap('<div class="img_holder" data-elementresizer-no-centering />'); 1148 1149 1150 // Set variables for calculating ColumnizeText 1151 Design.setStageProperties(); 1152 Design.titleHeight(); 1153 Design.intextImageHeight(); 1154 1155 // Find the height of the content before it is columnized 1156 Design.data.textBodyStartHeight = $('.project_content .textcolumns').height() + Design.data.intextImageHeight; 1157 1158 // Add event to fire things when it is complete 1159 Cargo.Event.trigger("formatting_complete", "Cargo"); 1160 1161 }, 1162 1163 mediaLinks: function () { 1164 1165 // if user wants an image to have an external link (they must wrap with a blank div) 1166 // Make sure this div works in element resizer and has a set heigh & width 1167 1168 $('.project_media > div').each(function() { 1169 1170 if (this.attributes.length === 0 ){ 1171 1172 imgPadding = parseInt($('.project_media img').css('margin-right')); 1173 this_Width = $(this).find('img').width(); 1174 1175 $(this).attr('data-elementresizer-no-centering', ''); 1176 $(this).find('a').attr('data-elementresizer-no-centering', ''); 1177 1178 $(this).width(this_Width + imgPadding); 1179 $(this).find('a').width(this_Width + imgPadding); 1180 $(this).find('img').css('margin-left', '0'); 1181 1182 } 1183 1184 }); 1185 1186 } 1187 1188}; 1189 1190/** 1191 * Events 1192 */ 1193 1194$(function() { 1195 1196 // run mobile init if it has not already 1197 if (!$('body').hasClass('phone')) { 1198 Design.Mobile.init(); 1199 } 1200 1201 // display the pagination loader 1202 $('#autopaginate_loader').css('display', 'block'); 1203 1204 // set first thumbsize and run first isotope 1205 Design.setThumbSizeAfterFirstLoad(); 1206 Design.dataRows(); 1207 1208 // if not on the phone, format sets 1209 if (!Cargo.Helper.isPhone()) { 1210 Design.setFormatting(); 1211 } 1212 1213 Cargo.Core.ReplaceLoadingAnims.init(); 1214 Design.bindKeys(); 1215 Design.hoverProject(); 1216 1217 // hide the project until ready to show 1218 $('.project').css('visibility', 'hidden'); 1219 1220}); 1221 1222 1223// Window Resize 1224$(window).on('resize', function() { 1225 1226 Design.setStageProperties(); 1227 Design.setThumbSize(); 1228 Design.horizontalIsotope(); 1229 1230 Design.columnizeText(); 1231 1232 Site.Project.mediaLinks(); 1233 1234 if (Cargo.Helper.isMobile()) { 1235 setTimeout(function(){ 1236 Design.setResizerOptions(); 1237 }, 250) 1238 } 1239}); 1240 1241// Project Load Complete 1242Cargo.Event.on("project_load_complete", function(pid) { 1243 1244 // load complete sometimes fires before doc.ready 1245 // For direct links, this is a problem, so delay this event 1246 if($("body[data-mobileload!='true']").length == 1) { 1247 setTimeout(function() { 1248 Cargo.Event.trigger("project_load_complete", pid); 1249 }, 100); 1250 return false;
1251 } 1252 1253 // Remove active state on Set link if thumbnails are hidden 1254 if ( (Cargo.Helper.GetCurrentPageType() =="page" && !Cargo.Model.DisplayOptions.get("thumbs_below_pages") && Cargo.Helper.IsOnSet()) ) { 1255 1256 $('.set_link.active').removeClass("active"); 1257 1258 } 1259 1260 Design.setStageProperties(); 1261 1262 // if we haven't already isotoped, run the first isotope 1263 if ($('#thumbnails').hasClass('first-isotope')) { 1264 Design.setThumbSizeAfterFirstLoad(); 1265 } 1266 1267 Site.Project.loadComplete(); 1268 1269 Site.Project.mediaLinks(); 1270 1271 $('.project_media').width(Design.data.allMediaWidth); 1272 1273 Design.setProjectMediaSize(); 1274 1275 Design.setResizerOptions(); 1276 1277 Design.thumbInfoClick(); 1278 1279 // scroll to the left on load 1280 Cargo.Helper.ScrollToLeft( $('#slide_container') ); 1281 1282 // scroll to left of project if you click on the active project thumb 1283 $('.project_thumb .active .thumb_image').click( function() { 1284 setTimeout(function() { 1285 Cargo.Helper.ScrollToLeft( $('#slide_container') ); 1286 }, 10) 1287 }); 1288 1289 1290}); 1291 1292 1293 1294Cargo.Event.on("project_load_start", function() { 1295 1296 $('.project_media').css('visibility', 'hidden'); 1297 1298}); 1299 1300Cargo.Event.on("formatting_complete", function() { 1301 1302 Design.setThumbSize(); 1303 1304 $('.project').css('visibility', 'visible'); 1305 1306 Design.captionFormatting(); 1307 1308 Design.columnizeText(); 1309 1310 if (!Cargo.Helper.isMobile() && Cargo.Model.DisplayOptions.get('image_scroll') == true && Cargo.Model.DisplayOptions.get('lightbox_view') == false) { 1311 1312 Design.imageScroll(); 1313 1314 } 1315 1316 // Re-check for audio components that have moved 1317 Cargo.Core.Audio.CheckForAudio(); 1318 1319 1320}); 1321 1322Cargo.Event.on("thumbsize_complete", function() { 1323 1324 Design.adjustStage(); 1325 1326}); 1327 1328 1329Cargo.Event.on("elementresizer_update_complete", function() { 1330// Set width for project media 1331 $('.project_media').width(Design.data.allMediaWidth); 1332 Design.setProjectMediaSize(); 1333 1334}); 1335 1336Cargo.Event.on("pagination_start", function() { 1337 1338 // add some extra width to thumbnails container, so we don't run pagination if thumbnails end in the center of the window 1339 $("#thumbnails").width($("#thumbnails").width()+ 500); 1340 1341}); 1342 1343Cargo.Event.on("pagination_complete", function() { 1344 1345 Design.isotopeOnPagination(); 1346 1347 Design.hoverProject(); 1348 1349}); 1350 1351Cargo.Event.on("column_complete", function() { 1352 1353 Design.setProjectMediaSize(); 1354 Design.noBreaksOnTop(); 1355 1356 1357}); 1358 1359Cargo.Event.on("project_change", function() { 1360 1361 $('body #thumbnails').removeClass('inline-block'); 1362 1363 if (!$('.project').hasClass('adjust_stage')) { 1364 setTimeout(function() { 1365 Design.adjustStage(); 1366 }, 100) 1367 } 1368 1369}); 1370
1371Cargo.Event.on("show_index_start", function() { 1372 1373 // run mobile init if it has not already 1374 if (!$('body').hasClass('phone')) { 1375 Design.Mobile.init(); 1376 } 1377 1378 // make sure the project thumbs are hidden 1379 $(".project_thumb").css('visibility', 'hidden'); 1380 1381 // scroll everything to left 1382 setTimeout(function() { 1383 Cargo.Helper.ScrollToLeft( $('#slide_container') ); 1384 }, 10) 1385 1386 Design.setStageProperties(); 1387 Design.setProjectMediaSize(); 1388 1389}); 1390 1391Cargo.Event.on("admin_edit_load_complete", function() {}); 1392 1393Cargo.Event.on("show_index_complete", function(pid) { 1394 1395 Design.setStageProperties(); 1396 1397 // make sure un-isotoped images are hidden 1398 $(".project_thumb[data-rowed!='true']").css('visibility', 'hidden'); 1399 1400 // if thumbnails have been isotoped, set the first thumb size 1401 if ($('#thumbnails').hasClass('first-isotope')) { 1402 Design.setThumbSizeAfterFirstLoad(); 1403 } 1404 1405 // remove inline-block class from thumbnails for index 1406 $('body #thumbnails').removeClass('inline-block'); 1407 1408}); 1409 1410 1411Cargo.Event.on("slideshow_on", function(el, obj) { 1412 1413 slide_length = $('.slideshow').length; 1414 slide_pad = parseInt($('.slideshow').css('margin-right')); 1415 default_img_w = parseInt(Cargo.Model.DisplayOptions.get('image_width')); 1416 1417 Design.data.allMediaWidth = slide_length * (slide_pad+default_img_w); 1418 1419 $('.project_media').width(Design.data.allMediaWidth); 1420 1421 Design.setProjectMediaSize(); 1422 1423}); 1424 1425Cargo.Event.on("reseed_navigation_complete", function() { 1426 1427 // hide the index before the page reloads 1428 $('#index').css('visibility', 'hidden'); 1429 1430 // if not on the phone, format sets 1431 if (!Cargo.Helper.isPhone()) { 1432 Design.setFormatting(); 1433 } 1434 1435 // hard reload the page 1436 document.location.href = document.location.href; 1437 1438}); 1439 1440Cargo.Event.on("navigation_set_toggle", function() {}); 1441 1442Cargo.Event.on("first_project_collection_reset", function() { 1443 1444 // if has isotope, destroy isotope 1445 if ($(".thumbnails").hasClass('isotope')) { 1446 $(".thumbnails").isotope('destroy'); 1447 } 1448 1449 Design.setStageProperties(); 1450 1451 Design.setResizerOptions(); 1452 1453}); 1454 1455Cargo.Event.on("fullscreen_destroy_hotkeys", function() { 1456 1457 Design.bindKeys(); 1458 1459}); 1460 1461Cargo.Event.on('fullscreen-initialized', function(fullscreen_view){ 1462 fullscreen_view.prevent_smart_image_picking = true; 1463}); 1464 1465// easeOutExpo easing effect (used in imageScroll) 1466jQuery.extend( jQuery.easing, 1467 { 1468 easeOutExpo: function (x, t, b, c, d) { 1469 return (t==d) ? b+c : c * (-Math.pow(2, -10 * t/d) + 1) + b; 1470 }, 1471});
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.