studio - Cambiar el color de un objeto en una aplicación de Android
curso android desarrollo de aplicaciones móviles pdf (3)
Creo que cometió el error de mover la imagen en escala de grises a la imagen coloreada.
Pruebe: Imgproc.cvtColor(mRgba, mIntermediateMat, Imgproc.COLOR_YUV2RGBA_NV21, 4);
En lugar de: Imgproc.cvtColor(mIntermediateMat, mRgba, Imgproc.COLOR_YUV2RGBA_NV21, 4);
Básicamente mi objetivo es cambiar el color del objeto en tiempo real para la aplicación de pintura. Para lograr este objetivo, sigo los siguientes conceptos:
- He usado el método de
canny()
para encontrar el objeto. - Usando
findContours()
para detección de bordes. - usando
drawContours()
para colorear el objeto.
Si se requiere algún otro concepto para lograr el objetivo, por favor sugiéramelo. Lo he intentado pero no obtengo los contornos exactos.
Entrada original:
Rendimiento esperado:
Salida de corriente:
Estoy obteniendo una imagen en escala de grises pero quiero en modo rgb.
aquí está mi código:
package com.example.imageprocess;
import java.util.ArrayList;
import java.util.List;
import org.opencv.android.BaseLoaderCallback;
import org.opencv.android.CameraBridgeViewBase;
import org.opencv.android.CameraBridgeViewBase.CvCameraViewFrame;
import org.opencv.android.CameraBridgeViewBase.CvCameraViewListener2;
import org.opencv.android.LoaderCallbackInterface;
import org.opencv.android.OpenCVLoader;
import org.opencv.core.CvType;
import org.opencv.core.Mat;
import org.opencv.core.MatOfPoint;
import org.opencv.core.Point;
import org.opencv.core.Scalar;
import org.opencv.core.Size;
import org.opencv.imgproc.Imgproc;
import android.app.Activity;
import android.os.Bundle;
import android.util.Log;
import android.view.WindowManager;
public class MainActivity extends Activity implements CvCameraViewListener2 {
private Mat mRgba;
private Mat mIntermediateMat;
private Mat mGray;
private CameraBridgeViewBase mOpenCvCameraView;
private BaseLoaderCallback mLoaderCallback = new BaseLoaderCallback(this) {
@Override
public void onManagerConnected(int status) {
switch (status) {
case LoaderCallbackInterface.SUCCESS:
{
Log.i("OPENCVACTIVITY", "OpenCV loaded successfully");
// Load native library after(!) OpenCV initialization
// System.loadLibrary("mixed_sample");
mOpenCvCameraView.enableView();
} break;
default:
{
super.onManagerConnected(status);
} break;
}
}
};
/* public MainActivity() {
Log.i("OPENCVACTIVITY", "Instantiated new " + this.getClass());
}
*/
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
setContentView(R.layout.activity_main);
mOpenCvCameraView = (CameraBridgeViewBase) findViewById(R.id.tutorial2_activity_surface_view);
mOpenCvCameraView.setCvCameraViewListener(this);
}
@Override
public void onPause()
{
super.onPause();
if (mOpenCvCameraView != null)
mOpenCvCameraView.disableView();
}
@Override
public void onResume()
{
super.onResume();
OpenCVLoader.initAsync(OpenCVLoader.OPENCV_VERSION_2_4_3, this, mLoaderCallback);
}
public void onDestroy() {
super.onDestroy();
if (mOpenCvCameraView != null)
mOpenCvCameraView.disableView();
}
@Override
public void onCameraViewStarted(int width, int height) {
// TODO Auto-generated method stub
mRgba = new Mat(height, width, CvType.CV_8UC4);
mIntermediateMat = new Mat(height, width, CvType.CV_8UC4);
mGray = new Mat(height, width, CvType.CV_8UC1);
}
@Override
public void onCameraViewStopped() {
mRgba.release();
mGray.release();
mIntermediateMat.release();
}
@Override
public Mat onCameraFrame(CvCameraViewFrame inputFrame) {
Mat gaussian_output = new Mat();
mRgba = inputFrame.rgba();
Imgproc.Canny(inputFrame.gray(), mIntermediateMat, 80, 100);
Imgproc.cvtColor(mIntermediateMat, mRgba, Imgproc.COLOR_YUV2RGBA_NV21, 4);
Imgproc.GaussianBlur(mIntermediateMat, gaussian_output, new Size(5, 5), 5);
List<MatOfPoint> contours = new ArrayList<MatOfPoint>();
Imgproc.findContours( gaussian_output, contours, new Mat(),Imgproc.RETR_EXTERNAL, Imgproc.CHAIN_APPROX_SIMPLE, new Point(0,0) );
Scalar color = new Scalar(165, 30, 215);
// Imgproc.drawContours(gaussian_output, contours, -1, color, 3);
Mat hierarchy = new Mat();
// find contours:
Imgproc.findContours(gaussian_output, contours, hierarchy, Imgproc.RETR_TREE,Imgproc.CHAIN_APPROX_SIMPLE);
for (int contourIdx = 0; contourIdx < contours.size(); contourIdx++) {
Imgproc.drawContours(gaussian_output, contours, contourIdx,color, -1);
}
return gaussian_output;
}
}
Un poco tarde para la fiesta. No he probado el código, pero sospecho:
mIntermediateMat = new Mat(height, width, CvType.CV_8UC4);
Aunque mIntermediateMat es una alfombrilla de 8 bits y 4 canales aquí,
Imgproc.Canny(inputFrame.gray(), mIntermediateMat, 80, 100);
Se convirtió en una alfombrilla de 8 bits y 1 canal aquí. ref: canny doc .
mapa de borde de salida; tiene el mismo tamaño y tipo de imagen.
Como resultado,
Imgproc.GaussianBlur(mIntermediateMat, gaussian_output, new Size(5, 5), 5);
gaussian_output es una alfombrilla de canal 1 de 8 bits, y ...
return gaussian_output;
devuelve una imagen de 8 bit 1 canal (escala de grises).
http://www.labbookpages.co.uk/software/imgProc/libPNG.html
Debe usar LIBPNG para el procesamiento de imágenes. Utilizándolo, puede convertirlo a escala de grises o a una imagen coloreada configurando la matriz de colores.