Android App开发之自定义图形中位图与图形互转、剪裁图形内部区域、给图形添加部件的讲解及实战(附源码 简单易懂)

简介: Android App开发之自定义图形中位图与图形互转、剪裁图形内部区域、给图形添加部件的讲解及实战(附源码 简单易懂)

需要图片和源码点赞关注收藏后评论区留言~~~

一、位图与图形互转

Drawable用于在界面上展示图片,Bitmap用于加工图像数据,所以两者之间的转换非常有必要,位图图形BitmapDrawable正是二者之间的桥梁,图形对象与位图对象互相转换都需要它。

图形对象转换成位图对象有个前提,就是该图形原本便是位图格式,否则会转换失败

Drawable类有个setAlpha方法,可以设置图形的灰度值,下面是位图转换成图形对象后再调用setAlpha方法  效果如下

可见不同的灰度比例会有不同的效果

代码如下

Java类

package com.example.picture;
import androidx.appcompat.app.AppCompatActivity;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.drawable.BitmapDrawable;
import android.graphics.drawable.Drawable;
import android.os.Bundle;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.ImageView;
import android.widget.Spinner;
public class DrawableConvertActivity extends AppCompatActivity {
    private Bitmap mOriginBitmap; // 原始位图
    private ImageView iv_picture; // 声明一个图像视图对象
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_drawable_convert);
        iv_picture = findViewById(R.id.iv_picture);
        mOriginBitmap = BitmapFactory.decodeResource(getResources(), R.drawable.mandarin_duck);
        initAlphaSpinner(); // 初始化灰度比例下拉框
    }
    // 初始化灰度比例下拉框
    private void initAlphaSpinner() {
        ArrayAdapter<String> alphaAdapter = new ArrayAdapter<>(this,
                R.layout.item_select, alphaNameArray);
        Spinner sp_alpha = findViewById(R.id.sp_alpha);
        sp_alpha.setPrompt("请选择灰度比例");
        sp_alpha.setAdapter(alphaAdapter);
        sp_alpha.setOnItemSelectedListener(new AlphaSelectedListener());
        sp_alpha.setSelection(0);
    }
    private String[] alphaNameArray = {"1", "0.75", "0.5", "0.25", "0"};
    class AlphaSelectedListener implements AdapterView.OnItemSelectedListener {
        public void onItemSelected(AdapterView<?> arg0, View arg1, int arg2, long arg3) {
            double ratio = Double.parseDouble(alphaNameArray[arg2]);
            // 根据指定位图创建图形对象
            Drawable drawable = new BitmapDrawable(getResources(), mOriginBitmap);
            drawable.setAlpha((int) (255*ratio)); // 设置图形的灰度值
            iv_picture.setImageDrawable(drawable); // 设置图像视图的图形对象
        }
        public void onNothingSelected(AdapterView<?> arg0) {}
    }
}

XML文件

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical" >
    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="40dp">
        <TextView
            android:layout_width="wrap_content"
            android:layout_height="match_parent"
            android:paddingLeft="5dp"
            android:gravity="center"
            android:text="请选择灰度比例"
            android:textColor="@color/black"
            android:textSize="17sp" />
        <Spinner
            android:id="@+id/sp_alpha"
            android:layout_width="0dp"
            android:layout_height="match_parent"
            android:layout_weight="1"
            android:gravity="center"
            android:spinnerMode="dialog" />
    </LinearLayout>
    <ImageView
        android:id="@+id/iv_picture"
        android:layout_width="match_parent"
        android:layout_height="200dp"
        android:scaleType="centerInside" />
</LinearLayout>

二、剪裁图形内部区域

有时候为了美观,并不会显示整个图像,而是显示剪裁后的图像,比如QQ的圆形头像等等。圆形剪裁正是位图图形的拿手好戏,只要调用画笔工具的setShader方法,设置位图着色器即可

下面实现 椭圆 圆角矩形 圆形的剪裁效果

代码如下

Java类

package com.example.picture;
import androidx.appcompat.app.AppCompatActivity;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.drawable.Drawable;
import android.os.Bundle;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.ImageView;
import android.widget.Spinner;
import com.example.picture.widget.CircleDrawable;
import com.example.picture.widget.OvalDrawable;
import com.example.picture.widget.RoundDrawable;
public class DrawableCutActivity extends AppCompatActivity {
    private Bitmap mOriginBitmap; // 原始位图
    private ImageView iv_picture; // 声明一个图像视图对象
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_drawable_cut);
        iv_picture = findViewById(R.id.iv_picture);
        mOriginBitmap = BitmapFactory.decodeResource(getResources(), R.drawable.mandarin_duck);
        initMethodSpinner(); // 初始化剪裁方式下拉框
    }
    // 初始化剪裁方式下拉框
    private void initMethodSpinner() {
        ArrayAdapter<String> methodAdapter = new ArrayAdapter<>(this,
                R.layout.item_select, methodArray);
        Spinner sp_method = findViewById(R.id.sp_method);
        sp_method.setPrompt("请选择剪裁方式");
        sp_method.setAdapter(methodAdapter);
        sp_method.setOnItemSelectedListener(new MethodSelectedListener());
        sp_method.setSelection(0);
    }
    private String[] methodArray = {"不裁剪", "圆形剪裁", "椭圆剪裁", "圆角矩形剪裁"};
    class MethodSelectedListener implements AdapterView.OnItemSelectedListener {
        public void onItemSelected(AdapterView<?> arg0, View arg1, int arg2, long arg3) {
            if (arg2 == 0) { // 不裁剪
                iv_picture.setImageBitmap(mOriginBitmap); // 设置图像视图的位图对象
            } else if (arg2 == 1) { // 圆形剪裁
                Drawable drawable = new CircleDrawable(DrawableCutActivity.this, mOriginBitmap);
                iv_picture.setImageDrawable(drawable); // 设置图像视图的图形对象
            } else if (arg2 == 2) { // 椭圆剪裁
                Drawable drawable = new OvalDrawable(DrawableCutActivity.this, mOriginBitmap);
                iv_picture.setImageDrawable(drawable); // 设置图像视图的图形对象
            } else if (arg2 == 3) { // 圆角矩形剪裁
                Drawable drawable = new RoundDrawable(DrawableCutActivity.this, mOriginBitmap);
                iv_picture.setImageDrawable(drawable); // 设置图像视图的图形对象
            }
        }
        public void onNothingSelected(AdapterView<?> arg0) {}
    }
}

XML文件

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical" >
    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="40dp">
        <TextView
            android:layout_width="wrap_content"
            android:layout_height="match_parent"
            android:paddingLeft="5dp"
            android:gravity="center"
            android:text="请选择剪裁方式"
            android:textColor="@color/black"
            android:textSize="17sp" />
        <Spinner
            android:id="@+id/sp_method"
            android:layout_width="0dp"
            android:layout_height="match_parent"
            android:layout_weight="1"
            android:gravity="center"
            android:spinnerMode="dialog" />
    </LinearLayout>
    <ImageView
        android:id="@+id/iv_picture"
        android:layout_width="match_parent"
        android:layout_height="200dp"
        android:scaleType="centerInside" />
</LinearLayout>

三、给图形添加小部件

除了剪裁图形之外,还能给图形添加小部件,比如文字,图标等等,原来自定义图形类的时候,重写draw方法等同于重写视图的onDraw方法,因此在draw方法中就可以添加图案。

此处可以设置个性化字体,用到了字体工具Typeface的createFromAsset方法,该方法允许从assets目录下的字体文件生成字体对象,然后调用画笔对象的setTypeface方法,就能使文字呈现对应的字体样式

同样能给图片加水印 效果如下

代码如下

Java类

package com.example.picture;
import androidx.appcompat.app.AppCompatActivity;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Typeface;
import android.os.Bundle;
import android.os.Handler;
import android.os.Looper;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.ImageView;
import android.widget.Spinner;
import com.example.picture.widget.MarkTextDrawable;
public class DrawableTextActivity extends AppCompatActivity {
    private final static String TAG = "DrawableTextActivity";
    private Bitmap mOriginBitmap; // 原始位图
    private ImageView iv_picture; // 声明一个图像视图对象
    private Typeface[] mTypeFaceArray; // 字体数组
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_drawable_text);
        iv_picture = findViewById(R.id.iv_picture);
        mOriginBitmap = BitmapFactory.decodeResource(getResources(), R.drawable.mandarin_duck);
        iv_picture.setImageBitmap(mOriginBitmap); // 设置图像视图的位图对象
        new Handler(Looper.myLooper()).post(() -> loadTypeFace()); // 加载字体文件
    }
    // 加载字体文件
    private void loadTypeFace() {
        mTypeFaceArray = new Typeface[fontFileArray.length];
        for (int i=0; i<fontFileArray.length; i++) {
            String fontFile = "fonts/" + fontFileArray[i] + ".ttf";
            // 根据assets目录下的字体文件创建字体对象
            mTypeFaceArray[i] = Typeface.createFromAsset(getAssets(), fontFile);
        }
        initFontSpinner(); // 初始化中文字体下拉框
    }
    // 初始化中文字体下拉框
    private void initFontSpinner() {
        ArrayAdapter<String> fontAdapter = new ArrayAdapter<>(this,
                R.layout.item_select, fontNameArray);
        Spinner sp_font = findViewById(R.id.sp_font);
        sp_font.setPrompt("请选择中文字体");
        sp_font.setAdapter(fontAdapter);
        sp_font.setOnItemSelectedListener(new FontSelectedListener());
        sp_font.setSelection(0);
    }
    private String[] fontNameArray = {"常规", "仿宋", "楷体", "隶书", "黑体", "幼圆",
            "华文行楷", "华文新魏", "华文彩云", "华文琥珀", "方正舒体", "方正姚体"};
    private String[] fontFileArray = {"Regular", "FangSong", "KaiTi", "LiShu", "HeiTi", "YouYuan",
            "HangKai", "XinWei", "CaiYun", "HuPo", "ShuTi", "YaoTi"};
    class FontSelectedListener implements AdapterView.OnItemSelectedListener {
        public void onItemSelected(AdapterView<?> arg0, View arg1, int arg2, long arg3) {
            // 根据指定位图创建水印图形对象
            MarkTextDrawable drawable = new MarkTextDrawable(DrawableTextActivity.this, mOriginBitmap);
            drawable.setMarkerText("鸳鸯戏水", mTypeFaceArray[arg2]); // 设置水印文字及其字体
            iv_picture.setImageDrawable(drawable); // 设置图像视图的图形对象
        }
        public void onNothingSelected(AdapterView<?> arg0) {}
    }
}

XML文件

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">
    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="40dp">
        <TextView
            android:layout_width="wrap_content"
            android:layout_height="match_parent"
            android:paddingLeft="5dp"
            android:gravity="center"
            android:text="请选择中文字体"
            android:textColor="@color/black"
            android:textSize="17sp" />
        <Spinner
            android:id="@+id/sp_font"
            android:layout_width="0dp"
            android:layout_height="match_parent"
            android:layout_weight="1"
            android:gravity="center"
            android:spinnerMode="dialog" />
    </LinearLayout>
    <ImageView
        android:id="@+id/iv_picture"
        android:layout_width="match_parent"
        android:layout_height="200dp"
        android:scaleType="centerInside" />
</LinearLayout>

创作不易 觉得有帮助请 点赞关注收藏~~~

相关文章
|
2天前
|
JavaScript 前端开发 Android开发
【03】仿站技术之python技术,看完学会再也不用去购买收费工具了-修改整体页面做好安卓下载发给客户-并且开始提交网站公安备案-作为APP下载落地页文娱产品一定要备案-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-优雅草卓伊凡
【03】仿站技术之python技术,看完学会再也不用去购买收费工具了-修改整体页面做好安卓下载发给客户-并且开始提交网站公安备案-作为APP下载落地页文娱产品一定要备案-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-优雅草卓伊凡
34 13
【03】仿站技术之python技术,看完学会再也不用去购买收费工具了-修改整体页面做好安卓下载发给客户-并且开始提交网站公安备案-作为APP下载落地页文娱产品一定要备案-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-优雅草卓伊凡
|
4天前
|
数据采集 JavaScript Android开发
【02】仿站技术之python技术,看完学会再也不用去购买收费工具了-本次找了小影-感觉页面很好看-本次是爬取vue需要用到Puppeteer库用node.js扒一个app下载落地页-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-优雅草卓伊凡
【02】仿站技术之python技术,看完学会再也不用去购买收费工具了-本次找了小影-感觉页面很好看-本次是爬取vue需要用到Puppeteer库用node.js扒一个app下载落地页-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-优雅草卓伊凡
29 7
【02】仿站技术之python技术,看完学会再也不用去购买收费工具了-本次找了小影-感觉页面很好看-本次是爬取vue需要用到Puppeteer库用node.js扒一个app下载落地页-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-优雅草卓伊凡
|
4天前
|
JavaScript 搜索推荐 Android开发
【01】仿站技术之python技术,看完学会再也不用去购买收费工具了-用python扒一个app下载落地页-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-客户的麻将软件需要下载落地页并且要做搜索引擎推广-本文用python语言快速开发爬取落地页下载-优雅草卓伊凡
【01】仿站技术之python技术,看完学会再也不用去购买收费工具了-用python扒一个app下载落地页-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-客户的麻将软件需要下载落地页并且要做搜索引擎推广-本文用python语言快速开发爬取落地页下载-优雅草卓伊凡
23 8
【01】仿站技术之python技术,看完学会再也不用去购买收费工具了-用python扒一个app下载落地页-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-客户的麻将软件需要下载落地页并且要做搜索引擎推广-本文用python语言快速开发爬取落地页下载-优雅草卓伊凡
|
9天前
|
开发框架 缓存 搜索推荐
PiliPala:开源项目真香,B站用户狂喜!这个开源APP竟能自定义主题+去广告?PiliPala隐藏功能大揭秘
嗨,大家好,我是小华同学。PiliPala 是一个基于 Flutter 开发的 BiliBili 第三方客户端,提供流畅、个性化的使用体验。核心功能包括视频浏览与推荐、用户互动、丰富的播放设置、多维度搜索和个性化主题等。相比官方客户端,PiliPala 功能更丰富、性能更优、界面更美观。
60 14
|
14天前
|
Dart 前端开发 Android开发
【09】flutter首页进行了完善-采用android studio 进行真机调试开发-增加了直播间列表和短视频人物列表-增加了用户中心-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
【09】flutter首页进行了完善-采用android studio 进行真机调试开发-增加了直播间列表和短视频人物列表-增加了用户中心-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
37 4
【09】flutter首页进行了完善-采用android studio 进行真机调试开发-增加了直播间列表和短视频人物列表-增加了用户中心-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
|
16天前
|
前端开发 Java Shell
【08】flutter完成屏幕适配-重建Android,增加GetX路由,屏幕适配,基础导航栏-多版本SDK以及gradle造成的关于fvm的使用(flutter version manage)-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
【08】flutter完成屏幕适配-重建Android,增加GetX路由,屏幕适配,基础导航栏-多版本SDK以及gradle造成的关于fvm的使用(flutter version manage)-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
121 20
【08】flutter完成屏幕适配-重建Android,增加GetX路由,屏幕适配,基础导航栏-多版本SDK以及gradle造成的关于fvm的使用(flutter version manage)-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
|
24天前
|
Dart 前端开发 容器
【07】flutter完成主页-完成底部菜单栏并且做自定义组件-完整短视频仿抖音上下滑动页面-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草央千澈
【07】flutter完成主页-完成底部菜单栏并且做自定义组件-完整短视频仿抖音上下滑动页面-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草央千澈
75 18
【07】flutter完成主页-完成底部菜单栏并且做自定义组件-完整短视频仿抖音上下滑动页面-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草央千澈
|
27天前
|
Dart 前端开发
【05】flutter完成注册页面完善样式bug-增加自定义可复用组件widgets-严格规划文件和目录结构-规范入口文件-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草央千澈
【05】flutter完成注册页面完善样式bug-增加自定义可复用组件widgets-严格规划文件和目录结构-规范入口文件-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草央千澈
116 75
【05】flutter完成注册页面完善样式bug-增加自定义可复用组件widgets-严格规划文件和目录结构-规范入口文件-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草央千澈
|
29天前
|
缓存 前端开发 Android开发
【04】flutter补打包流程的签名过程-APP安卓调试配置-结构化项目目录-完善注册相关页面-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程
【04】flutter补打包流程的签名过程-APP安卓调试配置-结构化项目目录-完善注册相关页面-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程
79 12
【04】flutter补打包流程的签名过程-APP安卓调试配置-结构化项目目录-完善注册相关页面-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程
|
1月前
|
Dart 前端开发 Android开发
【02】写一个注册页面以及配置打包选项打包安卓apk测试—开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草央千澈
【02】写一个注册页面以及配置打包选项打包安卓apk测试—开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草央千澈
36 1
【02】写一个注册页面以及配置打包选项打包安卓apk测试—开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草央千澈

热门文章

最新文章

  • 1
    如何修复 Android 和 Windows 不支持视频编解码器的问题?
  • 2
    Android历史版本与APK文件结构
  • 3
    当flutter react native 等混开框架-并且用vscode-idea等编译器无法打包apk,打包安卓不成功怎么办-直接用android studio如何打包安卓apk -重要-优雅草卓伊凡
  • 4
    Android经典面试题之Kotlin中Lambda表达式和匿名函数的区别
  • 5
    Cellebrite UFED 4PC 7.71 (Windows) - Android 和 iOS 移动设备取证软件
  • 6
    MNN-LLM App:在手机上离线运行大模型,阿里巴巴开源基于 MNN-LLM 框架开发的手机 AI 助手应用
  • 7
    【11】flutter进行了聊天页面的开发-增加了即时通讯聊天的整体页面和组件-切换-朋友-陌生人-vip开通详细页面-即时通讯sdk准备-直播sdk准备-即时通讯有无UI集成的区别介绍-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
  • 8
    原生鸿蒙版小艺APP接入DeepSeek-R1,为HarmonyOS应用开发注入新活力
  • 9
    【Azure App Service】基于Linux创建的App Service是否可以主动升级内置的Nginx版本呢?
  • 10
    【08】flutter完成屏幕适配-重建Android,增加GetX路由,屏幕适配,基础导航栏-多版本SDK以及gradle造成的关于fvm的使用(flutter version manage)-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
  • 1
    【03】仿站技术之python技术,看完学会再也不用去购买收费工具了-修改整体页面做好安卓下载发给客户-并且开始提交网站公安备案-作为APP下载落地页文娱产品一定要备案-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-优雅草卓伊凡
    34
  • 2
    【02】仿站技术之python技术,看完学会再也不用去购买收费工具了-本次找了小影-感觉页面很好看-本次是爬取vue需要用到Puppeteer库用node.js扒一个app下载落地页-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-优雅草卓伊凡
    29
  • 3
    【01】仿站技术之python技术,看完学会再也不用去购买收费工具了-用python扒一个app下载落地页-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-客户的麻将软件需要下载落地页并且要做搜索引擎推广-本文用python语言快速开发爬取落地页下载-优雅草卓伊凡
    23
  • 4
    【Azure Function】Function App门户上的Test/Run返回错误:Failed to fetch
    31
  • 5
    陪玩APP推送配置:陪玩系统手机锁屏收不到推送?可能是这些原因!解决方案来了!
    34
  • 6
    小游戏源码开发之可跨app软件对接是如何设计和开发的
    33
  • 7
    原生鸿蒙版小艺APP接入DeepSeek-R1,为HarmonyOS应用开发注入新活力
    135
  • 8
    PiliPala:开源项目真香,B站用户狂喜!这个开源APP竟能自定义主题+去广告?PiliPala隐藏功能大揭秘
    60
  • 9
    语音app系统软件源码开发搭建新手启蒙篇
    44
  • 10
    MNN-LLM App:在手机上离线运行大模型,阿里巴巴开源基于 MNN-LLM 框架开发的手机 AI 助手应用
    884