我有一个简短的问题:
假设我有一个(可变的)位图,我需要修改(添加图像,文本等...).
我没有考虑使用许多特殊的类来绘制画布(画布,画布,矩阵等),而是考虑为什么不使用Android的内置类来完成这项任务,只有当我需要真正定制的操作时,我仍然可以使用画布?
因此,例如,为了在位图上显示任何类型的视图(当然没有父视图),我可以调用下一个函数:
public void drawViewToBitmap(Bitmap b, View v, Rect rect) {
Canvas c = new Canvas(b);
// <= use rect to let the view to draw only into this boundary inside the bitmap
view.draw(c);
}
Run Code Online (Sandbox Code Playgroud)
这样的事情可能吗?也许这就是它在幕后工作的方式?
我应该在绘图和画布创作之间的部分写什么?
编辑:我已经尝试了下一个代码,但它没有工作:
public void drawFromViewToCanvas(final View view, final Rect rect, final Canvas canvas) {
final int widthSpec = View.MeasureSpec.makeMeasureSpec(rect.width(), View.MeasureSpec.EXACTLY);
final int heightSpec = View.MeasureSpec.makeMeasureSpec(rect.height(), View.MeasureSpec.EXACTLY);
view.measure(widthSpec, heightSpec);
// Lay the view out with the known dimensions
view.layout(0, 0, rect.width(), rect.height());
// …Run Code Online (Sandbox Code Playgroud) 我正在尝试decode和encode一个Bitmap图像.在某些设备上,它可以完美运行,而在其他设备上则不然.我正在上传Base64 String到服务器并Base64 String从服务器获取.我找到了各种解决方案,但仍然无法解决我的问题.这是我的代码:
编码方式:
button1.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
Intent i = new Intent(
Intent.ACTION_PICK,
android.provider.MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
getActivity().startActivityForResult(i, RESULT_LOAD_IMAGE);
}
});
//Image loading from Gallery
@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == RESULT_LOAD_IMAGE && resultCode == RESULT_OK
&& null != data) {
Uri selectedImage = data.getData();
String[] filePathColumn = { MediaStore.Images.Media.DATA };
Cursor …Run Code Online (Sandbox Code Playgroud) 所以我正在从Web服务加载图像,但是图像的大小有时比其他图像更小或更大,当我将它们放入android中的ListView时,可视化看起来很傻.我想修改我的ImageView的大小,以便它只显示图像的一部分,如果它大于预设量.我已经尝试了所有我能想到的设置setMaxWidth/setMaxHeight,将scale类型设置为centerCrop,使用ClipableDrawable包装我的BitmapDrawable,使用Drawable.setBounds()进行设置.我已经尝试过设置XML并以编程方式设置,但都没有工作.我很惊讶设置最大宽度/高度没有做任何事情.下面是我在布局文件中使用ImageView定义的XML:
<ImageView android:id="@+id/recipeImage"
android:maxHeight="64px"
android:maxWidth="64px"
android:scaleType="centerCrop"
android:layout_width="wrap_content"
android:layout_height="fill_parent"
android:layout_alignParentTop="true"
android:layout_alignParentBottom="true"
android:layout_marginRight="6dip"/>
Run Code Online (Sandbox Code Playgroud)
但是,没有任何效果.
我想从bytearray创建一个位图.
我尝试了以下代码
Bitmap bmp;
bmp = BitmapFactory.decodeByteArray(data, 0, data.length);
Run Code Online (Sandbox Code Playgroud)
和
ByteArrayInputStream bytes = new ByteArrayInputStream(data);
BitmapDrawable bmd = new BitmapDrawable(bytes);
bmp = bmd.getBitmap();
Run Code Online (Sandbox Code Playgroud)
但是,当我想用位图初始化Canvas对象时
Canvas canvas = new Canvas(bmp);
Run Code Online (Sandbox Code Playgroud)
它会导致错误
java.lang.IllegalStateException: Immutable bitmap passed to Canvas constructor
Run Code Online (Sandbox Code Playgroud)
然后如何从byteArray获取可变位图.
提前致谢.
我发现了几种用于优化WPF中位图处理的模式.但是,我不了解何时使用每种模式.我认为这是一个常见问题,我总结了我的理解和猜测,并请求您的帮助.如果您可以添加模式,解释它们的不同之处,解释它们是否使用CPU或GPU,并教授何时使用它们以及如何组合它们,这将是一个巨大的帮助!
上下文 - 图像"网格"场景:
我的应用程序必须显示许多位图图像.图像以行和列网格状组织显示在屏幕上(不一定是Grid或UniformGrid类,想想Window Media Player的Album视图).图像可能在不同的网格单元之间移动 任意单元格中的某些图像可能会被其他图像替换.图像应该是可点击的,应该提供一个上下文菜单,应该是可选择的,可拖动的等等.换句话说,"将小虫子组合成一个大的位图"是不适用的,至少不是天真的.
模式0:黑客
将小虫子组合成位图(如何绘制上下文?),并将其用作背景.使用空内容处理命中,上下文菜单,事件等的图像叠加此图像.
优点是我们这里只讨论两个位图:当前显示的位图和应该替换它的位图.这应该非常快.然而,我多年的经历引发了危险的危险.你的评论?
模式1:减小图像大小
如果您事先知道要调整大小的图像大小,以及当您准备丢失性能的详细信息(颜色)时,这是一个明智的做法:
见代码在这里.
模式2:背景预取
当您认为可以利用用户注视屏幕上的图像时,此模式适用,并提前准备要显示的下一个图像.除了内存开销之外,项目的缺点是它必须支持.Net Framework 4目标而不仅仅是客户端配置文件,因此它可能会在客户端上进行安装.你自己将不得不忍受异步编程的痛苦.
在此模式中,您可以精确创建所需数量的图像控件.当需要添加,移动或删除位图时,您只需修改Image控件的BitmapSource(s).BackgroundWorker任务负责预取BitmapSource(可能使用上面的"Reduce Image Size"模式)并将它们插入MemoryCache.
为此,您必须将BitmapImage的CacheOption设置为OnLoad,以便将工作卸载到后台工作程序.
模式3:绘制上下文
这是从在MSDN WPF论坛Microsoft支持建议谢尔登Ziao 这里.有关DrawingContext的说明,请参阅Adam Nathan的WPF 4中的第494页,第15章"2D图形".我不能说我理解它.根据这里的答案,我认为这将改善几何图纸的处理,而不是位图.接下来,我认为这不会支持图像的焦点和事件要求(我不好在论坛上没有更好地解释要求)而且,我很担心这本书的总结句:"注意使用DrawingContext不会改变您在保留模式系统中运行的事实.指定的图纸不会立即发生; 命令由WPF保留,直到需要它们为止."这意味着一旦我们的偶数处理程序恢复,我们就无法利用"背景预取"中的并行性.
模式4:可写位图
这里的MSDN文档将其描述为双缓冲系统:您的UI线程更新缓冲区; WPF的渲染线程将其移动到视频内存.
预期用法(参见此处)适用于在显示等视频电影中发生重大变化的位图.我不确定,但可能会被黑客攻击并与背景预取模式结合并在网格场景中使用.
模式5:缓存的位图
关于MSDN的信息不多(这里).在WPF论坛存档(这里),它解释说"BitmapCache API旨在缓存你的内容(当在硬件中渲染时)在视频内存中,这意味着它仍然驻留在你的GPU上.这样可以节省在将内容绘制到屏幕时重新呈现内容的成本."这似乎是一个好主意.但是,我不确定是什么陷阱以及如何使用它.
模式6:RenderTargetBitmap
RenderTargetBitmap将Visual转换为位图.我不确定这里是否相关.看到这里.
编辑:关于Paul Hoenecke的问题:我写过"我的应用程序必须显示许多位图".我没有提到,我需要显示约800图像并发.
人们可以阅读我的问题所涉及的性能问题WPF Bitmap性能以及如何使WPF上的图像显示更加"活泼"?
我已经修改了模式1的描述,以突出显示未创建或删除图像控件的概念(除非我们想要显示更大或更小的网格).只有它们的Sources被设置为不同的,新的或null的BitmapSources.
编辑: …
我正在开发一个Android应用程序.该应用程序有一个包含大量图像的视图.我有一个错误,我会尝试提供尽可能多的信息,希望有人可以给我一些建议.
该应用程序在所有本地测试中都运行良好.但是,我收到了很多来自用户的崩溃:java.lang.OutOfMemoryError: bitmap size exceeds VM budget
这是堆栈跟踪
0 java.lang.OutOfMemoryError: bitmap size exceeds VM budget
1 at android.graphics.Bitmap.nativeCreate(Native Method)
2 at android.graphics.Bitmap.createBitmap(Bitmap.java:507)
3 at android.graphics.Bitmap.createBitmap(Bitmap.java:474)
4 at android.graphics.Bitmap.createScaledBitmap(Bitmap.java:379)
5 at android.graphics.BitmapFactory.finishDecode(BitmapFactory.java:498)
6 at android.graphics.BitmapFactory.decodeStream(BitmapFactory.java:473)
7 at android.graphics.BitmapFactory.decodeResourceStream(BitmapFactory.java:336)
8 at android.graphics.BitmapFactory.decodeResource(BitmapFactory.java:359)
9 at android.graphics.BitmapFactory.decodeResource(BitmapFactory.java:385)
Run Code Online (Sandbox Code Playgroud)
我最大的问题是,即使在旧设备上,我也无法在本地重现问题.
我已经实现了很多东西来尝试解决这个问题:
onDestroy()方法中的所有必要步骤inSampleSize.用于计算正确inSampleSize的代码
public static int calculateInSampleSize(BitmapFactory.Options options, int reqWidth, int reqHeight)
{
// Raw height and width of image
final int height = options.outHeight;
final …Run Code Online (Sandbox Code Playgroud) 我正在使用Universal-Image-Loader,这个功能可以从SD卡访问图像的文件缓存.但我不知道如何将返回的文件缓存转换为位图.基本上我只想将位图分配给ImageView.
File mSaveBit = imageLoader.getDiscCache().get(easyPuzzle);
Log.d("#ImageValue: ", ""+mSaveBit.toString());
mImageView.setImageBitmap(mSaveBit);
Run Code Online (Sandbox Code Playgroud)
错误:"ImageView类型中的方法setImageBitmap(Bitmap)不适用于参数(File)"
我需要一种在.net中压缩图像的方法,所以我研究了使用.net GZipStream类(或DeflateStream).然而,我发现解压缩并不总是成功,有时图像会很好地解压缩,而有时我会得到GDI +错误,表明某些内容已损坏.
在调查问题后,我发现解压缩没有回复它压缩的所有字节.因此,如果我压缩2257974字节,我有时会回来2257870字节(实数).
最有趣的是,有时它会起作用.所以我创建了这个只压缩10个字节的小测试方法,现在我根本没有回复任何东西.
我用压缩类GZipStream和DeflateStream尝试了它,我仔细检查了我的代码是否存在可能的错误.我甚至尝试将流定位到0并冲洗所有流但没有运气.
这是我的代码:
public static void TestCompression()
{
byte[] test = new byte[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 };
byte[] result = Decompress(Compress(test));
// This will fail, result.Length is 0
Debug.Assert(result.Length == test.Length);
}
public static byte[] Compress(byte[] data)
{
var compressedStream = new MemoryStream();
var zipStream = new GZipStream(compressedStream, CompressionMode.Compress);
zipStream.Write(data, 0, data.Length);
return compressedStream.ToArray();
}
public static byte[] Decompress(byte[] data)
{
var compressedStream = new MemoryStream(data);
var zipStream …Run Code Online (Sandbox Code Playgroud) 我正在尝试使用SHARE INTENTAndroid从Facebook,Twitter等分享图像.
我找到了将图像发送到共享意图的代码,但是这段代码需要位图的URI: fullSizeImageUri
这是完整的代码:
private void startShareMediaActivity(Bitmap image) {
boolean isVideo=false;
String mimeType="bmp";
Uri fullSizeImageUri=null;
Intent intent = new Intent();
intent.setAction(Intent.ACTION_SEND);
intent.setType(mimeType);
intent.putExtra(Intent.EXTRA_STREAM, fullSizeImageUri);
try {
startActivity(Intent.createChooser(intent, (isVideo ? "video" : "image")));
} catch (android.content.ActivityNotFoundException ex) { }
}
Run Code Online (Sandbox Code Playgroud)
请问有人可以帮我将Bitmap转换为Uri吗?
谢谢
我正在尝试使用我创建的函数直接将位图保存到文件和特定文件.它不起作用.它在bitmap.compress部分之后崩溃(在here3之前).
File dir = new File(filepath);
if(!dir.exists())dir.mkdirs();
File file = new File(Environment.getExternalStorageDirectory() + filepath, side + ".png");
FileOutputStream fOut = new FileOutputStream(file);
bitmap.compress(Bitmap.CompressFormat.PNG, 85, fOut);
fOut.flush();
fOut.close();
System.out.println(filepath);
bitmap.recycle();
System.gc();
Run Code Online (Sandbox Code Playgroud)
错误日志:
06-29 00:16:38.089: D/AndroidRuntime(3260): Shutting down VM
06-29 00:16:38.089: W/dalvikvm(3260): threadid=1: thread exiting with uncaught exception (group=0xb587f4f0)
06-29 00:16:38.089: E/AndroidRuntime(3260): FATAL EXCEPTION: main
06-29 00:16:38.089: E/AndroidRuntime(3260): java.lang.RuntimeException: Failure delivering result ResultInfo{who=null, request=0, result=-1, data=Intent { act=android.intent.action.VIEW dat=content://org.openintents.filemanager/mimetype//mnt/sdcard/download/02977_awreckedboatintheocean_1280x1024.jpg }} to activity {com.polygonattraction.testbirds/com.polygonattraction.testbirds.functions.SelectImageSource}: java.lang.IllegalStateException: Can't compress a recycled bitmap
06-29 00:16:38.089: E/AndroidRuntime(3260): …Run Code Online (Sandbox Code Playgroud) bitmap ×10
android ×8
java ×3
image ×2
android-file ×1
base64 ×1
c# ×1
caching ×1
canvas ×1
compression ×1
draw ×1
file-io ×1
heap ×1
imageview ×1
mutable ×1
optimization ×1
performance ×1
uri ×1
wpf ×1
zip ×1