theblitz
theblitz

Reputation: 6881

Problems with setBackgroundResource

I am having weird problems with setBackgroundResource. For some reason when I run the folling code it doesn't set the backgropund.

layoutId is the id of a layout that I wish to add to another. That is performed before this and then I run this code.

viewToBorderId is the id of a view within that layout. It is around that view that I wish to place the border.

    ViewGroup contentView = (ViewGroup) this.getLayoutInflater().inflate(layoutId, null);
    RelativeLayout contentScreenRoot = (RelativeLayout) this.findViewById(R.id.content_screen_root);
    RelativeLayout.LayoutParams lp = new RelativeLayout.LayoutParams(
        ((ScrollView) contentScreenRoot.findViewById(R.id.content_screen_scroll_view)).getLayoutParams());
    lp.addRule(RelativeLayout.BELOW, R.id.content_screen_user_details);
    lp.setMargins(2, 0, 2, 0);

    contentScreenRoot.addView(contentView, lp);
    ViewGroup contentViewParent = (ViewGroup) this.getLayoutInflater().inflate(layoutId, null);
    ViewGroup contentView = (ViewGroup) contentViewParent.findViewById(viewToBorderId);

    GradientDrawable gd ;
    gd = (GradientDrawable) contentView.getBackground();
    if (gd == null){
        contentView.setBackgroundResource(R.drawable.content_screen_borders_no_rounding);
        gd = (GradientDrawable) contentView.getBackground();
    }

    gd.setCornerRadii(new float[]{0,0,0,0,0,0,20-3,20-3});

    contentView.setBackgroundDrawable(gd);

R.drawable.content_screen_borders_no_rounding

    <?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    >
    <stroke
        android:width="@dimen/content_screen_scroll_view_border"
        android:color="@color/content_screen_scroll_view_border"
        />
    <padding
        android:left="0dip"
        android:top="@dimen/content_screen_scroll_view_border"             
        android:right="0dip" 
        android:bottom="@dimen/content_screen_scroll_view_border"
        />
    <gradient
        android:angle="270"
        android:startColor="@color/listview_selected_item_start"
        android:endColor="@color/listview_selected_item_end"
        android:type="linear"
        />
</shape>

The weird thing is that if I set the background in advance using android:background="@drawable/content_screen_borders_no_rounding" then it works ok. The border is there and when I do the last bit of code for the rounding of the corner it works. It's only when I do the whole lot from within the code that it fails.

The "base" layout into which other layout are inserted:

<?xml version="1.0" encoding="UTF-8"?>

<RelativeLayout
    android:id="@+id/content_screen_secondary_title"
    android:layout_width="fill_parent"
    android:layout_height="wrap_content"
    android:layout_marginBottom="5dip"
    >

    <ImageView 
        android:id="@+id/content_screen_icon"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:paddingLeft="20dip"
        android:paddingRight="20dip"
        android:layout_alignParentLeft="true"
        android:gravity="top|left"
        />

    <!-- The following RelativeLayout container is required to force the Hebrew text on some devices to appear at the right of the background image instead of the left on certain devices -->
    <RelativeLayout
        android:id="@+id/content_screen_helper"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_toRightOf="@id/content_screen_icon"
        android:background="@drawable/title_bg"
        android:layout_alignParentRight="true"
        android:gravity="center_vertical"
        android:layout_centerVertical="true"
        >

        <TextView
            android:id="@+id/content_screen_title_text"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textColor="@color/content_text_color"
            android:textSize="18sp"
            android:textStyle="bold"
            android:gravity="center_vertical|right"
            android:layout_alignParentRight="true"
            android:paddingRight="25dip"
            />

    </RelativeLayout>

</RelativeLayout>

<RelativeLayout
    android:id="@+id/content_screen_user_details"
    android:layout_width="fill_parent"
    android:layout_height="wrap_content"
    android:background="@drawable/user_details_bg"
    android:layout_below="@id/content_screen_secondary_title"
    android:layout_marginBottom="4dip"
    android:layout_marginLeft="20dip"
    android:visibility="gone"
    >
    <!-- value for visibility can be either 'visible' or 'gone' -->

    <TextView
        android:id="@+id/content_screen_user_name_prompt"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentRight="true"
        android:paddingRight="25dip"
        android:text="@string/content_screen_name_prompt"
        android:textSize="12sp"
        android:textColor="@color/content_text_color"
        android:layout_centerVertical="true"
        android:gravity="center_vertical"
        />
    <TextView
        android:id="@+id/content_screen_user_name"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_toLeftOf="@id/content_screen_user_name_prompt"
        android:paddingRight="5dip"
        android:textSize="12sp"
        android:textColor="@color/content_text_color"
        android:layout_centerVertical="true"
        android:gravity="center_vertical"
        />
    <TextView
        android:id="@+id/content_screen_user_id_prompt"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_toRightOf="@+id/content_screen_user_id"
        android:layout_centerVertical="true"
        android:paddingLeft="5dip"
        android:text="@string/content_screen_id_prompt"
        android:textSize="12sp"
        android:textColor="@color/content_text_color"
        />
    <TextView
        android:id="@+id/content_screen_user_id"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentLeft="true"
        android:layout_centerVertical="true"
        android:paddingLeft="20dip"
        android:textSize="12sp"
        android:textColor="@color/content_text_color"
        />

</RelativeLayout>

<ScrollView
    android:id="@+id/content_screen_scroll_view"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:layout_below="@id/content_screen_user_details"
    android:background="@drawable/content_screen_borders"
    android:layout_marginRight="10dip"
    android:layout_marginLeft="10dip"
    android:layout_marginBottom="10dip"
    android:layout_marginTop="@dimen/content_screen_scroll_view_margintop"
    android:visibility="gone"
    >
    <!-- Set visibility to gone, until the user calls the method: setMainContent(), which causes this ScrollView to become visible and also assigns it with its content -->

</ScrollView>

<!-- The following RelativeLayyout container is required to make the Hebrew text on some devices to start at the right of the background image instead of the left -->
<RelativeLayout
    android:id="@+id/content_screen_details_container"
    android:layout_width="150dip"
    android:layout_height="wrap_content"
    android:layout_marginRight="10dip"
    android:layout_above="@id/content_screen_scroll_view"
    android:background="@drawable/details_bg"
    android:gravity="center_vertical|right"
    android:layout_alignParentRight="true"
    android:visibility="invisible"
    >
    <!-- Value for visibility can be 'visible' or 'invisible' -->

    <TextView
        android:id="@+id/content_screen_details"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:textColor="@color/content_text_color"
        android:layout_centerVertical="true"
        android:gravity="center_vertical|right"
        android:paddingRight="10dip"
        />

</RelativeLayout>

Then I call the above code to add something.

This is the sort of thing that I would add:

<LinearLayout
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:orientation="vertical"
    >

    <ListView
        android:id="@+id/searchable_list_list_view"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content" 
        android:paddingLeft="2dip" 
        android:paddingRight="2dip" 
        android:dividerHeight="1dip"
        android:footerDividersEnabled="true"
        android:listSelector="@drawable/listview_selected_item_background"
        android:fadingEdge="none"
        android:cacheColorHint = "#00000000"

        >

    </ListView>


</LinearLayout>

I would call the above method passing the layout as the first id and the id of "searchable_list_list_view" as the send. This tells it to insert this layout in the screen and to put a border around that specific view.

Upvotes: 2

Views: 6830

Answers (1)

Fuzzical Logic
Fuzzical Logic

Reputation: 13015

theblitz,

You state that it is only after you try to do the whole thing in code that it does not work. This implies that you changed the code in order to enhance the function. After scrutinizing your code to the finest detail, I believe the error here is that you are inflating the View twice, adding it once, and changing the background of the unadded View. This probably happened when making the change. I'll explain:

At the beginning of your block:

ViewGroup contentView = (ViewGroup) this.getLayoutInflater().inflate(layoutId, null);

Just a little later, you add the new View:

contentScreenRoot.addView(contentView, lp);

You haven't done any background stuff yet, so then we enter the next part.

ViewGroup contentViewParent = (ViewGroup) this.getLayoutInflater().inflate(layoutId, null);

This has the same ID as contentView, so we know you are inflating the same layout. However, no addView is ever performed so it kinda just sits there and will disappear at some later time. Obviously, you couldn't have the parent and view be the same, so you got the actual view from your parent.

ViewGroup contentView = (ViewGroup) contentViewParent.findViewById(viewToBorderId);

There it is, except there is one problem. First, contentView has already been defined. Second, it is finding the View inside a Group that has not been added. It changes the background of the new contentView, but then doesn't do anything else because it is never displayed.

Proposed Solution(s):

Change your code to the following (comments explain the changes)

// --> Rename this variable. It IS the inflated Parent and we only need to do this once.
  ViewGroup contentViewParent = (ViewGroup) this.getLayoutInflater().inflate(layoutId, null);
  RelativeLayout contentScreenRoot = (RelativeLayout) this.findViewById(R.id.content_screen_root);
  RelativeLayout.LayoutParams lp = new RelativeLayout.LayoutParams(
    ((ScrollView) contentScreenRoot.findViewById(R.id.content_screen_scroll_view)).getLayoutParams());
  lp.addRule(RelativeLayout.BELOW, R.id.content_screen_user_details);
  lp.setMargins(2, 0, 2, 0);

// --> Align the addView statement to use the new name
  contentScreenRoot.addView(contentViewParent, lp);

// --> Delete this line completely. (see? its the same ID)
//ViewGroup contentViewParent = (ViewGroup) this.getLayoutInflater().inflate(layoutId, null);

// Now this should be using the added ViewGroup, rather than the unadded one.
// AND it is not being redefined, like it was before.
  ViewGroup contentView = (ViewGroup) contentViewParent.findViewById(viewToBorderId);

  GradientDrawable gd ;
  gd = (GradientDrawable) contentView.getBackground();
  if (gd == null){
      contentView.setBackgroundResource(R.drawable.content_screen_borders_no_rounding);
      gd = (GradientDrawable) contentView.getBackground();
  }

gd.setCornerRadii(new float[]{0,0,0,0,0,0,20-3,20-3});

contentView.setBackgroundDrawable(gd);

Hope this helps,

FuzzicalLogic

Upvotes: 1

Related Questions