Skip to content

Commit b1a5797

Browse files
committed
添加动态页面
1 parent 5ec858b commit b1a5797

File tree

19 files changed

+305
-54
lines changed

19 files changed

+305
-54
lines changed

.idea/codeStyles/codeStyleConfig.xml

Lines changed: 5 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

.idea/misc.xml

Lines changed: 4 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

.idea/vcs.xml

Lines changed: 6 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

README.md

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
[![Platform](https://img.shields.io/badge/platform-Android-green.svg)](https://github.com/fmtjava/OpenGitHub)
33
[![API](https://img.shields.io/badge/API-17%2B-brightgreen.svg?style=flat)](https://android-arsenal.com/api?level=16)
44
[![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)
5-
[![Release Version](https://img.shields.io/badge/version-1.8-red.svg)](https://fir.im/8jw7)
5+
[![Release Version](https://img.shields.io/badge/version-1.9-red.svg)](https://fir.im/8jw7)
66
[![](https://img.shields.io/badge/Author-fmtjava-blue.svg)](https://github.com/fmtjava)
77
[![](https://img.shields.io/badge/QQ-2694746499-orange.svg)](https://github.com/fmtjava)<br />
88
基于Kotlin + Jetpack全家桶 + Coroutines(协程) 等架构实现的一款精简版Github客户端项目。<br />
@@ -84,8 +84,12 @@ Model-View-ViewModel,View 指绿色的 Activity/Fragment,主要负责界面
8484
Glide相比起Fresco要轻量很多,api调用起来也很简洁,对图片加载要求不是很高的话建议使用Glide。
8585

8686
# 更新日志
87+
### v1.9
88+
* 添加动态页面
89+
* 调整项目结构,优化代码
8790
### v1.8
8891
* 添加App启动优化代码,提示App的启动速度
92+
* 调整项目结构,优化代码
8993
### v1.7
9094
* 使用协程进一步简化异步代码,增强代码的可读性
9195
* BaseActivity、BaseMVActivity等基类再次进行封装

app/build.gradle

Lines changed: 13 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,8 @@ android {
1212
applicationId "com.fmt.github"
1313
minSdkVersion 17
1414
targetSdkVersion 28
15-
versionCode 8
16-
versionName "1.8"
15+
versionCode 9
16+
versionName "1.9"
1717
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
1818
}
1919
signingConfigs {
@@ -38,6 +38,10 @@ android {
3838
androidExtensions {
3939
experimental = true
4040
}
41+
compileOptions {
42+
sourceCompatibility 1.8
43+
targetCompatibility 1.8
44+
}
4145
}
4246

4347
dependencies {
@@ -46,15 +50,15 @@ dependencies {
4650
//Androidx
4751
implementation 'androidx.appcompat:appcompat:1.1.0'
4852
implementation 'androidx.constraintlayout:constraintlayout:1.1.3'
49-
testImplementation 'junit:junit:4.12'
53+
testImplementation 'junit:junit:4.13'
5054
androidTestImplementation 'androidx.test:runner:1.2.0'
5155
androidTestImplementation 'androidx.test.espresso:espresso-core:3.2.0'
5256
implementation 'androidx.recyclerview:recyclerview:1.1.0'
5357
implementation 'com.google.android.material:material:1.1.0'
5458

5559
//协程
56-
implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-core:1.3.0'
57-
implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-android:1.3.0'
60+
implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-core:1.3.3'
61+
implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-android:1.3.3'
5862

5963
//Android KTX 是一组 Kotlin 扩展程序,属于 Android Jetpack 系列
6064
implementation 'androidx.core:core-ktx:1.2.0'
@@ -63,10 +67,10 @@ dependencies {
6367
implementation 'androidx.lifecycle:lifecycle-livedata-ktx:2.2.0'
6468

6569

66-
//okhttp + retrofit(2.6.0支持协程)
70+
//okhttp + retrofit(2.6.0以后支持协程)
6771
implementation("com.squareup.okhttp3:logging-interceptor:4.0.0")
68-
implementation 'com.squareup.retrofit2:retrofit:2.6.0'
69-
implementation 'com.squareup.retrofit2:converter-gson:2.6.0'
72+
implementation 'com.squareup.retrofit2:retrofit:2.7.1'
73+
implementation 'com.squareup.retrofit2:converter-gson:2.7.1'
7074

7175
//协程 + room
7276
implementation "androidx.room:room-runtime:2.2.5"
@@ -85,7 +89,7 @@ dependencies {
8589
implementation 'de.hdodenhof:circleimageview:3.0.0'
8690
implementation 'com.just.agentweb:agentweb:4.0.3-beta'
8791
implementation project(path: ':simplebehavior')
88-
implementation 'com.github.bumptech.glide:glide:4.9.0'
92+
implementation 'com.github.bumptech.glide:glide:4.10.0'
8993
implementation 'com.github.GrenderG:Toasty:1.4.2'
9094
implementation 'com.github.jd-alexander:LikeButton:0.2.3'
9195
implementation 'com.github.Kennyc1012:MultiStateView:2.1'

app/src/main/java/com/fmt/github/ext/DataBindExt.kt

Lines changed: 44 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,18 @@
11
package com.fmt.github.ext
22

3+
import android.graphics.Typeface
34
import android.graphics.drawable.Drawable
5+
import android.text.Spannable
6+
import android.text.SpannableStringBuilder
7+
import android.text.style.StyleSpan
48
import android.widget.ImageView
59
import androidx.core.content.ContextCompat
610
import androidx.databinding.BindingAdapter
711
import androidx.databinding.BindingConversion
812
import com.bumptech.glide.Glide
913
import com.fmt.github.AppContext
1014
import com.fmt.github.R
15+
import com.fmt.github.home.model.ReceivedEventModel
1116
import com.fmt.github.repos.model.ReposItemModel
1217

1318
//DataBinding自定义属性
@@ -44,4 +49,42 @@ fun setReposLanguageBg(reposItemModel: ReposItemModel): Drawable? =
4449
"Dart" -> ContextCompat.getDrawable(AppContext, R.drawable.shape_dart_circular_bg)
4550
else -> ContextCompat.getDrawable(AppContext, R.drawable.shape_html_circular_bg)
4651
}
47-
}
52+
}
53+
54+
@BindingConversion
55+
fun setReceivedEventImage(receivedEventModel: ReceivedEventModel): Drawable? =
56+
when (receivedEventModel.type) {
57+
"WatchEvent" -> ContextCompat.getDrawable(AppContext, R.mipmap.icon_star_yellow)
58+
"ForkEvent", "PushEvent", "CreateEvent" -> ContextCompat.getDrawable(
59+
AppContext,
60+
R.mipmap.icon_fork_green
61+
)
62+
else -> null
63+
}
64+
65+
@BindingConversion
66+
fun setReceivedEventContent(receivedEventModel: ReceivedEventModel): CharSequence {
67+
val actor = receivedEventModel.actor.display_login
68+
val action = when (receivedEventModel.type) {
69+
"WatchEvent" -> "starred"
70+
"CreateEvent" -> "created"
71+
"ForkEvent" -> "forked"
72+
"PushEvent" -> "pushed"
73+
else -> receivedEventModel.type
74+
}
75+
76+
val repo = receivedEventModel.repo.name
77+
78+
//利用SpannableStringBuilder处理富文本
79+
return SpannableStringBuilder().apply {
80+
append("$actor $action $repo")
81+
82+
setSpan(StyleSpan(Typeface.BOLD), 0, actor.length, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE)
83+
setSpan(
84+
StyleSpan(Typeface.BOLD),
85+
actor.length + action.length + 2,
86+
actor.length + action.length + repo.length + 2,
87+
Spannable.SPAN_EXCLUSIVE_EXCLUSIVE
88+
)
89+
}
90+
}

app/src/main/java/com/fmt/github/home/activity/HomeActivity.kt

Lines changed: 11 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ import com.fmt.github.databinding.LayoutNavHeaderBinding
1919
import com.fmt.github.ext.showConfirmPopup
2020
import com.fmt.github.ext.yes
2121
import com.fmt.github.home.adapter.HomePageAdapter
22+
import com.fmt.github.home.fragment.HomeFragment
2223
import com.fmt.github.home.viewmodel.HomeViewModel
2324
import com.fmt.github.user.activity.AboutActivity
2425
import com.fmt.github.user.activity.LoginActivity
@@ -57,12 +58,13 @@ class HomeActivity : BaseVMActivity(), NavigationView.OnNavigationItemSelectedLi
5758
//Androidx的协程支持LifecycleScope、ViewModelScope
5859
mUser = mUserDao.getAll()[0]
5960
initHeaderLayout()
60-
initViewPager()
61+
initRecyclerView()
6162
}
6263
}
6364

6465
private fun initHeaderLayout() {
65-
val dataBind = LayoutNavHeaderBinding.inflate(LayoutInflater.from(this), mNavigationView,false)
66+
val dataBind =
67+
LayoutNavHeaderBinding.inflate(LayoutInflater.from(this), mNavigationView, false)
6668
dataBind.user = mUser
6769
mNavigationView.addHeaderView(dataBind.root)
6870
}
@@ -84,17 +86,14 @@ class HomeActivity : BaseVMActivity(), NavigationView.OnNavigationItemSelectedLi
8486
}
8587
}
8688

87-
private fun initViewPager() {
88-
val fragmentList = mutableListOf<Fragment>().apply {
89-
add(UserReposFragment.newInstance(mUser.login))
90-
add(UserReposFragment.newInstance(mUser.login, true))
91-
}
92-
val homePageAdapter = HomePageAdapter(
93-
supportFragmentManager, fragmentList,
94-
FragmentStatePagerAdapter.BEHAVIOR_RESUME_ONLY_CURRENT_FRAGMENT
89+
private fun initRecyclerView() {
90+
val beginTransaction = supportFragmentManager.beginTransaction()
91+
beginTransaction.replace(
92+
R.id.frameLayout,
93+
HomeFragment.newInstance(mUser.login),
94+
"Home_Fragment"
9595
)
96-
mViewPager.adapter = homePageAdapter
97-
mTabLayout.setupWithViewPager(mViewPager)
96+
beginTransaction.commit()
9897
}
9998

10099
override fun onNavigationItemSelected(menuItem: MenuItem): Boolean {
Lines changed: 74 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,74 @@
1+
package com.fmt.github.home.fragment
2+
3+
import android.content.Intent
4+
import android.os.Bundle
5+
import androidx.recyclerview.widget.LinearLayoutManager
6+
import com.fmt.github.BR
7+
import com.fmt.github.R
8+
import com.fmt.github.base.fragment.BaseListMVFragment
9+
import com.fmt.github.base.viewmodel.BaseViewModel
10+
import com.fmt.github.databinding.LayoutReceivedEventBinding
11+
import com.fmt.github.home.model.ReceivedEventModel
12+
import com.fmt.github.home.viewmodel.HomeViewModel
13+
import com.fmt.github.repos.activity.ReposDetailActivity
14+
import com.github.nitrico.lastadapter.LastAdapter
15+
import org.koin.androidx.viewmodel.ext.android.viewModel
16+
import com.github.nitrico.lastadapter.Type
17+
import kotlinx.android.synthetic.main.common_refresh_recyclerview.*
18+
19+
class HomeFragment : BaseListMVFragment<ReceivedEventModel>() {
20+
21+
private var mUserName = ""
22+
23+
private val mViewModel: HomeViewModel by viewModel()
24+
25+
override fun getViewModel(): BaseViewModel = mViewModel
26+
27+
companion object {
28+
29+
const val KEY = "key"
30+
const val BASE_WEB_URL = "https://github.com/"
31+
32+
fun newInstance(userName: String): HomeFragment {
33+
val reposFragment = HomeFragment()
34+
val arguments = Bundle()
35+
arguments.putString(KEY, userName)
36+
reposFragment.arguments = arguments
37+
return reposFragment
38+
}
39+
}
40+
41+
override fun initRecyclerView() {
42+
val type = Type<LayoutReceivedEventBinding>(R.layout.layout_received_event)
43+
.onClick {
44+
go2ReposDetailActivity(mListData[it.adapterPosition])
45+
}
46+
LastAdapter(mListData, BR.item)
47+
.map<ReceivedEventModel>(type)
48+
.into(mRecyclerView.apply {
49+
layoutManager = LinearLayoutManager(mActivity)
50+
})
51+
}
52+
53+
override fun initData() {
54+
arguments?.let {
55+
mUserName = it.getString(KEY)
56+
initViewModelAction()
57+
}
58+
}
59+
60+
override fun getListData() {
61+
mViewModel.queryReceivedEvents(mUserName, mPage).observe(this, mListObserver)
62+
}
63+
64+
private fun go2ReposDetailActivity(receivedEventModel: ReceivedEventModel) {
65+
val splitArr = receivedEventModel.repo.name.split("/")
66+
with(Intent(mActivity, ReposDetailActivity::class.java)) {
67+
putExtra(ReposDetailActivity.WEB_URL, "${BASE_WEB_URL}${receivedEventModel.repo.name}")
68+
putExtra(ReposDetailActivity.OWNER, splitArr[0])
69+
putExtra(ReposDetailActivity.REPO, splitArr[1])
70+
}.run {
71+
startActivity(this)
72+
}
73+
}
74+
}
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
package com.fmt.github.home.model
2+
3+
data class ReceivedEventModel(val id: String,val type:String,val actor: Actor,val repo:Repo,val created_at:String)
4+
5+
data class Actor(val login:String,val display_login : String,val avatar_url: String)
6+
7+
data class Repo(val name:String)

app/src/main/java/com/fmt/github/home/viewmodel/HomeViewModel.kt

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,10 +2,15 @@ package com.fmt.github.home.viewmodel
22

33
import androidx.lifecycle.LiveData
44
import com.fmt.github.base.viewmodel.BaseViewModel
5+
import com.fmt.github.home.model.ReceivedEventModel
56
import com.fmt.github.user.repository.UserRepository
67

78
class HomeViewModel(private val mUserRepository: UserRepository) : BaseViewModel() {
89

10+
fun queryReceivedEvents(user: String, page: Int): LiveData<List<ReceivedEventModel>> = emit {
11+
mUserRepository.queryReceivedEvents(user, page)
12+
}
13+
914
fun deleteAuthorization(id: Int): LiveData<Boolean> = emit {
1015
mUserRepository.deleteAuthorization(id).code() == 204
1116
}

0 commit comments

Comments
 (0)