我在Android Studio中使用以下算法来均衡图像。
但是它在getRaster
方法中显示错误并且无法识别它。此外getRGB
也显示错误。
请告诉我哪里出错了。
我按照你说的编辑了代码,但崩溃了。
import java.io.IOException;
import java.util.Arrays;
import java.lang.Object;
import android.app.Activity;
import android.app.Dialog;
import android.app.ProgressDialog;
import android.content.Context;
import android.content.Intent;
import android.content.pm.ActivityInfo;
import android.database.Cursor;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Paint.Style;
import android.graphics.Path;
import android.net.Uri;
import android.os.AsyncTask;
import android.os.Bundle;
import android.provider.MediaStore;
import android.util.DisplayMetrics;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.LinearLayout;
public class webhist extends Activity {
Bitmap bi = null;
boolean isColored;
LinearLayout view;
LinearLayout view_color;
boolean flag;
private int SIZE = 256;
// Red, Green, Blue
private int NUMBER_OF_COLOURS = 3;
public final int RED = 0;
public final int GREEN = 1;
public final int BLUE = 2;
private int[][] colourBins;
private volatile boolean loaded = false;
private int maxY;
private static final int LDPI = 0;
private static final int MDPI = 1;
private static final int TVDPI = 2;
private static final int HDPI = 3;
private static final int XHDPI = 4;
float offset = 1;
@Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);
setContentView(R.layout.activity_webhist);
DisplayMetrics metrics = new DisplayMetrics();
getWindowManager().getDefaultDisplay().getMetrics(metrics);
if(metrics.densityDpi==metrics.DENSITY_LOW)
offset = 0.75f;
else if(metrics.densityDpi==metrics.DENSITY_MEDIUM)
offset = 1f;
else if(metrics.densityDpi==metrics.DENSITY_TV)
offset = 1.33f;
else if(metrics.densityDpi==metrics.DENSITY_HIGH)
offset = 1.5f;
else if(metrics.densityDpi==metrics.DENSITY_XHIGH)
offset = 2f;
Log.e("NIRAV",""+offset);
colourBins = new int[NUMBER_OF_COLOURS][];
for (int i = 0; i < NUMBER_OF_COLOURS; i++) {
colourBins[i] = new int[SIZE];
}
loaded = false;
Button upload = (Button) findViewById(R.id.upload);
upload.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
if (flag) {
view_color.removeAllViews();
view.removeAllViews();
}
Intent it = new Intent(
Intent.ACTION_PICK,
android.provider.MediaStore.Images.Media.INTERNAL_CONTENT_URI);
startActivityForResult(it, 101);
flag = true;
/*
* LinearLayout view = (LinearLayout) findViewById(R.id.lyt);
* view.addView(new MyHistogram(getApplicationContext()));
*/
}
});
Button histogram = (Button) findViewById(R.id.hst_btn);
histogram.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
if (bi != null) {
isColored = false;
view = (LinearLayout) findViewById(R.id.lyt);
view.addView(new MyHistogram(getApplicationContext(), bi));
}
}
});
Button histogram_color = (Button) findViewById(R.id.hst_color_btn);
histogram_color.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
if (bi != null) {
isColored = true;
view_color = (LinearLayout) findViewById(R.id.lyt_color);
view_color.addView(new MyHistogram(getApplicationContext(),
bi));
}
}
});
}
protected void onActivityResult(int requestCode, int resultCode,
Intent imageReturnedIntent) {
super.onActivityResult(requestCode, resultCode, imageReturnedIntent);
switch (requestCode) {
case 101:
if (resultCode == RESULT_OK) {
Uri selectedImage = imageReturnedIntent.getData();
String filename = getRealPathFromURI(selectedImage);
bi = BitmapFactory.decodeFile(filename);
/*
ByteArrayOutputStream out = new ByteArrayOutputStream();
bi.compress(Bitmap.CompressFormat.JPEG,10,out);
bi = BitmapFactory.decodeStream(new ByteArrayInputStream(out.toByteArray()));*/
if(bi!=null)
{
try {
new MyAsync().execute();
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
}
}
public String getRealPathFromURI(Uri contentUri) {
Log.e("TEST", "GetRealPath : " + contentUri);
try {
if (contentUri.toString().contains("video")) {
String[] proj = { MediaStore.Video.Media.DATA };
Cursor cursor = managedQuery(contentUri, proj, null, null, null);
int column_index = cursor
.getColumnIndexOrThrow(MediaStore.Video.Media.DATA);
cursor.moveToFirst();
return cursor.getString(column_index);
} else {
String[] proj = { MediaStore.Images.Media.DATA };
Cursor cursor = managedQuery(contentUri, proj, null, null, null);
int column_index = cursor
.getColumnIndexOrThrow(MediaStore.Images.Media.DATA);
cursor.moveToFirst();
return cursor.getString(column_index);
}
} catch (IllegalArgumentException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;
}
class MyAsync extends AsyncTask
{
@Override
protected void onPreExecute() {
// TODO Auto-generated method stub
super.onPreExecute();
showDialog(0);
}
@Override
protected Object doInBackground(Object... params) {
// TODO Auto-generated method stub
try {
load(bi);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;
}
@Override
protected void onPostExecute(Object result) {
// TODO Auto-generated method stub
super.onPostExecute(result);
ImageView img = (ImageView) findViewById(R.id.img);
img.setImageBitmap(bi);
((Button) findViewById(R.id.hst_btn)).setVisibility(View.VISIBLE);
((Button) findViewById(R.id.hst_color_btn)).setVisibility(View.VISIBLE);
dismissDialog(0);
}
}
public void load(Bitmap bi) throws IOException {
if (bi != null) {
// Reset all the bins
for (int i = 0; i < NUMBER_OF_COLOURS; i++) {
for (int j = 0; j < SIZE; j++) {
colourBins[i][j] = 0;
}
}
for (int x = 0; x < bi.getWidth(); x++) {
for (int y = 0; y < bi.getHeight(); y++) {
int pixel = bi.getPixel(x, y);
colourBins[RED][Color.red(pixel)]++;
colourBins[GREEN][Color.green(pixel)]++;
colourBins[BLUE][Color.blue(pixel)]++;
}
}
maxY = 0;
for (int i = 0; i < NUMBER_OF_COLOURS; i++) {
for (int j = 0; j < SIZE; j++) {
if (maxY < colourBins[i][j]) {
maxY = colourBins[i][j];
}
}
}
loaded = true;
} else {
loaded = false;
}
}
class MyHistogram extends View {
public MyHistogram(Context context, Bitmap bi) {
super(context);
}
@Override
protected void onDraw(Canvas canvas) {
// TODO Auto-generated method stub
super.onDraw(canvas);
if (loaded) {
canvas.drawColor(Color.GRAY);
Log.e("NIRAV", "Height : " + getHeight() + ", Width : "
+ getWidth());
int xInterval = (int) ((double) getWidth() / ((double) SIZE + 1));
for (int i = 0; i < NUMBER_OF_COLOURS; i++) {
Paint wallpaint;
wallpaint = new Paint();
if (isColored) {
if (i == RED) {
wallpaint.setColor(Color.RED);
} else if (i == GREEN) {
wallpaint.setColor(Color.GREEN);
} else if (i == BLUE) {
wallpaint.setColor(Color.BLUE);
}
} else {
wallpaint.setColor(Color.WHITE);
}
wallpaint.setStyle(Style.FILL);
Path wallpath = new Path();
wallpath.reset();
wallpath.moveTo(0, getHeight());
for (int j = 0; j < SIZE - 1; j++) {
int value = (int) (((double) colourBins[i][j] / (double) maxY) * (getHeight()+100));
//if(j==0) {
// wallpath.moveTo(j * xInterval* offset, getHeight() - value);
//}
// else {
wallpath.lineTo(j * xInterval * offset, getHeight() - value);
// }
}
wallpath.lineTo(SIZE * offset, getHeight());
canvas.drawPath(wallpath, wallpaint);
}
}
}
}
public void gray(View view1) {
operation = Bitmap.createBitmap(bi.getWidth(),
bi.getHeight(), bi.getConfig());
histEqualize(bi,operation);
}
public int[] CalculateHist(Bitmap bi) {
int k;
//array represents the intecity values of the pixels
int levels[] = new int[256];
for (int i = 0; i < bi.getWidth(); i++) {
for (int j = 0; j < bi.getHeight(); j++) {
int pixel = bi.getPixel(i, j);
//increase if same pixel appears
levels[Color.red(pixel)]++;
}
}
//return the histogram array
return levels;
}
public void histEqualize(Bitmap bi, Bitmap bi_out) {
//call CalculateHist method to get the histogram
int[] h = CalculateHist(bi);
//calculate total number of pixel
int mass = bi.getWidth() * bi.getHeight();
int k = 0;
long sum = 0;
//calculate the scale factor
float scale = (float) 255.0 / mass;
//calculte cdf
for (int x = 0; x < h.length; x++) {
sum += h[x];
int value = (int) (scale * sum);
if (value > 255) {
value = 255;
}
h[x] = value;
}
for (int i = 0; i < bi.getWidth(); i++) {
for (int j = 0; j < bi.getHeight(); j++) {
int pixel = bi.getPixel(i, j);
//set the new value
k = h[Color.red(pixel)];
int rgb = Color.rgb(k, k, k);
bi_out.setPixel(i, j, rgb);
}
}
}
// int pixel[]; <-- remove this
@Override
protected Dialog onCreateDialog(int id) {
ProgressDialog dataLoadProgress = new ProgressDialog(this);
dataLoadProgress.setMessage("Loading...");
dataLoadProgress.setIndeterminate(true);
dataLoadProgress.setCancelable(false);
dataLoadProgress.setProgressStyle(android.R.attr.progressBarStyleLarge);
return dataLoadProgress;
}
}
这是我的layout.xml文件
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent">
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:background="@android:color/holo_blue_bright">
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="fill_parent"
android:gravity="center"
android:orientation="vertical"
android:background="@android:color/white">
<LinearLayout
android:id="@+id/lyt"
android:layout_width="383dp"
android:layout_height="140dp"
android:orientation="vertical" >
</LinearLayout>
<Button
android:id="@+id/hst_btn"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Show Histogram"
android:visibility="invisible"/>
<Button
android:id="@+id/hst_color_btn"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Show Color Histogram"
android:visibility="invisible"/>
<LinearLayout
android:id="@+id/lyt_color"
android:layout_width="match_parent"
android:layout_height="140dp"
android:orientation="vertical" >
</LinearLayout>
</LinearLayout>
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="267dp" >
<ImageView
android:id="@+id/img"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:scaleType="fitCenter"
/>
<Button android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Select Image"
android:id="@+id/upload"
android:layout_margin="20dp"
android:background="@android:color/white"
android:textColor="@android:color/black"/>
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Equalised image"
android:onClick="gray"
android:id="@+id/button"
android:layout_alignTop="@+id/upload"
android:layout_alignParentRight="true"
android:layout_alignParentEnd="true"
android:layout_marginRight="38dp"
android:layout_marginEnd="38dp" />
<ImageView
android:id="@+id/imageView"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:scaleType="fitCenter"
android:layout_alignParentEnd="false" />
</RelativeLayout>
</LinearLayout>
</ScrollView>
答案 0 :(得分:1)
Android getRaster()
课程中没有Bitmap
方法。相反,您可以直接在Bitmap
上致电getPixel()。该函数返回一个整数ARGB值,您可以将其分成各种组件:
int pixel = bi.getPixel(i, j);
//increase if same pixel appears
levels[Color.red(pixel)]++;
您可以设置如下像素:
int rgb = Color.rgb(k, k, k);
bi.setPixel(i, j, rgb);