2012-04-04 2 views
2

Ist es möglich, jedes berührte Pixel zu erkennen? Genauer gesagt, wenn der Benutzer den Bildschirm berührt, ist es möglich, alle x-y-Koordinaten des vom Benutzer berührten Punktclusters zu verfolgen? Woran erkenne ich den Unterschied zwischen dem Zeichnen mit dem Daumen und dem Zeichnen mit der Fingerspitze? Ich möchte den Pinsel Unterschied reflektieren, je nachdem, wie Benutzer den Bildschirm berühren, und möchte auch alle Pixel, die berührt werden, verfolgen.Erhalten einzelner Pixel vom Berührungspunkt

Ich bin derzeit mit den folgenden Codes aus der GLPaint Probe von Apple Entwickler-Website:

http://developer.apple.com/library/ios/#samplecode/GLPaint/Introduction/Intro.html

Die Probe-Codes ermöglicht mit einer vordefinierten Pinselgröße und die Verfolgung der x-y-Koordinaten auf dem Weg zu ziehen. Wie kann ich den Pinsel ändern, je nachdem, wie Benutzer den Bildschirm berühren und alle Pixel im Laufe der Zeit verfolgen?

// Drawings a line onscreen based on where the user touches 

- (void) renderLineFromPoint:(CGPoint)start toPoint:(CGPoint)end 

{ 
    NSLog(@"x:%f y:%f",start.x, start.y); 

    static GLfloat*   vertexBuffer = NULL; 

    static NSUInteger  vertexMax = 64; 

    NSUInteger    vertexCount = 0, 

        count, 

        i; 



    [EAGLContext setCurrentContext:context]; 

    glBindFramebufferOES(GL_FRAMEBUFFER_OES, viewFramebuffer); 



    // Convert locations from Points to Pixels 

    CGFloat scale = self.contentScaleFactor; 

    start.x *= scale; 

    start.y *= scale; 

    end.x *= scale; 

    end.y *= scale; 



    // Allocate vertex array buffer 

    if(vertexBuffer == NULL) 

      vertexBuffer = malloc(vertexMax * 2 * sizeof(GLfloat)); 



    // Add points to the buffer so there are drawing points every X pixels 

    count = MAX(ceilf(sqrtf((end.x - start.x) * (end.x - start.x) + (end.y - start.y) * (end.y - start.y))/kBrushPixelStep), 1); 

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

      if(vertexCount == vertexMax) { 

       vertexMax = 2 * vertexMax; 

       vertexBuffer = realloc(vertexBuffer, vertexMax * 2 * sizeof(GLfloat)); 

      } 



      vertexBuffer[2 * vertexCount + 0] = start.x + (end.x - start.x) * ((GLfloat)i/(GLfloat)count); 

      vertexBuffer[2 * vertexCount + 1] = start.y + (end.y - start.y) * ((GLfloat)i/(GLfloat)count); 

      vertexCount += 1; 

    } 



    // Render the vertex array 

    glVertexPointer(2, GL_FLOAT, 0, vertexBuffer); 

    glDrawArrays(GL_POINTS, 0, vertexCount); 



    // Display the buffer 

    glBindRenderbufferOES(GL_RENDERBUFFER_OES, viewRenderbuffer); 

    [context presentRenderbuffer:GL_RENDERBUFFER_OES]; 

} 


// Handles the start of a touch 

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event 

{ 

    CGRect     bounds = [self bounds]; 

    UITouch*  touch = [[event touchesForView:self] anyObject]; 

    firstTouch = YES; 

    // Convert touch point from UIView referential to OpenGL one (upside-down flip) 

    location = [touch locationInView:self]; 

    location.y = bounds.size.height - location.y; 

} 

// Handles the continuation of a touch. 

- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event 

{ 

    CGRect     bounds = [self bounds]; 

    UITouch*    touch = [[event touchesForView:self] anyObject]; 



    // Convert touch point from UIView referential to OpenGL one (upside-down flip) 

    if (firstTouch) { 

      firstTouch = NO; 

      previousLocation = [touch previousLocationInView:self]; 

      previousLocation.y = bounds.size.height - previousLocation.y; 

    } else { 

      location = [touch locationInView:self]; 

     location.y = bounds.size.height - location.y; 

      previousLocation = [touch previousLocationInView:self]; 

      previousLocation.y = bounds.size.height - previousLocation.y; 

    } 



    // Render the stroke 

    [self renderLineFromPoint:previousLocation toPoint:location]; 

} 



// Handles the end of a touch event when the touch is a tap. 

- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event 

{ 

    CGRect     bounds = [self bounds]; 

    UITouch*  touch = [[event touchesForView:self] anyObject]; 

    if (firstTouch) { 

      firstTouch = NO; 

      previousLocation = [touch previousLocationInView:self]; 

      previousLocation.y = bounds.size.height - previousLocation.y; 

      [self renderLineFromPoint:previousLocation toPoint:location]; 

    } 

} 


// Handles the end of a touch event. 

- (void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent *)event 

{ 

    // If appropriate, add code necessary to save the state of the application. 

    // This application is not saving state. 

} 

Antwort

1

AFAIK gibt es keine API für den Zugriff auf die Touch-Zone für eine Berührung. Ich bin mir nicht einmal sicher, angesichts der Grenzen eines kapazitiven Touchscreens, ob das, was Sie wollen, physikalisch möglich ist. Ich erinnere mich an eine Präsentation in einem kürzlich erschienenen Cocoa Heads, in der gezeigt wurde, dass einige Informationen unter OS X (über private API) für Trackpads verfügbar waren, nicht jedoch für iOS.

Ich glaube, dies ist ein Grund, die Grafiktabletts speziellen Griffel beschäftigen, die ihre eigene Sensorik eingebaut haben.

Eine teilweise Abhilfe für eine Zeichenanwendung könnte „Einfärben“ zu simulieren, da einige Desktop-Anwendungen zu tun : Wenn die Berührung eines Benutzers an einer bestimmten Stelle verweilt, zeichnen Sie so, als würde Tinte aus dem "Stift" austreten und nach und nach durch das "Papier" diffundieren.

+0

Vielen Dank für Ihre Antwort. Weißt du ob das auf Android möglich ist? – HappyAppDeveloper

+0

Ich habe keine Ahnung, sorry, ich entwickle nicht für Android. Ich bin sicher, dass andere eine Antwort haben werden. Wenn Sie bei der Suche nichts finden, schlage ich vor, eine neue Frage als Android zu veröffentlichen. –

1

Die Broadcomm-Hardware im iPad scannt den Bildschirm mit 64 Hz. Dies geschieht, indem auf die 39 transparenten leitfähigen Schichten, die die Touchscreen-Elektroden bilden, jeweils ein Signal für jeweils 400 μs gelegt wird. Wenn sich Ihr Finger um mehr als eine Pixelentfernung innerhalb von 0,015625 Sekunden bewegt, was wahrscheinlich ist, kann die Hardware dies nicht erkennen, da sie damit beschäftigt ist, andere Teile des Bildschirms nach mehr Berührungsereignissen zu messen.

Dies ist das gleiche unabhängig von iOS oder Android. Günstige Android-Tablets und große Bildschirme haben eine reduzierte Scan-Rate, so dass ihre Berührungsereignisse noch weiter auseinander liegen.

Eine Wacom-Tablette führt den Digitalisierer mit 100 Hz, so dass die Reihenfolge der Punkte feiner wird, aber immer noch die Pixel fehlen, die der Stift zwischen zwei Messungen berührt.