views:

339

answers:

5

Hey,

I have an input text :

<input name="Email" type="text" id="Email" value="[email protected]" />

I want to put a default value like "What's your programming question ? be specific." in StackOverFlow, and when the user click on it the default value disapear.

+4  A: 

EDIT: Although, this solution works, I would recommend you try MvanGeest's solution below which uses the placeholder-attribute and a javascript fallback for browsers which don't support it yet.

If you are looking for a Mootools equivalent to the JQuery fallback in MvanGeest's reply, here is one.

--

You should probably use onfocus and onblur events in order to support keyboard users who tab through forms.

Here's an example:

<input type="text" value="[email protected]" name="Email" id="Email"
 onblur="if (this.value == '') {this.value = '[email protected]';}"
 onfocus="if (this.value == '[email protected]') {this.value = '';}" />
mqchen
Thank you very much.
dotNET
-1 for polluting the DOM.
roosteronacid
Seconded. -1 for DOM pollution, there are more semantic solutions (not to mention cleaner, shorter etc.)
MvanGeest
What do you mean with "polluting the DOM"? Do you mean using the event attributes? What's wrong with that?
RoToRa
@MvanGeest: Show us one :) I've done this a long time and while I'd make this unobtrusive script, I disagree with your shorter argument. Can you show me *anything* shorter and works *now* in a cross-browser way, notice I said **now**, not 5 years from now.
Nick Craver
@Nick: take a look at my answer. It now includes a JavaScript-only function for doing just this. In terms of characters, it's just about the same length as the DOM-pollution shown in this answer.
roosteronacid
The shorter argument only applies when there's more than 1 of these inputs, which of course depends on the type of form (search/registration/...). Even then, I'd have to select the elements first... for which I would use jQuery... you're probably right :) And I've only got a few years of experience; I'm simply a purist.
MvanGeest
@roosteronacid - Your method is a) longer, and b) doesn't do the same thing, as I mentioned in comments on your answer, you don't check for a valid **non-default** value when focusing. I don't disagree it's the way to go, that's why my comment said "I'd make this unobtrusive script", but it's not shorter and is not any more "DOM" polluting...exactly how does it pollute the DOM? It's a perfectly valid way of attaching an event handler, *preferred*? no, *valid*? absolutely. What if the page was a post result, and the value wasn't `[email protected]` initially? This works, your's doesn't.
Nick Craver
I thought the asker just wanted a simple solution, so I just gave him the simplest without much second thought. But, I think the ideal solution (as you have pointed out) would be to use the `placeholder`-attribute with a Javascript fallback for browsers who don't support it yet.
mqchen
@Nick: I think my code does exactly what AZIRAR wants. The code provided in this answer is the very definition of DOM pollution: cramming JavaScript (or in-line styles for that matter) into your HTML.
roosteronacid
@mq.chen: This is fast and easy, sure. But I think you're being a bit too pragmatic :)
roosteronacid
@roosteronacid - You're confusing **clean source** with a **clean DOM**, these are 2 *very* different concepts. This is an *alternative way of attaching the handler*, the DOM will see very little difference between this an an unobtrusive method. The markup *is not the DOM*, it's the structure from which the DOM is initialized.
Nick Craver
@Nick: you're right. Polluting the source is what I'm getting at.
roosteronacid
IMHO there is nothing wrong with using the HTML attributes. Most importantly its not "polluting the DOM". It is the best and most reliable way to set event listeners that work immediately without having to wait for on-DOM-ready/onload. The only improvement that could be done would be to extract the inline code into functions.
RoToRa
A: 

If you use jquery you could try the jquery watermark plugin

See here for a demo

Rippo
+1  A: 

Using jQuery, you can do:

$("input:text").each(function ()
{
    // store default value
    var v = this.value;

    $(this).blur(function ()
    {
        // if input is empty, reset value to default 
        if (this.value.length == 0) this.value = v;
    }).focus(function ()
    {
        // when input is focused, clear its contents
        this.value = "";
    }); 
});

And you could stuff all this into a custom plug-in, like so:

jQuery.fn.hideObtrusiveText = function ()
{
    return this.each(function ()
    {
        var v = this.value;

        $(this).blur(function ()
        {
            if (this.value.length == 0) this.value = v;
        }).focus(function ()
        {
            this.value = "";
        }); 
    });
};

Here's how you would use the plug-in:

$("input:text").hideObtrusiveText();

Advantages to using this code is:

  • Its unobtrusive and doesn't pollute the DOM
  • Code re-use: it works on multiple fields
  • It figures out the default value of inputs by itself



Non-jQuery approach:

function hideObtrusiveText(id)
{
    var e = document.getElementById(id);

    var v = e.value;

    e.onfocus = function ()
    {
        e.value = "";
    };

    e.onblur = function ()
    {
        if (e.value.length == 0) e.value = v;
    };
}
roosteronacid
3 comments here: 1) `if (this.value == v) this.value = v;` should be `if (this.value === "") this.value = v;`, 2) You're clearing the value on focus, even if it's a valid, non-default value, and 3) Don't *assume* they're using jQuery.
Nick Craver
Aye. I spotted the mistake and corrected it. Thanks thou Nick :)
roosteronacid
@roosteronacid: Your solution still clears the element if I put any input and re-focus the element, this wouldn't be desirable behavior.
Nick Craver
+7  A: 

For future reference, I have to include the HTML5 way to do this.

<input name="Email" type="text" id="Email" value="[email protected]" placeholder="What's your programming question ? be specific." />

If you have a HTML5 doctype and a HTML5-compliant browser, this will work. However, many browsers do not currently support this, so at least Internet Explorer users will not be able to see your placeholder. However, see http://www.kamikazemusic.com/quick-tips/jquery-html5-placeholder-fix/ for a solution. Using that, you'll be very modern and standards-compliant, while also providing the functionality to most users.

Also, the provided link is a well-tested and well-developed solution, which should work out of the box.

MvanGeest
+3  A: 

This is somewhat cleaner, i think. Note the usage of the "defaultValue" property of the input:

<script>
function onBlur(el) {
    if (el.value == '') {
        el.value = el.defaultValue;
    }
}
function onFocus(el) {
    if (el.value == el.defaultValue) {
        el.value = '';
    }
}
</script>
<form>
<input type="text" value="[some default value]" onblur="onBlur(this)" onfocus="onFocus(this)" />
</form>
Jani
+1 I was just staring to write about `defaultValue`
Anpher