aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorweixing <weixing@hanwang.com.cn>2012-07-13 03:08:42 -0400
committerDmitry Torokhov <dmitry.torokhov@gmail.com>2012-07-13 03:14:27 -0400
commit8a90c034ae0d4282e2aeb9cf8311dc90c855d815 (patch)
tree475d003d61378939ef6b6c328a39856999f1e9d2
parent8314f532ebd55f1d6dc23b143cda3c1714ffe201 (diff)
Input: hanwang - add support for Art Master II tablet
This change adds support for old Hanwang Art master II tablet Signed-off-by: weixing <weixing@hanwang.com.cn> Signed-off-by: Dmitry Torokhov <dmitry.torokhov@gmail.com>
-rw-r--r--drivers/input/tablet/hanwang.c57
1 files changed, 42 insertions, 15 deletions
diff --git a/drivers/input/tablet/hanwang.c b/drivers/input/tablet/hanwang.c
index b2db3cfe3084..5cc04124995c 100644
--- a/drivers/input/tablet/hanwang.c
+++ b/drivers/input/tablet/hanwang.c
@@ -63,6 +63,7 @@ MODULE_LICENSE(DRIVER_LICENSE);
63enum hanwang_tablet_type { 63enum hanwang_tablet_type {
64 HANWANG_ART_MASTER_III, 64 HANWANG_ART_MASTER_III,
65 HANWANG_ART_MASTER_HD, 65 HANWANG_ART_MASTER_HD,
66 HANWANG_ART_MASTER_II,
66}; 67};
67 68
68struct hanwang { 69struct hanwang {
@@ -99,6 +100,8 @@ static const struct hanwang_features features_array[] = {
99 ART_MASTER_PKGLEN_MAX, 0x7f00, 0x4f60, 0x3f, 0x7f, 2048 }, 100 ART_MASTER_PKGLEN_MAX, 0x7f00, 0x4f60, 0x3f, 0x7f, 2048 },
100 { 0x8401, "Hanwang Art Master HD 5012", HANWANG_ART_MASTER_HD, 101 { 0x8401, "Hanwang Art Master HD 5012", HANWANG_ART_MASTER_HD,
101 ART_MASTER_PKGLEN_MAX, 0x678e, 0x4150, 0x3f, 0x7f, 1024 }, 102 ART_MASTER_PKGLEN_MAX, 0x678e, 0x4150, 0x3f, 0x7f, 1024 },
103 { 0x8503, "Hanwang Art Master II", HANWANG_ART_MASTER_II,
104 ART_MASTER_PKGLEN_MAX, 0x27de, 0x1cfe, 0x3f, 0x7f, 1024 },
102}; 105};
103 106
104static const int hw_eventtypes[] = { 107static const int hw_eventtypes[] = {
@@ -127,14 +130,30 @@ static void hanwang_parse_packet(struct hanwang *hanwang)
127 struct usb_device *dev = hanwang->usbdev; 130 struct usb_device *dev = hanwang->usbdev;
128 enum hanwang_tablet_type type = hanwang->features->type; 131 enum hanwang_tablet_type type = hanwang->features->type;
129 int i; 132 int i;
130 u16 x, y, p; 133 u16 p;
134
135 if (type == HANWANG_ART_MASTER_II) {
136 hanwang->current_tool = BTN_TOOL_PEN;
137 hanwang->current_id = STYLUS_DEVICE_ID;
138 }
131 139
132 switch (data[0]) { 140 switch (data[0]) {
133 case 0x02: /* data packet */ 141 case 0x02: /* data packet */
134 switch (data[1]) { 142 switch (data[1]) {
135 case 0x80: /* tool prox out */ 143 case 0x80: /* tool prox out */
136 hanwang->current_id = 0; 144 if (type != HANWANG_ART_MASTER_II) {
137 input_report_key(input_dev, hanwang->current_tool, 0); 145 hanwang->current_id = 0;
146 input_report_key(input_dev,
147 hanwang->current_tool, 0);
148 }
149 break;
150
151 case 0x00: /* artmaster ii pen leave */
152 if (type == HANWANG_ART_MASTER_II) {
153 hanwang->current_id = 0;
154 input_report_key(input_dev,
155 hanwang->current_tool, 0);
156 }
138 break; 157 break;
139 158
140 case 0xc2: /* first time tool prox in */ 159 case 0xc2: /* first time tool prox in */
@@ -154,15 +173,12 @@ static void hanwang_parse_packet(struct hanwang *hanwang)
154 default: 173 default:
155 hanwang->current_id = 0; 174 hanwang->current_id = 0;
156 dev_dbg(&dev->dev, 175 dev_dbg(&dev->dev,
157 "unknown tablet tool %02x ", data[0]); 176 "unknown tablet tool %02x\n", data[0]);
158 break; 177 break;
159 } 178 }
160 break; 179 break;
161 180
162 default: /* tool data packet */ 181 default: /* tool data packet */
163 x = (data[2] << 8) | data[3];
164 y = (data[4] << 8) | data[5];
165
166 switch (type) { 182 switch (type) {
167 case HANWANG_ART_MASTER_III: 183 case HANWANG_ART_MASTER_III:
168 p = (data[6] << 3) | 184 p = (data[6] << 3) |
@@ -171,6 +187,7 @@ static void hanwang_parse_packet(struct hanwang *hanwang)
171 break; 187 break;
172 188
173 case HANWANG_ART_MASTER_HD: 189 case HANWANG_ART_MASTER_HD:
190 case HANWANG_ART_MASTER_II:
174 p = (data[7] >> 6) | (data[6] << 2); 191 p = (data[7] >> 6) | (data[6] << 2);
175 break; 192 break;
176 193
@@ -180,17 +197,23 @@ static void hanwang_parse_packet(struct hanwang *hanwang)
180 } 197 }
181 198
182 input_report_abs(input_dev, ABS_X, 199 input_report_abs(input_dev, ABS_X,
183 le16_to_cpup((__le16 *)&x)); 200 be16_to_cpup((__be16 *)&data[2]));
184 input_report_abs(input_dev, ABS_Y, 201 input_report_abs(input_dev, ABS_Y,
185 le16_to_cpup((__le16 *)&y)); 202 be16_to_cpup((__be16 *)&data[4]));
186 input_report_abs(input_dev, ABS_PRESSURE, 203 input_report_abs(input_dev, ABS_PRESSURE, p);
187 le16_to_cpup((__le16 *)&p));
188 input_report_abs(input_dev, ABS_TILT_X, data[7] & 0x3f); 204 input_report_abs(input_dev, ABS_TILT_X, data[7] & 0x3f);
189 input_report_abs(input_dev, ABS_TILT_Y, data[8] & 0x7f); 205 input_report_abs(input_dev, ABS_TILT_Y, data[8] & 0x7f);
190 input_report_key(input_dev, BTN_STYLUS, data[1] & 0x02); 206 input_report_key(input_dev, BTN_STYLUS, data[1] & 0x02);
191 input_report_key(input_dev, BTN_STYLUS2, data[1] & 0x04); 207
208 if (type != HANWANG_ART_MASTER_II)
209 input_report_key(input_dev, BTN_STYLUS2,
210 data[1] & 0x04);
211 else
212 input_report_key(input_dev, BTN_TOOL_PEN, 1);
213
192 break; 214 break;
193 } 215 }
216
194 input_report_abs(input_dev, ABS_MISC, hanwang->current_id); 217 input_report_abs(input_dev, ABS_MISC, hanwang->current_id);
195 input_event(input_dev, EV_MSC, MSC_SERIAL, 218 input_event(input_dev, EV_MSC, MSC_SERIAL,
196 hanwang->features->pid); 219 hanwang->features->pid);
@@ -202,8 +225,8 @@ static void hanwang_parse_packet(struct hanwang *hanwang)
202 225
203 switch (type) { 226 switch (type) {
204 case HANWANG_ART_MASTER_III: 227 case HANWANG_ART_MASTER_III:
205 input_report_key(input_dev, BTN_TOOL_FINGER, data[1] || 228 input_report_key(input_dev, BTN_TOOL_FINGER,
206 data[2] || data[3]); 229 data[1] || data[2] || data[3]);
207 input_report_abs(input_dev, ABS_WHEEL, data[1]); 230 input_report_abs(input_dev, ABS_WHEEL, data[1]);
208 input_report_key(input_dev, BTN_0, data[2]); 231 input_report_key(input_dev, BTN_0, data[2]);
209 for (i = 0; i < 8; i++) 232 for (i = 0; i < 8; i++)
@@ -227,6 +250,10 @@ static void hanwang_parse_packet(struct hanwang *hanwang)
227 BTN_5 + i, data[6] & (1 << i)); 250 BTN_5 + i, data[6] & (1 << i));
228 } 251 }
229 break; 252 break;
253
254 case HANWANG_ART_MASTER_II:
255 dev_dbg(&dev->dev, "error packet %02x\n", data[0]);
256 return;
230 } 257 }
231 258
232 input_report_abs(input_dev, ABS_MISC, hanwang->current_id); 259 input_report_abs(input_dev, ABS_MISC, hanwang->current_id);
@@ -234,7 +261,7 @@ static void hanwang_parse_packet(struct hanwang *hanwang)
234 break; 261 break;
235 262
236 default: 263 default:
237 dev_dbg(&dev->dev, "error packet %02x ", data[0]); 264 dev_dbg(&dev->dev, "error packet %02x\n", data[0]);
238 break; 265 break;
239 } 266 }
240 267