দ্রষ্টব্য: কীকোড এখন হ্রাস করা হয়েছে।
আপনি ধারণাটি বুঝতে পারলে একাধিক কীস্ট্রোক সনাক্তকরণ সহজ
আমি যেভাবে এটি করি তা হ'ল:
var map = {}; // You could also use an array
onkeydown = onkeyup = function(e){
e = e || event; // to deal with IE
map[e.keyCode] = e.type == 'keydown';
/* insert conditional here */
}
এই কোডটি খুব সহজ: যেহেতু কম্পিউটারগুলি একবারে কেবল একটি কীস্ট্রোক পাস করে, তাই একাধিক কীগুলির ট্র্যাক রাখতে একটি অ্যারে তৈরি করা হয়। অ্যারেটি একবারে এক বা একাধিক কী পরীক্ষা করতে ব্যবহার করা যেতে পারে।
কেবল ব্যাখ্যা করার জন্য, আসুন আপনি চাপুন বলে দিন Aএবং Bপ্রত্যেকটি এমন keydown
ইভেন্টে আগুন map[e.keyCode]
দেয় যা এর মানকে নির্ধারণ করে e.type == keydown
যা সত্য বা মিথ্যাটিকে মূল্যায়ন করে । এখন উভয় map[65]
এবং map[66]
সেট করা হয় true
। যখন আপনি যেতে দিন A
, keyup
ইভেন্টটি জ্বলে ওঠে, একই যুক্তিটির ফলে map[65]
(এ) এর বিপরীত ফলাফল নির্ধারণ করে , যা এখন মিথ্যা , তবে যেহেতু map[66]
(বি) এখনও "ডাউন" (এটি কোনও কীআপ ইভেন্টটি ট্রিগার করে না), এটা সত্য রয়ে গেছে ।
map
অ্যারে, উভয় ঘটনা মাধ্যমে, ভালো দেখায়:
// keydown A
// keydown B
[
65:true,
66:true
]
// keyup A
// keydown B
[
65:false,
66:true
]
আপনি এখন দুটি জিনিস করতে পারেন:
ক) আপনি যখন এক বা একাধিক কী কোডগুলি দ্রুত বের করতে চান তখন একটি কী লগার ( উদাহরণ ) পরে হিসাবে উল্লেখ হিসাবে তৈরি করা যেতে পারে। ধরে নিচ্ছি আপনি একটি এইচটিএমএল উপাদান সংজ্ঞায়িত করেছেন এবং ভেরিয়েবলের সাথে এটি নির্দেশ করেছেন element
।
element.innerHTML = '';
var i, l = map.length;
for(i = 0; i < l; i ++){
if(map[i]){
element.innerHTML += '<hr>' + i;
}
}
দ্রষ্টব্য: আপনি সহজেই তার id
গুণাবলী দ্বারা কোনও উপাদান দখল করতে পারেন ।
<div id="element"></div>
এটি এমন একটি এইচটিএমএল উপাদান তৈরি করে যা জাভাস্ক্রিপ্টের সাথে সহজেই উল্লেখ করা যেতে পারে element
alert(element); // [Object HTMLDivElement]
এমনকি আপনি এটি ব্যবহার document.getElementById()
বা $()
দখল করতে হবে না। তবে সামঞ্জস্যের স্বার্থে, jQuery এর ব্যবহার $()
আরও বেশি প্রস্তাবিত।
স্ক্রিপ্ট ট্যাগটি এইচটিএমএলের মূল অংশের পরে আসবে তা নিশ্চিত করুন । অনুকূলকরণের পরামর্শ : বেশিরভাগ বড়-বড় ওয়েবসাইটগুলি স্ক্রিপ্ট ট্যাগটিকে অপ্টিমাইজেশনের জন্য বডি ট্যাগের পরে রাখে। এর কারণ স্ক্রিপ্ট ট্যাগটি এর স্ক্রিপ্টটি ডাউনলোড শেষ না হওয়া পর্যন্ত লোড করা থেকে আরও উপাদানকে অবরুদ্ধ করে। বিষয়বস্তুর সামনে রেখে কন্টেন্টটি আগেই লোড করার অনুমতি দেয়।
বি (যেখানে আপনার আগ্রহের বিষয়টি এখানে রয়েছে) আপনি যেখানে /*insert conditional here*/
ছিলেন এমন সময়ে এক বা একাধিক কী পরীক্ষা করতে পারেন , এই উদাহরণটি ধরুন:
if(map[17] && map[16] && map[65]){ // CTRL+SHIFT+A
alert('Control Shift A');
}else if(map[17] && map[16] && map[66]){ // CTRL+SHIFT+B
alert('Control Shift B');
}else if(map[17] && map[16] && map[67]){ // CTRL+SHIFT+C
alert('Control Shift C');
}
সম্পাদনা : এটি সর্বাধিক পঠনযোগ্য স্নিপেট নয়। পঠনযোগ্যতা গুরুত্বপূর্ণ, যাতে আপনি এটি চোখের কাছে আরও সহজ করার জন্য এরকম কিছু চেষ্টা করতে পারেন:
function test_key(selkey){
var alias = {
"ctrl": 17,
"shift": 16,
"A": 65,
/* ... */
};
return key[selkey] || key[alias[selkey]];
}
function test_keys(){
var keylist = arguments;
for(var i = 0; i < keylist.length; i++)
if(!test_key(keylist[i]))
return false;
return true;
}
ব্যবহার:
test_keys(13, 16, 65)
test_keys('ctrl', 'shift', 'A')
test_key(65)
test_key('A')
ইহা কি ভাল?
if(test_keys('ctrl', 'shift')){
if(test_key('A')){
alert('Control Shift A');
} else if(test_key('B')){
alert('Control Shift B');
} else if(test_key('C')){
alert('Control Shift C');
}
}
(সম্পাদনার শেষ)
এই উদাহরণটিতে চেক জন্য CtrlShiftA, CtrlShiftBএবংCtrlShiftC
এটি যেমন সহজ :)
মন্তব্য
কীকোডসের ট্র্যাক রাখা
একটি সাধারণ নিয়ম হিসাবে, কোড ডকুমেন্ট করা ভাল অনুশীলন, বিশেষত কী কোডগুলির মতো জিনিস (যেমন // CTRL+ENTER
) যাতে আপনি মনে করতে পারেন যে সেগুলি কী ছিল।
আপনার কী কোডগুলি ডকুমেন্টেশন ( CTRL+ENTER => map[17] && map[13]
, নয় map[13] && map[17]
) হিসাবে একই ক্রমে রাখা উচিত । আপনাকে যখন ফিরে যেতে হবে এবং কোডটি সম্পাদনা করতে হবে তখন আপনি কখনই বিভ্রান্ত হবেন না।
যদি-অন্য শৃঙ্খলাযুক্ত একটি গটচা
যদি বিবিধ পরিমাণের কম্বো (যেমন CtrlShiftAltEnterএবং CtrlEnter) অনুসন্ধান করা হয় তবে বৃহত্তর কম্বোয়ের পরে ছোট কম্বো লাগিয়ে দিন , না হলে ছোট কম্বোগুলি বড় কম্বোগুলিকে যথেষ্ট পরিমাণে মিলিয়ে গেলে ওভাররাইড করবে। উদাহরণ:
// Correct:
if(map[17] && map[16] && map[13]){ // CTRL+SHIFT+ENTER
alert('Whoa, mr. power user');
}else if(map[17] && map[13]){ // CTRL+ENTER
alert('You found me');
}else if(map[13]){ // ENTER
alert('You pressed Enter. You win the prize!')
}
// Incorrect:
if(map[17] && map[13]){ // CTRL+ENTER
alert('You found me');
}else if(map[17] && map[16] && map[13]){ // CTRL+SHIFT+ENTER
alert('Whoa, mr. power user');
}else if(map[13]){ // ENTER
alert('You pressed Enter. You win the prize!');
}
// What will go wrong: When trying to do CTRL+SHIFT+ENTER, it will
// detect CTRL+ENTER first, and override CTRL+SHIFT+ENTER.
// Removing the else's is not a proper solution, either
// as it will cause it to alert BOTH "Mr. Power user" AND "You Found Me"
গোচা: "আমি কীগুলি টিপছি না তবুও এই কী কম্বোটি সক্রিয় রাখে"
সতর্কতা বা মূল উইন্ডো থেকে দৃষ্টি নিবদ্ধ করে এমন কোনও কিছু নিয়ে কাজ করার সময়, map = []
শর্তটি শেষ হওয়ার পরে আপনি অ্যারেটিকে পুনরায় সেট করতে অন্তর্ভুক্ত করতে চাইতে পারেন । এটি কারণ কিছু বিষয় যেমন alert()
মূল উইন্ডো থেকে ফোকাসকে দূরে সরিয়ে দেয় এবং 'কীপ' ইভেন্টটি ট্রিগার না হওয়ার কারণ করে। উদাহরণ স্বরূপ:
if(map[17] && map[13]){ // CTRL+ENTER
alert('Oh noes, a bug!');
}
// When you Press any key after executing this, it will alert again, even though you
// are clearly NOT pressing CTRL+ENTER
// The fix would look like this:
if(map[17] && map[13]){ // CTRL+ENTER
alert('Take that, bug!');
map = {};
}
// The bug no longer happens since the array is cleared
গোচা: ব্রাউজার ডিফল্ট
সমাধানটির অন্তর্ভুক্ত সহ আমি এখানে একটি বিরক্তিকর জিনিস পেয়েছি:
সমস্যা: যেহেতু ব্রাউজারটিতে সাধারণত কী কম্বোজে ডিফল্ট ক্রিয়া থাকে (যেমন CtrlDবুকমার্ক উইন্ডো সক্রিয় করে, বা CtrlShiftCম্যাক্সথনে স্কিনোট সক্রিয় করে) তাই আপনি return false
পরে যুক্ত করতেও চাইবেন map = []
, সুতরাং আপনার সাইটের ব্যবহারকারীরা হতাশ হবেন না যখন "নকল ফাইল" ফাংশন, রাখা হচ্ছে CtrlD, পরিবর্তে পৃষ্ঠা বুকমার্ক।
if(map[17] && map[68]){ // CTRL+D
alert('The bookmark window didn\'t pop up!');
map = {};
return false;
}
ছাড়া return false
, বুকমার্ক উইন্ডোতে হবে পপ আপ, ব্যবহারকারী একটি বড় আতঙ্কের।
ফেরতের বিবৃতি (নতুন)
ঠিক আছে, সুতরাং আপনি সবসময় এই সময়ে ফাংশন থেকে প্রস্থান করতে চান না। কেন এটা event.preventDefault()
ফাংশন আছে। এটি যা করে তা একটি অভ্যন্তরীণ পতাকা সেট করে যা দোভাষীকে ব্রাউজারটিকে তার ডিফল্ট ক্রিয়াকলাপটি চালানোর অনুমতি না দেয়। এর পরে, ফাংশনটির সম্পাদন অব্যাহত থাকে (যেখানে return
তত্ক্ষণাত ফাংশনটি প্রস্থান করা হবে)।
এই পার্থক্য বুঝুন আগে আপনি কিনা তা স্থির ব্যবহার করতে return false
বাe.preventDefault()
event.keyCode
অবচয় করা হয়
ব্যবহারকারী শানভিয়ারা হ'ল মন্তব্যগুলিতে উল্লেখ করেছেন যে অবহেলাevent.keyCode
করা হয়েছে।
আছে: তিনি একটি চমৎকার বিকল্প দিলেন event.key
, যা চাবি একটি স্ট্রিং উপস্থাপনা ফেরৎ টেপা হচ্ছে, মত "a"
জন্য A, অথবা "Shift"
জন্য Shift।
আমি এগিয়ে গিয়ে বললাম স্ট্রিং পরীক্ষা করার জন্য একটি সরঞ্জাম রান্না করেছি ।
element.onevent
বনাম element.addEventListener
যার সাথে নিবন্ধিত হ্যান্ডলারগুলি addEventListener
স্ট্যাক করা যেতে পারে এবং নিবন্ধের ক্রমে ডাকা হয়, .onevent
সরাসরি সেট করা বরং আক্রমণাত্মক এবং আপনার পূর্বে যা কিছু ছিল সেগুলি ওভাররাইড করে।
document.body.onkeydown = function(ev){
// do some stuff
ev.preventDefault(); // cancels default actions
return false; // cancels this function as well as default actions
}
document.body.addEventListener("keydown", function(ev){
// do some stuff
ev.preventDefault() // cancels default actions
return false; // cancels this function only
});
.onevent
সম্পত্তি সবকিছু এবং আচরণকে ওভাররাইড বলে মনে হয় ev.preventDefault()
এবং return false;
বদলে অনিশ্চিত হতে পারে।
উভয় ক্ষেত্রেই, মাধ্যমে নিবন্ধিত হ্যান্ডলারগুলি addEventlistener
লেখার পক্ষে আরও সহজ এবং যুক্তিযুক্ত বলে মনে হয়।
এছাড়াও রয়েছে attachEvent("onevent", callback)
ইন্টারনেট এক্সপ্লোরার এর অ-মানক বাস্তবায়ন থেকে, কিন্তু এই অবচিত পরলোক হল এবং এমনকি জাভাস্ক্রিপ্ট (এটা নামক একটি গূঢ় ভাষা সংক্রান্ত অধিকারে থাকা না JScript )। পলিগ্লট কোড যতটা সম্ভব এড়ানো আপনার পক্ষে ভাল।
একটি সহায়ক শ্রেণি
বিভ্রান্তি / অভিযোগের সমাধানের জন্য, আমি একটি "শ্রেণি" লিখেছি যা এই বিমূর্ততা ( পেস্টবিন লিঙ্ক ) করে:
function Input(el){
var parent = el,
map = {},
intervals = {};
function ev_kdown(ev)
{
map[ev.key] = true;
ev.preventDefault();
return;
}
function ev_kup(ev)
{
map[ev.key] = false;
ev.preventDefault();
return;
}
function key_down(key)
{
return map[key];
}
function keys_down_array(array)
{
for(var i = 0; i < array.length; i++)
if(!key_down(array[i]))
return false;
return true;
}
function keys_down_arguments()
{
return keys_down_array(Array.from(arguments));
}
function clear()
{
map = {};
}
function watch_loop(keylist, callback)
{
return function(){
if(keys_down_array(keylist))
callback();
}
}
function watch(name, callback)
{
var keylist = Array.from(arguments).splice(2);
intervals[name] = setInterval(watch_loop(keylist, callback), 1000/24);
}
function unwatch(name)
{
clearInterval(intervals[name]);
delete intervals[name];
}
function detach()
{
parent.removeEventListener("keydown", ev_kdown);
parent.removeEventListener("keyup", ev_kup);
}
function attach()
{
parent.addEventListener("keydown", ev_kdown);
parent.addEventListener("keyup", ev_kup);
}
function Input()
{
attach();
return {
key_down: key_down,
keys_down: keys_down_arguments,
watch: watch,
unwatch: unwatch,
clear: clear,
detach: detach
};
}
return Input();
}
এই শ্রেণিটি সবকিছু করে না এবং এটি প্রতিটি অনুমেয় ব্যবহারের কেস পরিচালনা করবে না। আমি লাইব্রেরির লোক নই তবে সাধারণ ইন্টারেক্টিভ ব্যবহারের জন্য এটি ঠিক থাকতে হবে।
এই শ্রেণিটি ব্যবহার করার জন্য, একটি উদাহরণ তৈরি করুন এবং কীবোর্ড ইনপুটটির সাথে সংযুক্ত করতে চান এমন উপাদানটিতে এটি নির্দেশ করুন:
var input_txt = Input(document.getElementById("txt"));
input_txt.watch("print_5", function(){
txt.value += "FIVE ";
}, "Control", "5");
এটি যা করবে তা হ'ল উপাদানটির সাথে একটি নতুন ইনপুট শ্রোতা সংযুক্ত করা #txt
(আসুন ধরে নেওয়া যাক এটি একটি টেক্সেরিয়া আছে), এবং কী কম্বোয়ের জন্য একটি ওয়াচপয়েন্ট সেট করুন Ctrl+5
। যখন উভয় Ctrl
এবং 5
নিচে হয়, কলব্যাক ফাংশন আপনি পাস (এই ক্ষেত্রে, একটি ফাংশন যে যোগ করে "FIVE "
পাঠ্য এলাকা পর্যন্ত) বলা হবে। কলব্যাক নামের সাথে জড়িত print_5
, তাই এটি সরাতে আপনি সহজভাবে ব্যবহার করুন:
input_txt.unwatch("print_5");
উপাদান input_txt
থেকে বিচ্ছিন্ন করতে txt
:
input_txt.detach();
এই উপায়ে, আবর্জনা সংগ্রহটি বস্তুটি ( input_txt
) তুলতে পারে, এটি ফেলে দেওয়া উচিত, এবং আপনার কোনও পুরানো জম্বি ইভেন্ট শ্রোতা বাকি থাকবে না।
পুঙ্খানুপুঙ্খতার জন্য, সি / জাভা শৈলীতে উপস্থাপিত শ্রেণীর API এর একটি দ্রুত রেফারেন্স দেওয়া হয়েছে যাতে তারা কীভাবে ফিরে আসে এবং কী যুক্তিগুলি প্রত্যাশা করে তা আপনি জানেন।
Boolean key_down (String key);
নিচে true
থাকলে ফিরে key
আসে, অন্যথায় মিথ্যা।
Boolean keys_down (String key1, String key2, ...);
true
সমস্ত কীগুলি key1 .. keyN
নিচে থাকলে ফিরে আসে, অন্যথায় মিথ্যা।
void watch (String name, Function callback, String key1, String key2, ...);
এমন একটি "ওয়াচপয়েন্ট" তৈরি করে যা সমস্ত কিছু টিপলে কলব্যাকটি keyN
ট্রিগার হয়ে যায়
void unwatch (String name);
এর নাম দিয়ে ওয়াচপয়েন্টটি সরানো হয়েছে
void clear (void);
"কীগুলি নীচে" ক্যাশে মুছুন। map = {}
উপরের সমতুল্য
void detach (void);
Detaches ev_kdown
এবং ev_kup
পিতা বা মাতা উপাদান থেকে শ্রোতারা, এটা সম্ভব উপার্জন নিরাপদে উদাহরণস্বরূপ পরিত্রাণ পেতে
আপডেট 2017-12-02 GitHub এই প্রকাশ করতে একটি অনুরোধ জবাবে, আমি একটি তৈরি করেছেন সারকথা ।
2018-07-21 আপডেট করুন আমি কিছুক্ষণের জন্য ডিক্লেটারিটিভ স্টাইল প্রোগ্রামিং নিয়ে খেলছি, এবং এই উপায়টি এখন আমার ব্যক্তিগত প্রিয়: ফিডল , পেস্টবিন
সাধারণত, আপনি যেসব ক্ষেত্রে বাস্তবসম্মতভাবে চাইবেন (সিটিআরএল, এলইটি, শিফট) এটি কাজ করবে তবে আপনি যদি a+w
একই সাথে আঘাত করতে চান তবে বলুন, একই সাথে এই পদ্ধতির "একত্রিত" করা খুব কঠিন হবে না বহু-কী-অনুসন্ধান।
আমি আশা করি এটির পুরো ব্যাখ্যা করা মিনি ব্লগটি সহায়ক ছিল :)