首页 文章 精选 留言 我的

精选列表

搜索[官方],共10003篇文章
优秀的个人博客,低调大师

Ubuntu 21.10 官方壁纸现已可供下载

Ubuntu Linux 21.10“Impish Indri” 的新默认壁纸已经曝光。和预期的差不多,新的背景并没有偏离传统模板太远,而是延续了将大型动物吉祥物的脸放在紫色和橙色渐变中心的趋势。 其共包括了四种壁纸图案设计:2 张彩色和 2 张灰色;同时提供了从 1080p 到 8K 不等的分辨率下载选项。与以往的版本相较而言,此版本的吉祥物图案并没有那么风格化。“Indri 是一个更简单的演绎--但也许因此更加强大”。 Ubuntu 21.10 计划于 2021 年 10 月中旬发布,Beta 版则预计将于 9 月 23 日发布。 壁纸下载地址:https://discourse.ubuntu.com/t/official-artwork-downloads-for-impish-indri/24291

优秀的个人博客,低调大师

官方详解UOS与Deepin OS区别

1 月 14 日,统信软件宣布国产 OS——UOS 统一操作系统的正式版正式发布,首先推出的是面向合作伙伴的版本。很多之前试用过 UOS 的玩家都知道,UOS 实际上就是以武汉深度的 Deepin 系统为基础开发的,那这两者之间有什么区别呢? Deepin 社区前几天也发表过一次Q&A问答,解释过 UOS 与 Deepin OS 之间的关系,简单如下: 什么是 UOS?它与 Deepin 有什么不同? UOS 是 Linux 在中国的商业发行版,主要开发工作由 Deepin 团队完成,UOS 与 Deepin 的关系就像是 Fedora 和 Redhat RHEL 那样。 UOS 会取代 Deepin 吗? Deepin 是社区版,不会被 UOS 取代,UOS 只用于商业用途。 Deepin V20 版的进度如何? UOS 与 Deepin V20 系统是并行开发的,大部分功能及资源库都是一样的。UOS 基于 Deepin 系统,因此 Deepin 系统会更早得到一些功能更新,UOS 更新慢一些但会得到完整商业支持。 Deepin V20 系统预计会在 2 月底完成开发,2020 年 3 月份预计发布 beta 版以便公众测试。 Deepin V20 会在中国境之外的地区进行测试吗? 当然,会有一个 beta 版供用户进行整体测试,过去、现在和将来,Deepin 都会始终适用于全球用户和社区,欢迎使用 Deepin 并邀请更多用户来协助我们测试 Deepin V20 系统。 Deepin V20 中的 Root 权限是否会受到限制 Root 权限不会受到限制,默认就可以使用 Root 权限。如果是非技术用户安装了 Deepin 系统,为了避免危险的操作危及系统,你可以自由打开 Root 权限限制。 PS:很多人对 Deepin 系统不太了解,简单来说它也是全球众多 Linux 发行版之一,虽然名气、受众比不上 Ubuntu 等,但是深度公司做 Deepin 系统十年了,这个系统还是很有特色的,在国外也颇受欢迎,在 distrowatch 上受欢迎程度排第十,已经很不容易了。 有兴趣的可以试下最新的 RC 版,网络上有人分享过 ISO 镜像(X86_64)下载:https://pan.baidu.com/s/1c5C6uCvf9DWyXRTbsWWjjQ(提取码 45b8)

优秀的个人博客,低调大师

PostgreSQL官方并行更新时间表

2013年10月,创建了两个主要的基础架构:Dynamic Background Workers 和 Dynamic Shared Memory。 2014年11月,Amit Kapila发布了并行顺序扫描(parallel sequential scan)的草案补丁,Robert Haas 发布了并行模式和并行上下文的(parallel mode and parallel contexts)草案补丁以及引入了一个名为pg_background的contrib模块的补丁。 2016年1月,并行基础架构被提交到PostgreSQL 9.5。 2016年3月,并行顺序扫描被提交到PostgreSQL 9.6。支持 并行连接 和 并行聚合(parallel joins and parallel aggregation),并于4月发布。 2017

优秀的个人博客,低调大师

Android--BRVAH官方使用指南

版权声明:本文为博主原创文章,转载请标明出处。 https://blog.csdn.net/chaoyu168/article/details/80498446 BRVAH是一个强大的RecyclerAdapter框架(什么是RecyclerView?),它能节约开发者大量的开发时间,集成了大部分列表常用需求解决方案。为什么会有它?请查看「Android开源框架BRVAH由来篇」该框架于2016年4月10号发布的第1个版本到现在已经一年多了,经历了800多次代码提交,140多次版本打包,修复了1000多个问题,获得了9000多star,非常感谢大家的使用以及反馈。本篇为BRVAH的使用指南以及包含常见问题会第一时间更新最新的使用方法。最新版本请查看releases,由于持续更新。 文章目录 框架引入 优化Adapter代码和原始的adapter相对,减少70%的代码量。 添加Item事件Item的点击事件Item的长按事件Item子控件的点击事件Item子控件的长按事件 添加列表加载动画一行代码轻松切换5种默认动画。 添加头部、尾部一行代码搞定,感觉又回到ListView时代。 自动加载上拉加载无需监听滑动事件,可自定义加载布局,显示异常提示,自定义异常提示。同时支持下拉加载。 分组布局随心定义分组头部。 多布局简单配置、无需重写额外方法。 设置空布局比Listview的setEmptyView还要好用。 添加拖拽、滑动删除开启,监听即可,就是这么简单。 树形列表比ExpandableListView还要强大,支持多级。 自定义ViewHolder支持自定义ViewHolder,让开发者随心所欲。 扩展框架组合第三方框架,轻松实现更多需求定制。 框架引入 先在 build.gradle(Project:XXXX) 的 repositories 添加: allprojects { repositories { ... maven { url "https://jitpack.io" } } } 然后在 build.gradle(Module:app) 的 dependencies 添加: dependencies { compile 'com.github.CymChad:BaseRecyclerViewAdapterHelper:2.9.30' } 更新说明:https://github.com/CymChad/BaseRecyclerViewAdapterHelper/releases 注意 版本:2.9.28Change the method setVisible --> setGoneThe new method setVisible setVisible:Set a view visibility to VISIBLE (true) or INVISIBLE (false).setGone: Set a view visibility to VISIBLE (true) or GONE (false). 注意: 一旦出现加载失败的情况,只有两种情况: 配置没配置好配置没配置好,有几种情况:1. 只配置了dependencies2. 配置repositories,但是位置错了,build.gradle(Project:XXXX) 文件下的repositories有两个,一个是buildscript下面的,一个是allprojects下面的,要配置到allprojects下面才是对的。3. 版本号前面多一个v,这个是我的锅,在2.1.2版本之前都是带v的,之后(包含2.1.2)都不需要带v。 网络原因(这个就不解释了) 使用Adapter 和原始的adapter相对,减少70%的代码量。 使用代码 public class HomeAdapter extends BaseQuickAdapter<HomeItem, BaseViewHolder> { public HomeAdapter(int layoutResId, List data) { super(layoutResId, data); } @Override protected void convert(BaseViewHolder helper, HomeItem item) { helper.setText(R.id.text, item.getTitle()); helper.setImageResource(R.id.icon, item.getImageResource()); // 加载网络图片 Glide.with(mContext).load(item.getUserAvatar()).crossFade().into((ImageView) helper.getView(R.id.iv)); } } 注:如果想深入了解的原理可以查看RecyclerView.Adapter优化了吗? 使用 首先需要继承BaseQuickAdapter,然后BaseQuickAdapter<Status, BaseViewHolder>第一个泛型Status是数据实体类型,第二个BaseViewHolder是ViewHolder其目的是为了支持扩展ViewHolder。 赋值 可以直接使用viewHolder对象点相关方法通过传入viewId和数据进行,方法支持链式调用。如果是加载网络图片或自定义view可以通过viewHolder.getView(viewId)获取该控件。 常用方法 viewHolder.getLayoutPosition() 获取当前item的position 常见问题 这些问题不是使用该库的问题,但是经常有人问这些问题,所以特意写出来,帮助后续遇到以下问题的开发者们。 为什么有数据不显示?请检查一下你的RecyclerView是否设置了LayoutManager。 为什么有10条数据,只显示1条?请检查一下item的布局最外层的Layout是不是layout_height设置了match_parent. 数据状态错乱这个问题无论是RecyclerView还是ListView不做处理都会出现问题,这个本质上是由于布局重用机制导致的,解决办法是通过数据状态来控制控件的状态,一定要设置状态无论什么状态,if和else是少不了的,如下代码: if(entity.isCheck){ checkBox.isChecked(true); } else { checkBox.isChecked(false); } 解决缓存问题案例: 处理文本框和单选的缓存问题 实现三级伸缩,并解决多选框的复用 添加Item事件 Item的点击事件 adapter.setOnItemClickListener(new BaseQuickAdapter.OnItemClickListener() { @Override public void onItemClick(BaseQuickAdapter adapter, View view, int position) { Log.d(TAG, "onItemClick: "); Toast.makeText(ItemClickActivity.this, "onItemClick" + position, Toast.LENGTH_SHORT).show(); } }); Item的长按事件 adapter.setOnItemLongClickListener(new BaseQuickAdapter.OnItemLongClickListener() { @Override public boolean onItemLongClick(BaseQuickAdapter adapter, View view, int position) { Log.d(TAG, "onItemLongClick: "); Toast.makeText(ItemClickActivity.this, "onItemLongClick" + position, Toast.LENGTH_SHORT).show(); return false; } }); 注意:嵌套recycleView的情况下需要使用你使用 adapter. setOnItemClickListener 来设置点击事件,如果使用recycleView.addOnItemTouchListener会累计添加的。 Item子控件的点击事件首先在adapter的convert方法里面通过viewHolder.addOnClickListener绑定一下的控件id @Override protected void convert(BaseViewHolder viewHolder, Status item) { viewHolder.setText(R.id.tweetName, item.getUserName()) .setText(R.id.tweetText, item.getText()) .setText(R.id.tweetDate, item.getCreatedAt()) .setVisible(R.id.tweetRT, item.isRetweet()) .addOnClickListener(R.id.tweetAvatar) .addOnClickListener(R.id.tweetName) .linkify(R.id.tweetText); } 然后在设置 adapter.setOnItemChildClickListener(new BaseQuickAdapter.OnItemChildClickListener() { @Override public boolean onItemChildClick(BaseQuickAdapter adapter, View view, int position) { Log.d(TAG, "onItemChildClick: "); Toast.makeText(ItemClickActivity.this, "onItemChildClick" + position, Toast.LENGTH_SHORT).show(); return false; } }); Item子控件的长按事件步骤同上使用方法不同。adapter中绑定方法将addOnClickListener改成addOnLongClickListener.设置点击事件方法setOnItemChildClickListener改成setOnItemChildLongClickListener 注意:设置子控件的事件,如果不在adapter中绑定,点击事件无法生效,因为无法找到你需要设置的控件。 如果需要在点击事件中获取其他子控件可以使用: getViewByPosition(RecyclerView recyclerView, int position, @IdRes int viewId) 注意:如果有header的话需要处理一下position加上 headerlayoutcount。 添加列表加载动画 开启动画(默认为渐显效果)adapter.openLoadAnimation();默认提供5种方法(渐显、缩放、从下到上,从左到右、从右到左) public static final int ALPHAIN = 0x00000001; /** * Use with {@link #openLoadAnimation} */ public static final int SCALEIN = 0x00000002; /** * Use with {@link #openLoadAnimation} */ public static final int SLIDEIN_BOTTOM = 0x00000003; /** * Use with {@link #openLoadAnimation} */ public static final int SLIDEIN_LEFT = 0x00000004; /** * Use with {@link #openLoadAnimation} */ public static final int SLIDEIN_RIGHT = 0x00000005; 切换动画 quickAdapter.openLoadAnimation(BaseQuickAdapter.ALPHAIN); 自定义动画 quickAdapter.openLoadAnimation(new BaseAnimation() { @Override public Animator[] getAnimators(View view) { return new Animator[]{ ObjectAnimator.ofFloat(view, "scaleY", 1, 1.1f, 1), ObjectAnimator.ofFloat(view, "scaleX", 1, 1.1f, 1) }; } }); 动画默认只执行一次,如果想重复执行可设置 mQuickAdapter.isFirstOnly(false); 注:如果想深入了解的原理可以查看BaseRecyclerAdapter之添加动画(策略模式) 设置不显示动画数量 adapter.setNotDoAnimationCount(count); 首次到界面的item都依次执行加载动画 由于进入界面的item都是很多的速度进来的所以不会出现滑动显示的依次执行动画效果,这个时候会一起执行动画,如果觉得这样的效果不好可以使用setNotDoAnimationCount设置第一屏item不执行动画,但是如果需要依次执行动画可以重写startAnim让第一个屏幕的item动画延迟执行即可。 @Override protected void startAnim(Animator anim, int index) { super.startAnim(anim, index); if (index < count) anim.setStartDelay(index * 150); } 添加头部、尾部 添加 mQuickAdapter.addHeaderView(getView()); mQuickAdapter.addFooterView(getView()); 注:如果想深入了解的原理可以查看BaseRecyclerAdapter之添加不同布局(头部尾部) 删除指定view mQuickAdapter.removeHeaderView(getView); mQuickAdapter.removeFooterView(getView); 删除所有 mQuickAdapter.removeAllHeaderView(); mQuickAdapter.removeAllFooterView(); 默认出现了头部就不会显示Empty,和尾部,配置以下方法也支持同时显示: setHeaderAndEmpty setHeaderFooterEmpty 默认头部尾部都是占满一行,如果需要不占满可以配置: setHeaderViewAsFlow setFooterViewAsFlow 自动加载 上拉加载 // 滑动最后一个Item的时候回调onLoadMoreRequested方法 setOnLoadMoreListener(RequestLoadMoreListener); 默认第一次加载会进入回调,如果不需要可以配置: mQuickAdapter.disableLoadMoreIfNotFullPage(); 回调处理代码 mQuickAdapter.setOnLoadMoreListener(new BaseQuickAdapter.RequestLoadMoreListener() { @Override public void onLoadMoreRequested() { mRecyclerView.postDelayed(new Runnable() { @Override public void run() { if (mCurrentCounter >= TOTAL_COUNTER) { //数据全部加载完毕 mQuickAdapter.loadMoreEnd(); } else { if (isErr) { //成功获取更多数据 mQuickAdapter.addData(DataServer.getSampleData(PAGE_SIZE)); mCurrentCounter = mQuickAdapter.getData().size(); mQuickAdapter.loadMoreComplete(); } else { //获取更多数据失败 isErr = true; Toast.makeText(PullToRefreshUseActivity.this, R.string.network_err, Toast.LENGTH_LONG).show(); mQuickAdapter.loadMoreFail(); } } } }, delayMillis); } }, mReyclerView); 加载完成(注意不是加载结束,而是本次数据加载结束并且还有下页数据) mQuickAdapter.loadMoreComplete(); 加载失败 mQuickAdapter.loadMoreFail(); 加载结束 mQuickAdapter.loadMoreEnd(); 注意:如果上拉结束后,下拉刷新需要再次开启上拉监听,需要使用setNewData方法填充数据。 打开或关闭加载(一般用于下拉的时候做处理,因为上拉下拉不能同时操作) mQuickAdapter.setEnableLoadMore(boolean); 预加载 // 当列表滑动到倒数第N个Item的时候(默认是1)回调onLoadMoreRequested方法 mQuickAdapter.setPreLoadNumber(int); 设置自定义加载布局 mQuickAdapter.setLoadMoreView(new CustomLoadMoreView()); public final class CustomLoadMoreView extends LoadMoreView { @Override public int getLayoutId() { return R.layout.view_load_more; } /** * 如果返回true,数据全部加载完毕后会隐藏加载更多 * 如果返回false,数据全部加载完毕后会显示getLoadEndViewId()布局 */ @Override public boolean isLoadEndGone() { return true; } @Override protected int getLoadingViewId() { return R.id.load_more_loading_view; } @Override protected int getLoadFailViewId() { return R.id.load_more_load_fail_view; } /** * isLoadEndGone()为true,可以返回0 * isLoadEndGone()为false,不能返回0 */ @Override protected int getLoadEndViewId() { return 0; } } <?xml version="1.0" encoding="utf-8"?> <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="@dimen/dp_40"> <LinearLayout android:id="@+id/load_more_loading_view" android:layout_width="match_parent" android:layout_height="match_parent" android:gravity="center" android:orientation="horizontal"> <ProgressBar android:id="@+id/loading_progress" android:layout_width="wrap_content" android:layout_height="wrap_content" style="?android:attr/progressBarStyleSmall" android:layout_marginRight="@dimen/dp_4" android:indeterminateDrawable="@drawable/sample_footer_loading_progress"/> <TextView android:id="@+id/loading_text" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginLeft="@dimen/dp_4" android:text="@string/loading" android:textColor="#0dddb8" android:textSize="@dimen/sp_14"/> </LinearLayout> <FrameLayout android:id="@+id/load_more_load_fail_view" android:layout_width="match_parent" android:layout_height="match_parent" android:visibility="gone"> <TextView android:id="@+id/tv_prompt" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:textColor="#0dddb8" android:text="@string/load_failed"/> </FrameLayout> </FrameLayout> 下拉加载(符合聊天软件下拉历史数据需求) 设置开启开关 mAdapter.setUpFetchEnable(true); 设置监听 mAdapter.setUpFetchListener(new BaseQuickAdapter.UpFetchListener() { @Override public void onUpFetch() { startUpFetch(); } }); private void startUpFetch() { count++; /** * set fetching on when start network request. */ mAdapter.setUpFetching(true); /** * get data from internet. */ mRecyclerView.postDelayed(new Runnable() { @Override public void run() { mAdapter.addData(0, genData()); /** * set fetching off when network request ends. */ mAdapter.setUpFetching(false); /** * set fetch enable false when you don't need anymore. */ if (count > 5) { mAdapter.setUpFetchEnable(false); } } }, 300); } 开始加载的位置 mAdapter.setStartUpFetchPosition(2); 分组布局 实体类必须继承SectionEntity public class MySection extends SectionEntity<Video> { private boolean isMore; public MySection(boolean isHeader, String header) { super(isHeader, header); } public MySection(Video t) { super(t); } } adapter构造需要传入两个布局id,第一个是item的,第二个是head的,在convert方法里面加载item数据,在convertHead方法里面加载head数据 public class SectionAdapter extends BaseSectionQuickAdapter<MySection> { public SectionAdapter(int layoutResId, int sectionHeadResId, List data) { super(layoutResId, sectionHeadResId, data); } @Override protected void convert(BaseViewHolder helper, MySection item) { helper.setImageUrl(R.id.iv, (String) item.t); } @Override protected void convertHead(BaseViewHolder helper,final MySection item) { helper.setText(R.id.header, item.header); helper.setOnClickListener(R.id.more, new View.OnClickListener() { @Override public void onClick(View v) { Toast.makeText(context,item.header+"more..",Toast.LENGTH_LONG).show(); } }); } 多布局 实体类必须实现MultiItemEntity,在设置数据的时候,需要给每一个数据设置itemType public class MultipleItem implements MultiItemEntity { public static final int TEXT = 1; public static final int IMG = 2; private int itemType; public MultipleItem(int itemType) { this.itemType = itemType; } @Override public int getItemType() { return itemType; } } 在构造里面addItemType绑定type和layout的关系 public class MultipleItemQuickAdapter extends BaseMultiItemQuickAdapter<MultipleItem, BaseViewHolder> { public MultipleItemQuickAdapter(List data) { super(data); addItemType(MultipleItem.TEXT, R.layout.text_view); addItemType(MultipleItem.IMG, R.layout.image_view); } @Override protected void convert(BaseViewHolder helper, MultipleItem item) { switch (helper.getItemViewType()) { case MultipleItem.TEXT: helper.setImageUrl(R.id.tv, item.getContent()); break; case MultipleItem.IMG: helper.setImageUrl(R.id.iv, item.getContent()); break; } } } 注:如果想深入了解的原理可以查看BaseRecyclerAdapter之添加不同布局(优化篇) 如果考虑到在GridLayoutManager复用item问题可以配置: multipleItemAdapter.setSpanSizeLookup(new BaseQuickAdapter.SpanSizeLookup() { @Override public int getSpanSize(GridLayoutManager gridLayoutManager, int position) { return data.get(position).getSpanSize(); } }); 如果大家觉得这种多布局方式有点由于耦合了实体类,还有支持另外一种多布局方式具体可查看更便捷的多布局, 为 BaseQuickAdapter 设置代理. 如果使用多布局出现这个NotFoundException异常,有可能是addItemType()两个参数写反了。 设置空布局 // 没有数据的时候默认显示该布局 mQuickAdapter.setEmptyView(getView()); 如果用网格布局的话,设置空布局就不能给全屏,可以使用瀑布流布局。 添加拖拽、滑动删除 拖拽和滑动删除的回调方法 OnItemDragListener onItemDragListener = new OnItemDragListener() { @Override public void onItemDragStart(RecyclerView.ViewHolder viewHolder, int pos){} @Override public void onItemDragMoving(RecyclerView.ViewHolder source, int from, RecyclerView.ViewHolder target, int to) {} @Override public void onItemDragEnd(RecyclerView.ViewHolder viewHolder, int pos) {} } OnItemSwipeListener onItemSwipeListener = new OnItemSwipeListener() { @Override public void onItemSwipeStart(RecyclerView.ViewHolder viewHolder, int pos) {} @Override public void clearView(RecyclerView.ViewHolder viewHolder, int pos) {} @Override public void onItemSwiped(RecyclerView.ViewHolder viewHolder, int pos) {} }; adapter需要继承BaseItemDraggableAdapter public class ItemDragAdapter extends BaseItemDraggableAdapter<String, BaseViewHolder> { public ItemDragAdapter(List data) { super(R.layout.item_draggable_view, data); } @Override protected void convert(BaseViewHolder helper, String item) { helper.setText(R.id.tv, item); } } Activity使用代码 mAdapter = new ItemDragAdapter(mData); ItemDragAndSwipeCallback itemDragAndSwipeCallback = new ItemDragAndSwipeCallback(mAdapter); ItemTouchHelper itemTouchHelper = new ItemTouchHelper(itemDragAndSwipeCallback); itemTouchHelper.attachToRecyclerView(mRecyclerView); // 开启拖拽 mAdapter.enableDragItem(itemTouchHelper, R.id.textView, true); mAdapter.setOnItemDragListener(onItemDragListener); // 开启滑动删除 mAdapter.enableSwipeItem(); mAdapter.setOnItemSwipeListener(onItemSwipeListener); 默认不支持多个不同的 ViewType 之间进行拖拽,如果开发者有所需求: 重写ItemDragAndSwipeCallback里的onMove()方法,return true即可 树形列表 例子:三级菜单 // if you don't want to extent a class, you can also use the interface IExpandable. // AbstractExpandableItem is just a helper class. public class Level0Item extends AbstractExpandableItem<Level1Item> {...} public class Level1Item extends AbstractExpandableItem<Person> {...} public class Person {...} adapter需要继承BaseMultiItemQuickAdapter public class ExpandableItemAdapter extends BaseMultiItemQuickAdapter<MultiItemEntity, BaseViewHolder> { public ExpandableItemAdapter(List<MultiItemEntity> data) { super(data); addItemType(TYPE_LEVEL_0, R.layout.item_expandable_lv0); addItemType(TYPE_LEVEL_1, R.layout.item_expandable_lv1); addItemType(TYPE_PERSON, R.layout.item_text_view); } @Override protected void convert(final BaseViewHolder holder, final MultiItemEntity item) { switch (holder.getItemViewType()) { case TYPE_LEVEL_0: .... //set view content holder.itemView.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { int pos = holder.getAdapterPosition(); if (lv0.isExpanded()) { collapse(pos); } else { expand(pos); } }}); break; case TYPE_LEVEL_1: // similar with level 0 break; case TYPE_PERSON: //just set the content break; } } 开启所有菜单: adapter.expandAll(); 删除某一个item(添加和修改的思路是一样的) // 获取当前父级位置 int cp = getParentPosition(person); // 通过父级位置找到当前list,删除指定下级 ((Level1Item)getData().get(cp)).removeSubItem(person); // 列表层删除相关位置的数据 getData().remove(holder.getLayoutPosition()); // 更新视图 notifyDataSetChanged(); 自定义ViewHolder 需要继承BaseViewHolder public class MovieViewHolder extends BaseViewHolder 然后修改adapter的第二个泛型为自定义的ViewHolder public class DataBindingUseAdapter extends BaseQuickAdapter<Movie, DataBindingUseAdapter.MovieViewHolder> 注意:需要单独建一个外部类继承BaseViewHolder,否则部分机型会出现ClassCastException,如果是内部类的构造方法要是public,定义的那个类也最好是public。 混淆 -keep class com.chad.library.adapter.** { *; } -keep public class * extends com.chad.library.adapter.base.BaseQuickAdapter -keep public class * extends com.chad.library.adapter.base.BaseViewHolder -keepclassmembers class **$** extends com.chad.library.adapter.base.BaseViewHolder { <init>(...); } 扩展框架 由于adapter本身能力有限,我们又不想耦合view层所以有些需求是现实不了,于是合作了一些优秀开源库,为开发者提供更多可能性。以下扩展框架都是有结合BRVAH的demo。 PinnedSectionItemDecoration:一个强大的粘性标签库 EasyRefreshLayout:这个库让你轻松实现下拉刷新和上拉更多 EasySwipeMenuLayout:独立的侧滑删除 本文章由于持续更新,建议点赞收藏,便于查看。也欢迎大家提出更多建议,我就会第一时间看到后回复,持续到什么时候?只要还没去领盒饭,我就会持续,

优秀的个人博客,低调大师

官方简要解读 LinuxKit 工具包

LinuxKit 是什么? LinuxKit所包含的工具可以允许用户构建自定义的Linux子系统。所有的系统服务都是可以替换的容器,并且用户可以移除所有不需要的东西。这是一款非常符合Docker设计理念的工具,所有默认的组件都可以替换成与用户需求相匹配的组件。 安全性是 Docker 最重要的目标 LinuxKit是一个开源项目,Docker称之所以将其构建在容器中,是为了构建一个安全、精简和可移植的操作系统。 Docker 公司称安全性是其重要等级的目标,该目标与 NIST(美国国家标准技术研究所)在其《Application Container Security Guide》草案中的声明是一致的,即“使用特定的容器操作系统而不是通用的操作系统来减少攻击平面。当使用特定的容器操作系统时,其可攻击平面通常远小于通用操作系统,因此攻击和危害

优秀的个人博客,低调大师

android之官方下拉刷新组件SwipeRefreshLayout

一、问题描述 在android开发中,使用最多的数据刷新方式就是下拉刷新了,而完成此功能我们使用最多的就是第三方的开源库PullToRefresh。现如今,google也忍不住推出了自己的下拉组件SwipeRefreshLayout,下面我们通过api文档和源码来分析学习如何使用SwipeRefreshLayout。 先看效果图: 二、SwipeRefreshLayout的具体用法 下面我们来看SwipeRefreshLayout的具体用法,顾名思义此组件就是一个布局,只不过要注意的是此布局内只能有一个直接子View。其实通过文档我们可以知道SwipeRefreshLayout只不过是继承了ViewGroup。 查看文档,我们可以知道,在SwipRefreshLayout中存在一个接口,通过此接口我们可以监听滑动手势,其实使用此组件最重要的步骤就是实现此接口的onRefresh方法,在此方法中实现数据的更新操作。如下: 接口中的方法: 除了OnRefreshListener接口外,SwipRefreshLayout中还有一些其他重要的方法,具体如下: 1、setOnRefreshListener(SwipeRefreshLayout.OnRefreshListener listener):设置手势滑动监听器。 2、setProgressBackgroundColor(int colorRes):设置进度圈的背景色。 3、setColorSchemeResources(int… colorResIds):设置进度动画的颜色。 4、setRefreshing(Boolean refreshing):设置组件的刷洗状态。 5、setSize(int size):设置进度圈的大小,只有两个值:DEFAULT、LARGE 弄清楚API后,我们下面进行实际编码,首先先做布局,具体内容如下: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 <?xml version= "1.0" encoding= "utf-8" ?> <android.support.v4.widget.SwipeRefreshLayout xmlns:android= "http://schemas.android.com/apk/res/android" android:layout_width= "match_parent" android:layout_height= "match_parent" android:orientation= "vertical" android:id= "@+id/swipeLayout" > <ListView android:id= "@+id/mylist" android:layout_width= "match_parent" android:layout_height= "wrap_content" /> </android.support.v4.widget.SwipeRefreshLayout> Activity核心代码如下: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 swipeRefreshLayout = (SwipeRefreshLayout)findViewById(R.id.swipeLayout); swipeRefreshLayout.setColorSchemeResources(R.color.swipe_color_1, R.color.swipe_color_2, R.color.swipe_color_3, R.color.swipe_color_4); swipeRefreshLayout.setSize(SwipeRefreshLayout.LARGE);; swipeRefreshLayout.setProgressBackgroundColor(R.color.swipe_background_color); //swipeRefreshLayout.setPadding(20, 20, 20, 20); //swipeRefreshLayout.setProgressViewOffset(true, 100, 200); //swipeRefreshLayout.setDistanceToTriggerSync(50); swipeRefreshLayout.setProgressViewEndTarget( true , 100 ); swipeRefreshLayout.setOnRefreshListener( new OnRefreshListener() { @Override public void onRefresh() { new Thread( new Runnable() { @Override public void run() { data.clear(); for ( int i= 0 ;i< 20 ;i++){ data.add( "SwipeRefreshLayout下拉刷新" +i); } try { Thread.sleep( 5000 ); } catch (InterruptedException e) { e.printStackTrace(); } mHandler.sendEmptyMessage( 1 ); } }).start(); } }); //handler private Handler mHandler = new Handler(){ @Override public void handleMessage(Message msg) { super .handleMessage(msg); switch (msg.what) { case 1 : swipeRefreshLayout.setRefreshing( false ); adapter.notifyDataSetChanged(); //swipeRefreshLayout.setEnabled(false); break ; default : break ; } } }; 通过如上步骤,我们就实现了一个简单的下拉刷新操作,在此基础上,我们可以分析研究一下SwipeRefreshLayout是如何实现的。 通过源码我们发现SwipeRefreshLayout中的两个重要的属性: private MaterialProgressDrawable mProgress; private CircleImageView mCircleView; 这两个属性正是用于实现进度动画效果的,在方法createProgressView中,我们看到mCircleView最终加入到了SwipeRefreshLayout中。 1 2 3 4 5 6 7 8 private void createProgressView() { mCircleView = new CircleImageView(getContext(), CIRCLE_BG_LIGHT, CIRCLE_DIAMETER/ 2 ); mProgress = new MaterialProgressDrawable(getContext(), this ); mProgress.setBackgroundColor(CIRCLE_BG_LIGHT); mCircleView.setImageDrawable(mProgress); mCircleView.setVisibility(View.GONE); addView(mCircleView); } 同时我们也可以查看到CirlceImageView继承了ImageView,MaterialProgressDrawabel继承了Drawable,至此我们也就明白了下来进度动画是如何实现的了,具体的细节在不做过多赘述,可自行查看源码。 class CircleImageView extends ImageView class MaterialProgressDrawable extends Drawable implements Animatable 具体的下拉功能实现主要是在onInterceptTouchEvent、onTouchEvent方法中完成的,在此我就不在将具体代码贴出来了,大家可自行查看。 想要进一步了解的同学,可以下载完整工程,自行运行查看!有问题也可以跟帖讨论哦~ 本文转自 一点点征服 博客园博客,原文链接:http://www.cnblogs.com/ldq2016/p/5378851.html,如需转载请自行联系原作者

资源下载

更多资源
Oracle

Oracle

Oracle Database,又名Oracle RDBMS,或简称Oracle。是甲骨文公司的一款关系数据库管理系统。它是在数据库领域一直处于领先地位的产品。可以说Oracle数据库系统是目前世界上流行的关系数据库管理系统,系统可移植性好、使用方便、功能强,适用于各类大、中、小、微机环境。它是一种高效率、可靠性好的、适应高吞吐量的数据库方案。

Apache Tomcat

Apache Tomcat

Tomcat是Apache 软件基金会(Apache Software Foundation)的Jakarta 项目中的一个核心项目,由Apache、Sun 和其他一些公司及个人共同开发而成。因为Tomcat 技术先进、性能稳定,而且免费,因而深受Java 爱好者的喜爱并得到了部分软件开发商的认可,成为目前比较流行的Web 应用服务器。

JDK

JDK

JDK是 Java 语言的软件开发工具包,主要用于移动设备、嵌入式设备上的java应用程序。JDK是整个java开发的核心,它包含了JAVA的运行环境(JVM+Java系统类库)和JAVA工具。

Sublime Text

Sublime Text

Sublime Text具有漂亮的用户界面和强大的功能,例如代码缩略图,Python的插件,代码段等。还可自定义键绑定,菜单和工具栏。Sublime Text 的主要功能包括:拼写检查,书签,完整的 Python API , Goto 功能,即时项目切换,多选择,多窗口等等。Sublime Text 是一个跨平台的编辑器,同时支持Windows、Linux、Mac OS X等操作系统。