title: Android: Draw Custom TextView on Canvas
body: <p>I have following TextView</p>
  
  <pre><code>public class Cube extends TextView {
  
  Context mContext;
  
  Drawable background;//Hintergrund des Blocks
  char mLetter;//Buchstabe des Blocks
  int x, y;//Koordinaten des Blocks
  
  @SuppressWarnings("deprecation")
  @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
  public Cube(Context context, char letter, int _x, int _y) {
      super(context);
      mContext = context;
      mLetter = letter;
      background = ContextCompat.getDrawable(getContext(), R.drawable.cube);
      x = _x;
      y = _y;
      this.setText("" + letter);
      if(android.os.Build.VERSION.SDK_INT &lt; android.os.Build.VERSION_CODES.JELLY_BEAN)
          this.setBackgroundDrawable(background);
      else
          this.setBackground(background);
  }
  
  public void drawCube(Canvas canvas){//how to draw now!? This is called from a separate thread in SurfaceView
  }
  
  }
  </code></pre>
  
  <p>If I call following in drawCube():</p>
  
  <pre><code>    background.setBounds(x, y, x + 20, y + 20);
      background.draw(canvas);
  </code></pre>
  
  <p>it just draws the backgroundDrawable. But how can I draw it with the text/the letter inside? That it looks like this: (The background ist the canvas, the orange and white one is the Background and the "A" is the letter/text)</p>
  
  <p><a href="https://i.stack.imgur.com/HQrfa.png" rel="nofollow noreferrer"><img src="https://i.stack.imgur.com/HQrfa.png" alt="enter image description here"></a></p>
  
  <p><strong>EDIT: Code at 21.09</strong>
  This is my (shortened) thread:</p>
  
  <pre><code>public class CanvasThread extends Thread {
  
  private SurfaceHolder mSh;
  
  private ArrayList&lt;Cube&gt; mCubes;
  
  private Canvas mCanvas;
  private Context mContext;
  private boolean mRun = false;
  private boolean mDown = false;
  private boolean newCube = false;
  public CanvasThread(SurfaceHolder sh, Context context){
      mSh = sh;
      mCubes = new ArrayList&lt;&gt;();
      mContext = context;
  }
  
  public void run(){
      while(mRun){
          mCanvas = null;
  
          try{
              mCanvas = mSh.lockCanvas(null);
              synchronized (mSh){
                  mCanvas.drawColor(Color.TRANSPARENT, PorterDuff.Mode.CLEAR);
                  newCube = true;
                  for(int i = 0; i &lt; mCubes.size(); i++){
                      if(mCubes.get(i).getSpeed() &gt; 0)
                          newCube = false;
                      if(mDown) {
                          if (mCubes.get(i).moveDown(feld)) {
                              mDown = false;
                          }
                      }
                      //mCubes.get(i).invalidate();
                      //mCubes.get(i).requestLayout();
                      mCubes.get(i).draw(mCanvas);
                  }
                  if(newCube)
                      addCube();
              }
          } finally {
              if(mCanvas != null){
                  mSh.unlockCanvasAndPost(mCanvas);
              }
          }
      }
  }
  
  public void addCube(){
      Random r = new Random();
      Cube cube = new Cube(mContext, mBuchstaben[r.nextInt(29)], r.nextInt(10), 0, mCanvas);
      mCubes.add(cube);
  }
  </code></pre>
  
  <p>}</p>
  
  <p>This is my (shortened) fragment which uses the canvas/surface view:</p>
  
  <pre><code>public class KlassischFragment extends Fragment implements SurfaceHolder.Callback {
  
  SurfaceHolder sh;
  SurfaceView sv;
  
  private CanvasThread thread;
  
  @Override
  public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
      View view = inflater.inflate(R.layout.fragment_klassisch, container, false);
      sv = (SurfaceView) view.findViewById(R.id.surfaceView);
      sh = sv.getHolder();
      sh.addCallback(this);
      sh.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
      return view;
  }
  
  @Override
  public void surfaceCreated(SurfaceHolder holder) {
      thread = new CanvasThread(sh, getContext());
      thread.setRunnable(true);
      thread.start();
  }
  
  @Override
  public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
  }
  
  @Override
  public void surfaceDestroyed(SurfaceHolder holder) {
      boolean retry = true;
      //thread.setRunnable(false);
  
      while(retry){
          try{
              thread.join();
              retry = false;
          } catch(InterruptedException ie){
              //Immer wieder versuchen
          }
          break;
      }
      thread = null;
  }
  </code></pre>
  
  <p>}</p>