我已经看到很多类似这样的问题-但是我无法理解我正在做什么(尝试了几次)。那就是为什么我问一个可能重复的问题。
在我正在开发的android测试应用程序上,我正在尝试从当前视图保存位图。但是,当我尝试保存它时,就像视图已被放置(宽度和高度为零)一样。
我怀疑它是因为保存视图的方法在OnCreate方法内部,但是我看不到另一种方法。我的代码(.java文件和xml布局)非常简单。我要做的就是从当前视图中获取位图。
感谢您的任何投入(我再次在SO周围进行搜索,并看到许多与此特定问题相关的链接)。
谢谢
MainActivity.Java
package com.example.saveview;
import androidx.appcompat.app.AppCompatActivity;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.media.MediaScannerConnection;
import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;
import android.util.Log;
import android.view.View;
import android.widget.Toast;
import com.example.saveview.views.ViewParaSalvar;
import java.io.File;
import java.io.FileOutputStream;
import java.util.Date;
import java.util.Random;
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
final ViewParaSalvar MyCustomView = new ViewParaSalvar(this);
//Trying to save a screenshot of MyCustomView
// Bitmap BmpFromView = loadBitmapFromView(MyCustomView);
//saveImageToExternalStorage(BmpFromView);
}
public static Bitmap loadBitmapFromView(View v) {
Bitmap b = Bitmap.createBitmap( v.getLayoutParams().width, v.getLayoutParams().height, Bitmap.Config.ARGB_8888);
Canvas c = new Canvas(b);
v.layout(v.getLeft(), v.getTop(), v.getRight(), v.getBottom());
v.draw(c);
return b;
}
public void ExibirMensagemAlerta(String msg)
{
Toast.makeText(this, msg, Toast.LENGTH_SHORT).show();
}
private void saveImageToExternalStorage(Bitmap finalBitmap) {
String root = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES).toString();
File myDir = new File(root + "/saved_images");
myDir.mkdirs();
Random generator = new Random();
int n = 10000;
n = generator.nextInt(n);
String fname = "Image-" + n + ".jpg";
File file = new File(myDir, fname);
try {
FileOutputStream out = new FileOutputStream(file);
if(file.isDirectory())
{
finalBitmap.compress(Bitmap.CompressFormat.JPEG, 90, out);
MediaScannerConnection.scanFile(this, new String[] { file.toString() }, null,
new MediaScannerConnection.OnScanCompletedListener() {
public void onScanCompleted(String path, Uri uri) {
Log.i("ExternalStorage", "Scanned " + path + ":");
Log.i("ExternalStorage", "-> uri=" + uri);
}
});
ExibirMensagemAlerta(file.toString());
out.flush();
out.close();
}
else
{
ExibirMensagemAlerta("Path not created");
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
CustomView.Java
package com.example.saveview.views;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Rect;
import android.util.AttributeSet;
import android.view.View;
import android.widget.Toast;
import androidx.annotation.Nullable;
public class ViewParaSalvar extends View {
private static final int SQUARE_SIZE = 100;
private Rect mRectSquare;
private Paint mPaintSquare;
public Canvas pbCanvas;
public ViewParaSalvar(Context context) {
super(context);
init(null);
}
public ViewParaSalvar(Context context, @Nullable AttributeSet attrs) {
super(context, attrs);
init(attrs);
}
public ViewParaSalvar(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
init(attrs);
}
public ViewParaSalvar(Context context, @Nullable AttributeSet attrs, int defStyleAttr, int defStyleRes) {
super(context, attrs, defStyleAttr, defStyleRes);
init(attrs);
}
private void init(@Nullable AttributeSet set)
{
mRectSquare = new Rect();
mPaintSquare = new Paint(Paint.ANTI_ALIAS_FLAG);
}
@Override
protected void onDraw(Canvas canvas)
{
mRectSquare.top = 0;
mRectSquare.left = 10;
mRectSquare.bottom = mRectSquare.top + SQUARE_SIZE;
mRectSquare.right = mRectSquare.left + SQUARE_SIZE;
mPaintSquare.setColor(Color.RED);
mPaintSquare.setTextSize(60);
canvas.drawText("TEST DRAW CUSTOM VIEW",10,50,mPaintSquare);
pbCanvas = canvas;
}
}
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout 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">
<com.example.saveview.views.ViewParaSalvar
android:layout_width="match_parent"
android:layout_height="150dp"
android:id="@+id/idDaViewParaSalvar"/>
</RelativeLayout>
答案 0 :(得分:1)
您尝试将此侦听器添加到onCreate
事件中:
myCustomView.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
myCustomView.getViewTreeObserver().removeOnGlobalLayoutListener(this);
do_your_logic_to_save_bitmap_from_view;
}
});
addOnGlobalLayoutListener
将注册一个回调,以在全局布局状态或视图树中视图的可见性更改时调用。例如,当视图完全呈现时。