Android component which presents a dismissible view from the bottom of the screen

Related tags

Layout bottomsheet
Overview

BottomSheet

Build Status Join the chat at https://gitter.im/Flipboard/bottomsheet

BottomSheet is an Android component which presents a dismissible view from the bottom of the screen. BottomSheet can be a useful replacement for dialogs and menus but can hold any view so the use cases are endless. This repository includes the BottomSheet component itself but also includes a set of common view components presented in a bottom sheet. These are located in the commons module.

BottomSheet has been used in production at Flipboard for a while now so it is thoroughly tested. Here is a GIF of it in action inside of Flipboard!

FlipUI gif

Installation

If all you want is the BottomSheet component and don't need things from commons you can skip that dependency.

repositories {
    jcenter()
}

dependencies {
    compile 'com.flipboard:bottomsheet-core:1.5.3'
    compile 'com.flipboard:bottomsheet-commons:1.5.3' // optional
}

Getting Started

Get started by wrapping your layout in a BottomSheetLayout. So if you currently have this:

<LinearLayout
    android:id="@+id/root"
    android:orientation="vertical"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <View
        android:id="@+id/view1"
        android:layout_width="match_parent"
        android:layout_height="match_parent"/>

</LinearLayout>

You would have to update it to look like this:

<com.flipboard.bottomsheet.BottomSheetLayout
    android:id="@+id/bottomsheet"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <LinearLayout
        android:id="@+id/root"
        android:orientation="vertical"
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <View
            android:id="@+id/view1"
            android:layout_width="match_parent"
            android:layout_height="match_parent"/>

    </LinearLayout>

</com.flipboard.bottomsheet.BottomSheetLayout>

Back in your activity or fragment you would get a reference to the BottomSheetLayout like any other view.

BottomSheetLayout bottomSheet = (BottomSheetLayout) findViewById(R.id.bottomsheet);

Now all you need to do is show a view in the bottomSheet:

bottomSheet.showWithSheetView(LayoutInflater.from(context).inflate(R.layout.my_sheet_layout, bottomSheet, false));

You could also use one of the sheet views from the commons module.

bottomSheet.showWithSheetView(new IntentPickerSheetView(this, shareIntent, "Share with...", new IntentPickerSheetView.OnIntentPickedListener() {
    @Override
    public void onIntentPicked(IntentPickerSheetView.ActivityInfo activityInfo) {
        bottomSheet.dismissSheet();
        startActivity(activityInfo.getConcreteIntent(shareIntent));
    }
}));

That's it for the simplest of use cases. Check out the API documentation to find out how to customize BottomSheet to fit your use cases.

For more examples, also see the Recipes wiki.

Common Components

These are located in the optional bottomsheet-commons dependency and implement common use cases for bottom sheet.

Intent Picker Menu Sheet ImagePicker Sheet
IntentPickerSheetView gif MenuSheetView gif ImagePickerSheetView gif

IntentPickerSheetView

This component presents an intent chooser in the form of a BottomSheet view. Give it an intent such as a share intent and let the user choose what activity they want to share the intent with in a BottomSheet.

Example from the sample app.

IntentPickerSheetView intentPickerSheet = new IntentPickerSheetView(MainActivity.this, shareIntent, "Share with...", new IntentPickerSheetView.OnIntentPickedListener() {
    @Override
    public void onIntentPicked(IntentPickerSheetView.ActivityInfo activityInfo) {
        bottomSheet.dismissSheet();
        startActivity(activityInfo.getConcreteIntent(shareIntent));
    }
});
// Filter out built in sharing options such as bluetooth and beam.
intentPickerSheet.setFilter(new IntentPickerSheetView.Filter() {
    @Override
    public boolean include(IntentPickerSheetView.ActivityInfo info) {
        return !info.componentName.getPackageName().startsWith("com.android");
    }
});
// Sort activities in reverse order for no good reason
intentPickerSheet.setSortMethod(new Comparator<IntentPickerSheetView.ActivityInfo>() {
    @Override
    public int compare(IntentPickerSheetView.ActivityInfo lhs, IntentPickerSheetView.ActivityInfo rhs) {
        return rhs.label.compareTo(lhs.label);
    }
});
bottomSheet.showWithSheetView(intentPickerSheet);

MenuSheetView

This component presents a BottomSheet view that's backed by a menu. It behaves similarly to the new NavigationView in the Design support library, and is intended to mimic the examples in the Material Design spec. It supports list and grid states, with the former adding further support for separators and subheaders.

Example from the sample app.

MenuSheetView menuSheetView =
        new MenuSheetView(MenuActivity.this, MenuSheetView.MenuType.LIST, "Create...", new MenuSheetView.OnMenuItemClickListener() {
            @Override
            public boolean onMenuItemClick(MenuItem item) {
                Toast.makeText(MenuActivity.this, item.getTitle(), Toast.LENGTH_SHORT).show();
                if (bottomSheetLayout.isSheetShowing()) {
                    bottomSheetLayout.dismissSheet();
                }
                return true;
            }
        });
menuSheetView.inflateMenu(R.menu.create);
bottomSheetLayout.showWithSheetView(menuSheetView);

Contributing

We welcome pull requests for bug fixes, new features, and improvements to BottomSheet. Contributors to the main BottomSheet repository must accept Flipboard's Apache-style Individual Contributor License Agreement (CLA) before any changes can be merged.

Comments
  • Null pointer exception with recyclerview

    Null pointer exception with recyclerview

    I'm wrapping BottomSheetLayout around a LinearLayout that contains a RecyclerView (which is populated with RelativeLayouts). To test it, I'm calling

    BottomSheetLayout bottomSheet = (BottomSheetLayout) v.findViewById(R.id.bottomsheet);
        bottomSheet.showWithSheetView(inflater.inflate(R.layout.fragment_layout, bottomSheet, false));
    

    at the end of the fragment's onCreateView(), after the recyclerview has already been set up.

    However, this ends up breaking the RecyclerView, as any touch input causes this stack trace:

    java.lang.NullPointerException: Attempt to invoke virtual method 'boolean android.support.v7.widget.RecyclerView$LayoutManager.canScrollVertically()' on a null object reference
            at android.support.v7.widget.RecyclerView.computeVerticalScrollOffset(RecyclerView.java:1540)
            at android.view.View.canScrollVertically(View.java:12835)
            at android.support.v4.view.ViewCompatICS.canScrollVertically(ViewCompatICS.java:35)
            at android.support.v4.view.ViewCompat$ICSViewCompatImpl.canScrollVertically(ViewCompat.java:1161)
            at android.support.v4.view.ViewCompat.canScrollVertically(ViewCompat.java:1575)
            at android.support.v4.widget.SwipeRefreshLayout.canChildScrollUp(SwipeRefreshLayout.java:643)
            at android.support.v4.widget.SwipeRefreshLayout.onInterceptTouchEvent(SwipeRefreshLayout.java:657)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:1960)
            at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2405)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2049)
            at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2405)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2049)
            at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2405)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2049)
            at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2405)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2049)
            at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2405)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2049)
            at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2405)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2049)
            at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2405)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2049)
            at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2405)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2049)
            at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2405)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2049)
            at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2405)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2049)
            at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2405)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2049)
            at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2405)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2049)
            at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2405)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2049)
            at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2405)
            at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2049)
            at com.android.internal.policy.impl.PhoneWindow$DecorView.superDispatchTouchEvent(PhoneWindow.java:2369)
            at com.android.internal.policy.impl.PhoneWindow.superDispatchTouchEvent(PhoneWindow.java:1719)
            at android.app.Activity.dispatchTouchEvent(Activity.java:2742)
            at android.support.v7.internal.view.WindowCallbackWrapper.dispatchTouchEvent(WindowCallbackWrapper.java:60)
            at android.support.v7.internal.view.WindowCallbackWrapper.dispatchTouchEvent(WindowCallbackWrapper.java:60)
            at com.android.internal.policy.impl.PhoneWindow$DecorView.dispatchTouchEvent(PhoneWindow.java:2330)
            at android.view.View.dispatchPointerEvent(View.java:8666)
            at android.view.ViewRootImpl$ViewPostImeInputStage.processPointerEvent(ViewRootImpl.java:4123)
            at android.view.ViewRootImpl$ViewPostImeInputStage.onProcess(ViewRootImpl.java:3989)
            at android.view.ViewRootImpl$InputStage.deliver(ViewRootImpl.java:3544)
            at android.view.ViewRootImpl$InputStage.onDeliverToNext(ViewRootImpl.java:3597)
            at android.view.ViewRootImpl$InputStage.forward(ViewRootImpl.java:3563)
            at android.view.ViewRootImpl$AsyncInputStage.forward
    

    Here's a screenshot of what happens:

    image

    opened by alexdao 12
  • Fix black flick

    Fix black flick

    Suppose we have two fragments. Fragment A and Fragment B. When there is a transition between B --> A, bottomsheet flicks with a black screen causing transition seems awful.

    dimView.setBackgroundColor must be set to Color.TRANSPARENT.

    opened by charbgr 12
  • Migrate to AndroidX

    Migrate to AndroidX

    Context

    We are still using this library and recently migrated to AndroidX. It seems though the Jetifier is not handling correctly some parts leading to a crash.

    Field 'androidx.fragment.app.Fragment.mContainerId' is inaccessible to class 'androidx.core.app.AccessFragmentInternals' (declaration of 'androidx.core.app.AccessFragmentInternals' appears in base.apk)
           at androidx.core.app.AccessFragmentInternals.getContainerId(AccessFragmentInternals.java:9)
    

    Contents of the PR

    • Upgrade Gradle version to 5.2.1
    • Upgrade AGP version to 3.4.0-rc01
    • Upgrade compileSdkVersion to 28
    • Upgrade appCompat dependency to version 28.0.0
    • Upgrade supportv4 dependency to version 28.0.0
    • Upgrade Glide to version 4.9.0
    • Upgrade Novoda bintray-release plugin to version 0.9
    • Update travis.yml to use android-28 version
    • Update Glide call sites for the new usage
    • Migrate project to AndroidX, using Android Studio migrator

    It would be great if this PR could be merged in or at least a new branch is created in order to allow any users with AndroidX use it as well!

    opened by pavlospt 11
  • Click X & Y are slightly off on phones

    Click X & Y are slightly off on phones

    If you place views with OnClickListeners into the bottom sheet view, only the top part of the view registers clicks on phones.

    I resolved this by copying down the source code and changing line 446 to calculate the offset and push it down further (for some reason 24dp seems to be the magic number):

    event.offsetLocation(isTablet ? getX() - sheetStartX : 0, sheetTranslation - getHeight() - (isTablet ? 0 : DesignUtils.convertDpToPixel(24)));

    in onTouchEvent(). Full method with changes:

     @Override
        public boolean onTouchEvent(@NonNull MotionEvent event) {
            if (!isSheetShowing()) {
                return false;
            }
            if (isAnimating()) {
                return false;
            } 
            if (!hasIntercepted) {
                return onInterceptTouchEvent(event);
            }
    
        ....
            } else {
                // If the user clicks outside of the bottom sheet area we should dismiss the bottom sheet.
                boolean touchOutsideBottomSheet = event.getY() < getHeight() - sheetTranslation || !isXInSheet(event.getX());
                if (event.getAction() == MotionEvent.ACTION_UP && touchOutsideBottomSheet && interceptContentTouch) {
                    dismissSheet();
                    return true;
                }
    
                /******* CHANGE MADE HERE *********/
                event.offsetLocation(isTablet ? getX() - sheetStartX : 0, sheetTranslation - getHeight() - (isTablet ? 0 : DesignUtils.convertDpToPixel(24)));
                getSheetView().dispatchTouchEvent(event);
            }
    
            return true;
        }
    

    I should put in a pull request, but I'm not confident this is the appropriate way to address this. Ran this code on Sony Xperia Z3 Compact running 5.1.1 and a LG Optimus Exceed 2 running 4.4.2 and it resolved the touch point issue. On a Barnes & Noble Nook running 4.0.4 and a Nexus 7 running 5.1.1 work fine with the code as it is currently in the project.

    needs more info 
    opened by chanakin 11
  • Why the layout?

    Why the layout?

    Why can't you use the BottomSheet as a dialog like class instead of embedding it as part of a layout? If I'm not seeing it. please let me know, but this is far more useful if can use it in that way instead of it having to be put as a wrapper in every layout.

    Thanks, I like the features, but don't see why it needs to be done in this fashion.

    opened by KennyGoers 11
  • Bug?: ImagePickerSheetView not working in tablet Nexus 7 2013

    Bug?: ImagePickerSheetView not working in tablet Nexus 7 2013

    Hi, I have the same code running on a Nexus 5 and a Nexus 7 and IntentPickerSheetView isn't working when I click over camera action or a picture. Someone has happened to this?

    Thanks

    opened by Alxzu 10
  • Interaction with views in the background

    Interaction with views in the background

    I have implemented the Flipboard bottom sheet in a app. This is implemented along with the google maps (Very similar to the bottom sheet in google maps; click on balloon -> bottom sheet comes up).

    So I have got the bottom sheet to show up when a balloon is clicked and the bottom sheet takes a very small portion of the screen. I want to let the user interact with the map fragment even though the bottom sheet is being shown. From what I understand after going through the source code and a bit of google search is that it is not possible right now. Is that correct or am I missing something? It would be awesome if you could tell me what I have missed if I have or suggest a work around.

    Thanks

    question 
    opened by aadithyb 7
  • The height of the peeked sheet is too small when the sheet is shown after keyboard is dismissed

    The height of the peeked sheet is too small when the sheet is shown after keyboard is dismissed

    When the soft keyboard is already showing, and I show the image picker sheet, the height of the peeked sheet is too small that it cuts off the contents initially.

    The following is the correct height if the keyboard has been never displayed. device-2015-11-19-122932

    This is what happens when the sheet tries to show while the keyboard is dismissing device-2015-11-19-122946

    opened by raylee4204 7
  • Added custom peek & fixed touch on sheet view to allow dragging it

    Added custom peek & fixed touch on sheet view to allow dragging it

    Hi, thanks for the library! Here I've added a programmatically custom peek.

    Also I've fixed the dragging after recent merge from a pull request. Before wasn't possible anymore to drag up the sheet view if the click was on it due to return always false in method interceptTouchEvent. Now, the return value is in conjunction with condition where click happened. Not perfectly visible in the example but if there are scrollable views below the sheet it works and you can always drag up the sheet if event is on it.

    opened by davideas 7
  • BottomSheetLayout requires a child

    BottomSheetLayout requires a child

    If BottomSheetLayout doesn't have any children it will throw an exception when trying to show a sheet. For now the work around is to throw in an empty view like below.

    <com.flipboard.bottomsheet.BottomSheetLayout
        android:id="@+id/bottomsheet"
        android:fitsSystemWindows="true"
        android:layout_width="match_parent"
        android:layout_height="match_parent">
        <View
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"/>
        </com.flipboard.bottomsheet.BottomSheetLayout>
    
    opened by nschwermann 7
  • MenuSheetView is not working in GRID mode

    MenuSheetView is not working in GRID mode

    Hello! MenuSheetView isn't showing the icons in grid mode. My code

    
    MenuSheetView menuSheetView =
                    new MenuSheetView(getActivity(), MenuSheetView.MenuType.LIST, "Create...", new MenuSheetView.OnMenuItemClickListener() {
                        @Override
                        public boolean onMenuItemClick(MenuItem item) {
                            Toast.makeText(getActivity(), item.getTitle(), Toast.LENGTH_SHORT).show();
                            if (bottomSheetLayout.isSheetShowing()) {
                                bottomSheetLayout.dismissSheet();
                            }
                            return true;
                        }
                    });
            menuSheetView.inflateMenu(R.menu.menu_sheet_add_plan);
            bottomSheetLayout.showWithSheetView(menuSheetView);
    
    
    
    <?xml version="1.0" encoding="utf-8"?>
    <menu xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:id="@+id/plan_type_payment"
        android:icon="@drawable/creditcard"
        android:title="Payment"/>
    
    <item
        android:id="@+id/menu_subheader"
        android:title=""
        >
        <menu>
            <item
                android:id="@+id/plan_type_plane"
                android:icon="@drawable/plane"
                android:title="Plane"/>
            <item
                android:id="@+id/plan_type_train"
                android:icon="@drawable/train"
                android:title="Train"/>
            <item
                android:id="@+id/plan_type_car"
                android:icon="@drawable/car"
                android:title="Car"/>
            <item
                android:id="@+id/plan_type_bus"
                android:icon="@drawable/schooolbus"
                android:title="Bus"/>
            <item
                android:id="@+id/plan_type_taxi"
                android:icon="@drawable/taxi"
                android:title="Taxi"/>
            <item
                android:id="@+id/plan_type_cruise"
                android:icon="@drawable/cruise"
                android:title="Cruise"/>
            <item
                android:id="@+id/plan_type_sailboat"
                android:icon="@drawable/sailboat"
                android:title="Sailboat"/>
            <item
                android:id="@+id/plan_type_bike"
                android:icon="@drawable/bike"
                android:title="Bike"/>
        </menu>
    </item>
    
    </menu>
    
    
    needs more info 
    opened by demogorgorn 7
  • java.lang.NullPointerException RecycyclerView

    java.lang.NullPointerException RecycyclerView

    ERROR java.lang.NullPointerException: Attempt to invoke virtual method 'void androidx.recyclerview.widget.RecyclerView.setHasFixedSize(boolean)' on a null object reference

    `package com.computerscienceknowledge.zaaruri;

    import android.content.Intent; import android.os.Bundle; import android.view.LayoutInflater; import android.view.Menu; import android.view.MenuItem; import android.view.View; import android.view.ViewGroup; import android.widget.TextView;

    import com.computerscienceknowledge.zaaruri.Model.Products; import com.computerscienceknowledge.zaaruri.Prevalent.Prevalent; import com.computerscienceknowledge.zaaruri.ViewHolder.ProductViewHolder; import com.firebase.ui.database.FirebaseRecyclerAdapter; import com.firebase.ui.database.FirebaseRecyclerOptions; import com.google.android.material.floatingactionbutton.FloatingActionButton; import com.google.android.material.navigation.NavigationView; import com.google.android.material.snackbar.Snackbar; import com.google.firebase.database.DatabaseReference; import com.google.firebase.database.FirebaseDatabase; import com.squareup.picasso.Picasso;

    import androidx.annotation.NonNull; import androidx.appcompat.app.ActionBarDrawerToggle; import androidx.appcompat.app.AppCompatActivity; import androidx.appcompat.widget.Toolbar; import androidx.core.view.GravityCompat; import androidx.drawerlayout.widget.DrawerLayout; import androidx.recyclerview.widget.LinearLayoutManager; import androidx.recyclerview.widget.RecyclerView; //import androidx.recyclerview.widget.RecyclerView; import de.hdodenhof.circleimageview.CircleImageView; import io.paperdb.Paper;

    public class HomeActivity extends AppCompatActivity implements NavigationView.OnNavigationItemSelectedListener { DrawerLayout drawerLayout; ActionBarDrawerToggle toggle; Toolbar toolbar; NavigationView navigationView; View headerView; TextView userNameTextView; CircleImageView profileImageView; ProductViewHolder holder; View view; private DatabaseReference ProductsRef; private RecyclerView recyclerView; RecyclerView.LayoutManager layoutManager;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_home);
    
    
        ProductsRef = FirebaseDatabase.getInstance().getReference().child("Products");
    
        Paper.init(this);
    
    
        toolbar = findViewById(R.id.toolBar);
        toolbar.setTitle("Home");
        setSupportActionBar(toolbar);
    
    
        FloatingActionButton fab = findViewById(R.id.fab);
        fab.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Snackbar.make(view, "Replace with your own action", Snackbar.LENGTH_LONG)
                        .setAction("Action", null).show();
            }
        });
    
    
        drawerLayout =  findViewById(R.id.drawer);
        toggle = new ActionBarDrawerToggle(this, drawerLayout,toolbar,R.string.open,R.string.close);
        drawerLayout.addDrawerListener(toggle);
        toggle.syncState();
    
    
        navigationView = findViewById(R.id.nav_view);
        navigationView.setNavigationItemSelectedListener(this);
    
        headerView = navigationView.getHeaderView(0);
        userNameTextView = headerView.findViewById(R.id.user_profile_name);
        profileImageView = headerView.findViewById(R.id.user_profile_image);
        userNameTextView.setText(Prevalent.currentOnlineUser.getName());
    
        //   Picasso.get().load(Prevalent.currentOnlineUser.getImage()).placeholder(R.drawable.profile).into(profileImageView);
    
        recyclerView = findViewById(R.id.recycler_menu);
        recyclerView.setHasFixedSize(true);
        layoutManager = new LinearLayoutManager(this);
        recyclerView.setLayoutManager(layoutManager);
    }
    
    
    @Override
    protected void onStart()
    {
        super.onStart();
    
        FirebaseRecyclerOptions<Products> options =
                new FirebaseRecyclerOptions.Builder<Products>()
                        .setQuery(ProductsRef, Products.class)
                        .build();
    
        FirebaseRecyclerAdapter<Products,ProductViewHolder> adapter =
                new FirebaseRecyclerAdapter<Products, ProductViewHolder>(options) {
                    @Override
                    protected void onBindViewHolder(@NonNull ProductViewHolder holder, int position, @NonNull Products model)
                    {
                        holder.txtProductName.setText(model.getPname());
                        holder.txtProductDescription.setText(model.getDescription());
                        holder.txtProductPrice.setText("Price = " + model.getPrice() + "₹");
                        Picasso.get().load(model.getImage()).into(holder.imageView);
                    }
    
                    @NonNull
                    @Override
                    public ProductViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType)
                    {
                        view = LayoutInflater.from(parent.getContext()).inflate(R.layout.product_items_layout, parent, false);
                        holder = new ProductViewHolder(view);
                        return holder;
                    }
                };
    
        recyclerView.setAdapter(adapter);
        adapter.startListening();
    }
    
    @Override
    public void onBackPressed() {
        drawerLayout = findViewById(R.id.drawer);
        if (drawerLayout.isDrawerOpen(GravityCompat.START)) {
            drawerLayout.closeDrawer(GravityCompat.START);
        } else {
            super.onBackPressed();
        }
    }
    
    
    
    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
         getMenuInflater().inflate(R.menu.home, menu);
        return true;
    }
    
    
    
    @Override
    public boolean onOptionsItemSelected(MenuItem item)
    {
        int id = item.getItemId();
    

    /* if (id == R.id.action_settings) { return true; } */ return super.onOptionsItemSelected(item); }

    @SuppressWarnings("StatementWithEmptyBody")
    @Override
    public boolean onNavigationItemSelected(MenuItem item)
    {
        // Handle navigation view item clicks here.
        int id = item.getItemId();
    
        if (id == R.id.nav_cart)
        {
    
        }
        else if (id == R.id.nav_orders)
        {
    
        }
        else if (id == R.id.nav_categories)
        {
    
        }
        else if (id == R.id.nav_settings)
        {
            //  Intent intent = new Intent(HomeActivity.this, SettinsActivity.class);
            // startActivity(intent);
        }
        else if (id == R.id.nav_logout)
        {
            Paper.book().destroy();
    
            Intent intent = new Intent(HomeActivity.this, MainActivity.class);
            intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK);
            startActivity(intent);
            finish();
        }
    
        DrawerLayout drawer =  findViewById(R.id.drawer);
        drawer.closeDrawer(GravityCompat.START);
        return true;
    }
    

    } `

    content_home.xml

    `

    <androidx.recyclerview.widget.RecyclerView
        android:id="@+id/recycler_menu"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:scrollbars="vertical">
    
    </androidx.recyclerview.widget.RecyclerView>
    

    `

    opened by shriabhishekmishra 0
  • Dialog shadow is not appearing in front of status bar.

    Dialog shadow is not appearing in front of status bar.

    This is actually not an issue but I really want to know that how is your dialog shadow does not appear on the status bar. I'm trying to accomplish this task from past 1 week. Please help

    opened by shahishasank 0
  • Bug: bottom sheet looks almost non-existing when on landscape

    Bug: bottom sheet looks almost non-existing when on landscape

    I tried this piece of code:

        val galleryIntent: Intent = Intent(Intent.ACTION_GET_CONTENT)
        galleryIntent.type = "image/*"
        val intentPickerSheetView = IntentPickerSheetView(this, galleryIntent, "Share with...", IntentPickerSheetView.OnIntentPickedListener { activityInfo ->
            bottomsheet.dismissSheet()
        })
        bottomsheet.showWithSheetView(intentPickerSheetView)
    

    It works, but on landscape I get this tiny bottom sheet:

    image

    How come?

    Attached sample project.

    My Application.zip

    opened by AndroidDeveloperLB 1
  • BottomSheetFragment expands by himself when I remove elements from the view.

    BottomSheetFragment expands by himself when I remove elements from the view.

    Hi All.

    I am not sure if this is a known problem, but I could'n find anything similar. I hope someone can help me.

    I am Using a BottomSheetFragment to show details from certain Object. But the thing is that in some cases I need to change the visibility of a few elements to "GONE", like there are things that need to be show when the Fragment is expanded or in peek state. But when is removed an element, the BottomSheetFragment expands. And in some times doesn't let me get dismiss the Fragment.

    Thank you for your attention.

    opened by Balthair94 0
  • Bug in height size after expanded list

    Bug in height size after expanded list

    in landscape orientation when i expand bottomsheet and changing orientation my menu has many space from bottom of screen and i must to sweep again to resolve this problem

    ScreenShots

    http://www.rupload.ir/upload/2id6m56bv2jjwg8ww2u0.jpg

    http://www.rupload.ir/upload/j0nl2l06yl4bsrzrgec.jpg

    opened by pishguy 0
Releases(v1.5.3)
  • v1.5.3(Nov 29, 2016)

  • v1.5.2(Sep 9, 2016)

    Core

    • Fix scrolling issue when the BottomSheet contains a ViewPager with RecyclerViews inside

    Commons

    • Add a way to specify custom layouts for list items and grid items in MenuSheetView
    • Fix grid items text getting cut off when text is scaled to extra large
    Source code(tar.gz)
    Source code(zip)
  • v1.5.1(May 26, 2016)

    Core

    • Fixed duplicate state change notifications
    • Fixed possible incorrect sheet position and dimming

    Commons

    • IntentPickerSheet works below API 16
    Source code(tar.gz)
    Source code(zip)
  • v1.5.0(Dec 1, 2015)

    • Introducing BottomSheetFragment (https://github.com/Flipboard/bottomsheet/pull/79) in the commons module
    • Support for multiple state and dismiss listeners on a single sheet (https://github.com/Flipboard/bottomsheet/pull/86). Note: this is a breaking API change for listeners. Change your calls from setOnStateChangeListener to addOnStateChangeListener. Make sure to remove your listeners with a call to removeOnStateChangeListener after they're no longer useful, or you'll create a memory leak
    • Fixed sheets sometimes being in the wrong position with dynamic sizing (https://github.com/Flipboard/bottomsheet/issues/80)
    Source code(tar.gz)
    Source code(zip)
  • 1.4.3(Sep 16, 2015)

    Fixes mix-ins not working properly when using the getConcreteIntent method. Note: because of the changes required to fix that issue, there was a breaking change to the API for mix-ins

    Source code(tar.gz)
    Source code(zip)
  • 1.4.2(Sep 11, 2015)

    This release changes sheets are handled when a sheet is requested while another is already visible. Now, instead of throwing a RuntimeException, it will animate out the existing sheet and then show the new one afterward. This is a more natural behavior, and doesn't require developers to manage this themselves.

    Source code(tar.gz)
    Source code(zip)
  • 1.4.1(Sep 11, 2015)

    This release changes the behavior of the dim view to be INVISIBLE during the hidden state. This should ensure that it doesn't cause some undesired behavior on media views, such as using the Youtube SDK

    Source code(tar.gz)
    Source code(zip)
  • 1.4.0(Sep 1, 2015)

    Commons

    • Introducing ImagePickerSheetView! This is a SheetView that can be used to pick images from local storage, while also offering placeholder options for camera and picking. Android doesn't have a nice built-in option for having the user choose between a camera or local storage, so hopefully this will be a good utility for the community.
    • Check out the sample for some example usage, including intents to use for camera and picker tiles.
    ImagePickerSheetView sheetView = new ImagePickerSheetView.Builder(this)
            .setMaxItems(30)
            .setShowCameraOption(createCameraIntent() != null)
            .setShowPickerOption(createPickIntent() != null)
            .setImageProvider(new ImagePickerSheetView.ImageProvider() {
                @Override
                public void onProvideImage(ImageView imageView, Uri imageUri, int size) {
                    Glide.with(ImagePickerActivity.this)
                            .load(imageUri)
                            .centerCrop()
                            .crossFade()
                            .into(imageView);
                }
            })
            .setOnTileSelectedListener(new ImagePickerSheetView.OnTileSelectedListener() {
                @Override
                public void onTileSelected(ImagePickerSheetView.ImagePickerTile selectedTile) {
                    bottomSheetLayout.dismissSheet();
                    if (selectedTile.isCameraTile()) {
                        dispatchTakePictureIntent();
                    } else if (selectedTile.isPickerTile()) {
                        startActivityForResult(createPickIntent(), REQUEST_LOAD_IMAGE);
                    } else if (selectedTile.isImageTile()) {
                        showSelectedImage(selectedTile.getImageUri());
                    } else {
                        genericError();
                    }
                }
            })
            .setTitle("Choose an image...")
            .create();
    
    bottomSheetLayout.showWithSheetView(sheetView);
    
    • Fix: GridView columns not appearing sometimes on API < 17
    • Improvement: Sheets on tablets will now default to a reasonable width, and will no longer default/force MATCH_PARENT. You can still use MATCH_PARENT by setting your own LayoutParams on the sheet view before passing it in.
    • Improvement: Sheets on both phones and tablets will default to WRAP_CONTENT. You can still use MATCH_PARENT by setting your own LayoutParams on the sheet view before passing it in.
    • Improvement: Icons in the intent picker sheet are lazily loaded in the background, which should substantially reduce delay when opening.
    • Breaking API change: OnIntentPickedListener#onIntentPicked will now return the full ActivityInfo rather than the intent. This is to provide more flexibility and allow usage of its new tag field for storing other information.
      • To recreate the concrete intent, you can call the new getConcreteIntent(Intent) method.
    public Intent getConcreteIntent(Intent intent) {
                Intent concreteIntent = new Intent(intent);
                concreteIntent.setComponent(componentName);
                return concreteIntent;
            }
    

    BottomSheetLayout

    • New: Added methods for setting custom peek translations (@davideas)
    • New: Added two helper functions: predictedDefaultWidth and isTablet. These are for retrieving what BottomSheetLayout thinks its width and whether or not it is on a tablet.
    • Fix: Sheets not staying anchored to the bottom of the screen in some places
    • Fix: InterceptContentTouch flag not being handled correctly, which would sometimes cause problems with intercepting touches on the sheet view
    • Fix: Prevent the layout from rendering the sheet undismissable in race conditions (#48)

    Sample

    • We've included an ImagePicker demo, complete with image loading and intent handling.

    Enjoy!

    ImagePicker gif

    Source code(tar.gz)
    Source code(zip)
    bottomsheet-commons-javadoc.jar(73.89 KB)
    bottomsheet-commons-release.aar(44.69 KB)
    bottomsheet-commons-sources.jar(12.39 KB)
    bottomsheet-javadoc.jar(43.41 KB)
    bottomsheet-release.aar(19.78 KB)
    bottomsheet-sample-debug.apk(1.24 MB)
    bottomsheet-sources.jar(9.22 KB)
  • 1.3(Jul 23, 2015)

    Commons

    • Introducing MenuSheetView! This is a SheetView that can represent a menu resource as a list or grid.
      • A list can support submenus, and will include a divider and header for them where appropriate. Grids currently don't support submenus and don't in the Material Design spec either.
      • You can retrieve the underlying Menu instance via getMenu() and dynamically add your own items. Just make sure you call updateMenu() after you're done!
    MenuSheetView menuSheetView =
            new MenuSheetView(MenuActivity.this, menuType, "Create...", new MenuSheetView.OnMenuItemClickListener() {
                @Override
                public boolean onMenuItemClick(MenuItem item) {
                    Toast.makeText(MenuActivity.this, item.getTitle(), Toast.LENGTH_SHORT).show();
                    if (bottomSheetLayout.isSheetShowing()) {
                        bottomSheetLayout.dismissSheet();
                    }
                    return true;
                }
            });
    menuSheetView.inflateMenu(R.menu.create);
    bottomSheetLayout.showWithSheetView(menuSheetView);
    
    • Commons sheets have an appropriate shadow and elevation now. Unfortunately, we can't build this into BottomSheetLayout, but we've added a recipe explaining how to add this to your own sheets.
      • Issue #4

    BottomSheetLayout

    • Back press handling is handled now. Default behavior is to dismiss the entire sheet on back press, regardless of state. You can customize this via a new setPeekOnDismiss(boolean) API. Setting this to true will cause an expanded sheet collapse to the peeked state on back press, rather than dismissing.
      • PR #14, issue #10
      • Thanks to @iPaulPro and @evant for the discussion on this

    Sample

    • We've given the sample a little UI refresh and made it easier to add more commons examples in the future.

    Enjoy!

    MenuSheetView gif

    Source code(tar.gz)
    Source code(zip)
  • v1.1(Jun 8, 2015)

Owner
Flipboard
Flipboard
Android library used to create an awesome Android UI based on a draggable element similar to the last YouTube graphic component.

Draggable Panel DEPRECATED. This project is not maintained anymore. Draggable Panel is an Android library created to build a draggable user interface

Pedro Vicente Gómez Sánchez 3k Jan 5, 2023
Android library used to create an awesome Android UI based on a draggable element similar to the last YouTube New graphic component.

Please switch to DragView, for the best support, thank you DraggablePanel Download allprojects { repositories { ... maven { url 'https://jitp

Hoàng Anh Tuấn 103 Oct 12, 2022
This component like SwipeRefreshLayout, it is more beautiful than SwipeRefreshLayout.

android-PullRefreshLayout This component like SwipeRefreshLayout, it is more beautiful than SwipeRefreshLayout. Demo Usage Add dependency. dependencie

星一 2.1k Dec 3, 2022
A 3D Layout for Android,When you use it warp other view,it can became a 3D view,一秒让你的view拥有3D效果!

ThreeDLayout A 3D Layout,When you use it warp other view,it can became a 3D view 中文文档 preview USAGE 1.compile library allprojects { repositories {

androidwing 490 Oct 27, 2022
null 2.4k Dec 30, 2022
An Android Layout which has a same function like https://github.com/romaonthego/RESideMenu

ResideLayout An Android Layout which has a same function like https://github.com/romaonthego/RESideMenu. Can be used on Android 1.6(I haven't try it.)

Yang Hui 392 Oct 12, 2022
Draftsman is an on device layout inspector which can be embedded in your android app.

Draftsman Draftsman is an on-device layout inspector for Android apps. It allows you to view various properties of rendered Android Views such as widt

Gojek 243 Dec 22, 2022
a custom pull-to-refresh layout which contains a interesting animation

This is a project with custom pull-to-refresh layout which contains a interesting animation. And the animation is inspired by https://dribbble.com/sho

ZhangLei 1.8k Dec 27, 2022
A custom ViewPager title strip which gives continuous feedback to the user when scrolling

SmartTabLayout A custom ViewPager title strip which gives continuous feedback to the user when scrolling. This library has been added some features an

ogaclejapan 7k Jan 7, 2023
Linear Layout Manager which supports WRAP_CONTENT

Linear Layout Manager DEPRECATED RecyclerView supports WRAP_CONTENT starting from Android Support Library 23.2. More details here: http://android-deve

Sergey Solovyev 418 Nov 10, 2022
A wave view of android,can be used as progress bar.

WaveView ![Gitter](https://badges.gitter.im/Join Chat.svg) A wave view of android,can be used as progress bar. Screenshot APK demo.apk What can be use

Kai Wang 1.3k Dec 28, 2022
TileView is a subclass of android.view.ViewGroup that asynchronously displays, pans and zooms tile-based images. Plugins are available for features like markers, hotspots, and path drawing.

This project isn't maintained anymore. It is now recommended to use https://github.com/peterLaurence/MapView. MapView is maintained by Peter, one of o

Mike Dunn 1.5k Nov 21, 2022
A swipeable - auto resizing view group for android

SwipeableLayout A swipeable - auto resizing view group for android Usage build.gradle compile 'com.wmbest.widget:swipeable-layout:1.0.+@aar' -- or --

Bill Best 114 Nov 25, 2022
Bubble View for Android.

BubbleLayout Bubble View for Android with custom stroke width and color, arrow size, position and direction. BubbleLayout Extends the FrameLayout. Gra

Masayuki Suda 964 Dec 28, 2022
Show triangle view.

TriangleLabelView Show triangle view. How to Use To see how the TriangleLabelView are added to your xml layouts, check the sample project. <jp.shts.an

Shota Saito 877 Dec 6, 2022
VoronoiView is a view (ViewGroup) that allows you to add and display views inside Voronoi diagram regions.

Vorolay VoronoiView is a view (ViewGroup) that allows you to add and display views inside Voronoi diagram regions. [Voronoi diagram] (https://en.wikip

Daniil Jurjev 918 Dec 4, 2022
A library for showing different types of layouts when a list view is empty

Android Empty Layout Please note that this project is not being maintained now. Hopefully a new version will be available soon. A library for showing

Raquib-ul Alam (Kanak) 606 Nov 26, 2022
Material Design Search View Layout, now implemented in Google Maps, Dialer, etc

THIS PROJECT IS DEPRECATED Component is not maintained anymore. Implementation of Lollipop+ Dialer and Google Maps. DEMO Add in View Add to your layou

Sahil Dave 1.1k Dec 22, 2022