Facebook style "change picture" link

I’m looking at the “change picture” link that appears when you mouseover your profile picture on Facebook. I want to add a similar link to all images that appear on my site, but instead links to download the full size photo. Can this be done with simple CSS or do I need some sort of jquery, etc?

Have you had a look at the code they use (using Firebug)? I have a feeling it might be javascript rather than CSS.

Facebook uses some JavaScript there, but you could do this just with CSS. It’s a bit like a single-item drop down list.

What do you mean, though, when you speak of “downloading” the picture. Do you mean viewing the picture on its own page, or actually initiating the download process? That might be a different kettle of fish.

I guess my use of downloading was a bit off, I really meant just liking to the full size image.

So what you’re saying is just using simple CSS where the img link hover produces that little moverover deal in the same style as a drop down menu?

I just had a poke at it. They use javascript to change the class(es).

I see they’re using javascript as well and I don’t think I need to go that route. Like ralph.m said, it looks like it can be done with simple CSS, but I seem to be missing something. Here’s what I’ve cooked up so far:

.download { width: 75px; height: 25px; position: relative; float: right; background: #000; opacity: 0.5; display: none; z-index: 3; }
.download a:hover { display: inline; }

<a href="download url"><span class="download">Download Photo</span><img src="thumbnail url" alt="" /></a>

I’d just do something akin to the following,

a.picture { display: block; height: 150px; width: 75px; }
a.picture img { ..... }
a.picture span { positioning....; visibility: hidden }
a.picture:hover span { visibility: visible; }
<a href="/url/" class="picture">
    <img src="/url/" alt="/" />
    <span><a href="/url/">Change Picture</a></span>
</a>

I don’t really see the need for any javascript there.

Edit: You may chose to use display: none; over visibility. Visibility maintains it’s place on the page but isn’t visible: (e.g. as if something was invisible, it’s still there), display: none; completely removes it. You could probably do away with the span as well if the ‘change picture’ (/download photo) link is just a simple rectangular block (remember you can always set a background image with a colour and add padding to have something similar to Facebook’s approach.

Come to think of it I’m not actually sure if it’s ok to nest anchor tags? I’ve never had to.

Edit 2: Turns out nested anchors are illegal, http://www.w3.org/TR/html401/struct/links.html#h-12.2.2, though you could still achieve it by using a span as a container for the image. Just surround the img in an anchor as well if you want it to link elsewhere, e.g.

<span class="picture">
    <a href="/url/"><img src="/url/" alt="/" /></a>
    <a href="/url/" class="download">Download Photo</a>
</span>

If you are willing to use an image for the link box in the corner you can use the following code. The only thing with this example is it is going off of a fixed size for the photo thumbnail… so it will work if you have a gallery set up with all the same sized thumbnails which is what it kind of sounded like to me. Otherwise this particular approach would be a pain to tweak for multiple image sizes. (sorry ^^;; )

img {border:0;}
a {text-decoration:none;}
.photo {width:200px; height:130px;}
.profile-photo {z-index:1; position:absolute;}
a.photolink {
	width:200px; 
	height:130px; 
	float:left; 
	z-index:10; 
	position:absolute;}
a.photolink:hover {background: url(../images/download.png) no-repeat top right;}
<div class="photo">
	<img src="images/profile.jpg" class="profile-photo" />
	<a href="#" class="photolink"></a>
</div>

Matt, I can’t seem to get your code to work…

Works for me,

span.photo
{
	background: red;
	display: block;
	height: 200px;
	width: 175px;
}

span.photo a
{
	background: yellow;
	display: block;
	float: right;
	height: 25px;
	width: 120px;
	visibility: hidden;
}

span.photo:hover a
{
	visibility: visible;
}
<span class="photo">
    <a href="/">Download Photo</a>
</span>

To display the image you’d just set absolute positioning on the img (span.photo img { position: absolute; }) and anchor (float won’t work anymore) elements.

It took some wrangling, but here’s what I came up with that works:

.high-res-image { position: relative; width: 500px; margin: 0 auto; display: block; }
.high-res-text { position: absolute; top: 7px; left: 11px; padding: 5px; vertical-align: middle; background: rgba(255, 255, 255, .7); color: #000; border: 1px solid #fff; visibility: hidden; }
.high-res-image:hover .high-res-text { visibility: visible; }
<div class="high-res-image"><a href=""><img src="thumbnail url" alt="" /><div class="high-res-text">Download High Res Photo</div></a></div>

Thanks for helping to nudge me in the right direction.

@Matt
Great! That last example worked, but it’s not even close to your previous examples. XP

Nice to see it working with a text link. nod But now there’s no way to align it to the top-right corner (if that’s needed). I will admit that it’s nice because it works with any size image now. I’ll point out that the width and height values in span.photo are not needed since it will fit to the size of the contents.

If you want just a text option, you could use the basic model for a drop list, although you’d need a JS fix for IE6.

<p>
<img src="image.gif" alt="">
<a href="">Click</a>
</p>
p {position:relative; float:left;}

a {position: absolute; right: -9999px;}

p:hover a {display:block; padding:4px; background:white; right:0; top:0;}

@stanger1982 Nice! Very clean looking and it works like a charm! Now I wish I thought up that solution. :wink: