Browse Source

Rewrite of sticky's crucial 'stick' function to be more coherent, deal with scrolling better. Fixes to grid/menu/list. Demo page footer

pull/1129/head
jlukic 10 years ago
parent
commit
1758250f39
12 changed files with 233 additions and 157 deletions
  1. 2
      server/documents/elements/list.html.eco
  2. 5
      server/files/javascript/semantic.js
  3. 39
      server/files/stylesheets/semantic.css
  4. 24
      server/layouts/default.html.eco
  5. 7
      src/definitions/collections/grid.less
  6. 12
      src/definitions/elements/list.less
  7. 5
      src/definitions/elements/segment.less
  8. 267
      src/definitions/modules/sticky.js
  9. 9
      src/themes/packages/default/collections/grid.variables
  10. 2
      src/themes/packages/default/collections/menu.variables
  11. 17
      src/themes/packages/default/elements/list.variables
  12. 1
      src/themes/packages/default/globals/site.variables

2
server/documents/elements/list.html.eco

@ -837,7 +837,7 @@ themes : ['Default']
</div>
</div>
</div>
</div>
</div>

5
server/files/javascript/semantic.js

@ -118,7 +118,7 @@ semantic.ready = function() {
$examples = $exampleSet.slice(firstIndex, lastIndex + 1),
activeClass = (index === 0)
? 'active '
: 'active '
: ''
;
html += '<div class="item">';
html += '<a class="'+activeClass+'title"><i class="dropdown icon"></i> <b>' + $(this).text() + '</b></a>';
@ -163,7 +163,8 @@ semantic.ready = function() {
$sticky
.transition('fade', function() {
$sticky.sticky({
context: $container
context: $container,
offset: 50
});
})
;

39
server/files/stylesheets/semantic.css

@ -161,7 +161,6 @@ a:hover {
border-radius: 0px;
}
#example #menu .inverted.header {
margin-bottom: 0em;
color: rgba(255, 255, 255, 0.8);
}
#example #menu a.inverted.header.active,
@ -174,9 +173,6 @@ a:hover {
#example #menu .menu .active.item {
color: #6DFFFF !important;
}
#example #menu .item .item {
font-size: 0.875rem;
}
/* segment headers */
@ -754,6 +750,13 @@ body#example.hide {
width: auto;
}
/*----------------
Footer
-----------------*/
#example .page > .footer {
padding: 4em 0em;
}
/*----------------
Settings Table
@ -1438,44 +1441,46 @@ body.progress .ui.progress .bar {
}
#example .container {
position: relative;
right: 100px;
width: 915px;
margin: 0px auto;
}
#example .main.container .right.rail .sticky {
padding-top: 50px !important;
padding-bottom: 30px;
}
@media only screen and (max-width : 600px) {
#example .container {
width: auto;
margin: 0% 1em 0px;
margin: 0em 1rem;
}
}
@media only screen and (max-width : 1050px) {
@media only screen and (min-width : 600px) and (max-width : 1000px) {
#example .container {
width: auto;
margin: 0px 30px 0px;
margin: 0em 3rem;
}
}
@media only screen and (max-width : 1325px) {
#example .following.menu {
display: none;
}
@media only screen and (min-width : 1000px) and (max-width: 1325px) {
#example .container {
width: auto;
margin-right: auto;
margin-left: auto;
max-width: 700px;
}
#example.index .container {
margin-left: 8em;
margin-right: 8em;
}
@media only screen and (max-width : 1325px) {
#example .following.menu {
display: none;
}
}
@media only screen and (min-width : 1325px) {
#example .container {
right: 100px;
}
#example .following.menu {
display: block;
}
#example .container {
width: 850px;
}

24
server/layouts/default.html.eco

@ -254,6 +254,30 @@
<div class="pusher">
<div class="page">
<%- @content %>
<div class="ui vertical inverted black footer segment">
<div class="ui stackable page grid">
<div class="eight wide column">
<h3 class="ui inverted header">Keep Semantic UI Alive</h3>
<p>Donate money today to help fund the costs of development for Semantic UI</p>
<div class="ui inverted blue button">Donate</div>
</div>
<div class="four wide column">
<h5 class="ui inverted header">Contribute</h5>
<div class="ui inverted link list">
<a class="item">Translate</a>
<a class="item">Fix Bugs</a>
<a class="item">Create Themes</a>
</div>
</div>
<div class="four wide column">
<h5 class="ui inverted header">Semantic Network</h5>
<div class="ui inverted link list">
<a class="item">Semantic UI</a>
<a class="item">Learn Semantic</a>
<a class="item">Semantic Themes</a>
</div>
</div>
</div>
</div>
</div>
<script src="/javascript/library/less.js"></script>

7
src/definitions/collections/grid.less

@ -545,9 +545,14 @@
}
/* Inverted Divided */
.ui.inverted.divided.grid > .row {
.ui.inverted.divided.grid:not(.vertical) > .column,
.ui.inverted.divided.grid:not(.vertical) > .row > .column {
box-shadow: @dividedInvertedBorder;
}
.ui.inverted.divided.grid:not(.vertical) > .column:first-child,
.ui.inverted.divided.grid:not(.vertical) > .row > .column:first-child {
box-shadow: none;
}
.ui.inverted[class*="vertically divided"].grid > .row {
box-shadow: @verticallyDividedInvertedBorder;
}

12
src/definitions/elements/list.less

@ -282,14 +282,15 @@ ol.ui.list ol,
.ui.link.list a.item,
.ui.link.list .item a {
color: @linkListItemColor;
transition: @linkListTransition;
}
.ui.link.list a.item:hover,
.ui.link.list .item a:hover {
color:@linkListItemHoverColor;
color: @linkListItemHoverColor;
}
.ui.link.list a.item:active,
.ui.link.list .item a:active {
color:@linkListItemDownColor;
color: @linkListItemDownColor;
}
.ui.link.list .active.item,
.ui.link.list .active.item a {
@ -323,9 +324,14 @@ ol.ui.list ol,
cursor: pointer;
background: @selectionListBackground;
padding: @selectionListItemVerticalPadding @selectionListItemHorizontalPadding;
margin: @selectionListItemMargin;
color: @selectionListColor;
border-radius: @selectionListItemBorderRadius;
transition: @selectionListTransition;
}
.ui.selection.list .item:last-child {
margin-bottom: 0em;
}
.ui.selection.list .item:hover {
background: @selectionListHoverBackground;
color: @selectionListHoverColor;
@ -343,7 +349,7 @@ ol.ui.list ol,
.ui.inverted.selection.list .item {
background: @invertedSelectionListBackground;
color: @selectionListColor;
color: @invertedSelectionListColor;
}
.ui.inverted.selection.list .item:hover {
background: @invertedSelectionListHoverBackground;

5
src/definitions/elements/segment.less

@ -92,6 +92,11 @@
top: 1px;
}
/* Header */
.ui.inverted.segment > .ui.header {
color: @white;
}
/* Label */
.ui[class*="bottom attached"].segment > [class*="top attached"].label {
border-top-left-radius: 0em;

267
src/definitions/modules/sticky.js

@ -62,9 +62,6 @@ $.fn.sticky = function(parameters) {
module = {
initialize: function() {
if( !$module.is(':visible') ) {
module.error(error.visible, $module);
}
if(settings.context) {
$context = $(settings.context);
}
@ -75,17 +72,26 @@ $.fn.sticky = function(parameters) {
module.error(error.invalidContext, settings.context, $module);
return;
}
if(module.supports.sticky()) {
// needs to enable native ios support
module.verbose('Initializing sticky', settings, $container);
module.save.positions();
// error conditions
if( module.is.hidden() ) {
module.error(error.visible, $module);
}
if(module.cache.element.height > module.cache.context.height) {
module.reset();
module.error(error.elementSize, $module);
return;
}
$window
.on('resize' + eventNamespace, module.event.resize)
;
$scroll
.on('scroll' + eventNamespace, module.event.scroll)
;
module.verbose('Initializing sticky', settings, $container);
module.save.positions();
module.observeChanges();
module.instantiate();
},
@ -102,8 +108,10 @@ $.fn.sticky = function(parameters) {
module.verbose('Destroying previous module');
module.reset();
$window
.off('resize', module.event.resize)
.off('scroll', module.event.scroll)
.off('resize' + eventNamespace, module.event.resize)
;
$scroll
.off('scroll' + eventNamespace, module.event.scroll)
;
$module
.removeData(moduleNamespace)
@ -192,7 +200,7 @@ $.fn.sticky = function(parameters) {
}
;
module.cache = {
fits : ( element.height < $window.height() ),
fits : ( element.height < window.height ),
window: {
height: window.height
},
@ -233,30 +241,53 @@ $.fn.sticky = function(parameters) {
}
return direction;
},
currentOffset: function() {
return ( module.is.top() )
? parseInt($module.css('top'), 10) || 0
: parseInt($module.css('bottom'), 10) || 0
;
},
offsetChange: function(scroll) {
scrollChange: function(scroll) {
scroll = scroll || $scroll.scrollTop();
return (module.lastScroll)
? Math.abs(scroll - module.lastScroll)
? (scroll - module.lastScroll)
: 0
;
},
newOffset: function(scroll) {
currentElementScroll: function() {
return ( module.is.top() )
? Math.abs(parseInt($module.css('top'), 10)) || 0
: Math.abs(parseInt($module.css('bottom'), 10)) || 0
;
},
elementScroll: function(scroll) {
scroll = scroll || $scroll.scrollTop();
var
currentOffset = module.get.currentOffset(),
delta = module.get.offsetChange(scroll)
element = module.cache.element,
window = module.cache.window,
delta = module.get.scrollChange(scroll),
maxScroll = (element.height - window.height + settings.offset),
currentScroll = module.get.currentElementScroll(),
possibleScroll = (currentScroll + delta),
elementScroll
;
return Math.abs(currentOffset - delta);
if(possibleScroll < 0) {
elementScroll = 0;
}
else if (possibleScroll > maxScroll ) {
elementScroll = maxScroll;
}
else {
elementScroll = possibleScroll;
}
return elementScroll;
}
},
remove: {
offset: function() {
$module.css('margin-top', '');
}
},
set: {
offset: function() {
$module.css('margin-top', settings.offset);
},
containerSize: function() {
var
tagName = $container.get(0).tagName
@ -270,6 +301,18 @@ $.fn.sticky = function(parameters) {
$container.height(module.cache.context.height);
}
},
scroll: function(scroll) {
if( module.is.top() ) {
$module
.css('top', -scroll)
;
}
if( module.is.bottom() ) {
$module
.css('bottom', scroll)
;
}
},
size: function() {
if(module.cache.element.height !== 0 && module.cache.element.width !== 0) {
$module
@ -289,6 +332,12 @@ $.fn.sticky = function(parameters) {
bottom: function() {
return $module.hasClass(className.bottom);
},
initialPosition: function() {
return (!module.is.fixed() && !module.is.bound());
},
hidden: function() {
return (!$module.is(':visible'));
},
bound: function() {
return $module.hasClass(className.bound);
},
@ -304,114 +353,77 @@ $.fn.sticky = function(parameters) {
element = cache.element,
window = cache.window,
context = cache.context,
scrollTop = $scroll.scrollTop(),
screen = {
top : scrollTop + settings.offset,
bottom : scrollTop + window.height + settings.offset
scrollTop = $scroll.scrollTop() + settings.offset,
scroll = {
top : scrollTop,
bottom : scrollTop + window.height
},
direction = module.get.direction(scrollTop),
currentOffset = module.get.currentOffset(),
newOffset = module.get.newOffset(scrollTop),
elementPassed = (screen.bottom > element.top + element.height),
fixedBottom = (cache.element.height + screen.top)
elementScroll = module.get.elementScroll(scrollTop),
// shorthand
doesntFit = !fits,
elementVisible = (element.height !== 0)
;
// save current scroll for next run
module.save.scroll(scrollTop);
if(element.height !== 0) {
if( module.is.fixed() ) {
if(fits) {
// if module is fixed top
if(module.is.top()) {
if( screen.top < element.top ) {
module.unfix();
}
else if( fixedBottom > context.bottom ) {
module.debug('Top attached rail has reached bottom of container');
module.bindBottom();
}
}
// if module is fixed bottom
if(module.is.bottom() ) {
// top edge
if( (screen.bottom - element.height) < element.top) {
module.unfix();
}
// bottom edge
else if(screen.bottom > context.bottom) {
module.debug('Bottom attached rail has reached bottom of container');
module.bindBottom();
}
if(elementVisible) {
if( module.is.initialPosition() ) {
if(scroll.top >= element.top) {
module.debug('Element passed, fixing element to page');
module.fixTop();
}
}
else if( module.is.fixed() ) {
// currently fixed top
if( module.is.top() ) {
if( scroll.top < element.top ) {
module.debug('Fixed element reached top of container');
module.setInitialPosition();
}
if( fixedBottom > context.bottom ) {
else if( (element.height + scroll.top) > context.bottom ) {
module.debug('Fixed element reached bottom of container');
module.bindBottom();
}
}
else {
if(screen.bottom > context.bottom) {
module.bindBottom();
}
else if(elementPassed) {
if(module.is.top() && direction == 'down') {
module.debug('Stuck content at bottom edge');
if(newOffset >= (element.height - window.height)) {
$module
.css('top', '')
;
module.stickBottom();
}
else {
$module
.css('top', -newOffset)
;
}
}
if(module.is.bottom() && direction == 'up') {
module.debug('Stuck content at top edge');
if(newOffset >= (element.height - window.height)) {
$module
.css('bottom', '')
;
module.stickTop();
}
else {
$module
.css('bottom', -newOffset)
;
}
}
// currently fixed bottom
if(module.is.bottom() ) {
// top edge
if( (scroll.bottom - element.height) < element.top) {
module.setInitialPosition();
}
else {
module.unfix();
// bottom edge
else if(scroll.bottom > context.bottom) {
module.debug('Bottom attached rail has reached bottom of container');
module.bindBottom();
}
}
}
else {
// determine if needs to be bound
if(screen.top + element.height > context.bottom) {
module.bindBottom();
// scroll element if larger than screen
if(doesntFit) {
module.set.scroll(elementScroll);
}
if(fits) {
// fix to bottom of screen on way back up
if(module.is.bottom() ) {
if(settings.pushing) {
if(module.is.bound() && screen.bottom < context.bottom ) {
module.stickBottom();
}
}
else {
if(module.is.bound() && screen.top < context.bottom - element.height) {
module.stickTop();
}
}
else if( module.is.bottom() ) {
// fix to bottom of screen on way back up
if( module.is.bottom() ) {
if(settings.pushing) {
if(module.is.bound() && scroll.bottom < context.bottom ) {
module.fixBottom();
}
}
else if(screen.top >= element.top && screen.top < context.bottom - element.height) {
module.stickTop();
}
}
else {
if(elementPassed && screen.bottom < context.bottom ) {
module.stickBottom();
else {
if(module.is.bound() && (scroll.top < context.bottom - element.height) ) {
module.fixTop();
}
}
}
}
@ -420,6 +432,7 @@ $.fn.sticky = function(parameters) {
bindTop: function() {
module.debug('Binding element to top of parent container');
module.remove.offset();
$module
.css('left' , '')
.removeClass(className.fixed)
@ -432,6 +445,7 @@ $.fn.sticky = function(parameters) {
},
bindBottom: function() {
module.debug('Binding element to bottom of parent container');
module.remove.offset();
$module
.css('left' , '')
.removeClass(className.fixed)
@ -443,8 +457,15 @@ $.fn.sticky = function(parameters) {
$.proxy(settings.onUnstick, element)();
},
stickTop: function() {
setInitialPosition: function() {
module.unfix();
module.unbind();
},
fixTop: function() {
module.debug('Fixing element to top of page');
module.set.offset();
$module
.css('left', module.cache.element.left)
.removeClass(className.bound)
@ -455,8 +476,9 @@ $.fn.sticky = function(parameters) {
$.proxy(settings.onStick, element)();
},
stickBottom: function() {
fixBottom: function() {
module.debug('Sticking element to bottom of page');
module.set.offset();
$module
.css('left', module.cache.element.left)
.removeClass(className.bound)
@ -469,6 +491,7 @@ $.fn.sticky = function(parameters) {
unbind: function() {
module.debug('Removing absolute position on element');
module.remove.offset();
$module
.removeClass(className.bound)
.removeClass(className.top)
@ -478,6 +501,7 @@ $.fn.sticky = function(parameters) {
unfix: function() {
module.debug('Removing fixed position on element');
module.remove.offset();
$module
.removeClass(className.fixed)
.removeClass(className.top)
@ -689,9 +713,9 @@ $.fn.sticky.settings = {
name : 'Sticky',
namespace : 'sticky',
verbose : false,
debug : false,
performance : false,
verbose : true,
debug : true,
performance : true,
pushing : false,
@ -710,7 +734,8 @@ $.fn.sticky.settings = {
container : 'Sticky element must be inside a relative container',
visible : 'Element is hidden, you must call refresh after element becomes visible',
method : 'The method you called is not defined.',
invalidContext : 'Context specified does not exist'
invalidContext : 'Context specified does not exist',
elementSize : 'Sticky element is larger than its container, cannot create sticky.'
},
className : {

9
src/themes/packages/default/collections/grid.variables

@ -59,8 +59,8 @@
---------------*/
@dividedBorder:
-1px 0px 0px 0px rgba(0, 0, 0, 0.1),
-2px 0px 0px 0px rgba(255, 255, 255, 0.3)
-1px 0px 0px 0px rgba(255, 255, 255, 0.1),
-2px 0px 0px 0px rgba(0, 0, 0, 0.3)
;
@verticallyDividedBorder:
0px -1px 0px 0px rgba(0, 0, 0, 0.1),
@ -68,15 +68,14 @@
;
@dividedInvertedBorder:
-1px 0px 0px 0px rgba(0, 0, 0, 0.15),
-1px 0px 0px 0px rgba(255, 255, 255, 0.15),
-2px 0px 0px 0px rgba(0, 0, 0, 0.15)
;
@verticallyDividedInvertedBorder:
0px -1px 0px 0px rgba(0, 0, 0, 0.15),
0px -2px 0px 0px rgba(0, 0, 0, 0.15)
0px -2px 0px 0px rgba(255, 255, 255, 0.15)
;
/*--------------
Celled
---------------*/

2
src/themes/packages/default/collections/menu.variables

@ -60,7 +60,7 @@
/* Sub Menu */
@subMenuMargin: 0.5em;
@subMenuFontSize: 0.875rem;
@subMenuTextColor: @textColor;
@subMenuTextColor: @unselectedTextColor;
@subMenuHorizontalPadding: 0.5rem;
@subMenuVerticalPadding: 1.5rem;

17
src/themes/packages/default/elements/list.variables

@ -83,20 +83,25 @@
@linkListItemHoverColor: @hoveredTextColor;
@linkListItemDownColor: @pressedTextColor;
@linkListItemActiveColor: @selectedTextColor;
@linkListTransition:
0.2s color @defaultEasing
;
/* Inverted Link List */
@invertedLinkListItemColor: @invertedUnselectedTextColor;
@invertedLinkListItemHoverColor: @invertedUnselectedTextColor;
@invertedLinkListItemDownColor: @invertedTextColor;
@invertedLinkListItemHoverColor: @invertedHoveredTextColor;
@invertedLinkListItemDownColor: @invertedPressedTextColor;
@invertedLinkListItemActiveColor: @invertedSelectedTextColor;
/* Selection List */
@selectionListItemMargin: 0em 0em 0.3em 0em;
@selectionListItemBorderRadius: 0.5em;
@selectionListItemVerticalPadding: 0.5em;
@selectionListItemHorizontalPadding: 0.5em;
@selectionListTransition:
0.2s color ease,
0.2s padding-left ease,
0.2s background-color ease
0.2s color @defaultEasing,
0.2s padding-left @defaultEasing,
0.2s background-color @defaultEasing
;
/* Selection List States */
@selectionListBackground: transparent;
@ -114,7 +119,7 @@
@invertedSelectionListHoverBackground: @subtleTransparentWhite;
@invertedSelectionListHoverColor: @invertedHoveredTextColor;
@invertedSelectionListDownBackground: @transparentWhite;
@invertedSelectionListDownColor: @invertedHoveredTextColor;
@invertedSelectionListDownColor: @invertedPressedTextColor;
@invertedSelectionListActiveBackground: @transparentWhite;
@invertedSelectionListActiveColor: @invertedSelectedTextColor;

1
src/themes/packages/default/globals/site.variables

@ -151,6 +151,7 @@
@tealBackground : #D2F5F5;
@yellowBackground : #FCF5D8;
/*--- Colored Text ---*/
@blueTextColor : @blue;
@orangeTextColor : @orange;

Loading…
Cancel
Save