hide andriod mobile keyboard in React JS? - javascript

I am working on a project where I have to make an input field that is for search products. the search function is working well. but after pressing enter on Andriod mobile keyboard is not hidden. I am using keypress,keyup and keydown events. In the event function, I am using the blur function but it is not working. I am used to creating another visibility hidden input and button and then changing the focus to that field but it is not working. I am finding a solution on google but I found solutions in react native.
// e.target[0].blur();
if (e?.charCode == 13 || e?.type == 'blur' || e?.key === "Enter" || e?.key === 66 || e?.charCode == 66) {
// e.preventdefault();
// console.log("after if ............ ");
// const node = document.getElementById('search-bar-id');
// // node.readOnly = true;
// // node.disabled = true;
// node.setAttribute('readonly', 'readonly'); // Force keyboard to hide on input field.
// node.setAttribute('disabled', 'true'); // Force keyboard to hide on textarea field.
// setTimeout(function() {
// node.blur(); //actually close the keyboard
// // Remove readonly attribute after keyboard is hidden.
// node.removeAttribute('readonly');
// node.removeAttribute('disabled');
// }, 2000);
// setTimeout(function() {
// setMShow(true);
// }, 2000);
// document.getElementById('search-bar-id').disabled = true;
// setTimeout(function() {
// document.getElementById('search-bar-id').disabled = false;
// }, 2000);
// var button = document.createElement('BUTTON')
// button.style.visibility="hidden"
// button.click();
// setBShow(true);
// document.getElementById("search-bar-id1").blur();
// document.getElementById('search-bar-id2').focus();
// setTimeout(()=>{
// document.getElementById("search-bar-id1").style.display = "none";
// setBShow(false);
// },1000)
}
I have tried all my possible solutions. (react js,next js)
i am trying blur function and fake events but it is not working. i am expecting hide keyboard after click enter button in mobile keyboard.

Related

Capturing Tabbed Focus/Blur properly

So for accessibility purposes I am trying to captured tabbed focus and blur events to capture tab order within a modal.
For some reason I am running into some odd browser behavior.
Inside my component I have the following code:
// On Init
ngOnInit (){
// Get all of the buttons and anchors in the modal
var buttons = this.modal.nativeElement.querySelectorAll("button, a");
// Get the number of buttons
var numButtons = buttons.length;
// Get the last button
var lastButton = buttons[numButtons - 1];
// When the last button loses focus
lastButton.addEventListener("blur", (e: any) => {
// Prevent Default
e.preventDefault();
// Focus on the modals close button
this.focusCloseButton();
})
}
And TECHNICALLY this works perfectly. If I log out the active element after the call to this.focusCloseButton, I indeed get a reference to the close button.
HOWEVER, the tab actually moves to the browser itself into whatever the first element is. For Chrome this is the "View site information" button to the left of the URL bar. In Firefox this is the first tab in the list of tabs.
How can I capture this properly so that the browser is not hijacking the tab press?
Apparently the blur event happens too late to be captured before the browser takes over.
Instead I used keybinding to detect when the tab-key was pressed and did the capturing from there.
// The OnInit function handles capturing tab order
ngOnInit (){
// All of the buttons and links in the modal
var buttons = this.modal.nativeElement.querySelectorAll("button, a");
// The first button or link in the modal
var firstButton = buttons[0];
// The last button or link in the modal
var lastButton = buttons[buttons.length - 1];
// Listen for keydown events on the modal
this.modal.nativeElement.addEventListener("keydown", (e: any)=> {
// If the key pressed was the tab button
if ( e.keyCode === 9 && !e.shiftKey ) {
// If the currently active element is the last button
if (document.activeElement == lastButton){
// Prevent default action
e.preventDefault();
// Put focus on the close button
this.focusCloseButton();
}
} else if ( e.keyCode === 9 && e.shiftKey === true ){
// If the key pressed was shift+tab
// And the currently active button is the close button
if ( document.activeElement == firstButton ){
// Prevent Default
e.preventDefault();
// Focus the last button
lastButton.focus();
}
}
})
}
for those wondering about what this.focusCloseButton does:
// Puts focus on the close button
focusCloseButton: Function = function(){
this.closeButton.nativeElement.focus();
};
The reference to closeButton is created by ViewChild:
// Reference to the close button
#ViewChild("closeButton") closeButton: ElementRef;
Which ties into the dom with the marked element:
<button #closeButton></button>

how to prevent tab in jquery?

can we stop prevent blur or tabbing for 5 second in input field.then after 5 second user can tab from one field to another.I use off and on function but it is not working .here is my code
http://jsfiddle.net/GV3YY/99/
$("input").off("blur");
setTimeout(function(){
$("input").on("blur");
},5000)
You need to "lock" the inputs when they is focused and use setTimeout to "unlock" it after 5 seconds. A naive implementation could look something like this: https://jsfiddle.net/my7wk6gj/2/
Update: Now pseudo prevents bluring by click. The blur still happens, but focus is returned to the original input until the 5 seconds have passed. I couldn't get event.stopImmediatePropagation to work for blur, so this is the next best thing...
var lockInput = false;
var focusTarget = null;
var lockTimeout = null;
$('input').on('focus', function (e) {
if (lockTimeout) {
return;
}
lockInput = true;
lockTimeout = setTimeout(function () { lockInput = false; lockTimeout = null }, 5000)
}).on('keydown', function (e) {
if (e.keyCode === 9 && lockInput) {
e.preventDefault();
return false;
}
}).on('blur', function (e) {
console.log('blur')
if (lockInput && focusTarget === null) {
focusTarget = e.target;
setTimeout(function () {
focusTarget.focus();
focusTarget = null;
});
}
});
The global variables are used only for the example, i'd advice against that.
Also, if you have a large number of inputs, i'd suggest using event delegation, instead of adding a listener to every one of them.

Do an event when user has stopped typing into a text input

I want to do an action after user is finished typing into a text input, but ignoring the delete key.
I can "wait" for the user to finish typing into the text input by using underscore's debounce function.
I need to also listen to make sure the delete key wasn't used, and that is where my code seems to breakdown.
Here is what I've tried http://jsfiddle.net/4Wn8L/:
var lazyChange = _.debounce(function(e){
if (e.keyCode != 8) {
console.log('User entered a key that wasnt backspace!');
}
}, 300);
$('#appPreview').on('keyup', 'input', lazyTripChange);
You could do something like this:
<input type="search" class="lazy-search">
$(document).ready(function() {
var thread = null;
var delayMs = 500;
function doSearch(str) {
console.log('search: ' + str);
}
$('.lazy-search').keyup(function(e) {
if (e.keyCode != 8) {
clearTimeout(thread);
var target = $(this);
thread = setTimeout(function() {
doSearch(target.val());
}, delayMs);
}
});
});
Fiddle: http://jsfiddle.net/HfY2N/1/ (check console)
"When the user presses a key create a timeout which does a search after n milliseconds, but if the user presses a key again before that count has expired then clear it and create another one"

Keydown effect, alert if keyup before effect finishes

My goal: Press and HOLD space key while an effect occurs (to simulate a fingerprint scan). If user releases key before effect finishes, I want to display a confirm message. The keydown part works fine and proceeds to function "process", but no error message is displayed on keyup if it is released before the effect finishes. This is what I have...
var active = false;
$(document).one("keydown", function(e) {
if ((e.keyCode == 32) && (active == false)) {
active = true;
$(".panel_1").slideDown(5000, function() {
active = false;
$(".panel_1").slideUp(2000, function() {process(); })
});
}
});
$(document).one("keyup",function(e) {
if ((e.keyCode == 32) && (active == true)) {
var r=confirm("Oops! You must HOLD down the space key until scan is complete. Press OK to try again, or Cancel to return to homepage.");
if (r==true) {
reset();
}
else {
window.location.replace("home.html");
}
}
});
Verify that you are releasing the key during the first slideDown animation. According to your code, once it starts to slide up your active gets set to false and then makes it so the keyup event will not trigger.
Also as a side note I'd recommend using triple = in JavaScript.
Your code seems to work here: http://jsfiddle.net/D52eq/ but note that the confirmation message occurs only if the space bar is released during the .slideDown() phase of the effect - you're setting active = false; before the .slideUp() call.
If you want the confirmation if the space bar is released before completion of the entire animation and process() call then try this:
$(document).one("keydown", function(e) {
if ((e.keyCode == 32) && (!active)) {
active = true;
$(".panel_1").slideDown(5000).slideUp(2000, function() {
process();
active = false;
})
}
});
Note that then you can just chain the .slideDown() and .slideUp(), you don't need to supply a callback function to .slideDown(). Also I've replaced active == false with !active.
Demo: http://jsfiddle.net/D52eq/1/

jQuery: dealing with multiple keypress listeners?

I have a page that needs to do two things at once:
Listen all the time for input from a scanner (which presents as keyboard input), and notice when a string is entered in the right format.
Listen for a user focussing on a particular dropdown, and typing a set of initials - when a set of initials is entered that matches the title attribute of an item in the dropdown, focus on that dropdown.
I can do either of these things separately, but not together. Code:
// Listen for input when userlist is in focus.
$("#userlist").keypress(function (e) {
initials += String.fromCharCode(e.which).toUpperCase();
$(this).find("option").filter(function () {
return $(this).attr("title").toUpperCase().indexOf(initials) === 0;
}).first().attr("selected", true);
// uses timer to check for time between keypresses
return false;
});
// Listen for scanner input all the time.
var input = '',
r1 = /^~{1}$/,
r2 = /^~{1}\d+$/,
r3 = /^~{1}\d+\.$/,
r4 = /^~{1}\d+\.\d+$/,
r5 = /^~{1}\d+\.\d+~{1}$/;
$(window).keypress(function(e) {
// when input matches final regex, do something
}
If I have both, then while the user is focussed on the dropdown, the page does not 'hear' the input from the scanner.
How can I combine the two together to make sure the page reacts to scanner input, even while the user is focussed on the dropdown?
It's because you are overriding the listener on the window object with a listener on the keypress object. I would do something like this:
var input = '',
r1 = /^~{1}$/,
r2 = /^~{1}\d+$/,
r3 = /^~{1}\d+\.$/,
r4 = /^~{1}\d+\.\d+$/,
r5 = /^~{1}\d+\.\d+~{1}$/;
function checkRegex(e) { /* Check */ }
// Listen for input when userlist is in focus.
$("#userlist").keypress(function (e) {
checkRegex(e);
initials += String.fromCharCode(e.which).toUpperCase();
$(this).find("option").filter(function () {
return $(this).attr("title").toUpperCase().indexOf(initials) === 0;
}).first().attr("selected", true);
// uses timer to check for time between keypresses
return false;
});
// Listen for scanner input all the time.
$(window).keypress(function(e) {
checkRegex(e);
}
Wouldn't delegate give you the necessary control? You could then check for the event target and respond accordingly?
ie:
$(window).delegate('keypress', function(e){
if ($(e.target).attr('id') == 'userlist'){
// something
}else{
//something else
}
});
You don't need two handlers. Just have a single handler at the window level and then check which element raised the event:
$(window).keypress(function(e) {
var $target = $(e.target);
if ($target.is("#userlist")) {
initials += String.fromCharCode(e.which).toUpperCase();
$(this).find("option").filter(function () {
return $(this).attr("title").toUpperCase().indexOf(initials) === 0;
}).first().attr("selected", true);
// uses timer to check for time between keypresses
return false;
} else {
// when input matches final regex, do something
}
});
This is probably way more complex than you'd like it to be, but I think it'll fit your purpose.
I tried to make it in the style of a jQuery plugin, and allow you to attach it to any specific object (and customize of it should override bubbling up through the DOM (in the case of your combo box) in addition to allow for windows, etc.
Anyways, try it out and see what you think. I can make modifications if necessary, just need to know what they are.
Working Example: http://www.jsfiddle.net/bradchristie/xSMQd/4/
;(function($){
$.keyListener = function(sel, options){
// avoid scope issues by using base instead of this
var base = this;
// Setup jQuery DOM elements
base.$sel = $(sel);
base.sel = sel;
base.keyPresses = '';
base.validater = null;
// add a reverse reference to the DOM object
base.$sel.data('keyListener', base);
// create an initialization function we can call
base.init = function(){
base.opts = $.extend({}, $.keyListener.defaultOptions, options);
base.$sel.keypress(function(e){
base.keyPresses += String.fromCharCode(e.which);
if (base.validator != null)
clearTimeout(base.validator);
if (base.keyPresses != '')
base.validator = setTimeout(base.validateInput, base.opts.callbackDelay);
if (base.opts.preventDefault)
e.preventDefault();
else if (base.opts.stopPropagation)
e.stopPropagation();
});
};
base.validateInput = function(){
var filter = base.opts.filter;
var reCompare = (typeof(filter)=='object'
? filter.constructor.toString().match(/regexp/i)!==null
: false);
// exception when the input is cleared out
var input = base.sel.constructor.toString().match(/HTMLInputElement|HTMLSelectElement|HTMLTextAreaElement/i);
if (input && (!base.opts.preventDefault && base.$sel.val() == ''))
base.keyPresses = '';
// regular expression match
if (reCompare){
if (base.keyPresses.match(filter))
base.validateSuccess();
else
base.validateFailure();
// traditional string match
}else if (typeof(filter)=='string'){
if (base.keyPresses==filter)
base.validateSuccess();
else
base.validateFailure();
}
// reset string
base.keyPresses = '';
};
base.validateSuccess = function(){
if (typeof(base.opts.success)=='function')
base.opts.success(base.keyPresses);
};
base.validateFailure = function(){
if (typeof(base.opts.failure)=='function')
base.opts.failure(base.keyPresses);
};
// run the initializer
base.init();
};
$.keyListener.defaultOptions = {
// time to wait before triggering callback
// Give it time to accumulate the key presses and send it off
// as a compiled package
callbackDelay: 1000,
// Filter to apply to the input (can be a string match or a regular expression)
filter: /.*/,
// functions to callback when a match has or hasn't been made
success: function(i){},
failure: function(i){},
// would you like this to completely override key input?
preventDefault: false,
// stop it from going up the DOM tree (first object to grab the keypress
// gets it)
stopPropagation: true,
};
$.fn.extend({
keyListener: function(options){
// use return to allow jQuery to chain methods
return this.each(function(){
(new $.keyListener(this, options));
});
}
});
})(jQuery);
$('#listen-scanner,#listen-combo,#listen-text').add(window).keyListener({
filter: /^\d+$/,
success: function(input){
$('#output-scanner').text('Match!: '+input);
},
failure: function(input){
$('#output-scanner').text('No Match: '+input);
},
stopPropagation: true
});
And the HTML I tried it on:
<input type="text" id="listen-scanner" /><span id="output-scanner"></span><br />
<select id="listen-combo">
<option value="AA">Aardvarc</option>
<option value="AB">Abracabra</option>
<option value="AC">Accelerate</option>
<option value="AD">Adult</option>
</select><span id="output-combo"></span>
<textarea id="listen-text"></textarea>

Categories

Resources