OK,

Maybe it's time we work together and try to fix this bug. *A beaglebone
black that doesn't support correctly the touchscreen, it's a SHAME !*

So I'm going to try to fix it by myself =>

I prefer to put my conclusion here, because I don't hink everyone has the
time to read my research :




 *1) Presentation of the BUG*



   - When you touch the screen repeatedly ( up and down up and down ) the
   bug seems to happen ! ( rarely, but it does )
   - When you touch the screen continuously, you can see that sometime the
   mouse go far away from your finger .


*2) The driver*

The name of the driver is TI - TSC ADC (Touschscreen and analog digital
converter)

It's easy to find the source of this driver =>
drivers/input/touchscreen/ti_am335x_tsc.c

 *3) The  Interesting part*

 The interesting part of this driver, is this function :

static void titsc_read_coordinates(struct titsc *ts_dev,

                u32 *x, u32 *y, u32 *z1, u32 *z2)

{

        unsigned int fifocount = titsc_readl(ts_dev, REG_FIFO0CNT);

         unsigned int prev_val_x = ~0, prev_val_y = ~0;

        unsigned int prev_diff_x = ~0, prev_diff_y = ~0;

         unsigned int read, diff;

        unsigned int i, channel;

        unsigned int creads = ts_dev->coordinate_readouts;

        *z1 = *z2 = 0;

        if (fifocount % (creads * 2 + 2))

                 fifocount -= fifocount % (creads * 2 + 2);

        /*

         * Delta filter is used to remove large variations in sampled

         * values from ADC. The filter tries to predict where the next

         * coordinate could be. This is done by taking a previous

         * coordinate and subtracting it form current one. Further the

         * algorithm compares the difference with that of a present value,

         * if true the value is reported to the sub system.

         */

        for (i = 0; i < fifocount; i++) {

                read = titsc_readl(ts_dev, REG_FIFO0);

                 channel = (read & 0xf0000) >> 16;

                read &= 0xfff;

                 if (channel < creads) {

                        diff = abs(read - prev_val_x);

                         if (diff < prev_diff_x) {

                                prev_diff_x = diff;

                                 *x = read;

                        }

                        prev_val_x = read;

                } else if (channel < creads * 2) {

                        diff = abs(read - prev_val_y);

                        if (diff < prev_diff_y) {

                                prev_diff_y = diff;

                                *y = read;

                        }

                         prev_val_y = read;

                } else if (channel < creads * 2 + 1) {

                         *z1 = read;

                } else if (channel < creads * 2 + 2) {

                         *z2 = read;

                }

        }

}



So did you watch this code ? Well, In my case, I understand why there is
this huge bug !

We have to admit, that sometime there is noise during the transfer of the
coordinate between the LCD and the driver.

So, this code is supposed to filter any of noise with this :



                        diff = abs(read - prev_val_x);

                        if (diff < prev_diff_x) {

                                prev_diff_x = diff;

                                *x = read;

                        }

                        prev_val_x = read;


Well, I'm sorry, but if the noise happen, you should not save the noise
value has the last position (correct me if I'm wrong ?) .....

So, I changed the code with something like that :

             if (channel < creads) {
                        printk("raw x=%d\n", read);
                        diff = abs(read - prev_val_x);
                        if (diff < prev_diff_x) {
                                printk("x=%d & diff=%d\n", read, diff);
                                prev_diff_x = diff;
                                *x = read;
                                prev_val_x = read;
                        }

                } else if (channel < creads * 2) {
                        printk("raw y=%d\n", read);
                        diff = abs(read - prev_val_y);
                        if (diff < prev_diff_y) {
                                printk("y=%d & diff=%d\n", read, diff);
                                prev_diff_y = diff;
                                *y = read;
                                prev_val_y = read;
                        }

                } else if (channel < creads * 2 + 1) {
                        *z1 = read;

                } else if (channel < creads * 2 + 2) {
                        *z2 = read;
                }

Also, it's important to note that this function is called by the
function irqreturn_t titsc_irq:
I put a printk to be noticed when the function is called :

static irqreturn_t titsc_irq(int irq, void *dev)
{
        struct titsc *ts_dev = dev;
        struct input_dev *input_dev = ts_dev->input;
        unsigned int status, irqclr = 0;
        unsigned int x = 0, y = 0;
        unsigned int z1, z2, z;
        unsigned int fsm;

        status = titsc_readl(ts_dev, REG_IRQSTATUS);
        /*
         * ADC and touchscreen share the IRQ line.
         * FIFO1 threshold, FIFO1 Overrun and FIFO1 underflow
         * interrupts are used by ADC,
         * hence return from touchscreen IRQ handler if FIFO1
         * related interrupts occurred.
         */
        if ((status & IRQENB_FIFO1THRES) ||
                        (status & IRQENB_FIFO1OVRRUN) ||
                        (status & IRQENB_FIFO1UNDRFLW))
                return IRQ_NONE;
        else if (status & IRQENB_FIFO0THRES) {
             *   printk("start\n");*
*                titsc_read_coordinates(ts_dev, &x, &y, &z1, &z2);*


Now, it' time to test it ! I've a LCD7, and max x =  800, max y=480:

[  198.656774] start

[  198.656831] raw x=646
[  198.656854] diff 647
[  198.656876] x=646
[  198.656897] raw x=686
[  198.656918] diff 40
[  198.656937] x=686
[  198.656958] raw x=686
[  198.656979] diff 0
[  198.656998] x=686
[  198.657018] raw x=686
[  198.657038] diff 0
[  198.657058] raw x=686
[  198.657078] diff 0
[  198.657099] raw y=2891
[  198.657119] diff 2892
 [  198.657139] y=2891
[  198.657160] raw y=2890
[  198.657180] diff 1
[  198.657200] y=2890
[  198.657221] raw y=2889
[  198.657241] diff 1
[  198.657262] raw y=2888
[  198.657281] diff 2
[  198.657302] raw y=2885
[  198.657322] diff 5

[  198.659221] start

[  198.659250] raw x=685
[  198.659270] diff 686
[  198.659290] x=685
[  198.659310] raw x=686
[  198.659330] diff 1
[  198.659350] x=686
[  198.659370] raw x=685
[  198.659390] diff 1
 [  198.659410] raw x=683
[  198.659430] diff 3
[  198.659450] raw x=680
[  198.659470] diff 6
[  198.659490] raw y=2879
[  198.659510] diff 2880
[  198.659530] y=2879
[  198.659550] raw y=2878
[  198.659570] diff 1
[  198.659590] y=2878
[  198.659611] raw y=2879
[  198.659630] diff 1
[  198.659651] raw y=2879
[  198.659670] diff 1
[  198.659691] raw y=2873
[  198.659711] diff 5

+ other data


*My first question, is WHY the Y VALUE is that high ?  maybe because y is
not in pixel ?*


Also we can see that the function  titsc_read_coordinates is called
multiple times.........


And just now, I discover something ! There is a mistake between the role of
the  two function :

The function * irqreturn_t titsc_irq* call the function
* titsc_read_coordinates*. to calculate the position of x, y, and z . After
that the function * irqreturn_t titsc_irq* report to the upper level the
position and the pressure level with this:


 titsc_read_coordinates(ts_dev, &x, &y, &z1, &z2);

              if (ts_dev->pen_down && z1 != 0 && z2 != 0) {
                        /*
                         * Calculate pressure using formula
                         * Resistance(touch) = x plate resistance *
                         * x postion/4096 * ((z2 / z1) - 1)
                          */
                        z = z1 - z2;
                        z *= x;
                        z *= ts_dev->x_plate_resistance;
                        z /= z2;
                        z = (z + 2047) >> 12;

                        if (z <= MAX_12BIT) {
*                                input_report_abs(input_dev, ABS_X, x);*
*                                 input_report_abs(input_dev, ABS_Y, y);*
*                                input_report_abs(input_dev, ABS_PRESSURE,
z);*
*                                input_report_key(input_dev, BTN_TOUCH, 1);*
*                                input_sync(input_dev);*
                        }
                }

So, If I'm not wrong ( correct me if it is ), The function
titsc_read_coordinates should calculate just one x value and one y value.
Most of the times, the function works because it give the last position
(depending of some condition ...) of the FIFO ....

So why not calculate the average value of x and y ? If I do that, I will be
able to eliminate better, the noise .... but in counter part I will
increase the time of response .....

 I tried that, but I don't see any difference, but for me, it's better like
that, I feel that it's the correct thing to do !


So, I have still this horrible bug ! And I don't know why !!!! So I started
again some test, but this time, I want to see the value of the pressure !
 =>



.....
[   69.777100] start
[   69.777140] x=2982
[   69.777161] y=1223
[   69.777185] Z1 1612 Z2 3472 z=*224 *
[   69.779156] start
[   69.779201] x=2983
[   69.779222] y=1222
[   69.779245] Z1 1600 Z2 3474 z=*223*
[   69.781230] start
[   69.781271] x=2983
[   69.781292] y=1225
[   69.781316] Z1 1581 Z2 3486 z=*221*
[   69.783301] start
[   69.783344] x=2984
[   69.783365] y=1226
[   69.783389] Z1 1565 Z2 3488 z=*220*
[   69.785372] start
[   69.785413] x=2983
[   69.785433] y=1226
[   69.785458] Z1 1555 Z2 3493 z=*219*
[   69.787437] start
[   69.787479] x=2984
[   69.787499] y=1226
[   69.787522] Z1 1540 Z2 3500 z=*218*
[   69.789502] start
[   69.789543] x=2983
[   69.789564] y=1229
[   69.789587] Z1 1467 Z2 3532 z=*212*
[   69.791562] start
[   69.791602] x=*2986*
[   69.791623] y=*1231*
[   69.791646] Z1 1172 Z2 3678 z=*186*
[   69.793621] start
[  69.793663]*x=1807*
[   69.793683]* y=2596*
[   69.793707] Z1 1 Z2 4091* z=168*


AND NOW, it's starting to be VERY VERY interesting ! It looks like that
when you remove your finger, some times ( electrical problems ? ) we got
noise ! And THAT make the BIG bug !

I love linux and printk ^^

So, it's time to fix it, how ? by detecting the drop of z !!!! We just need
to ignore the x and y calculated if Z drop too much ! =>

It work sometime .. but not all of the time ==>


[  184.476665] start

[  184.476705] x=2889
[  184.476726] y=1300
[  184.476748] deltaZ=-7 z=207

[  184.478722] start

[  184.478764] x=2889
[  184.478784] y=1293
[  184.478806] deltaZ=-22 z=185
[  184.478827] z ignored, deltaZ=-22

[  184.480720] start

[  184.480760] x=2890
[  184.480781] y=1289
[  184.480803] deltaZ=-20 z=165
[  184.480824] z ignored, deltaZ=-20

[  184.482714] start

[  184.482753] x=719
[  184.482774] y=3591
[  184.482796] deltaZ=56 z=221



So, it looks like that it's not that perfect, not yet !











On Wed, Dec 18, 2013 at 9:00 PM, Terry Storm <[email protected]> wrote:

> Lots of alternatives you can download
> Aptoide <http://www.aptoide.com/> is one for example
> Only have to get the apk for that and then download using aptoide like any
> other App Store.
>
>
> On 18 December 2013 17:24, Ian Kidd <[email protected]> wrote:
>
>> I figured.  I'll give that a shot.  Be nice to have an App Store on that
>> TI image.
>>
>>
>> On Tuesday, December 17, 2013 9:19:22 PM UTC-7, Terry Storm wrote:
>>>
>>> Should read
>>>
>>> "but does not support the Hardware Graphics like the TI one"
>>>
>>> above.
>>>
>>> On Wednesday, 18 December 2013 13:27:18 UTC+13, Terry Storm wrote:
>>>>
>>>> Hi Ian
>>>>
>>>> Did you try the TI image instead of the Anderson image?
>>>> The TI one seems to be more stable and the buttons are actually mapped
>>>> to suit Android, which isn't the case on the Anderson image. Anderson Image
>>>> is Kernel 3.8 however, but also does support the Hardware Graphics like the
>>>> TI one, so the TI one is quite a bit faster too.
>>>> I haven't had to calibrate, both just worked for me.
>>>> Screen rotation utility was just from the App Store, just some free
>>>> rotation app. Cant remember what it was called off the top of my head.
>>>>
>>>> Try and TI image and report back.
>>>> Terry
>>>>
>>>> On Wednesday, 18 December 2013 12:38:01 UTC+13, Ian Kidd wrote:
>>>>>
>>>>> Hi, Terry.  I see you got the touchscreen working in Android.  I'm
>>>>> using the Anderson image, and while I can get swipe scrolling to work, it
>>>>> doesn't seem to be calibrated for the point of touch.  Any particular
>>>>> utility that you use to calibrate the touch on Android.
>>>>>
>>>>> Also, what was the screen rotation utility you mentioned?
>>>>>
>>>>  --
>> For more options, visit http://beagleboard.org/discuss
>> ---
>> You received this message because you are subscribed to a topic in the
>> Google Groups "BeagleBoard" group.
>> To unsubscribe from this topic, visit
>> https://groups.google.com/d/topic/beagleboard/SXTaSUf4aSk/unsubscribe.
>> To unsubscribe from this group and all its topics, send an email to
>> [email protected].
>>
>> For more options, visit https://groups.google.com/groups/opt_out.
>>
>
>  --
> For more options, visit http://beagleboard.org/discuss
> ---
> You received this message because you are subscribed to the Google Groups
> "BeagleBoard" group.
> To unsubscribe from this group and stop receiving emails from it, send an
> email to [email protected].
> For more options, visit https://groups.google.com/groups/opt_out.
>

-- 
For more options, visit http://beagleboard.org/discuss
--- 
You received this message because you are subscribed to the Google Groups 
"BeagleBoard" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
For more options, visit https://groups.google.com/groups/opt_out.

Reply via email to