代码之家  ›  专栏  ›  技术社区  ›  Nizar

在SurfaceView上绘制

  •  0
  • Nizar  · 技术社区  · 6 年前

    enter image description here

    这是我的密码:

    public class MainActivity extends AppCompatActivity  implements SurfaceHolder.Callback {
    
        SurfaceView surfaceView;
        SurfaceHolder surfaceHolder;
        Canvas canvas;
        private Path path;
        Paint mPaint = new Paint();
    
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate( savedInstanceState );
            setContentView( R.layout.activity_main );
    
            surfaceView = (SurfaceView) findViewById( R.id.surfaceView );
            surfaceHolder = surfaceView.getHolder();
            surfaceView.getHolder().addCallback( this );
    
            canvas = surfaceView.getHolder().lockCanvas();
    
            mPaint = new Paint();
            mPaint.setAntiAlias( true );
            mPaint.setDither( true );
            //  mPaint.setColor(0xff000000);
            mPaint.setStyle( Paint.Style.STROKE );
            mPaint.setStrokeJoin( Paint.Join.ROUND);
            mPaint.setStrokeCap( Paint.Cap.ROUND);
            mPaint.setStrokeWidth( 50);
        }
    
        @SuppressLint("ClickableViewAccessibility")
        @Override
        public void surfaceCreated(SurfaceHolder holder) {
            Log.d( "surfaceCreated", "surfaceCreated " );
    
    
            path = new Path();
            surfaceHolder = holder;
            surfaceView.setOnTouchListener( new View.OnTouchListener() {
                @Override
                public boolean onTouch(View v, MotionEvent event) {
                    float X = event.getX();
                    float Y = event.getY();
                    switch (event.getActionMasked()) {
                        case MotionEvent.ACTION_DOWN:
                            Log.d( "surfaceCreated", "action down x="+X );
    
    //                      canvas = surfaceHolder.lockCanvas();
    
                            path.moveTo(X,Y);
    
    
    
                            //  mv.touch_start(X,Y);
                            //  canvas = surfaceHolder.lockCanvas();
    
                            break;
                        case MotionEvent.ACTION_MOVE:
                            Log.d( "surfaceCreated", "action move  x="+X );
    
                            path.lineTo(X,Y);
                            break;
                        case MotionEvent.ACTION_UP:
                            Log.d( "surfaceCreated", "action up  x="+X );
    
                            path.lineTo(event.getX(),event.getY());
    
                            Canvas canvas = surfaceHolder.lockCanvas();
                            canvas.drawPath(path, mPaint);
                            path.reset();
                            surfaceHolder.unlockCanvasAndPost(canvas);
    
                            //  mCanvas.drawLine( downx, downy, upx, upy, mPaint );
                            break;
    
                    }
                    if(path != null){
                        Log.d( "surfaceCreated", "path is not null"+path );
                        Canvas canvas = surfaceHolder.lockCanvas();
                        canvas.drawPath(path, mPaint);
                        surfaceHolder.unlockCanvasAndPost(canvas);
                    }
                    return true;
    
                }
            });
    
    
        }
    
        @Override
        public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
    
        }
    
        @Override
        public void surfaceDestroyed(SurfaceHolder holder) {
    
        }
    }
    

    我怎样才能解决这个问题?以及我如何使表面视图变白,正如你在开始时看到的,它是黑色的。谢谢您!

    0 回复  |  直到 6 年前
        1
  •  3
  •   Brainnovo    5 年前

    1) 背景问题:

    根据:

    https://developer.android.com/reference/android/view/SurfaceView

    要显示的曲面。视图层次结构将负责 与曲面正确合成SurfaceView的任何同级 通常会出现在上面。这可以用来放置 它会对性能产生影响,因为

    基于 xav的 Set the Background Image of a SurfaceView

    为了更改曲面背景色,可以将一个视图(与曲面视图重叠)放置在surfaceView的顶部,surfaceHolder像素格式为transparent。

    2) 奇怪的绘图问题:“线的边缘会自行移动”

    纪尧姆亚当

    3) 示例:

    public class MainActivity extends AppCompatActivity  implements SurfaceHolder.Callback {
    
    private SurfaceView surfaceView;
    private View surfaceBackground;
    private Button b_change_surface_background_color;
    private Button b_clear;
    private Path path;
    private Paint mPaint = new Paint();
    private int[] colors = new int[]{Color.WHITE, Color.GREEN, Color.MAGENTA, Color.BLUE};
    private int currentSurfaceBackgroundColor = Color.WHITE;
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    
        b_change_surface_background_color = (Button) findViewById(R.id.b_change_surface_background_color);
        b_change_surface_background_color.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                int colorIndex = new Random().nextInt(colors.length);
                currentSurfaceBackgroundColor = colors[colorIndex];
                changeSurfaceBackgroundColor(currentSurfaceBackgroundColor);
            }
        });
    
        surfaceView = (SurfaceView) findViewById(R.id.surfaceView);
        surfaceView.setZOrderOnTop(true);
        surfaceView.getHolder().setFormat(PixelFormat.TRANSPARENT);
        surfaceView.getHolder().addCallback(this);
    
        surfaceBackground = (View) findViewById(R.id.surfaceBackground);
    
        mPaint = new Paint();
        mPaint.setAntiAlias(true);
        mPaint.setDither(true);
        mPaint.setColor(Color.BLACK);
        mPaint.setStyle(Paint.Style.STROKE);
        mPaint.setStrokeJoin(Paint.Join.ROUND);
        mPaint.setStrokeCap(Paint.Cap.ROUND);
        mPaint.setStrokeWidth(50);
    }
    
    @SuppressLint("ClickableViewAccessibility")
    @Override
    public void surfaceCreated(SurfaceHolder holder) {
        path = new Path();
        surfaceView.setOnTouchListener(new View.OnTouchListener() {
            @Override
            public boolean onTouch(View v, MotionEvent event) {
                float X = event.getX();
                float Y = event.getY();
                switch (event.getActionMasked()) {
                    case MotionEvent.ACTION_DOWN:
                        path.reset();
                        path.moveTo(X, Y);
                        break;
                    case MotionEvent.ACTION_MOVE:
                        path.lineTo(X, Y);
                        break;
                    case MotionEvent.ACTION_UP:
                        path.lineTo(event.getX(),event.getY());
                        Canvas canvas1 = surfaceView.getHolder().lockCanvas();
                        canvas1.drawPath(path, mPaint);
                        surfaceView.getHolder().unlockCanvasAndPost(canvas1);
                        break;
    
                }
                if(path != null){
                    Canvas canvas = surfaceView.getHolder().lockCanvas();
                    canvas.drawPath(path, mPaint);
                    surfaceView.getHolder().unlockCanvasAndPost(canvas);
                }
                return true;
    
            }
        });
    
    
    }
    
    @Override
    public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
    
    }
    
    @Override
    public void surfaceDestroyed(SurfaceHolder holder) {
    
    }
    
    private void changeSurfaceBackgroundColor(@ColorInt int color) {
        if (surfaceBackground != null) {
            surfaceBackground.setBackgroundColor(color);
        }
    }
    
    }
    

    活动_main.xml文件

    <?xml version="1.0" encoding="utf-8"?>
    <RelativeLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/rl"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
    
    <Button
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="Change Surface Background Color"
        android:textAllCaps="false"
        android:layout_alignParentTop="true"
        android:id="@+id/b_change_surface_background_color">
    </Button>
    
    <SurfaceView
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_below="@id/b_change_surface_background_color"
        android:id="@+id/surfaceView">
    </SurfaceView>
    
    <View
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:id="@+id/surfaceBackground"
        android:layout_below="@id/b_change_surface_background_color"
        android:background="@android:color/white">
    </View>
    
    </RelativeLayout>
    

    4) 输出

    output

        2
  •  1
  •   Guillaume Adam    6 年前

    Canvas canvas = surfaceHolder.lockCanvas();
    canvas.drawPath(path, mPaint);
    path.reset(); // move this line out
    surfaceHolder.unlockCanvasAndPost(canvas);
    

    试着移动 就在之前 .

    path.reset(); // add just above moveTo
    path.moveTo(X,Y);
    
        3
  •  0
  •   Rishabh Dhawan    6 年前

    表面视图实际上在你的窗户后面。它在窗户上打了个洞让你看。所以你可以把东西放在你的窗户上面,但是你的窗户后面什么也看不见。所以背景色不起作用。但是你得到的是带有表面视图的画布,所以你可以提供自己的颜色在画布上绘制。

     private void setRefreshColor(){
        Canvas canvas = surfaceHolder.lockCanvas();
        canvas.drawColor(Color.WHITE);
        surfaceHolder.unlockCanvasAndPost(canvas);
    }