├── README.md ├── app ├── .gitignore ├── build.gradle ├── proguard-rules.pro └── src │ ├── androidTest │ └── java │ │ └── pkanimation │ │ └── xly │ │ └── com │ │ └── brvahcircledemo │ │ └── ExampleInstrumentedTest.java │ ├── main │ ├── AndroidManifest.xml │ ├── java │ │ └── pkanimation │ │ │ └── xly │ │ │ └── com │ │ │ └── brvahcircledemo │ │ │ ├── BaseActivity.java │ │ │ ├── MainActivity.java │ │ │ ├── adapter │ │ │ └── DynamicsAdapter.java │ │ │ ├── constants │ │ │ └── Constants.java │ │ │ ├── divider │ │ │ ├── DividerLine.java │ │ │ ├── Dp2Px.java │ │ │ ├── Y_Divider.java │ │ │ ├── Y_DividerBuilder.java │ │ │ ├── Y_DividerItemDecoration.java │ │ │ └── Y_SideLine.java │ │ │ ├── model │ │ │ └── DynamicsModel.java │ │ │ └── util │ │ │ ├── DateUtil.java │ │ │ ├── ImageLoadUtils.java │ │ │ └── transform │ │ │ ├── RoundTransform.java │ │ │ └── SimpleCircleTransform.java │ └── res │ │ ├── layout │ │ ├── activity_main.xml │ │ ├── dynamice_comment_with_imgs.xml │ │ ├── dynamics_baishi.xml │ │ ├── dynamics_comment.xml │ │ ├── dynamics_gift.xml │ │ ├── dynamics_like_video.xml │ │ ├── dynamics_share_gain.xml │ │ ├── dynamics_share_video.xml │ │ └── item_comment_img.xml │ │ ├── mipmap-hdpi │ │ └── ic_launcher.png │ │ ├── mipmap-mdpi │ │ ├── ic_launcher.png │ │ ├── mine_omitted.png │ │ ├── user_bs_ticker_bg.png │ │ └── video_play_small.png │ │ ├── mipmap-xhdpi │ │ └── ic_launcher.png │ │ ├── mipmap-xxhdpi │ │ └── ic_launcher.png │ │ ├── mipmap-xxxhdpi │ │ └── ic_launcher.png │ │ ├── values-w820dp │ │ └── dimens.xml │ │ └── values │ │ ├── colors.xml │ │ ├── dimens.xml │ │ ├── strings.xml │ │ └── styles.xml │ └── test │ └── java │ └── pkanimation │ └── xly │ └── com │ └── brvahcircledemo │ └── ExampleUnitTest.java ├── build.gradle ├── gradle.properties └── settings.gradle /README.md: -------------------------------------------------------------------------------- 1 | # BRVAHCircleDemo 2 | 基于BRVAH的RecyclerView多布局实现的类似朋友圈Demo 3 | Relative to https://github.com/CymChad/BaseRecyclerViewAdapterHelper/issues/1560 4 | -------------------------------------------------------------------------------- /app/.gitignore: -------------------------------------------------------------------------------- 1 | /build 2 | -------------------------------------------------------------------------------- /app/build.gradle: -------------------------------------------------------------------------------- 1 | apply plugin: 'com.android.application' 2 | 3 | android { 4 | compileSdkVersion 25 5 | buildToolsVersion "25.0.3" 6 | defaultConfig { 7 | applicationId "pkanimation.xly.com.brvahcircledemo" 8 | minSdkVersion 17 9 | targetSdkVersion 25 10 | versionCode 1 11 | versionName "1.0" 12 | testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner" 13 | } 14 | buildTypes { 15 | release { 16 | minifyEnabled false 17 | proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' 18 | } 19 | } 20 | } 21 | 22 | dependencies { 23 | compile fileTree(dir: 'libs', include: ['*.jar']) 24 | androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', { 25 | exclude group: 'com.android.support', module: 'support-annotations' 26 | }) 27 | compile 'com.android.support:recyclerview-v7:25.3.1' 28 | compile 'com.android.support:appcompat-v7:25.3.1' 29 | compile 'com.android.support:support-v4:25.3.1' 30 | compile 'com.android.support:design:25.3.1' 31 | compile 'com.github.bumptech.glide:glide:3.8.0' 32 | compile 'com.alibaba:fastjson:1.1.64.android' 33 | 34 | compile 'com.github.CymChad:BaseRecyclerViewAdapterHelper:2.9.30' 35 | testCompile 'junit:junit:4.12' 36 | } 37 | -------------------------------------------------------------------------------- /app/proguard-rules.pro: -------------------------------------------------------------------------------- 1 | # Add project specific ProGuard rules here. 2 | # By default, the flags in this file are appended to flags specified 3 | # in /Users/xuleyuan/Library/Android/sdk/tools/proguard/proguard-android.txt 4 | # You can edit the include path and order by changing the proguardFiles 5 | # directive in build.gradle. 6 | # 7 | # For more details, see 8 | # http://developer.android.com/guide/developing/tools/proguard.html 9 | 10 | # Add any project specific keep options here: 11 | 12 | # If your project uses WebView with JS, uncomment the following 13 | # and specify the fully qualified class name to the JavaScript interface 14 | # class: 15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview { 16 | # public *; 17 | #} 18 | -------------------------------------------------------------------------------- /app/src/androidTest/java/pkanimation/xly/com/brvahcircledemo/ExampleInstrumentedTest.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo; 2 | 3 | import android.content.Context; 4 | import android.support.test.InstrumentationRegistry; 5 | import android.support.test.runner.AndroidJUnit4; 6 | 7 | import org.junit.Test; 8 | import org.junit.runner.RunWith; 9 | 10 | import static org.junit.Assert.*; 11 | 12 | /** 13 | * Instrumentation test, which will execute on an Android device. 14 | * 15 | * @see Testing documentation 16 | */ 17 | @RunWith(AndroidJUnit4.class) 18 | public class ExampleInstrumentedTest { 19 | @Test 20 | public void useAppContext() throws Exception { 21 | // Context of the app under test. 22 | Context appContext = InstrumentationRegistry.getTargetContext(); 23 | 24 | assertEquals("pkanimation.xly.com.brvahcircledemo", appContext.getPackageName()); 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /app/src/main/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | 6 | 7 | 8 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/BaseActivity.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo; 2 | 3 | import android.app.Activity; 4 | 5 | /** 6 | * Created by xuleyuan on 2017/10/12 7 | */ 8 | 9 | public abstract class BaseActivity extends Activity{ 10 | } 11 | -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/MainActivity.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo; 2 | 3 | import android.os.Bundle; 4 | import android.support.v7.widget.LinearLayoutManager; 5 | import android.support.v7.widget.RecyclerView; 6 | import android.text.TextUtils; 7 | 8 | import com.alibaba.fastjson.JSON; 9 | 10 | import java.util.ArrayList; 11 | import java.util.List; 12 | 13 | import pkanimation.xly.com.brvahcircledemo.adapter.DynamicsAdapter; 14 | import pkanimation.xly.com.brvahcircledemo.constants.Constants; 15 | import pkanimation.xly.com.brvahcircledemo.model.DynamicsModel; 16 | 17 | public class MainActivity extends BaseActivity { 18 | 19 | DynamicsAdapter adapter; 20 | private RecyclerView recyclerView; 21 | private List dynamicsModels; 22 | 23 | @Override 24 | protected void onCreate(Bundle savedInstanceState) { 25 | super.onCreate(savedInstanceState); 26 | setContentView(R.layout.activity_main); 27 | dynamicsModels = new ArrayList<>(); 28 | recyclerView = (RecyclerView) findViewById(R.id.rvDynamics); 29 | adapter = new DynamicsAdapter(dynamicsModels); 30 | LinearLayoutManager linearLayoutManager = new LinearLayoutManager(this); 31 | recyclerView.setLayoutManager(linearLayoutManager); 32 | recyclerView.setAdapter(adapter); 33 | 34 | fetchData(data); 35 | 36 | } 37 | /** 38 | * 获取数据操作 39 | * @param data 40 | */ 41 | private void fetchData(String data) { 42 | List dynamicsModels = JSON.parseArray(data, DynamicsModel.class); 43 | onGetData(dynamicsModels); 44 | } 45 | /** 46 | * 拿到数据的处理 47 | * @param dynamicsModelList 48 | */ 49 | private void onGetData(List dynamicsModelList) { 50 | 51 | for (int i = 0; i < dynamicsModelList.size(); i++) {///遍历所有的数据 52 | DynamicsModel dynamicsModel = dynamicsModelList.get(i); 53 | if (dynamicsModel.getAction() == Constants.COMMENT) { // 如果是评论类型的数据,要看是否有图片区分一下布局,这是因为后台没给我区分 54 | if (TextUtils.isEmpty(dynamicsModel.getImg_urls())) {//如果这个评论没有图片地址 55 | dynamicsModel.setItemType(Constants.COMMENT_NONE_IMG);//自己定义没有图片类型的布局 56 | } else { 57 | dynamicsModel.setItemType(Constants.COMMENT_WITH_IMG);//自己定义有图片类型的布局 58 | } 59 | } else {//普通动态直接填入后台数据类型 60 | dynamicsModel.setItemType(dynamicsModel.getAction()); 61 | } 62 | } 63 | dynamicsModels.addAll(dynamicsModelList); 64 | adapter.notifyDataSetChanged(); 65 | 66 | } 67 | /** 68 | * 这是网络数据 69 | */ 70 | private String data = "[{\n" + 71 | "\t\t\"action\": 5,\n" + 72 | "\t\t\"action_time\": 1506075300,\n" + 73 | "\t\t\"cid\": 2016,\n" + 74 | "\t\t\"content\": \"采购订单\",\n" + 75 | "\t\t\"des\": \"u0090mF9CQX-mp4\",\n" + 76 | "\t\t\"img_url\": \"http://ouo48szbk.bkt.clouddn.com/160175211281383424\",\n" + 77 | "\t\t\"img_urls\": \"\",\n" + 78 | "\t\t\"vid\": 149323\n" + 79 | "\t}, {\n" + 80 | "\t\t\"action\": 6,\n" + 81 | "\t\t\"action_time\": 1505979588,\n" + 82 | "\t\t\"cost\": 0,\n" + 83 | "\t\t\"days\": 31,\n" + 84 | "\t\t\"head\": \"http://image.52doushi.com/static/image/56/90/851903_1481543817044.jpg\",\n" + 85 | "\t\t\"master_uid\": 851903,\n" + 86 | "\t\t\"nick\": \"十万个女密码\"\n" + 87 | "\t}, {\n" + 88 | "\t\t\"action\": 5,\n" + 89 | "\t\t\"action_time\": 1506667882,\n" + 90 | "\t\t\"cid\": 5034,\n" + 91 | "\t\t\"content\": \"啥也不说\",\n" + 92 | "\t\t\"des\": \"日式游戏有特“色” 扒衣老司机入侵秋叶原\",\n" + 93 | "\t\t\"img_url\": \"http://qnimage.52doushi.com/2038419/1502245600061/cover\",\n" + 94 | "\t\t\"img_urls\": \"http://ouo48szbk.bkt.clouddn.com/2191731/1506668856427,http://ouo48szbk.bkt.clouddn.com/2191731/1506668050915,http://ouo48szbk.bkt.clouddn.com/2191731/1506668837176\",\n" + 95 | "\t\t\"vid\": 137011\n" + 96 | "\t},{\n" + 97 | "\t\t\"action\": 6,\n" + 98 | "\t\t\"action_time\": 1505979319,\n" + 99 | "\t\t\"cost\": 0,\n" + 100 | "\t\t\"days\": 31,\n" + 101 | "\t\t\"head\": \"http://image.52doushi.com/static/image/53/32/1271907_1490848023628.jpg\",\n" + 102 | "\t\t\"master_uid\": 1271907,\n" + 103 | "\t\t\"nick\": \"快厨房InstaChef\"\n" + 104 | "\t}, {\n" + 105 | "\t\t\"action\": 6,\n" + 106 | "\t\t\"action_time\": 1505979240,\n" + 107 | "\t\t\"cost\": 0,\n" + 108 | "\t\t\"days\": 31,\n" + 109 | "\t\t\"head\": \"http://image.52doushi.com/static/image/00/00/12_1490770803370.jpg\",\n" + 110 | "\t\t\"master_uid\": 1268406,\n" + 111 | "\t\t\"nick\": \"涛哥测评\"\n" + 112 | "\t}, {\n" + 113 | "\t\t\"action\": 3,\n" + 114 | "\t\t\"action_time\": 1505878018,\n" + 115 | "\t\t\"des\": \"中国的山寨货是如何碾压世界的?\",\n" + 116 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/85/25/1916117_1499753673621.jpg\",\n" + 117 | "\t\t\"vid\": 126881\n" + 118 | "\t}, {\n" + 119 | "\t\t\"action\": 5,\n" + 120 | "\t\t\"action_time\": 1505806501,\n" + 121 | "\t\t\"cid\": 1002,\n" + 122 | "\t\t\"content\": \"ll\",\n" + 123 | "\t\t\"des\": \"头顶青天烧脑无边\",\n" + 124 | "\t\t\"img_url\": \"http://ouo48szbk.bkt.clouddn.com/首页精选/13.png\",\n" + 125 | "\t\t\"img_urls\": \"\",\n" + 126 | "\t\t\"vid\": 130381\n" + 127 | "\t}, {\n" + 128 | "\t\t\"action\": 3,\n" + 129 | "\t\t\"action_time\": 1505806295,\n" + 130 | "\t\t\"des\": \"我为什么不劝分手 2-5\",\n" + 131 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/12/25/851903_1495021068509.jpg\",\n" + 132 | "\t\t\"vid\": 103821\n" + 133 | "\t}, {\n" + 134 | "\t\t\"action\": 3,\n" + 135 | "\t\t\"action_time\": 1505806271,\n" + 136 | "\t\t\"des\": \"你的男朋友是同性恋吗\",\n" + 137 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/99/43/851903_1495867268182.jpg\",\n" + 138 | "\t\t\"vid\": 108038\n" + 139 | "\t}, {\n" + 140 | "\t\t\"action\": 3,\n" + 141 | "\t\t\"action_time\": 1505806265,\n" + 142 | "\t\t\"des\": \"你的男朋友是同性恋吗\",\n" + 143 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/99/43/851903_1495867268182.jpg\",\n" + 144 | "\t\t\"vid\": 108038\n" + 145 | "\t}, {\n" + 146 | "\t\t\"action\": 5,\n" + 147 | "\t\t\"action_time\": 1505804014,\n" + 148 | "\t\t\"cid\": 4006,\n" + 149 | "\t\t\"content\": \"你\",\n" + 150 | "\t\t\"des\": \"男人为什么都爱网红脸?2-8\",\n" + 151 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/13/46/851903_1495108376759.jpg\",\n" + 152 | "\t\t\"img_urls\": \"\",\n" + 153 | "\t\t\"vid\": 104319\n" + 154 | "\t}, {\n" + 155 | "\t\t\"action\": 5,\n" + 156 | "\t\t\"action_time\": 1505804008,\n" + 157 | "\t\t\"cid\": 3008,\n" + 158 | "\t\t\"content\": \"贵\",\n" + 159 | "\t\t\"des\": \"男人为什么都爱网红脸?2-8\",\n" + 160 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/13/46/851903_1495108376759.jpg\",\n" + 161 | "\t\t\"img_urls\": \"\",\n" + 162 | "\t\t\"vid\": 104319\n" + 163 | "\t}, {\n" + 164 | "\t\t\"action\": 5,\n" + 165 | "\t\t\"action_time\": 1505804001,\n" + 166 | "\t\t\"cid\": 5003,\n" + 167 | "\t\t\"content\": \"薛\",\n" + 168 | "\t\t\"des\": \"男人为什么都爱网红脸?2-8\",\n" + 169 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/13/46/851903_1495108376759.jpg\",\n" + 170 | "\t\t\"img_urls\": \"\",\n" + 171 | "\t\t\"vid\": 104319\n" + 172 | "\t}, {\n" + 173 | "\t\t\"action\": 2,\n" + 174 | "\t\t\"action_time\": 1505803980,\n" + 175 | "\t\t\"des\": \"男人为什么都爱网红脸?2-8\",\n" + 176 | "\t\t\"gain_cid\": 4005,\n" + 177 | "\t\t\"gain_content\": \"不想说什么\",\n" + 178 | "\t\t\"gain_img\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505804455467\",\n" + 179 | "\t\t\"gvid\": 5004,\n" + 180 | "\t\t\"head\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505808722550\",\n" + 181 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/13/46/851903_1495108376759.jpg\",\n" + 182 | "\t\t\"like_count\": 0,\n" + 183 | "\t\t\"like_flag\": 0,\n" + 184 | "\t\t\"nick\": \"萌萌哒\",\n" + 185 | "\t\t\"play_url\": \"http://ouo4fr79u.bkt.clouddn.com/2191728/1505804314086\",\n" + 186 | "\t\t\"reply_count\": 0,\n" + 187 | "\t\t\"uid\": 2191728,\n" + 188 | "\t\t\"vid\": 104319\n" + 189 | "\t}, {\n" + 190 | "\t\t\"action\": 2,\n" + 191 | "\t\t\"action_time\": 1505803930,\n" + 192 | "\t\t\"des\": \"男人为什么都爱网红脸?2-8\",\n" + 193 | "\t\t\"gain_cid\": 5,\n" + 194 | "\t\t\"gain_content\": \"德国哈哈表现女性患白血病细胞的那些性能表\",\n" + 195 | "\t\t\"gain_img\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505804621377\",\n" + 196 | "\t\t\"gvid\": 4004,\n" + 197 | "\t\t\"head\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505808722550\",\n" + 198 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/13/46/851903_1495108376759.jpg\",\n" + 199 | "\t\t\"like_count\": 0,\n" + 200 | "\t\t\"like_flag\": 0,\n" + 201 | "\t\t\"nick\": \"萌萌哒\",\n" + 202 | "\t\t\"play_url\": \"http://ouo4fr79u.bkt.clouddn.com/2191728/1505803975909\",\n" + 203 | "\t\t\"reply_count\": 0,\n" + 204 | "\t\t\"uid\": 2191728,\n" + 205 | "\t\t\"vid\": 104319\n" + 206 | "\t}, {\n" + 207 | "\t\t\"action\": 2,\n" + 208 | "\t\t\"action_time\": 1505803722,\n" + 209 | "\t\t\"des\": \"男人为什么都爱网红脸?2-8\",\n" + 210 | "\t\t\"gain_cid\": 3007,\n" + 211 | "\t\t\"gain_content\": \"德国哈哈表现女性患白血病细胞的那些性能表d n\",\n" + 212 | "\t\t\"gain_img\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505803997720\",\n" + 213 | "\t\t\"gvid\": 5003,\n" + 214 | "\t\t\"head\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505808722550\",\n" + 215 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/13/46/851903_1495108376759.jpg\",\n" + 216 | "\t\t\"like_count\": 0,\n" + 217 | "\t\t\"like_flag\": 0,\n" + 218 | "\t\t\"nick\": \"萌萌哒\",\n" + 219 | "\t\t\"play_url\": \"http://ouo4fr79u.bkt.clouddn.com/2191728/1505804492831\",\n" + 220 | "\t\t\"reply_count\": 0,\n" + 221 | "\t\t\"uid\": 2191728,\n" + 222 | "\t\t\"vid\": 104319\n" + 223 | "\t}, {\n" + 224 | "\t\t\"action\": 2,\n" + 225 | "\t\t\"action_time\": 1505803711,\n" + 226 | "\t\t\"des\": \"男人为什么都爱网红脸?2-8\",\n" + 227 | "\t\t\"gain_cid\": 3006,\n" + 228 | "\t\t\"gain_content\": \"德国哈哈表现女性患白血病细胞的那些性能表s b bsb s b z b zna\",\n" + 229 | "\t\t\"gain_img\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505804117451\",\n" + 230 | "\t\t\"gvid\": 5002,\n" + 231 | "\t\t\"head\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505808722550\",\n" + 232 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/13/46/851903_1495108376759.jpg\",\n" + 233 | "\t\t\"like_count\": 0,\n" + 234 | "\t\t\"like_flag\": 0,\n" + 235 | "\t\t\"nick\": \"萌萌哒\",\n" + 236 | "\t\t\"play_url\": \"http://ouo4fr79u.bkt.clouddn.com/2191728/1505803775127\",\n" + 237 | "\t\t\"reply_count\": 0,\n" + 238 | "\t\t\"uid\": 2191728,\n" + 239 | "\t\t\"vid\": 104319\n" + 240 | "\t}, {\n" + 241 | "\t\t\"action\": 2,\n" + 242 | "\t\t\"action_time\": 1505803709,\n" + 243 | "\t\t\"des\": \"男人为什么都爱网红脸?2-8\",\n" + 244 | "\t\t\"gain_cid\": 2015,\n" + 245 | "\t\t\"gain_content\": \"德国哈哈表现女性患白血病细胞的那些性能表s b bsb s b z b zna\",\n" + 246 | "\t\t\"gain_img\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505803912231\",\n" + 247 | "\t\t\"gvid\": 4003,\n" + 248 | "\t\t\"head\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505808722550\",\n" + 249 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/13/46/851903_1495108376759.jpg\",\n" + 250 | "\t\t\"like_count\": 0,\n" + 251 | "\t\t\"like_flag\": 0,\n" + 252 | "\t\t\"nick\": \"萌萌哒\",\n" + 253 | "\t\t\"play_url\": \"http://ouo4fr79u.bkt.clouddn.com/2191728/1505803900471\",\n" + 254 | "\t\t\"reply_count\": 0,\n" + 255 | "\t\t\"uid\": 2191728,\n" + 256 | "\t\t\"vid\": 104319\n" + 257 | "\t}, {\n" + 258 | "\t\t\"action\": 2,\n" + 259 | "\t\t\"action_time\": 1505803701,\n" + 260 | "\t\t\"des\": \"男人为什么都爱网红脸?2-8\",\n" + 261 | "\t\t\"gain_cid\": 2014,\n" + 262 | "\t\t\"gain_content\": \"德国哈哈b x n x h b\",\n" + 263 | "\t\t\"gain_img\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505804608143\",\n" + 264 | "\t\t\"gvid\": 3004,\n" + 265 | "\t\t\"head\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505808722550\",\n" + 266 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/13/46/851903_1495108376759.jpg\",\n" + 267 | "\t\t\"like_count\": 0,\n" + 268 | "\t\t\"like_flag\": 0,\n" + 269 | "\t\t\"nick\": \"萌萌哒\",\n" + 270 | "\t\t\"play_url\": \"http://ouo4fr79u.bkt.clouddn.com/2191728/1505803736381\",\n" + 271 | "\t\t\"reply_count\": 0,\n" + 272 | "\t\t\"uid\": 2191728,\n" + 273 | "\t\t\"vid\": 104319\n" + 274 | "\t}, {\n" + 275 | "\t\t\"action\": 2,\n" + 276 | "\t\t\"action_time\": 1505803675,\n" + 277 | "\t\t\"des\": \"男人为什么都爱网红脸?2-8\",\n" + 278 | "\t\t\"gain_cid\": 2013,\n" + 279 | "\t\t\"gain_content\": \"德国哈哈\",\n" + 280 | "\t\t\"gain_img\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505803959443\",\n" + 281 | "\t\t\"gvid\": 3003,\n" + 282 | "\t\t\"head\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505808722550\",\n" + 283 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/13/46/851903_1495108376759.jpg\",\n" + 284 | "\t\t\"like_count\": 0,\n" + 285 | "\t\t\"like_flag\": 0,\n" + 286 | "\t\t\"nick\": \"萌萌哒\",\n" + 287 | "\t\t\"play_url\": \"http://ouo4fr79u.bkt.clouddn.com/2191728/1505803779029\",\n" + 288 | "\t\t\"reply_count\": 0,\n" + 289 | "\t\t\"uid\": 2191728,\n" + 290 | "\t\t\"vid\": 104319\n" + 291 | "\t}, {\n" + 292 | "\t\t\"action\": 5,\n" + 293 | "\t\t\"action_time\": 1506570283,\n" + 294 | "\t\t\"cid\": 2028,\n" + 295 | "\t\t\"content\": \"好想继续看细节\",\n" + 296 | "\t\t\"des\": \"佟丽娅变身女学霸带你玩转生命科学\",\n" + 297 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/81/26/1916117_1499399830380.jpg\",\n" + 298 | "\t\t\"img_urls\": \"http://ouo48szbk.bkt.clouddn.com/2194720/1506570737592,http://ouo48szbk.bkt.clouddn.com/2194720/1506570958212\",\n" + 299 | "\t\t\"vid\": 125677\n" + 300 | "\t}, {\n" + 301 | "\t\t\"action\": 2,\n" + 302 | "\t\t\"action_time\": 1505803658,\n" + 303 | "\t\t\"des\": \"男人为什么都爱网红脸?2-8\",\n" + 304 | "\t\t\"gain_cid\": 3005,\n" + 305 | "\t\t\"gain_content\": \"德国哈哈\",\n" + 306 | "\t\t\"gain_img\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505804322257\",\n" + 307 | "\t\t\"gvid\": 2001,\n" + 308 | "\t\t\"head\": \"http://ouo48szbk.bkt.clouddn.com/2191728/1505808722550\",\n" + 309 | "\t\t\"img_url\": \"http://image.52doushi.com/static/image/13/46/851903_1495108376759.jpg\",\n" + 310 | "\t\t\"like_count\": 1,\n" + 311 | "\t\t\"like_flag\": 0,\n" + 312 | "\t\t\"nick\": \"萌萌哒\",\n" + 313 | "\t\t\"play_url\": \"http://ouo4fr79u.bkt.clouddn.com/2191728/1505804240823\",\n" + 314 | "\t\t\"reply_count\": 3,\n" + 315 | "\t\t\"uid\": 2191728,\n" + 316 | "\t\t\"vid\": 104319\n" + 317 | "\t}]"; 318 | } 319 | -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/adapter/DynamicsAdapter.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo.adapter; 2 | 3 | import android.support.v7.widget.GridLayoutManager; 4 | import android.support.v7.widget.RecyclerView; 5 | import android.text.TextUtils; 6 | import android.view.View; 7 | import android.widget.ImageView; 8 | 9 | import com.chad.library.adapter.base.BaseMultiItemQuickAdapter; 10 | import com.chad.library.adapter.base.BaseQuickAdapter; 11 | import com.chad.library.adapter.base.BaseViewHolder; 12 | 13 | import java.util.ArrayList; 14 | import java.util.Collections; 15 | import java.util.List; 16 | 17 | import pkanimation.xly.com.brvahcircledemo.R; 18 | import pkanimation.xly.com.brvahcircledemo.constants.Constants; 19 | import pkanimation.xly.com.brvahcircledemo.divider.DividerLine; 20 | import pkanimation.xly.com.brvahcircledemo.model.DynamicsModel; 21 | import pkanimation.xly.com.brvahcircledemo.util.DateUtil; 22 | import pkanimation.xly.com.brvahcircledemo.util.ImageLoadUtils; 23 | 24 | import static pkanimation.xly.com.brvahcircledemo.util.DateUtil.FULL_TIME; 25 | 26 | /** 27 | * 我的动态适配器 28 | * Created by xuleyuan on 2017/8/30 29 | */ 30 | public class DynamicsAdapter extends BaseMultiItemQuickAdapter { 31 | 32 | private static final int COMMENT_WITH_IMG = 100; 33 | private static final int COMMENT_NONE_IMG = 101; 34 | private static final int NONE_IMG = 0; 35 | 36 | /** 37 | * Same as QuickAdapter#QuickAdapter(Context,int) but with 38 | * some initialization data. 39 | * 40 | * @param data A new list is created out of this one to avoid mutable list 41 | */ 42 | public DynamicsAdapter(List data) {//构造函数中需要把所有的布局类型与布局关联起来,漏了会出resource not found error 43 | super(data); 44 | addItemType(Constants.SHARE_VIDEO, R.layout.dynamics_share_video); 45 | addItemType(Constants.SHARE_GAIN, R.layout.dynamics_share_gain); 46 | addItemType(Constants.LIKE_VIDEO, R.layout.dynamics_like_video); 47 | addItemType(Constants.GIFT, R.layout.dynamics_gift); 48 | addItemType(Constants.BAISHI, R.layout.dynamics_baishi); 49 | addItemType(Constants.COMMENT_WITH_IMG, R.layout.dynamice_comment_with_imgs); 50 | addItemType(Constants.COMMENT_NONE_IMG, R.layout.dynamics_comment); 51 | } 52 | 53 | @Override 54 | protected void convert(BaseViewHolder helper, final DynamicsModel item) { 55 | long at = item.getAction_time() * 1000; 56 | String formatData = DateUtil.getDataFormat(at); 57 | String actionTime = DateUtil.getTime(at, FULL_TIME); 58 | helper.setText(R.id.tvDynamicsDate, formatData); 59 | switch (helper.getItemViewType()) { 60 | case Constants.SHARE_VIDEO://分享视频的布局,对应了 上面 ⬆️构造函数填入的布局,下面以此类推,要做的就是填入数据 61 | actionTime = mContext.getString(R.string.share_video, actionTime); 62 | helper.setText(R.id.tvAction, actionTime); 63 | helper.setText(R.id.tvContent, item.getContent()); 64 | ImageLoadUtils.displayImage(mContext, item.getImg_url(), (ImageView) helper.getView(R.id.ivVideo)); 65 | helper.addOnClickListener(R.id.ivOperation); 66 | break; 67 | 68 | case Constants.SHARE_GAIN: 69 | actionTime = mContext.getString(R.string.dynamic_results, actionTime); 70 | ImageLoadUtils.displayImage(mContext, item.getImg_url(), (ImageView) helper.getView(R.id.ivVideo)); 71 | ImageLoadUtils.displayImage(mContext, item.getGain_img(), (ImageView) helper.getView(R.id.ivGain), 0, 3); 72 | helper.setText(R.id.tvDes, item.getDes()); 73 | helper.setText(R.id.tvContent, item.getGain_content()); 74 | helper.addOnClickListener(R.id.ivOperation); 75 | helper.setOnClickListener(R.id.ivGain, new View.OnClickListener() { 76 | @Override 77 | public void onClick(View v) { 78 | 79 | } 80 | }); 81 | break; 82 | 83 | case Constants.LIKE_VIDEO: 84 | actionTime = mContext.getString(R.string.like_video, actionTime); 85 | ImageLoadUtils.displayImage(mContext, item.getImg_url(), (ImageView) helper.getView(R.id.ivVideo)); 86 | helper.setText(R.id.tvDes, item.getDes()); 87 | helper.getView(R.id.rlLikeVideo).setOnClickListener(new View.OnClickListener() { 88 | @Override 89 | public void onClick(View v) { 90 | 91 | } 92 | }); 93 | break; 94 | 95 | case Constants.GIFT: 96 | actionTime = mContext.getString(R.string.dynamic_send_gift, actionTime); 97 | ImageLoadUtils.displayImage(mContext, item.getGift_img(), (ImageView) helper.getView(R.id.ivSendGiftIcon)); 98 | helper.addOnClickListener(R.id.ivOperation); 99 | break; 100 | 101 | case COMMENT_NONE_IMG: 102 | actionTime = mContext.getString(R.string.publish_comment, actionTime); 103 | ImageLoadUtils.displayImage(mContext, item.getImg_url(), (ImageView) helper.getView(R.id.ivVideo)); 104 | helper.setText(R.id.tvDes, item.getDes()); 105 | if (!TextUtils.isEmpty(item.getContent())) { 106 | helper.setVisible(R.id.tvContent, true); 107 | helper.setText(R.id.tvContent, item.getContent()); 108 | } else { 109 | helper.setVisible(R.id.tvContent, false); 110 | } 111 | helper.addOnClickListener(R.id.ivOperation); 112 | helper.getView(R.id.ivVideo).setOnClickListener(new View.OnClickListener() { 113 | @Override 114 | public void onClick(View v) { 115 | } 116 | }); 117 | break; 118 | 119 | case COMMENT_WITH_IMG: 120 | RecyclerView recyclerView = helper.getView(R.id.rvCommentImg); 121 | BaseQuickAdapter imageAdapter; 122 | if (recyclerView.getAdapter() != null) { //adapter复用 123 | imageAdapter = (BaseQuickAdapter) recyclerView.getAdapter(); 124 | } else { 125 | imageAdapter = null; 126 | } 127 | 128 | if (imageAdapter == null){ 129 | imageAdapter = new BaseQuickAdapter(R.layout.item_comment_img, new ArrayList()) { 130 | @Override 131 | protected void convert(BaseViewHolder helper, String item) { 132 | ImageLoadUtils.displayImage(mContext, item, (ImageView) helper.getView(R.id.ivCommentImg)); 133 | 134 | } 135 | }; 136 | GridLayoutManager gridManager = new GridLayoutManager(mContext, 4); 137 | recyclerView.setLayoutManager(gridManager); 138 | DividerLine dividerLine = new DividerLine(mContext); 139 | recyclerView.addItemDecoration(dividerLine); 140 | recyclerView.setAdapter(imageAdapter); 141 | } 142 | List imgs =imageAdapter.getData(); 143 | imgs.clear(); 144 | actionTime = mContext.getString(R.string.publish_comment, actionTime); 145 | ImageLoadUtils.displayImage(mContext, item.getImg_url(), (ImageView) helper.getView(R.id.ivVideo)); 146 | String[] a = item.getImg_urls().split(","); 147 | Collections.addAll(imgs, a); 148 | imageAdapter.notifyDataSetChanged(); 149 | helper.setText(R.id.tvDes, item.getDes()); 150 | if (!TextUtils.isEmpty(item.getContent())) { 151 | helper.setText(R.id.tvContent, item.getContent()); 152 | } else { 153 | helper.setVisible(R.id.tvContent, false); 154 | } 155 | helper.getView(R.id.ivVideo).setOnClickListener(new View.OnClickListener() { 156 | @Override 157 | public void onClick(View v) { 158 | 159 | } 160 | }); 161 | break; 162 | 163 | case Constants.BAISHI: 164 | actionTime = mContext.getString(R.string.dynamic_from_master, actionTime); 165 | helper.setText(R.id.tvBaishiCost, mContext.getString(R.string.dynamic_master_cost, item.getCost())); 166 | helper.setText(R.id.tvBaishiAction, mContext.getString(R.string.dynamic_master_from, item.getNick())); 167 | ImageLoadUtils.setSimpleCircleHeadIcon(mContext, item.getHead(), NONE_IMG, (ImageView) helper.getView(R.id.ivMasterHead)); 168 | helper.getView(R.id.ivMasterHead).setOnClickListener(new View.OnClickListener() { 169 | @Override 170 | public void onClick(View v) { 171 | 172 | } 173 | }); 174 | break; 175 | } 176 | 177 | helper.setText(R.id.tvAction, actionTime); 178 | helper.setTag(R.id.ivOperation, item); 179 | helper.addOnClickListener(R.id.ivOperation); 180 | } 181 | 182 | // /** 183 | // * 设置动态评论图片 184 | // * 185 | // * @param recyclerView 186 | // * @param imgList 187 | // * @param imageAdapter 188 | // */ 189 | // private void setCommentImgList(RecyclerView recyclerView, List imgList, BaseQuickAdapter imageAdapter) { 190 | // if (imgList != null) { 191 | // return; 192 | // } 193 | // GridLayoutManager gridManager = new GridLayoutManager(mContext, 4); 194 | // recyclerView.setLayoutManager(gridManager); 195 | // DividerLine dividerLine = new DividerLine(DividerLine.VERTICAL); 196 | // dividerLine.setSize(18); 197 | // recyclerView.addItemDecoration(dividerLine); 198 | // dividerLine.setColor(R.color.white); 199 | // recyclerView.setAdapter(imageAdapter); 200 | // } 201 | 202 | private void initImageAdapter(List imgs, RecyclerView recyclerView, BaseQuickAdapter adapter) { 203 | 204 | } 205 | 206 | } 207 | -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/constants/Constants.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo.constants; 2 | 3 | /** 4 | * Created by xuleyuan on 2017/10/12 5 | */ 6 | 7 | public class Constants { 8 | 9 | /** 10 | * 分享视频 11 | */ 12 | public static final int SHARE_VIDEO = 1; 13 | /** 14 | * 分享成功 15 | */ 16 | public static final int SHARE_GAIN = 2; 17 | /** 18 | * 点赞视频 19 | */ 20 | public static final int LIKE_VIDEO = 3; 21 | /** 22 | * 礼物 23 | */ 24 | public static final int GIFT = 4; 25 | /** 26 | * 评论 27 | */ 28 | public static final int COMMENT = 5; 29 | /** 30 | * 拜师 31 | */ 32 | public static final int BAISHI = 6; 33 | /** 34 | * 图片类型评论 35 | */ 36 | public static final int COMMENT_WITH_IMG = 100; 37 | /** 38 | * 非图片评论 39 | */ 40 | public static final int COMMENT_NONE_IMG = 101; 41 | } 42 | -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/divider/DividerLine.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo.divider; 2 | 3 | import android.content.Context; 4 | import android.graphics.Canvas; 5 | import android.graphics.Paint; 6 | import android.support.v7.widget.LinearLayoutManager; 7 | import android.support.v7.widget.RecyclerView; 8 | import android.view.View; 9 | 10 | /** 11 | * Created by xiemy on 2016/9/23. 12 | */ 13 | 14 | public class DividerLine extends Y_DividerItemDecoration { 15 | 16 | public DividerLine(Context context) { 17 | super(context); 18 | } 19 | 20 | @Override 21 | public Y_Divider getDivider(int itemPosition) { 22 | Y_Divider divider = null; 23 | switch (itemPosition % 2) { 24 | case 0: 25 | //每一行第一个显示rignt和bottom 26 | divider = new Y_DividerBuilder() 27 | .setRightSideLine(true, 0xffffffff, 5, 0, 0) 28 | .setBottomSideLine(true, 0xffffffff, 5, 0, 0) 29 | .create(); 30 | break; 31 | case 1: 32 | //每一行第二个显示rignt和bottom 33 | divider = new Y_DividerBuilder() 34 | .setRightSideLine(true, 0xffffffff, 5, 0, 0) 35 | .setBottomSideLine(true, 0xffffffff, 5, 0, 0) 36 | .create(); 37 | break; 38 | case 2: 39 | //每一行第三个显示rignt和bottom 40 | divider = new Y_DividerBuilder() 41 | .setRightSideLine(true, 0xffffffff, 5, 0, 0) 42 | .setBottomSideLine(true, 0xffffffff, 5, 0, 0) 43 | .create(); 44 | break; 45 | case 3: 46 | //每一行第四个显示rignt和bottom 47 | divider = new Y_DividerBuilder() 48 | .setBottomSideLine(true, 0xffffffff, 5, 0, 0) 49 | .create(); 50 | break; 51 | default: 52 | break; 53 | } 54 | return divider; 55 | } 56 | } -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/divider/Dp2Px.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo.divider; 2 | 3 | import android.content.Context; 4 | import android.util.TypedValue; 5 | 6 | /** 7 | * Created by xuleyuan on 2017/8/13 8 | */ 9 | 10 | public class Dp2Px { 11 | private Dp2Px() { 12 | /* cannot be instantiated */ 13 | throw new UnsupportedOperationException("cannot be instantiated"); 14 | } 15 | 16 | /** 17 | * dp转px 18 | * 19 | * @param context 20 | * @param dpVal 21 | * @return 22 | */ 23 | public static int convert(Context context, float dpVal) { 24 | return (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 25 | dpVal, context.getResources().getDisplayMetrics()); 26 | } 27 | 28 | 29 | } -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/divider/Y_Divider.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo.divider; 2 | 3 | /** 4 | * Created by xuleyuan on 2017/8/13 5 | */ 6 | 7 | public class Y_Divider { 8 | 9 | public Y_SideLine leftSideLine; 10 | public Y_SideLine topSideLine; 11 | public Y_SideLine rightSideLine; 12 | public Y_SideLine bottomSideLine; 13 | 14 | 15 | public Y_Divider(Y_SideLine leftSideLine, Y_SideLine topSideLine, Y_SideLine rightSideLine, Y_SideLine bottomSideLine) { 16 | this.leftSideLine = leftSideLine; 17 | this.topSideLine = topSideLine; 18 | this.rightSideLine = rightSideLine; 19 | this.bottomSideLine = bottomSideLine; 20 | } 21 | 22 | public Y_SideLine getLeftSideLine() { 23 | return leftSideLine; 24 | } 25 | 26 | public void setLeftSideLine(Y_SideLine leftSideLine) { 27 | this.leftSideLine = leftSideLine; 28 | } 29 | 30 | public Y_SideLine getTopSideLine() { 31 | return topSideLine; 32 | } 33 | 34 | public void setTopSideLine(Y_SideLine topSideLine) { 35 | this.topSideLine = topSideLine; 36 | } 37 | 38 | public Y_SideLine getRightSideLine() { 39 | return rightSideLine; 40 | } 41 | 42 | public void setRightSideLine(Y_SideLine rightSideLine) { 43 | this.rightSideLine = rightSideLine; 44 | } 45 | 46 | public Y_SideLine getBottomSideLine() { 47 | return bottomSideLine; 48 | } 49 | 50 | public void setBottomSideLine(Y_SideLine bottomSideLine) { 51 | this.bottomSideLine = bottomSideLine; 52 | } 53 | } 54 | 55 | -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/divider/Y_DividerBuilder.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo.divider; 2 | 3 | import android.support.annotation.ColorInt; 4 | 5 | /** 6 | * Created by xuleyuan on 2017/8/13 7 | */ 8 | 9 | public class Y_DividerBuilder { 10 | 11 | private Y_SideLine leftSideLine; 12 | private Y_SideLine topSideLine; 13 | private Y_SideLine rightSideLine; 14 | private Y_SideLine bottomSideLine; 15 | 16 | 17 | public Y_DividerBuilder setLeftSideLine(boolean isHave, @ColorInt int color, float widthDp, float startPaddingDp, float endPaddingDp) { 18 | this.leftSideLine = new Y_SideLine(isHave, color, widthDp, startPaddingDp, endPaddingDp); 19 | return this; 20 | } 21 | 22 | public Y_DividerBuilder setTopSideLine(boolean isHave, @ColorInt int color, float widthDp, float startPaddingDp, float endPaddingDp) { 23 | this.topSideLine = new Y_SideLine(isHave, color, widthDp, startPaddingDp, endPaddingDp); 24 | return this; 25 | } 26 | 27 | public Y_DividerBuilder setRightSideLine(boolean isHave, @ColorInt int color, float widthDp, float startPaddingDp, float endPaddingDp) { 28 | this.rightSideLine = new Y_SideLine(isHave, color, widthDp, startPaddingDp, endPaddingDp); 29 | return this; 30 | } 31 | 32 | public Y_DividerBuilder setBottomSideLine(boolean isHave, @ColorInt int color, float widthDp, float startPaddingDp, float endPaddingDp) { 33 | this.bottomSideLine = new Y_SideLine(isHave, color, widthDp, startPaddingDp, endPaddingDp); 34 | return this; 35 | } 36 | 37 | public Y_Divider create() { 38 | //提供一个默认不显示的sideline,防止空指针 39 | Y_SideLine defaultSideLine = new Y_SideLine(false, 0xff666666, 0, 0, 0); 40 | 41 | leftSideLine = (leftSideLine != null ? leftSideLine : defaultSideLine); 42 | topSideLine = (topSideLine != null ? topSideLine : defaultSideLine); 43 | rightSideLine = (rightSideLine != null ? rightSideLine : defaultSideLine); 44 | bottomSideLine = (bottomSideLine != null ? bottomSideLine : defaultSideLine); 45 | 46 | return new Y_Divider(leftSideLine, topSideLine, rightSideLine, bottomSideLine); 47 | } 48 | 49 | 50 | } 51 | -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/divider/Y_DividerItemDecoration.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo.divider; 2 | 3 | import android.content.Context; 4 | import android.graphics.Canvas; 5 | import android.graphics.Paint; 6 | import android.graphics.Rect; 7 | import android.support.annotation.ColorInt; 8 | import android.support.v7.widget.RecyclerView; 9 | import android.util.TypedValue; 10 | import android.view.View; 11 | 12 | /** 13 | * Created by xuleyuan on 2017/8/13 14 | */ 15 | 16 | public abstract class Y_DividerItemDecoration extends RecyclerView.ItemDecoration { 17 | 18 | private Paint mPaint; 19 | 20 | private Context context; 21 | 22 | public Y_DividerItemDecoration(Context context) { 23 | this.context = context; 24 | mPaint = new Paint(Paint.ANTI_ALIAS_FLAG); 25 | mPaint.setStyle(Paint.Style.FILL); 26 | } 27 | 28 | @Override 29 | public void onDraw(Canvas c, RecyclerView parent, RecyclerView.State state) { 30 | //left, top, right, bottom 31 | int childCount = parent.getChildCount(); 32 | for (int i = 0; i < childCount; i++) { 33 | View child = parent.getChildAt(i); 34 | 35 | int itemPosition = ((RecyclerView.LayoutParams) child.getLayoutParams()).getViewLayoutPosition(); 36 | 37 | Y_Divider divider = getDivider(itemPosition); 38 | 39 | if (divider.getLeftSideLine().isHave()) { 40 | int lineWidthPx = Dp2Px.convert(context, divider.getLeftSideLine().getWidthDp()); 41 | int startPaddingPx = Dp2Px.convert(context, divider.getLeftSideLine().getStartPaddingDp()); 42 | int endPaddingPx = Dp2Px.convert(context, divider.getLeftSideLine().getEndPaddingDp()); 43 | drawChildLeftVertical(child, c, parent, divider.getLeftSideLine().getColor(), lineWidthPx, startPaddingPx, endPaddingPx); 44 | } 45 | if (divider.getTopSideLine().isHave()) { 46 | int lineWidthPx = Dp2Px.convert(context, divider.getTopSideLine().getWidthDp()); 47 | int startPaddingPx = Dp2Px.convert(context, divider.getTopSideLine().getStartPaddingDp()); 48 | int endPaddingPx = Dp2Px.convert(context, divider.getTopSideLine().getEndPaddingDp()); 49 | drawChildTopHorizontal(child, c, parent, divider.topSideLine.getColor(), lineWidthPx, startPaddingPx, endPaddingPx); 50 | } 51 | if (divider.getRightSideLine().isHave()) { 52 | int lineWidthPx = Dp2Px.convert(context, divider.getRightSideLine().getWidthDp()); 53 | int startPaddingPx = Dp2Px.convert(context, divider.getRightSideLine().getStartPaddingDp()); 54 | int endPaddingPx = Dp2Px.convert(context, divider.getRightSideLine().getEndPaddingDp()); 55 | drawChildRightVertical(child, c, parent, divider.getRightSideLine().getColor(), lineWidthPx, startPaddingPx, endPaddingPx); 56 | } 57 | if (divider.getBottomSideLine().isHave()) { 58 | int lineWidthPx = Dp2Px.convert(context, divider.getBottomSideLine().getWidthDp()); 59 | int startPaddingPx = Dp2Px.convert(context, divider.getBottomSideLine().getStartPaddingDp()); 60 | int endPaddingPx = Dp2Px.convert(context, divider.getBottomSideLine().getEndPaddingDp()); 61 | drawChildBottomHorizontal(child, c, parent, divider.getBottomSideLine().getColor(), lineWidthPx, startPaddingPx, endPaddingPx); 62 | } 63 | } 64 | } 65 | 66 | private void drawChildBottomHorizontal(View child, Canvas c, RecyclerView parent, @ColorInt int color, int lineWidthPx, int startPaddingPx, int endPaddingPx) { 67 | 68 | int leftPadding; 69 | int rightPadding; 70 | 71 | if (startPaddingPx <= 0) { 72 | //padding<0当作==0处理 73 | //上下左右默认分割线的两头都出头一个分割线的宽度,避免十字交叉的时候,交叉点是空白 74 | leftPadding = -lineWidthPx; 75 | } else { 76 | leftPadding = startPaddingPx; 77 | } 78 | 79 | if (endPaddingPx <= 0) { 80 | rightPadding = lineWidthPx; 81 | } else { 82 | rightPadding = -endPaddingPx; 83 | } 84 | 85 | RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child 86 | .getLayoutParams(); 87 | int left = child.getLeft() - params.leftMargin + leftPadding; 88 | int right = child.getRight() + params.rightMargin + rightPadding; 89 | int top = child.getBottom() + params.bottomMargin; 90 | int bottom = top + lineWidthPx; 91 | mPaint.setColor(color); 92 | 93 | c.drawRect(left, top, right, bottom, mPaint); 94 | 95 | } 96 | 97 | private void drawChildTopHorizontal(View child, Canvas c, RecyclerView parent, @ColorInt int color, int lineWidthPx, int startPaddingPx, int endPaddingPx) { 98 | int leftPadding; 99 | int rightPadding; 100 | 101 | if (startPaddingPx <= 0) { 102 | //padding<0当作==0处理 103 | //上下左右默认分割线的两头都出头一个分割线的宽度,避免十字交叉的时候,交叉点是空白 104 | leftPadding = -lineWidthPx; 105 | } else { 106 | leftPadding = startPaddingPx; 107 | } 108 | if (endPaddingPx <= 0) { 109 | rightPadding = lineWidthPx; 110 | } else { 111 | rightPadding = -endPaddingPx; 112 | } 113 | 114 | RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child 115 | .getLayoutParams(); 116 | int left = child.getLeft() - params.leftMargin + leftPadding; 117 | int right = child.getRight() + params.rightMargin + rightPadding; 118 | int bottom = child.getTop() - params.topMargin; 119 | int top = bottom - lineWidthPx; 120 | mPaint.setColor(color); 121 | 122 | c.drawRect(left, top, right, bottom, mPaint); 123 | 124 | } 125 | 126 | private void drawChildLeftVertical(View child, Canvas c, RecyclerView parent, @ColorInt int color, int lineWidthPx, int startPaddingPx, int endPaddingPx) { 127 | int topPadding; 128 | int bottomPadding; 129 | 130 | if (startPaddingPx <= 0) { 131 | //padding<0当作==0处理 132 | //上下左右默认分割线的两头都出头一个分割线的宽度,避免十字交叉的时候,交叉点是空白 133 | topPadding = -lineWidthPx; 134 | } else { 135 | topPadding = startPaddingPx; 136 | } 137 | if (endPaddingPx <= 0) { 138 | bottomPadding = lineWidthPx; 139 | } else { 140 | bottomPadding = -endPaddingPx; 141 | } 142 | 143 | RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child 144 | .getLayoutParams(); 145 | int top = child.getTop() - params.topMargin + topPadding; 146 | int bottom = child.getBottom() + params.bottomMargin + bottomPadding; 147 | int right = child.getLeft() - params.leftMargin; 148 | int left = right - lineWidthPx; 149 | mPaint.setColor(color); 150 | 151 | c.drawRect(left, top, right, bottom, mPaint); 152 | 153 | } 154 | 155 | private void drawChildRightVertical(View child, Canvas c, RecyclerView parent, @ColorInt int color, int lineWidthPx, int startPaddingPx, int endPaddingPx) { 156 | 157 | int topPadding; 158 | int bottomPadding; 159 | 160 | if (startPaddingPx <= 0) { 161 | //padding<0当作==0处理 162 | //上下左右默认分割线的两头都出头一个分割线的宽度,避免十字交叉的时候,交叉点是空白 163 | topPadding = -lineWidthPx; 164 | } else { 165 | topPadding = startPaddingPx; 166 | } 167 | if (endPaddingPx <= 0) { 168 | bottomPadding = lineWidthPx; 169 | } else { 170 | bottomPadding = -endPaddingPx; 171 | } 172 | 173 | RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child 174 | .getLayoutParams(); 175 | int top = child.getTop() - params.topMargin + topPadding; 176 | int bottom = child.getBottom() + params.bottomMargin + bottomPadding; 177 | int left = child.getRight() + params.rightMargin; 178 | int right = left + lineWidthPx; 179 | mPaint.setColor(color); 180 | 181 | c.drawRect(left, top, right, bottom, mPaint); 182 | 183 | } 184 | 185 | @Override 186 | public void getItemOffsets(Rect outRect, View view, RecyclerView parent, RecyclerView.State state) { 187 | 188 | //outRect 看源码可知这里只是把Rect类型的outRect作为一个封装了left,right,top,bottom的数据结构, 189 | //作为传递left,right,top,bottom的偏移值来用的 190 | 191 | int itemPosition = ((RecyclerView.LayoutParams) view.getLayoutParams()).getViewLayoutPosition(); 192 | 193 | Y_Divider divider = getDivider(itemPosition); 194 | int left = divider.getLeftSideLine().isHave() ? Dp2Px.convert(context, divider.getLeftSideLine().getWidthDp()) : 0; 195 | int top = divider.getTopSideLine().isHave() ? Dp2Px.convert(context, divider.getTopSideLine().getWidthDp()) : 0; 196 | int right = divider.getRightSideLine().isHave() ? Dp2Px.convert(context, divider.getRightSideLine().getWidthDp()) : 0; 197 | int bottom = divider.getBottomSideLine().isHave() ? Dp2Px.convert(context, divider.getBottomSideLine().getWidthDp()) : 0; 198 | 199 | outRect.set(left, top, right, bottom); 200 | } 201 | 202 | 203 | public abstract Y_Divider getDivider(int itemPosition); 204 | 205 | 206 | } 207 | 208 | -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/divider/Y_SideLine.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo.divider; 2 | 3 | import android.support.annotation.ColorInt; 4 | 5 | /** 6 | * Created by xuleyuan on 2017/8/13 7 | */ 8 | 9 | public class Y_SideLine { 10 | 11 | public boolean isHave = false; 12 | /** 13 | * A single color value in the form 0xAARRGGBB. 14 | **/ 15 | public int color; 16 | /** 17 | * 单位dp 18 | */ 19 | public float widthDp; 20 | /** 21 | * startPaddingDp,分割线起始的padding,水平方向左为start,垂直方向上为start 22 | * endPaddingDp,分割线尾部的padding,水平方向右为end,垂直方向下为end 23 | */ 24 | public float startPaddingDp; 25 | public float endPaddingDp; 26 | 27 | public Y_SideLine(boolean isHave, @ColorInt int color, float widthDp, float startPaddingDp, float endPaddingDp) { 28 | this.isHave = isHave; 29 | this.color = color; 30 | this.widthDp = widthDp; 31 | this.startPaddingDp = startPaddingDp; 32 | this.endPaddingDp = endPaddingDp; 33 | } 34 | 35 | public float getStartPaddingDp() { 36 | return startPaddingDp; 37 | } 38 | 39 | public void setStartPaddingDp(float startPaddingDp) { 40 | this.startPaddingDp = startPaddingDp; 41 | } 42 | 43 | public float getEndPaddingDp() { 44 | return endPaddingDp; 45 | } 46 | 47 | public void setEndPaddingDp(float endPaddingDp) { 48 | this.endPaddingDp = endPaddingDp; 49 | } 50 | 51 | public boolean isHave() { 52 | return isHave; 53 | } 54 | 55 | public void setHave(boolean have) { 56 | isHave = have; 57 | } 58 | 59 | public int getColor() { 60 | return color; 61 | } 62 | 63 | public void setColor(int color) { 64 | this.color = color; 65 | } 66 | 67 | public float getWidthDp() { 68 | return widthDp; 69 | } 70 | 71 | public void setWidthDp(float widthDp) { 72 | this.widthDp = widthDp; 73 | } 74 | } -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/model/DynamicsModel.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo.model; 2 | 3 | import com.chad.library.adapter.base.entity.MultiItemEntity; 4 | 5 | /** 6 | * Created by xuleyuan on 2017/8/29 7 | */ 8 | 9 | public class DynamicsModel implements MultiItemEntity { 10 | 11 | private int action; 12 | private int itemType; 13 | private long action_time; 14 | private int vid; //, 15 | private String des; //, 16 | private String img_url; //, 17 | private String ain_img; //, 18 | private String play_url; //, 19 | private int gain_cid; //, 20 | private String gain_content; //, 21 | private String gift_img; //, 22 | private int uid; //, 23 | private String uid_nick; //, 24 | private int to_uid; //, 25 | private String to_uid_nick; //, 26 | private String gift_name; // 27 | private int cid; //, 28 | private String content; //, 29 | private String img_urls; // 30 | private String days; //, 31 | private String head; //, 32 | private String nick; //, 33 | private int master_uid; //, 34 | private int cost; // 35 | private String gain_img; // 36 | 37 | public void setAction(int action) { 38 | this.action = action; 39 | } 40 | 41 | public void setAction_time(long action_time) { 42 | this.action_time = action_time; 43 | } 44 | 45 | public void setVid(int vid) { 46 | this.vid = vid; 47 | } 48 | 49 | public void setDes(String des) { 50 | this.des = des; 51 | } 52 | 53 | public void setImg_url(String img_url) { 54 | this.img_url = img_url; 55 | } 56 | 57 | public void setAin_img(String ain_img) { 58 | this.ain_img = ain_img; 59 | } 60 | 61 | public void setPlay_url(String play_url) { 62 | this.play_url = play_url; 63 | } 64 | 65 | public void setGain_cid(int gain_cid) { 66 | this.gain_cid = gain_cid; 67 | } 68 | 69 | public void setGain_content(String gain_content) { 70 | this.gain_content = gain_content; 71 | } 72 | 73 | public void setGift_img(String gift_img) { 74 | this.gift_img = gift_img; 75 | } 76 | 77 | public void setUid(int uid) { 78 | this.uid = uid; 79 | } 80 | 81 | public void setUid_nick(String uid_nick) { 82 | this.uid_nick = uid_nick; 83 | } 84 | 85 | public void setTo_uid(int to_uid) { 86 | this.to_uid = to_uid; 87 | } 88 | 89 | public void setTo_uid_nick(String to_uid_nick) { 90 | this.to_uid_nick = to_uid_nick; 91 | } 92 | 93 | public void setGift_name(String gift_name) { 94 | this.gift_name = gift_name; 95 | } 96 | 97 | public void setCid(int cid) { 98 | this.cid = cid; 99 | } 100 | 101 | public void setContent(String content) { 102 | this.content = content; 103 | } 104 | 105 | public void setImg_urls(String img_urls) { 106 | this.img_urls = img_urls; 107 | } 108 | 109 | public void setDays(String days) { 110 | this.days = days; 111 | } 112 | 113 | public void setHead(String head) { 114 | this.head = head; 115 | } 116 | 117 | public void setNick(String nick) { 118 | this.nick = nick; 119 | } 120 | 121 | public void setMaster_uid(int master_uid) { 122 | this.master_uid = master_uid; 123 | } 124 | 125 | public void setCost(int cost) { 126 | this.cost = cost; 127 | } 128 | 129 | public String getGain_img() { 130 | return gain_img; 131 | } 132 | 133 | public void setGain_img(String gain_img) { 134 | this.gain_img = gain_img; 135 | } 136 | 137 | @Override 138 | public int getItemType() { 139 | return itemType; 140 | } 141 | 142 | public void setItemType(int itemType) { 143 | this.itemType = itemType; 144 | } 145 | 146 | public int getAction() { 147 | return action; 148 | } 149 | 150 | public long getAction_time() { 151 | return action_time; 152 | } 153 | 154 | public int getVid() { 155 | return vid; 156 | } 157 | 158 | public String getDes() { 159 | if (des == null) 160 | return ""; 161 | return des; 162 | } 163 | 164 | public String getImg_url() { 165 | if (img_url == null) 166 | return ""; 167 | return img_url; 168 | } 169 | 170 | public String getAin_img() { 171 | return ain_img; 172 | } 173 | 174 | public String getPlay_url() { 175 | return play_url; 176 | } 177 | 178 | public int getGain_cid() { 179 | return gain_cid; 180 | } 181 | 182 | public String getGain_content() { 183 | return gain_content; 184 | } 185 | 186 | public String getGift_img() { 187 | return gift_img; 188 | } 189 | 190 | public int getUid() { 191 | return uid; 192 | } 193 | 194 | public String getUid_nick() { 195 | return uid_nick; 196 | } 197 | 198 | public int getTo_uid() { 199 | return to_uid; 200 | } 201 | 202 | public String getTo_uid_nick() { 203 | return to_uid_nick; 204 | } 205 | 206 | public String getGift_name() { 207 | return gift_name; 208 | } 209 | 210 | public int getCid() { 211 | return cid; 212 | } 213 | 214 | public String getContent() { 215 | if (content == null) 216 | return ""; 217 | return content; 218 | } 219 | 220 | public String getImg_urls() { 221 | return img_urls; 222 | } 223 | 224 | public String getDays() { 225 | return days; 226 | } 227 | 228 | public String getHead() { 229 | return head; 230 | } 231 | 232 | public String getNick() { 233 | if (nick == null) 234 | return ""; 235 | return nick; 236 | } 237 | 238 | public int getMaster_uid() { 239 | return master_uid; 240 | } 241 | 242 | public int getCost() { 243 | return cost; 244 | } 245 | } 246 | -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/util/DateUtil.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo.util; 2 | 3 | import android.util.Log; 4 | 5 | import java.text.SimpleDateFormat; 6 | import java.util.Calendar; 7 | import java.util.Date; 8 | 9 | /** 10 | * Created by xuleyuan on 2017/10/12 11 | */ 12 | 13 | public class DateUtil { 14 | 15 | public static final String FULL_DATE_PATTERN_SSS = "yyyy-MM-dd HH:mm:ss.SSS"; 16 | public static final String FULL_DATE_PATTERN = "yyyy-MM-dd HH:mm:ss"; 17 | public static final String DEFAULT_DATE_PATTERN = "yyyy-MM-dd"; 18 | public static final String YEAR = "yyyy年"; 19 | public static final String DYNAMICS = "yyyy年MM月dd日"; 20 | public static final String MONTH = "MM月"; 21 | public static final String FULL_TIME = "HH:mm"; 22 | public static final String VIDEO_TIME = "MM-dd HH:mm"; 23 | public static final String WITHIN_A_YEAR = "MM-dd HH:mm"; 24 | public static final String PURCHASE_TIEM = "yyyy年MM月dd号"; 25 | public static final String MONTH_AND_YEAR = "yyyy年MM月"; 26 | public static final String MORE_THAN_A_YEAR = "yy-MM-dd HH:mm"; 27 | public static final String RELATION_TIME = "yyyy.MM.dd"; 28 | private static int serverDifference = 0; 29 | 30 | public static String getDataFormat(long formatTime) { 31 | String currentData = getCurrentTime(); 32 | String formatData = getTime(formatTime); 33 | if (formatData.equals(currentData)) { 34 | return "今天"; 35 | } 36 | String yestDay = getYesTodayDate(); 37 | if (formatData.equals(yestDay)) { 38 | return "昨天"; 39 | } 40 | String dynamics = getTime(formatTime, DYNAMICS); 41 | dynamics = dynamics.substring(2, dynamics.length()); 42 | return dynamics; 43 | } 44 | 45 | /** 46 | * 得到昨天的日期 47 | * 48 | * @return 49 | */ 50 | public static String getYesTodayDate() { 51 | Calendar calendar = Calendar.getInstance(); 52 | calendar.add(Calendar.DATE, -1); 53 | SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd"); 54 | return sdf.format(calendar.getTime()); 55 | } 56 | 57 | 58 | public static String getTime(long time, String pattern) { 59 | return getString(new Date(time), pattern); 60 | } 61 | 62 | public static String getTime(long time) { 63 | return getTime(time, DEFAULT_DATE_PATTERN); 64 | } 65 | 66 | public static String getCurrentTime() { 67 | return getCurrentTime(DEFAULT_DATE_PATTERN); 68 | } 69 | 70 | public static String getCurrentTime(String pattern) { 71 | return getString(new Date(), pattern); 72 | } 73 | 74 | public static String getString(Date date, String pattern) { 75 | String str = ""; 76 | try { 77 | SimpleDateFormat sf = new SimpleDateFormat(pattern); 78 | str = sf.format(date); 79 | } catch (Exception e) { 80 | e.printStackTrace(); 81 | } 82 | return str; 83 | } 84 | 85 | } 86 | -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/util/ImageLoadUtils.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo.util; 2 | 3 | import android.annotation.TargetApi; 4 | import android.content.Context; 5 | import android.os.Build; 6 | import android.support.annotation.DrawableRes; 7 | import android.text.TextUtils; 8 | import android.view.View; 9 | import android.widget.ImageView; 10 | 11 | import com.bumptech.glide.Glide; 12 | import com.bumptech.glide.RequestManager; 13 | import com.bumptech.glide.load.engine.DiskCacheStrategy; 14 | 15 | 16 | import pkanimation.xly.com.brvahcircledemo.util.transform.RoundTransform; 17 | import pkanimation.xly.com.brvahcircledemo.util.transform.SimpleCircleTransform; 18 | 19 | import static com.bumptech.glide.Glide.with; 20 | 21 | /** 22 | * Created by xuleyuan on 2017/10/12 23 | */ 24 | 25 | public class ImageLoadUtils { 26 | /** 27 | * 异步加载图片 28 | * 29 | * @param imgUrl 图片url 30 | * @param imageView 31 | */ 32 | public static void displayImage(Context context, String imgUrl, ImageView imageView) { 33 | RequestManager rm = Glide.with(context); 34 | rm.load(imgUrl).centerCrop() 35 | .crossFade() 36 | .diskCacheStrategy(DiskCacheStrategy.ALL) 37 | .into(imageView); 38 | } 39 | 40 | /** 41 | * 异步加载图片 42 | * 43 | * @param imgUrl 图片url 44 | * @param imageView 45 | * @param drawableRes 默认图片资源id 46 | */ 47 | @TargetApi(Build.VERSION_CODES.JELLY_BEAN_MR1) 48 | public static void displayImage(Context context, String imgUrl, ImageView imageView, int drawableRes, float round) { 49 | with(context) 50 | .load(imgUrl) 51 | .centerCrop() 52 | .placeholder(drawableRes) 53 | .crossFade() 54 | .dontAnimate() 55 | .transform(new RoundTransform(context, round)) 56 | .diskCacheStrategy(DiskCacheStrategy.ALL) 57 | .into(imageView); 58 | } 59 | 60 | 61 | /** 62 | * 设置简单的圆头像 63 | * 64 | * @param headIconUrl 65 | */ 66 | @TargetApi(Build.VERSION_CODES.JELLY_BEAN_MR1) 67 | public static void setSimpleCircleHeadIcon(Context context, String headIconUrl, @DrawableRes int defaultResId, final ImageView view) { 68 | if (TextUtils.isEmpty(headIconUrl)) { 69 | setDefaultSimpleCircleHeadIcon(context, defaultResId, view); 70 | return; 71 | } 72 | 73 | with(context).load(headIconUrl).placeholder(defaultResId) 74 | .centerCrop().error(defaultResId).crossFade() 75 | .diskCacheStrategy(DiskCacheStrategy.ALL) 76 | .transform(new SimpleCircleTransform(context)).into(view); 77 | } 78 | 79 | /** 80 | * 设置默认的简单的圆头像 81 | */ 82 | public static void setDefaultSimpleCircleHeadIcon(Context context, 83 | @DrawableRes int defaultResId, final ImageView view) { 84 | with(context).load(defaultResId).placeholder(defaultResId) 85 | .crossFade().centerCrop().error(defaultResId) 86 | .diskCacheStrategy(DiskCacheStrategy.ALL) 87 | .transform(new SimpleCircleTransform(context)).into(view); 88 | 89 | } 90 | 91 | 92 | } 93 | -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/util/transform/RoundTransform.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo.util.transform; 2 | 3 | import android.content.Context; 4 | import android.content.res.Resources; 5 | import android.graphics.Bitmap; 6 | import android.graphics.BitmapShader; 7 | import android.graphics.Canvas; 8 | import android.graphics.Paint; 9 | import android.graphics.RectF; 10 | 11 | import com.bumptech.glide.load.engine.bitmap_recycle.BitmapPool; 12 | import com.bumptech.glide.load.resource.bitmap.BitmapTransformation; 13 | 14 | /** 15 | * Created by user on 2016/8/26. 16 | */ 17 | public class RoundTransform extends BitmapTransformation { 18 | 19 | private static float radius = 0f; 20 | 21 | public RoundTransform(Context context) { 22 | this(context, 4); 23 | } 24 | 25 | public RoundTransform(Context context, float dp) { 26 | super(context); 27 | this.radius = Resources.getSystem().getDisplayMetrics().density * dp; 28 | } 29 | 30 | @Override 31 | protected Bitmap transform(BitmapPool pool, Bitmap toTransform, int outWidth, int outHeight) { 32 | return roundCrop(pool, toTransform); 33 | } 34 | 35 | private static Bitmap roundCrop(BitmapPool pool, Bitmap source) { 36 | if (source == null) return null; 37 | 38 | Bitmap result = pool.get(source.getWidth(), source.getHeight(), Bitmap.Config.ARGB_8888); 39 | if (result == null) { 40 | result = Bitmap.createBitmap(source.getWidth(), source.getHeight(), Bitmap.Config.ARGB_8888); 41 | } 42 | 43 | Canvas canvas = new Canvas(result); 44 | Paint paint = new Paint(); 45 | paint.setShader(new BitmapShader(source, BitmapShader.TileMode.CLAMP, BitmapShader.TileMode.CLAMP)); 46 | paint.setAntiAlias(true); 47 | RectF rectF = new RectF(0f, 0f, source.getWidth(), source.getHeight()); 48 | canvas.drawRoundRect(rectF, radius, radius, paint); 49 | return result; 50 | } 51 | 52 | @Override 53 | public String getId() { 54 | return getClass().getName() + Math.round(radius); 55 | } 56 | } 57 | -------------------------------------------------------------------------------- /app/src/main/java/pkanimation/xly/com/brvahcircledemo/util/transform/SimpleCircleTransform.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo.util.transform; 2 | 3 | import android.content.Context; 4 | import android.graphics.Bitmap; 5 | import android.graphics.BitmapShader; 6 | import android.graphics.Canvas; 7 | import android.graphics.Paint; 8 | 9 | import com.bumptech.glide.load.engine.bitmap_recycle.BitmapPool; 10 | import com.bumptech.glide.load.resource.bitmap.BitmapTransformation; 11 | 12 | public class SimpleCircleTransform extends BitmapTransformation { 13 | public SimpleCircleTransform(Context context) { 14 | super(context); 15 | } 16 | 17 | @Override 18 | protected Bitmap transform(BitmapPool pool, Bitmap toTransform, int outWidth, int outHeight) { 19 | return circleCrop(pool, toTransform); 20 | } 21 | 22 | private static Bitmap circleCrop(BitmapPool pool, Bitmap source) { 23 | if (source == null) return null; 24 | 25 | int size = Math.min(source.getWidth(), source.getHeight()); 26 | int x = (source.getWidth() - size) / 2; 27 | int y = (source.getHeight() - size) / 2; 28 | 29 | // TODO this could be acquired from the pool too 30 | Bitmap squared = Bitmap.createBitmap(source, x, y, size, size); 31 | 32 | Bitmap result = pool.get(size, size, Bitmap.Config.ARGB_8888); 33 | if (result == null) { 34 | result = Bitmap.createBitmap(size, size, Bitmap.Config.ARGB_8888); 35 | } 36 | 37 | Canvas canvas = new Canvas(result); 38 | Paint paint = new Paint(); 39 | paint.setShader(new BitmapShader(squared, BitmapShader.TileMode.CLAMP, BitmapShader.TileMode.CLAMP)); 40 | paint.setAntiAlias(true); 41 | float r = size / 2f; 42 | canvas.drawCircle(r, r, r, paint); 43 | squared.recycle(); 44 | return result; 45 | } 46 | 47 | @Override 48 | public String getId() { 49 | return getClass().getName(); 50 | } 51 | } -------------------------------------------------------------------------------- /app/src/main/res/layout/activity_main.xml: -------------------------------------------------------------------------------- 1 | 2 | 6 | 7 | 11 | 12 | -------------------------------------------------------------------------------- /app/src/main/res/layout/dynamice_comment_with_imgs.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 19 | 20 | 29 | 30 | 40 | 41 | 50 | 51 | 60 | 61 | 67 | 68 | 72 | 73 | 79 | 80 | 90 | 91 | 101 | 102 | 103 | 104 | 105 | 113 | 114 | 115 | 116 | -------------------------------------------------------------------------------- /app/src/main/res/layout/dynamics_baishi.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 19 | 20 | 29 | 30 | 40 | 41 | 50 | 51 | 57 | 58 | 64 | 65 | 71 | 72 | 79 | 80 | 84 | 85 | 86 | 94 | 95 | 96 | 103 | 104 | 105 | 106 | 107 | 114 | 115 | -------------------------------------------------------------------------------- /app/src/main/res/layout/dynamics_comment.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 19 | 20 | 29 | 30 | 40 | 41 | 50 | 51 | 60 | 61 | 68 | 69 | 79 | 80 | 90 | 91 | 92 | 99 | 100 | 101 | -------------------------------------------------------------------------------- /app/src/main/res/layout/dynamics_gift.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 19 | 20 | 29 | 30 | 40 | 41 | 50 | 51 | 58 | 59 | 64 | 65 | 73 | 74 | 75 | 82 | 83 | -------------------------------------------------------------------------------- /app/src/main/res/layout/dynamics_like_video.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 19 | 20 | 29 | 30 | 40 | 41 | 50 | 51 | 58 | 59 | 68 | 69 | 79 | 80 | 81 | 88 | 89 | 90 | 91 | -------------------------------------------------------------------------------- /app/src/main/res/layout/dynamics_share_gain.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 19 | 20 | 29 | 30 | 40 | 41 | 50 | 51 | 60 | 61 | 67 | 68 | 76 | 77 | 84 | 85 | 91 | 92 | 101 | 102 | 112 | 113 | 114 | 115 | 116 | 123 | 124 | 125 | 126 | 127 | 128 | -------------------------------------------------------------------------------- /app/src/main/res/layout/dynamics_share_video.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 19 | 20 | 29 | 30 | 40 | 41 | 50 | 51 | 60 | 61 | 68 | 69 | 79 | 80 | 90 | 91 | 92 | 93 | 100 | 101 | 102 | 103 | -------------------------------------------------------------------------------- /app/src/main/res/layout/item_comment_img.xml: -------------------------------------------------------------------------------- 1 | 2 | 8 | -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/xlyasdasd/BRVAHCircleDemo/3812b957b5fa37996564e90b631f082cf529b06c/app/src/main/res/mipmap-hdpi/ic_launcher.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-mdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/xlyasdasd/BRVAHCircleDemo/3812b957b5fa37996564e90b631f082cf529b06c/app/src/main/res/mipmap-mdpi/ic_launcher.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-mdpi/mine_omitted.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/xlyasdasd/BRVAHCircleDemo/3812b957b5fa37996564e90b631f082cf529b06c/app/src/main/res/mipmap-mdpi/mine_omitted.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-mdpi/user_bs_ticker_bg.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/xlyasdasd/BRVAHCircleDemo/3812b957b5fa37996564e90b631f082cf529b06c/app/src/main/res/mipmap-mdpi/user_bs_ticker_bg.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-mdpi/video_play_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/xlyasdasd/BRVAHCircleDemo/3812b957b5fa37996564e90b631f082cf529b06c/app/src/main/res/mipmap-mdpi/video_play_small.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/xlyasdasd/BRVAHCircleDemo/3812b957b5fa37996564e90b631f082cf529b06c/app/src/main/res/mipmap-xhdpi/ic_launcher.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xxhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/xlyasdasd/BRVAHCircleDemo/3812b957b5fa37996564e90b631f082cf529b06c/app/src/main/res/mipmap-xxhdpi/ic_launcher.png -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xxxhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/xlyasdasd/BRVAHCircleDemo/3812b957b5fa37996564e90b631f082cf529b06c/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png -------------------------------------------------------------------------------- /app/src/main/res/values-w820dp/dimens.xml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 64dp 6 | 7 | -------------------------------------------------------------------------------- /app/src/main/res/values/colors.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | #3F51B5 4 | #303F9F 5 | #FF4081 6 | #272B3C 7 | #9B9FAD 8 | #EFEFEF 9 | #595d71 10 | #f2f2f2 11 | #ffffff 12 | 13 | -------------------------------------------------------------------------------- /app/src/main/res/values/dimens.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 16dp 4 | 16dp 5 | 15dp 6 | 20dp 7 | 13sp 8 | 9dp 9 | 12sp 10 | 10dp 11 | 20dp 12 | 15sp 13 | 20dp 14 | 50dp 15 | 14sp 16 | 1dp 17 | 54dp 18 | 10dp 19 | 15dp 20 | 21 | -------------------------------------------------------------------------------- /app/src/main/res/values/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | BRVAHCircleDemo 3 | 操作 4 | 视频 5 | 背景 6 | 师傅头像 7 | 送礼 8 | 最近成果 9 | 10 | 11 | 我的动态 12 | 分享视频 %1$s 13 | 晒成果 %1$s 14 | 点赞该视频 %1$s 15 | 赠送礼物 %1$s 16 | 发表评论 %1$s 17 | 拜师 %1$s 18 | 花费%1$d元拜师卷 19 | 拜“%1$s”为师 20 | 您赠送了一个给%1$s 21 | 删除该动态 22 | 23 | 24 | -------------------------------------------------------------------------------- /app/src/main/res/values/styles.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 10 | 11 | 12 | -------------------------------------------------------------------------------- /app/src/test/java/pkanimation/xly/com/brvahcircledemo/ExampleUnitTest.java: -------------------------------------------------------------------------------- 1 | package pkanimation.xly.com.brvahcircledemo; 2 | 3 | import org.junit.Test; 4 | 5 | import static org.junit.Assert.*; 6 | 7 | /** 8 | * Example local unit test, which will execute on the development machine (host). 9 | * 10 | * @see Testing documentation 11 | */ 12 | public class ExampleUnitTest { 13 | @Test 14 | public void addition_isCorrect() throws Exception { 15 | assertEquals(4, 2 + 2); 16 | } 17 | } -------------------------------------------------------------------------------- /build.gradle: -------------------------------------------------------------------------------- 1 | // Top-level build file where you can add configuration options common to all sub-projects/modules. 2 | 3 | buildscript { 4 | repositories { 5 | jcenter() 6 | } 7 | dependencies { 8 | classpath 'com.android.tools.build:gradle:2.2.2' 9 | 10 | // NOTE: Do not place your application dependencies here; they belong 11 | // in the individual module build.gradle files 12 | } 13 | } 14 | 15 | allprojects { 16 | repositories { 17 | jcenter() 18 | maven { url "https://jitpack.io" } 19 | } 20 | } 21 | 22 | task clean(type: Delete) { 23 | delete rootProject.buildDir 24 | } 25 | -------------------------------------------------------------------------------- /gradle.properties: -------------------------------------------------------------------------------- 1 | # Project-wide Gradle settings. 2 | 3 | # IDE (e.g. Android Studio) users: 4 | # Gradle settings configured through the IDE *will override* 5 | # any settings specified in this file. 6 | 7 | # For more details on how to configure your build environment visit 8 | # http://www.gradle.org/docs/current/userguide/build_environment.html 9 | 10 | # Specifies the JVM arguments used for the daemon process. 11 | # The setting is particularly useful for tweaking memory settings. 12 | org.gradle.jvmargs=-Xmx1536m 13 | 14 | # When configured, Gradle will run in incubating parallel mode. 15 | # This option should only be used with decoupled projects. More details, visit 16 | # http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects 17 | # org.gradle.parallel=true 18 | -------------------------------------------------------------------------------- /settings.gradle: -------------------------------------------------------------------------------- 1 | include ':app' 2 | --------------------------------------------------------------------------------