Sign up ×
Stack Overflow is a community of 4.7 million programmers, just like you, helping each other. Join them, it only takes a minute:

I am trying to create a 3D ribbon using CSS and JavaScript.

Main features needed are:

  1. Ribbon should use sticky scroll method. i.e. moves from bottom to top on page scroll and then get fixed at the top.
  2. 3D effect in ribbon, it changes it's perspective on scroll

I have created the effect, here's the demo page: http://staging.xhtml-lab.com/ribbon/

You can check the code by using view source, JS is at the bottom of page.

But it have some bugs, which i am not being able to fix and looking for help:

  1. Corner (triangles) are not moving properly on scroll
  2. It works fine if i scroll slowly, but everything is messed up on scrolling fast
  3. If i scroll down and refresh the page, ribbon is moved down and calculations are messed up.

I am looking for help to fix these issues.

Following is the JS code:

        $(document).ready(function() {

            var docHeight = $(window).height();
            var ribbonOffsetTop = 200;
            var ribbonOffsetBottom = 50;
            var initialPosition = parseInt($('#ribbon').css('top'));
            var lastScrollTop = 0;

            var ribbonHeight = 74;
            var availableScroll = docHeight-ribbonOffsetTop-ribbonOffsetBottom;
            var step = availableScroll/34;
            var remainingScroll = availableScroll-step;
            var stepsMoved = 0;

            console.log(availableScroll);

            $(window).scroll(function() {
                var st = $(this).scrollTop();

                if (st > lastScrollTop){
                    // downscroll code - Ribbon moving up
                    if (parseInt($('#ribbon').css('top')) > ribbonOffsetTop) {
                        $('#ribbon').css('top', initialPosition - parseInt(st));

                        var scrollingPosition = docHeight-st-ribbonOffsetTop-ribbonOffsetBottom;
                        if(remainingScroll > scrollingPosition) {
                            remainingScroll -= step;

                            $('.ribbon-front').css("top", $('.ribbon-front').position().top - 1);

                            if(stepsMoved < 17) {
                                $('.ribbon-edge-innerleft, .ribbon-edge-outerleft').css("border-width", (17 - stepsMoved)+"px 26px 0 0");
                                $('.ribbon-edge-innerright, .ribbon-edge-outerright').css("border-width", (17 - stepsMoved)+"px 0 0 26px");
                                $('.ribbon-edge-outerleft, .ribbon-edge-outerright').css("top", stepsMoved-34);
                            } else {
                                $('.ribbon-edge-innerleft, .ribbon-edge-innerright').css("top", stepsMoved -17);
                                $('.ribbon-edge-outerleft, .ribbon-edge-outerright').css("top", "23px");
                                $('.ribbon-edge-innerleft, .ribbon-edge-outerleft').css("border-width", "0px 26px "+(stepsMoved - 17)+"px 0");
                                $('.ribbon-edge-innerright, .ribbon-edge-outerright').css("border-width", "0px 0 "+(stepsMoved - 17)+"px 26px");
                            }
                            stepsMoved ++;
                        }
                    }
                } else if (st < lastScrollTop ) {
                    // upscroll code - Ribbon moving down
                    if (parseInt($(this).scrollTop()) <= docHeight-ribbonOffsetTop-ribbonOffsetBottom) {
                        $('#ribbon').css('top', (docHeight-parseInt(st))-ribbonHeight);

                        var scrollingPosition = docHeight-st-ribbonOffsetTop-ribbonOffsetBottom;

                        if(remainingScroll < scrollingPosition) {
                            remainingScroll += step;

                            $('.ribbon-front').css("top", $('.ribbon-front').position().top + 1);

                            if(stepsMoved > 17) {
                                $('.ribbon-edge-innerleft, .ribbon-edge-outerleft').css("border-width", "0px 26px "+(stepsMoved - 17)+"px 0");
                                $('.ribbon-edge-innerright, .ribbon-edge-outerright').css("border-width", "0px 0 "+(stepsMoved - 17)+"px 26px");
                            } else {
                                $('.ribbon-edge-innerleft, .ribbon-edge-innerright').css("top", stepsMoved -17);
                                $('.ribbon-edge-outerleft, .ribbon-edge-outerright').css("top", "23px");
                                $('.ribbon-edge-innerleft, .ribbon-edge-outerleft').css("border-width", (17 - stepsMoved)+"px 26px 0 0");
                                $('.ribbon-edge-innerright, .ribbon-edge-outerright').css("border-width", (17 - stepsMoved)+"px 0 0 26px");
                                $('.ribbon-edge-outerleft, .ribbon-edge-outerright').css("top", stepsMoved-34);
                            }
                            stepsMoved --;
                        }
                    }
                }
                lastScrollTop = st;
            });

        });
share|improve this question

closed as too localized by William Tate, George Cummins, Mario Sannum, khr055, Achrome Jun 14 '13 at 22:56

This question is unlikely to help any future visitors; it is only relevant to a small geographic area, a specific moment in time, or an extraordinarily narrow situation that is not generally applicable to the worldwide audience of the internet. For help making this question more broadly applicable, visit the help center.If this question can be reworded to fit the rules in the help center, please edit the question.

    

Browse other questions tagged or ask your own question.