2011-09-23 11 views
18

Sto sviluppando un'applicazione in cui sto incollando immagini, facendo disegno e dipingendo su tela. Questa app può anche ridimensionare su/giù la tela o trascinarla in un'altra posizione. Il mio problema è: non riesco a ottenere le coordinate di tela corrette dopo il ridimensionamento o il trascinamento del canvas. Voglio attirare colori a dita dopo che la tela è ridimensionato o trascinato, ma in grado di recuperare il posto giusto dove ho toccato .. :( Anche io sono nuovo ape. Ecco il codice.Ottieni le coordinate della tela dopo il ridimensionamento su/giù o il trascinamento in Android

@Override 
public void onDraw(Canvas canvas) { 
    super.onDraw(canvas); 

    canvas.save(); 
    //canvas.translate(mPosX, mPosY); 
    canvas.scale(mScaleFactor, mScaleFactor, super.getWidth() * 0.5f, 
      super.getHeight() * 0.5f); 
    mIcon.draw(canvas); 
    for (Path path : listPath) { 
     canvas.drawPath(path, paint); 
    } 
    canvas.restore(); 
} 

public TouchExampleView(Context context, AttributeSet attrs, int defStyle) { 
    super(context, attrs, defStyle); 

} 

@Override 
public boolean onTouchEvent(MotionEvent ev) { 
    // Let the ScaleGestureDetector inspect all events. 
    mScaleDetector.onTouchEvent(ev); 

    final int action = ev.getAction(); 
    switch (action & MotionEvent.ACTION_MASK) { 
    case MotionEvent.ACTION_DOWN: { 
     final float x = ev.getX(); 
     final float y = ev.getY(); 

     mLastTouchX = x; 
     mLastTouchY = y; 
     mActivePointerId = ev.getPointerId(0); 
     break; 
    } 

    case MotionEvent.ACTION_MOVE: { 
     final int pointerIndex = ev.findPointerIndex(mActivePointerId); 
     final float x = ev.getX(pointerIndex); 
     final float y = ev.getY(pointerIndex); 

     // Only move if the ScaleGestureDetector isn't processing a gesture. 
     if (!mScaleDetector.isInProgress()) { 
      final float dx = x - mLastTouchX; 
      final float dy = y - mLastTouchY; 

      mPosX += dx; 
      mPosY += dy; 

      invalidate(); 
     } 

     mLastTouchX = x; 
     mLastTouchY = y; 

     break; 
    } 

    case MotionEvent.ACTION_UP: { 
     mActivePointerId = INVALID_POINTER_ID; 
     break; 
    } 

    case MotionEvent.ACTION_CANCEL: { 
     mActivePointerId = INVALID_POINTER_ID; 
     break; 
    } 

    case MotionEvent.ACTION_POINTER_UP: { 
     final int pointerIndex = (ev.getAction() & MotionEvent.ACTION_POINTER_INDEX_MASK) >> MotionEvent.ACTION_POINTER_INDEX_SHIFT; 
     final int pointerId = ev.getPointerId(pointerIndex); 
     if (pointerId == mActivePointerId) { 
      // This was our active pointer going up. Choose a new 
      // active pointer and adjust accordingly. 
      final int newPointerIndex = pointerIndex == 0 ? 1 : 0; 
      mLastTouchX = ev.getX(newPointerIndex); 
      mLastTouchY = ev.getY(newPointerIndex); 
      mActivePointerId = ev.getPointerId(newPointerIndex); 
     } 
     break; 
    } 
    } 

    float objectNewX,objectNewY; 
    if (mScaleFactor >= 1) { 
     objectNewX = ev.getX() + (ev.getX() - super.getWidth() * 0.5f) * (mScaleFactor - 1); 
     objectNewY = ev.getY() + (ev.getY() - super.getHeight() * 0.5f) * (mScaleFactor - 1); 
    } else { 
     objectNewX = ev.getX() - (ev.getX() - super.getWidth() * 0.5f) * (1 - mScaleFactor); 
     objectNewY = ev.getY() - (ev.getY() - super.getHeight() * 0.5f) * (1 - mScaleFactor); 
    } 

    if (ev.getAction() == MotionEvent.ACTION_DOWN) { 
     path = new Path(); 
     path.moveTo(objectNewX,objectNewY); 
     path.lineTo(objectNewX,objectNewY); 
    } else if (ev.getAction() == MotionEvent.ACTION_MOVE) { 
     path.lineTo(objectNewX,objectNewY); 
     listPath.add(path); 
    } else if (ev.getAction() == MotionEvent.ACTION_UP) { 
     path.lineTo(objectNewX,objectNewY); 
     listPath.add(path); 
    } 

    return true; 
} 

private class ScaleListener extends 
     ScaleGestureDetector.SimpleOnScaleGestureListener { 
    @Override 
    public boolean onScale(ScaleGestureDetector detector) { 
     mScaleFactor *= detector.getScaleFactor(); 

     // Don't let the object get too small or too large. 
     mScaleFactor = Math.max(0.1f, Math.min(mScaleFactor, 5.0f)); 

     invalidate(); 
     return true; 
    } 
} 
+0

* Non riesco a ottenere le coordinate di tela corrette *. Devi essere più specifico. La scala stessa funziona? Definisci ciò che ti aspetti come * coordinate di tela corrette *? Cosa c'è di sbagliato in loro adesso? – Knickedi

+0

prova a ingrandire l'immagine e poi dipingi qualcosa su tela ... poi verrai a sapere. –

+0

anche non commentato canvas.translate (mPosX, mPosY); –

risposta

19

Done . finalmente da solo

disegnare tutto applicando questa formula per (px, py) coordinate

float px = ev.getX()/mScaleFactor + rect.left; 
float py = ev.getY()/mScaleFactor + rect.top; 
rect = canvas.getClipBounds(); 
//Get them in on Draw function and apply above formula before drawing 
+0

Hey awais Sono anche bloccato alla stessa cosa. Non ho capito bene la tua soluzione per favore puoi condividere il tuo codice o aiutarmi con lo stesso? – user1169079

+0

dov'è il tuo problema ??? Nel mio caso, dove devo disegnare qualcosa sullo schermo, ho usato float x = ev.getX()/mScaleFactor + rect.left; per X invece di event.getX(); allo stesso modo per l'asse Y. Rect è il clipbounds della tela disegnata. Dobbiamo salvarlo in alcune variabili rettangolari. Si aggiornano continuamente nella funzione onDraw. –

+0

http://stackoverflow.com/questions/9989170/clickable-area-after-scaling-with-respect-to-positions-of-touch-event .. controlla se puoi aiutare sarà fantastico ... – user1169079

7
@Override 
protected void onDraw(Canvas canvas) { 
    super.onDraw(canvas); 
    clipBounds_canvas = canvas.getClipBounds(); 
    /////Do whatever you want to do..!!!    
}; 

@Override 
public boolean onTouchEvent(MotionEvent ev) { 
    int x = ev.getX()/zoomFactor + clipBounds_canvas.left; 
    int y = ev.getY()/zoomFactor + clipBounds_canvas.top; 
    //Use the above two values insted of ev.getX() and ev.getY(); 
} 

Spero che questo vi aiuterà

.
+0

Quelli sopra i due valori xey sono l'offset in cui sarà la mia area/clic di successo? O ho bisogno di aggiornare i miei oggetti di disegno usando il valore xey di cui sopra? – user1169079

+0

è necessario aggiornare gli oggetti disegnati, supponendo in base alle x e y relative relative. –

+0

Grazie amico !!! Ho capito dove si muove il mio oggetto ... ma non so come spostare l'area cliccabile nella stessa posizione su cui sto lavorando ... se hai qualche idea, suggerisci !!! Ho provato getHitRect e aggiungo l'offset ad esso? lavoro a forza !!! – user1169079

Problemi correlati