如何在Java中模拟按下媒体键? [英] How to emulate pressing media keys in Java?

查看:84
本文介绍了如何在Java中模拟按下媒体键?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

如何模拟Java中的媒体键按下?例如播放/暂停,下一个/上一个,音量控制.

How can I emulate pressing media keys in Java? Such as play/pause, next/previous, volume control.

C#具有VK_MEDIA_PLAY_PAUSEVK_MEDIA_NEXT_TRACK等.

Java具有用于键的类Robot,但是没有媒体键.

Java has class Robot for working with keys, but there are no media keys.

推荐答案

我使用JNI库通过C语言编写的代码来模拟按键操作.我已经创建了一个.dll文件和.java文件,用于点击音量"向下",增大音量",静音",上一曲目",下一曲目"和播放/暂停曲目"媒体键.

I used the JNI Library to simulate the key presses using code written in C. I've created a .dll file and .java file for hitting the "Volume Down", "Volume Up", "Volume Mute", "Previous Track", "Next Track", and "Play/Pause Track" media keys.

这是到完整存储库的链接,但是,我将对此进行解释在下面有更详细的说明.

Here is a link to the full repository, however, I will explain it in more detail below.

MediaKeys.java必须位于名为"commands"的程序包中.

MediaKeys.java must be in a package named "commands" to work.

MediaKeys.dll在编译时必须与"src"文件夹位于同一路径,或与.class文件位于同一路径.

MediaKeys.dll must be in same path as the "src" folder or in the same path as the .class file when compiled.

MediaKeys.java文件包含以下内容:

MediaKeys.java file contains the following:

package commands

public class MediaKeys {

    //loads library from "MediaKeys.dll"
    static {
        System.loadLibrary("MediaKeys");
    }



    public static native void volumeMute();

    public static native void volumeDown();

    public static native void volumeUp();


    public static native void songPrevious();

    public static native void songNext();

    public static native void songPlayPause();



    //test driver
    public static void main(String[] args) {

        //volumeMute();

    }

}

静态块加载.dll文件,然后使用native关键字声明用C编程的功能.

The static block loads the .dll file and then the functions programmed in C are declared using the native keyword.

如果仅需要这些功能,则可以将.dll文件用于Windows.如果您需要.dll的源代码,则它包含在上方的链接中,并且我将在下面更详细地解释它.

If you only need the functions, then you can use the .dll file for Windows. If you require the source code for the .dll it is included in the link above and I will explain it in more detail below.

.dll由两个文件组成,一个是函数源代码的C文件,另一个是头文件. (分别名为MediaKeys.c和MediaKeys.h)

The .dll is made from two files, a C file for the functions' source code and a header file. (Named MediaKeys.c and MediaKeys.h)

MediaKeys.c包含按所需键的代码.为了节省空间,C和头文件的以下代码块仅针对下一曲目",上一曲目"和暂停/播放曲目"功能进行了格式化.

The MediaKeys.c contains the code that presses the desired keys. In order to preserve space, the following code blocks for the C and header files are formatted only for "Next Track", "Previous Track", and "Pause/Play Track" functions.

头文件: MediaKeys.h

The header file: MediaKeys.h

/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class MediaKeys */

#ifndef _Included_MediaKeys
#define _Included_MediaKeys
#ifdef __cplusplus
extern "C" {
#endif
/*
 * Class:     MediaKeys
 * Method:    songPrevious
 * Signature: ()V
 */
JNIEXPORT void JNICALL Java_commands_MediaKeys_songPrevious
  (JNIEnv *, jclass);

/*
 * Class:     MediaKeys
 * Method:    songNext
 * Signature: ()V
 */
JNIEXPORT void JNICALL Java_commands_MediaKeys_songNext
  (JNIEnv *, jclass);

/*
 * Class:     MediaKeys
 * Method:    songPlayPause
 * Signature: ()V
 */
JNIEXPORT void JNICALL Java_commands_MediaKeys_songPlayPause
  (JNIEnv *, jclass);

#ifdef __cplusplus
}
#endif
#endif

头文件包含以下格式的每种方法所需的语句:

The header file contains a statement for each method needed in the following format:

JNIEXPORT void JNICALL Java_{package_name}_{class_name}_{method_name}
  (JNIEnv *, jclass);

然后,C文件必须与头文件相对应. MediaKeys.c

The C file must then correspond to the header file. MediaKeys.c

//standard dependencies for C and the JNI Library
#include <jni.h>
#include <stdio.h>
#include "MediaKeys.h"

//dependencies required to hit the media keys
#define WINVER 0x0500
#include <windows.h>


//hits the previous track key
JNIEXPORT void JNICALL Java_commands_MediaKeys_songPrevious (JNIEnv *env, jobject thisObj) {

    KEYBDINPUT kbi;

    //specific keycode
    kbi.wVk = VK_MEDIA_PREV_TRACK; //this can be changed depending on the key

    kbi.wScan = 0;
    kbi.dwFlags = 0;
    kbi.time = 0;
    kbi.dwExtraInfo = (ULONG_PTR) GetMessageExtraInfo();

    INPUT input;
    input.type = INPUT_KEYBOARD;
    input.ki   = kbi;

    SendInput(1, &input, sizeof(INPUT));

    return;

}


//hits the next track key
JNIEXPORT void JNICALL Java_commands_MediaKeys_songNext (JNIEnv *env, jobject thisObj) {

    KEYBDINPUT kbi;

    //specific keycode
    kbi.wVk = VK_MEDIA_NEXT_TRACK;

    kbi.wScan = 0;
    kbi.dwFlags = 0;
    kbi.time = 0;
    kbi.dwExtraInfo = (ULONG_PTR) GetMessageExtraInfo();

    INPUT input;
    input.type = INPUT_KEYBOARD;
    input.ki   = kbi;

    SendInput(1, &input, sizeof(INPUT));

    return;

}


//hits the play/pause key
JNIEXPORT void JNICALL Java_commands_MediaKeys_songPlayPause (JNIEnv *env, jobject thisObj) {

    KEYBDINPUT kbi;

    //specific keycode
    kbi.wVk = VK_MEDIA_PLAY_PAUSE;

    kbi.wScan = 0;
    kbi.dwFlags = 0;
    kbi.time = 0;
    kbi.dwExtraInfo = (ULONG_PTR) GetMessageExtraInfo();

    INPUT input;
    input.type = INPUT_KEYBOARD;
    input.ki   = kbi;

    SendInput(1, &input, sizeof(INPUT));

    return;

}

C文件为每个标头语句包含一个对应的函数,格式如下:

The C file contains a corresponding function for each header statement following the format below:

JNIEXPORT void JNICALL Java_{package_name}_{class_name}_{method_name} (JNIEnv *env, jobject thisObj) {

    //specific code goes here
    return;

}

并且如代码中所述,您可以通过更改以下内容来更改特定键:kbi.wVk = specific_key_goes_here;.可以在此处找到可用密钥的列表. >.

And as noted in the code, you can change the specific key by changing: kbi.wVk = specific_key_goes_here;. A list of available keys can be found here.

一旦创建了C和头文件,就可以将它们编译为dll文件.为此,我使用Code :: Blocks创建了一个新的动态链接库项目,添加了MediaKeys.c和MediaKeys.h文件,然后单击build.

Once the C and header files are created, they can then be compiled into a dll file. To do this, I used Code::Blocks to create a new Dynamic Link Library project, added the MediaKeys.c and MediaKeys.h files, and clicked build.

由于我的JVM是64位的,而Code :: Blocks默认编译器是32位的,因此我必须

Since my JVM is 64-bit and Code::Blocks default compiler is 32-bit, I had to install a 64-bit compiler into Code::Blocks.

还必须添加指向jni.h库的链接.要在Code :: Blocks中执行此操作,请转到Settings>Compiler>Search Directories并添加目录C:\Program Files\Java\jdk1.8.0_171\includeC:\Program Files\Java\jdk1.8.0_171\include\win32.您很可能必须根据jdk版本更改文件路径.

You also must add links to the jni.h libraries. To do this in Code::Blocks go to Settings>Compiler>Search Directories and add the directories C:\Program Files\Java\jdk1.8.0_171\include and C:\Program Files\Java\jdk1.8.0_171\include\win32. You will most likely have to change the file paths depending on your jdk version.

一旦构建,然后将dll文件复制到Java程序所需的位置.

Once built, then copy the dll file to the required location for the java program.

有关设置Java本机接口的更多信息,我发现

For more information about setting up the Java Native Interface, I found this link exceptionally helpful.

我知道这则帖子有些陈旧,但我认为此信息可能会对其他人有所帮助.

I know this post is a bit old but I figured this information might help others.

这篇关于如何在Java中模拟按下媒体键?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆