WebHID API की मदद से वेबसाइटें, सहायक कीबोर्ड और गेमपैड ऐक्सेस कर सकती हैं.
पब्लिश होने की तारीख: 15 सितंबर, 2020
ऐसे कई ह्यूमन इंटरफ़ेस डिवाइस (एचआईडी) हैं जो बहुत नए, बहुत पुराने या बहुत कम इस्तेमाल किए जाते हैं. जैसे, वैकल्पिक कीबोर्ड या खास गेमपैड. इसलिए, सिस्टम के डिवाइस ड्राइवर इन्हें ऐक्सेस नहीं कर पाते. WebHID API इस समस्या को हल करता है. यह JavaScript में डिवाइस के हिसाब से लॉजिक लागू करने का तरीका उपलब्ध कराता है.
इस्तेमाल के सुझाए गए उदाहरण
एचआईडी डिवाइस, लोगों से इनपुट लेता है या उन्हें आउटपुट देता है. डिवाइसों के उदाहरणों में कीबोर्ड, पॉइंटिंग डिवाइस (माउस, टचस्क्रीन वगैरह), और गेमपैड शामिल हैं. एचआईडी प्रोटोकॉल की मदद से, ऑपरेटिंग सिस्टम ड्राइवर का इस्तेमाल करके डेस्कटॉप कंप्यूटर पर इन डिवाइसों को ऐक्सेस किया जा सकता है. वेब प्लैटफ़ॉर्म, इन ड्राइवर पर भरोसा करके एचआईडी डिवाइसों के साथ काम करता है.
एचआईडी डिवाइसों को ऐक्सेस न कर पाने की समस्या तब ज़्यादा होती है, जब बात वैकल्पिक ऑक्सिलरी कीबोर्ड (जैसे, Elgato Stream Deck, Jabra हेडसेट, X-keys) और गेमपैड के लिए खास सपोर्ट की हो. डेस्कटॉप के लिए डिज़ाइन किए गए गेमपैड, अक्सर गेमपैड इनपुट (बटन, जॉयस्टिक, ट्रिगर) और आउटपुट (एलईडी, रंबल) के लिए एचआईडी का इस्तेमाल करते हैं.
माफ़ करें, गेमपैड के इनपुट और आउटपुट को अच्छी तरह से स्टैंडर्ड नहीं किया गया है. साथ ही, वेब ब्राउज़र को अक्सर कुछ डिवाइसों के लिए कस्टम लॉजिक की ज़रूरत होती है. यह तरीका सही नहीं है. इससे पुराने और कम इस्तेमाल किए जाने वाले डिवाइसों के लिए, बेहतर तरीके से सहायता नहीं दी जा सकती. इससे ब्राउज़र को कुछ डिवाइसों के व्यवहार में मौजूद कमियों पर भी निर्भर रहना पड़ता है.
शब्दावली
ह्यूमन इंटरफ़ेस डिवाइस (एचआईडी), लोगों से इनपुट ले सकता है या उन्हें आउटपुट दे सकता है. एचआईडी प्रोटोकॉल, होस्ट और डिवाइस के बीच दोनों तरफ़ से कम्यूनिकेशन करने का एक स्टैंडर्ड है. इसे इंस्टॉल करने की प्रोसेस को आसान बनाने के लिए डिज़ाइन किया गया है.
एचआईडी में दो बुनियादी कॉन्सेप्ट शामिल होते हैं: रिपोर्ट और रिपोर्ट डिस्क्रिप्टर. रिपोर्ट, वह डेटा होता है जो किसी डिवाइस और सॉफ़्टवेयर क्लाइंट के बीच शेयर किया जाता है. रिपोर्ट डिस्क्रिप्टर, डिवाइस के साथ काम करने वाले डेटा के फ़ॉर्मैट और मतलब के बारे में बताता है.
ऐप्लिकेशन और एचआईडी डिवाइस, तीन तरह की रिपोर्ट के ज़रिए बाइनरी डेटा का आदान-प्रदान करते हैं:
| रिपोर्ट का टाइप | ब्यौरा |
|---|---|
| इनपुट रिपोर्ट | वह डेटा जो डिवाइस से ऐप्लिकेशन को भेजा जाता है. उदाहरण के लिए, कोई बटन दबाया गया. |
| आउटपुट रिपोर्ट | ऐसा डेटा जो ऐप्लिकेशन से डिवाइस पर भेजा जाता है. उदाहरण के लिए, कीबोर्ड की बैकलाइट चालू करने का अनुरोध. |
| सुविधा की रिपोर्ट | ऐसा डेटा जिसे दोनों में से किसी भी दिशा में भेजा जा सकता है. यह फ़ॉर्मैट, डिवाइस के हिसाब से तय होता है. |
रिपोर्ट डिस्क्रिप्टर, डिवाइस के साथ काम करने वाली रिपोर्ट के बाइनरी फ़ॉर्मैट के बारे में बताता है. इसका स्ट्रक्चर क्रमबद्ध होता है. इसमें रिपोर्ट को एक साथ ग्रुप किया जा सकता है. साथ ही, टॉप-लेवल के कलेक्शन में अलग-अलग कलेक्शन के तौर पर भी ग्रुप किया जा सकता है. डेस्क्रिप्टर का फ़ॉर्मैट, एचआईडी स्पेसिफ़िकेशन के हिसाब से तय होता है.
एचआईडी यूसेज, एक संख्यात्मक वैल्यू होती है. यह स्टैंडर्ड इनपुट या आउटपुट को दिखाता है. इस्तेमाल की वैल्यू से, डिवाइस को यह बताने में मदद मिलती है कि डिवाइस का इस्तेमाल किस मकसद से किया जाना है. साथ ही, इसकी रिपोर्ट में मौजूद हर फ़ील्ड का मकसद क्या है. उदाहरण के लिए, एक को माउस के बाएं बटन के लिए तय किया जाता है. इस्तेमाल के पेजों में भी इस्तेमाल के डेटा को व्यवस्थित किया जाता है. इससे डिवाइस या रिपोर्ट की कैटगरी के बारे में जानकारी मिलती है.
WebHID API का इस्तेमाल करना
WebHID API काम करता है या नहीं, यह देखने के लिए इस कोड का इस्तेमाल करें:
if ("hid" in navigator) {
// The WebHID API is supported.
}
HID कनेक्शन खोलना
WebHID API को एसिंक्रोनस तरीके से डिज़ाइन किया गया है, ताकि इनपुट का इंतज़ार करते समय वेबसाइट का यूज़र इंटरफ़ेस (यूआई) ब्लॉक न हो. यह ज़रूरी है, क्योंकि एचआईडी डेटा कभी भी मिल सकता है. इसलिए, इसे सुनने का तरीका होना चाहिए.
एचआईडी कनेक्शन खोलने के लिए, सबसे पहले HIDDevice ऑब्जेक्ट को ऐक्सेस करें. इसके लिए, उपयोगकर्ता को navigator.hid.requestDevice() को कॉल करके डिवाइस चुनने के लिए कहा जा सकता है. इसके अलावा, navigator.hid.getDevices() से कोई डिवाइस चुना जा सकता है. इससे उन डिवाइसों की सूची मिलती है जिन्हें वेबसाइट को पहले ऐक्सेस करने की अनुमति दी गई थी.
navigator.hid.requestDevice() फ़ंक्शन, एक ज़रूरी ऑब्जेक्ट लेता है. यह ऑब्जेक्ट, फ़िल्टर तय करता है. इनका इस्तेमाल, यूएसबी वेंडर आइडेंटिफ़ायर (vendorId), यूएसबी प्रॉडक्ट आइडेंटिफ़ायर (productId), इस्तेमाल की जानकारी वाले पेज की वैल्यू (usagePage), और इस्तेमाल की वैल्यू (usage) से कनेक्ट किए गए किसी भी डिवाइस से मिलान करने के लिए किया जाता है. इन्हें यूएसबी आईडी रिपॉज़िटरी और एचआईडी इस्तेमाल की जानकारी वाली टेबल के दस्तावेज़ से पाया जा सकता है.
इस फ़ंक्शन से मिले कई HIDDevice ऑब्जेक्ट, एक ही फ़िज़िकल डिवाइस पर मौजूद कई एचआईडी इंटरफ़ेस को दिखाते हैं.
// Filter on devices with the Nintendo Switch Joy-Con USB Vendor/Product IDs.
const filters = [
{
vendorId: 0x057e, // Nintendo Co., Ltd
productId: 0x2006 // Joy-Con Left
},
{
vendorId: 0x057e, // Nintendo Co., Ltd
productId: 0x2007 // Joy-Con Right
}
];
// Prompt user to select a Joy-Con device.
const [device] = await navigator.hid.requestDevice({ filters });
// Get all devices the user has previously granted the website access to.
const devices = await navigator.hid.getDevices();
इसके अलावा, exclusionFilters की में navigator.hid.requestDevice() का इस्तेमाल करके, ब्राउज़र पिकर से कुछ ऐसे डिवाइसों को हटाया जा सकता है जिनके ठीक से काम न करने की जानकारी है.
// Request access to a device with vendor ID 0xABCD. The device must also have
// a collection with usage page Consumer (0x000C) and usage ID Consumer
// Control (0x0001). The device with product ID 0x1234 is malfunctioning.
const [device] = await navigator.hid.requestDevice({
filters: [{ vendorId: 0xabcd, usagePage: 0x000c, usage: 0x0001 }],
exclusionFilters: [{ vendorId: 0xabcd, productId: 0x1234 }],
});
HIDDevice ऑब्जेक्ट में, डिवाइस की पहचान करने के लिए यूएसबी वेंडर और प्रॉडक्ट आइडेंटिफ़ायर होते हैं. इसके collections एट्रिब्यूट को, डिवाइस के रिपोर्ट फ़ॉर्मैट के क्रमबद्ध ब्यौरे के साथ शुरू किया जाता है.
for (let collection of device.collections) {
// An HID collection includes usage, usage page, reports, and subcollections.
console.log(`Usage: ${collection.usage}`);
console.log(`Usage page: ${collection.usagePage}`);
for (let inputReport of collection.inputReports) {
console.log(`Input report: ${inputReport.reportId}`);
// Loop through inputReport.items
}
for (let outputReport of collection.outputReports) {
console.log(`Output report: ${outputReport.reportId}`);
// Loop through outputReport.items
}
for (let featureReport of collection.featureReports) {
console.log(`Feature report: ${featureReport.reportId}`);
// Loop through featureReport.items
}
// Loop through subcollections with collection.children
}
HIDDevice डिवाइस डिफ़ॉल्ट रूप से "बंद" स्थिति में लौटाए जाते हैं. डेटा भेजने या पाने से पहले, open() को कॉल करके इन्हें चालू करना ज़रूरी है.
// Wait for the HID connection to open before sending/receiving data.
await device.open();
इनपुट रिपोर्ट पाना

एचआईडी कनेक्शन बन जाने के बाद, डिवाइस से मिलने वाली "inputreport" इवेंट को सुनकर, इनपुट रिपोर्ट मैनेज की जा सकती हैं. इन इवेंट में, एचआईडी डेटा को DataView ऑब्जेक्ट (data) के तौर पर शामिल किया जाता है. साथ ही, इसमें एचआईडी डिवाइस (device) और इनपुट रिपोर्ट से जुड़ा 8-बिट रिपोर्ट आईडी (reportId) भी शामिल होता है.
पिछले उदाहरण को जारी रखते हुए, यह कोड आपको यह पता लगाने में मदद करता है कि उपयोगकर्ता ने Joy-Con Right डिवाइस पर कौनसा बटन दबाया है, ताकि आप इसे घर पर आज़मा सकें.
device.addEventListener("inputreport", event => {
const { data, device, reportId } = event;
// Handle only the Joy-Con Right device and a specific report ID.
if (device.productId !== 0x2007 && reportId !== 0x3f) return;
const value = data.getUint8(0);
if (value === 0) return;
const someButtons = { 1: "A", 2: "X", 4: "B", 8: "Y" };
console.log(`User pressed button ${someButtons[value]}.`);
});
CodePen पर डेमो देखें.
आउटपुट रिपोर्ट भेजना
किसी एचआईडी डिवाइस को आउटपुट रिपोर्ट भेजने के लिए, आउटपुट रिपोर्ट (reportId) से जुड़े 8-बिट रिपोर्ट आईडी और बाइट को device.sendReport() में BufferSource (data) के तौर पर पास करें. रिपोर्ट भेजे जाने के बाद, प्रॉमिस रिज़ॉल्व हो जाता है. अगर एचआईडी डिवाइस, रिपोर्ट आईडी का इस्तेमाल नहीं करता है, तो reportId को 0 पर सेट करें.
अगला उदाहरण Joy-Con डिवाइस पर लागू होता है. इसमें बताया गया है कि आउटपुट रिपोर्ट की मदद से, डिवाइस को कैसे वाइब्रेट किया जा सकता है.
// First, send a command to enable vibration.
// Magical bytes come from https://github.com/mzyy94/joycon-toolweb
const enableVibrationData = [1, 0, 1, 64, 64, 0, 1, 64, 64, 0x48, 0x01];
await device.sendReport(0x01, new Uint8Array(enableVibrationData));
// Then, send a command to make the Joy-Con device rumble.
// Actual bytes are available in the sample.
const rumbleData = [ /* ... */ ];
await device.sendReport(0x10, new Uint8Array(rumbleData));
CodePen पर डेमो देखें.
सुविधा की रिपोर्ट भेजना और पाना

सुविधा की रिपोर्ट, एचआईडी डेटा की रिपोर्ट का एक ऐसा टाइप है जो दोनों दिशाओं में काम कर सकता है. इनसे एचआईडी डिवाइसों और ऐप्लिकेशन को, एचआईडी का ऐसा डेटा ट्रांसफ़र करने की अनुमति मिलती है जो स्टैंडर्ड नहीं है. इनपुट और आउटपुट रिपोर्ट के उलट, ऐप्लिकेशन को सुविधा की रिपोर्ट नियमित तौर पर नहीं मिलती हैं और न ही वह इन्हें भेजता है.
किसी एचआईडी डिवाइस को सुविधा की रिपोर्ट भेजने के लिए, सुविधा की रिपोर्ट (reportId) से जुड़े 8-बिट रिपोर्ट आईडी और बाइट को device.sendFeatureReport() को BufferSource (data) के तौर पर पास करें. रिपोर्ट भेजे जाने के बाद, रिस्पॉन्स में मिला प्रॉमिस रिज़ॉल्व हो जाता है. अगर एचआईडी डिवाइस, रिपोर्ट आईडी का इस्तेमाल नहीं करता है, तो reportId को 0 पर सेट करें.
इस उदाहरण में, सुविधा की रिपोर्ट इस्तेमाल करने का तरीका बताया गया है. इसमें आपको यह दिखाया गया है कि Apple कीबोर्ड की बैकलाइट वाले डिवाइस का अनुरोध कैसे करें, उसे कैसे खोलें, और उसे कैसे ब्लिंक करें.
const waitFor = duration => new Promise(r => setTimeout(r, duration));
// Prompt user to select an Apple Keyboard Backlight device.
const [device] = await navigator.hid.requestDevice({
filters: [{ vendorId: 0x05ac, usage: 0x0f, usagePage: 0xff00 }]
});
// Wait for the HID connection to open.
await device.open();
// Blink!
const reportId = 1;
for (let i = 0; i < 10; i++) {
// Turn off
await device.sendFeatureReport(reportId, Uint32Array.from([0, 0]));
await waitFor(100);
// Turn on
await device.sendFeatureReport(reportId, Uint32Array.from([512, 0]));
await waitFor(100);
}
CodePen पर डेमो देखें.
किसी एचआईडी डिवाइस से सुविधा की रिपोर्ट पाने के लिए, सुविधा की रिपोर्ट (reportId) से जुड़ा 8-बिट रिपोर्ट आईडी, device.receiveFeatureReport() को पास करें. यह प्रॉमिस, DataView ऑब्जेक्ट के साथ रिज़ॉल्व होता है. इस ऑब्जेक्ट में, सुविधा की रिपोर्ट का कॉन्टेंट होता है. अगर एचआईडी डिवाइस, रिपोर्ट आईडी का इस्तेमाल नहीं करता है, तो reportId को 0 पर सेट करें.
// Request feature report.
const dataView = await device.receiveFeatureReport(/* reportId= */ 1);
// Read feature report contents with dataView.getInt8(), getUint8(), etc...
कनेक्ट और डिसकनेक्ट करने की सूचना सुनना
जब वेबसाइट को एचआईडी डिवाइस ऐक्सेस करने की अनुमति मिल जाती है, तो वह "connect" और "disconnect" इवेंट को सुनकर, कनेक्शन और डिसकनेक्शन इवेंट को तुरंत पा सकती है.
navigator.hid.addEventListener("connect", event => {
// Automatically open event.device or warn user a device is available.
});
navigator.hid.addEventListener("disconnect", event => {
// Remove |event.device| from the UI.
});
किसी एचआईडी डिवाइस का ऐक्सेस रद्द करना
वेबसाइट, एचआईडी डिवाइस को ऐक्सेस करने की उन अनुमतियों को हटा सकती है जिन्हें वह अब बनाए रखने में दिलचस्पी नहीं रखती. इसके लिए, उसे HIDDevice इंस्टेंस पर forget() को कॉल करना होगा. उदाहरण के लिए, शिक्षा से जुड़ा कोई वेब ऐप्लिकेशन है, जिसे कई डिवाइसों के साथ शेयर किए गए कंप्यूटर पर इस्तेमाल किया जाता है. ऐसे में, उपयोगकर्ता की जनरेट की गई अनुमतियों की ज़्यादा संख्या होने से, उपयोगकर्ता को खराब अनुभव मिलता है.
HIDDevice के किसी एक इंस्टेंस पर forget() को कॉल करने से, एक ही फ़िज़िकल डिवाइस पर मौजूद सभी एचआईडी इंटरफ़ेस का ऐक्सेस रद्द हो जाएगा.
// Voluntarily revoke access to this HID device.
await device.forget();
forget() की सुविधा Chrome 100 या उसके बाद के वर्शन में उपलब्ध है. इसलिए, यह देखें कि यह सुविधा इन पर काम करती है या नहीं:
if ("hid" in navigator && "forget" in HIDDevice.prototype) {
// forget() is supported.
}
डेवलपर के लिए सलाह

इंटरनल पेज about://device-logका इस्तेमाल करके, Chrome में एचआईडी को डीबग करें. इस पेज पर, एचआईडी और यूएसबी डिवाइस से जुड़े सभी इवेंट एक ही जगह पर देखे जा सकते हैं.
एचआईडी डिवाइस की जानकारी को आसानी से पढ़े जा सकने वाले फ़ॉर्मैट में डंप करने के लिए, एचआईडी एक्सप्लोरर देखें. यह हर एचआईडी इस्तेमाल के लिए, इस्तेमाल की वैल्यू को नामों पर मैप करता है.
ज़्यादातर Linux सिस्टम पर, एचआईडी डिवाइसों को डिफ़ॉल्ट रूप से सिर्फ़ पढ़ने की अनुमतियों के साथ मैप किया जाता है. Chrome को एचआईडी डिवाइस खोलने की अनुमति देने के लिए, आपको एक नया udev
rule जोड़ना होगा. /etc/udev/rules.d/50-yourdevicename.rules पर यह कॉन्टेंट डालकर एक फ़ाइल बनाएं:
KERNEL=="hidraw*", ATTRS{idVendor}=="[yourdevicevendor]", MODE="0664", GROUP="plugdev"
इस कोड में, [yourdevicevendor] 057e है. उदाहरण के लिए, अगर आपका डिवाइस Nintendo Switch Joy-Con है. ATTRS{idProduct} को किसी खास नियम के लिए जोड़ा जा सकता है. पक्का करें कि आपका user, plugdev ग्रुप का सदस्य हो. इसके बाद, अपने डिवाइस को फिर से कनेक्ट करें.
डेमो
WebHID के कुछ डेमो, web.dev/hid-examples पर दिए गए हैं.
सुरक्षा और निजता
WebHID API को स्पेसिफ़िकेशन के लेखकों ने डिज़ाइन और लागू किया है. इसके लिए, वेब प्लैटफ़ॉर्म की सुविधाओं के ऐक्सेस को कंट्रोल करना में बताए गए मुख्य सिद्धांतों का इस्तेमाल किया गया है. इनमें उपयोगकर्ता का कंट्रोल, पारदर्शिता, और एर्गोनॉमिक्स शामिल हैं. इस एपीआई का इस्तेमाल करने की सुविधा, मुख्य रूप से अनुमति देने वाले मॉडल पर आधारित होती है. यह मॉडल, एक बार में सिर्फ़ एक एचआईडी डिवाइस को ऐक्सेस करने की अनुमति देता है. उपयोगकर्ता के प्रॉम्प्ट के जवाब में, उसे किसी एचआईडी डिवाइस को चुनने के लिए ज़रूरी कार्रवाई करनी होगी.
सुरक्षा से जुड़े फ़ायदों और नुकसानों के बारे में जानने के लिए, WebHID स्पेसिफ़िकेशन के सुरक्षा और निजता से जुड़ी बातों का ध्यान रखना सेक्शन देखें.
इसके अलावा, Chrome हर टॉप-लेवल कलेक्शन के इस्तेमाल की जांच करता है. अगर किसी टॉप-लेवल कलेक्शन का इस्तेमाल सुरक्षित तरीके से किया जाता है (जैसे कि सामान्य कीबोर्ड, माउस), तो कोई वेबसाइट उस कलेक्शन में तय की गई कोई भी रिपोर्ट न तो भेज पाएगी और न ही पा पाएगी. सुरक्षित इस्तेमाल की पूरी सूची सार्वजनिक तौर पर उपलब्ध है.
ध्यान दें कि सुरक्षा के लिहाज़ से संवेदनशील एचआईडी डिवाइसों (जैसे कि ज़्यादा सुरक्षित तरीके से पुष्टि करने के लिए इस्तेमाल किए जाने वाले FIDO एचआईडी डिवाइस) को भी Chrome में ब्लॉक कर दिया जाता है. यूएसबी ब्लॉकलिस्ट और एचआईडी ब्लॉकलिस्ट फ़ाइलें देखें.
सुझाव/राय दें या शिकायत करें
Chrome टीम, WebHID API के बारे में आपके विचारों और अनुभवों के बारे में जानना चाहती है.
हमें एपीआई डिज़ाइन के बारे में बताएं
क्या एपीआई के बारे में कुछ ऐसा है जो आपकी उम्मीद के मुताबिक काम नहीं करता? या क्या कोई ऐसा तरीका या प्रॉपर्टी है जो मौजूद नहीं है और आपको अपने आइडिया को लागू करने के लिए उसकी ज़रूरत है?
WebHID API के GitHub डेटा स्टोर पर, खास जानकारी से जुड़ी समस्या की शिकायत करें या किसी मौजूदा समस्या के बारे में अपने विचार जोड़ें.
लागू करने से जुड़ी समस्या की शिकायत करना
क्या आपको Chrome के साथ काम करने में कोई गड़बड़ी मिली? या क्या स्पेसिफ़िकेशन से अलग तरीके से लागू किया गया है?
WebHID से जुड़ी गड़बड़ियों की शिकायत करने का तरीका जानें. ज़्यादा से ज़्यादा जानकारी शामिल करें. साथ ही, गड़बड़ी को दोबारा बनाने के लिए निर्देश दें और कॉम्पोनेंट को Blink>HID पर सेट करें.
काम के लिंक
- खास जानकारी
- ट्रैकिंग बग
- ChromeStatus.com एंट्री
- Blink कॉम्पोनेंट:
Blink>HID
Acknowledgements
समीक्षा करने के लिए मैट रेनॉल्ड्स और जो मेडली का धन्यवाद.