summaryrefslogtreecommitdiffstats
path: root/firmware
diff options
context:
space:
mode:
authorDominik Wenger <domonoky@googlemail.com>2009-10-27 20:25:40 +0000
committerDominik Wenger <domonoky@googlemail.com>2009-10-27 20:25:40 +0000
commit04ebf48fe4cb7bdd4d125e9e5f2507d03ede6a5b (patch)
tree0b3b501a59d9a774019d277b0947ee4194de0af4 /firmware
parent6f9724706f4df78a91f3bf9a10b50be109aac996 (diff)
downloadrockbox-04ebf48fe4cb7bdd4d125e9e5f2507d03ede6a5b.tar.gz
rockbox-04ebf48fe4cb7bdd4d125e9e5f2507d03ede6a5b.zip
Initial touchscreen support for mini2440. Based on D2 touchscreen driver
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@23370 a1c6a512-1295-4272-9138-f99709370657
Diffstat (limited to 'firmware')
-rw-r--r--firmware/SOURCES1
-rw-r--r--firmware/export/config-cowond2.h2
-rw-r--r--firmware/export/config-mini2440.h5
-rw-r--r--firmware/target/arm/s3c2440/adc-s3c2440.c11
-rw-r--r--firmware/target/arm/s3c2440/mini2440/adc-target.h6
-rw-r--r--firmware/target/arm/s3c2440/mini2440/button-mini2440.c11
-rw-r--r--firmware/target/arm/s3c2440/mini2440/button-target.h16
-rw-r--r--firmware/target/arm/s3c2440/mini2440/touchscreen-mini2440.c190
-rw-r--r--firmware/target/arm/s3c2440/mini2440/touchscreen-target.h33
9 files changed, 265 insertions, 10 deletions
diff --git a/firmware/SOURCES b/firmware/SOURCES
index 2c666cb27c..adb54c7a35 100644
--- a/firmware/SOURCES
+++ b/firmware/SOURCES
@@ -1411,6 +1411,7 @@ target/arm/s3c2440/mini2440/backlight-mini2440.c
target/arm/s3c2440/mini2440/button-mini2440.c
target/arm/s3c2440/mini2440/led-mini2440.c
target/arm/s3c2440/mini2440/power-mini2440.c
+target/arm/s3c2440/mini2440/touchscreen-mini2440.c
#ifndef BOOTLOADER
target/arm/s3c2440/mini2440/powermgmt-mini2440.c
target/arm/s3c2440/mini2440/pcm-mini2440.c
diff --git a/firmware/export/config-cowond2.h b/firmware/export/config-cowond2.h
index 45bf90bbd0..f31c0a81c3 100644
--- a/firmware/export/config-cowond2.h
+++ b/firmware/export/config-cowond2.h
@@ -89,7 +89,7 @@
#define CONFIG_KEYPAD COWOND2_PAD
#define HAVE_TOUCHSCREEN
#define HAVE_BUTTON_DATA
-
+
/* The D2 has either a PCF50606 or PCF50635, RTC_D2 handles both */
#define CONFIG_RTC RTC_D2
diff --git a/firmware/export/config-mini2440.h b/firmware/export/config-mini2440.h
index b9d5dadf9c..83505d8994 100644
--- a/firmware/export/config-mini2440.h
+++ b/firmware/export/config-mini2440.h
@@ -71,6 +71,8 @@
/* Keypad */
#define CONFIG_KEYPAD MINI2440_PAD
+#define HAVE_TOUCHSCREEN
+#define HAVE_BUTTON_DATA
/* I2C */
/* We do not use currently use hardware I2C, but does not build without */
@@ -108,6 +110,9 @@
/* RMC TODO: what is this for?? */
/* define this if you have access to the pitchscreen */
#define HAVE_PITCHSCREEN
+#define HAVE_QUICKSCREEN
+
+
/* Define this if you do software codec */
#define CONFIG_CODEC SWCODEC
diff --git a/firmware/target/arm/s3c2440/adc-s3c2440.c b/firmware/target/arm/s3c2440/adc-s3c2440.c
index fd5151a3bf..f42a3d2b6a 100644
--- a/firmware/target/arm/s3c2440/adc-s3c2440.c
+++ b/firmware/target/arm/s3c2440/adc-s3c2440.c
@@ -24,6 +24,10 @@
#include "adc-target.h"
#include "kernel.h"
+#ifdef MINI2440
+#include "touchscreen-target.h"
+#endif
+
static unsigned short adc_readings[NUM_ADC_CHANNELS];
/* prototypes */
@@ -122,7 +126,7 @@ static unsigned short __adc_read(int channel)
/* add this to the tick so that the ADC converts are done in the background */
static void adc_tick(void)
{
- static unsigned channel;
+ static unsigned channel=0;
/* Check if the End Of Conversion is set */
if (ADCCON & (1<<15))
@@ -132,7 +136,10 @@ static void adc_tick(void)
{
channel = 0;
}
-
+#ifdef MINI2440
+ /* interleave a touchscreen read if neccessary */
+ touchscreen_scan_device();
+#endif
/* setup the next conversion and start it*/
ADCCON = (ADCCON & ~(0x7<<3)) | (channel<<3) | 0x01;
}
diff --git a/firmware/target/arm/s3c2440/mini2440/adc-target.h b/firmware/target/arm/s3c2440/mini2440/adc-target.h
index 24e878e735..5abf0d06c5 100644
--- a/firmware/target/arm/s3c2440/mini2440/adc-target.h
+++ b/firmware/target/arm/s3c2440/mini2440/adc-target.h
@@ -26,16 +26,12 @@
Channels 4-7 are routed to LCD connector for touchscreen operation if
supported by display panel.
*/
-#define NUM_ADC_CHANNELS 8
+#define NUM_ADC_CHANNELS 4
#define ADC_ONBOARD 0
#define ADC_SPARE_1 1
#define ADC_SPARE_2 2
#define ADC_SPARE_3 3
-#define ADC_TSYM 4
-#define ADC_TSYP 5
-#define ADC_TSXM 6
-#define ADC_TSXP 7
#define ADC_READ_ERROR 0xFFFF
diff --git a/firmware/target/arm/s3c2440/mini2440/button-mini2440.c b/firmware/target/arm/s3c2440/mini2440/button-mini2440.c
index 787c04d1ef..0435f47559 100644
--- a/firmware/target/arm/s3c2440/mini2440/button-mini2440.c
+++ b/firmware/target/arm/s3c2440/mini2440/button-mini2440.c
@@ -24,6 +24,7 @@
#include "system.h"
#include "button.h"
#include "kernel.h"
+#include "touchscreen-target.h"
void button_init_device(void)
{
@@ -50,6 +51,8 @@ void button_init_device(void)
S3C2440_GPIO_PULLUP (GPGUP, 9, GPIO_PULLUP_ENABLE);
S3C2440_GPIO_PULLUP (GPGUP, 10, GPIO_PULLUP_ENABLE);
+ /* init touchscreen */
+ touchscreen_init_device();
}
inline bool button_hold(void)
@@ -57,12 +60,18 @@ inline bool button_hold(void)
return 0;
}
-int button_read_device(void)
+int button_read_device(int* data)
{
int btn = BUTTON_NONE;
+ static int old_data = 0;
+
+ *data = old_data;
/* Read the buttons - active low */
btn = (GPGDAT & BUTTON_MAIN) ^ BUTTON_MAIN;
+
+ /* read touchscreen */
+ btn |= touchscreen_read_device(data, &old_data);
return btn;
}
diff --git a/firmware/target/arm/s3c2440/mini2440/button-target.h b/firmware/target/arm/s3c2440/mini2440/button-target.h
index 4a84014462..66419b464a 100644
--- a/firmware/target/arm/s3c2440/mini2440/button-target.h
+++ b/firmware/target/arm/s3c2440/mini2440/button-target.h
@@ -27,7 +27,7 @@
bool button_hold(void);
void button_init_device(void);
-int button_read_device(void);
+int button_read_device(int*);
void touchpad_set_sensitivity(int level);
/* Mini2440 specific button codes */
@@ -43,6 +43,20 @@ void touchpad_set_sensitivity(int level);
#define BUTTON_SEVEN 0x0200
#define BUTTON_EIGHT 0x0400
+/* Touch Screen Area Buttons */
+#define BUTTON_TOPLEFT 0x010000
+#define BUTTON_TOPMIDDLE 0x020000
+#define BUTTON_TOPRIGHT 0x040000
+#define BUTTON_MIDLEFT 0x080000
+#define BUTTON_CENTER 0x100000
+#define BUTTON_MIDRIGHT 0x200000
+#define BUTTON_BOTTOMLEFT 0x400000
+#define BUTTON_BOTTOMMIDDLE 0x800000
+#define BUTTON_BOTTOMRIGHT 0x100000
+
+#define BUTTON_TOUCH 0x200000
+
+
#define BUTTON_MENU BUTTON_ONE
#define BUTTON_UP BUTTON_TWO
#define BUTTON_SELECT BUTTON_THREE
diff --git a/firmware/target/arm/s3c2440/mini2440/touchscreen-mini2440.c b/firmware/target/arm/s3c2440/mini2440/touchscreen-mini2440.c
new file mode 100644
index 0000000000..ce7c8d5dd7
--- /dev/null
+++ b/firmware/target/arm/s3c2440/mini2440/touchscreen-mini2440.c
@@ -0,0 +1,190 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___void
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Copyright (C) 2008 by Rob Purchase
+ *
+ * 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.
+ *
+ ****************************************************************************/
+
+#include "config.h"
+#include "touchscreen-target.h"
+#include "adc-target.h"
+#include "system.h"
+#include "stdlib.h"
+#include "button.h"
+#include "touchscreen.h"
+
+#define NO_OF_TOUCH_DATA 5
+
+struct touch_calibration_point {
+ short px_x; /* known pixel value */
+ short px_y;
+ short val_x; /* touchscreen value at the known pixel */
+ short val_y;
+};
+
+static struct touch_calibration_point topleft, bottomright;
+
+static bool touch_available = false;
+
+static short x[NO_OF_TOUCH_DATA], y[NO_OF_TOUCH_DATA];
+
+/* comparator for qsort */
+static int short_cmp(const void *a, const void *b)
+{
+ return *(short*)a - *(short*)b;
+}
+
+static int touch_to_pixels(short val_x, short val_y)
+{
+ short x,y;
+
+ x=val_x;
+ y=val_y;
+
+ x = (x-topleft.val_x)*(bottomright.px_x - topleft.px_x)
+ / (bottomright.val_x - topleft.val_x) + topleft.px_x;
+
+ y = (y-topleft.val_y)*(bottomright.px_y - topleft.px_y)
+ / (bottomright.val_y - topleft.val_y) + topleft.px_y;
+
+ if (x < 0)
+ x = 0;
+ else if (x>=LCD_WIDTH)
+ x=LCD_WIDTH-1;
+
+ if (y < 0)
+ y = 0;
+ else if (y>=LCD_HEIGHT)
+ y=LCD_HEIGHT-1;
+
+ return (x<<16)|y;
+}
+
+void touchscreen_init_device()
+{
+ /* set touchscreen adc controller into wait for interrupt mode */
+ ADCTSC = 0xd3; /* Wfait,XP-PU,XP_DIS,XM_DIS,YP_dis,YM_end */
+
+ /* Arbitrary touchscreen calibration */
+ topleft.px_x = 0;
+ topleft.px_y = 0;
+ topleft.val_x = 105;
+ topleft.val_y = 925;
+
+ bottomright.px_x = LCD_WIDTH;
+ bottomright.px_y = LCD_HEIGHT;
+ bottomright.val_x = 890;
+ bottomright.val_y = 105;
+
+ touch_available = false;
+}
+
+void touchscreen_scan_device()
+{
+ static long last_touch_read = 0;
+ static int touch_data_index = 0;
+
+ int saveADCDLY;
+
+ /* check touch state */
+ if(ADCDAT1 & (1<<15))
+ {
+ return;
+ }
+
+ if (TIME_AFTER(current_tick, last_touch_read + 1))
+ {
+ /* resets the index if the last touch could not be read 5 times */
+ touch_data_index = 0;
+ }
+
+ /* read touch data */
+ saveADCDLY = ADCDLY;
+ ADCDLY = 40000; /*delay ~0.8ms (1/50M)*4000 */
+ ADCTSC = (1<<3)|(1<<2); /* pullup disable, seq x,y pos measure */
+ /* start adc */
+ ADCCON|= 0x1;
+ /* wait for start and end */
+ while(ADCCON & 0x1);
+ while(!(ADCCON & 0x8000));
+
+ x[touch_data_index] = ADCDAT0&0x3ff;
+ y[touch_data_index] = ADCDAT1&0x3ff;
+
+ ADCTSC = 0xd3; /* back to interrupt mode */
+ ADCDLY = saveADCDLY;
+
+ touch_data_index++;
+
+ if (touch_data_index > NO_OF_TOUCH_DATA - 1)
+ {
+ /* coordinates 5 times read */
+ touch_available = true;
+ touch_data_index = 0;
+ }
+ last_touch_read = current_tick;
+}
+
+int touchscreen_read_device(int *data, int *old_data)
+{
+ int btn = BUTTON_NONE;
+ static bool touch_hold = false;
+ static long last_touch = 0;
+
+ if (touch_available || touch_hold)
+ {
+ short x_touch, y_touch;
+ static short last_x = 0, last_y = 0;
+
+ if (touch_hold)
+ {
+ /* get rid of very fast unintended double touches */
+ x_touch = last_x;
+ y_touch = last_y;
+ }
+ else
+ {
+ /* sort the 5 data taken and use the median value */
+ qsort(x, NO_OF_TOUCH_DATA, sizeof(short), short_cmp);
+ qsort(y, NO_OF_TOUCH_DATA, sizeof(short), short_cmp);
+
+ x_touch = last_x = x[(NO_OF_TOUCH_DATA - 1)/2];
+ y_touch = last_y = y[(NO_OF_TOUCH_DATA - 1)/2];
+
+ last_touch = current_tick;
+
+ touch_hold = true;
+ touch_available = false;
+ }
+
+ *old_data = *data = touch_to_pixels(x_touch, y_touch);
+
+ btn |= touchscreen_to_pixels((*data&0xffff0000) >> 16,
+ (*data&0x0000ffff),
+ data);
+ }
+
+ if (TIME_AFTER(current_tick, last_touch + 10))
+ {
+ /* put the touchscreen back into interrupt mode */
+ touch_hold = false;
+ }
+
+ return btn;
+}
+
+
diff --git a/firmware/target/arm/s3c2440/mini2440/touchscreen-target.h b/firmware/target/arm/s3c2440/mini2440/touchscreen-target.h
new file mode 100644
index 0000000000..1019a98330
--- /dev/null
+++ b/firmware/target/arm/s3c2440/mini2440/touchscreen-target.h
@@ -0,0 +1,33 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Copyright (C) 2009 by Dominik Wenger
+ *
+ * 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 _TOUCHSCREEN_TARGET_H
+#define _TOUCHSCREEN_TARGET_H
+
+/* try to get a touchscreen reading from adc */
+void touchscreen_scan_device(void);
+/* init touchscreen driver */
+void touchscreen_init_device(void);
+
+int touchscreen_read_device(int *data, int *old_data);
+
+#endif
+