gpt4 book ai didi

java - 如何保证我的 Android SurfaceView 是透明的而不是黑色的?

转载 作者:太空宇宙 更新时间:2023-11-03 10:58:41 25 4
gpt4 key购买 nike

我有一个自定义 View ,它扩展了 SurfaceView 覆盖了我界面的其余部分,它在模拟器上工作,当调试器连接到我的手机上时,但是当手机使用电池运行时 View 永远不会清除。

public class CustomView extends SurfaceView {

private final Paint paint;
private final SurfaceHolder holder;
private final Context context;

private float strokeWidth = 4;

private boolean canvasAlreadyLocked = false;

public CustomView(Context viewContext, AttributeSet attrs)
{
super(viewContext, attrs);
Log.i("CustomView", "CustomView create context & attrs");
holder = getHolder();
context = viewContext;
paint = new Paint(Paint.ANTI_ALIAS_FLAG);
paint.setColor(Color.WHITE);
paint.setStyle(Paint.Style.STROKE);
paint.setStrokeWidth(strokeWidth);
drawLine();
setZOrderOnTop(true);
holder.setFormat(PixelFormat.TRANSPARENT);
}

public void resume() {
Log.i("CustomView", "Resume the customview display.");
setZOrderOnTop(true);
holder.setFormat(PixelFormat.TRANSPARENT);
}

@Override
public void onAttachedToWindow(){
super.onAttachedToWindow();
setZOrderOnTop(true);
}

@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
}

protected void drawLine() {
if (!canvasAlreadyLocked) {
invalidate();
if (holder.getSurface().isValid()) {
try {
final Canvas canvas = holder.lockCanvas();
canvasAlreadyLocked = true;
if (canvas != null) {
canvas.drawColor(Color.TRANSPARENT, PorterDuff.Mode.CLEAR);
paint.setColor(Color.BLACK);
paint.setStrokeWidth(strokeWidth * 2);
canvas.drawLine(0, getY(), getWidth(), getY(), paint);
paint.setColor(Color.WHITE);
paint.setStrokeWidth(strokeWidth);
canvas.drawLine(0, getY(), getWidth(), getY(), paint);
holder.unlockCanvasAndPost(canvas);
canvasAlreadyLocked = false;
}
}
catch (IllegalArgumentException iae)
{
Log.w("CustomView", "Exception trying to lock canvas: "+iae.getMessage());
Log.getStackTraceString(iae);

}
}
}
}

private float getY() {
getHeight()/2;
}

}

我知道这里的一些调用是多余的——这主要是尝试很多不同的东西来让它工作的遗留问题。您会注意到我已经完成了 this answer 中推荐的所有操作.

布局是这样的:

<FrameLayout 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="com.custom.CustomViewApp">

<FrameLayout
android:id="@+id/control"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_alignParentBottom="true"
android:layout_alignParentStart="true">

<com.custom.AutoFitTextureView
android:id="@+id/texture"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentStart="true"
android:layout_alignParentTop="true" />

<ImageButton
android:id="@+id/gpsNotification"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="@drawable/gps_unfixed"
android:layout_gravity="right"
android:tint="@color/gps_unfixed"
android:background="@null" />

<ProgressBar
android:id="@+id/camera_spinner"
style="?android:attr/progressBarStyle"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal|center_vertical"
android:gravity="center"
android:layout_centerHorizontal="true"
android:layout_centerVertical="true"
android:visibility="invisible"
/>

<com.custom.CustomView
android:id="@+id/custom_view"
android:background="@color/transparent"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentStart="true"
android:layout_alignParentTop="true" />

</FrameLayout>
</FrameLayout>

这是从 ViewFragment 中提取的:

@Override
public void onViewCreated(final View view, Bundle savedInstanceState) {
mTextureView = (AutoFitTextureView) view.findViewById(R.id.texture);
gpsNotification = (ImageButton) view.findViewById(R.id.gpsNotification);
customView = (CustomView) view.findViewById(R.id.custom_view);
spinner = (ProgressBar) view.findViewById(R.id.camera_spinner);
spinner.setVisibility(VISIBLE);
}

我已尝试尽可能简化这一点,显然在这种情况下发生了很多事情,但希望这足以表明问题可能来自何处。

AutoFitTextureView 正在显示来自相机的 View 。

  • 当我在模拟器中运行它时,一切都按预期显示,无论电池设置如何。
  • 当我在通过 USB 连接的手机上运行它时,一切都按预期显示。
  • 当我在断开连接的手机上运行它时, View 通常(但并非总是)显示为纯黑色 - AutoFitTextureView 完全被遮挡,但 CustomView 被绘制。其他组件 可见,这让我怀疑我调用 setZOrderOnTop() 的时间或方式有问题。
  • 如果我在 fragment 中打断点并将 CustomView 的可见性设置为 INVISIBLE,我可以立即看到其他所有内容,但正如您可能预料的那样,我丢失了叠加层.此时手动调用 setZOrderOnTop 似乎没有任何改变。
  • 当它正确运行时,我可以使用 Layout Inspector 工具检查结构,但是当 SurfaceView 不透明时,Layout Inspector 会引发 Unexpected Error: Empty View Hierarchy 消息。我无法在 Logcat 中找到相应的错误消息。

如何确保我的 SurfaceView 派生 View 始终透明?如果我不能保证这一点,有什么方法可以测试它当前是否 透明,如果不是,我可以调解?

最佳答案

认为 我现在已经解决了这个问题,问题是我试图将 SurfaceView 派生类型放在 TextureView 派生类型上.将 AutofitTextureView 换成另一个显示相机预览的 SurfaceView 似乎已经成功了。

关于java - 如何保证我的 Android SurfaceView 是透明的而不是黑色的?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50511373/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com