-webkit-transform: rotate - hides elements on top - css

I'm using -webkit-transform: rotate(40 deg) and it seems that the rotated element is hiding parts of elements which are on top ( not children ) of the rotated one.
I created a jsFiddle here with the code, since it will be easier to demonstrate.
Probably this is because the rotated element hides parts of other elements, but I don't want this effect. How can I fix that?
I used z-index but it doesn't help!

You're doing a 3D transform. You have 'rotateY' in the fiddle not 'rotate'.
So you're moving part of the plane in front of the buttons.
Check for yourself by changing code for the second button to
$("div.buttonB").click( function() {
$("div.background").css('-webkit-transform', 'rotateY(-190deg)')
});
​This way after clicking buttonB, buttonB will be clickable but buttonA won't.
Now change -190deg to 190deg and you'll see that it works other way around.
If you want to wrap your head around 3D transformations check out this site.
http://thewebrocks.com/demos/3D-css-tester/
Watch the video and play with the controls. Hope this helps.

Related

Repeat Error on Slick Carousel

I'm trying to use CSS transforms to make the center object in a carousel have more focus/attention. (Carousel is Slick.js)
Everything works great, except when I go from the last item back to the first item, there is a pause and a jump before the change appears.
What is causing this? How do I fix it?
https://jsfiddle.net/6d91cqoq/1/
//pseudo code
EDIT: It also happens going from the first to the last.
EDIT 2:
It's worth noting I took the idea from the Slick.js website: http://kenwheeler.github.io/slick/
On the page with the 'Center Mode' example, it is using transforms to do this exact thing. I cannot for the life of me figure out what is different, other than the target element.
EDIT 3: I did attempt to change my elements to H3 elements, as is in the sample. No change.
The cause for this is that Slick changes the DOM order of the slide elements when switching from "first to last". The transition doesn't kick in when dom elements are removed and added back... You can work around this by playing around with javascript and Slicks beforeChange and afterChange events instead of a pure CSS solution. I have made an example, although the example I made also slightly changes the effect (the center slide won't widen until it is in the center, e.g. afterChange). Maybe with Slicks, next and previous slide parameters you can make it work like your example, didn't have time to investigate it more.
https://jsfiddle.net/6d91cqoq/2/
Changes made to your example:
//Added my own "active" class, so it does not to interfere with slicks active class
.slick-slide.active {
opacity: 1;
transform: scale(1.50);
}
JS
//make current center active after initialization
$('.slick-center').addClass('active');
//before slide change, make all "inactive"
$('.center').on('beforeChange', function(event, slick, index){
$('.slick-slide').removeClass('active');
});
//after change make the center one "active"
$('.center').on('afterChange', function(event, slick, index){
$(slick.$slides[index]).addClass('active');
});

How do I get rid of PNG invisible borders?

I'm new to web programming, recently I've been asked to make some home pages for someone.
Unfortunately I've run into some problem, the homepage will be on a touch screen for touch input, I've got reports like buttons most of the time doesn't work when clicked on, one of my suspects is invisible borders caused by PNGs.
TL;DR - http://puu.sh/6HQez.jpg The corner of the red button is being blocked by the invisible border of the purple button, are there any ways to fix that?
EDIT: No I'm not asking for how to remove the dotted line, I made them visible to show you.
It seems like what you are referring to is not an 'invisible border' but an 'invisible background'.
Your PNG files are rectangular shaped when it comes to event handling, even if some parts are transparent.
If you need to disable some elements from being clicked, you can go about it few ways:
Disable pointer-events with CSS to make sure that a specific
element does not caputre clicks.
#mypurplediv {pointer-events: none;}
Use Z-index to decide the hierarchy of your elements:
#mypurplediv {z-index: 0;}
#myrediv {z-index: 1;}
EDIT:
Per your comments, it seems that you need to retain the abiity to click on ALL elements.
As I mentioned above , your current PNGs are actually rectangles with some parts being transparents.
So you have these options:
1) Use SVG which are vector based shapes (that will by default not have invisible backgrounds). Good tutorial here.
2) Use image mapping and area to create your shapes and give them href. This is a good tutorial about image mapping.
example - <area shape="poly" coords="74,0,113,29,98,72,52,72,38,27" href="index.htm">
3) Use 3rd party javascript/jQuery libraries such as ImageMapster.
Hope this helps!
That dotted border is called focus outline. You can turn it off by applying CSS to the image.
img { outline: none; }

Using CSS3 transition flip effects to show a modal dialog?

I'd like to show a modal dialog using a 3D flip effect, exactly like the "3D flip (horizontal)" example in the Effeckt.css library.
However I really don't need the whole Effeckt library, since I just want this one effect. So I've tried to strip out the relevant bits of the library into free-standing CSS and JavaScript.
This is my attempt, but it's not working: http://jsfiddle.net/eJsZx/
As the JSFiddle demonstrates, it's only showing the overlap - not the modal itself. This is odd, because the element inspector suggests that the modal should be visible - it has display: block, visibility: visible and zindex: 2000 (higher than the overlay element).
This is the JavaScript:
$('button').on('click', function() {
$("#effeckt-modal-wrap").show();
$("#effeckt-modal-wrap").addClass('md-effect-8');
$("#effeckt-modal-wrap").addClass("effeckt-show");
$('#effeckt-overlay').addClass("effeckt-show");
$(".effeckt-modal-close, .effeckt-overlay").on("click", function() {
$("#effeckt-modal-wrap").fadeOut();
$('#effeckt-modal-wrap').removeClass("effeckt-show");
$("#effeckt-modal-wrap").removeClass('md-effect-8');
$('#effeckt-overlay').removeClass("effeckt-show");
});
});
What am I doing wrong?
There were a couple of issues in the code.
First, your styles were missing the following:
.effeckt-show .effeckt-modal {
visibility: visible;
}
This was causing the modal to remain invisible.
Once the dialog was visible, the dialog would rotate in just fine, however when being dismissed it would not rotate out. This was due to the following line:
$("#effeckt-modal-wrap").removeClass('md-effect-8');
If you want to remove this class, it would need to be done after the animation is complete otherwise the 3d effect is lost. It doesn't necessarily need to be removed, but that depends on what the rest of your content needs.
The final issue was that the wrapper, on completion of the fadeout, was getting its local style set to display: none. Because of this, the second time showing the dialog would cause it to simply appear because it was moving from display: none to display: block. There are a couple of options here.
Use CSS to animate the fade in/out.
Use window.setTimeout after calling $.show on the element to give the dom a chance to update.
The final result: Working Fiddle

why is google's infoWindow CSS not exposed? customization is too hard

This really bugs me - a lot.
After wading through google maps v3 generated client side code in firebug, I'm about ready to drive down the street and give some of these engineers a piece of my mind... arrrgh :P
The infowWindow class produces HTML that personally I would think is simply nuts. maybe someone can help me make sense of it.
The infowWindow HTML structure is like this:
#map_canvas > div > div > div > div > div // 5 levels of elements,
no big deal here, ok...
> div // top left corner
div // top right corner
div // bottom left corner
div // bottom right corner
// now comes fun stuff for the speech bubble arrow:
div
div
div
div
div
div
div
div
div
div
// the 10 divs above are stacked diagonally with odd sizes to make this arrow.
i'm sorry but WHY?!? is it done like that? I suppose they wanted the user to be
able to grab the map even right next to the arrow. Think about this: do users
really need to be able to not grab the arrow? if grabbing the arrow causes map pan,
as is the case for the shadow images, would that really be a problem?
div // bottom middle for image background border or something
div // top middle
div // middle
div // bottom middle, again
div // entire block of the infoWindow, probably the container
> img // close box
div // center block with the contents of the infoWindow
div // text content container
WOW - thats nuts!
notice there is no real semantic structure, and - gosh, dare I have such an
assumption - no class names anywhere, nothing. I figured maybe they have some
kind of 9-slice box going on and then produce the arrow separately; I mean,
the image sprite in iw3.png sure isn't going to be the problem here.
I dearly hope someone who has an effect on this api comes across this and
hopefully google will eventually find a way to solve this such that custom
infoWindow visuals are as straightforward as markers.
Thanks for tuning in! happy commenting.
meanwhile I shall use a hack to get to these crazy divs and make them do my bidding.
earlier I commented on some other post and I think it shouldn't be too much to ask for a method in the API that lets you use custom UI without resorting to a near-duplication of the whole window object as is currently necessary (see google extension classes v3).
google.maps.infoWindow.setStyle({
'topleft' : {
'background' : 'url(images/windowsprite.png) 0 0 no-repeat',
'width' : '10px',
'height' : '10px'
},
'topRight' : {
...etc...
}
...etc...
})
Have you tried InfoBox?
http://googlegeodevelopers.blogspot.com/2010/04/infobox-10-highly-customizable.html
or InfoBubble?
http://google-maps-utility-library-v3.googlecode.com/svn/trunk/infobubble/examples/example.html/
They both give you a bit more control over the appearance of infowindows, while still abstracting some of the complicated parts.
The lack of classes on elements is a (good) design decision for an API. It eliminates the potential for clashes with user defined classes.
After much trial and eror I decided the best way to resolve this is to use OverlayView class and simply custom build a container. Well, "simply" is an understatement, but it works. And now I have full control over layout and functionality.
You try styling with CSS? The below example shows this. This is the most straight forward way to change the UI.
http://code.google.com/apis/maps/documentation/javascript/overlays.html#InfoWindows

Click through div to underlying elements

I have a div that has background:transparent, along with border. Underneath this div, I have more elements.
Currently, I'm able to click the underlying elements when I click outside of the overlay div. However, I'm unable to click the underlying elements when clicking directly on the overlay div.
I want to be able to click through this div so that I can click on the underlying elements.
Yes, you CAN do this.
Using pointer-events: none along with CSS conditional statements for IE11 (does not work in IE10 or below), you can get a cross browser compatible solution for this problem.
Using AlphaImageLoader, you can even put transparent .PNG/.GIFs in the overlay div and have clicks flow through to elements underneath.
CSS:
pointer-events: none;
background: url('your_transparent.png');
IE11 conditional:
filter:progid:DXImageTransform.Microsoft.AlphaImageLoader(src='your_transparent.png', sizingMethod='scale');
background: none !important;
Here is a basic example page with all the code.
Yes, you CAN force overlapping layers to pass through (ignore) click events.
PLUS you CAN have specific children excluded from this behavior...
You can do this, using pointer-events
pointer-events influences the reaction to click-, tap-, scroll- und hover events.
In a layer that should ignore / pass-through mentioned events you set
pointer-events: none;
Children of that unresponsive layer that need to react mouse / tap events again need:
pointer-events: auto;
That second part is very helpful if you work with multiple overlapping div layers (probably some parents being transparent), where you need to be able to click on child elements and only that child elements.
Example usage:
.parent {
pointer-events:none;
}
.child {
pointer-events:auto;
}
<div class="parent">
I'm unresponsive
I'm clickable again, wohoo !
</div>
Allowing the user to click through a div to the underlying element depends on the browser. All modern browsers, including Firefox, Chrome, Safari, and Opera, understand pointer-events:none.
For IE, it depends on the background. If the background is transparent, clickthrough works without you needing to do anything. On the other hand, for something like background:white; opacity:0; filter:Alpha(opacity=0);, IE needs manual event forwarding.
See a JSFiddle test and CanIUse pointer events.
I'm adding this answer because I didn’t see it here in full. I was able to do this using elementFromPoint. So basically:
attach a click to the div you want to be clicked through
hide it
determine what element the pointer is on
fire the click on the element there.
var range-selector= $("")
.css("position", "absolute").addClass("range-selector")
.appendTo("")
.click(function(e) {
_range-selector.hide();
$(document.elementFromPoint(e.clientX,e.clientY)).trigger("click");
});
In my case the overlaying div is absolutely positioned—I am not sure if this makes a difference. This works on IE8/9, Safari Chrome and Firefox at least.
Hide overlaying the element
Determine cursor coordinates
Get element on those coordinates
Trigger click on element
Show overlaying element again
$('#elementontop').click(e => {
$('#elementontop').hide();
$(document.elementFromPoint(e.clientX, e.clientY)).trigger("click");
$('#elementontop').show();
});
I needed to do this and decided to take this route:
$('.overlay').click(function(e){
var left = $(window).scrollLeft();
var top = $(window).scrollTop();
//hide the overlay for now so the document can find the underlying elements
$(this).css('display','none');
//use the current scroll position to deduct from the click position
$(document.elementFromPoint(e.pageX-left, e.pageY-top)).click();
//show the overlay again
$(this).css('display','block');
});
I currently work with canvas speech balloons. But because the balloon with the pointer is wrapped in a div, some links under it aren't click able anymore. I cant use extjs in this case.
See basic example for my speech balloon tutorial requires HTML5
So I decided to collect all link coordinates from inside the balloons in an array.
var clickarray=[];
function getcoo(thatdiv){
thatdiv.find(".link").each(function(){
var offset=$(this).offset();
clickarray.unshift([(offset.left),
(offset.top),
(offset.left+$(this).width()),
(offset.top+$(this).height()),
($(this).attr('name')),
1]);
});
}
I call this function on each (new) balloon. It grabs the coordinates of the left/top and right/down corners of a link.class - additionally the name attribute for what to do if someone clicks in that coordinates and I loved to set a 1 which means that it wasn't clicked jet. And unshift this array to the clickarray. You could use push too.
To work with that array:
$("body").click(function(event){
event.preventDefault();//if it is a a-tag
var x=event.pageX;
var y=event.pageY;
var job="";
for(var i in clickarray){
if(x>=clickarray[i][0] && x<=clickarray[i][2] && y>=clickarray[i][1] && y<=clickarray[i][3] && clickarray[i][5]==1){
job=clickarray[i][4];
clickarray[i][5]=0;//set to allready clicked
break;
}
}
if(job.length>0){
// --do some thing with the job --
}
});
This function proofs the coordinates of a body click event or whether it was already clicked and returns the name attribute. I think it is not necessary to go deeper, but you see it is not that complicate.
Hope in was enlish...
Another idea to try (situationally) would be to:
Put the content you want in a div;
Put the non-clicking overlay over the entire page with a z-index higher,
make another cropped copy of the original div
overlay and abs position the copy div in the same place as the original content you want to be clickable with an even higher z-index?
Any thoughts?
I think the event.stopPropagation(); should be mentioned here as well. Add this to the Click function of your button.
Prevents the event from bubbling up the DOM tree, preventing any parent handlers from being notified of the event.
Just wrap a tag around all the HTML extract, for example
<a href="/categories/1">
<img alt="test1" class="img-responsive" src="/assets/photo.jpg" />
<div class="caption bg-orange">
<h2>
test1
</h2>
</div>
</a>
in my example my caption class has hover effects, that with pointer-events:none; you just will lose
wrapping the content will keep your hover effects and you can click in all the picture, div included, regards!
An easier way would be to inline the transparent background image using Data URIs as follows:
.click-through {
pointer-events: none;
background: url(data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7);
}
I think that you can consider changing your markup. If I am not wrong, you'd like to put an invisible layer above the document and your invisible markup may be preceding your document image (is this correct?).
Instead, I propose that you put the invisible right after the document image but changing the position to absolute.
Notice that you need a parent element to have position: relative and then you will be able to use this idea. Otherwise your absolute layer will be placed just in the top left corner.
An absolute position element is positioned relative to the first parent
element that has a position other than static.
If no such element is found, the containing block is html
Hope this helps. See here for more information about CSS positioning.
You can place an AP overlay like...
#overlay {
position: absolute;
top: -79px;
left: -60px;
height: 80px;
width: 380px;
z-index: 2;
background: url(fake.gif);
}
<div id="overlay"></div>
just put it over where you dont want ie cliked. Works in all.
This is not a precise answer for the question but may help in finding a workaround for it.
I had an image I was hiding on page load and displaying when waiting on an AJAX call then hiding again however...
I found the only way to display my image when loading the page then make it disappear and be able to click things where the image was located before hiding it was to put the image into a DIV, make the size of the DIV 10x10 pixels or small enough to prevent it causing an issue then hiding the containing div. This allowed the image to overflow the div while visible and when the div was hidden, only the divs area was affected by inability to click objects beneath and not the whole size of the image the DIV contained and was displaying.
I tried all the methods to hide the image including CSS display=none/block, opacity=0, hiding the image with hidden=true. All of them resulted in my image being hidden but the area where it was displayed to act like there was a cover over the stuff underneath so clicks and so on wouldn't act on the underlying objects. Once the image was inside a tiny DIV and I hid the tiny DIV, the entire area occupied by the image was clear and only the tiny area under the DIV I hid was affected but as I made it small enough (10x10 pixels), the issue was fixed (sort of).
I found this to be a dirty workaround for what should be a simple issue but I was not able to find any way to hide the object in its native format without a container. My object was in the form of etc. If anyone has a better way, please let me know.
I couldn't always use pointer-events: none in my scenario, because I wanted both the overlay and the underlying element(s) to be clickable / selectable.
The DOM structure looked like this:
<div id="outerElement">
<div id="canvas-wrapper">
<canvas id="overlay"></canvas>
</div>
<!-- Omitted: element(s) behind canvas that should still be selectable -->
</div>
(The outerElement, canvas-wrapper and canvas elements have the same size.)
To make the elements behind the canvas act normally (e.g. selectable, editable), I used the following code:
canvasWrapper.style.pointerEvents = 'none';
outerElement.addEventListener('mousedown', event => {
const clickedOnElementInCanvas = yourCheck // TODO: check if the event *would* click a canvas element.
if (!clickedOnElementInCanvas) {
// if necessary, add logic to deselect your canvas elements ...
wrapper.style.pointerEvents = 'none';
return true;
}
// Check if we emitted the event ourselves (avoid endless loop)
if (event.isTrusted) {
// Manually forward element to the canvas
const mouseEvent = new MouseEvent(event.type, event);
canvas.dispatchEvent(mouseEvent);
mouseEvent.stopPropagation();
}
return true;
});
Some canvas objects also came with input fields, so I had to allow keyboard events, too.
To do this, I had to update the pointerEvents property based on whether a canvas input field was currently focused or not:
onCanvasModified(canvas, () => {
const inputFieldInCanvasActive = // TODO: Check if an input field of the canvas is active.
wrapper.style.pointerEvents = inputFieldInCanvasActive ? 'auto' : 'none';
});
it doesn't work that way. the work around is to manually check the coordinates of the mouse click against the area occupied by each element.
area occupied by an element can found found by 1. getting the location of the element with respect to the top left of the page, and 2. the width and the height. a library like jQuery makes this pretty simple, although it can be done in plain js. adding an event handler for mousemove on the document object will provide continuous updates of the mouse position from the top and left of the page. deciding if the mouse is over any given object consists of checking if the mouse position is between the left, right, top and bottom edges of an element.
Nope, you can't click ‘through’ an element. You can get the co-ordinates of the click and try to work out what element was underneath the clicked element, but this is really tedious for browsers that don't have document.elementFromPoint. Then you still have to emulate the default action of clicking, which isn't necessarily trivial depending on what elements you have under there.
Since you've got a fully-transparent window area, you'll probably be better off implementing it as separate border elements around the outside, leaving the centre area free of obstruction so you can really just click straight through.

Resources