Page scrolls to top also fixed navbar when external link opens Tab - javascript

I have a link in my navigation that opens a specific tab on a page, the link works fine, but the page opens so the beginning of the content is hidden by the fixed navbar. Can anybody help me, I am new to bootstrap and not very good in java:
var gotoHashTab = function (customHash) {
var hash = customHash || location.hash;
var hashPieces = hash.split('?'),
activeTab = $('[href=' + hashPieces[0] + ']');
activeTab && activeTab.tab('show');
}
// onready go to the tab requested in the page hash
gotoHashTab();
// when the nav item is selected update the page hash
$('.nav a').on('shown', function (e) {
window.location.hash = e.target.hash;
})
// when a link within a tab is clicked, go to the tab requested
$('.tab-pane a').click(function (event) {
if (event.target.hash) {
gotoHashTab(event.target.hash);
}
});
or is there a better script to use external links to open a specific tab on different page for bootstrap 3 ?

Put the class .anchor on the anchor (the target).
If the navbar is only fixed on certain sizes, then where the ???px is, put the min-width of that breakpoint (992px for md and up, 1200px for large and up, and 768px for small and up).
#media (min-width: ???px) {
.anchor {
padding-top: 60px;
margin-top: -60px;
}
}
If fixed at all screen sizes:
.anchor {
padding-top: 60px;
margin-top: -60px;
}
Assumes height of 50px on the navbar. Also, this may not be necessary if your body top padding has the padding of the height of navbar as per the getbootstrap.com examples.

Related

Unable to find code that hides left menu on smaller screens

I've been asked to make an update to the left side nav menu on our website whesearchreporting.com (you can enter anything for the username & password, if you'd like to access the site. Site's still in test mode). Currently, the nav menu is visible on full width screens, but if you reduce your screen width to around 900px), the menu disappears but can be expanded via a menu toggle icon in the top left. They would now however, like to change this logic to the following, which I'm having problems figuring out how to fix:
On a full screen, there is no menu toggle button visible in the top left. The menu always stays open
On a small or mobile screen, the menu toggle button becomes visible.
So basically, I need to find the code that handles making the left nav menu disappear when the screen size is reduced to around 950px & apply that same logic to the top left menu toggle icon. Is this something handled in bootstrap?
If it helps, here's some of the code that handles making my nav menu smaller or larger (although I don't think it has much to do with making the menu disappear on smaller screens):
$(function () {
$('#sidebar-menu li ul').slideUp();
$('#sidebar-menu li').removeClass('active');
$('#sidebar-menu li').on('click touchstart', function() {
var link = $('a', this).attr('href');
if(link) {
window.location.href = link;
} else {
if ($(this).is('.active')) {
$(this).removeClass('active');
$('ul', this).slideUp();
} else {
$('#sidebar-menu li').removeClass('active');
$('#sidebar-menu li ul').slideUp();
$(this).addClass('active');
$('ul', this).slideDown();
}
}
});
$('#menu_toggle').click(function () {
if ($('body').hasClass('nav-md')) {
$('body').removeClass('nav-md').addClass('nav-sm');
$('.left_col').removeClass('scroll-view').removeAttr('style');
$('.sidebar-footer').hide();
if ($('#sidebar-menu li').hasClass('active')) {
$('#sidebar-menu li.active').addClass('active-sm').removeClass('active');
}
} else {
$('body').removeClass('nav-sm').addClass('nav-md');
$('.sidebar-footer').show();
if ($('#sidebar-menu li').hasClass('active-sm')) {
$('#sidebar-menu li.active-sm').addClass('active').removeClass('active-sm');
}
}
});
});
And here's the html for that code section:
<div class="nav toggle">
<a id="menu_toggle"><i class="fa fa-bars"></i></a>
</div>
Any idea where I should be looking to find the code that handles making that menu disappear on smaller screens?
Thanks
You should search for #media queries in your Content/css/custom.css file

element css follows jquery declaration, not stylesheet

I have this initially in my .css stylesheet:
#media only screen and (min-width: 901px){
#main_panel {
width: 750px;
}
}
#media only screen and (min-width: 300px) and (max-width: 900px), handheld {
#main_panel {
width: 500px;
}
}
And then after some user interaction, this jQuery command changes this CSS-value:
$("#collapse").click(function() {
if ((($(window).width()) >= 600) && ($(window).width() <= 900)) {
$("#main_panel").animate({width: "500px"}, 'slow');
}
});
When I resize the window to more than 901px, it still follows the recent declaration by the jQuery and not the CSS-declaration in the stylesheet for 901px.
How to prioritize CSS-declaration when resizing the window?
Or how do you handle this better?
Please don't make me rely to $(window).resize() event forever :) That disregards the CSS.
** EDIT **
If you want to give priority to the CSS and still be able to animate it, what you probably need is this:
http://jsfiddle.net/2Fe22/1/
1) create a "normal" panel class and style it
.panel {width:750px;height:400px}
2) create a collapsed class and style it
.collapsed {width:500px}
3) create a function to read the collapsed and normal widths from the css:
function getClassWidth(aClass) {
return parseInt($("<div />").addClass(aClass).css('width'));
}
4) handle the click by first animating and then (at the end of the animation) add or remove the "collapsed" class to the panel and removing inline styles left by the animation:
var collapsed=false;
$("#collapse").click(function() {
collapsed=!collapsed;
if(collapsed) {
$("#main_panel").animate({width: (getClassWidth('collapsed'))+"px"}, 'slow',afterAnimation);
} else {
$("#main_panel").animate({width: (getClassWidth('panel'))+"px"}, 'slow',afterAnimation);
}
});
function afterAnimation() {
if(collapsed) $("#main_panel").addClass( "collapsed" ).removeAttr("style");
else $("#main_panel").removeClass( "collapsed" ).removeAttr("style");
}
You do this, so if the user resizes the window and the css changes your screen updates correctly.
** OLD POST (for reference) **
If you set sizes with JQuery you may go on setting them this way:
var collapsed=false;
$( window ).resize(calculateNewSizes); // When resized
calculateNewSizes(); // At startup
function calculateNewSizes() {
if(collapsed) {
// if screen width < xxx set elemt width to yyy, etc.. collapsed version
} else {
// if screen width < xxx set elemt width to yyy, etc..
}
}
// This toggles the collapsed state if user clicks on an element
$("#collapse").click(function() {
collapsed=!collapsed;
calculateNewSizes(); // or do the animation here
});
This script should be called as fast as possible after the beginning of all the elements to be resized to avoid a FOUC.
<div class="to be resized">
<script>
//do the $( window ).resize(...) here
</script>
... all other stuff </div>.
Warning, this code is UNTESTED. It is just to show an idea.
Since you are using jQuery Animate, the element style will directly receive width value.
Like this:
<el id="mainpanel" style="width: 500px">
This will always override any css on the element unless you use !IMPORTANT:
width: 100px !IMPORTANT;
http://codepen.io/rafaelcastrocouto/pen/suEHn (DEMO)
Notice that you should avoid that since you won't be able to change this if you need.

slideToggle overriding media queries

I am trying to create a slideToggle navigation only on mobile. However, the settings are also affecting the larger browser sizes. On the large browser, the first child is hidden:
#menu-menu-1 li {
display: block;
}
#menu-menu-1 li:first-child {
display: none;
}
And on mobile, it is reversed. The first child is shown, the rest hidden:
#menu-menu-1 li {
display: none;
}
#menu-menu-1 li:first-child {
display: block;
}
And thus, because the first child is now set to display:block, you can use this slideToggle:
$('#menu-menu-1 li:first-child').click(function(e){
e.preventDefault();
$('#menu-menu-1 li:first-child').siblings().slideToggle();
});
This works fine, until you use it to slide the content back up, and change the browser size back. That makes all the siblings set back to display:none, even though the larger browser media queries has them at display:block .
Is there a way as soon as the browser is expanded, the slideToggle settings are ignored?
This is a module I wrote to help with the problem of triggering javascript when I want it on resize and to help with chekcing the size:
jQuery(function($){
//resize window events
//store the reference outside the event handler:
var $window = $(window);
function checkWidth() {
var windowSize = $window.width();
return windowSize;
}
// Execute on load
checkWidth();
// Bind event listener
//remove console.log from production version
$(window).resize(function(){
console.log('checkWidth: ', checkWidth() + 'px' );
if(checkWidth() >= [yourDesiredWidth]){
//do something
}
});
});

jquery nav menu not marking current page when click on sub menu

here is my jsfiddle: http://jsfiddle.net/HhBEJ/3/
Despite some of the code not looking good in jsfiddle because i have background images and such - I am having a problem with my nav menu.
What I want it to do is:
When I load the page(index.htm) I want it to have a page marker ( which i have named current) to mark that I'm currently on the home page. When I click on another page to navigate to - I want it to remove current from prev page and make curPage the new current (you can see I did this in jquery (i think i did it right)) and if i click on a sub menu. for instance i go to "web > web215 > JavaScript" when I click on javaScript I want the Web parent Web215 child AND the javaScript grandchild to highlight all with the 'current' id. but it's not doing it to any of them except for a quick second when i click - it's not saving it when the page loads. I think the culprit is somewhere in here:
function youAreHere() {
var pathName = $(location).attr('pathname');
var curPage = pathName.substring(pathName.lastIndexOf('/') + 1);
$('a').each(function () {
if ($(this).attr('href') == curPage) {
$(this).attr('id', 'current');
} else if (curPage == '') {
$('a:first').attr('id', 'current');
}
}); //END function
I know when i put an alert it's calling the page correctly and it's working as intended but the current class isn't either A: staying after it loads or B: loading up at all.
your css is wrong, you are setting the id of current to the a tag but in the css you are setting the id of current to the li tag. This is what you need:
div#menu li a#current {
font-weight: bold;
font-size: 16px;
z-index: 6;
background: transparent url('../images/menu_level1_item.png') repeat-x scroll 0pt 100%;
}
div#menu li a#current ul {
font-weight: normal;
font-size: 12px;
}

Store positioning information from each element (JQuery/Javascript)

Pleasantries
I've been playing around with this idea for a couple of days but can't seem to get a good grasp of it. I feel I'm almost there, but could use some help. I'm probably going to slap myself right in the head when I get an answer.
Actual Problem
I have a series of <articles> in my <section>, they are generated with php (and TWIG). The <article> tags have an image and a paragraph within them. On the page, only the image is visible. Once the user clicks on the image, the article expands horizontally and the paragraph is revealed. The article also animates left, thus taking up the entire width of the section and leaving all other articles hidden behind it.
I have accomplished this portion of the effect without problem. The real issue is getting the article back to where it originally was. Within the article is a "Close" <button>. Once the button is clicked, the effect needs to be reversed (ie. The article returns to original size, only showing the image, and returns to its original position.)
Current Theory
I think I need to retrieve the offset().left information from each article per section, and make sure it's associated with its respective article, so that the article knows where to go once the "Close" button is clicked. I'm of course open to different interpretations.
I've been trying to use the $.each, each(), $.map, map() and toArray() functions to know avail.
Actual Code
/*CSS*/
section > article.window {
width:170px;
height:200px;
padding:0;
margin:4px 0 0 4px;
position:relative;
float:left;
overflow:hidden;
}
section > article.window:nth-child(1) {margin-left:0;}
<!--HTML-->
<article class="window">
<img alt="Title-1" />
<p><!-- I'm a paragraph filled with text --></p>
<button class="sClose">Close</button>
</article>
<article class="window">
<!-- Ditto + 2 more -->
</article>
Failed Attempt Example
function winSlide() {
var aO = $(this).parent().offset()
var aOL = aO.left
var dO = $(this).offset()
var dOL = dO.left
var dOT = dO.top
var adTravel = dOL-aOL
$(this).addClass('windowOP');
$(this).children('div').animate({left:-(adTravel-3)+'px', width:'740px'},250)
$(this).children('div').append('<button class="sClose">Close</button>');
$(this).unbind('click', winSlide);
}
$('.window').on('click', winSlide)
$('.window').on('click', 'button.sClose', function() {
var wW = $(this).parents('.window').width()
var aO = $(this).parents('section').offset()
var aOL = aO.left
var pOL = $(this).parents('.window').offset().left
var apTravel = pOL - aOL
$(this).parent('div').animate({left:'+='+apTravel+'px'},250).delay(250, function() {$(this).animate({width:wW+'px'},250); $('.window').removeClass('windowOP');})
$('.window').bind('click', winSlide)
})
Before you go scratching your head, I have to make a note that this attempt involved an extra div within the article. The idea was to have the article's overflow set to visible (.addclass('windowOP')) with the div moving around freely. This method actually did work... almost. The animation would fail after it fired off a second time. Also for some reason when closing the first article, the left margin was property was ignored.
ie.
First time a window is clicked: Performs open animation flawlessly
First time window's close button is clicked: Performs close animation flawlessly, returns original position
Second time SAME window is clicked: Animation fails, but opens to correct size
Second time window's close button is clicked (if visible): Nothing happens
Thank you for your patience. If you need anymore information, just ask.
EDIT
Added a jsfiddle after tinkering with Flambino's code.
http://jsfiddle.net/6RV88/66/
The articles that are not clicked need to remain where they are. Having problems achieving that now.
If you want to go for storing the offsets, you can use jQuery's .data method to store data "on" the elements and retrieve it later:
// Store offset before any animations
// (using .each here, but it could also be done in a click handler,
// before starting the animation)
$(".window").each(function () {
$(this).data("closedOffset", $(this).position());
});
// Retrieve the offsets later
$('.window').on('click', 'button.sClose', function() {
var originalOffset = $(this).data("originalOffset");
// ...
});
Here's a (very) simple jsfiddle example
Update: And here's a more fleshed-out one
Big thanks to Flambino
I was able to create the effect desired. You can see it here: http://jsfiddle.net/gck2Y/ or you can look below to see the code and some explanations.
Rather than having each article's offset be remembered, I used margins on the clicked article's siblings. It's not exactly pretty, but it works exceptionally well.
<!-- HTML -->
<section>
<article>Click!</article>
<article>Me Too</article>
<article>Me Three</article>
<article>I Aswell</article>
</section>
/* CSS */
section {
position: relative;
width: 404px;
border: 1px solid #000;
height: 100px;
overflow:hidden
}
article {
height:100px;
width:100px;
position: relative;
float:left;
background: green;
border-right:1px solid orange;
}
.expanded {z-index:2;}
//Javascript
var element = $("article");
element.on("click", function () {
if( !$(this).hasClass("expanded") ) {
$(this).addClass("expanded");
$(this).data("originalOffset", $(this).offset().left);
element.data("originalSize", {
width: element.width(),
height: element.height()
});
var aOffset = $(this).data("originalOffset");
var aOuterWidth = $(this).outerWidth();
if(!$(this).is('article:first-child')){
$(this).prev().css('margin-right',aOuterWidth)
} else {
$(this).next().css('margin-left',aOuterWidth)
}
$(this).css({'position':'absolute','left':aOffset});
$(this).animate({
left: 0,
width: "100%"
}, 500);
} else {
var offset = $(this).data("originalOffset");
var size = $(this).data("originalSize");
$(this).animate({
left: offset + "px",
width: size.width + "px"
}, 500, function () {
$(this).removeClass("expanded");
$(this).prev().css('margin-right','0')
$(this).next().css('margin-left','0')
element.css({'position':'relative','left':0});
});
}
});​

Categories