Reputation: 538
I was in need of adding a border to a CardView and the way I found to do that (here in stackoverflow) was creating a FrameLayout inside and add a shape background to it. This approach worked nicely but now I need to extend this to a custom layout to avoid duplicating this code every time I want to use this cardviewWithBorders!
The current code looks like this:
<android.support.v7.widget.CardView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="8dp"
android:elevation="4dp"
app:cardCornerRadius="4dp"
app:cardUseCompatPadding="true">
<FrameLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@drawable/shape_border_corner_radius"
android:padding="16dp">
<EditText
android:id="@+id/fieldInput"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@android:color/transparent"
android:lineSpacingMultiplier="1.5"
android:textAppearance="@style/LatoRegular"
android:textSize="16sp"
tools:hint="Type in your E-mail" />
</FrameLayout>
</android.support.v7.widget.CardView>
All I want is to have a component of the CardView and the FrameLayout which I could use like this:
<com.example.BorderCardView
android:layout_width="match_parent"
android:layout_height="wrap_content">
<content goes here />
</com.example.BorderCardView>
What can I do to achieve this behavior?
Upvotes: 1
Views: 2161
Reputation: 54204
You're in luck that your "inner" view is a FrameLayout
and that CardView
extends FrameLayout, since this means that you don't need to worry about the exact type of your child views' LayoutParams
objects.
public class BorderCardView extends CardView {
public BorderCardView(Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
protected void onFinishInflate() {
super.onFinishInflate();
FrameLayout.LayoutParams params =
new FrameLayout.LayoutParams(MATCH_PARENT, MATCH_PARENT);
FrameLayout frame = new FrameLayout(getContext());
frame.setLayoutParams(params);
frame.setBackground(/* your background drawable */);
frame.setPadding(/* your left/top/right/bottom padding */);
while (getChildCount() > 0) {
View child = getChildAt(0);
FrameLayout.LayoutParams childParams =
(FrameLayout.LayoutParams) child.getLayoutParams();
removeView(child);
frame.addView(child);
child.setLayoutParams(childParams);
}
addView(frame);
}
}
What you're doing here is dynamically creating your "inner" FrameLayout
, and then looping over all children from your layout, removing them from the CardView
and adding them to the FrameLayout
instead, and then finally adding the "inner" frame to the CardView
.
Upvotes: 3