2016-07-16 4 views
0

보기에 "물건"을 그릴 목적으로 OverlayBuild라는 클래스가 있지만, 어떤 이유로 간단한 것처럼 보이는 문제가 발생했지만 여전히 많은 비용이 든다. 시각. 문제는 클래스가 두 번째 (세 번째, 네 번째 등) 클래스에 사용될 때 드로잉/뷰가 부모 뷰에 추가되지 않거나 최소한 보이지 않는다는 것입니다.안드로이드에서보기 추가 두 번째 시간은 안 보이다.

오류의 원인을 식별하기 위해 클래스를 단순화하려고 시도했지만 여전히 발생합니다.

public class OverlayBuild { 

    private String tag; 
    private Context context; 
    private ViewGroup container; 
    private RelativeLayout overlay; 
    public static boolean layoutLoaded; 
    private int backgroundWidth  = 1500; 
    private int backgroundHeight = 1500; 
    private boolean overlayLayoutCompleted; 


    public OverlayBuild(Context context, ViewGroup container, String tag) { 
     this.tag      = tag; 
     this.context     = context; 
     this.container     = container; 
     this.overlay     = new RelativeLayout(context); 
     layoutLoaded     = false; 
    } 

    public OverlayBuild setLayoutListener(final LayoutListener layoutListener) { 
     container.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() { 
      @Override 
      public void onGlobalLayout() { 
       if (!layoutLoaded) { 
        layoutListener.layoutPrepared(container); 
        layoutLoaded = true; 
       } 
      } 
     }); 

     return this; 
    } 
    public OverlayBuild setBackgroundDimens(int width, int height) { 
     this.backgroundWidth = width; 
     this.backgroundHeight = height; 
     return this; 
    } 

    public OverlayBuild hideOverlay(){ 
     if(overlay != null){ 
      overlay.setVisibility(View.GONE); 
     } 
     return this; 
    } 


    public OverlayBuild commit() { 
     View view = getViewByTag(tag); 
     if (view == null) { 
      container.addView(overlay); 
      overlayLayoutCompleted = true; 
      overlay.setTag(tag); 

      overlay.bringToFront(); 
      overlay.setVisibility(View.VISIBLE); 

      container.setBackgroundResource(R.color.red); 
      overlay.setBackgroundResource(R.color.blue_mid); 
     } 


     return this; 
    } 


    private View getViewByTag(String tag) { 
     return container.findViewWithTag(tag); 
    } 

    public interface LayoutListener { 
     void layoutPrepared(ViewGroup view); 
    } 

을 그리고 여기에 내가 "그리기"로 클래스를 사용하는 방법입니다 : 그래서 여기

먼저 OverlayBuild 클래스 내 코드입니다

public static void showEmptyState(final Context context, final Button createAgentBtn, final ViewGroup parentView, final String tag) { 

      final OverlayBuild builder = new OverlayBuild(context, parentView, tag); 
      builder.setLayoutListener(new OverlayBuild.LayoutListener() { 
       @Override 
       public void layoutPrepared(ViewGroup view) { 
        final ViewGroup.MarginLayoutParams btnParams = (ViewGroup.MarginLayoutParams) createAgentBtn.getLayoutParams(); 

        final int parentWidth = parentView.getWidth(); 
        final int parentHeight = parentView.getHeight(); 

        builder.setBackgroundDimens(parentWidth,parentHeight) 
          .commit(); 
       } 
      }); 
     } 

당신은에서 볼 수 있듯이 메서드는 "commit()"이라고 불리며, 테스트 용으로 배경색을 설정하고 있습니다. 결론적으로 색상이 처음에는 화면에 표시되지만 다음 번에는 볼 수 없음을 알 수 있습니다.

디버깅을 많이했고 코드의 모든 위치에 도달했는지 확인할 수 있습니다. 그것을해야합니다.

정말 누군가 나를 도울 수 있기를 바랍니다. 어떤 도움이라도 대단히 감사하겠습니다.

답변

1

답을 직접 찾았습니다. 필드를 변경함으로써 :

public static boolean layoutLoaded 

는 "비 정적"다음 호출시 상태의 혼란 발생이 부울의 단일 인스턴스 만이 있다는

public boolean layoutLoaded 

문제는 해결되었다 두 번째.

+0

아! 네, 그렇게 할거예요. – w3bshark

1

확신 할 수 없지만 commit()이 두 번째 호출 될 때보기가 아마도 == null이 아닙니다. 그리고 귀하의 addView() 전화가 null 체크에 포함되어 있기 때문에보기가 다시 추가되지 않습니다.

"레이아웃 경계 표시"설정을 사용하여 현재 코드를 테스트해야합니다. 조회수가 표시되지 않을 때이 기능을 통해 많은 도움이되었습니다. 설정 -> 개발자 옵션 -> "레이아웃 경계 표시"를 선택하십시오. 그런 다음 두 번째보기를 추가 할 위치로 코드를 실행하고 두 번째 오버레이보기의 레이아웃 경계를 볼 수 있는지 확인하십시오.

또한 overlay.bringToFront();을 호출하지 않으셨습니까? 스택에 추가 된 오버레이보기를 추적하고 추가/제거 할 때 밀어 넣기/팝업을 시도 할 수도 있습니다.

희망이 도움이됩니다.

+0

감사합니다. 난 다른 접근법을 많이 시도했는데, 특히 null 체크를 가진 제안을 포함하여 뭔가 잘못되었다고 의심되는 commit() 메서드에서. 내가 게시 한 솔루션은 많은 솔루션 중 하나 일뿐입니다. 그러나 나는 여전히 귀하의 답변이 다른 방법 (예 : "레이아웃 레이아웃 표시")에 도움이된다는 사실을 발견 했으므로 답변을 upvote 할 것입니다. 그러나 문제의 해결책을 결국 찾았습니다 (관심있는 경우 내 대답 참조). – Langkiller

관련 문제