<option name="testRunner" value="GRADLE" /> | <option name="testRunner" value="GRADLE" /> | ||||
<option name="distributionType" value="DEFAULT_WRAPPED" /> | <option name="distributionType" value="DEFAULT_WRAPPED" /> | ||||
<option name="externalProjectPath" value="$PROJECT_DIR$" /> | <option name="externalProjectPath" value="$PROJECT_DIR$" /> | ||||
<option name="gradleJvm" value="Embedded JDK" /> | |||||
<option name="modules"> | <option name="modules"> | ||||
<set> | <set> | ||||
<option value="$PROJECT_DIR$" /> | <option value="$PROJECT_DIR$" /> |
<component name="DesignSurface"> | <component name="DesignSurface"> | ||||
<option name="filePathToZoomLevelMap"> | <option name="filePathToZoomLevelMap"> | ||||
<map> | <map> | ||||
<entry key="..\:/Work/XKL/XklLocal/app/src/main/res/drawable/theme_splash_bg.xml" value="0.22" /> | |||||
<entry key="..\:/Work/XKL/XklLocal/app/src/main/res/layout/activity_fullscreen.xml" value="0.10144927536231885" /> | <entry key="..\:/Work/XKL/XklLocal/app/src/main/res/layout/activity_fullscreen.xml" value="0.10144927536231885" /> | ||||
<entry key="..\:/Work/XKL/XklLocal/app/src/main/res/layout/activity_main.xml" value="0.1" /> | <entry key="..\:/Work/XKL/XklLocal/app/src/main/res/layout/activity_main.xml" value="0.1" /> | ||||
<entry key="..\:/Work/XKL/XklLocal/app/src/main/res/layout/activity_splash.xml" value="0.1" /> | |||||
</map> | </map> | ||||
</option> | </option> | ||||
</component> | </component> |
项目中遇到的错误: | |||||
使用jectPack时的依赖: | |||||
· androidx.appcompat: appcompat 依赖中已经带了livedata、viewmodel等,可以不用再依赖,再依赖时出现了异常编译错误,未解决 | |||||
且 依赖版本不同,对应的livedata等版本也不同 |
ext.dependencies_androidTestImplementation : 测试依赖 | ext.dependencies_androidTestImplementation : 测试依赖 | ||||
ext.dependencies_custom : 自己添加的依赖项,按需定制 | ext.dependencies_custom : 自己添加的依赖项,按需定制 | ||||
androidx.appcompat:appcompat 自带jetpack中的lifecycle、viewmodel、livedata | |||||
app: | app: | ||||
module : 按模块进行业务划分 | module : 按模块进行业务划分 | ||||
plugins { | plugins { | ||||
id 'com.android.application' | id 'com.android.application' | ||||
id 'kotlin-android' | id 'kotlin-android' | ||||
id 'kotlin-kapt' | |||||
} | } | ||||
def androidConfig = rootProject.ext.android | def androidConfig = rootProject.ext.android | ||||
android { | android { | ||||
//配置产品变种 与 构建变体 | //配置产品变种 与 构建变体 | ||||
//flavorDimensions :变种维度 | //flavorDimensions :变种维度 | ||||
flavorDimensions "version" | |||||
productFlavors{ //产品变种 | |||||
demo{ | |||||
dimension "version" | |||||
//applicationId后追加 .demo 也可以重新定义applicationId 属性 | |||||
applicationIdSuffix ".demo" | |||||
versionNameSuffix "-demo" | |||||
} | |||||
full { | |||||
dimension "version" | |||||
applicationIdSuffix ".full" | |||||
versionNameSuffix '-full' | |||||
} | |||||
} | |||||
// flavorDimensions "version" | |||||
// productFlavors{ //产品变种 | |||||
// demo{ | |||||
// dimension "version" | |||||
// //applicationId后追加 .demo 也可以重新定义applicationId 属性 | |||||
// applicationIdSuffix ".demo" | |||||
// versionNameSuffix "-demo" | |||||
// } | |||||
// full { | |||||
// dimension "version" | |||||
// applicationIdSuffix ".full" | |||||
// versionNameSuffix '-full' | |||||
// } | |||||
// } | |||||
//变体过滤器 | //变体过滤器 | ||||
variantFilter { variant -> | |||||
def names = variant.flavors*.name | |||||
if (name.contains("demo")){ | |||||
setIgnore(true) | |||||
} | |||||
} | |||||
// variantFilter { variant -> | |||||
// def names = variant.flavors*.name | |||||
// if (name.contains("demo")){ | |||||
// setIgnore(true) | |||||
// } | |||||
// } | |||||
compileOptions { | compileOptions { | ||||
sourceCompatibility JavaVersion.VERSION_1_8 | sourceCompatibility JavaVersion.VERSION_1_8 | ||||
} | } | ||||
buildFeatures { | buildFeatures { | ||||
viewBinding true | viewBinding true | ||||
dataBinding true | |||||
} | } | ||||
} | } | ||||
dependencies { | dependencies { | ||||
implementation 'androidx.appcompat:appcompat:1.2.0' | |||||
implementation 'com.google.android.material:material:1.3.0' | |||||
implementation 'androidx.constraintlayout:constraintlayout:2.0.4' | |||||
implementation 'androidx.legacy:legacy-support-v4:1.0.0' | implementation 'androidx.legacy:legacy-support-v4:1.0.0' | ||||
implementation project(path: ':lib:common') | |||||
rootProject.ext.dependencies_required.each{ k, v -> implementation v} | rootProject.ext.dependencies_required.each{ k, v -> implementation v} | ||||
testImplementation rootProject.ext.dependencies_testImplementation.junit | testImplementation rootProject.ext.dependencies_testImplementation.junit | ||||
rootProject.ext.dependencies_androidTestImplementation.each{ k,v -> androidTestImplementation v} | rootProject.ext.dependencies_androidTestImplementation.each{ k,v -> androidTestImplementation v} | ||||
// kapt rootProject.ext.dependencies_kapt.lifecycle_compiler | |||||
def lifecycle_version = "2.5.0-alpha02" | |||||
def arch_version = "2.1.0" | |||||
// | |||||
// // ViewModel | |||||
// implementation "androidx.lifecycle:lifecycle-viewmodel-ktx:$lifecycle_version" | |||||
// // ViewModel utilities for Compose | |||||
// implementation "androidx.lifecycle:lifecycle-viewmodel-compose:$lifecycle_version" | |||||
// // LiveData | |||||
// implementation "androidx.lifecycle:lifecycle-livedata-ktx:$lifecycle_version" | |||||
// // Lifecycles only (without ViewModel or LiveData) | |||||
// implementation "androidx.lifecycle:lifecycle-runtime-ktx:$lifecycle_version" | |||||
// | |||||
// // Saved state module for ViewModel | |||||
// implementation "androidx.lifecycle:lifecycle-viewmodel-savedstate:$lifecycle_version" | |||||
// | |||||
// // Annotation processor | |||||
//// kapt "androidx.lifecycle:lifecycle-compiler:$lifecycle_version" | |||||
// // alternately - if using Java8, use the following instead of lifecycle-compiler | |||||
// implementation "androidx.lifecycle:lifecycle-common-java8:$lifecycle_version" | |||||
// // optional - helpers for implementing LifecycleOwner in a Service | |||||
// implementation "androidx.lifecycle:lifecycle-service:$lifecycle_version" | |||||
// | |||||
// // optional - ProcessLifecycleOwner provides a lifecycle for the whole application process | |||||
// implementation "androidx.lifecycle:lifecycle-process:$lifecycle_version" | |||||
// | |||||
// // optional - ReactiveStreams support for LiveData | |||||
// implementation "androidx.lifecycle:lifecycle-reactivestreams-ktx:$lifecycle_version" | |||||
// | |||||
// // optional - Test helpers for LiveData | |||||
// testImplementation "androidx.arch.core:core-testing:$arch_version" | |||||
} | } |
android:supportsRtl="true" | android:supportsRtl="true" | ||||
android:theme="@style/Theme.XklLocal"> | android:theme="@style/Theme.XklLocal"> | ||||
<activity | <activity | ||||
android:name=".module.main.MainActivity" | |||||
android:name=".module.splash.SplashActivity" | |||||
android:configChanges="orientation|keyboardHidden|screenSize" | android:configChanges="orientation|keyboardHidden|screenSize" | ||||
android:exported="true" > | |||||
android:exported="true" | |||||
android:theme="@style/Theme.Splash"> | |||||
<intent-filter> | <intent-filter> | ||||
<action android:name="android.intent.action.MAIN" /> | <action android:name="android.intent.action.MAIN" /> | ||||
<category android:name="android.intent.category.LAUNCHER" /> | <category android:name="android.intent.category.LAUNCHER" /> | ||||
</intent-filter> | </intent-filter> | ||||
</activity> | </activity> | ||||
<activity | |||||
android:name=".module.main.MainActivity" | |||||
android:configChanges="orientation|keyboardHidden|screenSize"/> | |||||
</application> | </application> | ||||
</manifest> | </manifest> |
package com.xkl.cdl.module.center_learn | |||||
package com.xkl.cdl.module.m_center_learn | |||||
import android.os.Bundle | import android.os.Bundle | ||||
import androidx.fragment.app.Fragment | import androidx.fragment.app.Fragment |
package com.xkl.cdl.module.memo | |||||
package com.xkl.cdl.module.m_memo | |||||
import android.os.Bundle | import android.os.Bundle | ||||
import androidx.fragment.app.Fragment | import androidx.fragment.app.Fragment |
package com.xkl.cdl.module.my | |||||
package com.xkl.cdl.module.m_my | |||||
import android.os.Bundle | import android.os.Bundle | ||||
import androidx.fragment.app.Fragment | import androidx.fragment.app.Fragment |
package com.xkl.cdl.module.statics | |||||
package com.xkl.cdl.module.m_statics | |||||
import android.os.Bundle | import android.os.Bundle | ||||
import androidx.fragment.app.Fragment | import androidx.fragment.app.Fragment |
package com.xkl.cdl.module.splash | |||||
import android.os.Bundle | |||||
import android.os.Handler | |||||
import android.os.Looper | |||||
import android.os.Message | |||||
import androidx.databinding.ObservableField | |||||
import com.suliang.common.base.activity.BaseActivity | |||||
import com.xkl.cdl.databinding.ActivitySplashBinding | |||||
class SplashActivity : BaseActivity<ActivitySplashBinding>() { | |||||
val textvalue = ObservableField<String>() | |||||
private val handler = object : Handler(Looper.getMainLooper()){ | |||||
override fun handleMessage(msg: Message) { | |||||
super.handleMessage(msg) | |||||
binding.text.text = textvalue.get() | |||||
} | |||||
} | |||||
override fun onCreate(savedInstanceState: Bundle?) { | |||||
if(!isTaskRoot){ | |||||
finish() | |||||
return | |||||
} | |||||
super.onCreate(savedInstanceState) | |||||
} | |||||
var count = 1 | |||||
override fun initActivity(savedInstanceState: Bundle?) { | |||||
val x = Tvalue(textvalue) | |||||
binding.name = x | |||||
handler.postDelayed(object : Runnable{ | |||||
override fun run() { | |||||
count ++ | |||||
textvalue.set("$count") | |||||
handler.postDelayed(this,1000) | |||||
} | |||||
},1000) | |||||
} | |||||
} | |||||
data class Tvalue(val value : ObservableField<String>) |
<?xml version="1.0" encoding="utf-8"?> | |||||
<layer-list xmlns:android="http://schemas.android.com/apk/res/android"> | |||||
<item android:drawable="@color/white"/> | |||||
<item android:gravity="center" android:bottom="100dp"> | |||||
<bitmap | |||||
android:src="@mipmap/splash_logo" | |||||
android:scaleType="centerInside"/> | |||||
</item> | |||||
</layer-list> |
<?xml version="1.0" encoding="utf-8"?> | |||||
<layout xmlns:android="http://schemas.android.com/apk/res/android" | |||||
xmlns:app="http://schemas.android.com/apk/res-auto" | |||||
xmlns:tools="http://schemas.android.com/tools"> | |||||
<data> | |||||
<variable | |||||
name="name" | |||||
type="com.xkl.cdl.module.splash.Tvalue" /> | |||||
</data> | |||||
<androidx.constraintlayout.widget.ConstraintLayout | |||||
android:layout_width="match_parent" | |||||
android:layout_height="match_parent" | |||||
tools:context=".module.splash.SplashActivity"> | |||||
<ImageView | |||||
android:id="@+id/img" | |||||
android:layout_width="match_parent" | |||||
android:layout_height="0dp" | |||||
app:layout_constraintLeft_toLeftOf="parent" | |||||
app:layout_constraintRight_toRightOf="parent" | |||||
app:layout_constraintTop_toTopOf="parent" | |||||
app:layout_constraintBottom_toBottomOf="parent" | |||||
app:layout_constraintVertical_bias="0.6" | |||||
app:layout_constraintDimensionRatio="1125:813" | |||||
android:src="@drawable/illustration_splash" | |||||
/> | |||||
<TextView | |||||
android:id="@+id/text" | |||||
android:layout_width="wrap_content" | |||||
android:layout_height="wrap_content" | |||||
android:text="@={name.value}" | |||||
android:textSize="18dp" | |||||
app:layout_constraintBottom_toBottomOf="parent" | |||||
app:layout_constraintStart_toStartOf="parent" | |||||
app:layout_constraintEnd_toEndOf="parent"/> | |||||
</androidx.constraintlayout.widget.ConstraintLayout> | |||||
</layout> |
xmlns:tools="http://schemas.android.com/tools" | xmlns:tools="http://schemas.android.com/tools" | ||||
android:layout_width="match_parent" | android:layout_width="match_parent" | ||||
android:layout_height="match_parent" | android:layout_height="match_parent" | ||||
tools:context=".module.center_learn.LearnCenterFragment"> | |||||
tools:context=".module.m_center_learn.LearnCenterFragment"> | |||||
<!-- TODO: Update blank fragment layout --> | <!-- TODO: Update blank fragment layout --> | ||||
<TextView | <TextView |
xmlns:tools="http://schemas.android.com/tools" | xmlns:tools="http://schemas.android.com/tools" | ||||
android:layout_width="match_parent" | android:layout_width="match_parent" | ||||
android:layout_height="match_parent" | android:layout_height="match_parent" | ||||
tools:context=".module.memo.MemoFragment"> | |||||
tools:context=".module.m_memo.MemoFragment"> | |||||
<!-- TODO: Update blank fragment layout --> | <!-- TODO: Update blank fragment layout --> | ||||
<TextView | <TextView |
xmlns:tools="http://schemas.android.com/tools" | xmlns:tools="http://schemas.android.com/tools" | ||||
android:layout_width="match_parent" | android:layout_width="match_parent" | ||||
android:layout_height="match_parent" | android:layout_height="match_parent" | ||||
tools:context=".module.my.MyFragment"> | |||||
tools:context=".module.m_my.MyFragment"> | |||||
<!-- TODO: Update blank fragment layout --> | <!-- TODO: Update blank fragment layout --> | ||||
<TextView | <TextView |
xmlns:tools="http://schemas.android.com/tools" | xmlns:tools="http://schemas.android.com/tools" | ||||
android:layout_width="match_parent" | android:layout_width="match_parent" | ||||
android:layout_height="match_parent" | android:layout_height="match_parent" | ||||
tools:context=".module.statics.StaticsFragment"> | |||||
tools:context=".module.m_statics.StaticsFragment"> | |||||
<!-- TODO: Update blank fragment layout --> | <!-- TODO: Update blank fragment layout --> | ||||
<TextView | <TextView |
<resources xmlns:tools="http://schemas.android.com/tools"> | <resources xmlns:tools="http://schemas.android.com/tools"> | ||||
<!-- Base application theme. --> | <!-- Base application theme. --> | ||||
<style name="Theme.XklLocal" parent="Theme.MaterialComponents.DayNight.DarkActionBar"> | |||||
<style name="Theme.XklLocal" parent="Theme.MaterialComponents.Light.DarkActionBar"> | |||||
<!-- Primary brand color. --> | <!-- Primary brand color. --> | ||||
<item name="colorPrimary">@color/purple_500</item> | |||||
<item name="colorPrimaryVariant">@color/purple_700</item> | |||||
<item name="colorOnPrimary">@color/white</item> | |||||
<!-- Secondary brand color. --> | |||||
<item name="colorSecondary">@color/teal_200</item> | |||||
<item name="colorSecondaryVariant">@color/teal_700</item> | |||||
<item name="colorOnSecondary">@color/black</item> | |||||
<!-- Status bar color. --> | |||||
<item name="android:statusBarColor" tools:targetApi="l">?attr/colorPrimaryVariant</item> | |||||
<item name="colorPrimary">@color/white</item> <!--AppBar背景色--> | |||||
<!-- <item name="colorPrimaryVariant">@color/white</item>--> | |||||
<item name="colorOnPrimary">@color/black</item> | |||||
<!-- <!– Secondary brand color. –>--> | |||||
<!-- <item name="colorSecondary">@color/white</item>--> | |||||
<!-- <item name="colorSecondaryVariant">@color/white</item>--> | |||||
<!-- <item name="colorOnSecondary">@color/white</item>--> | |||||
<!-- <!– Status bar color. –>--> | |||||
<item name="android:statusBarColor" tools:targetApi="l">@color/white</item> | |||||
<!-- Customize your theme here. --> | <!-- Customize your theme here. --> | ||||
<item name="android:textAllCaps">false</item> | |||||
<item name="android:windowActionBar">false</item> | |||||
<item name="windowActionBar">false</item> | |||||
<item name="windowNoTitle">true</item> | |||||
<item name="android:windowNoTitle">true</item> | |||||
<item name="android:windowIsTranslucent">true</item> | |||||
<item name="android:windowDrawsSystemBarBackgrounds">true</item> | |||||
<item name="android:windowEnableSplitTouch">false</item> | |||||
<item name="android:splitMotionEvents">false</item> | |||||
<item name="android:windowBackground">@android:color/transparent</item> | |||||
</style> | |||||
<!--启动页背景图层--> | |||||
<style name="Theme.Splash" parent="Theme.XklLocal"> | |||||
<item name="android:windowBackground">@drawable/theme_splash_bg</item> | |||||
</style> | </style> | ||||
</resources> | </resources> |
repositories { | repositories { | ||||
google() | google() | ||||
mavenCentral() | mavenCentral() | ||||
maven { url 'https://jitpack.io' } | |||||
} | } | ||||
dependencies { | dependencies { | ||||
classpath "com.android.tools.build:gradle:7.0.1" | classpath "com.android.tools.build:gradle:7.0.1" | ||||
//在项目级别定义某些属性并在所有模块之间共享这些属性 | //在项目级别定义某些属性并在所有模块之间共享这些属性 | ||||
ext { | ext { | ||||
android = [ | android = [ | ||||
compile_sdk_version: 30, //使用rootProject.ext.android.compile_sdk_version | |||||
compile_sdk_version: 31, //使用rootProject.ext.android.compile_sdk_version | |||||
build_tools_version: "30.0.2", | build_tools_version: "30.0.2", | ||||
min_sdk_version : 21, | min_sdk_version : 21, | ||||
target_sdk_version : 30, | |||||
target_sdk_version : 31, | |||||
version_code : 100, | version_code : 100, | ||||
version_name : "100", | version_name : "100", | ||||
applicationId : "com.xkl.cdl" | applicationId : "com.xkl.cdl" | ||||
] | ] | ||||
versions = [ | versions = [ | ||||
core_ktx_version : "1.3.2", | core_ktx_version : "1.3.2", | ||||
appcompat_version: "1.2.0", | |||||
appcompat_version: "1.4.1", | |||||
material_version : "1.3.0", | material_version : "1.3.0", | ||||
lifecycle_version: "2.5.0-alpha02" | |||||
] | ] | ||||
//必须依赖 | //必须依赖 | ||||
dependencies_required = [ | dependencies_required = [ | ||||
//为属于Android框架的通用库提供扩展程序 | //为属于Android框架的通用库提供扩展程序 | ||||
core_ktx : "androidx.core:core-ktx:${versions.core_ktx_version}", | |||||
core_ktx : "androidx.core:core-ktx:${versions.core_ktx_version}", | |||||
//Androidx 依赖 | //Androidx 依赖 | ||||
appcompat: "androidx.appcompat:appcompat:${versions.appcompat_version}", | |||||
appcompat : "androidx.appcompat:appcompat:${versions.appcompat_version}", | |||||
//material_design | //material_design | ||||
material : "com.google.android.material:material:${versions.material_version}", | |||||
material : "com.google.android.material:material:${versions.material_version}", | |||||
//constraintlayout | |||||
constraintlayout : "androidx.constraintlayout:constraintlayout:2.0.4", | |||||
//lifecycle | |||||
// lifecycle : "androidx.lifecycle:lifecycle-runtime-ktx:${versions.lifecycle_version}", | |||||
// //lifecycle saved state module for viewmodel | |||||
//// lifecycle_viewmodel_savestate: "androidx.lifecycle:lifecycle-viewmodel-savedstate:${versions.lifecycle_version}", | |||||
// //ViewModel | |||||
// viewmodel : "androidx.lifecycle:lifecycle-viewmodel-ktx:${versions.lifecycle_version}", | |||||
// //livedata | |||||
// livedata : "androidx.lifecycle:lifecycle-livedata-ktx:${versions.lifecycle_version}", | |||||
//java8 lifecycle_compiler | |||||
// lifecycle_compiler : "androidx.lifecycle:lifecycle-common-java8:${versions.lifecycle_version}" | |||||
] | ] | ||||
dependencies_testImplementation = [ | dependencies_testImplementation = [ | ||||
junit: "junit:junit:4.+" | junit: "junit:junit:4.+" | ||||
test_ext_junit : "androidx.test.ext:junit:1.1.2", | test_ext_junit : "androidx.test.ext:junit:1.1.2", | ||||
test_espresson_core: "androidx.test.espresso:espresso-core:3.3.0" | test_espresson_core: "androidx.test.espresso:espresso-core:3.3.0" | ||||
] | ] | ||||
//按需依赖项 | |||||
dependencies_custom = [] | |||||
//依赖项 | |||||
dependencies_custom = [ | |||||
//设置状态栏和导航栏的框架 https://github.com/Zackratos/UltimateBarX | |||||
UltimateBarX: "com.gitee.zackratos:UltimateBarX:0.8.0", | |||||
] | |||||
//注解 | |||||
// dependencies_kapt = [ | |||||
// lifecycle_compiler: "androidx.lifecycle:lifecycle-compiler:${versions.lifecycle_version}", | |||||
// | |||||
// ] | |||||
} | } |
kotlinOptions { | kotlinOptions { | ||||
jvmTarget = '1.8' | jvmTarget = '1.8' | ||||
} | } | ||||
viewBinding{ | |||||
enabled true | |||||
} | |||||
dataBinding{ | |||||
enabled true | |||||
buildFeatures { | |||||
viewBinding true | |||||
dataBinding true | |||||
} | } | ||||
} | } | ||||
rootProject.ext.dependencies_required.each{ k,v -> implementation v} | rootProject.ext.dependencies_required.each{ k,v -> implementation v} | ||||
testImplementation rootProject.ext.dependencies_testImplementation.junit | testImplementation rootProject.ext.dependencies_testImplementation.junit | ||||
rootProject.ext.dependencies_androidTestImplementation.each{ k,v -> androidTestImplementation v} | rootProject.ext.dependencies_androidTestImplementation.each{ k,v -> androidTestImplementation v} | ||||
// api rootProject.ext.dependencies_custom.UltimateBarX | |||||
// kapt rootProject.ext.dependencies_kapt.lifecycle_compiler | |||||
def lifecycle_version = "2.5.0-alpha02" | |||||
def arch_version = "2.1.0" | |||||
// // ViewModel | |||||
// implementation "androidx.lifecycle:lifecycle-viewmodel-ktx:$lifecycle_version" | |||||
// // ViewModel utilities for Compose | |||||
// implementation "androidx.lifecycle:lifecycle-viewmodel-compose:$lifecycle_version" | |||||
// // LiveData | |||||
// implementation "androidx.lifecycle:lifecycle-livedata-ktx:$lifecycle_version" | |||||
// // Lifecycles only (without ViewModel or LiveData) | |||||
// implementation "androidx.lifecycle:lifecycle-runtime-ktx:$lifecycle_version" | |||||
// | |||||
// // Saved state module for ViewModel | |||||
// implementation "androidx.lifecycle:lifecycle-viewmodel-savedstate:$lifecycle_version" | |||||
// | |||||
// // Annotation processor | |||||
//// kapt "androidx.lifecycle:lifecycle-compiler:$lifecycle_version" | |||||
// // alternately - if using Java8, use the following instead of lifecycle-compiler | |||||
// implementation "androidx.lifecycle:lifecycle-common-java8:$lifecycle_version" | |||||
// // optional - helpers for implementing LifecycleOwner in a Service | |||||
// implementation "androidx.lifecycle:lifecycle-service:$lifecycle_version" | |||||
// | |||||
// // optional - ProcessLifecycleOwner provides a lifecycle for the whole application process | |||||
// implementation "androidx.lifecycle:lifecycle-process:$lifecycle_version" | |||||
// | |||||
// // optional - ReactiveStreams support for LiveData | |||||
// implementation "androidx.lifecycle:lifecycle-reactivestreams-ktx:$lifecycle_version" | |||||
// | |||||
// // optional - Test helpers for LiveData | |||||
// testImplementation "androidx.arch.core:core-testing:$arch_version" | |||||
} | } |
package com.suliang.common.base.activity | package com.suliang.common.base.activity | ||||
import android.os.Bundle | import android.os.Bundle | ||||
import android.view.LayoutInflater | |||||
import androidx.appcompat.app.AppCompatActivity | import androidx.appcompat.app.AppCompatActivity | ||||
import androidx.databinding.DataBindingUtil | |||||
import androidx.databinding.ViewDataBinding | |||||
import androidx.databinding.ViewDataBindingKtx | |||||
import java.lang.reflect.Method | |||||
import androidx.lifecycle.ViewModelProvider | |||||
import androidx.lifecycle.ViewModelProviders | |||||
import androidx.viewbinding.ViewBinding | |||||
import com.suliang.common.extension.initBinding | |||||
import com.suliang.common.util.ActivityStackManager | |||||
import java.lang.reflect.ParameterizedType | import java.lang.reflect.ParameterizedType | ||||
/** | /** | ||||
* 基类Activity | * 基类Activity | ||||
*/ | */ | ||||
abstract class BaseActivity<VB : ViewDataBinding> : AppCompatActivity() { | |||||
lateinit var databinding: VB | |||||
abstract class BaseActivity<VB : ViewBinding> : AppCompatActivity() { | |||||
lateinit var binding: VB | |||||
override fun onCreate(savedInstanceState: Bundle?) { | override fun onCreate(savedInstanceState: Bundle?) { | ||||
super.onCreate(savedInstanceState) | super.onCreate(savedInstanceState) | ||||
addStackManager() | |||||
initFirst() | |||||
initActivity(savedInstanceState) } | |||||
protected open fun initFirst() { | |||||
setLayoutBefore() | setLayoutBefore() | ||||
initBinding() | |||||
binding = initBinding(layoutInflater) | |||||
setContentView(binding.root) | |||||
initStatusBar() | |||||
setLayoutAfter() | setLayoutAfter() | ||||
} | |||||
/** | |||||
* 状态栏初始化方法 | |||||
*/ | |||||
open fun initStatusBar() { | |||||
// statusBarOnly { | |||||
// fitWindow = true | |||||
// color = Color.WHITE | |||||
// light = true | |||||
// } | |||||
} | |||||
override fun onDestroy() { | |||||
super.onDestroy() | |||||
ActivityStackManager.removeActivity(this) | |||||
} | } | ||||
private fun addStackManager() { | |||||
ActivityStackManager.addActivity(this) | |||||
} | |||||
/** 布局前操作 : 空实现 */ | /** 布局前操作 : 空实现 */ | ||||
public fun setLayoutBefore() { | |||||
public open fun setLayoutBefore() { | |||||
} | } | ||||
/** | /** | ||||
* 实例化 binding和 设置布局 | |||||
* 布局后操作:空实现 | |||||
*/ | */ | ||||
private fun initBinding() { | |||||
// https://www.jianshu.com/p/e3d2421a0277 | |||||
// val genericSuperClass = this::class.java.genericSuperclass as ParameterizedType //超类 | |||||
// val type = genericSuperClass.actualTypeArguments[0].javaClass | |||||
// val infate: Method = type.getDeclaredMethod("inflate") | |||||
public open fun setLayoutAfter() { | |||||
} | } | ||||
/** | /** | ||||
* 布局后操作:空实现 | |||||
* onCreate中给与app中用户的具体实现 | |||||
* @param savedInstanceState Bundle? | |||||
*/ | */ | ||||
public fun setLayoutAfter() { | |||||
abstract fun initActivity(savedInstanceState: Bundle?) | |||||
} | |||||
// @SuppressWarnings("unchecked") | |||||
// fun initBinding(inflater: LayoutInflater): VB { | |||||
// val vbClass = | |||||
// (javaClass.genericSuperclass as ParameterizedType).actualTypeArguments.filterIsInstance<Class<VB>>() | |||||
// val inflate = vbClass[0].getDeclaredMethod("inflate", LayoutInflater::class.java) | |||||
// return inflate.invoke(null, inflater) as VB | |||||
// } | |||||
public abstract fun layoutRes(): Int | |||||
} | } |
package com.suliang.common.base.activity | |||||
import android.os.Bundle | |||||
import androidx.databinding.ViewDataBinding | |||||
import androidx.lifecycle.ViewModel | |||||
import androidx.viewbinding.ViewBinding | |||||
/** | |||||
* Activity DataBinding 与 ViewModel基类,封装DataBinding和ViewModel | |||||
* @property VB : ViewDataBinding | |||||
* @property VM: ViewModel | |||||
*/ | |||||
abstract class BaseActivityVM<VB : ViewDataBinding, VM:ViewModel> : BaseActivity<VB>() { | |||||
private lateinit var vm : VM | |||||
override fun initFirst() { | |||||
vm = initViewModel() | |||||
super.initFirst() | |||||
binding.lifecycleOwner = this | |||||
} | |||||
abstract fun initViewModel() : VM | |||||
} |
package com.suliang.common.base.adapter | |||||
import android.view.ViewGroup | |||||
import androidx.recyclerview.widget.RecyclerView | |||||
abstract class BaseAdapter<T> : | |||||
RecyclerView.Adapter<BaseAdapterViewHolder>() { | |||||
companion object{ | |||||
val TYPE_EMPTY = -1 | |||||
} | |||||
//数据源 | |||||
private var mData: MutableList<T> = mutableListOf<T>() | |||||
/** 是否需要显示空布局 */ | |||||
var needShowEmptyView = false | |||||
/** | |||||
* 当前位置是否需要显示空布局,主要是为0的时候,这个判断才会有效 | |||||
* @param position Int | |||||
*/ | |||||
private fun enableEmptyPosition(position:Int): Boolean{ | |||||
return position == 0 && mData.isEmpty() && needShowEmptyView | |||||
} | |||||
override fun getItemCount(): Int { | |||||
return if (needShowEmptyView && mData.isEmpty()) 1 else mData.size | |||||
} | |||||
override fun getItemViewType(position: Int): Int { | |||||
if (enableEmptyPosition(position)){ | |||||
return TYPE_EMPTY | |||||
} | |||||
return super.getItemViewType(position) | |||||
} | |||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): BaseAdapterViewHolder { | |||||
return when(viewType){ | |||||
TYPE_EMPTY -> coverEmptyViewHolder(parent) | |||||
else -> coverViewHolder(parent,viewType) | |||||
} | |||||
} | |||||
override fun onBindViewHolder(holder: BaseAdapterViewHolder, position: Int) { | |||||
if (enableEmptyPosition(position)){ | |||||
onBindEmptyViewHolder(holder) | |||||
}else{ | |||||
onBindVH(holder,position) | |||||
} | |||||
} | |||||
/** 创建空布局的ViewHolder 如果needShowEmpty = false 则可以不创建 */ | |||||
abstract fun coverEmptyViewHolder(parent: ViewGroup): BaseAdapterViewHolder | |||||
/** 空布局的数据绑定 */ | |||||
abstract fun onBindEmptyViewHolder(holder: BaseAdapterViewHolder) | |||||
/** 创建 正常item的 ViewHolder */ | |||||
abstract fun coverViewHolder(parent: ViewGroup,viewType: Int): BaseAdapterViewHolder | |||||
/** 绑定 正常item 的数据 */ | |||||
abstract fun onBindVH(holder: BaseAdapterViewHolder,position: Int) | |||||
/** | |||||
* 设置数据,并更新列表 | |||||
* @param data List<T>? | |||||
*/ | |||||
fun setData(data: MutableList<T>?) { | |||||
data?.let { it -> //不为空 | |||||
mData = it | |||||
} ?: let { //为空 | |||||
mData = mutableListOf() | |||||
} | |||||
notifyItemRangeChanged(0, mData.size) | |||||
} | |||||
/** | |||||
* 添加单条数据 | |||||
* @param data T? | |||||
* @param position Int? | |||||
*/ | |||||
fun addData(data: T?, position: Int?) { | |||||
data?.let { | |||||
val size = mData.size | |||||
val startPosition = position?.let { it -> | |||||
when { | |||||
it < 0 -> 0 | |||||
it >= size -> size | |||||
else -> it | |||||
} | |||||
} ?: size | |||||
mData.add(startPosition,data) | |||||
notifyItemInserted(startPosition) | |||||
notifyItemRangeChanged(startPosition,mData.size + 1) | |||||
} | |||||
} | |||||
/** | |||||
* 添加数据集 | |||||
* @param data List<T>? 数据集 | |||||
* @param position Int? 添加到指定位置,可空 | |||||
*/ | |||||
fun addData(data: List<T>?, position: Int? = null) { | |||||
if (!data.isNullOrEmpty()) { | |||||
val size = mData.size | |||||
val startPosition = position?.let { it -> | |||||
when { | |||||
it < 0 -> 0 | |||||
it >= size -> size | |||||
else -> it | |||||
} | |||||
} ?: size | |||||
mData.addAll(startPosition, data) | |||||
//通知有新的item插入进来了 | |||||
notifyItemInserted(startPosition) | |||||
//范围性更新,直接调用onBindViewHolder | |||||
notifyItemRangeChanged(startPosition, mData.size + 1 ) | |||||
} | |||||
} | |||||
} |
package com.suliang.common.base.adapter | |||||
import androidx.databinding.ViewDataBinding | |||||
import androidx.recyclerview.widget.RecyclerView | |||||
class BaseAdapterViewHolder(binding: ViewDataBinding) : RecyclerView.ViewHolder(binding.root) |
package com.suliang.common.base.fragment | package com.suliang.common.base.fragment | ||||
class BaseFragment { | |||||
import android.os.Bundle | |||||
import android.view.LayoutInflater | |||||
import android.view.View | |||||
import android.view.ViewGroup | |||||
import androidx.databinding.ViewDataBinding | |||||
import androidx.fragment.app.Fragment | |||||
import com.suliang.common.extension.initBinding | |||||
/** | |||||
* Fragment ViewBinding基类,封装ViewDataBinding | |||||
* @property VB : ViewDataBinding | |||||
* @property VM: ViewModel | |||||
*/ | |||||
abstract class BaseFragment<VB: ViewDataBinding>: Fragment(){ | |||||
lateinit var binding: VB | |||||
override fun onCreateView( | |||||
inflater: LayoutInflater, | |||||
container: ViewGroup?, | |||||
savedInstanceState: Bundle? | |||||
): View? { | |||||
binding = initBinding(inflater,container) | |||||
return super.onCreateView(inflater, container, savedInstanceState) | |||||
} | |||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) { | |||||
super.onViewCreated(view, savedInstanceState) | |||||
initFirst() | |||||
initFragment() | |||||
} | |||||
abstract fun initFirst() | |||||
abstract fun initFragment() | |||||
} | } |
package com.suliang.common.base.fragment | |||||
import androidx.databinding.ViewDataBinding | |||||
import androidx.lifecycle.ViewModel | |||||
/** | |||||
* Fragment DataBinding 与 ViewModel基类,封装DataBinding和ViewModel | |||||
* @property VB : ViewDataBinding | |||||
* @property VM: ViewModel | |||||
*/ | |||||
abstract class BaseFragmentVM<VB:ViewDataBinding,VM:ViewModel>:BaseFragment<VB>() { | |||||
lateinit var viewModel: VM | |||||
override fun initFirst() { | |||||
viewModel = initViewModel() | |||||
} | |||||
abstract fun initViewModel():VM | |||||
} |
package com.suliang.common.extension | |||||
import android.view.LayoutInflater | |||||
import android.view.ViewGroup | |||||
import androidx.viewbinding.ViewBinding | |||||
import java.lang.reflect.ParameterizedType | |||||
/** | |||||
* 扩展方法,获取到ViewBinding的子类VB实例,主要用于Activity | |||||
* @receiver VB | |||||
* @param inflater LayoutInflater | |||||
* @param vbPosition Int 在超类泛型中的vb位置 | |||||
* @return VB | |||||
*/ | |||||
@SuppressWarnings("unchecked") | |||||
inline fun <VB : ViewBinding> Any.initBinding(inflater: LayoutInflater,vbPosition:Int = 0): VB { | |||||
val vbClass = | |||||
(javaClass.genericSuperclass as ParameterizedType).actualTypeArguments.filterIsInstance<Class<VB>>() | |||||
val inflate = vbClass[vbPosition].getDeclaredMethod("inflate", LayoutInflater::class.java) | |||||
return inflate.invoke(null, inflater) as VB | |||||
} | |||||
/** | |||||
* 扩展方法,获取ViewBinding的实例 主要用于Fragment、ListItem等 | |||||
* @receiver Any | |||||
* @param inflater LayoutInflater | |||||
* @param container ViewGroup? | |||||
* @param vbPosition Int | |||||
* @return VB | |||||
*/ | |||||
@SuppressWarnings("unchecked") | |||||
inline fun <VB: ViewBinding> Any.initBinding(inflater: LayoutInflater, container:ViewGroup?,vbPosition:Int = 0):VB{ | |||||
val vbClass = (javaClass.genericSuperclass as ParameterizedType).actualTypeArguments.filterIsInstance<Class<VB>>() | |||||
val inflater = vbClass[vbPosition].getDeclaredMethod("inflate",LayoutInflater::class.java,ViewGroup::class.java,Boolean::class.java) | |||||
return inflater.invoke(null,inflater,container,false) as VB | |||||
} |
package com.suliang.common.util | |||||
import android.app.Activity | |||||
import java.util.* | |||||
/** | |||||
* Activity 栈管理 | |||||
*/ | |||||
object ActivityStackManager { | |||||
@Volatile | |||||
private var activityStack: Stack<Activity> = Stack() | |||||
/** | |||||
* 入栈 | |||||
* @param activity Activity | |||||
*/ | |||||
fun addActivity(activity: Activity) { | |||||
activityStack.add(activity) | |||||
} | |||||
/** | |||||
* 出栈 | |||||
* @param activity Activity | |||||
*/ | |||||
fun removeActivity(activity: Activity) { | |||||
activityStack.remove(activity) | |||||
} | |||||
/** | |||||
* 结束指定类名的Activity | |||||
* @param cls Class<*> | |||||
*/ | |||||
fun finishActivity(cls: Class<*>) { | |||||
run { | |||||
activityStack.forEach { activity -> | |||||
if (activity.javaClass == cls) { | |||||
activity.finish() | |||||
return@run | |||||
} | |||||
} | |||||
} | |||||
} | |||||
} |
package com.suliang.common.util | |||||
import java.io.File | |||||
/** | |||||
* author suliang | |||||
* create 2020/12/11 9:43 | |||||
* Describe: 常量类 | |||||
*/ | |||||
object Constants { | |||||
const val PLATFORM = "android" //平台 | |||||
const val YOUTH_VERSION = 1 //青少版 | |||||
const val CHILDREN_VERSION = 2 //幼儿版 | |||||
// public static final String ENVIRONMENT_PRODUCTION = "production" ; //正式环境 | |||||
// public static final String ENVIRONMENT_DEVELOPMENT = "development"; //开发环境 | |||||
// public static final String ENVIRONMENT_TEST = "test"; //测试环境 | |||||
const val ACCOUNT = "account" | |||||
const val USER_INFO = "userinfo" | |||||
const val TOKEN = "token" | |||||
/** 默认发音 */ | |||||
const val DEFAULT_SOUND = "default_sound" | |||||
/** 更换fragment中的颜色 */ | |||||
const val ACTION_NOTIFY_FRAGMENT_SKIN = "notify_skin" | |||||
//项目subjectId | |||||
const val SUBJECT_ENGLISH: Long = 3 //英语 | |||||
const val SUBJECT_CHINESE: Long = 1 //语文 | |||||
//课程类型的coursepack --> categoryId | |||||
const val CATEGORY_ENGLISH_WORD: Long = 1 //英语: 单词速记 | |||||
const val CATEGORY_ENGLISH_SOUNDMARK: Long = 4 //英语: 音标 | |||||
const val CATEGORY_ENGLISH_SPOKEN: Long = 13 //英语: 口语 | |||||
const val CATEGORY_CHINESE_COMPOSITION: Long = 2 //语文: 作文 | |||||
const val CATEGORY_CHINESE_LITERACY: Long = 3 //语文: 识字 | |||||
const val CATEGORY_CHINESE_PINYIN: Long = 5 //语文: 拼音 | |||||
//项目的课程类型: course --> typeId | |||||
const val COURSE_TYPE_DISCERN = 1 //认读、口语 | |||||
const val COURSE_TYPE_VOICE = 2 //辨音 | |||||
const val COURSE_TYPE_SPELL = 3 //拼写 | |||||
const val COURSE_TYPE_POINTS = 4 //作文知识点 | |||||
const val COURSE_TYPE_LITERACY = 5 //识字 | |||||
const val COURSE_TYPE_SOUNDMARK = 6 //音标 | |||||
const val COURSE_TYPE_PINYIN = 7 //拼音 | |||||
const val COURSE_TYPE_SPOKEN = 8 //口语 | |||||
//作文课时类型 | |||||
const val COMPOSITION_TYPE_VIDEO = 1 //视频 | |||||
const val COMPOSITION_TYPE_KNOWLEDGE = 2 //知识点学习 | |||||
const val COMPOSITION_TYPE_EXAM = 3 //知识点测试 | |||||
const val COMPOSITION_TYPE_READING = 4 //课堂练习 | |||||
const val COMPOSITION_TYPE_TASK = 5 //课外练习 | |||||
//口语课时类型 | |||||
const val SPOKEN_LESSON_TYPE_WORD = 1 //口语词汇 | |||||
const val SPOKEN_LESSON_TYPE_SENTENCE = 2 //口语句型 | |||||
const val SPOKEN_LESSON_TYPE_DIALOGUE = 3 //口语对话 | |||||
//课程包过期信息状态值 | |||||
const val EXPIRY_NOMAL = 1 //正常态 | |||||
const val EXPIRY_WILL_OVER = 2 //快过期 小于39天 | |||||
const val EXPIRY_OVER = 3 //已过期 | |||||
//课程包内容是否下载状态值 | |||||
const val CONTENT_NOT_DOWN = 0 //未下载 | |||||
const val CONTENT_DOWNING = 1 //下载中 | |||||
const val CONTENT_NOMAL = 2 //正常态(已下载) | |||||
val FILE_ENGLISH = "english" + File.separator + "pack" //英语项目包 | |||||
val FILE_CHINESE = "chinese" + File.separator + "pack" //作文项目包 | |||||
//课程数据包解压后保存的名称 | |||||
const val DBFILENAME = "course_data.db" | |||||
const val FILE_VOICE = "voice" //音频地址 | |||||
const val VOICE_COMMON_KONGGE = "kongge.mp3" | |||||
const val VOICE_COMMON_MISTAKE = "mistake.mp3" | |||||
const val VOICE_COMMON_DI = "di.mp3" //叮咚 | |||||
const val FILE_UPLOAD_FAIL = "error" //上传失败地址 | |||||
const val FILE_IMG = "glide" //图片缓存地址 | |||||
/********发音默认type */ | |||||
const val SOUND_TYPE_US = 1 //美 | |||||
const val SOUND_TYPE_UK = 2 //英 | |||||
const val SOUND_TYPE_CN = 3 //中文 | |||||
const val TEST_QUEST_TYPE_FIELD = 1 //测试题选项类型 :字段名 | |||||
const val TEST_QUEST_TYPE_ID = 2 //测试题选项类型: 选项id | |||||
// 分组(1:普通测试(词汇测试,不做redis统计关联) 2:章节学前测试 3:章节学后测试 4:学前总测试 5:学后总测试 6:备忘录测试(不做redis统计关联);7:作文知识点测试,8:服务中心的课程测试) | |||||
const val TEST_TYPE_NORMAL = 1 //普通测试(词汇测试,不做redis统计关联) | |||||
const val TEST_TYPE_BEFORE = 2 //学前测试 | |||||
const val TEST_TYPE_AFTER = 3 //学后测试 | |||||
const val TEST_TYPE_BEFORE_TOTAL = 4 //学前总测试 | |||||
const val TEST_TYPE_AFTER_TOTAL = 5 //学后总测试 | |||||
const val TEST_TYPE_MEMO = 6 //备忘录测试 | |||||
const val TEST_TYPE_COMPOSITION = 7 //作文知识点测试 | |||||
const val TEST_TYPE_SERVICE_CENTER = 8 //服务中心的课程测试 | |||||
const val TEST_DB_DATA_WORD = 1 // data_word | |||||
const val TEST_DB_DATA_EXAM = 2 // data_exam | |||||
const val TEST_CORRECT = 1 //答题正确 | |||||
const val TEST_ERROR = -1 //答题错误 | |||||
const val TEST_UNANSWER = 0 //答题未答 | |||||
const val TEST_TO_NEXT_TIME_CORRECT = 500 //认读辨音 正确 0.5秒跳下一题 | |||||
const val TEST_TO_NEXT_TIME_ERROR = 2000 //认读辨音 答错 2秒 | |||||
const val TEST_TO_NEXT_TIME_UNANSWER = 2000 //认读辨音 未答 2秒 | |||||
const val TEST_TO_NEXT_TIME_SPELL = 1500 //辨音错误到下一题需要1.5秒 | |||||
const val TEST_WORD_COUNT_DOWN_TIME_DISCERN = 6000 //认读单个单词倒计时时间 6秒 | |||||
const val TEST_WORD_COUNT_DOWN_TIME_SPELL_SINGLE = 1600 //拼写单个单词字母的倒计时时间 | |||||
const val TEST_WORD_COUNT_DOWN_TOME_COMPOSITION = 15000 //作文测试倒计时时间 | |||||
const val SCORE_1 = 80 //小于score_1 悲伤 | |||||
const val SCORE_2 = 90 //大于等于score1 小于 score_2 加油 | |||||
const val SCORE_SPOKEN_DIALOGUE_1 = 60 //口语对话练习课时后测试通过标准 80以上优秀,中间良好 | |||||
const val TEST_COUNT_TOTAL = 25 //总测试 50题 | |||||
const val TEST_COUNT_NORAM = 20 //章节测试 25题 | |||||
const val TEST_COUNT_VOCABULARY = 100 //词汇量测试 | |||||
//测试的题目类型 | |||||
const val TEST_QUEST_TYPE_CHOICE = 1 //选择题 | |||||
const val TEST_QUEST_TYPE_GAP_FILLING = 2 //填空题 | |||||
const val TEST_QUEST_TYPE_JUDGE = 3 //判断题 | |||||
const val TEST_QUEST_TYPE_SPOKEN_DIALOGUE = 4 //口语对话测试 | |||||
//课时状态 | |||||
const val LESSON_STATE_NORMAL = 0 //普通状态 | |||||
// public static final int LESSON_STATE_SELECT = 1 ; //选中状态 | |||||
const val LESSON_STATE_LOCKED = 1 //锁定状态 | |||||
//答题左侧按钮状态 | |||||
const val ANSWER = 0 //答案 | |||||
const val CORRECT = 1 //正确 | |||||
const val NEXT = 2 //下一条 | |||||
//有效时间 : 18秒 | |||||
const val VALID_TIME: Long = 18000 | |||||
//最后一课时 虚拟下一课时标记(主要用于判断最后一课时学后测试是否有通过) | |||||
const val LAST_LESSON_NEXT_FLAG = "-1_-1" | |||||
//学习 | |||||
const val LEARN_FLAG = 1 | |||||
//复习 | |||||
const val REVIEW_FLAG = 2 | |||||
//拼写中 | |||||
const val STATE_SPELLING = 1 | |||||
//纠错中 | |||||
const val STATE_MODIFYING = 2 | |||||
//不可操作状态 | |||||
const val STATE_UNENABLE = 3 | |||||
//拼写结果: 全对 | |||||
const val RESULT_ALL_RIGHT = 1 | |||||
//拼写结果:错误;可容错 | |||||
const val RESULT_ERROR_CAN_MODIFY = 2 | |||||
//拼写结果: 错误,无容错 | |||||
const val RESULT_ERROR = 3 | |||||
//拼写修改完成 | |||||
const val RESULT_MODIFY_OVER = 4 | |||||
// 0: 自己按顺序加载状态页 1复习页 2学前总测页 3 目录页 4学后总测未测 5、学后总测未通过 6、学后总测已通过 | |||||
const val PAGE_LOADING_NORAML = 0 | |||||
const val PAGE_LOADING_REVIEW = 1 | |||||
const val PAGE_LOADING_BEFORE = 2 | |||||
const val PAGE_LOADING_CATALOG = 3 | |||||
const val PAGE_LOADING_AFTER_NOT = 4 | |||||
const val PAGE_LOADING_AFTER_NO_PASS = 5 | |||||
const val PAGE_LOADING_AFTER_PASS = 6 | |||||
//收藏类型 | |||||
const val COMPOSITON_COLLECT_VIDEO_BLACK_BOOK = 1 //收藏类型:视频版本 | |||||
const val COMPOSITON_COLLECT_READING = 2 //阅读材料 | |||||
//模块联通通知类型 | |||||
const val NOTIFY_ENGLISH_REVIEW = 1 //英语有复习 | |||||
const val NOTIFY_ENGLISH_ERROR = 2 //英语学习有错误 | |||||
const val NOTIFY_COMPOSITION_REVIEW = 3 //作文有复习 | |||||
const val NOTIFY_COMPOSITION_ERROR = 4 //作文学习有错误 | |||||
const val NOTIFY_LEARN_RECORD_CHANGE = 5 //学习记录有变化 | |||||
//游戏 | |||||
const val GAME_GAPFILLING = 1 //填空 | |||||
const val GAME_CHOOSE = 2 //消消乐 | |||||
const val GAME_TRANSLATE = 3 //翻译排序 | |||||
//口语自动播放模式 | |||||
const val SPOKEN_AUTO_PLAY_MODEL = 1 //自动播放模式 | |||||
const val SPOKEN_AUTO_FLOWER_MODEL = 2 //跟读模式 | |||||
//收藏本: 句子type 2 | |||||
const val COLLECT_TYPE_SENTENCE: Long = 2 | |||||
} |
google() | google() | ||||
mavenCentral() | mavenCentral() | ||||
jcenter() // Warning: this repository is going to shut down soon | jcenter() // Warning: this repository is going to shut down soon | ||||
maven { url 'https://jitpack.io' } | |||||
} | } | ||||
} | } | ||||
rootProject.name = "XklLocal" | rootProject.name = "XklLocal" |