

Using pushState? Make sure your links are fine - jcxplorer
http://dev.tenfarms.com/posts/proper-link-handling

======
JoshTriplett
Something seems fundamentally wrong here. If I middle-click or ctrl-click on a
link, the browser shouldn't _allow_ the site to interfere with that,
accidentally or otherwise. Those shortcuts represent part of browser chrome,
just like the shortcuts for the URL bar, the search bar, and the back button.

~~~
skymt
It's not that pushState() apps _interfere_ with middle-clicking on links, it's
that they have no real links to middle-click on. Common practice is to have a
<div> or <span> (or maybe <a> without an href) styled to look like a
link/button, then onclick run some code that performs a task and changes the
URL with pushState(). This article suggests making your pushState() "links"
actual links to the desired URL, then overriding the unmodified click case to
run the desired code rather than fetch a new page from the server.

~~~
alanh
Oh god — that’s common practice? … What happened to progressive enhancement &
unobtrusive JS being best practices?

~~~
pbiggar
Both progressive enhancement and unobtrusive JS are dead. They died, in my
opinion, for a lot of good reasons:

\- basically everyone has JS enabled

\- they were too hard to do

\- IE6 went away

\- you can make significantly better UX without them

\- there is business value to usable apps

\- there is no business value to catering to people who disable javascript

\- the existence of things like Modernizer make it possible to assume that
everyone has the fancy features you need.

~~~
alanh
Some of your points are quite valid, but I must disagree progressive
enhancement & unobtrusive JS are “dead” or should be.

> _\- you can make significantly better UX without them_

This is the biggest place where you’re wrong, as the examples of right-
clicking or middle-clicking a “div with JavaScript” plainly illustrate.

Now obviously complicated web apps can’t work 100% or sometimes even 10%
without JavaScript, but when reasonably possible, using progressive
enhancement & unobtrusive JS will increase your compatibility across UAs,
search engines, and other agents, and will avoid cases where your site seems
broken in some crucial way.

Not to mention users with accessibility needs will do much better interacting
with your `<a>` tags than scripted `<div>`s. Have we forgotten about them
again, already?

 _Edited to add:_ Biggest tips w.r.t. accessibility: (a) Spend an hour using a
screenreader and no mouse — e.g. VoiceOver, which comes with your Mac and
works just fine in Safari. (b) Using semantic tags & progressive enhancement
means your code will make the most sense to the screenreader — e.g. you will
be able to tab onto your button/link because you actually defined it as one —
and it will be described fairly accurately. Your "clickable" <span> is plainly
going to be trickier for a screenreader… (c) Read up on WAI-ARIA, which lets
you define roles for certain elements (like "notification" or "button"). If
you want to make your AJAX work well for those with accessibility needs, this
becomes fairly important as it can also help you manage focus and direct user
attention.

~~~
pbiggar
Certainly, there's the right way and the wrong way, but don't throw the baby
out with the bathwater. It's still early days for pushstate apps, and they
have yet to get their "Rails moment". Middle-clicking problems and the like
are inevitable. (Do you remember sites used sessions to remember where you
clicked, so tabs didnt work at all? This too shall pass).

You say progressive enhancement helps you out in all these cases, but I just
see opinion, and very little evidence. So all I have to offer you in rebuttal
is the same - I believe the opposite.

I agree about accessibility. I frankly don't know what to do there. On the one
hand, I hate the idea that I might be excluding somebody. On the other hand, I
tend to implement things lazily, so if I'm never asked for a feature, I
probably won't do it.

------
jordanlev
Your post brings up a great point, and I _hate_ it when I can't open links in
new windows (Harvest invoice/estimate list, I'm looking at you!). But I wonder
if there's a way to handle it in a more abstract fashion -- in the sense that
you let the browser tell you if a link is to be opened in a new window/tab, as
opposed to hardcoding various keyboard buttons.

For example, does your technique handle middle-clicks (clicking on the middle
mouse button, which is equivalent to shift-clicking)?

~~~
pbiggar
On a Mac, middle-click is not exactly the same as Cmd-clicking. Middle-click
can't be overridden, Cmd-click can. On my site, middle clicking works fine,
but I have to put in a hack to make Cmd-click work.

------
alanh

      rel="internal"
    

raised my eyebrows. Yes, it makes sense. But the `rel` attribute is not to be
used lightly and values are not to be invented on a whim, because eventually
the value can be defined for _all_ sites, not just yours.

Without thoroughly researching it, it looks like `rel=internal` is not
standardized. That means you should not use it!

Instead, consider:

    
    
      <a href="/page" data-push-state="push">Foo</a>
    

and

    
    
      jQuery('a[data-push-state=push]')
    

The data-* attributes are explicitly defined as open for your own invention
and use.

~~~
bcherry
Or `jQuery("a[href^='/']")` and you don't need extra attributes at all.

~~~
jcxplorer
Great suggestion, thanks! I just updated the blog post with. I'll be happy to
link to your site/twitter at the end of the post if you give me that
information :)

~~~
saurik
Do you really never use relative URLs?

------
pbiggar
The author is very right. The links on my site (<https://circleci.com>) don't
work if you middle-click them. Some kind StackOverflow users found the
problem, which appears to be the click handler in Sammy.JS.

A lot more info about this is in the question, an the links from it, including
history, Mozilla accessibility discussion, and code samples:

[http://stackoverflow.com/questions/10660360/command-click-
do...](http://stackoverflow.com/questions/10660360/command-click-doesnt-open-
a-new-tab-but-middle-click-does)

------
pud
Good timing. About 5 minutes ago I pushed this live on my site. Click any of
the video thumbnails here to see (and report bugs if you find any..:)

Also, I'm using hashbangs if the browser doesn't support pushState (like IE).

And if you're visiting from a mobile browser, I don't do any of the pushState
fanciness either.

<http://fandalism.com>

~~~
derpmeister
Looks borked from here: <http://imgur.com/6ZDvR>

------
jchavannes
I'd argue the majority of the time hashbangs should be used over pushstate.
Until HTML5 is the norm (>99%, so basically never) there isn't much reason to
use pushstate. I know this is not what this article is about so I'm not going
to go into detail.

------
drivebyacct2
Wow, I feel really stupid. I had no idea that the browser let JS override the
default on regular <a>'s with onclick handlers with modifier keys.

No wonder so many gdamn sites get it wrong. Nothing infuriates me more than
whichever lightbox implementation always sieves control of my ctrl+clicks and
then _doesn't allow me to view the picture in a larger size_. Infuriating.

