2

I have been using the HTML 5 placeholder and just realised that it does not work outside HTML5 devices. As you can see by the code below the placeholder is always in lowercase and the value is always in upper case.

#maphead input::-webkit-input-placeholder {
    text-transform:lowercase;
}
#maphead input:-moz-placeholder {
    text-transform:lowercase;
}
<input id="start" type="text" spellcheck="false" placeholder="enter your post code" style="text-transform:uppercase;" class="capital"/>

This is all fine except when dealing with non HTML 5 devices. For this I have employed a bastardised bit of javascript.

function activatePlaceholders() {
        var detect = navigator.userAgent.toLowerCase(); 
        if (detect.indexOf("safari") > 0) return false;
        var inputs = document.getElementsByTagName("input");
        for (var i=0;i<inputs.length;i++) {
            if (inputs[i].getAttribute("type") == "text") {
                var placeholder = inputs[i].getAttribute("placeholder");
                if (placeholder.length > 0 || value == placeholder) {
                    inputs[i].value = placeholder;
                    inputs[i].onclick = function() {
                        if (this.value == this.getAttribute("placeholder")) {
                            this.value = "";
                        }

                        return false;
                    }
                    inputs[i].onblur = function() {
                        if (this.value.length < 1) {
                            this.value = this.getAttribute("placeholder");
                            $('.capital').each(function() {
            var current = $(this).val();
            var place = $(this).attr('placeholder');
            if (current == place) {
                $(this).css('text-transform','lowercase')
            }
            });
                        }
                    }
                }
            }
        }
    }

    window.onload = function() {
        activatePlaceholders();
    }

Firstly this Javascript is rancid. There must be an easier JQuery way. Now although this above does work (reasonably) it does not respond to keeping the placeholder in lowercase and the value in uppercase since it sets the value with the placeholder.

I've set you all up with a nice Fiddle http://jsfiddle.net/Z9YLZ/1/

Trott
  • 66,479
  • 23
  • 173
  • 212
Walrus
  • 19,801
  • 35
  • 121
  • 199

4 Answers4

4

Try something like this:

$(function() {
    $('input[type="text"]').each(function () {
        $(this).focus(function () {
            if ($(this).attr('value') === $(this).attr('placeholder')) {
                $(this).css('text-transform','lowercase');
                $(this).attr('value', '');
            }
        }).blur(function () {
            if ($(this).attr('value') === '') {
                $(this).css('text-transform','uppercase');
                $(this).attr('value', $(this).attr('placeholder'));
            }
        }).blur();
    });
});

Edit: Explicitly declare the text-transform to cascade properly.

Peter Stone
  • 3,756
  • 4
  • 23
  • 14
  • well, it'll still have the problem with lower case, but it's hard to deny that the code is neater. – Spudley May 27 '11 at 16:02
  • .empty { text-transform: lowercase; } in the CSS should handle the case transform. Edit: ... unless you run into cascading problems, then you can declare the style explicitly. – Peter Stone May 27 '11 at 16:06
  • problem with this approach is that for you won't see placeholder text. – krcko May 27 '11 at 16:06
  • Your code is correct actually but the wrong way round. Sorry I dismissed it. Change lowercase and uppercase to the other way round and problem solved. – Walrus May 27 '11 at 16:38
0

Try this one, I'm using it for a while and it works perfectly:

(function($, undefined) {

var input = document.createElement('input');
if ('placeholder' in input) {
    $.fn.hinttext = $.hinttext = $.noop;
    $.hinttext.defaults = {};
    delete input;
    return;
}
delete input;

var boundTo = {},
    expando = +new Date + Math.random() * 100000 << 1,
    prefix = 'ht_',
    dataName = 'hinttext';

$.fn.hinttext = function(options) {

    if (options == 'refresh') {

    return $(this).each(function() {
        if ($(this).data(dataName) != null) {
            focusout.call(this);
        }
    });
    }

    options = $.extend({}, $.hinttext.defaults, options);

    if (!(options.inputClass in boundTo)) {

    $('.' + options.inputClass)
        .live('focusin click', function() {
        $($(this).data(dataName)).hide();
        })
        .live('focusout', focusout);
    boundTo[options.inputClass] = true;
        }

    return $(this).each(function(){

    var input = $(this),
        placeholder = input.attr('placeholder');

        if (placeholder && input.data(dataName) === undefined) {

        var input_id = input.attr('id'),
            label_id = prefix + expando++;

        if (!input_id) {
            input.attr('id', input_id = prefix + expando++);
        }

        $('<label/>')
            .hide()
            .css('position', options.labelPosition)
            .addClass(options.labelClass)
            .text(placeholder)
            .attr('for', input_id)
            .attr('id', label_id)
            .insertAfter(input);

        input
            .data(dataName, '#' + label_id)
            .addClass(options.inputClass)
            .change(function() {
                focusout.call(this);
            });
        }

        focusout.call(this);
    });
};

$.hinttext = function(selector, options) {
    if (typeof selector != 'string') {
        options = selector;
        selector = 'input[placeholder],textarea[placeholder]';
    }
    $(selector).hinttext(options);
    return $;
};

$.hinttext.defaults = {
    labelClass: 'placeholder',
    inputClass: 'placeholder',
    labelPosition: 'absolute'
};

function focusout() {

    var input = $(this),
        pos = input.position();

    $(input.data(dataName)).css({
        left: pos.left + 'px',
        top: pos.top + 'px',
        width: input.width() + 'px',
        height: input.height() + 'px'
    })

    .text(input.attr('placeholder'))

    [['show', 'hide'][!!input.val().length * 1]]();
}

$($.hinttext);

})(jQuery);

You just need to make sure to style label.placeholder with CSS to look the same as HTML5 placeholder text (color: #999)

krcko
  • 2,834
  • 1
  • 16
  • 11
0

Try this: http://jsfiddle.net/msm595/Z9YLZ/12/

Alex
  • 1,327
  • 2
  • 11
  • 20
  • Actually that caused additional problems with CSS styles and did not work effectively on firefox – Walrus May 27 '11 at 16:37
0

Bit late but here's what I do. Store all the default values on page load and then clear value text ONLY when it's the default value that is clicked on. This prevents the JS clearing user entered text.

jQuery(document).ready(function($){

var x = 0; // count for array length

$("input.placeholder").each(function(){
    x++; //incrementing array length
});

var _values = new Array(x); //create array to hold default values

x = 0; // reset counter to loop through array

$("input.placeholder").each(function(){ // for each input element
    x++;
    var default_value = $(this).val(); // get default value.
    _values[x] = default_value; // create new array item with default value
});

var current_value; // create global current_value variable

$('input.placeholder').focus(function(){
    current_value = $(this).val(); // set current value
    var is_default = _values.indexOf(current_value); // is current value is also default value

    if(is_default > -1){ //i.e false
        $(this).val(''); // clear value
    }
});

$('input.placeholder').focusout(function(){
    if( $(this).val() == ''){ //if it is empty...
        $(this).val(current_value); //re populate with global current value
    }

});

});
iamjonesy
  • 24,732
  • 40
  • 139
  • 206