11f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar/*
21f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar * Copyright (C) 2014 The Android Open Source Project
31f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar *
41f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar * Licensed under the Apache License, Version 2.0 (the "License");
51f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar * you may not use this file except in compliance with the License.
61f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar * You may obtain a copy of the License at
71f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar *
81f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar *      http://www.apache.org/licenses/LICENSE-2.0
91f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar *
101f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar * Unless required by applicable law or agreed to in writing, software
111f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar * distributed under the License is distributed on an "AS IS" BASIS,
121f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
131f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar * See the License for the specific language governing permissions and
141f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar * limitations under the License.
151f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar */
161f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
171f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyarpackage com.example.android.supportv7.widget;
181f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
191f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyarimport android.app.Activity;
201f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyarimport android.os.Bundle;
21413444125c69c7071767b1bac60d4d857097abccYigit Boyarimport android.support.v7.widget.DefaultItemAnimator;
221f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyarimport android.support.v7.widget.LinearLayoutManager;
231f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyarimport android.support.v7.widget.RecyclerView;
245b611d45d8d84bd604e6ce855f9520499ff89b68Yigit Boyarimport android.view.LayoutInflater;
251f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyarimport android.view.View;
261f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyarimport android.view.ViewGroup;
271f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyarimport android.widget.BaseAdapter;
281f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyarimport android.widget.CheckBox;
291f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyarimport android.widget.EditText;
301f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyarimport android.widget.Spinner;
311f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyarimport android.widget.TextView;
321f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
3327644c071b7fc0e1e4f91194f2a08b4aa2cf1465Aurimas Liutikasimport com.example.android.supportv7.Cheeses;
3427644c071b7fc0e1e4f91194f2a08b4aa2cf1465Aurimas Liutikasimport com.example.android.supportv7.R;
3527644c071b7fc0e1e4f91194f2a08b4aa2cf1465Aurimas Liutikasimport com.example.android.supportv7.widget.adapter.SimpleStringAdapter;
3627644c071b7fc0e1e4f91194f2a08b4aa2cf1465Aurimas Liutikasimport com.example.android.supportv7.widget.util.ConfigToggle;
3727644c071b7fc0e1e4f91194f2a08b4aa2cf1465Aurimas Liutikasimport com.example.android.supportv7.widget.util.ConfigViewHolder;
3827644c071b7fc0e1e4f91194f2a08b4aa2cf1465Aurimas Liutikas
391f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar/**
401f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar * A simple activity that can be extended to demonstrate LayoutManagers.
411f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar * <p>
421f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar * It initializes a sample adapter and a list of configuration options. Extending activities can
431f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar * define the {@link ConfigToggle} list depending on its functionality.
441f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar */
451f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyarabstract public class BaseLayoutManagerActivity<T extends RecyclerView.LayoutManager>
461f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        extends Activity {
471f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
481f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    protected T mLayoutManager;
491f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
501f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    protected RecyclerView mRecyclerView;
511f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
521f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    private ConfigToggle[] mConfigToggles;
531f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
541f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    @Override
551f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    protected void onCreate(Bundle savedInstanceState) {
561f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        super.onCreate(savedInstanceState);
571f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        setContentView(R.layout.activity_base_layout_manager);
581f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        initToggles();
591f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        initRecyclerView();
601f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        initSpinner();
611f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    }
621f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
631f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    abstract protected T createLayoutManager();
641f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
651f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    private void initRecyclerView() {
66fa2e2acf79d791a90410025daad438968550d18cAlan Viverette        mRecyclerView = findViewById(R.id.recycler_view);
671f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        mRecyclerView.setHasFixedSize(true);
681f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        mLayoutManager = createLayoutManager();
691f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        mRecyclerView.setLayoutManager(mLayoutManager);
701f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        mRecyclerView.setAdapter(createAdapter());
71413444125c69c7071767b1bac60d4d857097abccYigit Boyar        ((DefaultItemAnimator)mRecyclerView.getItemAnimator()).setSupportsChangeAnimations(true);
721f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        onRecyclerViewInit(mRecyclerView);
731f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    }
741f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
751f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    protected void onRecyclerViewInit(RecyclerView recyclerView) {
761f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
771f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    }
781f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
791f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    protected RecyclerView.Adapter createAdapter() {
801f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        return new SimpleStringAdapter(this, Cheeses.sCheeseStrings) {
811f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            @Override
821f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            public SimpleStringAdapter.ViewHolder onCreateViewHolder(ViewGroup parent,
831f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                    int viewType) {
841f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                final SimpleStringAdapter.ViewHolder vh = super
851f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                        .onCreateViewHolder(parent, viewType);
861f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                vh.itemView.setOnClickListener(new View.OnClickListener() {
871f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                    @Override
881f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                    public void onClick(View v) {
894fa1fe35a2e2f6aa8973bbb698f5191b7acc8d95Yigit Boyar                        final int pos = vh.getAdapterPosition();
904fa1fe35a2e2f6aa8973bbb698f5191b7acc8d95Yigit Boyar                        if (pos != RecyclerView.NO_POSITION && pos + 1 < getItemCount()) {
911f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                            swap(pos, pos + 1);
921f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                        }
931f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                    }
941f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                });
951f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                return vh;
961f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            }
971f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        };
981f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    }
991f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
1001f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    private void initToggles() {
1011f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        mConfigToggles = createConfigToggles();
102fa2e2acf79d791a90410025daad438968550d18cAlan Viverette        RecyclerView configView = findViewById(R.id.config_recycler_view);
1031f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        configView.setAdapter(mConfigAdapter);
1041f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        configView.setLayoutManager(new LinearLayoutManager(this, LinearLayoutManager.HORIZONTAL,
1051f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                false));
1061f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        configView.setHasFixedSize(true);
1071f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    }
1081f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
1091f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    public void onScrollClicked(View view) {
110fa2e2acf79d791a90410025daad438968550d18cAlan Viverette        final EditText scrollOffset = findViewById(R.id.scroll_offset);
111fa2e2acf79d791a90410025daad438968550d18cAlan Viverette        final CheckBox checkBox = findViewById(R.id.enable_smooth_scroll);
112fa2e2acf79d791a90410025daad438968550d18cAlan Viverette        final Spinner spinner = findViewById(R.id.spinner);
1131f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
1141f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        Integer offset = null;
1151f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        String offsetString = scrollOffset.getText().toString();
1161f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        try {
1171f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            offset = Integer.parseInt(offsetString);
1181f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        } catch (NumberFormatException ex) {
1191f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
1201f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        }
1211f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        final boolean smooth = checkBox.isChecked();
1221f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        if (offset == null) {
1231f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            scrollToPosition(smooth, spinner.getSelectedItemPosition());
1241f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        } else {
1251f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            scrollToPositionWithOffset(smooth, spinner.getSelectedItemPosition(), offset);
1261f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        }
1271f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    }
1281f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
1291f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    private void initSpinner() {
130fa2e2acf79d791a90410025daad438968550d18cAlan Viverette        final Spinner spinner = findViewById(R.id.spinner);
1311f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        spinner.setAdapter(new BaseAdapter() {
1321f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            @Override
1331f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            public int getCount() {
1341f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                return mRecyclerView.getAdapter().getItemCount();
1351f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            }
1361f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
1371f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            @Override
1381f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            public Integer getItem(int position) {
1391f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                return position;
1401f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            }
1411f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
1421f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            @Override
1431f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            public long getItemId(int position) {
1441f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                return position;
1451f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            }
1461f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
1471f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            @Override
1481f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            public View getView(int position, View convertView, ViewGroup parent) {
1491f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                if (convertView == null) {
1501f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                    convertView = new TextView(parent.getContext());
1511f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                }
1521f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                ((TextView) convertView).setText(" " + position + " ");
1531f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar                return convertView;
1541f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            }
1551f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        });
1561f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    }
1571f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
1581f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    protected void scrollToPosition(boolean smooth, int position) {
1591f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        if (smooth) {
1601f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            mRecyclerView.smoothScrollToPosition(position);
1611f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        } else {
1621f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            mRecyclerView.scrollToPosition(position);
1631f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        }
1641f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    }
1651f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
1661f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    protected void scrollToPositionWithOffset(boolean smooth, int position, int offset) {
1671f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        scrollToPosition(smooth, position);
1681f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    }
1691f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
1708faffcd819c6272f9e6537d563c8492854787968Chris Craik    protected ConfigToggle[] createConfigToggles() {
1718faffcd819c6272f9e6537d563c8492854787968Chris Craik        return new ConfigToggle[] {};
1728faffcd819c6272f9e6537d563c8492854787968Chris Craik    }
1731f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
1741f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    private RecyclerView.Adapter mConfigAdapter = new RecyclerView.Adapter<ConfigViewHolder>() {
1751f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        @Override
1761f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        public ConfigViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
1775b611d45d8d84bd604e6ce855f9520499ff89b68Yigit Boyar            return new ConfigViewHolder(LayoutInflater.from(parent.getContext())
1785b611d45d8d84bd604e6ce855f9520499ff89b68Yigit Boyar                    .inflate(R.layout.config_view_toggle, parent, false));
1791f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        }
1801f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
1811f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        @Override
1821f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        public void onBindViewHolder(ConfigViewHolder holder, int position) {
1831f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            ConfigToggle toggle = mConfigToggles[position];
1841f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            holder.bind(toggle);
1851f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        }
1861f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar
1871f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        @Override
1881f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        public int getItemCount() {
1891f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar            return mConfigToggles.length;
1901f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar        }
1911f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar    };
1921f30fc8732560027f364ad42bbc3f7db8aace8adYigit Boyar}
193