Focus and blur events triggered on wrong element - javascript

I'm trying to set a default value for several inputs at once, removing that value on focus and setting it again on blur if the input is empty. To achieve that, using jQuery, I've got this code:
var settings = {
value: '',
focusColor: 'black',
blurColor: '#CCC',
value : 'test'
};
$.each($('input'), function(index, el) {
$(el).on('blur', function(ev) {
$el = $(this);
console.log('blur ' + $el.attr('value') + ' ' + $el.attr('id'));
if ($el.attr('value') == '')
$el.attr('value', settings.value).css('color', settings.blurColor);
}).on('focus', function(ev) {
console.log('focus ' + $el.attr('value') + ' ' + $el.attr('id'));
if ($el.attr('value') == settings.value)
$(this).attr('value', '').css('color', settings.focusColor);
});
$(el).trigger('blur');
});
Having this HTML:
<input id="text" type="text" />
<input id="email" type="email" />
The problem is that, if I focus on the first input and right after on the second one, the events triggered are: focus on first input, blur on first input and focus on first input again. So if I type something in the first one, then focus on the second and in the first one again, it won't remove the sample text and will remove what I typed in.
You can see the (not) working example here. Opening the JavaScript console you'll see clearly the wrong behavior.
​

You forgot the set $el inside the focus event.
$.each($('input'), function(index, el) {
$(el).on('blur', function(ev) {
$el = $(this);
console.log('blur ' + $el.attr('value') + ' ' + $el.attr('id'));
if ($el.attr('value') == '')
$el.attr('value', settings.value).css('color', settings.blurColor);
}).on('focus', function(ev) {
$el = $(this); // <-- should update $el
console.log('focus ' + $el.attr('value') + ' ' + $el.attr('id'));
if ($el.attr('value') == settings.value)
$(this).attr('value', '').css('color', settings.focusColor);
});
$(el).trigger('blur');
});

do you mean something like this:
$('input').on('blur', function(ev) {
$el = $(this);
console.log('blur ' + $el.va() + ' ' + $el.attr('id'));
if ($el.val() == '')
$el.attr('value', settings.value).css('color', settings.blurColor);
})
$('input').on('focus', function(ev) {
$el = $(this);
console.log('focus ' + $el.val() + ' ' + $el.attr('id'));
if ($el.val() == settings.value) {
$(this).val("");
$(this).css('color', settings.focusColor);
}
});
DEMO: http://jsfiddle.net/fnBeZ/4/

Related

Textarea not generating from jQuery

I'm trying to make a website using jquery-1.11.1 where I want a <textarea> to be spawned whenever I click on the link which only shows on mouseenter on a div. But I'm getting an error in my console,
Uncaught ReferenceError: inputdivEditor is not defined (Please ignore JSFiddle errors)
I've absolutely no idea why I'm getting this. Here are my codes,
$(document).ready(function () {
$("[id^=divEditor-]").each(function () {
var content = $(this).html();
var targetID = $(this).attr('id');
var txtID = 'input' + targetID;
$('<textarea id="input' + targetID + '" name="' + txtID + '" >' + content + '</textarea>').insertBefore(this).css('display', 'none');
var button = "<a onclick='activateDivEditor(this, " + txtID + ")' class='custom-edit-button editDiv' id='active" + targetID + "'>Embed Code</a>";
$(this).on('mouseenter', function () {
$(this).prepend($(button));
$(this).css('position', 'relative');
});
$(this).on('mouseleave', function () {
$('.editDiv').remove();
});
});
});
function activateDivEditor(btn, txtId) {
var targetID = $(btn).parent().get(0).id;
var update = "<a onclick='deactivateDivEditor(this, " + txtId + ")' class='custom-edit-button updatediv' id='deactive" + targetID + "'>Update</a>";
var cancel = "<a onclick='cancelactivateDivEditor(this)' class='custom-edit-button cancel' id='cancelactive" + targetID + "'>Cancel</a>";
var targetClass = $('#' + targetID).attr('class');
var targetWidth = $('#' + targetID).width();
$('#' + targetID).css('display', 'none');
$('#input' + targetID).css('display', 'block').css('width', targetWidth - 2).css('height', '125px');
$('#input' + targetID).parent().css('position', 'relative');
$(update).prependTo($('#input' + targetID).parent());
$(cancel).prependTo($('#input' + targetID).parent());
}
JSFiddle Demo
How can I generate a textarea whenever I click on the button link? Need this help badly. Thanks.

jQuery "Unexpected token ILLEGAL"

I have two functions, that are for showing and hiding elements by class:
if (typeof showClass != 'function') {
function showClass(trClass, buttonId, hideMessage, showMessage) {
var button = '#' + buttonId;
var value = hideMessage;
$(button).attr("value", value);
$(button).attr("onclick", "hideClass('" + trClass + "', '" + buttonId + "', '" + showMessage + "', '" + hideMessage + ");");
var classToShow = '.' + trClass;
$(classToShow).css('visibility', 'visible');
}
}
if (typeof hideClass != 'function') {
function hideClass(trClass, buttonId, showMessage, hideMessage) {
var button = '#' + buttonId;
var value = showMessage;
$(button).attr("value", value);
$(button).attr("onclick", "showClass('" + trClass + "', '" + buttonId + "', '" + hideMessage + "', '" + showMessage + ");");
var classToHide = '.' + trClass;
$(classToHide).css('visibility', 'hidden');
}
}
showClass works as excepted, but hideClass causes error "Unexpected token ILLEGAL" in Chrome. With FireFox I don't get any errors, but the function doesn't work with either of the browsers. I tried with different editors to find some illegal characters etc., but no luck. What could be the cause for this?
You're apparently trying to set up a toggling button, but it's the most convoluted mess of jQuery and inline event handlers I've ever seen.
Try this:
function setupToggle(trigger, target, hideMessage, showMessage) {
var state = false; // true means button says "show", target is hidden
var $el = $(trigger);
function update() {
$el.attr('value', state ? showMessage : hideMessage);
$(target).css('visibility', state ? 'hidden' : 'visible');
}
update(); // set initial state
$el.on('click', function() {
state = !state; // on click, flick state and refresh
update();
});
}
usage:
setupToggle('#mybutton', '.mytr', 'Hide it', 'Show it');
The code above may require minor tweaks depending on whether the default state is "hidden" or "shown".

Select dropdown style function jquery

I've got a function that styles select inputs by generating a div with an anchor, list and a hidden field:
function selectMenu() {
var selectMenu = $("#cf-budget");
$('<input id="' + selectMenu.attr("id") + '-hidden" type="hidden" name="' + selectMenu.attr("name") + '" value="" />').insertAfter(selectMenu);
selectMenu.hide();
var selectTitle = selectMenu.children("option:eq(0)").text();
var newSelectMenu = '<div class="selectmenu"><div class="selectmenu-selected"><a rel="placeholder">'+ selectTitle +'</a></div><ul class="selectmenu-menu"><li><a rel="placeholder">'+ selectTitle +'</a></li>';
selectMenu.find("option:not(:eq(0))").each(function () {
newSelectMenu += '<li><a rel="' + $(this).val() + '">' + $(this).text() + "</a></li>";
});
newSelectMenu += "</ul></div>";
$(newSelectMenu).insertAfter(selectMenu);
var newSelectMenu = $("div.selectmenu");
$("div.selectmenu-selected a", newSelectMenu).live("click", function () {
$("ul.selectmenu-menu", newSelectMenu).toggle();
return false;
});
$("body").live("click", function () {
$("ul.selectmenu-menu", newSelectMenu).hide();
});
$("ul.selectmenu-menu a", newSelectMenu).live("click", function () {
var optionValue = $(this).attr("rel");
var optionText = $(this).text();
$("ul.selectmenu-menu", newSelectMenu).hide();
$("div.selectmenu-selected a", newSelectMenu).text(optionText);
$("#" + selectMenu.attr("id") + "-hidden").val(optionValue);
var activeMessageType = $("ul.message-type.active");
if (activeMessageType.length) {
activeMessageType.slideUp(300, function () {
$("#" + optionValue).addClass("active").slideDown(300);
}).removeClass("active");
} else {
$("#" + optionValue).addClass("active").slideDown(300);
}
return false;
});
}
$(document).ready(function() {
selectMenu();
});
My question is how can I adjust this to make it work for 'x' amount of select inputs? Currently it only takes the Id or class of a single select.
I'm guessing I'd need to pass the function a select id or class name so that it can do it stuff to each dropdown?
I have made a jsFiddle here for this that now is fully working: http://jsfiddle.net/7TaqN/1/
The suggestion by ach was perfect, however there was an issue with the body of your code. The following changes had to be made to make it work:
This line had to be removed as it overrode the 'this' selector:
var selectMenu = $("#cf-budget");
This line had to be modified to select the class with the ID of the element clicked to
prevent all elements from being affected:
$(newSelectMenu).insertAfter(selectMenu);
var newSelectMenu = $("div.selectmenu#"+ selectMenu.attr("id"));
This is the full working code as a jQuery module:
(Note this will only work with jQuery 1.8 as the .live() method you are using is deprecated in 1.9
$.fn.selectMenu = function () {
return this.each(function () {
var selectMenu = $(this);
//Body of your selectMenu() function goes here
//All selectors should be in the context of the selectMenu element
$('<input id="' + selectMenu.attr("id") + '-hidden" type="hidden" name="' + selectMenu.attr("name") + '" value="" />').insertAfter(selectMenu);
selectMenu.hide();
var selectTitle = selectMenu.children("option:eq(0)").text();
var newSelectMenu = '<div id="' + selectMenu.attr("id") + '" class="selectmenu"><div id="' + selectMenu.attr("id") + '" class="selectmenu-selected"><a rel="placeholder">' + selectTitle + '</a></div><ul class="selectmenu-menu"><li><a rel="placeholder">' + selectTitle + '</a></li>';
selectMenu.find("option:not(:eq(0))").each(function () {
newSelectMenu += '<li><a rel="' + $(this).val() + '">' + $(this).text() + "</a></li>";
});
newSelectMenu += "</ul></div>";
$(newSelectMenu).insertAfter(selectMenu);
var newSelectMenu = $("div.selectmenu#"+ selectMenu.attr("id"));
$("div.selectmenu-selected a", newSelectMenu).live("click", function () {
$("ul.selectmenu-menu", newSelectMenu).toggle();
return false;
});
$("body").live("click", function () {
$("ul.selectmenu-menu", newSelectMenu).hide();
});
$("ul.selectmenu-menu a", newSelectMenu).live("click", function () {
var optionValue = $(this).attr("rel");
var optionText = $(this).text();
$("ul.selectmenu-menu", newSelectMenu).hide();
$("div.selectmenu-selected a", newSelectMenu).text(optionText);
$("#" + selectMenu.attr("id") + "-hidden").val(optionValue);
var activeMessageType = $("ul.message-type.active");
if (activeMessageType.length) {
activeMessageType.slideUp(300, function () {
$("#" + optionValue).addClass("active").slideDown(300);
}).removeClass("active");
} else {
$("#" + optionValue).addClass("active").slideDown(300);
}
return false;
});
});
};
$(document).ready(function () {
$('.mySelectClass').selectMenu();
});
You could make it into a jQuery plugin:
$.fn.selectMenu = function() {
return this.each(function() {
var selectMenu = $(this);
//Body of your selectMenu() function goes here
//All selectors should be in the context of the selectMenu element
});
};
Then use it with standard jQuery selectors like so:
$('.mySelectClass').selectMenu();
Edit: Looks like you're already setting the context using the second parameter of jQuery() so additional use of find shouldn't be necessary. That's a lot of code to parse through visually, though -- a jsfiddle might help.
You'll also need to replace some of your selectors so that they're evaluated on the children of the selectMenu element, for example:
selectMenu.find("div.selectmenu-selected a", newSelectMenu).live("click", function () {

jquery click does not work

Anyone have an idea why my jQuery click won't work?
It's attached to a hyperlink.
jQuery(function ($) {
$(".delete").click(function(e) {
alert("Hello");
});
var socket = io.connect();
var $messageForm = $('#sendmessage');
var $messageTitle = $('#title');
var $messageBox = $('#message');
var $chat = $('#chat');
$messageForm.click(function (e) {
if ($.trim($("#title").val()).length === 0) {
alert('You must provide valid input');
$messageTitle.val('');
$messageBox.val('');
return false;
}
if ($.trim($("#message").val()).length === 0) {
alert('You must provide valid input');
$messageTitle.val('');
$messageBox.val('');
return false;
} else {
e.preventDefault();
socket.emit('send message',
'<b>' + $messageTitle.val() + '</b>' + ' - '
+ $messageBox.val() + ' ' + '[' +
'<a class="delete" href="#">Delete</a>' + ']');
$messageTitle.val('');
$messageBox.val('');
}
});
socket.on('new message', function (data) {
$chat.prepend(data + "<br/>");
});
});
Since the delete links are dynamically generated, you need to use event delegation:
$('#chat').on('click', '.delete', function(e) {
alert("Hello");
});
Hello try to modify your jquery initialization like this:
(function($){ }(jQuery)
If your script still doesn't fire the click event, check if $messageForm exists, using console.log($messageForm). You can modify var $messageForm in var messageForm from what I seen that variable does not need a scope so wide. I hope this could help you

Jquery Scope Problems

function drawLabel(labelsIndex) {
// Check not deleted Label data:(DBID, text, styling, x, y, isDeleted)
if (!labelData[labelsIndex][5]) {
// Create
var newLabel = $('<div id="label' + labelsIndex + '" style="font-size:' + (labelData[labelsIndex][6] * currentScale) + 'px;z-index:9999;position:absolute;left:' + labelData[labelsIndex][3] + 'px;top:' + labelData[labelsIndex][4] + 'px;' + labelData[labelsIndex][2] + '">' + labelData[labelsIndex][1] + '</div>');
$('#thePage').append(newLabel);
// Click edit
$('#label' + labelsIndex).dblclick(function() {
if (!isDraggingMedia) {
var labelText = $('#label' + labelsIndex).html();
$('#label' + labelsIndex).html('<input type="text" id="labelTxtBox' + labelsIndex + '" value="' + labelText + '" />');
document.getElementById('#label' + labelsIndex).blur = (function(index) {
return function() {
var labelText = $('#labelTxtBox' + index).val();
$('#label' + index).html(labelText);
};
})(labelsIndex);
}
});
The code is meant to replace a div's text with a textbox, then when focus is lost, the textbox dissapears and the divs html becomes the textbox value.
Uncaught TypeError: Cannot set property 'blur' of null
$.draggable.start.isDraggingMediaresources.js:27
c.event.handlejquery1.4.4.js:63
I think I'm getting a tad confused with the scope, if anyone could give me some points I'd appreciate it. It would also be good if someone could show me how to remove the blur function after it has been executed (unbind?)
document.getElementById('#label' + labelsIndex).blur is a javascript function and less jquery :) therefore the # hash there is just irrelevant.
$('#label'+labelsIndex).bind('blur',function (){
//labelText value goes here //
});
EDIT
to be honest ur over complicating it :)
<div id="txt1">I am div</div>
<textarea id="txt2">I am text</textarea>
$('#edit_button').click(function (){
var val = $('#txt1').hide().html();// hide the div,then get value,
$('#txt2').show().val(val);//show txtarea then put value of div into it
});
Do the opposite for $('#save_button');

Categories