1
0
Fork 0
forked from len0rd/rockbox

Rework the simulators button reading to not implement it's own complete driver.

Instead, implement it more as a target driver with button_read_device(), button_init_device() and button_hold(), then use the normal button driver from firmware/drivers/button.c.
Fixes FS#10451 ("backlight off on hold doesn't function properly").

git-svn-id: svn://svn.rockbox.org/rockbox/trunk@22799 a1c6a512-1295-4272-9138-f99709370657
This commit is contained in:
Thomas Martitz 2009-09-23 16:59:56 +00:00
parent fe4526e868
commit ca85c401f5
3 changed files with 96 additions and 208 deletions

View file

@ -33,13 +33,16 @@
#include "serial.h" #include "serial.h"
#include "power.h" #include "power.h"
#include "powermgmt.h" #include "powermgmt.h"
#ifdef SIMULATOR
#include "button-sdl.h"
#else
#include "button-target.h" #include "button-target.h"
#endif
#ifdef HAVE_REMOTE_LCD #ifdef HAVE_REMOTE_LCD
#include "lcd-remote.h" #include "lcd-remote.h"
#endif #endif
#ifndef SIMULATOR
#if 0 #if 0
/* Older than MAX_EVENT_AGE button events are going to be ignored. /* Older than MAX_EVENT_AGE button events are going to be ignored.
* Used to prevent for example volume going up uncontrollable when events * Used to prevent for example volume going up uncontrollable when events
@ -82,9 +85,9 @@ static int button_read(void);
#endif #endif
#ifdef HAVE_TOUCHSCREEN #ifdef HAVE_TOUCHSCREEN
int last_touchscreen_touch; static int last_touchscreen_touch;
#endif #endif
#if defined(HAVE_HEADPHONE_DETECTION) #if defined(HAVE_HEADPHONE_DETECTION) && !defined(SIMULATOR)
static struct timeout hp_detect_timeout; /* Debouncer for headphone plug/unplug */ static struct timeout hp_detect_timeout; /* Debouncer for headphone plug/unplug */
/* This callback can be used for many different functions if needed - /* This callback can be used for many different functions if needed -
just check to which object tmo points */ just check to which object tmo points */
@ -211,8 +214,10 @@ static void button_tick(void)
/* Safety net for players without hardware /* Safety net for players without hardware
poweroff */ poweroff */
#ifndef SIMULATOR
if(repeat_count > POWEROFF_COUNT * 10) if(repeat_count > POWEROFF_COUNT * 10)
power_off(); power_off();
#endif
} }
#endif #endif
} }
@ -376,7 +381,11 @@ long button_get_w_tmo(int ticks)
intptr_t button_get_data(void) intptr_t button_get_data(void)
{ {
#if defined(SIMULATOR)
return button_get_data_sdl();
#else
return button_data; return button_data;
#endif
} }
void button_init(void) void button_init(void)
@ -416,6 +425,7 @@ void button_init(void)
tick_add_task(button_tick); tick_add_task(button_tick);
} }
#ifndef SIMULATOR
#ifdef BUTTON_DRIVER_CLOSE #ifdef BUTTON_DRIVER_CLOSE
void button_close(void) void button_close(void)
{ {
@ -423,7 +433,7 @@ void button_close(void)
} }
#endif /* BUTTON_DRIVER_CLOSE */ #endif /* BUTTON_DRIVER_CLOSE */
#ifdef HAVE_LCD_BITMAP /* only bitmap displays can be flipped */ #ifdef HAVE_LCD_FLIP
/* /*
* helper function to swap LEFT/RIGHT, UP/DOWN (if present), and F1/F3 (Recorder) * helper function to swap LEFT/RIGHT, UP/DOWN (if present), and F1/F3 (Recorder)
*/ */
@ -508,7 +518,7 @@ void button_set_flip(bool flip)
restore_irq(oldlevel); restore_irq(oldlevel);
} }
} }
#endif /* HAVE_LCD_BITMAP */ #endif /* HAVE_LCD_FLIP */
#ifdef HAVE_BACKLIGHT #ifdef HAVE_BACKLIGHT
void set_backlight_filter_keypress(bool value) void set_backlight_filter_keypress(bool value)
@ -523,6 +533,7 @@ void set_remote_backlight_filter_keypress(bool value)
#endif #endif
#endif #endif
#endif /* SIMULATOR */
/* /*
* Get button pressed from hardware * Get button pressed from hardware
*/ */
@ -537,10 +548,11 @@ static int button_read(void)
#endif #endif
int retval; int retval;
#ifdef HAVE_LCD_BITMAP #ifdef HAVE_LCD_FLIP
if (btn && flipped) if (btn && flipped)
btn = button_flip(btn); /* swap upside down */ btn = button_flip(btn); /* swap upside down */
#endif #endif /* HAVE_LCD_FLIP */
#ifdef HAVE_TOUCHSCREEN #ifdef HAVE_TOUCHSCREEN
if (btn & BUTTON_TOUCHSCREEN) if (btn & BUTTON_TOUCHSCREEN)
last_touchscreen_touch = current_tick; last_touchscreen_touch = current_tick;
@ -574,7 +586,6 @@ int touchscreen_last_touch(void)
return last_touchscreen_touch; return last_touchscreen_touch;
} }
#endif #endif
#endif /* SIMULATOR */
#ifdef HAVE_WHEEL_ACCELERATION #ifdef HAVE_WHEEL_ACCELERATION
/* WHEEL_ACCEL_FACTOR = 2^16 / WHEEL_ACCEL_START */ /* WHEEL_ACCEL_FACTOR = 2^16 / WHEEL_ACCEL_START */

View file

@ -0,0 +1,42 @@
/***************************************************************************
* __________ __ ___.
* Open \______ \ ____ ____ | | _\_ |__ _______ ___
* Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
* Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
* Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
* \/ \/ \/ \/ \/
* $Id$
*
* Copyright (C) 2009 by Thomas Martitz
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
* KIND, either express or implied.
*
****************************************************************************/
#ifndef _BUTTON_SDL_H_
#define _BUTTON_SDL_H_
#include <stdbool.h>
#include "config.h"
#include "button-target.h"
#define HAS_BUTTON_HOLD
#undef HAVE_LCD_FLIP
#undef button_init_device
#define button_init_device()
bool button_hold(void);
void button_init_sdl(void);
intptr_t button_get_data_sdl(void);
#undef button_init_device
#define button_init_device() button_init_sdl()
#endif

View file

@ -28,15 +28,13 @@
#include "backlight.h" #include "backlight.h"
#include "misc.h" #include "misc.h"
#include "sim_tasks.h" #include "sim_tasks.h"
#include "button-sdl.h"
#include "debug.h" #include "debug.h"
static intptr_t button_data; /* data value from last message dequeued */
#ifdef HAVE_TOUCHSCREEN #ifdef HAVE_TOUCHSCREEN
#include "touchscreen.h" #include "touchscreen.h"
static int mouse_coords = 0; static int mouse_coords = 0;
static int last_touchscreen_touch = 0xffff;
#endif #endif
/* how long until repeat kicks in */ /* how long until repeat kicks in */
#define REPEAT_START 6 #define REPEAT_START 6
@ -91,23 +89,9 @@ bool remote_button_hold(void) {
} }
#endif #endif
static int lastbtn;
void button_event(int key, bool pressed) void button_event(int key, bool pressed)
{ {
int new_btn = 0; int new_btn = 0;
int diff = 0;
int data = 0;
static int count = 0;
static int repeat_speed = REPEAT_INTERVAL_START;
static int repeat_count = 0;
static bool repeat = false;
static bool post = false;
#ifdef HAVE_BACKLIGHT
static bool skip_release = false;
#ifdef HAVE_REMOTE_LCD
static bool skip_remote_release = false;
#endif
#endif
static bool usb_connected = false; static bool usb_connected = false;
if (usb_connected && key != SDLK_u) if (usb_connected && key != SDLK_u)
return; return;
@ -116,7 +100,6 @@ void button_event(int key, bool pressed)
#ifdef HAVE_TOUCHSCREEN #ifdef HAVE_TOUCHSCREEN
case BUTTON_TOUCHSCREEN: case BUTTON_TOUCHSCREEN:
data = mouse_coords;
switch (touchscreen_get_mode()) switch (touchscreen_get_mode())
{ {
case TOUCHSCREEN_POINT: case TOUCHSCREEN_POINT:
@ -129,7 +112,8 @@ void button_event(int key, bool pressed)
{BUTTON_MIDLEFT, BUTTON_CENTER, BUTTON_MIDRIGHT}, {BUTTON_MIDLEFT, BUTTON_CENTER, BUTTON_MIDRIGHT},
{BUTTON_BOTTOMLEFT, BUTTON_BOTTOMMIDDLE, BUTTON_BOTTOMRIGHT}, {BUTTON_BOTTOMLEFT, BUTTON_BOTTOMMIDDLE, BUTTON_BOTTOMRIGHT},
}; };
int px_x = ((data&0xffff0000)>>16), px_y = ((data&0x0000ffff)); int px_x = ((mouse_coords&0xffff0000)>>16);
int px_y = ((mouse_coords&0x0000ffff));
new_btn = touchscreen_buttons[px_y/(LCD_HEIGHT/3)][px_x/(LCD_WIDTH/3)]; new_btn = touchscreen_buttons[px_y/(LCD_HEIGHT/3)][px_x/(LCD_WIDTH/3)];
break; break;
} }
@ -1223,177 +1207,30 @@ void button_event(int key, bool pressed)
btn |= new_btn; btn |= new_btn;
else else
btn &= ~new_btn; btn &= ~new_btn;
}
/* Lots of stuff copied from real button.c. Not good, I think... */ #ifdef HAVE_BUTTON_DATA
int button_read_device(int* data)
/* Find out if a key has been released */ {
diff = btn ^ lastbtn; (void)data;
if(diff && (btn & diff) == 0)
{
#ifdef HAVE_BACKLIGHT
#ifdef HAVE_REMOTE_LCD
if(diff & BUTTON_REMOTE)
if(!skip_remote_release)
queue_post(&button_queue, BUTTON_REL | diff, data);
else
skip_remote_release = false;
else
#endif
if(!skip_release)
queue_post(&button_queue, BUTTON_REL | diff, data);
else
skip_release = false;
#else #else
queue_post(&button_queue, BUTTON_REL | diff, data); int button_read_device(void)
#endif
}
else
{
if ( btn )
{
/* normal keypress */
if ( btn != lastbtn )
{
post = true;
repeat = false;
repeat_speed = REPEAT_INTERVAL_START;
}
else /* repeat? */
{
if ( repeat )
{
if (!post)
count--;
if (count == 0)
{
post = true;
/* yes we have repeat */
repeat_speed--;
if (repeat_speed < REPEAT_INTERVAL_FINISH)
repeat_speed = REPEAT_INTERVAL_FINISH;
count = repeat_speed;
repeat_count++;
}
}
else
{
if (count++ > REPEAT_START)
{
post = true;
repeat = true;
repeat_count = 0;
/* initial repeat */
count = REPEAT_INTERVAL_START;
}
}
}
if ( post )
{
if(repeat)
{
if (queue_empty(&button_queue))
{
queue_post(&button_queue, BUTTON_REPEAT | btn, data);
#ifdef HAVE_BACKLIGHT
#ifdef HAVE_REMOTE_LCD
if(btn & BUTTON_REMOTE)
{
if(skip_remote_release)
skip_remote_release = false;
}
else
#endif
if(skip_release)
skip_release = false;
#endif
post = false;
}
}
else
{
#ifdef HAVE_BACKLIGHT
#ifdef HAVE_REMOTE_LCD
if (btn & BUTTON_REMOTE) {
if (!remote_filter_first_keypress
|| is_remote_backlight_on(false))
queue_post(&button_queue, btn, data);
else
skip_remote_release = true;
}
else
#endif
if (!filter_first_keypress
|| is_backlight_on(false))
queue_post(&button_queue, btn, data);
else
skip_release = true;
#else /* no backlight, nothing to skip */
queue_post(&button_queue, btn, data);
#endif
post = false;
}
#ifdef HAVE_REMOTE_LCD
if(btn & BUTTON_REMOTE)
remote_backlight_on();
else
#endif
backlight_on();
}
}
else
{
repeat = false;
count = 0;
}
}
lastbtn = btn & ~(BUTTON_REL | BUTTON_REPEAT);
}
/* Again copied from real button.c... */
int button_queue_count( void )
{ {
return queue_count(&button_queue); #endif
} static int hold_button_old = false;
int hold_button = button_hold();
long button_get(bool block) /* light handling */
{ if (hold_button != hold_button_old)
struct queue_event ev; {
hold_button_old = hold_button;
if ( block || !queue_empty(&button_queue) ) { backlight_hold_changed(hold_button);
queue_wait(&button_queue, &ev);
button_data = ev.data;
return ev.id;
} }
if (hold_button)
return BUTTON_NONE; return BUTTON_NONE;
return btn;
} }
long button_get_w_tmo(int ticks)
{
struct queue_event ev;
queue_wait_w_tmo(&button_queue, &ev, ticks);
if (ev.id == SYS_TIMEOUT)
ev.id = BUTTON_NONE;
else
button_data = ev.data;
return ev.id;
}
intptr_t button_get_data(void)
{
#ifdef HAVE_TOUCHSCREEN
return button_data;
#else
/* Needed by the accelerating wheel driver for Sansa e200 */
return 1 << 24;
#endif
}
#ifdef HAVE_TOUCHSCREEN #ifdef HAVE_TOUCHSCREEN
extern bool debug_wps; extern bool debug_wps;
@ -1416,31 +1253,29 @@ void mouse_tick_task(void)
} }
mouse_coords = (x<<16)|y; mouse_coords = (x<<16)|y;
last_touchscreen_touch = current_tick;
button_event(BUTTON_TOUCHSCREEN, true); button_event(BUTTON_TOUCHSCREEN, true);
if (debug_wps) if (debug_wps)
printf("Mouse at: (%d, %d)\n", x, y); printf("Mouse at: (%d, %d)\n", x, y);
} }
} }
int touchscreen_last_touch(void)
{
return last_touchscreen_touch;
}
#endif #endif
void button_init(void)
intptr_t button_get_data_sdl(void)
{
#ifdef HAVE_TOUCHSCREEN
/* pass the mouse coordinates to the button driver */
return mouse_coords;
#else
/* pass scrollwheel acceleration to the button driver */
return 1<<24;
#endif
}
void button_init_sdl(void)
{ {
#ifdef HAVE_TOUCHSCREEN #ifdef HAVE_TOUCHSCREEN
tick_add_task(mouse_tick_task); tick_add_task(mouse_tick_task);
#endif #endif
} }
int button_status(void)
{
return btn;
}
void button_clear_queue(void)
{
queue_clear(&button_queue);
}