예제 #1
0
파일: qemulator.c 프로젝트: pras710/qemu
static void
qemulator_setup( QEmulator*  emulator )
{
    AndroidOptions*  opts = emulator->opts;

    if ( !emulator->window && !opts->no_window ) {
        SkinLayout*  layout = emulator->layout;
        double       scale  = get_default_scale(emulator->opts);

        static const SkinWindowFuncs skin_window_funcs = {
            .key_event = &qemulator_window_key_event,
            .mouse_event = &qemulator_window_mouse_event,
            .generic_event = &qemulator_window_generic_event,
            .opengles_show = &android_showOpenglesWindow,
            .opengles_hide = &android_hideOpenglesWindow,
            .opengles_redraw = &android_redrawOpenglesWindow,
        };

        emulator->window = skin_window_create(layout,
                                              emulator->win_x,
                                              emulator->win_y,
                                              scale,
                                              0,
                                              &skin_window_funcs);
        if (emulator->window == NULL)
            return;

        {
            SkinTrackBall*           ball;
            SkinTrackBallParameters  params;

            params.diameter   = 30;
            params.ring       = 2;
            params.ball_color = 0xffe0e0e0;
            params.dot_color  = 0xff202020;
            params.ring_color = 0xff000000;
            params.event_func = &qemulator_trackball_event;

            ball = skin_trackball_create( &params );
            emulator->trackball = ball;
            skin_window_set_trackball( emulator->window, ball );

            emulator->lcd_brightness = 128;  /* 50% */
            skin_window_set_lcd_brightness( emulator->window, emulator->lcd_brightness );
        }

        if ( emulator->onion != NULL )
            skin_window_set_onion( emulator->window,
                                   emulator->onion,
                                   emulator->onion_rotation,
                                   emulator->onion_alpha );

        qemulator_set_title(emulator);

        skin_window_enable_touch ( emulator->window,
                                   !androidHwConfig_isScreenNoTouch(android_hw));
        skin_window_enable_dpad  ( emulator->window, android_hw->hw_dPad != 0 );
        skin_window_enable_qwerty( emulator->window, android_hw->hw_keyboard != 0 );
        skin_window_enable_trackball( emulator->window, android_hw->hw_trackBall != 0 );
    }
예제 #2
0
static void
qemulator_setup( QEmulator*  emulator )
{
    AndroidOptions*  opts = emulator->opts;

    if ( !emulator->window && !opts->no_window ) {
        SkinLayout*  layout = emulator->layout;
        double       scale  = get_default_scale(emulator->opts);

        emulator->window = skin_window_create( layout, emulator->win_x, emulator->win_y, scale, 0);
        if (emulator->window == NULL)
            return;

        {
            SkinTrackBall*           ball;
            SkinTrackBallParameters  params;

            params.diameter   = 30;
            params.ring       = 2;
            params.ball_color = 0xffe0e0e0;
            params.dot_color  = 0xff202020;
            params.ring_color = 0xff000000;

            ball = skin_trackball_create( &params );
            emulator->trackball = ball;
            skin_window_set_trackball( emulator->window, ball );

            emulator->lcd_brightness = 128;  
            skin_window_set_lcd_brightness( emulator->window, emulator->lcd_brightness );
        }

        if ( emulator->onion != NULL )
            skin_window_set_onion( emulator->window,
                                   emulator->onion,
                                   emulator->onion_rotation,
                                   emulator->onion_alpha );

        qemulator_set_title(emulator);

        skin_window_enable_touch ( emulator->window,
                                   !androidHwConfig_isScreenNoTouch(android_hw));
        skin_window_enable_dpad  ( emulator->window, android_hw->hw_dPad != 0 );
        skin_window_enable_qwerty( emulator->window, android_hw->hw_keyboard != 0 );
        skin_window_enable_trackball( emulator->window, android_hw->hw_trackBall != 0 );
    }

    
    uicmd_set_brightness_change_callback(qemulator_light_brightness,
                                         emulator);
}
static void
emulator_window_setup( EmulatorWindow*  emulator )
{
    static const SkinWindowFuncs my_window_funcs = {
        .key_event = &emulator_window_window_key_event,
        .mouse_event = &emulator_window_window_mouse_event,
        .generic_event = &emulator_window_window_generic_event,
        .opengles_show = &emulator_window_opengles_show_window,
        .opengles_hide = &emulator_window_opengles_hide_window,
        .opengles_redraw = &emulator_window_opengles_redraw_window,
        .opengles_free = &android_stopOpenglesRenderer,
    };

    static const SkinTrackBallParameters my_trackball_params = {
        .diameter = 30,
        .ring = 2,
        .ball_color = 0xffe0e0e0,
        .dot_color = 0xff202020,
        .ring_color = 0xff000000,
        .event_func = &emulator_window_trackball_event,
    };

    if (emulator->opts->no_window || emulator->ui) {
        return;
    }

    SkinUIParams my_ui_params = {
        .enable_touch = !androidHwConfig_isScreenNoTouch(android_hw),
        .enable_dpad = android_hw->hw_dPad != 0,
        .enable_keyboard = android_hw->hw_keyboard != 0,
        .enable_trackball = android_hw->hw_trackBall != 0,

        .window_x = emulator->win_x,
        .window_y = emulator->win_y,
        .window_scale = get_default_scale(emulator->opts),

        .keyboard_charmap = emulator->opts->charmap,
        .keyboard_raw_keys = emulator->opts->raw_keys != 0,
#if CONFIG_QT
        .win32_ignore_events = true,
#else
        .win32_ignore_events = false,
#endif
    };

    write_window_name(my_ui_params.window_name,
                      sizeof(my_ui_params.window_name),
                      android_base_port,
                      avdInfo_getName(android_avdInfo));

    static const SkinUIFuncs my_ui_funcs = {
        .window_funcs = &my_window_funcs,
        .trackball_params = &my_trackball_params,
        .keyboard_event = &emulator_window_keyboard_event, //user_event_key,
        .keyboard_flush = &user_event_keycodes,
        .network_toggle = &emulator_window_network_toggle,
        .framebuffer_invalidate = &emulator_window_framebuffer_invalidate,
    };

    // Determine whether to use an EmuGL sub-window or not.
    const char* env = getenv("ANDROID_GL_SOFTWARE_RENDERER");
    s_use_emugl_subwindow = !env || !env[0] || env[0] == '0';

    if (s_use_emugl_subwindow) {
        VERBOSE_PRINT(gles, "Using EmuGL sub-window for GPU display");
    } else {
        VERBOSE_PRINT(gles, "Using glReadPixels() for GPU display");
    }

    emulator->ui = skin_ui_create(emulator->layout_file,
                                  android_hw->hw_initialOrientation,
                                  &my_ui_funcs,
                                  &my_ui_params);
    if (!emulator->ui) {
        return;
    }

    if (emulator->onion) {
        skin_ui_set_onion(emulator->ui,
                          emulator->onion,
                          emulator->onion_rotation,
                          emulator->onion_alpha);
    }

    // Determine whether to use an EmuGL sub-window or not.
    if (!s_use_emugl_subwindow) {
        gpu_frame_set_post_callback(looper_newCore(),
                                    emulator,
                                    _emulator_window_on_gpu_frame);
    }

    skin_ui_reset_title(emulator->ui);
}

static void
emulator_window_fb_update( void*   _emulator, int  x, int  y, int  w, int  h )
{
    EmulatorWindow*  emulator = _emulator;

    if (emulator->opts->no_window) {
        return;
    }

    if (!emulator->ui) {
        emulator_window_setup(emulator);
    }
    skin_ui_update_display(emulator->ui, x, y, w, h);
}

static void
emulator_window_fb_rotate( void*  _emulator, int  rotation )
{
    EmulatorWindow*  emulator = _emulator;

    emulator_window_setup( emulator );
}
예제 #4
0
void events_dev_init(uint32_t base, qemu_irq irq)
{
    events_state *s;
    int iomemtype;
    AndroidHwConfig*  config = android_hw;

    s = (events_state *) qemu_mallocz(sizeof(events_state));

    /* now set the events capability bits depending on hardware configuration */
    /* apparently, the EV_SYN array is used to indicate which other
     * event classes to consider.
     */

    /* configure EV_KEY array
     *
     * All Android devices must have the following keys:
     *   KEY_HOME, KEY_BACK, KEY_SEND (Call), KEY_END (EndCall),
     *   KEY_SOFT1 (Menu), VOLUME_UP, VOLUME_DOWN
     *
     *   Note that previous models also had a KEY_SOFT2,
     *   and a KEY_POWER  which we still support here.
     *
     *   Newer models have a KEY_SEARCH key, which we always
     *   enable here.
     *
     * A Dpad will send: KEY_DOWN / UP / LEFT / RIGHT / CENTER
     *
     * The KEY_CAMERA button isn't very useful if there is no camera.
     *
     * BTN_MOUSE is sent when the trackball is pressed
     * BTN_TOUCH is sent when the touchscreen is pressed
     */
    events_set_bit (s, EV_SYN, EV_KEY );

    events_set_bit(s, EV_KEY, KEY_HOME);
    events_set_bit(s, EV_KEY, KEY_BACK);
    events_set_bit(s, EV_KEY, KEY_SEND);
    events_set_bit(s, EV_KEY, KEY_END);
    events_set_bit(s, EV_KEY, KEY_SOFT1);
    events_set_bit(s, EV_KEY, KEY_VOLUMEUP);
    events_set_bit(s, EV_KEY, KEY_VOLUMEDOWN);
    events_set_bit(s, EV_KEY, KEY_SOFT2);
    events_set_bit(s, EV_KEY, KEY_POWER);
    events_set_bit(s, EV_KEY, KEY_SEARCH);

    if (config->hw_dPad) {
        events_set_bit(s, EV_KEY, KEY_DOWN);
        events_set_bit(s, EV_KEY, KEY_UP);
        events_set_bit(s, EV_KEY, KEY_LEFT);
        events_set_bit(s, EV_KEY, KEY_RIGHT);
        events_set_bit(s, EV_KEY, KEY_CENTER);
    }

    if (config->hw_trackBall) {
        events_set_bit(s, EV_KEY, BTN_MOUSE);
    }
    if (androidHwConfig_isScreenTouch(config)) {
        events_set_bit(s, EV_KEY, BTN_TOUCH);
    }

    if (strcmp(config->hw_camera_back, "none") ||
        strcmp(config->hw_camera_front, "none")) {
        /* Camera emulation is enabled. */
        events_set_bit(s, EV_KEY, KEY_CAMERA);
    }

    if (config->hw_keyboard) {
        /* since we want to implement Unicode reverse-mapping
         * allow any kind of key, even those not available on
         * the skin.
         *
         * the previous code did set the [1..0x1ff] range, but
         * we don't want to enable certain bits in the middle
         * of the range that are registered for mouse/trackball/joystick
         * events.
         *
         * see "linux_keycodes.h" for the list of events codes.
         */
        events_set_bits(s, EV_KEY, 1, 0xff);
        events_set_bits(s, EV_KEY, 0x160, 0x1ff);

        /* If there is a keyboard, but no DPad, we need to clear the
         * corresponding bits. Doing this is simpler than trying to exclude
         * the DPad values from the ranges above.
         */
        if (!config->hw_dPad) {
            events_clr_bit(s, EV_KEY, KEY_DOWN);
            events_clr_bit(s, EV_KEY, KEY_UP);
            events_clr_bit(s, EV_KEY, KEY_LEFT);
            events_clr_bit(s, EV_KEY, KEY_RIGHT);
            events_clr_bit(s, EV_KEY, KEY_CENTER);
        }
    }

    /* configure EV_REL array
     *
     * EV_REL events are sent when the trackball is moved
     */
    if (config->hw_trackBall) {
        events_set_bit (s, EV_SYN, EV_REL );
        events_set_bits(s, EV_REL, REL_X, REL_Y);
    }

    /* configure EV_ABS array.
     *
     * EV_ABS events are sent when the touchscreen is pressed
     */
    if (!androidHwConfig_isScreenNoTouch(config)) {
        ABSEntry* abs_values;

        events_set_bit (s, EV_SYN, EV_ABS );
        events_set_bits(s, EV_ABS, ABS_X, ABS_Z);
        /* Allocate the absinfo to report the min/max bounds for each
         * absolute dimension. The array must contain 3, or ABS_MAX tuples
         * of (min,max,fuzz,flat) 32-bit values.
         *
         * min and max are the bounds
         * fuzz corresponds to the device's fuziness, we set it to 0
         * flat corresponds to the flat position for JOEYDEV devices,
         * we also set it to 0.
         *
         * There is no need to save/restore this array in a snapshot
         * since the values only depend on the hardware configuration.
         */
        s->abs_info_count = androidHwConfig_isScreenMultiTouch(config) ? ABS_MAX * 4 : 3 * 4;
        const int abs_size = sizeof(uint32_t) * s->abs_info_count;
        s->abs_info = malloc(abs_size);
        memset(s->abs_info, 0, abs_size);
        abs_values = (ABSEntry*)s->abs_info;

        abs_values[ABS_X].max = config->hw_lcd_width-1;
        abs_values[ABS_Y].max = config->hw_lcd_height-1;
        abs_values[ABS_Z].max = 1;

        if (androidHwConfig_isScreenMultiTouch(config)) {
            /*
             * Setup multitouch.
             */
            events_set_bit(s, EV_ABS, ABS_MT_SLOT);
            events_set_bit(s, EV_ABS, ABS_MT_POSITION_X);
            events_set_bit(s, EV_ABS, ABS_MT_POSITION_Y);
            events_set_bit(s, EV_ABS, ABS_MT_TRACKING_ID);
            events_set_bit(s, EV_ABS, ABS_MT_TOUCH_MAJOR);
            events_set_bit(s, EV_ABS, ABS_MT_PRESSURE);

            abs_values[ABS_MT_SLOT].max = multitouch_get_max_slot();
            abs_values[ABS_MT_TRACKING_ID].max = abs_values[ABS_MT_SLOT].max + 1;
            abs_values[ABS_MT_POSITION_X].max = abs_values[ABS_X].max;
            abs_values[ABS_MT_POSITION_Y].max = abs_values[ABS_Y].max;
            abs_values[ABS_MT_TOUCH_MAJOR].max = 0x7fffffff; // TODO: Make it less random
            abs_values[ABS_MT_PRESSURE].max = 0x100; // TODO: Make it less random
        }
    }

    /* configure EV_SW array
     *
     * EV_SW events are sent to indicate that the keyboard lid
     * was closed or opened (done when we switch layouts through
     * KP-7 or KP-9).
     *
     * We only support this when hw.keyboard.lid is true.
     */
    if (config->hw_keyboard && config->hw_keyboard_lid) {
        events_set_bit(s, EV_SYN, EV_SW);
        events_set_bit(s, EV_SW, 0);
    }

    iomemtype = cpu_register_io_memory(events_readfn, events_writefn, s);

    cpu_register_physical_memory(base, 0xfff, iomemtype);

    qemu_add_kbd_event_handler(events_put_keycode, s);
    qemu_add_mouse_event_handler(events_put_mouse, s, 1, "goldfish-events");

    s->base = base;
    s->irq = irq;

    s->first = 0;
    s->last = 0;
    s->state = STATE_INIT;
    s->name = qemu_strdup(config->hw_keyboard_charmap);

    /* This function migh fire buffered events to the device, so
     * ensure that it is called after initialization is complete
     */
    user_event_register_generic(s, events_put_generic);

    register_savevm( "events_state", 0, EVENTS_STATE_SAVE_VERSION,
                      events_state_save, events_state_load, s );
}