广告
返回顶部
首页 > 资讯 > 精选 >Android实现绘画板功能的示例分析
  • 692
分享到

Android实现绘画板功能的示例分析

2023-06-15 05:06:10 692人浏览 八月长安
摘要

这篇文章主要介绍Android实现绘画板功能的示例分析,文中介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们一定要看完!实现流程:        一、预期效果&nbs

这篇文章主要介绍Android实现绘画板功能的示例分析,文中介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们一定要看完!

实现流程:

        一、预期效果
        二、设置横竖屏切换
        三、确定布局
        四、自定义滑动条
        五、绘画区域
        六、MainActivity

实现步骤:

一、预期效果

Android实现绘画板功能的示例分析

二、设置横竖屏切换

screenOrientation属性       作用
user用户当前设置的方向。
unspecified由系统选择显示方向,不同的设备可能会有所不同。(旋转手机,界面会跟着旋转)
landscape限制界面为横屏,旋转屏幕也不会改变当前状态。
portrait限制界面为竖屏,旋转屏幕也不会改变当前状态。
behind与前一个activity方向相同。
sensor根据传感器定位方向,旋转手机90度,180,270,360,界面都会发生变化。
nosensor不由传感器确定方向。旋转设备的时候,界面不会跟着旋转。初始界面方向由系统提供。
sensorLandscape(横屏的旋转,不会出现竖屏的现象)根据传感器定位方向,旋转手机180度界面旋转。一般横屏游戏会是这个属性。
sensorPortrait(竖屏的旋转,不会出现横屏的现象)根据传感器定位方向,旋转手机180度界面会旋转。

三、确定布局

因为横竖屏切换后控件的宽高都是不一样的,也就是不固定的,不能用线性布局,而是根据相对位置进行布局。先用constraintLayout约束,再将小控件组合成一个线性布局,然后对整个线性布局进行相对布局。

Android实现绘画板功能的示例分析

<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="Http://schemas.android.com/apk/res/android"    xmlns:app="http://schemas.android.com/apk/res-auto"    xmlns:tools="http://schemas.android.com/tools"    android:layout_width="match_parent"    android:layout_height="match_parent"    tools:context=".MainActivity">    <androidx.constraintlayout.widget.ConstraintLayout        android:layout_width="match_parent"        android:layout_height="0dp"        app:layout_constraintTop_toTopOf="parent"        app:layout_constraintBottom_toTopOf="@id/operation"        >        <!--滑动条-->        <com.example.a16drawboard.Slider            android:id="@+id/slider"            android:layout_width="20dp"            android:layout_height="match_parent"            android:layout_marginLeft="20dp"            android:layout_marginTop="20dp"            android:layout_marginBottom="20dp"            app:layout_constraintLeft_toLeftOf="parent"            />        <!--画板-->        <com.example.a16drawboard.DrawBoardView            android:id="@+id/board"            android:layout_width="0dp"            android:layout_height="match_parent"            app:layout_constraintLeft_toRightOf="@id/slider"            app:layout_constraintRight_toLeftOf="@id/color"/>    <!--选颜色-->        <LinearLayout            android:id="@+id/color"            android:layout_width="60dp"            android:layout_height="match_parent"            android:orientation="vertical"            android:layout_marginRight="20dp"            app:layout_constraintRight_toRightOf="parent"            android:gravity="center">            <Button                android:layout_width="match_parent"                android:layout_height="50dp"                android:background="@color/colorAccent"                android:onClick="choiceColor"/>            <Button                android:layout_width="match_parent"                android:layout_height="50dp"                android:background="@color/colorPrimary"                android:onClick="choiceColor"/>            <Button                android:layout_width="match_parent"                android:layout_height="50dp"                android:background="#f00"                android:onClick="choiceColor"/>            <Button                android:layout_width="match_parent"                android:layout_height="50dp"                android:background="#000"                android:onClick="choiceColor"/>        </LinearLayout>    </androidx.constraintlayout.widget.ConstraintLayout>    <LinearLayout        android:id="@+id/operation"        android:layout_width="match_parent"        android:layout_height="60dp"        android:background="#f00"        android:orientation="horizontal"        app:layout_constraintBottom_toBottomOf="parent"        android:gravity="center">        <Button            android:layout_width="70dp"            android:layout_height="wrap_content"            android:text="撤销"            android:onClick="GoBack"/>        <Button            android:layout_width="70dp"            android:layout_height="wrap_content"            android:text="清空"            android:onClick="clear"/>        <Button            android:layout_width="70dp"            android:layout_height="wrap_content"            android:text="橡皮擦"            android:onClick="eraser"/>        <Button            android:layout_width="70dp"            android:layout_height="wrap_content"            android:text="保存"            android:onClick="save"/>        <Button            android:layout_width="70dp"            android:layout_height="wrap_content"            android:text="上一步"            android:onClick="lastStep"/>    </LinearLayout></androidx.constraintlayout.widget.ConstraintLayout>

四、自定义滑动条

public class Slider extends View {    private int lineSize = 6; // 线条的粗细    private int lineColor = Color.BLACK;// 默认线条颜色    private Paint linePaint;    private Paint circlePaint; // 圆点画笔    private int thumbColor = Color.MAGENTA; // 圆点颜色    private int cx; // 中心点x    private int cy; // 中心点y    private int radius; // 小圆点半径    private int thumbScale = 4; // 圆点缩放尺寸    private float position; // 触摸点的坐标    private Paint progressPaint; // 进度条进度的画笔    private int progressColor = Color.MAGENTA; // 进度条颜色    public static int PROGRESS = 0; // 进度条    public static int SLIDER = 1; // 滑动条    private int style = PROGRESS; // 用户选择的样式,默认为进度条    public int max = 100; // 设置最大值    public float progress; // 进度值    private OnSliderChangeListener onSliderChangeListener; // 滑动改变监听者    public Slider(Context context) {        super(context);    }    public Slider(Context context, AttributeSet attrs) {        super(context, attrs);        init();    }    private void init(){        // 背景线        linePaint = new Paint(Paint.ANTI_ALIAS_FLAG);        linePaint.setColor(lineColor);        linePaint.setStrokeWidth(lineSize);        // 圆点        circlePaint = new Paint(Paint.ANTI_ALIAS_FLAG);        circlePaint.setColor(thumbColor);        circlePaint.setStyle(Paint.Style.FILL);        // 进度条        progressPaint = new Paint(Paint.ANTI_ALIAS_FLAG);        progressPaint.setColor(progressColor);        progressPaint.setStrokeWidth(lineSize);    }    @Override    protected void onDraw(canvas canvas) {        if (getWidth() > getHeight()){            // 横着            canvas.drawLine(0, getHeight()/2, getWidth(), getHeight()/2, linePaint);            if (position>0){                canvas.drawLine(0, getHeight()/2, position, getHeight()/2, progressPaint);            }            radius = getHeight()/thumbScale;            cy = getHeight()/2;            // 确定cx的值            if (position < radius) {                cx = radius;            }else if (position > getWidth()-radius){                cx = getWidth()-radius;            }else {                cx = (int) position;            }        }else{            // 竖着            canvas.drawLine(getWidth()/2, 0, getWidth()/2, getHeight(), linePaint);            if (position>0){                canvas.drawLine(getWidth()/2, 0, getWidth()/2, position, progressPaint);            }            radius = getWidth()/thumbScale;            cx = getWidth()/2;            // 确定中心点cy的值            if (position<radius){                cy = radius;            }else if (position > getHeight()-radius){                cy = getHeight()-radius;            }else {                cy = (int) position;            }        }        // 画小圆点        if (style == SLIDER){            canvas.drawCircle(cx,cy,radius,circlePaint);        }    }    @Override    public boolean onTouchEvent(MotionEvent event) {        switch (event.getAction()){            case MotionEvent.ACTION_DOWN:                // 圆点放大                thumbScale = 2;                // 点下去就到那个位置                if (getWidth()>getHeight()){                    // 横向时,y不变 x改变                    position = event.getX();                }else {                    // 纵向时,x不变 y改变                    position = event.getY();                }                callback();                break;            case MotionEvent.ACTION_MOVE:                // 获取当前触摸点的值XY                if (getWidth()>getHeight()){                    // 横向时,y不变 x改变                    position = event.getX();                    if (position<0){                        progress = 0;                    }else if (position>getWidth()){                        position = getWidth();                    }                }else {                    // 竖着时,x不变 y改变                    position = event.getY();                    if (position<0){                        progress = 0;                    }else if (position>getHeight()){                        position = getHeight();                    }                }                callback();                break;            case MotionEvent.ACTION_UP:                thumbScale = 4;                break;        }        if (style == SLIDER){            invalidate();        }        return true;    }    private void callback(){        if (onSliderChangeListener != null){            if (getWidth()>getHeight()){                progress = position/getWidth();            }else {                progress = position/getHeight();            }            onSliderChangeListener.progressChange(progress*max);        }    }    public int getStyle() {        return style;    }    public void setStyle(int style) {        this.style = style;    }    public float getProgress() {        return progress;    }    public void setProgress(int progress){        // 计算比例        float rate = (float)(progress*1.0/max);        setProgress(rate);    }    public void setProgress(float progress) {        this.progress = progress;        if (progress <1.001) {            // 将进度值转化为控件中的尺寸位置            if (getWidth() > getHeight()) {                position = progress * getWidth();            } else {                position = progress * getHeight();            }            invalidate();        }    }    @Override    protected void onSizeChanged(int w, int h, int oldw, int oldh) {        if (getWidth() > getHeight()) {            position = progress * getWidth();        } else {            position = progress * getHeight();        }    }    public void setMax(int max) {        this.max = max;    }    public interface OnSliderChangeListener{        void progressChange(float progress);    }    public void setOnSliderChangeListener(OnSliderChangeListener onSliderChangeListener) {        this.onSliderChangeListener = onSliderChangeListener;    }}

五、绘画区域

public class DrawBoardView extends View {    private ArrayList<Graph> graphs; // 操作数组    private ArrayList<Graph> orginalGraphs; // 原始数组    private int lineColor = Color.BLACK;    private int lineSize = 5;    Path mPath;    public DrawBoardView(Context context) {        super(context);    }    public DrawBoardView(Context context, @Nullable AttributeSet attrs) {        super(context, attrs);        init();    }    private void init(){        // 初始化数组        graphs = new ArrayList<>();        orginalGraphs = new ArrayList<>();        setBackgroundColor(Color.WHITE);    }    @Override    protected void onDraw(Canvas canvas) {        // 遍历数组        Iterator<Graph> iterator = graphs.iterator();        while (iterator.hasNext()){            // 从集合中获取一个图形对象            Graph line = iterator.next();            // 绘制图形            canvas.drawPath(line.path,line.paint);        }    }    @Override    public boolean onTouchEvent(MotionEvent event) {        switch (event.getAction()){            case MotionEvent.ACTION_DOWN:                // 创建这条线对应的paint和path                Paint mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);                mPaint.setColor(lineColor);                mPaint.setStrokeWidth(lineSize);                mPaint.setStyle(Paint.Style.STROKE);                mPath = new Path();                // 设置图形的起点                mPath.moveTo(event.getX(),event.getY());                // 保存当前这个图形的详细信息                Graph temp = new Graph(mPaint,mPath);                graphs.add(temp);                orginalGraphs.add(temp);                break;            case MotionEvent.ACTION_MOVE:                // 连接从path终点到当前触摸点的线                mPath.lineTo(event.getX(),event.getY());                break;            case MotionEvent.ACTION_UP:                break;        }        invalidate();        return true;    }    // 用私有类来管理图形的画笔和路径    private class Graph{        Paint paint;        Path path;        public Graph(Paint paint,Path path){            this.paint=paint;            this.path=path;        }    }    // 删除最后一个图形  撤销    public void removeLast(){        if (graphs.size() >0){            graphs.remove(graphs.size()-1);            invalidate();        }    }    // 删除所有 清空    public void removeAll(){        graphs.clear();        invalidate();    }    // 还原上一步    public void returnToLastStep(){        // 判断缓存中是否有        if (graphs.size() < orginalGraphs.size()){            // 获取上一步的索引值            int index = graphs.size()-1+1;            // 从缓存中获取index,添加到操作数组中            graphs.add(orginalGraphs.get(index));            invalidate();        }    }    public int getLineSize() {        return lineSize;    }    public void setLineSize(int lineSize) {        this.lineSize = lineSize;    }    public int getLineColor() {        return lineColor;    }    public void setLineColor(int lineColor) {        this.lineColor = lineColor;    }}

六、MainActivity

public class MainActivity extends AppCompatActivity {    private DrawBoardView boardView;    @Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.activity_main);        // 获取画板对象        boardView = findViewById(R.id.board);        // 获取滑动条对象        final Slider slider = findViewById(R.id.slider);        slider.setStyle(Slider.SLIDER);        slider.setMax(30);        slider.setOnSliderChangeListener(new Slider.OnSliderChangeListener() {            @Override            public void progressChange(float progress) {                boardView.setLineSize((int) progress);            }        });        slider.setProgress(boardView.getLineSize());    }    @Override    public void onWindowFocusChanged(boolean hasFocus) {        super.onWindowFocusChanged(hasFocus);    }    @Override    protected void onStart() {        super.onStart();    }    @Override    protected void onResume() {        super.onResume();        // 设置横屏        setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_FULL_SENSOR);    }    @Override    protected void onPause() {        super.onPause();    }    @Override    protected void onStop() {        super.onStop();    }    // 选择颜色 获取按钮上面的背景颜色    public void choiceColor(View view) {        // 获取按钮上面的背景颜色        ColorDrawable drawable = (ColorDrawable) view.getBackground();        // 获取颜色        boardView.setLineColor(drawable.getColor());    }    // 撤回    public void goBack(View view) {        boardView.removeLast();    }    // 清空    public void clear(View view) {        boardView.removeAll();    }    // 橡皮擦    public void eraser(View view) {        // 获取画板的drawable        ColorDrawable drawable = (ColorDrawable) boardView.getBackground();        // 设置线条颜色和背景色相同        if (drawable != null){            boardView.setLineColor(drawable.getColor());        }else {            boardView.setLineColor(Color.TRANSPARENT);        }    }    // 保存    public void save(View view) {    }    // 还原    public void lastStep(View view) {        boardView.returnToLastStep();    }}

到这里就结束啦。

Android是什么

Android是一种基于linux内核的自由及开放源代码的操作系统,主要使用于移动设备,如智能手机和平板电脑,由美国Google公司和开放手机联盟领导及开发

以上是“Android实现绘画板功能的示例分析”这篇文章的所有内容,感谢各位的阅读!希望分享的内容对大家有帮助,更多相关知识,欢迎关注编程网精选频道!

--结束END--

本文标题: Android实现绘画板功能的示例分析

本文链接: https://www.lsjlt.com/news/277808.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • Android实现绘画板功能的示例分析
    这篇文章主要介绍Android实现绘画板功能的示例分析,文中介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们一定要看完!实现流程:        一、预期效果&nbs...
    99+
    2023-06-15
  • Android实现绘画板功能
    目录实现流程:实现步骤:一、预期效果二、设置横竖屏切换三、确定布局四、自定义滑动条五、绘画区域六、MainActivity实现流程:     ...
    99+
    2022-11-12
  • Android如何实现绘画板功能
    这篇文章主要介绍了Android如何实现绘画板功能,具有一定借鉴价值,感兴趣的朋友可以参考下,希望大家阅读完这篇文章之后大有收获,下面让小编带着大家一起了解一下。实现流程:     &nbs...
    99+
    2023-06-15
  • Android实现画板功能(一)
    本文实例为大家分享了Android实现画板功能的具体代码,供大家参考,具体内容如下 前言 最近看到了一些Android手写相关的功能,比如说: 钉钉手写签名功能,输入法手写功能,笔记...
    99+
    2022-11-12
  • Android实现画板功能(二)
    本文实例为大家分享了Android实现画板功能的具体代码,讲解使用imageView,bitmap的方式实现画板功能,供大家参考,具体内容如下 前言 在上一篇Android实现画板功...
    99+
    2022-11-12
  • Android自定义SurfaceView实现画板功能
    接触了这么久的View,总不能一直停留在View里,现在开始呢,就要学习一个新的知识点:SurfaceView,实际上SurfaceView与View的原理都差不多,只是效率和...
    99+
    2022-06-06
    surfaceview 画板 Android
  • Android实现画板、写字板功能(附源码下载)
    前言 本文给大家分享一个使用Android开发写字板功能Dem、简单操作内存中的图像、对图像进行简单的处理、绘制直线、以达到写字板的效果 效果图如下 XML布局代码 &...
    99+
    2022-06-06
    源码下载 写字板 画板 源码 Android
  • android实现简单的画画板实例代码
    直接看代码,注释都写清楚了 代码如下:public class MainActivity extends Activity { private ImageView ...
    99+
    2022-06-06
    画板 Android
  • Android自定义View实现简易画板功能
    本文实例为大家分享了Android自定义View实现简易画板的具体代码,供大家参考,具体内容如下 自定义VIew实现简易画板效果,功能包括清空、选择颜色,选择大小,效果如下 画板布...
    99+
    2022-11-13
  • webpack实用小功能的示例分析
    这篇文章主要介绍webpack实用小功能的示例分析,文中介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们一定要看完!webpack比较实用的功能1.overlayoverlay属于devServer的属...
    99+
    2022-10-19
  • node.js+express留言板功能实现示例
    目录留言板所需类库开源项目项目结构留言板 基于nodejs+express+art-template的留言板功能。包含列表界面、添加界面和发送留言功能。 所需类库 直接copy以下p...
    99+
    2022-11-12
  • Android动画之小球拟合动画的示例分析
    这篇文章给大家分享的是有关Android动画之小球拟合动画的示例分析的内容。小编觉得挺实用的,因此分享给大家做个参考,一起跟随小编过来看看吧。Android动画之小球拟合动画实例实现效果:动画组成:通过三阶贝塞尔曲线来拟合圆,拟合系数的由来...
    99+
    2023-05-31
    android
  • Angular5.1新功能的示例分析
    这篇文章主要介绍Angular5.1新功能的示例分析,文中介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们一定要看完!新特性Angular Material和CDK稳定版CLI中支持Service Wo...
    99+
    2022-10-19
  • Android开发中项目实现一个画板功能
    这期内容当中小编将会给大家带来有关Android开发中项目实现一个画板功能,文章内容丰富且以专业的角度为大家分析和叙述,阅读完这篇文章希望大家可以有所收获。效果图如下XML布局代码<RelativeLayout xmlns:andro...
    99+
    2023-05-31
    android roi
  • Android编程实现分页加载ListView功能示例
    本文实例讲述了Android编程实现分页加载ListView功能。分享给大家供大家参考,具体如下: package eoe.listview; import android....
    99+
    2022-06-06
    示例 listview 分页 Android
  • Android实现刮刮乐示例分析
    微信公众号有很多都做刮刮乐的活动,本文就实现了刮刮乐的效果,具体代码如下: 首先要做一个类似橡皮擦的东西吧,然后才能把纸上的笔迹擦除   public c...
    99+
    2022-06-06
    示例 Android
  • Android实现登录功能demo示例
    本文实例讲述了Android实现登录功能的方法。分享给大家供大家参考,具体如下: 安卓,在小编实习之前的那段岁月里面,小编都没有玩儿过,如果说玩儿过,那就是安卓手机了,咳咳,敲...
    99+
    2022-06-06
    demo Android
  • angularjs结合pagination插件实现分页功能的示例分析
    小编给大家分享一下angularjs结合pagination插件实现分页功能的示例分析,希望大家阅读完这篇文章之后都有所收获,下面让我们一起去探讨吧!angularjs与pagination插件可以完美实现...
    99+
    2022-10-19
  • Android实现视频的画中画功能
    简介: Android 8.0(API 级别 26)允许以画中画 (PIP) 模式启动 Activity。画中画是一种特殊类型的多窗口模式,最常用于视频播放。使用该模式,用户可以通过...
    99+
    2022-11-12
  • Android怎么自定义View实现简易画板功能
    这篇文章主要介绍“Android怎么自定义View实现简易画板功能”的相关知识,小编通过实际案例向大家展示操作过程,操作方法简单快捷,实用性强,希望这篇“Android怎么自定义View实现简易画板功能”文章能帮助大家解决问题。自定义VIe...
    99+
    2023-06-30
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作