手机AIDE使用OpenCV



需要使用OpenCV.jar和so文件

android 复制代码
package com.example.application;

import android.app.Activity;
import android.os.Bundle;
import android.graphics.BitmapFactory;
import android.graphics.Bitmap;
import android.view.View;
import java.util.ArrayList;
import android.widget.Toast;
import java.io.ByteArrayOutputStream;
import java.io.PrintStream;
import java.io.File;
import java.io.RandomAccessFile;
import java.util.Queue;
import android.graphics.Color;
import java.util.LinkedList;
import org.opencv.android.OpenCVLoader;
import org.opencv.core.Mat;
import org.opencv.android.Utils;
import org.opencv.imgproc.Imgproc;
import org.opencv.core.MatOfPoint;
import java.util.List;
import org.opencv.core.Scalar;
import org.opencv.core.Core;


public class MainActivity extends Activity {
    private huabu hb;
	private Bitmap bitmap;
	static {
		// 加载OpenCV的.so库(库名与文件前缀一致,libopencv_java4.so对应"opencv_java4")
		System.loadLibrary("opencv_java4");
	}
	@Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        hb = findViewById(R.id.huabu);
		if (!OpenCVLoader.initDebug()) {
			Toast.makeText(this, "OpenCV初始化失败", Toast.LENGTH_SHORT).show();
		}
		String str="/storage/emulated/0/脚本/Aj图片/screenshot_1759871209890.png";
		bitmap = BitmapFactory.decodeFile(str);
	}
	public void huiduhua(View v) {
		processImage();
	}
	private void processImage() {
		// 这里假设你要处理的图片在手机存储的指定路径,替换为实际图片路径
		if (bitmap == null) {
			Toast.makeText(this, "无法读取图片", Toast.LENGTH_SHORT).show();
			return;
		}
		 Mat mat = new Mat();
		 Utils.bitmapToMat(bitmap, mat);
		 Mat grayMat = new Mat();
		 Imgproc.cvtColor(mat, grayMat, Imgproc.COLOR_BGR2GRAY);
		 Bitmap grayBitmap = Bitmap.createBitmap(grayMat.cols(), grayMat.rows(), Bitmap.Config.ARGB_8888);
		 Utils.matToBitmap(grayMat, grayBitmap);
		 hb.setbittmap(grayBitmap);
	}
	public void hualunkuo(View v) {
	    //boolean a=colors.isSimilar("#000000", "#000010", 25);
		detectBlackFonts();
	}
	// 识别黑色字体的核心方法
	private void detectBlackFonts() {
		Bitmap originalBitmap = this.bitmap;
		if (originalBitmap == null) {
			Toast.makeText(this, "图片读取失败", Toast.LENGTH_SHORT).show();
			return;
		}

		Mat srcMat = new Mat();
		Utils.bitmapToMat(originalBitmap, srcMat);
		// 处理透明通道
		if (srcMat.channels() == 4) {
			Imgproc.cvtColor(srcMat, srcMat, Imgproc.COLOR_RGBA2BGR);
		}

		// 转为灰度图
		Mat grayMat = new Mat();
		Imgproc.cvtColor(srcMat, grayMat, Imgproc.COLOR_BGR2GRAY);

		// 阈值化(突出黑色字体)
		Mat binaryMat = new Mat();
		Imgproc.threshold(grayMat, binaryMat, 150, 255, Imgproc.THRESH_BINARY_INV);

		// 形态学操作:连接笔画
		Mat kernel = Imgproc.getStructuringElement(Imgproc.MORPH_RECT, new org.opencv.core.Size(4, 5));
		Imgproc.dilate(binaryMat, binaryMat, kernel);
		Imgproc.erode(binaryMat, binaryMat, kernel);

		// 提取所有轮廓
		List<MatOfPoint> contours = new ArrayList<>();
		Mat hierarchy = new Mat();
		Imgproc.findContours(binaryMat, contours, hierarchy, Imgproc.RETR_EXTERNAL, Imgproc.CHAIN_APPROX_SIMPLE);

		// 过滤有效轮廓并绘制边界矩形
		Scalar red = new Scalar(0, 0, 255); // 红色矩形
		for (MatOfPoint contour : contours) {
			// 1. 计算轮廓面积,过滤过小轮廓
			double area = Imgproc.contourArea(contour);
			if (area < 50) {
				contour.release();
				continue;
			}

			// 2. 获取轮廓的边界矩形(左上角和右下角坐标)
			org.opencv.core.Rect rect = Imgproc.boundingRect(contour);
			int width = rect.width;
			int height = rect.height;

			// 3. 过滤宽高比异常的矩形
			if (width == 0 || height == 0) {
				contour.release();
				continue;
			}
			double ratio = (double) width / height;
			if (ratio < 0.2 || ratio > 3.2) {
				contour.release();
				continue;
			}

			// 4. 绘制边界矩形(左上角(x1,y1),右下角(x2,y2))
			Imgproc.rectangle(
				srcMat,
				new org.opencv.core.Point(rect.x, rect.y), // 左上角坐标
				new org.opencv.core.Point(rect.x + width, rect.y + height), // 右下角坐标
				red, // 颜色
				2 // 线宽
			);

			contour.release(); // 及时释放资源
		}
		Toast.makeText(this, "完成"+contours.size(), 0).show();
		// 转换为Bitmap显示
		Mat resultMat = new Mat();
		Imgproc.cvtColor(srcMat, resultMat, Imgproc.COLOR_BGR2RGBA);
		Bitmap resultBitmap = Bitmap.createBitmap(resultMat.cols(), resultMat.rows(), Bitmap.Config.ARGB_8888);
		Utils.matToBitmap(resultMat, resultBitmap);
		hb.setbittmap(resultBitmap);

		// 释放剩余资源
		srcMat.release();
		grayMat.release();
		binaryMat.release();
		hierarchy.release();
		kernel.release();
		resultMat.release();
	}
	
	
	
	private void log(Exception e) {
		ByteArrayOutputStream baos = new ByteArrayOutputStream();
		e.printStackTrace(new PrintStream(baos));
		String str = baos.toString();
		log(str);
	}
	public Boolean log(String strcontent) {
		try {
			strcontent += "\n";
			String filePath="/sdcard/log.txt";
			File file=new File(filePath);//路径
			if (!file.exists()) {
				file.getParentFile().mkdirs();
				file.createNewFile();//创建txt文件
			}
			RandomAccessFile raf=new RandomAccessFile(file, "rwd");
			raf.seek(file.length());
			raf.write(strcontent.getBytes());
			raf.close();
			return true;
		} catch (Exception e) {
		}
		return false;
	}
}
相关推荐
crmscs10 分钟前
剪映永久解锁版/电脑版永久会员VIP/安卓SVIP手机永久版下载
android·智能手机·电脑
localbob12 分钟前
杀戮尖塔 v6 MOD整合版(Slay the Spire)安卓+PC端免安装中文版分享 卡牌肉鸽神作!杀戮尖塔中文版,电脑和手机都能玩!杀戮尖塔.exe 杀戮尖塔.apk
android·杀戮尖塔apk·杀戮尖塔exe·游戏分享
机建狂魔17 分钟前
手机秒变电影机:Blackmagic Camera + LUT滤镜包的专业级视频解决方案
android·拍照·摄影·lut滤镜·拍摄·摄像·录像
hudawei99617 分钟前
flutter和Android动画的对比
android·flutter·动画
lxysbly2 小时前
md模拟器安卓版带金手指2026
android
儿歌八万首3 小时前
硬核春节:用 Compose 打造“赛博鞭炮”
android·kotlin·compose·春节
消失的旧时光-19435 小时前
从 Kotlin 到 Dart:为什么 sealed 是处理「多种返回结果」的最佳方式?
android·开发语言·flutter·架构·kotlin·sealed
Jinkxs6 小时前
Gradle - 与Groovy/Kotlin DSL对比 构建脚本语言选择指南
android·开发语言·kotlin
&有梦想的咸鱼&6 小时前
Kotlin委托机制的底层实现深度解析(74)
android·开发语言·kotlin
LDORntKQH6 小时前
基于深度强化学习的混合动力汽车能量管理策略 1.利用DQN算法控制电池和发动机发电机组的功率分配 2
android