How to get SVG element dimensions in FireFox? - firefox

In most browsers, the following would work.
window.onload = function(){
console.log( document.getElementById('svgElm').getBoundingClientRect().width );
};
Here is a demo. If you try it in Google Chrome, the console will output 200. However, FireFox returns 0.

I've ended up falling back to the parent dimensions if SVG properties cannot be returned. Here is a demo http://jsbin.com/uzoyik/1/edit.
The relavent code is:
svg.clientWidth || svg.parentNode.clientWidth
svg.clientHeight || svg.parentNode.clientHeight

I don't think "width" is a standard cross-browser property of the object returned by the getBoundingClientRect method. I typically do something like:
var box = el.getBoundingClientRect();
var width = box.right-box.left;
var height = box.bottom-box.top;

The solution I found for this was to use .getComputedStyle(). And since svg elements are not supported in old IE8- browsers, .getComputedStyle() is the way to give consistent results.
So I ended up using this function in my library:
var heightComponents = ['height', 'paddingTop', 'paddingBottom', 'borderTopWidth', 'borderBottomWidth'],
widthComponents = ['width', 'paddingLeft', 'paddingRight', 'borderLeftWidth', 'borderRightWidth'];
var svgCalculateSize = function (el) {
var gCS = window.getComputedStyle(el), // using gCS because IE8- has no support for svg anyway
bounds = {
width: 0,
height: 0
};
heightComponents.forEach(function (css) {
bounds.height += parseFloat(gCS[css]);
});
widthComponents.forEach(function (css) {
bounds.width += parseFloat(gCS[css]);
});
return bounds;
};

This Firefox bug was fixed in Firefox 33 which was released on 14 October 2014.
See bug 530985 for details.

Related

Hammer js (v 2.0.4) not working well for an img on Desktop IE 11

I am trying to add swipe and press support to an img using Hammer js version 2.0.4 and I have noticed that it does not work well on Desktop IE11. The gestures are triggered maybe once for every 20 attempts.
Here is a jsfiddle with an example.
http://jsfiddle.net/bhptL6mf/32/
$(function() {
var myImg = document.getElementById("myImg");
var blue = document.getElementById("blue");
var hammerManager = new Hammer.Manager(myImg);
var panRecognizer = new Hammer.Pan({
threshold: 0,
pointers: 0
});
hammerManager.add(panRecognizer);
var swipeRecognizer = new Hammer.Swipe({
threshold: 0,
velocity: 0.01
});
hammerManager.add(swipeRecognizer).recognizeWith(hammerManager.get('pan'));
hammerManager.on('swipe', function(event) {
if (event.type == 'swipe') {
($(blue).text() === "Swiped") ? $(blue).text(" "): $(blue).text("Swiped");
}
});
})
Anyone else seeing this issue and know of a workaround? I am also seeing the same issue when gestures are applied to anchors
Setting img attribute draggable to false will fix this on IE.
Also noticed a similar issue on Desktop Fire Fox and had to set -moz-user-select to none and prevent dragstart event in addition to setting draggable to false to fix it.

Bing Maps API v7 Custom HTML pushpins in Firefox not positioned correctly

I've created an app where I use several custom HTML pushpins. Each one of these pushpins has a click event that will call setView on the map to center the map on the selected pin. This works perfectly in all browsers except for Firefox (testing version 22.0).
In Firefox, after the setView animation completes and the map is centered on the pushpin, the pushpin is then offset horizontally, vertically or both by a certain amount of pixels. The amount seems to correspond with amount of pixels the map has moved. If you then drag the map manually with the mouse, upon releasing the mouse button, the pushpin snaps back to its proper place. I've checked the top and left position values of the MapPushpinBase anchor tag in compared it with other browsers and the values differ.
Unfortunately, I cannot post a live example because the product has not yet been publicly released. But see below for the code I'm using.
this.clickHandlers.push(Microsoft.Maps.Events.addHandler(node, 'click', function (e) {
var element = $(e.target._htmlContent);
self.nodeHitboxHandler(element);
}));
Within the nodeHitboxHandler function, the only piece of Bing Map code is this:
this.map.setView({
center: new Microsoft.Maps.Location(panStart.latitude, panStart.longitude),
zoom: this.zoom,
mapTypeId: Microsoft.Maps.MapTypeId[self.mapTypeId]
});
Thanks in advance for any help.
UPDATE:
In order to make things clearer, I've created a simple example that demonstrates the problem. You can see it here: http://ginof.com/tests/bing/
In Firefox, try clicking on the different pushpins and watch the behaviour of the pushpin you've just clicked on after the map finishes panning to its new location. The map works fine in all browsers except Firefox.
Here's the complete JavaScript code for this example:
$(document).ready(function () {
var map = null,
initialCoordinates = {latitude: 40.71435, longitude: -74.00597},
initialPoint = new Microsoft.Maps.Location(initialCoordinates.latitude, initialCoordinates.longitude),
range = {
top: 3,
right: 5,
bottom: 0.01,
left: 5
},
mapOptions = {
credentials:"BING-MAPS-API-KEY",
disableKeyboardInput: true,
disableZooming: true,
enableClickableLogo: false,
enableSearchLogo: false,
showBreadcrumb: false,
showDashboard: false,
showMapTypeSelector: false,
showScalebar: false,
inertiaIntensity: 0.5,
mapTypeId: Microsoft.Maps.MapTypeId.birdseye,
labelOverlay: Microsoft.Maps.LabelOverlay.hidden,
center: initialPoint,
zoom: 14
};
function GetMap() {
// Initialize the map
map = new Microsoft.Maps.Map(document.getElementById("mapDiv"), mapOptions);
// Create nodes
map.entities.clear();
var pushpinOptions,
pushpin,
nodeCoordinates;
for (var i = 0; i < 5; i++) {
pushpinOptions = {width: null, height: null, htmlContent: '<div id="node' + i + '" class="node">' + i + '. Custom HTML</div>'};
nodeCoordinates = {latitude: initialCoordinates.latitude + i * 0.005, longitude: initialCoordinates.longitude + i * 0.005};
pushpin = new Microsoft.Maps.Pushpin(new Microsoft.Maps.Location(nodeCoordinates.latitude, nodeCoordinates.longitude), pushpinOptions);
pushpinClick = Microsoft.Maps.Events.addHandler(pushpin, 'click',
(function () {
var nodeId = i,
homeCoordinates = nodeCoordinates;
return function () {
console.log("node " + nodeId + " clicked.");
map.setView({center: new Microsoft.Maps.Location(homeCoordinates.latitude, homeCoordinates.longitude)});
}
})()
);
map.entities.push(pushpin);
}
}
GetMap();
});
Thanks again for any help.
This is a known issue which I was able to reproduce an has been escalated to the development team. Note that the Bing Maps forums are the best place to report these types of issues. You can find a similar thread on this topic here: http://social.msdn.microsoft.com/Forums/en-US/f77e6a80-2e0f-44c3-81cc-edb4c2327016/custom-html-pushpins-in-firefox-not-positioned-correctly

Can I set windows sonsole width in Node.js?

Can I Set Windows Console width in Node.js?
process.stdout.columns =300;
process.stdout.rows = 300;
console.log(process.stdout.columns)
console.log(process.stdout.rows)
it doesn't work?
it's not very complicated.
var COORD=
refStruct({
X: ref.types.int16
,Y: ref.types.int16
})
//kernel32
this.kernel32 = new ffi.Library('kernel32', {
'SetConsoleScreenBufferSize': ['bool', ['int32', COORD]]
, 'GetStdHandle': ['int32', ['long']]
});
this.setConsoleBufferSize = function (colume,row) {
var handle = winapi.kernel32.GetStdHandle(-11);
var x = winapi.kernel32.SetConsoleScreenBufferSize(handle, new COORD({
X: colume
, Y: row
}));
};
Based on your comments and the documentation for process.stdout I would say that .columns and .rows are read only.
I've been looking for a while and it does not seem like there is any way to resize the console window from node.

Why can't I programmatically scroll to a given row in a YUI ScrollingDataTable?

It appears the ScrollingDataTable scrollTo method is broken.
As an alternative, I've tried scrollIntoView() and jQuery's scrollTop on the correct dom elements without luck. I've also tried YAHOO.util.Scroll and it doesn't work either.
The datatable is in a div that has a vertical scrollbar.
jQuery version:
var scrollToThisRow = dataTable.getTrEl(recordToScrollTo);
var scrollPos = $(scrollToThisRow).position().top;
$('#tableBodyDiv').scrollTop(scrollPos);
Here's what I tried using YAHOO.util.Scroll:
var scrollToThisRow = dataTable.getTrEl(recordToScrollTo);
var scrollPos = $(scrollToThisRow).position().top;
var attributes = {
scroll: { to: [0, scrollPos] }
};
var anim = new YAHOO.util.Scroll($('#tableBodyDiv'), attributes);
anim.animate();

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