How to show shadow around the linearlayout in Android?

前端 未结 13 2354
名媛妹妹
名媛妹妹 2020-11-27 10:51

How can I show shadow for my linear layout. I want white colored rounded background with shadow around the linearlayout. I have done this so far.



        
相关标签:
13条回答
  • 2020-11-27 11:00

    I know this is old, but most of these answers require a ton of extra code.

    If you have a light colored background, you can simply use this:

    android:elevation="25dp"
    
    0 讨论(0)
  • 2020-11-27 11:02

    Actually I agree with @odedbreiner but I put the dialog_frame inside the first layer and hide the black background under the white layer.

        <?xml version="1.0" encoding="utf-8"?>
    <layer-list xmlns:android="http://schemas.android.com/apk/res/android">
        <item
            android:drawable="@android:drawable/dialog_frame"
            android:right="2dp" android:left="2dp" android:bottom="2dp" android:top="5dp" >
            <shape android:shape="rectangle">
                <corners android:radius="5dp"/>
            </shape>
        </item>
        <item>
            <shape
                android:shape="rectangle">
                <solid android:color="@android:color/white"/>
                <corners android:radius="5dp"/>
            </shape>
        </item>
    </layer-list>
    
    0 讨论(0)
  • 2020-11-27 11:02

    set this xml drwable as your background;---

    <?xml version="1.0" encoding="utf-8"?>
    <layer-list xmlns:android="http://schemas.android.com/apk/res/android" >
    
    <!-- Bottom 2dp Shadow -->
    <item>
        <shape android:shape="rectangle" >
            <solid android:color="#d8d8d8" />-->Your shadow color<--
    
            <corners android:radius="15dp" />
        </shape>
    </item>
    
    <!-- White Top color -->
    <item android:bottom="3px" android:left="3px" android:right="3px" android:top="3px">-->here you can customize the shadow size<---
        <shape android:shape="rectangle" >
            <solid android:color="#FFFFFF" />
    
            <corners android:radius="15dp" />
        </shape>
    </item>
    
    </layer-list>
    
    0 讨论(0)
  • 2020-11-27 11:04

    For lollipop and above you can use elevation.

    For older versions:

    Here is a lazy hack from: http://odedhb.blogspot.com/2013/05/android-layout-shadow-without-9-patch.html

    (toast_frame does not work on KitKat, shadow was removed from toasts)

    just use:

    android:background="@android:drawable/toast_frame"
    

    or:

    android:background="@android:drawable/dialog_frame"
    

    as a background

    examples:

    <TextView
            android:layout_width="fill_parent"
            android:text="I am a simple textview with a shadow"
            android:layout_height="wrap_content"
            android:textSize="18sp"
            android:padding="16dp"
            android:textColor="#fff"
            android:background="@android:drawable/toast_frame"
            />
    

    and with different bg color:

    <LinearLayout
            android:layout_height="64dp"
            android:layout_width="fill_parent"
            android:gravity="center"
            android:background="@android:drawable/toast_frame"
            android:padding="4dp"
            >
        <Button
                android:layout_width="fill_parent"
                android:layout_height="fill_parent"
                android:text="Button shadow"
                android:background="#33b5e5"
                android:textSize="24sp"
                android:textStyle="bold"
                android:textColor="#fff"
                android:layout_gravity="center|bottom"
                />
    
    </LinearLayout>
    
    0 讨论(0)
  • 2020-11-27 11:07

    You can use following class for xml tag:

    import android.annotation.SuppressLint;
    import android.content.Context;
    import android.content.res.TypedArray;
    import android.graphics.Bitmap;
    import android.graphics.BlurMaskFilter;
    import android.graphics.Canvas;
    import android.graphics.Color;
    import android.graphics.Paint;
    import android.graphics.PorterDuff;
    import android.graphics.Rect;
    import android.os.Build;
    import android.support.annotation.FloatRange;
    import android.util.AttributeSet;
    import android.view.ViewGroup;
    import android.view.ViewTreeObserver;
    import android.widget.FrameLayout;
    
    import com.webappmate.weeassure.R;
    
    /**
     * Created by GIGAMOLE on 13.04.2016.
     */
    public class ShadowLayout extends FrameLayout {
    
        // Default shadow values
        private final static float DEFAULT_SHADOW_RADIUS = 30.0F;
        private final static float DEFAULT_SHADOW_DISTANCE = 15.0F;
        private final static float DEFAULT_SHADOW_ANGLE = 45.0F;
        private final static int DEFAULT_SHADOW_COLOR = Color.DKGRAY;
    
        // Shadow bounds values
        private final static int MAX_ALPHA = 255;
        private final static float MAX_ANGLE = 360.0F;
        private final static float MIN_RADIUS = 0.1F;
        private final static float MIN_ANGLE = 0.0F;
        // Shadow paint
        private final Paint mPaint = new Paint(Paint.ANTI_ALIAS_FLAG) {
            {
                setDither(true);
                setFilterBitmap(true);
            }
        };
        // Shadow bitmap and canvas
        private Bitmap mBitmap;
        private final Canvas mCanvas = new Canvas();
        // View bounds
        private final Rect mBounds = new Rect();
        // Check whether need to redraw shadow
        private boolean mInvalidateShadow = true;
    
        // Detect if shadow is visible
        private boolean mIsShadowed;
    
        // Shadow variables
        private int mShadowColor;
        private int mShadowAlpha;
        private float mShadowRadius;
        private float mShadowDistance;
        private float mShadowAngle;
        private float mShadowDx;
        private float mShadowDy;
    
        public ShadowLayout(final Context context) {
            this(context, null);
        }
    
        public ShadowLayout(final Context context, final AttributeSet attrs) {
            this(context, attrs, 0);
        }
    
        public ShadowLayout(final Context context, final AttributeSet attrs, final int defStyleAttr) {
            super(context, attrs, defStyleAttr);
    
            setWillNotDraw(false);
            setLayerType(LAYER_TYPE_HARDWARE, mPaint);
    
            // Retrieve attributes from xml
            final TypedArray typedArray = context.obtainStyledAttributes(attrs, R.styleable.ShadowLayout);
    
            try {
                setIsShadowed(typedArray.getBoolean(R.styleable.ShadowLayout_sl_shadowed, true));
                setShadowRadius(
                        typedArray.getDimension(
                                R.styleable.ShadowLayout_sl_shadow_radius, DEFAULT_SHADOW_RADIUS
                        )
                );
                setShadowDistance(
                        typedArray.getDimension(
                                R.styleable.ShadowLayout_sl_shadow_distance, DEFAULT_SHADOW_DISTANCE
                        )
                );
                setShadowAngle(
                        typedArray.getInteger(
                                R.styleable.ShadowLayout_sl_shadow_angle, (int) DEFAULT_SHADOW_ANGLE
                        )
                );
                setShadowColor(
                        typedArray.getColor(
                                R.styleable.ShadowLayout_sl_shadow_color, DEFAULT_SHADOW_COLOR
                        )
                );
            } finally {
                typedArray.recycle();
            }
        }
    
        @Override
        protected void onDetachedFromWindow() {
            super.onDetachedFromWindow();
            // Clear shadow bitmap
            if (mBitmap != null) {
                mBitmap.recycle();
                mBitmap = null;
            }
        }
    
        public boolean isShadowed() {
            return mIsShadowed;
        }
    
        public void setIsShadowed(final boolean isShadowed) {
            mIsShadowed = isShadowed;
            postInvalidate();
        }
    
        public float getShadowDistance() {
            return mShadowDistance;
        }
    
        public void setShadowDistance(final float shadowDistance) {
            mShadowDistance = shadowDistance;
            resetShadow();
        }
    
        public float getShadowAngle() {
            return mShadowAngle;
        }
    
        @SuppressLint("SupportAnnotationUsage")
        @FloatRange
        public void setShadowAngle(@FloatRange(from = MIN_ANGLE, to = MAX_ANGLE) final float shadowAngle) {
            mShadowAngle = Math.max(MIN_ANGLE, Math.min(shadowAngle, MAX_ANGLE));
            resetShadow();
        }
    
        public float getShadowRadius() {
            return mShadowRadius;
        }
    
        public void setShadowRadius(final float shadowRadius) {
            mShadowRadius = Math.max(MIN_RADIUS, shadowRadius);
    
            if (isInEditMode()) return;
            // Set blur filter to paint
            mPaint.setMaskFilter(new BlurMaskFilter(mShadowRadius, BlurMaskFilter.Blur.NORMAL));
            resetShadow();
        }
    
        public int getShadowColor() {
            return mShadowColor;
        }
    
        public void setShadowColor(final int shadowColor) {
            mShadowColor = shadowColor;
            mShadowAlpha = Color.alpha(shadowColor);
    
            resetShadow();
        }
    
        public float getShadowDx() {
            return mShadowDx;
        }
    
        public float getShadowDy() {
            return mShadowDy;
        }
    
        // Reset shadow layer
        private void resetShadow() {
            // Detect shadow axis offset
            mShadowDx = (float) ((mShadowDistance) * Math.cos(mShadowAngle / 180.0F * Math.PI));
            mShadowDy = (float) ((mShadowDistance) * Math.sin(mShadowAngle / 180.0F * Math.PI));
    
            // Set padding for shadow bitmap
            final int padding = (int) (mShadowDistance + mShadowRadius);
            setPadding(padding, padding, padding, padding);
            requestLayout();
        }
    
        private int adjustShadowAlpha(final boolean adjust) {
            return Color.argb(
                    adjust ? MAX_ALPHA : mShadowAlpha,
                    Color.red(mShadowColor),
                    Color.green(mShadowColor),
                    Color.blue(mShadowColor)
            );
        }
    
        @Override
        protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
            super.onMeasure(widthMeasureSpec, heightMeasureSpec);
    
            // Set ShadowLayout bounds
            mBounds.set(
                    0, 0, MeasureSpec.getSize(widthMeasureSpec), MeasureSpec.getSize(heightMeasureSpec)
            );
        }
    
        @Override
        public void requestLayout() {
            // Redraw shadow
            mInvalidateShadow = true;
            super.requestLayout();
        }
    
        @Override
        protected void dispatchDraw(final Canvas canvas) {
            // If is not shadowed, skip
            if (mIsShadowed) {
                // If need to redraw shadow
                if (mInvalidateShadow) {
                    // If bounds is zero
                    if (mBounds.width() != 0 && mBounds.height() != 0) {
                        // Reset bitmap to bounds
                        mBitmap = Bitmap.createBitmap(
                                mBounds.width(), mBounds.height(), Bitmap.Config.ARGB_8888
                        );
                        // Canvas reset
                        mCanvas.setBitmap(mBitmap);
    
                        // We just redraw
                        mInvalidateShadow = false;
                        // Main feature of this lib. We create the local copy of all content, so now
                        // we can draw bitmap as a bottom layer of natural canvas.
                        // We draw shadow like blur effect on bitmap, cause of setShadowLayer() method of
                        // paint does`t draw shadow, it draw another copy of bitmap
                        super.dispatchDraw(mCanvas);
    
                        // Get the alpha bounds of bitmap
                        final Bitmap extractedAlpha = mBitmap.extractAlpha();
                        // Clear past content content to draw shadow
                        mCanvas.drawColor(0, PorterDuff.Mode.CLEAR);
    
                        // Draw extracted alpha bounds of our local canvas
                        mPaint.setColor(adjustShadowAlpha(false));
                        mCanvas.drawBitmap(extractedAlpha, mShadowDx, mShadowDy, mPaint);
    
                        // Recycle and clear extracted alpha
                        extractedAlpha.recycle();
                    } else {
                        // Create placeholder bitmap when size is zero and wait until new size coming up
                        mBitmap = Bitmap.createBitmap(1, 1, Bitmap.Config.RGB_565);
                    }
                }
    
                // Reset alpha to draw child with full alpha
                mPaint.setColor(adjustShadowAlpha(true));
                // Draw shadow bitmap
                if (mCanvas != null && mBitmap != null && !mBitmap.isRecycled())
                    canvas.drawBitmap(mBitmap, 0.0F, 0.0F, mPaint);
            }
    
            // Draw child`s
            super.dispatchDraw(canvas);
        }
    
    
    }
    

    use Tag in xml like this:

    <yourpackagename.ShadowLayout
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_alignParentBottom="true"
            android:layout_centerHorizontal="true"
            android:layout_gravity="center_horizontal"
            app:sl_shadow_color="#9e000000"
            app:sl_shadow_radius="4dp">
    <child views>
    </yourpackagename.ShadowLayout>
    

    UPDATE

    put the below code in attrs.xml in resource>>values

      <declare-styleable name="ShadowLayout">
        <attr name="sl_shadowed" format="boolean"/>
        <attr name="sl_shadow_distance" format="dimension"/>
        <attr name="sl_shadow_angle" format="integer"/>
        <attr name="sl_shadow_radius" format="dimension"/>
        <attr name="sl_shadow_color" format="color"/>
    </declare-styleable>
    
    0 讨论(0)
  • 2020-11-27 11:11

    Well, this is easy to achieve .

    Just build a GradientDrawable that comes from black and goes to a transparent color, than use parent relationship to place your shape close to the View that you want to have a shadow, then you just have to give any values to height or width .

    Here is an example, this file have to be created inside res/drawable , I name it as shadow.xml :

    <?xml version="1.0" encoding="utf-8"?>
    <shape xmlns:android="http://schemas.android.com/apk/res/android"
        android:shape="rectangle">
    
        <gradient
            android:startColor="#9444"
            android:endColor="#0000"
            android:type="linear"
            android:angle="90"> <!-- Change this value to have the correct shadow angle, must be multiple from 45 -->
        </gradient>
    
    </shape>
    

    Place the following code above from a LinearLayout , for example, set the android:layout_width and android:layout_height to fill_parent and 2.3dp, you'll have a nice shadow effect on your LinearLayout .

    <View
        android:id="@+id/shadow"
        android:layout_width="fill_parent"
        android:layout_height="2.3dp"  
        android:layout_above="@+id/id_from_your_LinearLayout" 
        android:background="@drawable/shadow">
    </View>
    

    Note 1: If you increase android:layout_height more shadow will be shown .

    Note 2: Use android:layout_above="@+id/id_from_your_LinearLayout" attribute if you are placing this code inside a RelativeLayout, otherwise ignore it.

    Hope it help someone.

    0 讨论(0)
提交回复
热议问题