2013-02-10 25 views
10

Windows (Vista, 7,…) için basit bir node-webkit uygulaması geliştiriyorum ve özellikle sistem genelinde kısayol tuşlarını bağlamak ve tuş vuruşlarını temel almak için bazı WinAPI işlevlerini, özellikle RegisterHotKey ve SendInput kullanmam gerekiyor. Bu konuda. Düğüm-webkit tarafından sağlanan böyle bir API yok, bu yüzden bu işlevleri çağırmak için node-ffi kullanmayı düşündüm.Node-webkit WinAPI

WinAPI geliştirmesinde yeniyim, bu yüzden bazı MSDN kılavuzlarını okudum, ancak örneklerin çoğunun pencere, ileti döngüsü, ileti işleme yordamı vb. Öyleyse, iyi bir şekilde anlayamadım, ayrı bir pencere oluşturmadan, node-webkit'ten WinAPI'ye doğru şekilde nasıl çağrı yapılır?

Node-ffi tutorial bu durumu kapsamaz, bu yüzden node Windows kitaplığını buldum, ancak Windows uygulamasını düğüm aracılığıyla gerçekleştiriyor gibi görünüyor.

Windows uygulaması oluşturmadan yerel çağrılar gerçekleştirmenin bir yolu var mı? Bunu yapmanın doğru yolu nedir?

+1

Burada gördünüz mü: http://stackoverflow.com/questions/9624536/create-a-node-js-native-extension-on-windows. josh3736'nın cevabı senin için alakalı. – user568109

+1

API'nizi eklemek için node-webkit'i modifiye etmenin yolu daha kolay ve daha iyi. Katkıda bulunursanız, kodunuzu birleştirmeye çalışabilirim. –

cevap

17

Windows'ta kısayol tuşlarını ffi, ref ve ref-struct modüllerini kullanarak yakalayan bir düğüm komut dosyası yazdım. ffi ve ref yerel eklentiler olduklarından, paketlenmiş bir .exe'de çalışmalarına neden olan bazı sorunlar yaşadım. Daha fazla bilgi için, bir süre önce açtığım bu github issue'a bakın.

Neyse, işte kod:

var FFI = require('ffi'), 
    ref = require('ref'), 
    Struct = require('ref-struct'); 

/* First, create the necessary data structures that'll be used 
    by our windows api calls. */ 

var pointStruct = Struct({ 
    'x': 'long', 
    'y': 'long' 
}); 

var msgStruct = Struct({ 
    'hwnd': 'int32', 
    'message': 'int32', 
    'wParam': 'int32', 
    'lParam': 'int32', 
    'time': 'int32', 
    'pt': pointStruct 
}); 

var msgStructPtr = ref.refType(msgStruct); 

/* Second, register the functions we'd like to use by providing 
    their method signatures. */ 

var user32 = new FFI.Library('user32', { 

    'RegisterHotKey': [ 
    'bool', ['int32', 'int', 'int32', 'int32'] 
    ], 

    'GetMessageA': [ 
    'bool', [msgStructPtr, 'int32', 'int32', 'int32'] 
    ] 

    /* You may prefer to use PeekMessageA which has the same 
    signature as GetMessageA, but is non-blocking. I haven't 
    tested it, though. 

}); 

/* Third, register your hotkeys. I wanted to control a media player, 
    so these keys reflect that. */ 

var ALT = 0x0001, 
    CTRL = 0x0002, 
    SHIFT = 0x0004; 

var MEDIA_NEXT = 0xB0, 
    MEDIA_PREV = 0xB1, 
    MEDIA_STOP = 0xB2, 
    MEDIA_PLAY_PAUSE = 0xB3, 
    MEDIA_LAUNCH = 0xB5; 

var PERIOD = 0xBE, 
    COMMA = 0xBC, 
    EQUAL = 0xBB, 
    DIVIDE = 0xBF, 
    SQUOTE = 0xDE, 
    PAGEUP = 0x21, 
    PAGEDOWN = 0x22; 

registrations = []; 
registrations.push(user32.RegisterHotKey(0, 1, 0, MEDIA_NEXT)); 
registrations.push(user32.RegisterHotKey(0, 1, 0, MEDIA_PREV)); 
registrations.push(user32.RegisterHotKey(0, 1, 0, MEDIA_STOP)); 
registrations.push(user32.RegisterHotKey(0, 1, 0, MEDIA_PLAY_PAUSE)); 
registrations.push(user32.RegisterHotKey(0, 1, 0, MEDIA_LAUNCH)); 
registrations.push(user32.RegisterHotKey(0, 1, CTRL, PERIOD)); 
registrations.push(user32.RegisterHotKey(0, 1, CTRL, COMMA)); 
registrations.push(user32.RegisterHotKey(0, 1, CTRL, EQUAL)); 
registrations.push(user32.RegisterHotKey(0, 1, CTRL, DIVIDE)); 
registrations.push(user32.RegisterHotKey(0, 1, CTRL | ALT, PAGEUP)); 
registrations.push(user32.RegisterHotKey(0, 1, CTRL | ALT, PAGEDOWN)); 

// an array of booleans telling us which registrations failed/succeeded 
console.log(registrations); 

/* Fourth, wait for new hotkey events from the message queue. */ 

var myMsg = new msgStruct; 
while (user32.GetMessageA(myMsg.ref(), 0, 0, 0)) { 
    var key = myMsg.lParam >> 16; 
    switch (key) { 
     case MEDIA_NEXT: console.log('media next'); break; 
     case MEDIA_PREV: console.log('media prev'); break; 
     case MEDIA_STOP: console.log('media stop'); break; 
     case MEDIA_PLAY_PAUSE: console.log('media play/pause'); break; 
     case MEDIA_LAUNCH: console.log('media launch'); break; 
     case PERIOD: console.log('next'); break; 
     case COMMA: console.log('previous'); break; 
     case EQUAL: console.log('play/pause'); break; 
     case DIVIDE: console.log('info'); break; 
     case PAGEUP: console.log('volume up'); break; 
     case PAGEDOWN: console.log('volume down'); break; 
     default: console.log('undefined hotkey', key, key.toString(16)); 
    } 
} 

bu, düğüm-webkit çalışmak yapmak istiyorsanız nod sürümü için --target set ile nw-gyp ile tüm yerli eklentileri kurmak emin (benim durumumda 0.5.1) webkit:

# Make sure you run this command in the following directories (where the binding.gyp files are): 
# node_modules/ffi/ 
# node_modules/ffi/node_modules/ref/ 
# node_modules/ref/ 
$ nw-gyp clean configure --target=v0.5.1 build 

İnceleme MSDN dokümanlar kullanılan yöntem imzaları ve yapılar anlamak için. Bu yardımcı olur umarım!

İlgili konular