Scaled Transparent PNGs lose anti-aliasing after jQuery animation in Webkit browsers - javascript

I have a script that lays out these circular icons on the map, you hover over them, they spring up, text appears, etc. The icons are scaled relative to their position on the map, ie, the distance from 0 on the y-axis. I've tried to set the scale through CSS's width and height attributes and through the html width & heights on the img tag and still have the same problem:
Basically, in their dormant state, such as when the page is first loaded, or the user flicks between tabs, the images (trans' PNGs) are anti-aliased. However, when the hover() function, and thus the animate() function, is invoked, the images suddenly become jagged and horrid. I've noticed that this behaviour doesn't exist in firefox but does in safari and chrome. I don't know whether this is to do with Webkit, jQuery or just javascript itself but maybe someone could shine some light as google resulted in nothing. Any thoughts? :)
Please also note that the bottom left and bottom right icons look fine in both attached screenshots- they're unscaled ones!
Thanks a lot :)
Matt

i can only guess on this, but my assumption is that gecko and webkit use different scaling algorithms for images. thus it has nothing to do with javascript, jquery or png at all.
in fact, the image still has antialiased edges even in the webkit screenshot. (you see that when you zoom in)
the border is just messed up which is usually the result of a bad scaling algorithm.
try the following to confirm this assumption:
<img src="youricon.png" width="90%" height="90%">
and compare the result in the two browsers. you should see the same problem.
possible solutions:
make a smaller version of the image and replace image with the smaller one on hover instead of scaling it.
use a scalable vector graphics format like SVG for your icons.

Related

Calculation in JavaScript that uses CSS pixels is incorrect for zoomed-out views (zoom levels below 100%)

For my page, I run a calculation in JS that uses values that are measured in CSS pixels. This calculation happens every time the viewer zooms the page. If you'd like to know what the calculation is for, it's used for scaling a div to a desired size depending on the zoom.
This is working perfectly in Firefox across all zoom levels, but I get a certain problem when I test it in Chrome and other browsers. It works fine until you try testing zoom levels below 100% (zoomed-out views). When you're in a zoomed-out view the calculation becomes incorrect (it's bigger than it should be). I think it might be because CSS pixels become smaller than device pixels when you reach zoomed-out views (right?), and because my calculation is in CSS pixel units it no longer is accurate. But if that's the case, then why are my zoomed-out views in Firefox working? In an effort to try to fix the problem on non-Firefox browsers, I converted the calculation to operate in device pixels when in zoomed-out views and that fixed the problem (in Chrome and other browsers), but then when I went back to Firefox to make sure its zoomed-out views still worked, the calculation was no longer correct (it was smaller than it should be).
From my findings, it seems that...
Firefox expects you to only use CSS pixels (even in zoomed-out views)
Chrome and other browsers expect you to convert between CSS and device pixels depending on the zoom (CSS pixels when zoomed in, device pixels when zoomed out)
So what's the deal here? How does one create a solution that works for both without browser sniffing?
Also, is it normal to convert between CSS and device pixels depending on the zoom? Or should I just be doing it the Firefox way and only deal with CSS pixels? I don't know which way is considered the normal way, but it seems that most browsers make you convert.

How to scale an iFrame inside of iOS UIWebView

The Problem:
I've been seeing problems with the native iOS UIWebView with regard to CSS3 transform:scale3D(scalar, scalar, 1)
We have an <iframe> which contains pixel-perfect art, consisting of many elements (text, rectangles, videos, etc), and my task is to scale the <iframe> where it fits fullscreen, not just the designed 320x480 or whatever
First of all, touch events aren't propagating through at all. Secondly, when the user holds down on the <iframe>, they can see DOM outlines for the elements at the prior, incorrect locations, at incorrect sizes (before the <iframe> was scaled to fit the screen)
The blue area should be the entire screen, not the original location
To top it all off, sometimes the scaling introduces random horizontal / vertical lines where the UIWebView decided not to repaint
My Attempts:
I tried using css zoom: which I understand is somewhat of a replacement for the <meta> tag viewport zooming, but I was still seeing random unpainted lines. I'm not exactly sure if I tried using hardware acceleration (transform in z / 3d space) but I'm pretty sure I did, the same as with the regular transform:scale3d approach
I also tried to crawl the configuration object, which has properties like x, y, width, height, but it seems like some properties need to be rounded where others do not (text font size and letter spacing for example, border widths etc). Rasterizing is causing a headache and I can't seem to get a pixel-perfect, scaled <iframe> I'm not sure which elements support decimal px CSS, so I'm considering converting everything to em
I haven't yet used an actual <meta> tag because it can't be dynamically appended.. needs to be on the HTML before the DOM is rendered. Another reason I didn't use the <meta> is because I need to know the viewport size prior to writing the <meta> properties (I can possibly query from out native counterpart if someone confirms this solution works)
The Question:
Has anyone encountered this problem before? Is it possible to get a pixel-perfect, scaled representation, given that the scalar may be 1.333333? I know that Apple is replacing the UIWebView with an embeddable Safari implementation (mobile web works fine for my usecase, just not native iOS), but in the meantime, is there any hope for iOS? Links highly appreciated! Thanks in advance..
My coworker found the answer!
Answer:
You can't scale an <iframe> from the outside DOM, you have to postMessage() into the <iframe> and use document.body.style.webkitTransform = "scale(1337)"
Hope this helps somebody else in need!
Credit ultimately goes to http://adexcite.com/iframe_scaling_test.html

Layering issue with Adobe Edge on iPad only

I have a fairly simple button symbol that I'm adding dynamically to the stage. The button has a background layer and a text layer. Everything works fine in the standard browsers but on iPad the background layer unexpectedly covers the text (as if on a higher z-index though no value shows in the DOM and attempts to override the z-index via css do nothing). Further more this issue only seems to trigger when I go to a label in the button such as;
button.stop("Idle");
Has anyone else had random layering issue on iPad that may relate to this?
For anyone who may be searching; Apparently vector shapes do not appear smoothly and consistently in all webkit browsers (the primary culprit mentioned was Android native browser). As an artificial optimization you can apply a 3D transform (but without actually scaling or rotating) in order to improve the vector rendering. In Adobe Edge this is done by applying a 'translateZ" transform to all of the elements on the stage. However this also causes random issues with any item I'm trying to layer with "z-index".
The solution is to clear out this transform on the problematic elements (or edit the edge classes to removed them globally) like so;
buttonFrameSym.$("select_arrow").css("-webkit-transform", "none");

image resize gives slight, brief, pixelation in WebKit browsers

jsfiddle: http://jsfiddle.net/UenFN/. Notice the slight, brief pixelation after the animation. This error only happens in WebKit browsers.
Using jQuery, I have an image resize into a smaller one. The new dimensions are precisely half of the old ones. Right after resizing, however, the image appears slightly pixelated, then about 2 seconds later it looks better.
How can I fix this problem?
EDIT: Still no progress. Any idea is appreciated.
The solution is to enable the Hardware Acceleration in Webkit.
img {
-webkit-transform: translate3d(0, 0, 0);
}
I have a small library which resize image and HTML to always fit the parent div. Safari bugged me with its own unique way to do a quick and dirty pass before doing the bicubic one. Forcing the hardware acceleration solved the issue, In my case as I do a lot of resizing I do notice some performance degradation yet in the end the overhaul result is more appealing.
You can test this fix here: http://www.visualfox.me/app/nanjing-2014
Under Safari the image used as a mask is never pixelated, regardless of the resizing, upscale or downscale (just resize the browser to test it). You can compare that with this other demo which doesn't use the fix: http://www.visualfox.me/app/bold
Notice how the logo is temporally pixelated when you resize the browser.
my! enjoy!
I discovered that the only time it does not do it is when the size upon completion is the native image size.
from 150 to 300 pixels, no pixelation...
http://jsfiddle.net/UenFN/1/
and from 450 to 300 pixels, still no pixelation...
http://jsfiddle.net/UenFN/2/
So the fix, or workaround, would be to make sure your final size is the native image size wherever possible.
You could use an image appropriate to the dimensions you are going for.
If you can't do that then you could use a callback method to replace the resized image with an image that is the size of the new dimensions. What you are doing is no different than stretching an image (in fact thats exactly what you're doing) so there is going to be pixelation.
In order to fix this, I inserted the same image a second time, but with the dimensions I want to use. At the millisecond after the animation, I replace the main image with the previously hidden image.
jsfiddle: http://jsfiddle.net/wLwrc/1/
Solved in 2013. https://bugs.webkit.org/show_bug.cgi?id=74600
image-rendering: optimizeQuality;
I had the exact same problem. I changed the *.jpg that I was animating the size of, to a *.svg and the pixelation went away.

IE GIF/PNG Transparency issue with jQuery

Ok, this is pretty weird...
Here's the page in question: http://s289116086.onlinehome.us/lawjournaltv/index.php
The main blue callout background was originally a PNG, but when I applied some jQuery trickery to it (click the numbers in the top right to see what I mean), an ugly white border appeared where the transparency should be. See this screenshot from IE8: http://skitch.com/darkdriving/n62bu/windows-xp-professional
I figured I could sacrifice the quality/flexibility of a PNG and just resaved each of the backgrounds as GIFs and set the matte color to white (for now). Well, I was proven wrong because IE is treating the GIF transparency the same as the original PNGs.
I've read here that the issue with PNGs, Javascript, and IE has something to do with multiple filters can't be applied to one image, but shouldn't GIFs be exempt from this because they lack the Alpha Channel? Is there any way to make this page look similar in IE to Firefox or Webkit browsers?
Thanks in advance!
This is a bug in IE.
No current version of IE supports the opacity CSS proeprty, so jQuery uses the Alpha filter instead. However, filters force the element to be fully opaque, so they don't work orrectly with transparent PNGs.
To use transparent PNGs in semi-transparent elements, the PNGs need to be applied using the AlphaImageLoader filter (even in IE8). For example:
if ($.browser.msie)
$(something).css({
background: 'none',
filter: 'progid:DXImageTransform.Microsoft.AlphaImageLoader(src="/Folder/Image.png", sizingMethod="scale"),alpha(opacity=100)'
});
(This code works; I'm using it right now)
I basically solved this by loading a different set of images (using PHP) on each page refresh. It's not as dynamic, but my attempts at using the ugly, proprietary CSS filters or other javascript-based plugins were all fruitless. In my eyes, this is clearly one of the biggest bugs I've come across in my time spent hacking away at IE. In fact, I'm suprised it took this long for me to encounter it.
Word to the wise in this case: try to back transparent imagery on a solid color or suffer the consequences in IE.

Categories