Reading this question you're probably thinking 'not again' and want to mark it as duplicate. But after I've tried about every fix I could find up here and in other parts of the internet I couldn't think of another way to get a solution than asking here.
The problem is: I have a container, which should be completely clickable. The problem in this particular website is, that we can not control what elements will be inside of the container. Since there could be block-elements inside, we can't use an <a> tag instead of <div> as the container. We also want to the site to work in a no-js environment, so an onclick on the container is a no-go unfortunately.
That's why we choose an absolutely positioned <a> which will be an overlay for the entire container. This works well in every browser, except for IE.
In IE all content of the container is painted above the <a>, thus making it a non-clickable area. This isn't really much of a problem with the example here: just a small piece of text. But in other container we have images, tables etc. which completely fill the size of the container.
Even if I'd change the z-index of the <p> to 0 and the z-index of the <a> to 1, the paragraph is still on top of the link. How is this possible? I've read all about stacking contexts and levels, and I still can't find a single thing wrong in my code.
Note: there's a display: hidden; <span> in the <a>, but that's for internal use and I don't think it will affect this issue.
Note: the div.content__container has a parent from which it can get the 100% dimensions.
HTML:
<div class="content__container">
<p class="__align-to-bottom __right" >text <span class="__icon">f</span></p>
<span>text</span>
</div>
CSS:
.content__container {
position: relative;
overflow: hidden;
width: 100%;
height: 100%;
}
.content__container > *{
position: relative;
}
.__align-to-bottom {
position: absolute !important;
bottom: 0;
left: 0;
}
.__align-to-bottom.__right {
left: auto;
right: 0;
}
a.__link {
position: absolute !important;
display: block;
width: 100%;
height: 100%;
left: 0;
top: 0;
}
a.__link span{
display: none;
}
As said this works fine in every browser out there except for IE. I'm currently testing in 9 & 10 and I'm guessing IE<9 isn't going to be a walk in park either.
EDIT
As suggested I've created a fiddle. In this fiddle I've already implemented some remarks. Such as the display: block; line for a.__link and removing the content__container > *{} from my css. I've added some JS to clarify which element is being clicked on. In IE it's still not working: the onclick event from the paragraph is being triggered.
I came across an issue like this once where I had a blank link positioned absolutely over the top of some content I wanted to be clickable - I tried everything to get it to work and finally found a really dirty hack:
Make a transparent gif or png (has to be at least 50x50) and then use it as the background of the anchor. It should then be clickable, if it is the highest z-index
I take it your link is a block element and actually covers the 100% height and width too
Since there could be block-elements inside, we can't use an <a> tag instead of <div> as the container.
Why not? Are block-level elements allowed inside inline-level elements in HTML5?
ps. Your fiddle code works in IE8.
Related
Problem
I'm trying to stretch a ::before element from the very left hand side of the page to the right hand side, even though the element it's attached to is centred and somewhat down the page (and thus does not know what the window size is etc).
Here's a working example of what I want:
http://codepen.io/robcampo/pen/dilCe
Problem with this is that I'm using static values to define the width and left position:
left: -9000px;
width: 99999px;
which isn't ideal. I understand this could be solved if I moved the element to another location on the page, but I need it next to the element it's attached to.
Question
Is there a clean way to make the ::before content span the entire page width without using static values?
Note
There is content above and below this element and it is far down the DOM tree away from the body
I could solve using JS but I want a pure CSS solution
If you remove position: relative from the parent element, you can easily do this.
You can center .title like this instead:
.title {
margin: 0 auto;
}
Then you can adjust the ::before like this:
.title::before {
position: absolute;
left: 0;
width: 100%;
}
Bringing it all together: http://codepen.io/anon/pen/xLKGc
PS: Note that IE8 and before don't support the double-colon (CSS3) notation, so if you need to support IE8, make sure to use a single colon (CSS 2.1), which is supported by other browsers as well, and will probably be for a while.
I'm certainly no CSS guru, but I am working on a problem where I'd like to make copying of images just slightly more burdensome for users. Sure, they can still easily be retrieved, but this makes it so you can't just drag/drop them on your desktop. Basically, I had a bunch of markup like this:
<img width="400" src="my image.png" class="foo" alt="foo">
Instead, I decided to put this into a background image and change the element to a div:
<div width="400" class="foo">
The problem I have is that the images have a fixed width, but a variable height. This worked excellent when I was using an img tag. It doesn't have the same behavior when I use a div tag. Instead, the CSS is requiring me to force a height property to display anything at all:
This doesn't work
.foo {
display: block;
margin: 0;
padding: 0;
width: 400px;
background-image: url(myimage.png);
/* height: 200px; */
}
This sorta does:
.foo {
display: block;
margin: 0;
padding: 0;
width: 400px;
background-image: url(myimage.png);
height: 200px;
}
The problem is the height for the images are all variable as I mentioned before. So it tiles over and over if I hard code a size. The container can be a placeholder for well over 5,000 images, so setting it by hand won't do it. If I can get this div to behave exactly like the img tag did, the problem is solved.
If you are just trying to prevent people from clicking and drag/dropping, I would say put each img into it's own div with position: relative. Add another div inside that relative div that has the following style:
div.img_box {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: none;
z-index: 9999; /* or anything higher than your img's z-index */
}
That will cover up the image with a transparent div.
That way the image (which is part of your content) is still syntactically correct in the html.
Everybody is of course correct in saying that they have already downloaded the images to their computers just by visiting the site.
If you're trying to prevent users from reusing your content easily, some good methods are to:
1. Use images with lower resolution to limit reuse potential
2. Watermark your images
3. A combination of both, in an image sprite.
Hacking at it will just be ugly, ineffective, and difficult to maintain.
You are just setting the background of the div, you aren't adding an image to the div. The div can be resized to whatever it won't resize to what it's background image is. Just use the tag.
The only thing you could do with CSS is add a height which would work for all images. So if you're images range from 200-250px in height, set the div to 250px. Otherwise, you'll need javascript or server-side scripting to determine the height of the image and set the the CSS.
I created a fiddle that exemplifies the problem:
http://jsfiddle.net/vZtBb/
This is working exactly as I want it, but the problem is that in IE7 the absolutely positioned span (hover-tooltip-container) starts at the top of the line instead of at the bottom like it does in the other browsers. If you add a border to hover-tooltip-container, you can see this.
This is a problem because I want the tooltip to go up, but the anchor to still be exposed. You should be able to mouse over the tooltip as well, but the gap in IE7 makes this impossible.
If there is any way to get the hover-tooltip-container span to start in the same place on the line in IE7, IE8, and FFX, that would be perfect.
Javascript is not a solution.
The most simple thing you could do with the code you already have, is add a star hack to adjust the bottom rule within .hover-tooltip, for IE7.
.hover-tooltip {
display: block;
padding: 15px;
position: absolute;
margin: 0 auto;
bottom: 1em;
*bottom: 0;
width: 100%;
border: 2px outset #c0c0c0;
background-color: #f0f0f0;
text-align: center;
}
However, the double, nested absolute positions of .hover-tooltip-container and .hover-tooltip seem unnecessary.
I did something quite different (also renamed your classes, to much of a hassle to play with those looooooooooong name).
http://jsfiddle.net/vZtBb/16/
I removed the nested absolute positionning : They are the one causing the issue, since element in absolute position are taken out of context. So, 2 solo, nested absolute positionned element means that one element is in nothing (glitchy and really not wanted).
Instead of that, I placed your tooltip box in absolute, but made it start higher than the anchor by use of a negative position (top:-70px). It's sketchy a bit, but you should get my point.
Trying putting this after the .hover-tooltip div:
<div class="clear fix"></div>
and this css:
.clearfix:after {content: ".";display: block;clear: both;visibility: hidden;line-height: 0;height: 0;}
.clearfix {display: inline-block; }
html[xmlns] .clearfix {display: block; }* html .clearfix {height: 1%; }
I was able to solve the problem by having the "container" element float left and have relative position. This achieves the appearance of breaking out of containers but still provides a reference for the tooltip to go up from.
I have an absolute positioned popup (hover over "ice white" image to see popup) which has css left:50%. Now this should appear in the middle of page but doesn't. Any suggestions please? Thanks in advance.
You're also supposed to add margin-left with the negative of a half of visible width of the element. So, for example:
width: 400px;
padding: 10px;
border-width: 2px;
/* -(400 + 10 + 2)/2 = -206 */
margin-left: -206px;
left: 50%;
Note that margin: auto suggested by others won't work because you've positioned the element absolutely.
position: absolute;
left: 50%;
transform: translate(-50%,0)
Lol, no. The left side of the image appears at 50% of the page width. Hence; left: 50%.
In order to center your image, set margin: auto instead.
Your code is working correctly. The popup is being positioned with left of 50% ... of the TD tag it's nested inside.
Try either taking the popup out of the table, or setting it to 50% of the document width instead. (Your javascript is minified and unreadable to me, or I'd help further.)
u can try to change CSS Style like this
#displayDiv {
background-color: white;
font-weight: bold;
height: 460px;
left: 50%;
margin: auto auto auto -475px;/* change done here */
overflow: hidden;
position: absolute;
text-align: center;
top: 80px;
width: 950px;
z-index: 1;
}
Looks to me like there's a containing element somewhere in between the "Ice White" image and the body (specifically, Firebug reveals that it's the <a class="popup1" ... >) that is relatively positioned, so your 50% is relative to that rather than the whole page.
I know this seems a bit counterintuitive: Why should it be relative to a parent element if the poput uses absolute positioning? It's basically because relative positioning is relative to where the element is in the normal flow of the document, whereas absolute positioning yanks the element out of that flow. See sections 9.4.3 and 9.6 of the W3C's explanation of the visual formatting model for more info.
Check out a tutorial or two if this is giving you trouble. I like Learn CSS Positioning in Ten Steps and css-tricks.com's "Absolute Positioning Inside Relative Positioning" (to which I'd provide a link if not for the spam filter; first-time answerer here ;) ).
As for what to do about it, you might be able to move the popups out of the relatively positioned parent, as mblaze75 suggests, but it looks (and I'm guessing here) like that <a> is what's triggering your JavaScript event, so you probably can't do that. Instead, I'd try removing the relative positioning and using margins instead.
Also, bear in mind what Greg Agnew said: Even with that problem solved, you're still centering the left edge rather than the center of your popup. I think duri's answer will take care of that.
I use this html code
<div class="titleIn">
<h2>link2</h2>
</div>
and for some reason the link2 is not clickable (no hand cursor)
The CSS is:
.titleIn {
direction: rtl;
margin-bottom: 10px;
margin-right: 0;
margin-top: -10px;
position: relative;
text-align: right;
z-index: -1;
}
Any idea?
I can't say I know why, but I know what's causing it: Your z-index: -1. If you remove that, the problem goes away (at least, it does for me on Chrome, Firefox, and Opera; not on IE6 or IE7, though). Here's a live copy of your example, and an updated copy with z-index: 0 instead.
By giving it a z-index less than zero, you're putting it below the main flow content, and I guess the document isn't letting the event pass through it (just like any element with a non-transparent background setting).
IE seems to have a separate issue with the combination of direction: rtl; and position: relative;, but I think it is a separate issue. If I remove every style in .titleIn except direction: rtl; position: relative;, IE still breaks (the link is unclickable). If I remove either of those, IE starts working (but of course, your layout doesn't do what you want).
Unless you made the body's z-index <-1, you are essentially putting the link behind the entire body of the page, of course it's not click-able. (Elements such as body and headings will span the entire width that it is defined, thus invisibly blocking other elements that maybe visible, but not click-able)
If you used Firebug, it will illustrate that pretty well by highlighting the area of the tag.
Well, when I try this in IE, the link becomes active only after I remove position: relative; and margin-top: -10px;. Soooo, do you really need the position: relative? :)