Karena mengandung kode2 dalam Bahasa Inggris, jadi harusnya pengunjung yang mau mencoba ini tau Bahasa Inggris. Jadi cukup versi itu saja ya, kali ini.
This page has been mentioned in Digg. Click here if you like this page! By the way, the methods described below is for educational purposes only. Maybe somehow can let web-browser makers know another security measures that can be taken with this kind of trick.
Introduction
Hi! This is a demonstration on how links can deceive you. Try to click any link on the box below. See your status bar or right click and select properties if you still don't believe.
Place your mouse on those links. What do you see in the status bar of your browser? Right-click on the link and select copy to clipboard or similar. What do you get on the clipboard? Is it different from the address you arrive at when you click the link?
It has been tested on IE 6, Firefox 1.5 and Opera 8.
Click here if you want to download the solution directly!
The Trick
The trick is quite simple. Just place an onmousedown event that sets the link address to the new one. So when the user clicks on the link, he/she will go to the new address.
Before:
<A href="http://www.microsoft.com/ie">
After:
<A href="http://www.microsoft.com/ie"
onmousedown="this.href = 'http://mozilla.org'"
>
Problem 1
When the user goes back to this page, or cancels the loading of the new page, he/she will see the new link address in his/her status bar. So we need to change it back to the old address after the user clicks it.
<A href="http://www.microsoft.com/ie"
onmousedown="this.href = 'http://mozilla.org'"
onclick="this.href = 'http://www.microsoft.com/ie'"
>
Does it work? No! Because the old address will be set again just before the user goes to the new page. So doing this is useless. Hmm, what to do?
Apparently adding a very small delay solves the problem.
<A href="http://www.microsoft.com/ie"
onmousedown="this.href = 'http://mozilla.org'"
onclick="setTimeout(function() {
this.href = 'http://www.microsoft.com/ie';
}, 1)"
>
The "1" above means that the link address will be restored 1 millisecond after the user clicks on the link.
Hurray, the problem is solved!
Problem 2
It's not good to have the old link string mentioned twice. It would be nice if we can just specify it once.
Fine, lets just store the old address before setting the new one. Before that, let's move the event handler outside for more convience. We also add the onclick handler on-the-fly.
linkMap = new Map(); // code is below
function down(obj, e, url) {
linkMap.put(obj, obj.href);
obj.href = url;
obj.onmouseup = obj.onclick = function () {
up(this);
};
}
function up(obj) {
setTimeout(function() {
obj.href = linkMap.get(obj);
}, 1);
}
After that, we can make our link much more simple. That is:
<A href="http://www.microsoft.com/ie"
onmousedown="down(this, event, 'http://mozilla.org')"
>
Problem 3
When the user right-clicks, the new address is shown instead of the old address.
Hmm, seems we need to filter which click triggers the address change. Just modify the down() function to be like this, which supports left-click and middle-click:
function down(obj, e, url) {
linkMap.put(obj, obj.href);
if (!e || !e.which || e.which <= 2) obj.href = url;
obj.onmouseup = obj.onclick = function () {
up(this);
};
}
The !e, !e.which etc is done for the BAD IE browser.
Problem 4
How about keypresses, like for users who navigate links using keyboard?
Fortunately this is not too complicated, just add a onkeydown event that calls the same function as the onmousedown event if the key pressed is 13 (enter) or 32 (space).
function key(obj, e) {
if (e.keyCode == 13 || e.keyCode == 32) obj.onmousedown(obj);
}
And for the link:
<A href="http://www.microsoft.com/ie"
onmousedown="down(this, event, 'http://mozilla.org')"
onkeydown="key(this, event)"
>
How do I make such links?
1. Insert this code inside <script> tags in your page.
function Map() {
this.keys = [];
this.values = [];
this.count = 0;
this.put = function (key, value) {
with (this) {
for (i=0; i<count; i++) if (keys[i] == key) {
values[i] = value;
return;
}
keys[count] = key;
values[count] = value;
count++;
}
}
this.get = function (key) {
with (this) for (i=0; i<count; i++) {
if (keys[i] == key) return values[i];
}
}
}
var linkMap = new Map();
function key(obj, e) {
if (e.keyCode == 13 || e.keyCode == 32) obj.onmousedown(obj);
}
function down(obj, e, url) {
linkMap.put(obj, obj.href);
if (!e || !e.which || e.which <= 2) obj.href = url;
setTimeout(function () {
window.status = linkMap.get(obj);
}, 1);
obj.onmouseup = obj.onkeyup = obj.onclick
= obj.onmouseout = function () {
up(this);
};
}
function up(obj) {
setTimeout(function() {
window.status = obj.href = linkMap.get(obj);
}, 1);
}
2. Create your links. To create it, use this HTML tags:
<a href="the displayed URL"
onmousedown="down(this, event, 'the actual destination URL')
onkeydown="key(this, event)"
>
(Replace the italicized text above with the actual values)
Known Problems
- Using the script above, visitor can still visit the original link address by right-clicking and selecting "Open". You can modify it to handle right click, but the new address will be shown in the status bar. Any suggestion is appreciated.
- In Opera, you can middle-click on the link and open the old address.
- In Firefox, you can hold down the left button to show the new address.
Anyway, majority of the user will only left-click it normally, right?
Conclusion
What is it used for? DON'T FOLLOW THESE SUGGESTIONS!
- To trick people. To surprise people that the link they thought was pointing to some site has misled them.
- To silently count external link clicks on your web page. E.g. the link is shown as http://yahoo.com but is actually http://yoursite.com/count.php?url=http://yahoo.com
- ..... just for fun.
Written by: yuku