Spy Scroll Issue - scroll

I am making a webpage with a "time line" style, it's navigated horizontally but has a fixed menu with an element that slides along a bar when you click on every element.
Now I was using a blueprint of vertical timeline that also moved the element across the bar when you got to the element by scrolling normally
http://www.webdesigncrowd.com/demo/slider-timeline-menu-12.2.13/
Now, I am using a page-wrap div to keep the elements within a certain boundary along with a css style for the body to stack elements horizontally.
When I click on ever it takes me to the correct page like normal, and the bar element works as intended, but the feature for it to work when the linked element moves into view doesn't seem to work anymore
This is the original JS code
// Scroll Spy
$(window).scroll(function() {
var top = $(window).scrollTop() + 100; // Take into account height of fixed menu
$(".container").each(function() {
var c_top = $(this).offset().top;
var c_bot = c_top + $(this).height();
var hash = $(this).attr("id");
var li_tag = $('a[href$="' + hash + '"]').parent();
if ((top > c_top) && (top < c_bot)) {
if (li_tag.hasClass("active")) {
return false;
} else {
li_tag.siblings().andSelf().removeClass("active");
li_tag.addClass("active");
$(".menu ul li.active a").slideToPos();
}
}
});
});
And this is what I edited to try to make it work on a Horizontal display.
// Scroll Spy
$(window).scroll(function() {
var left = $(window).scrollLeft() + 1300; // Take into account height of fixed menu
$(".container").each(function() {
var c_Left = $(this).offset().left;
var c_bot = c_left + $(this).width();
var hash = $(this).attr("id");
var li_tag = $('a[href$="' + hash + '"]').parent();
if ((left > c_Left) && (left < c_bot)) {
if (li_tag.hasClass("active")) {
return false;
} else {
li_tag.siblings().andSelf().removeClass("active");
li_tag.addClass("active");
$(".menu ul li.active a .navut").slideToPos();
}
}
});
});
Now I have tried using the original one without change too, but that feature is still not working.
I thank you guys in advance.

Related

hammer.js detect variables in panmove and unbind when it hits certain criteria

my goal is detect when an element has reached a certain margin-left, and than unbind or stop the panmove from continuing if it hits that threshold.
I have a "panmove" bound to an element using hammer.js, and jquery hammer plugin.
I noticed that in the panmove, console.log(e) will fire hundreds of times as you move the elements, which is expected. If you however put an if statement in the panmove function, it only goes off of the initial state of the first panmove and not the current one.
.bind("panmove", function (e) {
var count = 0;
console.log(e);
console.log(count++);
var _this = $(e.target);
var _thisDataLeft = _this.attr("data-left");
var _thisDataMaxLeft = _this.attr("data-maxleft"); // this is derived from the width of the Delete box, which can be any width.
if (Math.abs(_thisDataLeft) < Number(_thisDataMaxLeft)) {
_this.css({ left: Number(_thisDataLeft) + e.gesture.deltaX }); // controls movement of top layer
console.log(count++);
}
I noticed that the console.log(count++) always fires 1, instead of iterating up, as if it is only reading it once in the beginning.
How can I run an if statement inside of this Pan, so that it is always the current information, and not just the first iteration?
Ended up moving away from Hammer.js, was not able to get the results I needed. It looks like the more basic jquery.event.move.js was easier to use than hammer.
here is my example in js fiddle
https://jsfiddle.net/williamhowley/o9uvo50y/
$(document).ready(function () {
// http://stephband.info/jquery.event.move/
// http://stephband.info/jquery.event.swipe/
// add swipe functionality to the rows.
// I think you will need to add the swipe left, after it is activated by a HOLD down press.
// idk, how do you always make something swipable.
var wrap = $('ul#main');
$('ul#main > li')
.on('movestart', function (e) {
console.log("move start");
// var $li = $(e.target).closest('.swipable'); // this would be normal live integration
var $li = $(e.target);
if ($li.attr("data-hasplaceholder") !== "true") { // if it does not have a placeholder, add one.
createBackgroundSpacer($li);
$li.attr("data-hasplaceholder", true); // signify that a placeholder has been created for this element already.
}
// If the movestart heads off in a upwards or downwards
// direction, prevent it so that the browser scrolls normally.
if ((e.distX > e.distY && e.distX < -e.distY) ||
(e.distX < e.distY && e.distX > -e.distY)) {
e.preventDefault();
return;
}
// To allow the slide to keep step with the finger,
// temporarily disable transitions.
wrap.addClass('notransition'); // add this to the container wrapper.
})
.on('move', function (e) {
// event definitions
// startX : 184, where from left the mouse curser started.
// deltaX: ?
// distX: how far the mouse has moved, if negative moving left. Still need to account for double movement, currently can only handle one movement.
console.log("move");
console.log(e);
var maxLeft = $('.rightContent').width();
var marginLeftNum = Number($(this).css('margin-left').replace(/[^-\d\.]/g, ''));
if (marginLeftNum <= -maxLeft && e.deltaX < 0) { // Case when user is at outermost left threshold, and trying to move farther left.
$(this).css({ 'margin-left': -maxLeft });
}
else if (marginLeftNum == -maxLeft && e.deltaX > 0) { // When user is at threshold, and trying to move back right.
$(this).css({ 'margin-left': marginLeftNum + e.deltaX });
}
else if (e.target.offsetLeft>=0 && e.deltaX>0) { // If the offset is 0 or more, and the user is scrolling right (which is a positive delta, than limit the element. )
$(this).css({ 'margin-left': 0 });
}
// Must have a Negative offset, and e.deltaX is Negative so it is moving left.
else if (e.deltaX < 0) { // Case when element is at 0, and mouse movement is going left.
$(this).css({ 'margin-left': marginLeftNum + e.deltaX });
}
else { // Moving Right when not on 0
$(this).css({ 'margin-left': marginLeftNum + e.deltaX });
}
})
.on('swipeleft', function (e) {
console.log("swipeleft");
})
.on('activate', function (e) {
// not seeing this activate go off, i think this is custom function we can add on if swipe left hits a threshold or something.
console.log("activate");
})
.on('moveend', function (e) {
console.log("move end");
wrap.removeClass('notransition');
});
var createBackgroundSpacer = function ($shoppingListRow) {
var border = 2;
$shoppingListRow.css({ 'width': $shoppingListRow.width() + border, 'height': $shoppingListRow.height() + border }); // gives itself set width and height
$shoppingListRow.addClass('swipable');
// placeholder HTML
var leftPlaceholder = $('<div class="leftPlaceholder"></div>').css({ 'height': $shoppingListRow.height()});
var rightPlaceholder = $('<div class="rightPlaceholder"></div>')
var rightContent = $('<div class="rightContent">Delete</div>').css({ 'height': $shoppingListRow.height()});
rightPlaceholder.append(rightContent);
var placeHolder = $('<div class="swipePlaceholder clearfix"></div>'); // goes around the two floats.
placeHolder.css({ 'width': $shoppingListRow.width(), 'height': $shoppingListRow.height() });
placeHolder.append(leftPlaceholder, rightPlaceholder);
$shoppingListRow.before(placeHolder); // adds placeholder before the row.
$shoppingListRow.css({ 'marginTop': -($shoppingListRow.height() + border) });
};
});

How to programmatically move a tab to another window in a firefox Addon-SDK extension?

While it looks like you can change the order of a tab within a window by updating the tab .index property, it doesn't look like the tabs api directly supports the move of a tab to another window.
Am I missing something? Is there a viable workaround?
It is possible through the low level module window/utils. The example below duplicates the active tab across every open window
const { getMostRecentBrowserWindow, windows: getWindows } = require("sdk/window/utils");
const { ActionButton } = require("sdk/ui/button/action");
var button = ActionButton({
id: "duplicatetab-button",
label: "Duplicate tab",
icon: "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAACUElEQVQ4jaWTTWtTURCGjzc33CCpbVKN4kexC9EUY1Hov+iqPyDrbgtuCrViKUERqsWVguBGQaW4UiKiaEVxoShFGgnuBMUqNW3zce49Z+ZxUWtwoRR8YXbzPswM7xj+JgVEiXGsYVknxgII4Ltt5p8AB8RArOAUVQfqQJNtAFA8QgvF6i9PR1Dt0KbVBTjncM4hIni/OZv3HsRB+wvefiP2LcQnJIkQe49FEJFNQLPZZHh4mEwmQyqVoqenh3K5TGvlK1dOlageH+HG4DFar1/S0A6Lr99xdN8QxWKRXC6HGR0dJZvNMjk5Sb1ep1gskk6nuTo/D+/ec7dvkBdhP9cKeX7UXxEZQ2/YRxRFLC8vY+bm5qhUKnjvsdYyPj5OFEWcnTnHujiS5TfcPDbAw50h9w7u5f7UadLZFLVaDRHBiGzuY61lbGyMXC5HoVBgrbGGWAW/TvvxHR7s7udFKs/1oyfZ+PSRTqeDqm7eoFqtEoYhmUyG2dlZVJU4iREfI/WP3Nt9iMUdu7jdf5Anly5i0oaVlRWazSZmYWGBIAiIoohyucz09DQTExPMnJli9dlT5vcM8Kh3gFsHDuNqb9mb7yXMRBhjWFpawpRKJVKpFMYYgiAgDEOCIOD81BkunBjh8pEhKqUhGkvP6bQ/U//wgUP5/YRhSDabxbTbbVQV5xyq2q0kgR8NdOM7JKuo/Y5qggqIdPvMlnkrQCKCquJFsOrxeHAJxA48eFU6Xv4EqOpv41YqnQirqliv4MEmQtN7RBSs7wL+/gvb038DfgJnyUabbHzUbQAAAABJRU5ErkJggg==",
onClick: function() {
var xulwindows = getWindows("navigator:browser");
var xulactivewindow = getMostRecentBrowserWindow();
var xulactivetab = xulactivewindow.gBrowser.selectedTab;
xulwindows.forEach(function(win){
if(win === xulactivewindow)
return;
var duplicatedtab = win.gBrowser.duplicateTab(xulactivetab);
win.gBrowser.moveTabTo(duplicatedtab, 0); // the second argument is the index
});
}
});
#paa's solution is nice but it doesn't move a tab. His is duplicating the tab. So flash movies will not retain their position etc. And its not a move its a duplicatio, like he explained.
I did a lot of research was real fun. The way they move tabs in Firefox is via docShell swapping. This will accomplish what you want. It's written for bootstrap though so needs touch up for addon sdk.
Pass second argument as string of tabbed or non-tabbed if you want to move it to a new window. Else pass second argument an existing window and it will be moved there. can copy paste and run this code from sratchpad.
this uses the gBrowser.swapBrowsersAndCloseOther function
function moveTabToWin(aTab, tDOMWin) {
//tDOMWin means target DOMWindow means the window you want the tab in
//if tDOMWin == 'tabbed' or == 'non-tabbed' it opens in a new window
//if aTopContWin is the last in its window, then its window is closed
if (tDOMWin == 'tabbed' || tDOMWin == 'non-tabbed') {
var sa = Cc["#mozilla.org/supports-array;1"].createInstance(Ci.nsISupportsArray);
var wuri = Cc["#mozilla.org/supports-string;1"].createInstance(Ci.nsISupportsString);
wuri.data = 'about:blank';
sa.AppendElement(wuri);
let features = "chrome,dialog=no";
if (tDOMWin == 'tabbed') {
features += ',all';
}
var sDOMWin = aTab.ownerGlobal; //source DOMWindow
if (PrivateBrowsingUtils.permanentPrivateBrowsing || PrivateBrowsingUtils.isWindowPrivate(sDOMWin)) {
features += ",private";
} else {
features += ",non-private";
}
var XULWindow = Services.ww.openWindow(null, 'chrome://browser/content/browser.xul', null, features, sa);
XULWindow.addEventListener('load', function() {
var DOMWindow = XULWindow.QueryInterface(Ci.nsIInterfaceRequestor).getInterface(Ci.nsIDOMWindowInternal || Ci.nsIDOMWindow);
DOMWindow.gBrowser.selectedTab.linkedBrowser.webNavigation.stop(Ci.nsIWebNavigation.STOP_ALL);
DOMWindow.gBrowser.swapBrowsersAndCloseOther(DOMWindow.gBrowser.selectedTab, aTab);
//DOMWindow.gBrowser.selectedTab = newTab;
}, false);
} else if (tDOMWin) {
//existing dom window
var newTab = tDOMWin.gBrowser.addTab('about:blank');
newTab.linkedBrowser.webNavigation.stop(Ci.nsIWebNavigation.STOP_ALL);
tDOMWin.gBrowser.swapBrowsersAndCloseOther(newTab, aTab);
tDOMWin.gBrowser.selectedTab = newTab;
}
}
moveTabToWin(gBrowser.selectedTab, 'tabbed');
I'v got inspired by #Noitidart's answer and came up with my solution.
I'm adding setWindow(window, index) method to Tab's prototype, so that any SDK tab can be moved to another window from anywhere in the addon with a simple call like this:
browserWindows[0].activeTab.setWindow(browserWindows.activeWindow, 0);
This will move active tab of window 0 to the beginning of active window.
And here is the method:
Update:
I've put together a module to do exactly this: jetpack-tab-setwindow
Old solution (breaks in FF43)
var Tab = require("sdk/tabs/tab").Tab;
Tab.prototype.setWindow = function (window, index) {
var tab = this;
var oldWindow = tab.window;
if ( oldWindow !== window ) {
// We have to use lower-level API here
var Ci = require('chrome').Ci;
var viewFor = require("sdk/view/core").viewFor;
var aTab = viewFor(tab);
var aWin = viewFor(window);
var gBrowser = aWin.gBrowser;
// Get tab properties
var isSelected = oldWindow.activeTab == tab;
var isPinned = aTab.pinned;
// Log for debugging:
var tabId = tab.id;
console.log('setWindow', {index, isSelected, isPinned, tab, tabId});
// Create a placeholder-tab on destination windows
var newTab = gBrowser.addTab('about:newtab');
newTab.linkedBrowser.webNavigation.stop(Ci.nsIWebNavigation.STOP_ALL); // we don't need this tab anyways
// If index specified, move placeholder-tab to desired index
if ( index != undefined ) {
var length = gBrowser.tabContainer.childElementCount;
if ( index < 0 ) index = length - index;
if( 0 <= index && index < length ) {
gBrowser.moveTabTo(newTab, index);
}
}
// Copy tab properties to placeholder-tab
if ( isPinned ) {
gBrowser.pinTab(newTab);
}
// For some reason this doesn't seem to work :-(
if ( isSelected ) {
gBrowser.selectedTab = newTab;
}
// Swap tabs and remove placeholder-tab
gBrowser.swapBrowsersAndCloseOther(newTab, aTab);
}
};

Infinite Scrolling with wookmark plugins scrolling

With ref. to above subject, I am using wookmark plugin to scroll our home page data dynamically….I have studied the tutorial provided on wookmark and I m using the exact script provided by wookmark and working fine shorts of not 100% working.
Things it stucks when it reaches at bottom of the window then we slightly press the up arrow key, that loads the products again and this is happens randomly some time it scrolls perfectly and some time it stucks and if presses up arrow key it starts working again.
Kindly help me out where I m going wrong. Kindly provide me the easy working script for the same.
I m using following code :
(function ($) {
$('#main').imagesLoaded(function () {
var handler = null;
// Prepare layout options.
var options = {
itemWidth: 200, // Optional min width of a grid item
autoResize: true, // This will auto-update the layout when the browser window is resized.
container: $('#main'), // Optional, used for some extra CSS styling
offset: 20, // Optional, the distance between grid items
outerOffset: 20, // Optional the distance from grid to parent
flexibleWidth: 300 // Optional, the maximum width of a grid item
};
function applyLayout() {
$('#main').imagesLoaded(function () {
// Destroy the old handler
if (handler.wookmarkInstance) {
handler.wookmarkInstance.clear();
}
// Create a new layout handler.
handler = $('#display li');
handler.wookmark(options);
});
handler.wookmark(options);
}
/**
* When scrolled all the way to the bottom, add more tiles.
*/
function onScroll(event) {
// Check if we're within 100 pixels of the bottom edge of the broser window.
var winHeight = window.innerHeight ? window.innerHeight : $(window).height(); // iphone fix
//var closeToBottom = ($(window).scrollTop() >= $((document)).height() - $((window)).height() - $("#footer").height() - 500); //(($(window).scrollTop() - 100)); //+ "%"
var closeToBottom = ($(window).scrollTop() + winHeight > $(document).height() - 100);
if (closeToBottom) {
// Get the first then items from the grid, clone them, and add them to the bottom of the grid.
var items = $('#display li'),
firstTen = items.slice(0, 10);
//$('#display').append(firstTen.clone());
applyLayout();
}
};
// Capture scroll event.
$(window).bind('scroll', onScroll);
// Call the layout function.
handler = $('#display li');
handler.wookmark(options);
});
$(window).load(function () {
handler.wookmark(options);
});
})(jQuery);
If you commented out
//$('#display').append(firstTen.clone());
then the new items will not be loaded on the end of list. You need to uncomment that line to get new items.
In real life instead of
var items = $('#display li'),
firstTen = items.slice(0, 10);
$('#display').append(firstTen.clone());
you would need a code that will load new items.
Also I think it might make sense to change > to >=
var closeToBottom = ($(window).scrollTop() + winHeight >= $(document).height() - 100);
to load new items if scroll position is more or equal to the height of window - 100, where 100 is just some value - you could try 200 or even more to see if it will work better for you.

Change text in Div using jQuery, MetaData and Map highlights

I'm a newbie to jQuery and I have a map with a highlight plugin, when mouse over an area I want to change the text in a div with an ID and the text I will get it from the area attribute Alt="some text"
Here is the code that used for area loops, I'm pretty sure I can add a small function here but I couldn't figure it out.
//map
clicks$(".tabs area").click(function(){
//areas loop:
$(".tabs area").each(function(){
var d = $(this).data('maphilight') || {};
if(d.alwaysOn == true){
d.alwaysOn = false;
}
});
var data = $(this).data('maphilight') || {};
data.alwaysOn = true;
$(this).data('maphilight', data).trigger('alwaysOn.maphilight');
if ($(this).hasClass("current") == false)
{
var thisTarget = $(this).attr("href");
$(this).parents(".tabs").find('area.current').removeClass('current');
$(this).addClass('current');
$(this).parents(".tabs").nextAll(".tab-content").children(":visible").fadeOut(1, function() {
$(thisTarget).fadeIn("fast");
});
}
return false;
});
Any help or suggestions on how I can get this done would be highly appreciated.
I'm not familiar with the highlights plugin, but I think you just wanna add a mouseover event to each area like so (you would place this before/after your .click declaration):
$(".tabs area").mouseover(function() {
var alt_text = $(this).attr('alt');
$("#YOUR_TEXT_DIV_ID").html(alt_text);
}).mouseout(function() {
//do something on mouseout
});

Adding screenshot functionality to a firefox extension

Is there a cross-platform approach to taking screenshots from a firefox extension?
Ideally I'd like to be able to take a screenshot of a dom element (irrespective of whether it's visible on the page or not), something like:
var screenshot = screenshot(document.getElementById('example');
Any pointers or suggestions would be nice, searching https://developer.mozilla.org/ only yields screenshots they've used in various guides.
After examining the code of several extensions. I took the following approach (to take a snapshot of a particular dom element). This can be used in a Firefox extension to take screenshots of the whole page, to take screenshots of the browser window and to take screenshots of a particular dom element (and all of its child nodes):
Add canvas to xul.
Find dimensions and top-left co-ordinates of element.
Copy portion of window to canvas.
Convert canvas to base64 PNG file.
function getElementScreenshot(elm) {
var x = findPosX(elm);
var y = findPosY(elm);
var width = elm.clientWidth;
var height = elm.clientHeight;
var cnvs = document.getElementById("aCanvas");
cnvs.width = width;
cnvs.height = height;
var ctx = cnvs.getContext("2d");
// To take a snapshot of entire window
// ctx.drawWindow(mainWindow.content, 0, 0, mainWindow.innerWidth, mainWindow.innerHeight, "rgb(255,255,255)");
ctx.drawWindow(mainWindow.content, x, y, width, height, "rgb(255,255,255)");
return(cnvs.toDataURL());
}
To find top left coordinate of an element
function findPosX(obj) {
var curleft = 0;
if (obj.offsetParent) {
while (1) {
curleft += obj.offsetLeft;
if (!obj.offsetParent) {
break;
}
obj = obj.offsetParent;
}
} else if (obj.x) {
curleft += obj.x;
}
return curleft;
}
function findPosY(obj) {
var curtop = 0;
if (obj.offsetParent) {
while (1) {
curtop += obj.offsetTop;
if (!obj.offsetParent) {
break;
}
obj = obj.offsetParent;
}
} else if (obj.y) {
curtop += obj.y;
}
return curtop;
}
To get access to browser.xul from sidebar
var mainWindow = window.QueryInterface(Components.interfaces.nsIInterfaceRequestor)
.getInterface(Components.interfaces.nsIWebNavigation)
.QueryInterface(Components.interfaces.nsIDocShellTreeItem)
.rootTreeItem
.QueryInterface(Components.interfaces.nsIInterfaceRequestor)
.getInterface(Components.interfaces.nsIDOMWindow);
mainWindow.gBrowser.addTab(...);
Download one of the many Firefox screen capture extensions, and look at their code to see how they do it. Eg Screengrab, Fireshot, or Page Saver
I guess it would be something like this:
Copy the DOM element in question to a separate iframe or browser (which is not visible to the user)
Paint the window of that iframe onto an html canvas using drawWindow(). Check out the source of the Tab Preview addon to see how this is done.

Resources