├── .idea
├── $CACHE_FILE$
├── .gitignore
├── CustomProgressView.iml
├── codeStyles
│ └── Project.xml
├── dbnavigator.xml
├── dictionaries
├── externalDependencies.xml
├── inspectionProfiles
│ ├── Project_Default.xml
│ └── profiles_settings.xml
├── misc.xml
├── modules.xml
└── vcs.xml
├── CPV.jpeg
├── CustomView
├── .gitignore
├── .idea
│ ├── $CACHE_FILE$
│ ├── .name
│ ├── codeStyles
│ │ └── Project.xml
│ ├── compiler.xml
│ ├── dbnavigator.xml
│ ├── dictionaries
│ ├── externalDependencies.xml
│ ├── gradle.xml
│ ├── inspectionProfiles
│ │ ├── Project_Default.xml
│ │ └── profiles_settings.xml
│ ├── jarRepositories.xml
│ ├── misc.xml
│ ├── runConfigurations.xml
│ └── vcs.xml
├── app
│ ├── .gitignore
│ ├── build.gradle
│ ├── proguard-rules.pro
│ └── src
│ │ ├── androidTest
│ │ └── java
│ │ │ └── androidstack
│ │ │ └── customview
│ │ │ └── ExampleInstrumentedTest.java
│ │ ├── main
│ │ ├── AndroidManifest.xml
│ │ ├── assets
│ │ │ ├── 706.svga
│ │ │ ├── car.svga
│ │ │ ├── images
│ │ │ │ ├── img_0.png
│ │ │ │ └── img_1.png
│ │ │ ├── liwu.json
│ │ │ ├── love.svga
│ │ │ ├── posche.svga
│ │ │ └── test.json
│ │ ├── java
│ │ │ └── androidstack
│ │ │ │ └── customview
│ │ │ │ ├── App.java
│ │ │ │ ├── BasisViewActivity.java
│ │ │ │ ├── CustomDialog.java
│ │ │ │ ├── MainActivity.java
│ │ │ │ ├── MaskActivity.java
│ │ │ │ ├── TestActivity.java
│ │ │ │ ├── animation
│ │ │ │ ├── advanced
│ │ │ │ │ ├── LoadingPathView.java
│ │ │ │ │ ├── LoadingSuccessView.java
│ │ │ │ │ └── PathMeasureActivity.java
│ │ │ │ ├── interpolator
│ │ │ │ │ ├── InterpolatorActivity.java
│ │ │ │ │ └── ReverseInterpolator.java
│ │ │ │ ├── property
│ │ │ │ │ ├── PropertyAnimationActivity.java
│ │ │ │ │ ├── advanced
│ │ │ │ │ │ ├── AdvancedPropertyActivity.java
│ │ │ │ │ │ ├── PhoneActivity.java
│ │ │ │ │ │ └── ViewGroupAnimateActivity.java
│ │ │ │ │ ├── evaluator
│ │ │ │ │ │ ├── CharEvaluator.java
│ │ │ │ │ │ ├── EvaluatorActivity.java
│ │ │ │ │ │ └── ReverseEvaluator.java
│ │ │ │ │ ├── object
│ │ │ │ │ │ ├── FallingBallObjectActivity.java
│ │ │ │ │ │ ├── FallingImageView.java
│ │ │ │ │ │ └── ObjectAnimatorActivity.java
│ │ │ │ │ ├── set
│ │ │ │ │ │ ├── AnimatorSetActivity.java
│ │ │ │ │ │ └── MenuActivity.java
│ │ │ │ │ └── value
│ │ │ │ │ │ ├── FallingBallEvaluator.java
│ │ │ │ │ │ ├── FallingBallValueActivity.java
│ │ │ │ │ │ ├── LoadingImageView.java
│ │ │ │ │ │ └── ValueAnimatorActivity.java
│ │ │ │ └── view
│ │ │ │ │ ├── ViewAnimationActivity.java
│ │ │ │ │ ├── frame
│ │ │ │ │ └── FrameAnimationActivity.java
│ │ │ │ │ └── tween
│ │ │ │ │ ├── AlphaAnimationActivity.java
│ │ │ │ │ ├── RotateAnimationActivity.java
│ │ │ │ │ ├── ScaleAnimationActivity.java
│ │ │ │ │ ├── SetAnimationActivity.java
│ │ │ │ │ ├── TranslateAnimationActivity.java
│ │ │ │ │ ├── TweenAnimationActivity.java
│ │ │ │ │ └── effect
│ │ │ │ │ ├── CameraActivity.java
│ │ │ │ │ ├── LoadingActivity.java
│ │ │ │ │ └── ScannerActivity.java
│ │ │ │ ├── custom
│ │ │ │ └── CustomProgressActivity.java
│ │ │ │ ├── drawing
│ │ │ │ ├── PaintActivity.java
│ │ │ │ └── matrix
│ │ │ │ │ └── MatrixActivity.java
│ │ │ │ ├── rv
│ │ │ │ ├── layoutmanager
│ │ │ │ │ ├── CardActivity.java
│ │ │ │ │ ├── CardItemView.java
│ │ │ │ │ ├── CardLayoutManager.java
│ │ │ │ │ └── Pool.java
│ │ │ │ └── partrv
│ │ │ │ │ ├── PartRvActivity.java
│ │ │ │ │ └── PartRvAdapter.java
│ │ │ │ ├── svg
│ │ │ │ ├── SvgActivity.java
│ │ │ │ ├── lottie
│ │ │ │ │ └── LottieActivity.java
│ │ │ │ └── svga
│ │ │ │ │ ├── SvgaActivity.java
│ │ │ │ │ └── SvgaTextActivity.java
│ │ │ │ ├── text
│ │ │ │ ├── GradientTextView.java
│ │ │ │ └── TextActivity.java
│ │ │ │ ├── toolbar
│ │ │ │ └── ToolBarActivity.java
│ │ │ │ └── view
│ │ │ │ ├── BasisView.java
│ │ │ │ ├── CustomProgressView.java
│ │ │ │ └── mask
│ │ │ │ ├── GuideMask.java
│ │ │ │ └── GuideMaskSet.java
│ │ └── res
│ │ │ ├── anim
│ │ │ ├── alpha_test.xml
│ │ │ ├── rotate_test.xml
│ │ │ ├── scale_test.xml
│ │ │ ├── set_sanner.xml
│ │ │ ├── set_test.xml
│ │ │ └── translate_test.xml
│ │ │ ├── animator
│ │ │ ├── animator_logo.xml
│ │ │ └── animator_set.xml
│ │ │ ├── drawable-v21
│ │ │ └── ic_logo.xml
│ │ │ ├── drawable-v24
│ │ │ └── ic_launcher_foreground.xml
│ │ │ ├── drawable
│ │ │ ├── animation_list_loading.xml
│ │ │ ├── ic_launcher_background.xml
│ │ │ ├── ic_logo.xml
│ │ │ ├── ic_love.xml
│ │ │ ├── item.jpg
│ │ │ ├── shape_scanner.xml
│ │ │ └── vector_logo.xml
│ │ │ ├── layout
│ │ │ ├── activity_advanced_property.xml
│ │ │ ├── activity_alpha_animation.xml
│ │ │ ├── activity_animator_set.xml
│ │ │ ├── activity_basis_view.xml
│ │ │ ├── activity_camera.xml
│ │ │ ├── activity_card.xml
│ │ │ ├── activity_custom_progress.xml
│ │ │ ├── activity_evaluator.xml
│ │ │ ├── activity_falling_ball_object.xml
│ │ │ ├── activity_falling_ball_value.xml
│ │ │ ├── activity_frame_animation.xml
│ │ │ ├── activity_interpolator.xml
│ │ │ ├── activity_loading.xml
│ │ │ ├── activity_lottie.xml
│ │ │ ├── activity_main.xml
│ │ │ ├── activity_mask.xml
│ │ │ ├── activity_matrix.xml
│ │ │ ├── activity_menu.xml
│ │ │ ├── activity_music.xml
│ │ │ ├── activity_object_animator.xml
│ │ │ ├── activity_paint.xml
│ │ │ ├── activity_part_rv.xml
│ │ │ ├── activity_path_measure.xml
│ │ │ ├── activity_phone.xml
│ │ │ ├── activity_property_animation.xml
│ │ │ ├── activity_rotate_animation.xml
│ │ │ ├── activity_scale_animation.xml
│ │ │ ├── activity_svg.xml
│ │ │ ├── activity_svga.xml
│ │ │ ├── activity_svga_text.xml
│ │ │ ├── activity_test.xml
│ │ │ ├── activity_text.xml
│ │ │ ├── activity_tool_bar.xml
│ │ │ ├── activity_translate_animation.xml
│ │ │ ├── activity_tween_animation.xml
│ │ │ ├── activity_value_animator.xml
│ │ │ ├── activity_view_animation.xml
│ │ │ ├── activity_view_group_animate.xml
│ │ │ ├── dialog_custom.xml
│ │ │ ├── item.xml
│ │ │ ├── item_part_rv.xml
│ │ │ └── layout_mask.xml
│ │ │ ├── mipmap-anydpi-v26
│ │ │ ├── ic_launcher.xml
│ │ │ └── ic_launcher_round.xml
│ │ │ ├── mipmap-hdpi
│ │ │ ├── ic_launcher.png
│ │ │ └── ic_launcher_round.png
│ │ │ ├── mipmap-mdpi
│ │ │ ├── ic_launcher.png
│ │ │ └── ic_launcher_round.png
│ │ │ ├── mipmap-xhdpi
│ │ │ ├── ic_launcher.png
│ │ │ └── ic_launcher_round.png
│ │ │ ├── mipmap-xxhdpi
│ │ │ ├── add_focus_big.png
│ │ │ ├── ic_arrow.png
│ │ │ ├── ic_camera.jpeg
│ │ │ ├── ic_launcher.png
│ │ │ ├── ic_launcher_round.png
│ │ │ ├── ic_loading.png
│ │ │ ├── ic_phone.png
│ │ │ ├── ic_scanner.png
│ │ │ ├── ic_test.png
│ │ │ ├── loading_01.png
│ │ │ ├── loading_010.png
│ │ │ ├── loading_02.png
│ │ │ ├── loading_03.png
│ │ │ ├── loading_04.png
│ │ │ ├── loading_05.png
│ │ │ ├── loading_06.png
│ │ │ ├── loading_07.png
│ │ │ ├── loading_08.png
│ │ │ └── loading_09.png
│ │ │ ├── mipmap-xxxhdpi
│ │ │ ├── ic_launcher.png
│ │ │ ├── ic_launcher_round.png
│ │ │ └── ic_paper.jpeg
│ │ │ └── values
│ │ │ ├── attr.xml
│ │ │ ├── colors.xml
│ │ │ ├── dimens.xml
│ │ │ ├── strings.xml
│ │ │ └── styles.xml
│ │ └── test
│ │ └── java
│ │ └── androidstack
│ │ └── customview
│ │ └── ExampleUnitTest.java
├── build.gradle
├── gradle.properties
├── gradle
│ └── wrapper
│ │ ├── gradle-wrapper.jar
│ │ └── gradle-wrapper.properties
├── gradlew
├── gradlew.bat
└── settings.gradle
├── DrawingBasis.jpeg
├── Heartbeat1647.svga
├── Heartbeat1701.svga
├── Heartbeat1717.svga
├── Heartbeat1746.svga
├── HeartbeatText.svga
├── HeartbeatText1-3.svga
├── README.md
├── SVG2VECTOR.png
├── Video_20200819_071634_945.gif
├── Video_20200819_073506_981.gif
├── Video_20200819_073636_929.gif
├── ic_sing_single.png
├── ic_week_star_frame_new.9.png
├── svga_nihongdeng
├── tween.jpeg
├── 公众号.bmp
├── 抛物动画.gif
├── 插值器.jpeg
├── 电话响铃动画.gif
├── 菜单动画.gif
└── 逐帧动画.jpeg
/.idea/$CACHE_FILE$:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 | Android
10 |
11 |
12 | CorrectnessLintAndroid
13 |
14 |
15 | General
16 |
17 |
18 | Kotlin
19 |
20 |
21 | LintAndroid
22 |
23 |
24 | PerformanceLintAndroid
25 |
26 |
27 | Plugin DevKit
28 |
29 |
30 |
31 |
32 |
33 |
--------------------------------------------------------------------------------
/.idea/.gitignore:
--------------------------------------------------------------------------------
1 | # Default ignored files
2 | /workspace.xml
--------------------------------------------------------------------------------
/.idea/CustomProgressView.iml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/.idea/dictionaries:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/.idea/externalDependencies.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/.idea/inspectionProfiles/Project_Default.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
--------------------------------------------------------------------------------
/.idea/inspectionProfiles/profiles_settings.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
--------------------------------------------------------------------------------
/.idea/modules.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
--------------------------------------------------------------------------------
/.idea/vcs.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/CPV.jpeg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CPV.jpeg
--------------------------------------------------------------------------------
/CustomView/.gitignore:
--------------------------------------------------------------------------------
1 | *.iml
2 | .gradle
3 | /local.properties
4 | /.idea/caches
5 | /.idea/libraries
6 | /.idea/modules.xml
7 | /.idea/workspace.xml
8 | /.idea/navEditor.xml
9 | /.idea/assetWizardSettings.xml
10 | .DS_Store
11 | /build
12 | /captures
13 | .externalNativeBuild
14 | .cxx
15 |
--------------------------------------------------------------------------------
/CustomView/.idea/$CACHE_FILE$:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 | Android
10 |
11 |
12 | CorrectnessLintAndroid
13 |
14 |
15 | General
16 |
17 |
18 | Kotlin
19 |
20 |
21 | LintAndroid
22 |
23 |
24 | PerformanceLintAndroid
25 |
26 |
27 | Plugin DevKit
28 |
29 |
30 |
31 |
32 |
33 |
--------------------------------------------------------------------------------
/CustomView/.idea/.name:
--------------------------------------------------------------------------------
1 | CustomProgressView
--------------------------------------------------------------------------------
/CustomView/.idea/compiler.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/CustomView/.idea/dictionaries:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/CustomView/.idea/externalDependencies.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/CustomView/.idea/gradle.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
21 |
22 |
--------------------------------------------------------------------------------
/CustomView/.idea/inspectionProfiles/Project_Default.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
--------------------------------------------------------------------------------
/CustomView/.idea/inspectionProfiles/profiles_settings.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
--------------------------------------------------------------------------------
/CustomView/.idea/jarRepositories.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
--------------------------------------------------------------------------------
/CustomView/.idea/runConfigurations.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
--------------------------------------------------------------------------------
/CustomView/.idea/vcs.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/CustomView/app/.gitignore:
--------------------------------------------------------------------------------
1 | /build
--------------------------------------------------------------------------------
/CustomView/app/build.gradle:
--------------------------------------------------------------------------------
1 | apply plugin: 'com.android.application'
2 |
3 | apply plugin: 'kotlin-android'
4 | apply plugin: 'kotlin-android-extensions'
5 |
6 | android {
7 | compileSdkVersion 29
8 | buildToolsVersion "29.0.3"
9 |
10 | defaultConfig {
11 | applicationId "androidstack.customview"
12 | minSdkVersion 17
13 | targetSdkVersion 29
14 | versionCode 1
15 | versionName "1.0"
16 |
17 | testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
18 | }
19 |
20 | buildTypes {
21 | release {
22 | minifyEnabled false
23 | proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
24 | }
25 | }
26 | compileOptions {
27 | sourceCompatibility JavaVersion.VERSION_1_8
28 | targetCompatibility JavaVersion.VERSION_1_8
29 | }
30 | }
31 |
32 | dependencies {
33 | implementation fileTree(dir: "libs", include: ["*.jar"])
34 | implementation 'androidx.appcompat:appcompat:1.2.0'
35 | implementation 'androidx.constraintlayout:constraintlayout:2.0.0'
36 | testImplementation 'junit:junit:4.13'
37 | androidTestImplementation 'androidx.test.ext:junit:1.1.2'
38 | androidTestImplementation 'androidx.test.espresso:espresso-core:3.3.0'
39 |
40 | implementation 'com.github.yyued:SVGAPlayer-Android:2.5.8'
41 | implementation 'com.airbnb.android:lottie:3.1.0'
42 |
43 | implementation 'com.google.android.material:material:1.2.0'
44 | }
--------------------------------------------------------------------------------
/CustomView/app/proguard-rules.pro:
--------------------------------------------------------------------------------
1 | # Add project specific ProGuard rules here.
2 | # You can control the set of applied configuration files using the
3 | # proguardFiles setting in build.gradle.
4 | #
5 | # For more details, see
6 | # http://developer.android.com/guide/developing/tools/proguard.html
7 |
8 | # If your project uses WebView with JS, uncomment the following
9 | # and specify the fully qualified class name to the JavaScript interface
10 | # class:
11 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
12 | # public *;
13 | #}
14 |
15 | # Uncomment this to preserve the line number information for
16 | # debugging stack traces.
17 | #-keepattributes SourceFile,LineNumberTable
18 |
19 | # If you keep the line number information, uncomment this to
20 | # hide the original source file name.
21 | #-renamesourcefileattribute SourceFile
--------------------------------------------------------------------------------
/CustomView/app/src/androidTest/java/androidstack/customview/ExampleInstrumentedTest.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview;
2 |
3 | import android.content.Context;
4 |
5 | import androidx.test.platform.app.InstrumentationRegistry;
6 | import androidx.test.ext.junit.runners.AndroidJUnit4;
7 |
8 | import org.junit.Test;
9 | import org.junit.runner.RunWith;
10 |
11 | import static org.junit.Assert.*;
12 |
13 | /**
14 | * Instrumented test, which will execute on an Android device.
15 | *
16 | * @see Testing documentation
17 | */
18 | @RunWith(AndroidJUnit4.class)
19 | public class ExampleInstrumentedTest {
20 | @Test
21 | public void useAppContext() {
22 | // Context of the app under test.
23 | Context appContext = InstrumentationRegistry.getInstrumentation().getTargetContext();
24 | assertEquals("androidstack.progress", appContext.getPackageName());
25 | }
26 | }
--------------------------------------------------------------------------------
/CustomView/app/src/main/AndroidManifest.xml:
--------------------------------------------------------------------------------
1 |
2 |
4 |
5 |
6 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
56 |
57 |
58 |
59 |
60 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/assets/706.svga:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/assets/706.svga
--------------------------------------------------------------------------------
/CustomView/app/src/main/assets/car.svga:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/assets/car.svga
--------------------------------------------------------------------------------
/CustomView/app/src/main/assets/images/img_0.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/assets/images/img_0.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/assets/images/img_1.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/assets/images/img_1.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/assets/liwu.json:
--------------------------------------------------------------------------------
1 | {"v":"5.1.8","fr":30,"ip":0,"op":41,"w":70,"h":70,"nm":"禮物盒","ddd":0,"assets":[{"id":"image_0","w":34,"h":17,"u":"images/","p":"img_0.png"},{"id":"image_1","w":30,"h":15,"u":"images/","p":"img_1.png"},{"id":"image_2","w":88,"h":76,"u":"images/","p":"img_2.png"},{"id":"image_3","w":36,"h":36,"u":"images/","p":"img_3.png"}],"layers":[{"ddd":0,"ind":1,"ty":2,"nm":"liheshang.png","cl":"png","parent":2,"refId":"image_0","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":1,"k":[{"i":{"x":[0.227],"y":[1]},"o":{"x":[0.333],"y":[0]},"n":["0p227_1_0p333_0"],"t":9,"s":[0],"e":[-15]},{"i":{"x":[0.667],"y":[1]},"o":{"x":[0.769],"y":[0]},"n":["0p667_1_0p769_0"],"t":17,"s":[-15],"e":[7]},{"i":{"x":[0.384],"y":[0.384]},"o":{"x":[0.333],"y":[0]},"n":["0p384_0p384_0p333_0"],"t":24,"s":[7],"e":[-8]},{"i":{"x":[0.833],"y":[0.833]},"o":{"x":[0.167],"y":[0.167]},"n":["0p833_0p833_0p167_0p167"],"t":32,"s":[-8],"e":[0]},{"t":40}],"ix":10},"p":{"a":1,"k":[{"i":{"x":0.833,"y":0.833},"o":{"x":0.167,"y":0.167},"n":"0p833_0p833_0p167_0p167","t":11,"s":[-2,0.75,0],"e":[-2,-2.25,0],"to":[0,-0.5,0],"ti":[0,0,0]},{"i":{"x":0.833,"y":0.833},"o":{"x":0.167,"y":0.167},"n":"0p833_0p833_0p167_0p167","t":13,"s":[-2,-2.25,0],"e":[-2,0.75,0],"to":[0,0,0],"ti":[0,-1.16666662693024,0]},{"i":{"x":0.833,"y":0.833},"o":{"x":0.167,"y":0.167},"n":"0p833_0p833_0p167_0p167","t":24,"s":[-2,0.75,0],"e":[-2,4.75,0],"to":[0,1.16666662693024,0],"ti":[0,0,0]},{"i":{"x":0.833,"y":0.833},"o":{"x":0.167,"y":0.167},"n":"0p833_0p833_0p167_0p167","t":32,"s":[-2,4.75,0],"e":[-2,0.75,0],"to":[0,0,0],"ti":[0,0.66666668653488,0]},{"t":40}],"ix":2},"a":{"a":0,"k":[0,17,0],"ix":1},"s":{"a":0,"k":[100,100,100],"ix":6}},"ao":0,"ip":5,"op":43,"st":5,"bm":0},{"ddd":0,"ind":2,"ty":2,"nm":"lihexia.png","cl":"png","refId":"image_1","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":1,"k":[{"i":{"x":0.833,"y":0.833},"o":{"x":0.167,"y":0.167},"n":"0p833_0p833_0p167_0p167","t":13,"s":[34.75,38.781,0],"e":[34.75,42.781,0],"to":[0,0.66666668653488,0],"ti":[0,-0.66666668653488,0]},{"t":20}],"ix":2},"a":{"a":0,"k":[15,7.5,0],"ix":1},"s":{"a":1,"k":[{"i":{"x":[0.833,0.833,0.833],"y":[0.833,0.833,0.833]},"o":{"x":[0.167,0.167,0.167],"y":[0.167,0.167,0.167]},"n":["0p833_0p833_0p167_0p167","0p833_0p833_0p167_0p167","0p833_0p833_0p167_0p167"],"t":5,"s":[20,20,100],"e":[120,120,100]},{"i":{"x":[0.833,0.833,0.833],"y":[0.833,0.833,0.833]},"o":{"x":[0.167,0.167,0.167],"y":[0.167,0.167,0.167]},"n":["0p833_0p833_0p167_0p167","0p833_0p833_0p167_0p167","0p833_0p833_0p167_0p167"],"t":11,"s":[120,120,100],"e":[100,100,100]},{"t":20}],"ix":6}},"ao":0,"ip":5,"op":43,"st":5,"bm":0},{"ddd":0,"ind":3,"ty":2,"nm":"feichu.png","cl":"png","parent":2,"refId":"image_2","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[13.302,0.097,0],"ix":2},"a":{"a":0,"k":[44,38,0],"ix":1},"s":{"a":1,"k":[{"i":{"x":[0.833,0.833,0.833],"y":[0.833,0.833,0.833]},"o":{"x":[0.167,0.167,0.167],"y":[0.167,0.167,0.167]},"n":["0p833_0p833_0p167_0p167","0p833_0p833_0p167_0p167","0p833_0p833_0p167_0p167"],"t":8,"s":[37.89,37.89,100],"e":[63.89,63.89,100]},{"t":16}],"ix":6}},"ao":0,"ip":8,"op":17,"st":3,"bm":0},{"ddd":0,"ind":4,"ty":2,"nm":"组 1132@2x.png","cl":"png","refId":"image_3","sr":1,"ks":{"o":{"a":1,"k":[{"i":{"x":[0.833],"y":[0.833]},"o":{"x":[0.167],"y":[0.167]},"n":["0p833_0p833_0p167_0p167"],"t":3,"s":[100],"e":[0]},{"t":12}],"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[35,35,0],"ix":2},"a":{"a":0,"k":[18,18,0],"ix":1},"s":{"a":1,"k":[{"i":{"x":[0.833,0.833,0.833],"y":[0.833,0.833,0.833]},"o":{"x":[0.167,0.167,0.167],"y":[0.167,0.167,0.167]},"n":["0p833_0p833_0p167_0p167","0p833_0p833_0p167_0p167","0p833_0p833_0p167_0p167"],"t":3,"s":[100,100,100],"e":[0,0,100]},{"t":12}],"ix":6}},"ao":0,"ip":0,"op":43,"st":-2,"bm":0}],"markers":[{"tm":3,"cm":"1","dr":0}]}
--------------------------------------------------------------------------------
/CustomView/app/src/main/assets/love.svga:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/assets/love.svga
--------------------------------------------------------------------------------
/CustomView/app/src/main/assets/posche.svga:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/assets/posche.svga
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/App.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview;
2 |
3 | import android.app.Application;
4 | import android.net.http.HttpResponseCache;
5 |
6 | import java.io.File;
7 | import java.io.IOException;
8 |
9 | /**
10 | * Created on 2020/8/17 15:05
11 | *
12 | * @author zhangchaozhou
13 | * @email 13760289294@139.com
14 | * @wechat 13760289294
15 | */
16 | public class App extends Application {
17 | @Override
18 | public void onCreate() {
19 | super.onCreate();
20 | try {
21 | File cacheDir = new File(getCacheDir(), "http");
22 | HttpResponseCache.install(cacheDir, 1024 * 1024 * 128);
23 | } catch (IOException e) {
24 | System.out.println(e.getMessage());
25 | }
26 | }
27 | }
28 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/BasisViewActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview;
2 |
3 | import android.os.Bundle;
4 |
5 | import androidx.annotation.Nullable;
6 | import androidx.appcompat.app.AppCompatActivity;
7 |
8 | /**
9 | * Created on 2020/7/22 07:15
10 | *
11 | * @author zhangchaozhou
12 | * @email 13760289294@139.com
13 | * @wechat 13760289294
14 | */
15 | public class BasisViewActivity extends AppCompatActivity {
16 | @Override
17 | protected void onCreate(@Nullable Bundle savedInstanceState) {
18 | super.onCreate(savedInstanceState);
19 | setContentView(R.layout.activity_basis_view);
20 | }
21 | }
22 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/CustomDialog.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview;
2 |
3 | import android.app.Dialog;
4 | import android.content.Context;
5 | import android.os.Build;
6 | import android.os.Bundle;
7 | import android.view.Gravity;
8 | import android.view.LayoutInflater;
9 | import android.view.View;
10 | import android.view.Window;
11 | import android.view.WindowManager;
12 |
13 | import androidx.annotation.NonNull;
14 | import androidx.annotation.Nullable;
15 | import androidx.constraintlayout.widget.ConstraintLayout;
16 |
17 | import static android.graphics.Color.WHITE;
18 |
19 | /**
20 | * Created on 2020/8/20 16:55
21 | *
22 | * @author zhangchaozhou
23 | * @email 13760289294@139.com
24 | * @wechat 13760289294
25 | */
26 | public class CustomDialog extends Dialog {
27 | public CustomDialog(@NonNull Context context) {
28 | super(context);
29 | }
30 |
31 | public CustomDialog(@NonNull Context context, int themeResId) {
32 | super(context, themeResId);
33 | }
34 |
35 | protected CustomDialog(@NonNull Context context, boolean cancelable, @Nullable OnCancelListener cancelListener) {
36 | super(context, cancelable, cancelListener);
37 | }
38 |
39 | @Override
40 | protected void onStart() {
41 | super.onStart();
42 | immerseStatusBarColor(getWindow(), true, WHITE, true);
43 | }
44 |
45 | @Override
46 | protected void onCreate(Bundle savedInstanceState) {
47 | super.onCreate(savedInstanceState);
48 | View v = LayoutInflater.from(getContext()).inflate(R.layout.dialog_custom, null);
49 | Window w = getWindow();
50 | w.setContentView(v);
51 | WindowManager.LayoutParams lp = w.getAttributes();
52 | lp.width = ConstraintLayout.LayoutParams.MATCH_PARENT;
53 | lp.height = ConstraintLayout.LayoutParams.MATCH_PARENT;
54 | lp.gravity = Gravity.BOTTOM;
55 | w.setAttributes(lp);
56 | w.setBackgroundDrawable(null);
57 | w.clearFlags(WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM);
58 | }
59 |
60 | /**
61 | * 设置沉浸模式
62 | * @param isDarkMode 状态栏字体为黑色
63 | */
64 | public static void immerseStatusBarColor(Window window, boolean isDarkMode, int color, boolean isDialog) {
65 | if (Build.VERSION.SDK_INT < Build.VERSION_CODES.M) return;
66 | int uiVisibility = window.getDecorView().getSystemUiVisibility();
67 | if (isDarkMode) {
68 | uiVisibility ^= View.SYSTEM_UI_FLAG_LAYOUT_STABLE;
69 | uiVisibility |= View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR;
70 | } else {
71 | uiVisibility ^= View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR;
72 | uiVisibility |= View.SYSTEM_UI_FLAG_LAYOUT_STABLE;
73 | }
74 | window.clearFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);
75 | window.addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS);
76 | // if (isDialog){
77 | // uiVisibility |=View.SYSTEM_UI_FLAG_HIDE_NAVIGATION |
78 | // View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN|View.SYSTEM_UI_FLAG_IMMERSIVE;
79 | // }else {
80 | // uiVisibility |= View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN;
81 | // }
82 | window.setStatusBarColor(color);
83 | window.getDecorView().setSystemUiVisibility(uiVisibility);
84 | }
85 | }
86 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/MaskActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview;
2 |
3 | import android.graphics.Color;
4 | import android.os.Bundle;
5 | import android.widget.ImageView;
6 |
7 | import androidstack.customview.view.mask.GuideMask;
8 | import androidstack.customview.view.mask.GuideMaskSet;
9 | import androidx.annotation.Nullable;
10 | import androidx.appcompat.app.AppCompatActivity;
11 |
12 | /**
13 | * Created on 2020/8/24 13:05
14 | *
15 | * @author zhangchaozhou
16 | * @email 13760289294@139.com
17 | * @wechat 13760289294
18 | */
19 | public class MaskActivity extends AppCompatActivity {
20 | private ImageView mIvTest;
21 | @Override
22 | protected void onCreate(@Nullable Bundle savedInstanceState) {
23 | super.onCreate(savedInstanceState);
24 | setContentView(R.layout.activity_mask);
25 |
26 | mIvTest = findViewById(R.id.iv_test);
27 |
28 | GuideMask guideMask = new GuideMask.Builder(this)
29 | //蒙版所在activity
30 | .setMaskActivity(this)
31 | //目标布局
32 | .setTargetView(mIvTest)
33 | //蒙版背景颜色包括透明度
34 | .setBgColor(Color.parseColor("#40000000"))
35 | //蒙版布局
36 | .setMaskLayout(R.layout.layout_mask)
37 | //关闭蒙版的按钮
38 | .setMaskCloseId(R.id.btn_close)
39 | //围栏与目标布局的距离
40 | .setFencePadding(5,5,5,5)
41 | //围栏布局四角的角度
42 | .setFenceRadius(100)
43 | .build();
44 |
45 | GuideMaskSet guideMaskSet = new GuideMaskSet();
46 | //添加蒙版
47 | guideMaskSet.addGuide(guideMask);
48 | //显示所有蒙版
49 | guideMaskSet.show();
50 | }
51 | }
52 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/TestActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview;
2 |
3 | import android.os.Bundle;
4 |
5 | import androidx.annotation.Nullable;
6 | import androidx.appcompat.app.AppCompatActivity;
7 |
8 | /**
9 | * Created on 2020/9/2 19:25
10 | *
11 | * @author zhangchaozhou
12 | * @email 13760289294@139.com
13 | * @wechat 13760289294
14 | */
15 | public class TestActivity extends AppCompatActivity {
16 | @Override
17 | protected void onCreate(@Nullable Bundle savedInstanceState) {
18 | super.onCreate(savedInstanceState);
19 | setContentView(R.layout.activity_test);
20 | }
21 | }
22 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/advanced/LoadingPathView.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.advanced;
2 |
3 | import android.animation.ValueAnimator;
4 | import android.content.Context;
5 | import android.graphics.Bitmap;
6 | import android.graphics.BitmapFactory;
7 | import android.graphics.Canvas;
8 | import android.graphics.Color;
9 | import android.graphics.Matrix;
10 | import android.graphics.Paint;
11 | import android.graphics.Path;
12 | import android.graphics.PathMeasure;
13 | import android.util.AttributeSet;
14 | import android.view.View;
15 |
16 | import androidstack.customview.R;
17 | import androidx.annotation.Nullable;
18 |
19 | /**
20 | * Created on 2020/8/16 17:42
21 | *
22 | * @author zhangchaozhou
23 | * @email 13760289294@139.com
24 | * @wechat 13760289294
25 | */
26 | public class LoadingPathView extends View {
27 |
28 | private Bitmap mArrow;
29 | private Paint mPaint;
30 | private Path mDstPath;
31 | private Path mCirclePath;
32 | private PathMeasure mPathMeasure;
33 | private Float mCurrentAnimValue;
34 | float mStop = 0.0f;
35 | float mStart = 0.0f;
36 | private float[] mPos = new float[2];
37 | private float[] mTan = new float[2];
38 | private Matrix mMatrix;
39 | public LoadingPathView(Context context) {
40 | this(context,null);
41 | }
42 |
43 | public LoadingPathView(Context context, @Nullable AttributeSet attrs) {
44 | this(context, attrs,0);
45 | }
46 |
47 | public LoadingPathView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
48 | super(context, attrs, defStyleAttr);
49 | init();
50 | }
51 |
52 | /**
53 | * 根据手机的分辨率从 dp 的单位 转成为 px(像素)
54 | */
55 | public static int dip2px(Context context, float dpValue) {
56 | final float scale = context.getResources().getDisplayMetrics().density;
57 | return (int) (dpValue * scale + 0.5f);
58 | }
59 |
60 | private void init() {
61 | setLayerType(LAYER_TYPE_SOFTWARE,null);
62 | mArrow = BitmapFactory.decodeResource(getResources(), R.mipmap.ic_arrow);
63 | mMatrix = new Matrix();
64 | mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
65 | mPaint.setStyle(Paint.Style.STROKE);
66 | mPaint.setStrokeWidth(4);
67 | mPaint.setColor(Color.RED);
68 |
69 | mDstPath = new Path();
70 | mCirclePath = new Path();
71 | mCirclePath.addCircle(dip2px(getContext(),100),dip2px(getContext(),100),dip2px(getContext(),25),Path.Direction.CW);
72 | mPathMeasure = new PathMeasure(mCirclePath,true);
73 |
74 | ValueAnimator animator = ValueAnimator.ofFloat(0,1);
75 | animator.setRepeatCount(ValueAnimator.INFINITE);
76 | animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
77 | @Override
78 | public void onAnimationUpdate(ValueAnimator animation) {
79 | //获取到旋转的角度值后刷新界面
80 | mCurrentAnimValue = (Float) animation.getAnimatedValue();
81 | invalidate();
82 | }
83 | });
84 | animator.setDuration(2000);
85 | animator.start();
86 | }
87 |
88 |
89 |
90 |
91 | @Override
92 | protected void onDraw(Canvas canvas) {
93 | super.onDraw(canvas);
94 | mStop = mPathMeasure.getLength()*mCurrentAnimValue;
95 | mStart = (float) (mStop-((0.5-Math.abs(mCurrentAnimValue-0.5))*mPathMeasure.getLength()));
96 | mDstPath.reset();
97 | mPathMeasure.getSegment(mStart,mStop, mDstPath,true);
98 | //绘制路径
99 | canvas.drawPath(mDstPath, mPaint);
100 |
101 | mMatrix = new Matrix();
102 |
103 | /**
104 | * 第一种方式
105 | */
106 | mPathMeasure.getPosTan(mStop,mPos,mTan);
107 | float degrees = (float)(Math.atan2(mTan[1],mTan[0])*180.0/Math.PI);
108 | mMatrix.postRotate(degrees,mArrow.getWidth()/2,mArrow.getHeight()/2);
109 | mMatrix.postTranslate(mPos[0]-mArrow.getWidth()/2,mPos[1]-mArrow.getHeight()/2);
110 |
111 | /**
112 | * 第二种方式
113 | */
114 | mPathMeasure.getMatrix(mStop,mMatrix,PathMeasure.POSITION_MATRIX_FLAG|PathMeasure.TANGENT_MATRIX_FLAG);
115 | mMatrix.preTranslate(mArrow.getWidth()/2,-mArrow.getHeight()/2);
116 | //绘制箭头
117 | canvas.drawBitmap(mArrow,mMatrix,mPaint);
118 | }
119 | }
120 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/advanced/LoadingSuccessView.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.advanced;
2 |
3 | import android.content.Context;
4 | import android.graphics.Path;
5 | import android.util.AttributeSet;
6 | import android.view.View;
7 |
8 | import androidx.annotation.Nullable;
9 |
10 | /**
11 | * Created on 2020/8/18 07:01
12 | *
13 | * @author zhangchaozhou
14 | * @email 13760289294@139.com
15 | * @wechat 13760289294
16 | */
17 | public class LoadingSuccessView extends View {
18 | private Path mDstPath;
19 | private Path mCirclePath;
20 |
21 | public LoadingSuccessView(Context context) {
22 | this(context, null);
23 | }
24 |
25 | public LoadingSuccessView(Context context, @Nullable AttributeSet attrs) {
26 | this(context, attrs, 0);
27 | }
28 |
29 | public LoadingSuccessView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
30 | super(context, attrs, defStyleAttr);
31 | init();
32 | }
33 |
34 | /**
35 | * 根据手机的分辨率从 dp 的单位 转成为 px(像素)
36 | */
37 | public static int dip2px(Context context, float dpValue) {
38 | final float scale = context.getResources().getDisplayMetrics().density;
39 | return (int) (dpValue * scale + 0.5f);
40 | }
41 |
42 | private void init() {
43 | mDstPath = new Path();
44 | mCirclePath = new Path();
45 | mCirclePath.addCircle(getWidth()/2,getHeight()/2, dip2px(getContext(),10), Path.Direction.CW);
46 |
47 | }
48 |
49 | }
50 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/advanced/PathMeasureActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.advanced;
2 |
3 | import android.graphics.Matrix;
4 | import android.graphics.Path;
5 | import android.graphics.PathMeasure;
6 | import android.os.Bundle;
7 |
8 | import androidstack.customview.R;
9 | import androidx.annotation.Nullable;
10 | import androidx.appcompat.app.AppCompatActivity;
11 |
12 | /**
13 | * Created on 2020/8/16 11:31
14 | *
15 | * @author zhangchaozhou
16 | * @email 13760289294@139.com
17 | * @wechat 13760289294
18 | */
19 | public class PathMeasureActivity extends AppCompatActivity {
20 | private LoadingPathView mLoadingPathView;
21 |
22 | @Override
23 | protected void onCreate(@Nullable Bundle savedInstanceState) {
24 | super.onCreate(savedInstanceState);
25 | setContentView(R.layout.activity_path_measure);
26 | mLoadingPathView = findViewById(R.id.lpv_circle);
27 | }
28 |
29 |
30 | public void path() {
31 |
32 | Path path = new Path();
33 | PathMeasure pathMeasure1 = new PathMeasure();
34 | /**
35 | * 路径是否闭合 forceClosed
36 | */
37 | pathMeasure1.setPath(path, true);
38 |
39 |
40 | PathMeasure pathMeasure2 = new PathMeasure(path, true);
41 |
42 |
43 | /**
44 | * 路径长度,测量的是当前路径状态的长度,如果forceClosed为true,则不论路径是否闭合,测量的都是路径的闭合长度。
45 | * 获取到的长度是当前曲线的长度。
46 | */
47 | System.out.println(pathMeasure1.getLength());
48 |
49 | System.out.println(pathMeasure2.getLength());
50 |
51 | /**
52 | * 判断路径是否闭合
53 | */
54 | System.out.println(pathMeasure1.isClosed());
55 |
56 |
57 | /**
58 | * 跳转到下一条曲线,true表示跳转成功,false表示跳转失败。
59 | *
60 | */
61 | System.out.println(pathMeasure1.nextContour());
62 |
63 |
64 | /**
65 | * 通过nextContour得到的曲线的顺序和Path中添加的顺序相同。
66 | */
67 | do {
68 | System.out.println(pathMeasure1.getLength());
69 | } while (pathMeasure1.nextContour());
70 |
71 | /**
72 | * 截取整个Path中startD到stopD的某个片段,如果不在范围则返回false,截取后添加Path到dst中。
73 | * startWithMoveTo:如果为true,则被截取的Path片段保持原状添加到dst中;如果为false,则被截取的Path片段的起始点移动到dst的最后一个点,保证dst路径的连续性。
74 | * 需要禁用硬件加速功能,setLayerType(LAYER_TYPE_SOFTWARE,null)。
75 | * 路径截取是以左上角顺时针Path.Direction.CW或逆时针Path.Direction.CCW截取。
76 | */
77 | boolean isSuccess = pathMeasure1.getSegment(0, 10, new Path(), true);
78 |
79 |
80 | /**
81 | *
82 | * 获取路径上某一长度的位置以及该位置的正切值
83 | * distance:距离path起始点的长度,0<=distance<=pathMeasure1.getLength()
84 | * pos 位置的坐标值,pos[0]是x坐标,pos[1]是y坐标
85 | * tan 位置坐标的正切值,也就是坐标到原点与X轴所成夹角对应的正切值,tan[0]是x坐标,tan[1]是y坐标,是半径为1的圆的对应点,y/x就是正切值
86 | * 求反正切值,根据正切值获得对应夹角的度数,也就是反正切,atan(double d)传入弧度值也就是正切的结果值,atan2(double x, double y)传入正切的点的坐标值。
87 | * 如果想要让移动点旋转至与切线重合,则旋转角度要与正切角度相同。
88 | */
89 | boolean isTanSuccess = pathMeasure1.getPosTan(1, new float[]{1F, 1F}, new float[]{1F, 1F});
90 |
91 |
92 | /**
93 | * 得到路径上某一长度的位置,以及该位置的正切值的矩阵。
94 | * distance:距离Path起始点的长度
95 | * matrix:matrix会根据flags的设置而存入不同的内容。
96 | * flags:指定存入matrix中的内容。POSITION_MATRIX_FLAG:获取位置信息。TANGENT_MATRIX_FLAG:获取切边信息,使得图片按Path旋转。
97 | */
98 | boolean isMatrixSuccess = pathMeasure1.getMatrix(1, new Matrix(), PathMeasure.POSITION_MATRIX_FLAG);
99 |
100 |
101 | /**
102 | * getMatrix()是getPosTan()函数的另一种实现。
103 | * getPosTan()将获取到的位置信息和切边信息存储在pos和tan数组中;
104 | * getMatrix()将位置信息和切边信息存储在matrix中。
105 | */
106 | }
107 | }
108 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/interpolator/ReverseInterpolator.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.interpolator;
2 |
3 | import android.view.animation.Interpolator;
4 |
5 | /**
6 | * Created on 2020/8/15 09:29
7 | * 自定义插值器,实现时间插值器TimeInterpolator后,实现获取插值Interpolation的方法,此方法的实现需要数学知识。
8 | * 也可以直接实现Interpolator,因为Interpolator继承的是时间插值器TimeInterpolator。
9 | *
10 | * @author zhangchaozhou
11 | * @email 13760289294@139.com
12 | * @wechat 13760289294
13 | */
14 | public class ReverseInterpolator implements Interpolator {
15 |
16 | /**
17 | * @param input 取值范围为0-1,表示当前动画进度,0刚开始动画,1结束动画,0-1,动画进行中。
18 | * @return 返回实际想要的进度,小于0表示小于开始位置,大于1表示超过目标位置,0-1表示在开始位置和目标位置中间。
19 | */
20 | @Override
21 | public float getInterpolation(float input) {
22 | return 1 - input;
23 | }
24 | }
25 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/property/advanced/PhoneActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.property.advanced;
2 |
3 | import android.animation.Keyframe;
4 | import android.animation.ObjectAnimator;
5 | import android.animation.PropertyValuesHolder;
6 | import android.os.Bundle;
7 | import android.view.View;
8 | import android.widget.ImageView;
9 |
10 | import androidstack.customview.R;
11 | import androidx.annotation.Nullable;
12 | import androidx.appcompat.app.AppCompatActivity;
13 |
14 | /**
15 | * Created on 2020/8/16 09:31
16 | *
17 | * @author zhangchaozhou
18 | * @email 13760289294@139.com
19 | * @wechat 13760289294
20 | */
21 | public class PhoneActivity extends AppCompatActivity implements View.OnClickListener {
22 | private ImageView mIvPhone;
23 |
24 | @Override
25 | protected void onCreate(@Nullable Bundle savedInstanceState) {
26 | super.onCreate(savedInstanceState);
27 | setContentView(R.layout.activity_phone);
28 | mIvPhone = findViewById(R.id.iv_phone);
29 | mIvPhone.setOnClickListener(this);
30 | }
31 |
32 | @Override
33 | public void onClick(View v) {
34 | switch (v.getId()) {
35 | case R.id.iv_phone:
36 | //旋转效果,左右震动
37 | Keyframe keyframe1 = Keyframe.ofFloat(0f, 0);
38 | Keyframe keyframe2 = Keyframe.ofFloat(0.1f, -20f);
39 | Keyframe keyframe3 = Keyframe.ofFloat(0.2f, 20f);
40 | Keyframe keyframe4 = Keyframe.ofFloat(0.3f, -20f);
41 | Keyframe keyframe5 = Keyframe.ofFloat(0.4f, 20f);
42 | Keyframe keyframe6 = Keyframe.ofFloat(0.5f, -20f);
43 | Keyframe keyframe7 = Keyframe.ofFloat(0.6f, 20f);
44 | Keyframe keyframe8 = Keyframe.ofFloat(0.7f, -20f);
45 | Keyframe keyframe9 = Keyframe.ofFloat(0.8f, 20f);
46 | Keyframe keyframe10 = Keyframe.ofFloat(0.9f, -20f);
47 | Keyframe keyframe11 = Keyframe.ofFloat(1.0f, 0f);
48 | PropertyValuesHolder propertyValuesHolder = PropertyValuesHolder.ofKeyframe("rotation",
49 | keyframe1, keyframe1, keyframe2, keyframe3, keyframe4, keyframe5,
50 | keyframe6, keyframe7, keyframe8, keyframe9, keyframe10, keyframe11);
51 | //缩放效果 X
52 | Keyframe keyframeScaleX0 = Keyframe.ofFloat(0,1f);
53 | Keyframe keyframeScaleX1 = Keyframe.ofFloat(0.1f,1.1f);
54 | Keyframe keyframeScaleX9 = Keyframe.ofFloat(0.9f,1.1f);
55 | Keyframe keyframeScaleX10 = Keyframe.ofFloat(1f,1f);
56 | PropertyValuesHolder propertyValuesHolderScaleX = PropertyValuesHolder.ofKeyframe("ScaleX",
57 | keyframeScaleX0,keyframeScaleX1,keyframeScaleX9,keyframeScaleX10);
58 |
59 | //缩放效果 Y
60 | Keyframe keyframeScaleY0 = Keyframe.ofFloat(0,1f);
61 | Keyframe keyframeScaleY1 = Keyframe.ofFloat(0.1f,1.1f);
62 | Keyframe keyframeScaleY9 = Keyframe.ofFloat(0.9f,1.1f);
63 | Keyframe keyframeScaleY10 = Keyframe.ofFloat(1f,1f);
64 | PropertyValuesHolder propertyValuesHolderScaleY = PropertyValuesHolder.ofKeyframe("ScaleY",
65 | keyframeScaleY0,keyframeScaleY1,keyframeScaleY9,keyframeScaleY10);
66 |
67 | ObjectAnimator objectAnimator = ObjectAnimator.ofPropertyValuesHolder(mIvPhone,
68 | propertyValuesHolder,propertyValuesHolderScaleX,propertyValuesHolderScaleY);
69 | objectAnimator.setDuration(1000);
70 | objectAnimator.start();
71 | break;
72 | default:
73 | break;
74 | }
75 | }
76 | }
77 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/property/advanced/ViewGroupAnimateActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.property.advanced;
2 |
3 | import android.animation.LayoutTransition;
4 | import android.animation.ObjectAnimator;
5 | import android.os.Bundle;
6 | import android.view.View;
7 | import android.widget.ImageView;
8 |
9 | import androidstack.customview.R;
10 | import androidx.annotation.Nullable;
11 | import androidx.appcompat.app.AppCompatActivity;
12 | import androidx.constraintlayout.widget.ConstraintLayout;
13 |
14 | /**
15 | * Created on 2020/8/16 10:36
16 | *
17 | * LayoutAnimation:ListView的进场动画
18 | * GridLayoutAnimation:GridView的进场动画
19 | * android:animateLayoutChanges属性:ViewGroup添加删除子View默认动画
20 | * 布局动画 LayoutTransition:ViewGroup添加删除子View添加删除的自定义动画
21 | *
22 | * LayoutTransition.APPEARING;新元素在容器中出现时的动画;
23 | * LayoutTransition.CHANGE_APPEARING;容器中显示新元素,其他元素需要变化时的动画;
24 | * LayoutTransition.CHANGE_DISAPPEARING;容器中移除旧元素,其他元素需要变化时的动画;
25 | * LayoutTransition.CHANGING;
26 | * LayoutTransition.DISAPPEARING;旧元素在容器中移除时的动画;
27 | *
28 | * @author zhangchaozhou
29 | * @email 13760289294@139.com
30 | * @wechat 13760289294
31 | */
32 | public class ViewGroupAnimateActivity extends AppCompatActivity implements View.OnClickListener {
33 | private ConstraintLayout mClLayoutTransition;
34 | private ImageView mIvTest;
35 |
36 | @Override
37 | protected void onCreate(@Nullable Bundle savedInstanceState) {
38 | super.onCreate(savedInstanceState);
39 | setContentView(R.layout.activity_view_group_animate);
40 | mClLayoutTransition = findViewById(R.id.cl_layout_transition);
41 | mIvTest = findViewById(R.id.iv_test);
42 | mIvTest.setOnClickListener(this);
43 |
44 | /**
45 | * 设置移除容器内图片控件时候的动画
46 | */
47 | LayoutTransition layoutTransition = new LayoutTransition();
48 | ObjectAnimator objectAnimator = ObjectAnimator.ofFloat(null, "rotation", 0f, 90f, 0f);
49 | layoutTransition.setAnimator(LayoutTransition.DISAPPEARING, objectAnimator);
50 | /**
51 | * 设置动画间的间隔
52 | */
53 | layoutTransition.setStagger(LayoutTransition.DISAPPEARING, 1000);
54 | mClLayoutTransition.setLayoutTransition(layoutTransition);
55 |
56 | }
57 |
58 | @Override
59 | public void onClick(View v) {
60 | switch (v.getId()) {
61 | case R.id.iv_test:
62 | /**
63 | * 移除布局
64 | */
65 | mClLayoutTransition.removeView(mIvTest);
66 | break;
67 | default:
68 | break;
69 | }
70 | }
71 | }
72 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/property/evaluator/CharEvaluator.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.property.evaluator;
2 |
3 | import android.animation.TypeEvaluator;
4 |
5 | /**
6 | * Created on 2020/8/15 15:00
7 | *
8 | * @author zhangchaozhou
9 | * @email 13760289294@139.com
10 | * @wechat 13760289294
11 | */
12 | public class CharEvaluator implements TypeEvaluator {
13 | @Override
14 | public Character evaluate(float fraction, Character startValue, Character endValue) {
15 | char currentChar = (char) (startValue+fraction*(endValue-startValue));
16 | return currentChar;
17 | }
18 | }
19 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/property/evaluator/ReverseEvaluator.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.property.evaluator;
2 |
3 | import android.animation.TypeEvaluator;
4 |
5 | /**
6 | * Created on 2020/8/15 11:24
7 | * 自定义估值器,实现类型估值器TypeEvaluator,并传入泛型的具体类型
8 | *
9 | * @author zhangchaozhou
10 | * @email 13760289294@139.com
11 | * @wechat 13760289294
12 | */
13 | public class ReverseEvaluator implements TypeEvaluator {
14 |
15 | /**
16 | * @param fraction 插值器中的进度返回值
17 | * @param startValue 动画数值区间的起始数值
18 | * @param endValue 动画数值区间的结束数值
19 | * @return 估值器返回给监听器的具体动画数值
20 | */
21 | @Override
22 | public Integer evaluate(float fraction, Integer startValue, Integer endValue) {
23 | return (int) (endValue - fraction * (endValue - startValue));
24 | }
25 | }
26 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/property/object/FallingBallObjectActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.property.object;
2 |
3 | import android.animation.ObjectAnimator;
4 | import android.graphics.Point;
5 | import android.os.Bundle;
6 | import android.view.View;
7 |
8 | import androidstack.customview.R;
9 | import androidstack.customview.animation.property.value.FallingBallEvaluator;
10 | import androidx.annotation.Nullable;
11 | import androidx.appcompat.app.AppCompatActivity;
12 |
13 | /**
14 | * Created on 2020/8/15 15:55
15 | *
16 | * @author zhangchaozhou
17 | * @email 13760289294@139.com
18 | * @wechat 13760289294
19 | */
20 | public class FallingBallObjectActivity extends AppCompatActivity implements View.OnClickListener {
21 | private FallingImageView mIvBall;
22 | @Override
23 | protected void onCreate(@Nullable Bundle savedInstanceState) {
24 | super.onCreate(savedInstanceState);
25 | setContentView(R.layout.activity_falling_ball_object);
26 | mIvBall = findViewById(R.id.iv_ball);
27 | mIvBall.setOnClickListener(this);
28 | }
29 |
30 | @Override
31 | public void onClick(View v) {
32 | switch (v.getId()){
33 | case R.id.iv_ball:
34 | ObjectAnimator objectAnimator = ObjectAnimator.ofObject(mIvBall,"fallingPos",new FallingBallEvaluator(),new Point(0,0),new Point(500,500));
35 | objectAnimator.setDuration(2000);
36 | objectAnimator.start();
37 | break;
38 | default:
39 | break;
40 | }
41 | }
42 | }
43 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/property/object/FallingImageView.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.property.object;
2 |
3 | import android.content.Context;
4 | import android.graphics.Point;
5 | import android.util.AttributeSet;
6 |
7 | /**
8 | * Created on 2020/8/15 16:59
9 | *
10 | * @author zhangchaozhou
11 | * @email 13760289294@139.com
12 | * @wechat 13760289294
13 | */
14 | public class FallingImageView extends androidx.appcompat.widget.AppCompatImageView {
15 |
16 | public FallingImageView(Context context) {
17 | super(context);
18 | }
19 |
20 | public FallingImageView(Context context, AttributeSet attrs) {
21 | super(context, attrs);
22 | }
23 |
24 | public FallingImageView(Context context, AttributeSet attrs, int defStyleAttr) {
25 | super(context, attrs, defStyleAttr);
26 | }
27 |
28 | /**
29 | * 对象动画会使用反射自动调用此set方法
30 | * @param point
31 | */
32 | public void setFallingPos(Point point){
33 | layout(point.x,point.y,point.x+getWidth(),point.y+getHeight());
34 | }
35 |
36 | /**
37 | * 当指定一个动画值时,动画会通过get方法来获取初始值,否则会崩溃
38 | * @return
39 | */
40 | public Point getFallingPos(){
41 | return new Point(0,0);
42 | }
43 |
44 | }
45 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/property/object/ObjectAnimatorActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.property.object;
2 |
3 | import android.animation.ObjectAnimator;
4 | import android.os.Bundle;
5 | import android.view.View;
6 | import android.widget.ImageView;
7 |
8 | import androidstack.customview.R;
9 | import androidx.annotation.Nullable;
10 | import androidx.appcompat.app.AppCompatActivity;
11 |
12 | /**
13 | * Created on 2020/8/15 16:25
14 | * 对象动画继承自值动画,让动画直接与控件关联,解放监听过程
15 | * 对象动画是通过控件中相关的set方法进行操作的,View已经实现了alpha、rotation、translate、scale等相关方法。
16 | * setTranslationX(float translationX)
17 | * setTranslationY(float translationY)
18 | * setTranslationZ(float translationZ)
19 | * setScaleX(float scaleX)
20 | * setScaleY(float scaleY)
21 | *
22 | * 属性动画之对象动画:
23 | * 1、指定动画数值区间以及属性和控件
24 | * 2、指定插值器,定义动画数值的进度变化规律
25 | * 3、指定估值器,根据插值器的进度变化规律,计算具体的动画数值
26 | * 4、系统自定调用控件的set方法,根据属性拼装set方法并反射调用,并将当前值作为参数传入
27 | *
28 | * @author zhangchaozhou
29 | * @email 13760289294@139.com
30 | * @wechat 13760289294
31 | */
32 | public class ObjectAnimatorActivity extends AppCompatActivity implements View.OnClickListener {
33 | private ImageView mIvBall;
34 |
35 | @Override
36 | protected void onCreate(@Nullable Bundle savedInstanceState) {
37 | super.onCreate(savedInstanceState);
38 | setContentView(R.layout.activity_object_animator);
39 | mIvBall = findViewById(R.id.iv_ball);
40 | mIvBall.setOnClickListener(this);
41 | }
42 |
43 | /**
44 | * 根据ImageView的setAlpha(int alpha)方法设置
45 | */
46 | public void alpha() {
47 | ObjectAnimator objectAnimator = ObjectAnimator.ofFloat(mIvBall, "alpha", 1, 0, 1);
48 | objectAnimator.setDuration(2000);
49 | objectAnimator.start();
50 | }
51 |
52 | /**
53 | * 通过View的setRotation(float rotation)方法设置
54 | * setRotationY(float rotationY)
55 | * setRotationX(float rotationX)
56 | */
57 | public void rotation() {
58 | ObjectAnimator objectAnimator = ObjectAnimator.ofFloat(mIvBall, "rotation", 0, 180, 0);
59 | objectAnimator.setDuration(2000);
60 | objectAnimator.start();
61 | }
62 |
63 | @Override
64 | public void onClick(View v) {
65 | switch (v.getId()) {
66 | case R.id.iv_ball:
67 | // alpha();
68 | rotation();
69 | break;
70 | default:
71 | break;
72 | }
73 | }
74 | }
75 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/property/value/FallingBallEvaluator.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.property.value;
2 |
3 | import android.animation.TypeEvaluator;
4 | import android.graphics.Point;
5 |
6 | /**
7 | * Created on 2020/8/15 15:56
8 | * 自定义估值器,一般与自定义View配合使用
9 | * @author zhangchaozhou
10 | * @email 13760289294@139.com
11 | * @wechat 13760289294
12 | */
13 | public class FallingBallEvaluator implements TypeEvaluator {
14 | private Point mPoint = new Point();
15 | @Override
16 | public Point evaluate(float fraction, Point startValue, Point endValue) {
17 | mPoint.x = (int)(startValue.x+fraction*(endValue.x-startValue.x));
18 | if (fraction*2<1){
19 | mPoint.y = (int) (startValue.y+fraction*2*(endValue.y-startValue.y));
20 | }else {
21 | mPoint.y = endValue.y;
22 | }
23 | return mPoint;
24 | }
25 | }
26 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/property/value/FallingBallValueActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.property.value;
2 |
3 | import android.animation.ValueAnimator;
4 | import android.graphics.Point;
5 | import android.os.Bundle;
6 | import android.view.View;
7 | import android.widget.ImageView;
8 |
9 | import androidstack.customview.R;
10 | import androidx.annotation.Nullable;
11 | import androidx.appcompat.app.AppCompatActivity;
12 |
13 | /**
14 | * Created on 2020/8/15 15:55
15 | *
16 | * @author zhangchaozhou
17 | * @email 13760289294@139.com
18 | * @wechat 13760289294
19 | */
20 | public class FallingBallValueActivity extends AppCompatActivity implements View.OnClickListener {
21 | private ImageView mIvBall;
22 | @Override
23 | protected void onCreate(@Nullable Bundle savedInstanceState) {
24 | super.onCreate(savedInstanceState);
25 | setContentView(R.layout.activity_falling_ball_value);
26 | mIvBall = findViewById(R.id.iv_ball);
27 | mIvBall.setOnClickListener(this);
28 | }
29 | private Point mPoint=null;
30 | @Override
31 | public void onClick(View v) {
32 | switch (v.getId()){
33 | case R.id.iv_ball:
34 | ValueAnimator animator = ValueAnimator.ofObject(new FallingBallEvaluator(),new Point(0,0),new Point(500,500));
35 | animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
36 | @Override
37 | public void onAnimationUpdate(ValueAnimator animation) {
38 | mPoint = (Point) animation.getAnimatedValue();
39 | mIvBall.layout(mPoint.x,mPoint.y,mPoint.x+mIvBall.getWidth(),mPoint.y+mIvBall.getHeight());
40 | }
41 | });
42 | animator.setDuration(2000);
43 | animator.start();
44 | break;
45 | default:
46 | break;
47 | }
48 | }
49 | }
50 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/property/value/LoadingImageView.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.property.value;
2 |
3 | import android.animation.Animator;
4 | import android.animation.ValueAnimator;
5 | import android.content.Context;
6 | import android.util.AttributeSet;
7 |
8 | import androidstack.customview.R;
9 | import androidstack.customview.animation.interpolator.ReverseInterpolator;
10 |
11 | /**
12 | * Created on 2020/8/14 20:29
13 | * 自定义加载ImageView
14 | *
15 | * @author zhangchaozhou
16 | * @email 13760289294@139.com
17 | * @wechat 13760289294
18 | */
19 | public class LoadingImageView extends androidx.appcompat.widget.AppCompatImageView {
20 | private int mTop;
21 | private int mCurrRepeatCount = 0;
22 | private int mImageCount = 3;
23 |
24 | public LoadingImageView(Context context) {
25 | this(context, null);
26 | }
27 |
28 | public LoadingImageView(Context context, AttributeSet attrs) {
29 | this(context, attrs, 0);
30 | }
31 |
32 | public LoadingImageView(Context context, AttributeSet attrs, int defStyleAttr) {
33 | super(context, attrs, defStyleAttr);
34 | initData();
35 | }
36 |
37 | private void initData() {
38 | ValueAnimator valueAnimator = ValueAnimator.ofInt(0, 100, 0);
39 | valueAnimator.setRepeatMode(ValueAnimator.REVERSE);
40 | valueAnimator.setRepeatCount(ValueAnimator.INFINITE);
41 | valueAnimator.setDuration(2000);
42 | valueAnimator.setInterpolator(new ReverseInterpolator());
43 | valueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
44 | @Override
45 | public void onAnimationUpdate(ValueAnimator animation) {
46 | int dy = (int) animation.getAnimatedValue();
47 | /**
48 | * 监听动画取值,根据取值改变空间的位置
49 | */
50 | setTop(mTop - dy);
51 | }
52 | });
53 | valueAnimator.addListener(new Animator.AnimatorListener() {
54 | @Override
55 | public void onAnimationStart(Animator animation) {
56 | setImageDrawable(getResources().getDrawable(R.mipmap.ic_test));
57 |
58 | }
59 |
60 | @Override
61 | public void onAnimationEnd(Animator animation) {
62 |
63 | }
64 |
65 | @Override
66 | public void onAnimationCancel(Animator animation) {
67 |
68 | }
69 |
70 | @Override
71 | public void onAnimationRepeat(Animator animation) {
72 | /**
73 | * 通过对动画的重复次数的监听,改变空间的图片资源
74 | */
75 | mCurrRepeatCount++;
76 | switch (mCurrRepeatCount % mImageCount) {
77 | case 0:
78 | setImageDrawable(getResources().getDrawable(R.mipmap.ic_test));
79 | break;
80 | case 1:
81 | setImageDrawable(getResources().getDrawable(R.mipmap.ic_loading));
82 | break;
83 | case 2:
84 | setImageDrawable(getResources().getDrawable(R.mipmap.ic_scanner));
85 | break;
86 | default:
87 | break;
88 | }
89 | }
90 | });
91 | valueAnimator.start();
92 |
93 | }
94 |
95 |
96 | @Override
97 | protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
98 | super.onLayout(changed, left, top, right, bottom);
99 | /**
100 | * 获取初始top
101 | */
102 | mTop = top;
103 | }
104 | }
105 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/view/ViewAnimationActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.view;
2 |
3 | import android.content.Intent;
4 | import android.os.Bundle;
5 | import android.view.View;
6 | import android.widget.Button;
7 |
8 | import androidstack.customview.R;
9 | import androidstack.customview.animation.view.frame.FrameAnimationActivity;
10 | import androidstack.customview.animation.view.tween.TweenAnimationActivity;
11 | import androidx.annotation.Nullable;
12 | import androidx.appcompat.app.AppCompatActivity;
13 |
14 | /**
15 | * Created on 2020/8/12 18:15
16 | *
17 | * @author zhangchaozhou
18 | * @email 13760289294@139.com
19 | * @wechat 13760289294
20 | */
21 | public class ViewAnimationActivity extends AppCompatActivity implements View.OnClickListener {
22 | private Button mBtnTween;
23 | private Button mBtnFrame;
24 |
25 | @Override
26 | protected void onCreate(@Nullable Bundle savedInstanceState) {
27 | super.onCreate(savedInstanceState);
28 | setContentView(R.layout.activity_view_animation);
29 | mBtnTween = findViewById(R.id.btn_tween_animation);
30 | mBtnTween.setOnClickListener(this);
31 |
32 | mBtnFrame = findViewById(R.id.btn_frame_animation);
33 | mBtnFrame.setOnClickListener(this);
34 | }
35 |
36 | @Override
37 | public void onClick(View v) {
38 | switch (v.getId()) {
39 | case R.id.btn_tween_animation:
40 | startActivity(new Intent(this, TweenAnimationActivity.class));
41 | break;
42 |
43 | case R.id.btn_frame_animation:
44 | startActivity(new Intent(this, FrameAnimationActivity.class));
45 | break;
46 | default:
47 | break;
48 | }
49 | }
50 | }
51 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/view/frame/FrameAnimationActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.view.frame;
2 |
3 | import android.graphics.drawable.AnimationDrawable;
4 | import android.graphics.drawable.Drawable;
5 | import android.os.Bundle;
6 | import android.widget.ImageView;
7 |
8 | import androidstack.customview.R;
9 | import androidx.annotation.Nullable;
10 | import androidx.appcompat.app.AppCompatActivity;
11 |
12 | /**
13 | * Created on 2020/8/12 18:15
14 | *
15 | * @author zhangchaozhou
16 | * @email 13760289294@139.com
17 | * @wechat 13760289294
18 | */
19 | public class FrameAnimationActivity extends AppCompatActivity {
20 |
21 | private ImageView mIvLoading;
22 |
23 | private ImageView mIvLoadingCode;
24 |
25 | @Override
26 | protected void onCreate(@Nullable Bundle savedInstanceState) {
27 | super.onCreate(savedInstanceState);
28 | setContentView(R.layout.activity_frame_animation);
29 | mIvLoading = findViewById(R.id.iv_loading);
30 | mIvLoadingCode = findViewById(R.id.iv_loading_code);
31 | codeAnimation();
32 | xmlAnimation();
33 | }
34 |
35 |
36 | /**
37 | * oneshot 表示是否只执行一次
38 | */
39 | public void codeAnimation() {
40 | int num = 10;
41 | AnimationDrawable animationDrawable = new AnimationDrawable();
42 | for (int i = 1; i <= num; i++) {
43 | int id = getResources().getIdentifier("loading_0" + i, "mipmap", getPackageName());
44 | Drawable drawable = getResources().getDrawable(id);
45 | animationDrawable.addFrame(drawable, 50);
46 | }
47 | animationDrawable.setOneShot(false);
48 | mIvLoadingCode.setBackgroundDrawable(animationDrawable);
49 | animationDrawable.start();
50 | }
51 |
52 |
53 | private void xmlAnimation() {
54 | AnimationDrawable animationDrawable = (AnimationDrawable) mIvLoading.getDrawable();
55 | animationDrawable.start();
56 | }
57 | }
58 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/view/tween/AlphaAnimationActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.view.tween;
2 |
3 | import android.os.Bundle;
4 | import android.view.View;
5 | import android.view.animation.AlphaAnimation;
6 | import android.view.animation.Animation;
7 | import android.view.animation.AnimationUtils;
8 | import android.widget.ImageView;
9 |
10 | import androidstack.customview.R;
11 | import androidx.annotation.Nullable;
12 | import androidx.appcompat.app.AppCompatActivity;
13 |
14 | /**
15 | * Created on 2020/8/12 18:06
16 | *
17 | * @author zhangchaozhou
18 | * @email 13760289294@139.com
19 | * @wechat 13760289294
20 | */
21 | public class AlphaAnimationActivity extends AppCompatActivity implements View.OnClickListener {
22 |
23 |
24 | private ImageView mIvTest;
25 |
26 | @Override
27 | protected void onCreate(@Nullable Bundle savedInstanceState) {
28 | super.onCreate(savedInstanceState);
29 | setContentView(R.layout.activity_alpha_animation);
30 | mIvTest = findViewById(R.id.iv_test);
31 | mIvTest.setOnClickListener(this);
32 | }
33 |
34 | private void codeAnimation() {
35 | AlphaAnimation alphaAnimation = new AlphaAnimation(1.0f,0.1f);
36 | alphaAnimation.setDuration(1000);
37 | alphaAnimation.setRepeatCount(Animation.INFINITE);
38 | alphaAnimation.setRepeatMode(Animation.REVERSE);
39 | mIvTest.startAnimation(alphaAnimation);
40 | }
41 |
42 | private void xmlAnimation() {
43 | Animation animation = AnimationUtils.loadAnimation(this, R.anim.alpha_test);
44 | mIvTest.startAnimation(animation);
45 | }
46 |
47 | /**
48 | *
54 | *
55 | * 动画开始时的透明度:0-1
56 | * 动画结束时的透明度:0-1
57 | *
58 | * @param v
59 | */
60 | @Override
61 | public void onClick(View v) {
62 | switch (v.getId()) {
63 | case R.id.iv_test:
64 | codeAnimation();
65 | // xmlAnimation();
66 | break;
67 | default:
68 | break;
69 | }
70 | }
71 |
72 | }
73 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/view/tween/RotateAnimationActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.view.tween;
2 |
3 | import android.os.Bundle;
4 | import android.view.View;
5 | import android.view.animation.Animation;
6 | import android.view.animation.AnimationUtils;
7 | import android.view.animation.RotateAnimation;
8 | import android.widget.ImageView;
9 |
10 | import androidstack.customview.R;
11 | import androidx.annotation.Nullable;
12 | import androidx.appcompat.app.AppCompatActivity;
13 |
14 | /**
15 | * Created on 2020/8/12 18:06
16 | *
17 | * @author zhangchaozhou
18 | * @email 13760289294@139.com
19 | * @wechat 13760289294
20 | */
21 | public class RotateAnimationActivity extends AppCompatActivity implements View.OnClickListener {
22 |
23 |
24 | private ImageView mIvTest;
25 |
26 | @Override
27 | protected void onCreate(@Nullable Bundle savedInstanceState) {
28 | super.onCreate(savedInstanceState);
29 | setContentView(R.layout.activity_rotate_animation);
30 | mIvTest = findViewById(R.id.iv_test);
31 | mIvTest.setOnClickListener(this);
32 | }
33 |
34 |
35 |
36 | private void codeAnimation(){
37 | RotateAnimation rotateAnimation = new RotateAnimation(90,-270,Animation.RELATIVE_TO_SELF,0.5f,Animation.RELATIVE_TO_SELF,0.5f);
38 | rotateAnimation.setDuration(1000);
39 | rotateAnimation.setRepeatCount(Animation.INFINITE);
40 | rotateAnimation.setRepeatMode(Animation.REVERSE);
41 | mIvTest.startAnimation(rotateAnimation);
42 | }
43 | private void xmlAnimation() {
44 | Animation animation = AnimationUtils.loadAnimation(this, R.anim.rotate_test);
45 | mIvTest.startAnimation(animation);
46 | }
47 | /**
48 | *
59 | *
60 | * 动画开始旋转时的角度位置:正数顺时针,负数逆时针
61 | * 动画结束旋转时的角度位置:正数顺时针,负数逆时针
62 | *
63 | * @param v
64 | */
65 | @Override
66 | public void onClick(View v) {
67 | switch (v.getId()) {
68 | case R.id.iv_test:
69 | codeAnimation();
70 | // xmlAnimation();
71 | break;
72 | default:
73 | break;
74 | }
75 | }
76 |
77 | }
78 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/view/tween/ScaleAnimationActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.view.tween;
2 |
3 | import android.os.Bundle;
4 | import android.view.View;
5 | import android.view.animation.AccelerateInterpolator;
6 | import android.view.animation.Animation;
7 | import android.view.animation.AnimationUtils;
8 | import android.view.animation.ScaleAnimation;
9 | import android.widget.ImageView;
10 |
11 | import androidstack.customview.R;
12 | import androidx.annotation.Nullable;
13 | import androidx.appcompat.app.AppCompatActivity;
14 |
15 | /**
16 | * Created on 2020/8/12 17:43
17 | * pivot:枢轴 中心点
18 | *
19 | * @author zhangchaozhou
20 | * @email 13760289294@139.com
21 | * @wechat 13760289294
22 | */
23 | public class ScaleAnimationActivity extends AppCompatActivity implements View.OnClickListener {
24 |
25 | private ImageView mIvTest;
26 |
27 | @Override
28 | protected void onCreate(@Nullable Bundle savedInstanceState) {
29 | super.onCreate(savedInstanceState);
30 | setContentView(R.layout.activity_scale_animation);
31 | mIvTest = findViewById(R.id.iv_test);
32 | mIvTest.setOnClickListener(this);
33 | }
34 |
35 |
36 | private void codeAnimation() {
37 | ScaleAnimation scaleAnimation = new ScaleAnimation(1.5f,0.5f,1.5f,0.5f,Animation.RELATIVE_TO_SELF,0.5f,Animation.RELATIVE_TO_SELF,0.5f);
38 | scaleAnimation.setDuration(1000);
39 | scaleAnimation.setFillAfter(true);
40 | scaleAnimation.setFillBefore(false);
41 | scaleAnimation.setFillEnabled(false);
42 | scaleAnimation.setRepeatCount(Animation.INFINITE);
43 | scaleAnimation.setRepeatMode(Animation.REVERSE);
44 | scaleAnimation.setInterpolator(new AccelerateInterpolator());
45 | mIvTest.startAnimation(scaleAnimation);
46 | }
47 |
48 | private void xmlAnimation() {
49 | Animation animation = AnimationUtils.loadAnimation(this, R.anim.scale_test);
50 | mIvTest.startAnimation(animation);
51 | }
52 |
53 | /**
54 | *
68 | *
69 | * 完成一次动画的持续时间,单位毫秒
70 | * 动画结束后,停留在结束时的状态
71 | * 动画结束后,回到开始前的状态
72 | * 动画结束后,回到开始前的状态
73 | * 动画开始时空间在X轴相对自身的缩放比例
74 | * 动画开始时空间在Y轴相对自身的缩放比例
75 | * 插值器:指定动画效果
76 | * 缩放起始点X轴坐标:以当前控件的左上角为原点加上:数值、百分数(自身宽度的百分数)、百分数p(父控件宽度的百分数)
77 | * 缩放起始点Y轴坐标:以当前控件的左上角为原点加上:数值、百分数(自身高度的百分数)、百分数p(父控件高度的百分数)
78 | * 重复次数:infinite为无限循环
79 | * 重复模式:reverse为倒序回放;restart为重放,且必须与repeatCount一起使用
80 | * 动画结束时空间在X轴相对自身的缩放比例
81 | * 动画结束时空间在Y轴相对自身的缩放比例
82 | *
83 | * @param v
84 | */
85 | @Override
86 | public void onClick(View v) {
87 | switch (v.getId()) {
88 | case R.id.iv_test:
89 | codeAnimation();
90 | // xmlAnimation();
91 | break;
92 | default:
93 | break;
94 | }
95 | }
96 |
97 |
98 |
99 |
100 | }
101 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/view/tween/TranslateAnimationActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.view.tween;
2 |
3 | import android.os.Bundle;
4 | import android.view.View;
5 | import android.view.animation.Animation;
6 | import android.view.animation.AnimationUtils;
7 | import android.view.animation.TranslateAnimation;
8 | import android.widget.ImageView;
9 |
10 | import androidstack.customview.R;
11 | import androidx.annotation.Nullable;
12 | import androidx.appcompat.app.AppCompatActivity;
13 |
14 | /**
15 | * Created on 2020/8/12 17:43
16 | *
17 | * @author zhangchaozhou
18 | * @email 13760289294@139.com
19 | * @wechat 13760289294
20 | */
21 | public class TranslateAnimationActivity extends AppCompatActivity implements View.OnClickListener {
22 |
23 | private ImageView mIvTest;
24 |
25 | @Override
26 | protected void onCreate(@Nullable Bundle savedInstanceState) {
27 | super.onCreate(savedInstanceState);
28 | setContentView(R.layout.activity_translate_animation);
29 | mIvTest = findViewById(R.id.iv_test);
30 | mIvTest.setOnClickListener(this);
31 | }
32 |
33 |
34 | private void codeAnimation() {
35 | TranslateAnimation translateAnimation = new TranslateAnimation(Animation.RELATIVE_TO_SELF, 0.1f, Animation.RELATIVE_TO_SELF, 1.0f, Animation.RELATIVE_TO_SELF, 0.1f, Animation.RELATIVE_TO_SELF, 1.0f);
36 | translateAnimation.setDuration(1000);
37 | translateAnimation.setRepeatCount(Animation.INFINITE);
38 | translateAnimation.setRepeatMode(Animation.REVERSE);
39 | mIvTest.startAnimation(translateAnimation);
40 | }
41 |
42 | private void xmlAnimation() {
43 | Animation animation = AnimationUtils.loadAnimation(this, R.anim.translate_test);
44 | mIvTest.startAnimation(animation);
45 | }
46 |
47 |
48 | /**
49 | *
58 | *
59 | * 起始点X轴坐标
60 | * 起始点Y轴坐标
61 | * 结束点X轴坐标
62 | * 结束点Y轴坐标
63 | *
64 | * @param v
65 | */
66 | @Override
67 | public void onClick(View v) {
68 | switch (v.getId()) {
69 | case R.id.iv_test:
70 | codeAnimation();
71 | // xmlAnimation();
72 | break;
73 | default:
74 | break;
75 | }
76 | }
77 |
78 |
79 | }
80 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/view/tween/TweenAnimationActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.view.tween;
2 |
3 | import android.content.Intent;
4 | import android.os.Bundle;
5 | import android.view.View;
6 | import android.widget.Button;
7 |
8 | import androidstack.customview.R;
9 | import androidstack.customview.animation.view.tween.effect.CameraActivity;
10 | import androidstack.customview.animation.view.tween.effect.LoadingActivity;
11 | import androidstack.customview.animation.view.tween.effect.ScannerActivity;
12 | import androidx.annotation.Nullable;
13 | import androidx.appcompat.app.AppCompatActivity;
14 |
15 | /**
16 | * Created on 2020/8/12 18:12
17 | *
18 | * @author zhangchaozhou
19 | * @email 13760289294@139.com
20 | * @wechat 13760289294
21 | */
22 | public class TweenAnimationActivity extends AppCompatActivity implements View.OnClickListener {
23 |
24 | private Button mBtnScale;
25 | private Button mBtnAlpha;
26 | private Button mBtnTranslate;
27 | private Button mBtnRotate;
28 | private Button mBtnSet;
29 | private Button mBtnCamera;
30 | private Button mBtnLoading;
31 | private Button mBtnScanner;
32 | @Override
33 | protected void onCreate(@Nullable Bundle savedInstanceState) {
34 | super.onCreate(savedInstanceState);
35 | setContentView(R.layout.activity_tween_animation);
36 | mBtnScale = findViewById(R.id.btn_scale_animation);
37 | mBtnScale.setOnClickListener(this);
38 | mBtnAlpha = findViewById(R.id.btn_alpha_animation);
39 | mBtnAlpha.setOnClickListener(this);
40 | mBtnTranslate = findViewById(R.id.btn_translate_animation);
41 | mBtnTranslate.setOnClickListener(this);
42 | mBtnRotate = findViewById(R.id.btn_rotate_animation);
43 | mBtnRotate.setOnClickListener(this);
44 | mBtnSet = findViewById(R.id.btn_set_animation);
45 | mBtnSet.setOnClickListener(this);
46 | mBtnCamera = findViewById(R.id.btn_camera);
47 | mBtnCamera.setOnClickListener(this);
48 | mBtnLoading = findViewById(R.id.btn_loading);
49 | mBtnLoading.setOnClickListener(this);
50 | mBtnScanner = findViewById(R.id.btn_scanner);
51 | mBtnScanner.setOnClickListener(this);
52 | }
53 |
54 | @Override
55 | public void onClick(View v) {
56 | switch (v.getId()){
57 | case R.id.btn_scale_animation:
58 | startActivity(new Intent(this,ScaleAnimationActivity.class));
59 | break;
60 | case R.id.btn_alpha_animation:
61 | startActivity(new Intent(this,AlphaAnimationActivity.class));
62 | break;
63 | case R.id.btn_translate_animation:
64 | startActivity(new Intent(this,TranslateAnimationActivity.class));
65 | break;
66 | case R.id.btn_rotate_animation:
67 | startActivity(new Intent(this,RotateAnimationActivity.class));
68 | break;
69 | case R.id.btn_set_animation:
70 | startActivity(new Intent(this,SetAnimationActivity.class));
71 | break;
72 | case R.id.btn_camera:
73 | startActivity(new Intent(this, CameraActivity.class));
74 | break;
75 | case R.id.btn_loading:
76 | startActivity(new Intent(this, LoadingActivity.class));
77 | break;
78 |
79 | case R.id.btn_scanner:
80 | startActivity(new Intent(this, ScannerActivity.class));
81 | break;
82 | default:
83 | break;
84 | }
85 | }
86 | }
87 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/view/tween/effect/CameraActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.view.tween.effect;
2 |
3 | import android.os.Bundle;
4 | import android.view.View;
5 | import android.view.animation.Animation;
6 | import android.view.animation.BounceInterpolator;
7 | import android.view.animation.ScaleAnimation;
8 | import android.widget.ImageView;
9 |
10 | import androidstack.customview.R;
11 | import androidx.annotation.Nullable;
12 | import androidx.appcompat.app.AppCompatActivity;
13 |
14 | /**
15 | * Created on 2020/8/13 12:56
16 | *
17 | * @author zhangchaozhou
18 | * @email 13760289294@139.com
19 | * @wechat 13760289294
20 | */
21 | public class CameraActivity extends AppCompatActivity implements View.OnClickListener {
22 | private ImageView mIvTest;
23 | @Override
24 | protected void onCreate(@Nullable Bundle savedInstanceState) {
25 | super.onCreate(savedInstanceState);
26 | setContentView(R.layout.activity_camera);
27 | mIvTest = findViewById(R.id.iv_test);
28 | mIvTest.setOnClickListener(this);
29 | }
30 |
31 | @Override
32 | public void onClick(View v) {
33 | switch (v.getId()){
34 | case R.id.iv_test:
35 | ScaleAnimation scaleAnimation = new ScaleAnimation(1.0f,1.2f,1.0f,1.2f, Animation.RELATIVE_TO_SELF,0.5f,Animation.RELATIVE_TO_SELF,0.5f);
36 | scaleAnimation.setDuration(6000);
37 | scaleAnimation.setFillAfter(true);
38 | scaleAnimation.setInterpolator(new BounceInterpolator());
39 | mIvTest.startAnimation(scaleAnimation);
40 | break;
41 | default:
42 | break;
43 | }
44 | }
45 | }
46 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/view/tween/effect/LoadingActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.view.tween.effect;
2 |
3 | import android.os.Bundle;
4 | import android.view.View;
5 | import android.view.animation.Animation;
6 | import android.view.animation.LinearInterpolator;
7 | import android.view.animation.RotateAnimation;
8 | import android.widget.ImageView;
9 |
10 | import androidstack.customview.R;
11 | import androidx.annotation.Nullable;
12 | import androidx.appcompat.app.AppCompatActivity;
13 |
14 | /**
15 | * Created on 2020/8/13 13:12
16 | *
17 | * @author zhangchaozhou
18 | * @email 13760289294@139.com
19 | * @wechat 13760289294
20 | */
21 | public class LoadingActivity extends AppCompatActivity implements View.OnClickListener {
22 | private ImageView mIvTest;
23 |
24 | @Override
25 | protected void onCreate(@Nullable Bundle savedInstanceState) {
26 | super.onCreate(savedInstanceState);
27 | setContentView(R.layout.activity_loading);
28 | mIvTest = findViewById(R.id.iv_test);
29 | mIvTest.setOnClickListener(this);
30 | }
31 |
32 |
33 |
34 | private void codeAnimation(){
35 | RotateAnimation rotateAnimation = new RotateAnimation(0,360, Animation.RELATIVE_TO_SELF,0.5f,Animation.RELATIVE_TO_SELF,0.5f);
36 | rotateAnimation.setDuration(2000);
37 | rotateAnimation.setRepeatCount(Animation.INFINITE);
38 | rotateAnimation.setInterpolator(new LinearInterpolator());
39 | mIvTest.startAnimation(rotateAnimation);
40 | }
41 |
42 |
43 | @Override
44 | public void onClick(View v) {
45 | switch (v.getId()) {
46 | case R.id.iv_test:
47 | codeAnimation();
48 | break;
49 | default:
50 | break;
51 | }
52 | }
53 | }
54 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/animation/view/tween/effect/ScannerActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.animation.view.tween.effect;
2 |
3 | import android.os.Bundle;
4 | import android.view.View;
5 | import android.view.animation.Animation;
6 | import android.view.animation.AnimationUtils;
7 | import android.widget.ImageView;
8 |
9 | import androidstack.customview.R;
10 | import androidx.annotation.Nullable;
11 | import androidx.appcompat.app.AppCompatActivity;
12 |
13 | /**
14 | * Created on 2020/8/13 13:23
15 | *
16 | * @author zhangchaozhou
17 | * @email 13760289294@139.com
18 | * @wechat 13760289294
19 | */
20 | public class ScannerActivity extends AppCompatActivity implements View.OnClickListener {
21 | private View mIv1;
22 | private View mIv2;
23 | private View mIv3;
24 | private View mIv4;
25 | private ImageView mIvScanner;
26 |
27 | @Override
28 | protected void onCreate(@Nullable Bundle savedInstanceState) {
29 | super.onCreate(savedInstanceState);
30 | setContentView(R.layout.activity_music);
31 | mIv1 = findViewById(R.id.iv_1);
32 | mIv2 = findViewById(R.id.iv_2);
33 | mIv3 = findViewById(R.id.iv_3);
34 | mIv4 = findViewById(R.id.iv_4);
35 | mIvScanner = findViewById(R.id.iv_scanner);
36 | mIvScanner.setOnClickListener(this);
37 |
38 |
39 | }
40 |
41 | @Override
42 | public void onClick(View v) {
43 | switch (v.getId()){
44 | case R.id.iv_scanner:
45 |
46 | Animation animation1 = AnimationUtils.loadAnimation(this,R.anim.set_sanner);
47 | Animation animation2 = AnimationUtils.loadAnimation(this,R.anim.set_sanner);
48 | Animation animation3 = AnimationUtils.loadAnimation(this,R.anim.set_sanner);
49 | Animation animation4 = AnimationUtils.loadAnimation(this,R.anim.set_sanner);
50 | mIv1.startAnimation(animation1);
51 | animation2.setStartOffset(600);
52 | mIv2.startAnimation(animation2);
53 |
54 | animation3.setStartOffset(1200);
55 | mIv3.startAnimation(animation3);
56 |
57 | animation4.setStartOffset(1800);
58 | mIv4.startAnimation(animation4);
59 | break;
60 | default:
61 | break;
62 | }
63 | }
64 | }
65 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/custom/CustomProgressActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.custom;
2 |
3 | import android.graphics.Color;
4 | import android.os.Bundle;
5 |
6 | import androidstack.customview.R;
7 | import androidstack.customview.view.CustomProgressView;
8 | import androidx.annotation.Nullable;
9 | import androidx.appcompat.app.AppCompatActivity;
10 |
11 | /**
12 | * Created on 2020/8/13 23:44
13 | *
14 | * @author zhangchaozhou
15 | * @email 13760289294@139.com
16 | * @wechat 13760289294
17 | */
18 | public class CustomProgressActivity extends AppCompatActivity {
19 |
20 | private CustomProgressView mCustomProgressView;
21 | @Override
22 | protected void onCreate(@Nullable Bundle savedInstanceState) {
23 | super.onCreate(savedInstanceState);
24 | setContentView(R.layout.activity_custom_progress);
25 |
26 | mCustomProgressView = findViewById(R.id.cpv);
27 | mCustomProgressView.setProgressMax(100);
28 | mCustomProgressView.setCpBackgroundColor(Color.parseColor("#FFF3F3"));
29 | mCustomProgressView.setCpPercentTextcolor(Color.parseColor("#666666"));
30 | mCustomProgressView.setCpProgressColor(Color.parseColor("#FEC7CD"));
31 | mCustomProgressView.setProgressCurrent(40);
32 | mCustomProgressView.setCpBackgroundIsStroke(false);
33 | mCustomProgressView.setCpPercentTextsize(40);
34 | }
35 | }
36 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/drawing/PaintActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.drawing;
2 |
3 | import android.os.Bundle;
4 |
5 | import androidstack.customview.R;
6 | import androidx.annotation.Nullable;
7 | import androidx.appcompat.app.AppCompatActivity;
8 |
9 | /**
10 | * Created on 2020/8/19 23:08
11 | *
12 | * @author zhangchaozhou
13 | * @email 13760289294@139.com
14 | * @wechat 13760289294
15 | */
16 | public class PaintActivity extends AppCompatActivity {
17 | @Override
18 | protected void onCreate(@Nullable Bundle savedInstanceState) {
19 | super.onCreate(savedInstanceState);
20 | setContentView(R.layout.activity_paint);
21 | }
22 | /**
23 | * 硬件加速:GPU 图形处理器,全称Graphic Processing Unit,专门处理多媒体的计算、存储任务。
24 | * Android11之前没有GPU硬件加速;
25 | * Android11-13:有GPU硬件加速,但是默认关闭;
26 | * Android14开始:默认开启硬件加速。
27 | */
28 |
29 |
30 |
31 | }
32 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/drawing/matrix/MatrixActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.drawing.matrix;
2 |
3 | import android.os.Bundle;
4 |
5 | import androidstack.customview.R;
6 | import androidx.annotation.Nullable;
7 | import androidx.appcompat.app.AppCompatActivity;
8 |
9 | /**
10 | * Created on 2020/8/18 18:09
11 | *
12 | * @author zhangchaozhou
13 | * @email 13760289294@139.com
14 | * @wechat 13760289294
15 | */
16 | public class MatrixActivity extends AppCompatActivity {
17 | @Override
18 | protected void onCreate(@Nullable Bundle savedInstanceState) {
19 | super.onCreate(savedInstanceState);
20 | setContentView(R.layout.activity_matrix);
21 | }
22 | }
23 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/rv/layoutmanager/CardActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.rv.layoutmanager;
2 |
3 | import android.os.Bundle;
4 | import android.view.LayoutInflater;
5 | import android.view.View;
6 | import android.view.ViewGroup;
7 | import android.widget.TextView;
8 | import android.widget.Toast;
9 |
10 | import androidx.appcompat.app.AppCompatActivity;
11 | import androidx.recyclerview.widget.RecyclerView;
12 |
13 | import java.util.Random;
14 |
15 | import androidstack.customview.R;
16 |
17 | public class CardActivity extends AppCompatActivity {
18 |
19 | private static final int[] COLORS = {0xff00FFFF, 0xffDEB887, 0xff5F9EA0,
20 | 0xff7FFF00, 0xff6495ED, 0xffDC143C,
21 | 0xff008B8B, 0xff006400, 0xff2F4F4F,
22 | 0xffFF69B4, 0xffFF00FF, 0xffCD5C5C,
23 | 0xff90EE90, 0xff87CEFA, 0xff800000};
24 |
25 | private RecyclerView mRecyclerView;
26 | private Adapter mAdapter = new Adapter();
27 |
28 | private int mCount = 50;
29 | private int mGroupSize = 3;
30 |
31 | @Override
32 | protected void onCreate(Bundle savedInstanceState) {
33 | super.onCreate(savedInstanceState);
34 | setContentView(R.layout.activity_card);
35 | mRecyclerView = (RecyclerView) findViewById(R.id.list);
36 | init();
37 | }
38 |
39 | private void init() {
40 | mRecyclerView.setLayoutManager(new CardLayoutManager(mGroupSize, true));
41 | mRecyclerView.setAdapter(mAdapter);
42 | }
43 |
44 | public void add(View view) {
45 | mCount += 10;
46 | mAdapter.notifyDataSetChanged();
47 | }
48 |
49 | public void change(View view) {
50 | if (mGroupSize == 3) { mGroupSize = 9;}
51 | else { mGroupSize = 3;}
52 | init();
53 | }
54 |
55 | class Adapter extends RecyclerView.Adapter {
56 |
57 | @Override
58 | public Holder onCreateViewHolder(ViewGroup parent, int viewType) {
59 | View item = LayoutInflater.from(parent.getContext())
60 | .inflate(R.layout.item, parent, false);
61 | return new Holder(item);
62 | }
63 |
64 | @Override
65 | public void onBindViewHolder(final Holder holder, final int position) {
66 | // holder.item.setText("" + position);
67 | holder.item.setCardColor(randomColor());
68 | holder.text.setText("菜单" + position);
69 | holder.item.setOnClickListener(new View.OnClickListener() {
70 | @Override
71 | public void onClick(View view) {
72 | Toast.makeText(CardActivity.this, holder.text.getText(), Toast.LENGTH_SHORT).show();
73 | }
74 | });
75 | }
76 |
77 | @Override
78 | public int getItemCount() {
79 | return mCount;
80 | }
81 |
82 | private int randomColor() {
83 | return COLORS[new Random().nextInt(COLORS.length)];
84 | }
85 |
86 | class Holder extends RecyclerView.ViewHolder {
87 | CardItemView item;
88 | TextView text;
89 | public Holder(View itemView) {
90 | super(itemView);
91 | item = (CardItemView) itemView.findViewById(R.id.item);
92 | text = (TextView) itemView.findViewById(R.id.text);
93 | }
94 | }
95 | }
96 | }
97 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/rv/layoutmanager/CardItemView.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.rv.layoutmanager;
2 |
3 | import android.content.Context;
4 | import android.content.res.TypedArray;
5 | import android.graphics.Canvas;
6 | import android.graphics.Color;
7 | import android.graphics.Paint;
8 | import android.graphics.Path;
9 | import android.graphics.RectF;
10 | import android.graphics.Region;
11 | import android.util.AttributeSet;
12 | import android.view.MotionEvent;
13 | import android.view.View;
14 |
15 | import androidstack.customview.R;
16 |
17 | /**
18 | * Created by qibin on 16-9-26.
19 | */
20 |
21 | public class CardItemView extends View {
22 |
23 | private int mSize;
24 | private Paint mPaint;
25 | private Path mDrawPath;
26 | private Region mRegion;
27 |
28 | public CardItemView(Context context) {
29 | this(context, null, 0);
30 | }
31 |
32 | public CardItemView(Context context, AttributeSet attrs) {
33 | this(context, attrs, 0);
34 | }
35 |
36 | public CardItemView(Context context, AttributeSet attrs, int defStyleAttr) {
37 | super(context, attrs, defStyleAttr);
38 | mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
39 | mPaint.setStyle(Paint.Style.FILL);
40 | TypedArray ta = context.obtainStyledAttributes(attrs, R.styleable.Card, defStyleAttr, 0);
41 | mSize = ta.getDimensionPixelSize(R.styleable.Card_size, 10);
42 | mPaint.setColor(ta.getColor(R.styleable.Card_bgColor, 0));
43 | ta.recycle();
44 |
45 | mRegion = new Region();
46 | mDrawPath = new Path();
47 |
48 | mDrawPath.moveTo(0, mSize / 2);
49 | mDrawPath.lineTo(mSize / 2, 0);
50 | mDrawPath.lineTo(mSize, mSize / 2);
51 | mDrawPath.lineTo(mSize / 2, mSize);
52 | mDrawPath.close();
53 | }
54 |
55 | @Override
56 | protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
57 | setMeasuredDimension(mSize, mSize);
58 | }
59 |
60 | @Override
61 | public boolean dispatchTouchEvent(MotionEvent event) {
62 | if (event.getAction() == MotionEvent.ACTION_DOWN) {
63 | if (!isEventInPath(event)) { return false;}
64 | }
65 |
66 | return super.dispatchTouchEvent(event);
67 | }
68 |
69 | private boolean isEventInPath(MotionEvent event) {
70 | RectF bounds = new RectF();
71 | mDrawPath.computeBounds(bounds, true);
72 | mRegion.setPath(mDrawPath, new Region((int)bounds.left,
73 | (int)bounds.top, (int)bounds.right, (int)bounds.bottom));
74 | return mRegion.contains((int) event.getX(), (int) event.getY());
75 | }
76 |
77 | @Override
78 | protected void onDraw(Canvas canvas) {
79 | canvas.drawColor(Color.TRANSPARENT);
80 | canvas.drawPath(mDrawPath, mPaint);
81 | }
82 |
83 | public void setCardColor(int color) {
84 | mPaint.setColor(color);
85 | invalidate();
86 | }
87 | }
88 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/rv/layoutmanager/Pool.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.rv.layoutmanager;
2 |
3 |
4 | import androidx.collection.SparseArrayCompat;
5 |
6 | /**
7 | * Created by qibin on 16-9-25.
8 | */
9 |
10 | public class Pool {
11 | private SparseArrayCompat mPool;
12 | private New mNewInstance;
13 |
14 | public Pool(New newInstance) {
15 | mPool = new SparseArrayCompat<>();
16 | mNewInstance = newInstance;
17 | }
18 |
19 | public T get(int key) {
20 | T res = mPool.get(key);
21 | if (res == null) {
22 | res = mNewInstance.get();
23 | mPool.put(key, res);
24 | }
25 | return res;
26 | }
27 |
28 | public interface New {
29 | T get();
30 | }
31 | }
32 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/rv/partrv/PartRvActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.rv.partrv;
2 |
3 | import android.os.Bundle;
4 |
5 | import androidx.annotation.Nullable;
6 | import androidx.appcompat.app.AppCompatActivity;
7 | import androidx.recyclerview.widget.GridLayoutManager;
8 | import androidx.recyclerview.widget.RecyclerView;
9 |
10 | import java.util.ArrayList;
11 | import java.util.List;
12 |
13 | import androidstack.customview.R;
14 |
15 | public class PartRvActivity extends AppCompatActivity {
16 |
17 |
18 |
19 | private PartRvAdapter mPartRvAdapter;
20 | private RecyclerView mRvPart;
21 | private RecyclerView mRvPart1;
22 | private RecyclerView mRvPart2;
23 | private List mParts;
24 | @Override
25 | protected void onCreate(@Nullable Bundle savedInstanceState) {
26 | super.onCreate(savedInstanceState);
27 | setContentView(R.layout.activity_part_rv);
28 | mRvPart = findViewById(R.id.rv_part);
29 | mRvPart1 = findViewById(R.id.rv_part_1);
30 | mRvPart2 = findViewById(R.id.rv_part_2);
31 |
32 | mPartRvAdapter = new PartRvAdapter(this);
33 |
34 | mParts = new ArrayList<>();
35 | for (int i=0;i<20;i++){
36 | mParts.add(getString(R.string.app_name)+" - "+i);
37 | }
38 |
39 | mPartRvAdapter.setParts(mParts);
40 | GridLayoutManager gridLayoutManager = new GridLayoutManager(this,5);
41 | gridLayoutManager.setOrientation(RecyclerView.HORIZONTAL);
42 |
43 | GridLayoutManager gridLayoutManager1 = new GridLayoutManager(this,5);
44 | gridLayoutManager1.setOrientation(RecyclerView.HORIZONTAL);
45 |
46 |
47 | GridLayoutManager gridLayoutManager2 = new GridLayoutManager(this,5);
48 | gridLayoutManager2.setOrientation(RecyclerView.HORIZONTAL);
49 |
50 | mRvPart.setHasFixedSize(true);
51 | mRvPart1.setHasFixedSize(true);
52 | mRvPart2.setHasFixedSize(true);
53 | mRvPart.setLayoutManager(gridLayoutManager);
54 | mRvPart1.setLayoutManager(gridLayoutManager1);
55 | mRvPart2.setLayoutManager(gridLayoutManager2);
56 | mRvPart.setAdapter(mPartRvAdapter);
57 | mRvPart1.setAdapter(mPartRvAdapter);
58 | mRvPart2.setAdapter(mPartRvAdapter);
59 |
60 | }
61 | }
62 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/rv/partrv/PartRvAdapter.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.rv.partrv;
2 |
3 | import android.content.Context;
4 | import android.view.LayoutInflater;
5 | import android.view.View;
6 | import android.view.ViewGroup;
7 | import android.widget.TextView;
8 |
9 | import androidx.annotation.NonNull;
10 | import androidx.recyclerview.widget.RecyclerView;
11 |
12 | import java.util.List;
13 |
14 | import androidstack.customview.R;
15 |
16 | public class PartRvAdapter extends RecyclerView.Adapter {
17 |
18 |
19 | private List mParts;
20 |
21 |
22 | private Context mContext;
23 |
24 | public PartRvAdapter(Context mContext) {
25 | this.mContext = mContext;
26 | }
27 |
28 | public void setParts(List parts) {
29 | this.mParts = parts;
30 | }
31 |
32 | @NonNull
33 | @Override
34 | public PartRvHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
35 | View view = LayoutInflater.from(mContext).inflate(R.layout.item_part_rv, parent, false);
36 | return new PartRvHolder(view);
37 | }
38 |
39 | @Override
40 | public void onBindViewHolder(@NonNull PartRvHolder holder, int position) {
41 | holder.textView.setText(mParts.get(position));
42 | }
43 |
44 | @Override
45 | public int getItemCount() {
46 | return mParts == null ? 0 : mParts.size();
47 | }
48 |
49 | class PartRvHolder extends RecyclerView.ViewHolder {
50 |
51 | private TextView textView;
52 |
53 | public PartRvHolder(@NonNull View itemView) {
54 | super(itemView);
55 | textView = itemView.findViewById(R.id.tv_part_rv);
56 | }
57 | }
58 | }
59 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/svg/SvgActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.svg;
2 |
3 | import android.graphics.drawable.Animatable;
4 | import android.graphics.drawable.AnimatedVectorDrawable;
5 | import android.os.Build;
6 | import android.os.Bundle;
7 | import android.widget.ImageView;
8 |
9 | import androidstack.customview.R;
10 | import androidx.annotation.Nullable;
11 | import androidx.annotation.RequiresApi;
12 | import androidx.appcompat.app.AppCompatActivity;
13 | import androidx.vectordrawable.graphics.drawable.AnimatedVectorDrawableCompat;
14 |
15 | /**
16 | * Created on 2020/8/17 10:09
17 | *
18 | * SVG 可缩放矢量图形 Scalable Vector Graphics:
19 | * 经过数学计算利用直线和曲线绘制而成,无论怎么放大,都不会出现马赛克现象。
20 | * illustrator:矢量图绘图软件。
21 | *
22 | * Bitmap 位图:
23 | * 由一个个像素点组成,放大后会出现马赛克。
24 | * PhotoShop:位图绘图软件。
25 | *
26 | * SVG优势:
27 | * 使用xml格式定义图形,读取和修改的工具多。
28 | * 不会失真,无需根据分辨率适配多套图标。
29 | * 占用空间小。
30 | * 可以转换为Path路径,与Path动画相结合,形成更丰富的动画。
31 | *
32 | * SVG标签:
33 | * rect 矩形
34 | * circle 圆形
35 | * line 线段
36 | * polyline 折线段
37 | * ellipse 椭圆
38 | * polygon 多边形
39 | * path 路径
40 | *
41 | * https://editor.method.ac/
42 | * 制作 SVG 图像。
43 | *
44 | * http://www.iconfont.cn/
45 | * Iconfont是一种比较成熟的 SVG 解决方案,它的原理是:
46 | * 把矢量图标打包成一个.ttf文件,在 Android 中应用这个.ttf文件来方便地加载和指定各种图标。
47 | *
48 | * http://inloop.github.io/svg2android/
49 | * SVG转vector
50 | *
51 | * Android Studio-File-New-Vector Asset-Local File-RTL
52 | * SVG转vector:ic_love.xml
53 | *
54 | * trimPathStart 属性表示截掉 从起点到某个位置的部分,保留剩下的部分;
55 | * trimPathEnd 属性表示截掉 从某个位置到终点的部分,保留剩下的部分。
56 | *
57 | * @author zhangchaozhou
58 | * @email 13760289294@139.com
59 | * @wechat 13760289294
60 | */
61 | public class SvgActivity extends AppCompatActivity {
62 |
63 | private ImageView mIvSvgVectorAnimation;
64 |
65 | @Override
66 | protected void onCreate(@Nullable Bundle savedInstanceState) {
67 | super.onCreate(savedInstanceState);
68 | setContentView(R.layout.activity_svg);
69 | mIvSvgVectorAnimation = findViewById(R.id.iv_svg_vector_animation);
70 | start1();
71 | // start2();
72 | }
73 |
74 | private void start1() {
75 | AnimatedVectorDrawableCompat animatedVectorDrawableCompat = AnimatedVectorDrawableCompat.create(
76 | this, R.drawable.ic_logo
77 | );
78 | mIvSvgVectorAnimation.setImageDrawable(animatedVectorDrawableCompat);
79 | ((Animatable) mIvSvgVectorAnimation.getDrawable()).start();
80 | }
81 |
82 | @RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
83 | private void start2() {
84 | AnimatedVectorDrawable anim =
85 | (AnimatedVectorDrawable) getResources().getDrawable(R.drawable.ic_logo);
86 | mIvSvgVectorAnimation.setImageDrawable(anim);
87 | anim.start();
88 |
89 | }
90 | }
91 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/svg/lottie/LottieActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.svg.lottie;
2 |
3 | import android.os.Bundle;
4 |
5 | import com.airbnb.lottie.LottieAnimationView;
6 |
7 | import androidstack.customview.R;
8 | import androidx.annotation.Nullable;
9 | import androidx.appcompat.app.AppCompatActivity;
10 |
11 | import static com.airbnb.lottie.LottieDrawable.INFINITE;
12 |
13 | /**
14 | * Created on 2020/8/17 10:11
15 | *
16 | * @author zhangchaozhou
17 | * @email 13760289294@139.com
18 | * @wechat 13760289294
19 | */
20 | public class LottieActivity extends AppCompatActivity {
21 |
22 |
23 | private LottieAnimationView mLavGift;
24 | private LottieAnimationView mLavTest;
25 |
26 |
27 | @Override
28 | protected void onCreate(@Nullable Bundle savedInstanceState) {
29 | super.onCreate(savedInstanceState);
30 | setContentView(R.layout.activity_lottie);
31 | mLavGift = findViewById(R.id.animation_view);
32 | mLavTest = findViewById(R.id.animation_view_test);
33 | // initGift();
34 | initTest();
35 | }
36 |
37 | private void initTest() {
38 | mLavGift.setAnimation("test.json");
39 | mLavGift.setRepeatCount(INFINITE);
40 | mLavGift.playAnimation();
41 | }
42 |
43 | private void initGift() {
44 | mLavTest.setAnimation("liwu.json");
45 | mLavTest.setRepeatCount(INFINITE);
46 | mLavTest.setImageAssetsFolder("images/");
47 | mLavTest.playAnimation();
48 | }
49 | }
50 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/svg/svga/SvgaActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.svg.svga;
2 |
3 | import android.os.Bundle;
4 | import android.widget.FrameLayout;
5 |
6 | import com.opensource.svgaplayer.SVGADrawable;
7 | import com.opensource.svgaplayer.SVGAImageView;
8 | import com.opensource.svgaplayer.SVGAParser;
9 | import com.opensource.svgaplayer.SVGAVideoEntity;
10 |
11 | import java.net.MalformedURLException;
12 | import java.net.URL;
13 |
14 | import androidstack.customview.R;
15 | import androidx.annotation.Nullable;
16 | import androidx.appcompat.app.AppCompatActivity;
17 | import androidx.constraintlayout.widget.ConstraintLayout;
18 |
19 | /**
20 | * Created on 2020/8/17 14:39
21 | *
22 | * @author zhangchaozhou
23 | * @email 13760289294@139.com
24 | * @wechat 13760289294
25 | */
26 | public class SvgaActivity extends AppCompatActivity {
27 | private SVGAImageView mSvgaTest;
28 | private ConstraintLayout mCLSvga;
29 | private FrameLayout mFlSvga1;
30 | private FrameLayout mFlSvga2;
31 |
32 | @Override
33 | protected void onCreate(@Nullable Bundle savedInstanceState) {
34 | super.onCreate(savedInstanceState);
35 | setContentView(R.layout.activity_svga);
36 | mSvgaTest = findViewById(R.id.svga_test);
37 | mCLSvga = findViewById(R.id.cl_svga);
38 | mFlSvga1 = findViewById(R.id.fl_svga1);
39 | mFlSvga2 = findViewById(R.id.fl_svga2);
40 |
41 |
42 | /**
43 | * xml代码实现:
44 | * source:表示 svga 文件的路径,提供一个在 assets 目录下的文件名,或者提供一个 http url 地址。
45 | * autoPlay:当动画加载完成后,自动播放。
46 | * loopCount:默认为 0,设置动画的循环次数,0 表示无限循环。
47 | * clearsAfterStop:默认为 true,当动画播放完成后,是否清空画布。
48 | * fillMode:默认为 Forward。Forward 表示动画结束后,将停留在最后一帧。Backward 表示动画结束后,将停留在第一帧。
49 | */
50 | codeAnimation();
51 |
52 |
53 | }
54 |
55 | private void codeAnimation() {
56 |
57 | SVGAImageView svgaImageView = new SVGAImageView(this);
58 | SVGAParser.Companion.shareParser().init(this);
59 | SVGAParser parser = SVGAParser.Companion.shareParser();
60 | parser = new SVGAParser(this);
61 | parser.decodeFromAssets("car.svga", new SVGAParser.ParseCompletion() {
62 | @Override
63 | public void onComplete(SVGAVideoEntity svgaVideoEntity) {
64 | SVGADrawable drawable = new SVGADrawable(svgaVideoEntity);
65 | svgaImageView.setImageDrawable(drawable);
66 | mFlSvga1.addView(svgaImageView );
67 | svgaImageView.startAnimation();
68 | }
69 |
70 | @Override
71 | public void onError() {
72 |
73 | System.out.println("解析错误decodeFromAssets");
74 | }
75 | });
76 |
77 | try {
78 | SVGAImageView svgaImageView1 = new SVGAImageView(this);
79 | SVGAParser parser1 = SVGAParser.Companion.shareParser();
80 | parser1 = new SVGAParser(this);
81 | URL url = new URL("https://github.com/yyued/SVGA-Samples/blob/master/posche.svga?raw=true");
82 | parser1.decodeFromURL(url, new SVGAParser.ParseCompletion() {
83 | @Override
84 | public void onComplete(SVGAVideoEntity svgaVideoEntity) {
85 | SVGADrawable drawable = new SVGADrawable(svgaVideoEntity);
86 | svgaImageView1.setImageDrawable(drawable);
87 | mFlSvga2.addView(svgaImageView1 );
88 | svgaImageView1.startAnimation();
89 | }
90 |
91 | @Override
92 | public void onError() {
93 | System.out.println("解析错误decodeFromURL");
94 | }
95 | });
96 | } catch (MalformedURLException e) {
97 | System.out.println(e.getMessage());
98 | }
99 | }
100 |
101 | }
102 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/svg/svga/SvgaTextActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.svg.svga;
2 |
3 | import android.graphics.Color;
4 | import android.os.Bundle;
5 | import android.text.TextPaint;
6 | import android.text.TextUtils;
7 | import android.view.View;
8 | import android.widget.Button;
9 | import android.widget.EditText;
10 | import android.widget.Toast;
11 |
12 | import androidx.annotation.Nullable;
13 | import androidx.appcompat.app.AppCompatActivity;
14 |
15 | import com.opensource.svgaplayer.SVGADrawable;
16 | import com.opensource.svgaplayer.SVGADynamicEntity;
17 | import com.opensource.svgaplayer.SVGAImageView;
18 | import com.opensource.svgaplayer.SVGAParser;
19 | import com.opensource.svgaplayer.SVGAVideoEntity;
20 |
21 | import org.jetbrains.annotations.NotNull;
22 |
23 | import java.net.URL;
24 |
25 | import androidstack.customview.R;
26 |
27 | public class SvgaTextActivity extends AppCompatActivity {
28 |
29 |
30 | private Button mBtnSvgaText;
31 | private EditText mEdtSvgaText;
32 |
33 |
34 | private SVGAParser svgaParser;
35 |
36 | private SVGAImageView svgaImageView;
37 |
38 | private SVGAVideoEntity videoEntity;
39 | @Override
40 | protected void onCreate(@Nullable Bundle savedInstanceState) {
41 | super.onCreate(savedInstanceState);
42 | setContentView(R.layout.activity_svga_text);
43 |
44 | mBtnSvgaText = findViewById(R.id.btn_svga_text);
45 | mEdtSvgaText = findViewById(R.id.edt_svga_text);
46 | svgaImageView = findViewById(R.id.svga_text);
47 | svgaParser = new SVGAParser(this);
48 |
49 | try {
50 | svgaParser.parse(new URL("https://github.com/yyued/SVGA-Samples/blob/master/kingset.svga?raw=true"),
51 | new SVGAParser.ParseCompletion() {
52 |
53 |
54 | @Override
55 | public void onComplete(@NotNull SVGAVideoEntity videoItem) {
56 | videoEntity =videoItem;
57 | }
58 | @Override
59 | public void onError() {
60 | Toast.makeText(SvgaTextActivity.this,"出错",Toast.LENGTH_LONG).show();
61 | }
62 | }
63 | );
64 | } catch (Exception e) {
65 | System.out.print(true);
66 | }
67 |
68 |
69 | mBtnSvgaText.setOnClickListener(new View.OnClickListener() {
70 | @Override
71 | public void onClick(View v) {
72 | String content = mEdtSvgaText.getText().toString();
73 | if (TextUtils.isEmpty(content)){
74 | Toast.makeText(SvgaTextActivity.this,"输入内容",Toast.LENGTH_LONG).show();
75 | return;
76 | }
77 | if (videoEntity==null){
78 | Toast.makeText(SvgaTextActivity.this,"svga资源解析中",Toast.LENGTH_LONG).show();
79 | return;
80 | }
81 | SVGADynamicEntity dynamicEntity = new SVGADynamicEntity();
82 | TextPaint textPaint = new TextPaint();
83 | textPaint.setColor(Color.WHITE);
84 | textPaint.setTextSize(28);
85 | dynamicEntity.setDynamicText(content, textPaint, "banner");
86 | SVGADrawable drawable = new SVGADrawable(videoEntity, dynamicEntity);
87 | svgaImageView.setImageDrawable(drawable);
88 | svgaImageView.startAnimation();
89 | }
90 | });
91 | }
92 | }
93 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/text/GradientTextView.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.text;
2 |
3 | import android.content.Context;
4 | import android.graphics.Color;
5 | import android.graphics.LinearGradient;
6 | import android.graphics.Shader;
7 | import android.util.AttributeSet;
8 | import android.widget.TextView;
9 |
10 | import androidx.annotation.NonNull;
11 | import androidx.annotation.Nullable;
12 |
13 | /**
14 | * @author zhangchaozhou
15 | * @time 2021/3/21 22:42
16 | */
17 | public class GradientTextView extends TextView {
18 |
19 | public enum GradientDirection {
20 | TOP_2_BOTTOM(1),
21 | START_2_END(2),
22 | TOP_START_2_BOTTOM_END(3);
23 |
24 | int direction;
25 |
26 | GradientDirection(int direction) {
27 | this.direction = direction;
28 | }
29 |
30 |
31 | public int getDirection() {
32 | return direction;
33 | }
34 | }
35 |
36 |
37 | public GradientTextView(@NonNull Context context) {
38 | super(context);
39 | }
40 |
41 | public GradientTextView(@NonNull Context context, @Nullable AttributeSet attrs) {
42 | super(context, attrs);
43 | }
44 |
45 | public GradientTextView(@NonNull Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
46 | super(context, attrs, defStyleAttr);
47 | }
48 |
49 | @Override
50 | protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
51 | super.onLayout(changed, left, top, right, bottom);
52 | if (changed) {
53 | // getPaint().setShader(new LinearGradient(
54 | // 0, 0, getWidth(), getHeight(),
55 | // new int[]{0xFFFFEABA, 0xFFDFBB82, 0xFFBE8B49}, new float[]{0, 0.5f, 1},
56 | // Shader.TileMode.CLAMP));
57 |
58 | Shader shader = new LinearGradient(0, 0, 0, getHeight(), Color.parseColor("#EE6A00"), Color.parseColor("#B80000"), Shader.TileMode.CLAMP);
59 | getPaint().setShader(shader);
60 | }
61 | }
62 | }
63 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/text/TextActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.text;
2 |
3 | import android.graphics.LinearGradient;
4 | import android.graphics.Shader;
5 | import android.os.Bundle;
6 |
7 | import androidx.annotation.Nullable;
8 | import androidx.appcompat.app.AppCompatActivity;
9 |
10 | import androidstack.customview.R;
11 |
12 | /**
13 | * @author zhangchaozhou
14 | * @time 2021/3/21 22:43
15 | */
16 | public class TextActivity extends AppCompatActivity {
17 |
18 | private GradientTextView mTvGradientText;
19 | @Override
20 | protected void onCreate(@Nullable Bundle savedInstanceState) {
21 | super.onCreate(savedInstanceState);
22 | setContentView(R.layout.activity_text);
23 | mTvGradientText = findViewById(R.id.tv_gradient_text);
24 | // mTvGradientText.getPaint().setShader(new LinearGradient(
25 | // 0, 0, mTvGradientText.getWidth(), mTvGradientText.getHeight(),
26 | // new int[]{0xFFFFEABA, 0xFFDFBB82, 0xFFBE8B49}, new float[]{0, 0.5f, 1},
27 | // Shader.TileMode.CLAMP));
28 | // Shader shader_vertical=new LinearGradient(0, mTvGradientText.getHeight()/4, 0, mTvGradientText.getHeight(), Color.parseColor("#D51400"), Color.parseColor("#F96F00"), Shader.TileMode.CLAMP);
29 | // mTvGradientText.getPaint().setShader(shader_vertical);
30 |
31 | mTvGradientText.setText("00000000999925");
32 | }
33 | }
34 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/toolbar/ToolBarActivity.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.toolbar;
2 |
3 | import android.os.Bundle;
4 |
5 | import androidstack.customview.R;
6 | import androidx.annotation.Nullable;
7 | import androidx.appcompat.app.AppCompatActivity;
8 | import androidx.appcompat.widget.Toolbar;
9 |
10 | /**
11 | * Created on 2020/8/31 12:19
12 | *
13 | * @author zhangchaozhou
14 | * @email 13760289294@139.com
15 | * @wechat 13760289294
16 | */
17 | public class ToolBarActivity extends AppCompatActivity {
18 | @Override
19 | protected void onCreate(@Nullable Bundle savedInstanceState) {
20 | super.onCreate(savedInstanceState);
21 | setContentView(R.layout.activity_tool_bar);
22 | Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
23 | setSupportActionBar(toolbar);
24 | }
25 | }
26 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/java/androidstack/customview/view/mask/GuideMaskSet.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview.view.mask;
2 |
3 | import java.util.ArrayList;
4 | import java.util.List;
5 |
6 | /**
7 | * 蒙版集合
8 | * @author zhangchaozhou
9 | */
10 | public class GuideMaskSet {
11 |
12 | private List mGuideMasks = new ArrayList<>();
13 |
14 | private int mPosition = 0;
15 |
16 | /**
17 | * 添加蒙版
18 | * @param guideMask
19 | */
20 | public void addGuide(GuideMask guideMask) {
21 | mGuideMasks.add(guideMask);
22 | guideMask.setOnDismissListener(new GuideMask.OnDismissListener() {
23 | @Override
24 | public void onDismiss() {//关闭后显示下一个蒙版
25 | int nextPosition = mPosition + 1;
26 | if (mGuideMasks.size() > nextPosition) {
27 | GuideMask next = mGuideMasks.get(nextPosition);
28 | mPosition++;
29 | next.show();
30 | }
31 | }
32 | });
33 | }
34 |
35 | /**
36 | * 显示蒙版集合
37 | */
38 | public void show(){
39 | mGuideMasks.get(0).show();
40 | }
41 | }
42 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/anim/alpha_test.xml:
--------------------------------------------------------------------------------
1 |
2 |
8 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/anim/rotate_test.xml:
--------------------------------------------------------------------------------
1 |
2 |
13 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/anim/scale_test.xml:
--------------------------------------------------------------------------------
1 |
2 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/anim/set_sanner.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
12 |
13 |
17 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/anim/set_test.xml:
--------------------------------------------------------------------------------
1 |
2 |
7 |
8 |
18 |
19 |
24 |
25 |
35 |
36 |
44 |
45 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/anim/translate_test.xml:
--------------------------------------------------------------------------------
1 |
2 |
11 |
12 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/animator/animator_logo.xml:
--------------------------------------------------------------------------------
1 |
2 |
10 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/animator/animator_set.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
9 |
15 |
16 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/drawable-v21/ic_logo.xml:
--------------------------------------------------------------------------------
1 |
2 |
4 |
7 |
8 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/drawable-v24/ic_launcher_foreground.xml:
--------------------------------------------------------------------------------
1 |
7 |
8 |
9 |
15 |
18 |
21 |
22 |
23 |
24 |
30 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/drawable/animation_list_loading.xml:
--------------------------------------------------------------------------------
1 |
2 |
4 |
7 |
10 |
13 |
16 |
19 |
20 |
23 |
26 |
29 |
32 |
35 |
36 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/drawable/ic_logo.xml:
--------------------------------------------------------------------------------
1 |
2 |
4 |
7 |
8 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/drawable/ic_love.xml:
--------------------------------------------------------------------------------
1 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/drawable/item.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/drawable/item.jpg
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/drawable/shape_scanner.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/drawable/vector_logo.xml:
--------------------------------------------------------------------------------
1 |
2 |
7 |
8 |
13 |
14 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_advanced_property.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
15 |
16 |
17 |
18 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_alpha_animation.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
16 |
17 |
18 |
19 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_animator_set.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
16 |
17 |
18 |
19 |
20 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_basis_view.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
10 |
11 |
12 |
13 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_camera.xml:
--------------------------------------------------------------------------------
1 |
2 |
5 |
6 |
12 |
13 |
14 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_card.xml:
--------------------------------------------------------------------------------
1 |
2 |
12 |
13 |
20 |
21 |
27 |
28 |
34 |
35 |
36 |
41 |
42 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_custom_progress.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
8 |
19 |
20 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_evaluator.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
16 |
17 |
18 |
19 |
27 |
28 |
33 |
34 |
39 |
40 |
45 |
46 |
53 |
54 |
55 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_falling_ball_object.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
14 |
15 |
16 |
17 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_falling_ball_value.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
14 |
15 |
16 |
17 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_frame_animation.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
8 |
16 |
17 |
18 |
19 |
29 |
30 |
31 |
32 |
33 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_interpolator.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
16 |
17 |
18 |
19 |
26 |
30 |
31 |
36 |
37 |
38 |
45 |
46 |
53 |
54 |
55 |
62 |
63 |
64 |
71 |
72 |
73 |
80 |
81 |
88 |
89 |
96 |
97 |
104 |
105 |
106 |
113 |
114 |
115 |
116 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_loading.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
16 |
17 |
18 |
19 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_lottie.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
17 |
18 |
27 |
28 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_main.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
8 |
9 |
13 |
14 |
15 |
22 |
23 |
24 |
25 |
26 |
31 |
32 |
33 |
40 |
41 |
48 |
49 |
56 |
57 |
62 |
63 |
64 |
69 |
70 |
75 |
76 |
81 |
82 |
87 |
88 |
93 |
94 |
99 |
100 |
101 |
106 |
107 |
112 |
113 |
114 |
119 |
120 |
121 |
126 |
127 |
128 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_mask.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
16 |
17 |
18 |
19 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_matrix.xml:
--------------------------------------------------------------------------------
1 |
2 |
5 |
6 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_menu.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
8 |
9 |
10 |
20 |
21 |
22 |
23 |
33 |
34 |
35 |
36 |
46 |
47 |
48 |
49 |
50 |
60 |
61 |
62 |
63 |
73 |
74 |
75 |
85 |
86 |
87 |
88 |
89 |
90 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_music.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
16 |
17 |
26 |
27 |
28 |
37 |
38 |
39 |
48 |
49 |
59 |
60 |
61 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_object_animator.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
16 |
17 |
18 |
19 |
20 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_paint.xml:
--------------------------------------------------------------------------------
1 |
2 |
5 |
6 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_part_rv.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
8 |
11 |
12 |
16 |
23 |
24 |
25 |
26 |
32 |
33 |
34 |
35 |
41 |
42 |
43 |
44 |
45 |
46 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_path_measure.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
15 |
16 |
17 |
18 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_phone.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
15 |
16 |
17 |
18 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_property_animation.xml:
--------------------------------------------------------------------------------
1 |
2 |
5 |
9 |
10 |
14 |
15 |
21 |
22 |
28 |
29 |
30 |
36 |
37 |
38 |
44 |
45 |
51 |
52 |
53 |
59 |
60 |
61 |
67 |
68 |
74 |
75 |
81 |
82 |
83 |
84 |
85 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_rotate_animation.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
16 |
17 |
18 |
19 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_scale_animation.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
16 |
17 |
18 |
19 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_svg.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
8 |
16 |
17 |
18 |
26 |
27 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_svga.xml:
--------------------------------------------------------------------------------
1 |
2 |
7 |
8 |
16 |
17 |
23 |
24 |
25 |
26 |
32 |
33 |
34 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_svga_text.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
12 |
13 |
14 |
15 |
16 |
21 |
22 |
23 |
24 |
32 |
33 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_test.xml:
--------------------------------------------------------------------------------
1 |
2 |
5 |
6 |
7 |
8 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_text.xml:
--------------------------------------------------------------------------------
1 |
2 |
7 |
8 |
9 |
17 |
18 |
19 |
20 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_tool_bar.xml:
--------------------------------------------------------------------------------
1 |
2 |
8 |
9 |
15 |
16 |
26 |
27 |
35 |
36 |
41 |
42 | >
43 |
44 |
54 |
55 |
56 |
57 |
62 |
63 |
64 |
65 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_translate_animation.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
16 |
17 |
18 |
19 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_tween_animation.xml:
--------------------------------------------------------------------------------
1 |
2 |
5 |
6 |
7 |
11 |
12 |
16 |
17 |
23 |
24 |
25 |
32 |
33 |
40 |
41 |
48 |
49 |
56 |
57 |
58 |
59 |
67 |
68 |
75 |
76 |
77 |
84 |
85 |
86 |
87 |
88 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_value_animator.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
16 |
17 |
18 |
19 |
27 |
28 |
29 |
30 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_view_animation.xml:
--------------------------------------------------------------------------------
1 |
2 |
5 |
6 |
7 |
11 |
12 |
16 |
17 |
23 |
24 |
25 |
32 |
33 |
34 |
35 |
36 |
37 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/activity_view_group_animate.xml:
--------------------------------------------------------------------------------
1 |
2 |
7 |
8 |
9 |
18 |
19 |
20 |
21 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/dialog_custom.xml:
--------------------------------------------------------------------------------
1 |
2 |
7 |
8 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/item.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
7 |
8 |
15 |
16 |
22 |
23 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/item_part_rv.xml:
--------------------------------------------------------------------------------
1 |
2 |
7 |
8 |
18 |
19 |
20 |
21 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/layout/layout_mask.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
25 |
26 |
37 |
38 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-anydpi-v26/ic_launcher.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-anydpi-v26/ic_launcher_round.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-hdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-hdpi/ic_launcher.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-hdpi/ic_launcher_round.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-hdpi/ic_launcher_round.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-mdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-mdpi/ic_launcher.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-mdpi/ic_launcher_round.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-mdpi/ic_launcher_round.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xhdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xhdpi/ic_launcher.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xhdpi/ic_launcher_round.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xhdpi/ic_launcher_round.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/add_focus_big.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/add_focus_big.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/ic_arrow.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/ic_arrow.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/ic_camera.jpeg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/ic_camera.jpeg
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/ic_launcher.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/ic_loading.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/ic_loading.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/ic_phone.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/ic_phone.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/ic_scanner.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/ic_scanner.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/ic_test.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/ic_test.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/loading_01.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/loading_01.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/loading_010.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/loading_010.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/loading_02.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/loading_02.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/loading_03.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/loading_03.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/loading_04.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/loading_04.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/loading_05.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/loading_05.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/loading_06.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/loading_06.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/loading_07.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/loading_07.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/loading_08.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/loading_08.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxhdpi/loading_09.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxhdpi/loading_09.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/mipmap-xxxhdpi/ic_paper.jpeg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/app/src/main/res/mipmap-xxxhdpi/ic_paper.jpeg
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/values/attr.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/values/colors.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 | #6200EE
4 | #3700B3
5 | #03DAC5
6 | #733aaa
7 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/values/dimens.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 | 16dp
4 | 16dp
5 |
6 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/values/strings.xml:
--------------------------------------------------------------------------------
1 |
2 | CustomProgressView
3 |
--------------------------------------------------------------------------------
/CustomView/app/src/main/res/values/styles.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
9 |
10 |
--------------------------------------------------------------------------------
/CustomView/app/src/test/java/androidstack/customview/ExampleUnitTest.java:
--------------------------------------------------------------------------------
1 | package androidstack.customview;
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() {
15 | assertEquals(4, 2 + 2);
16 | }
17 | }
--------------------------------------------------------------------------------
/CustomView/build.gradle:
--------------------------------------------------------------------------------
1 | // Top-level build file where you can add configuration options common to all sub-projects/modules.
2 | buildscript {
3 | repositories {
4 | google()
5 | jcenter()
6 | }
7 | dependencies {
8 | classpath "com.android.tools.build:gradle:4.0.0"
9 |
10 | classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:1.3.72"
11 | // NOTE: Do not place your application dependencies here; they belong
12 | // in the individual module build.gradle files
13 | }
14 | }
15 |
16 | allprojects {
17 | repositories {
18 | google()
19 | jcenter()
20 | //SVGA
21 | maven { url 'https://jitpack.io' }
22 | }
23 | }
24 |
25 | task clean(type: Delete) {
26 | delete rootProject.buildDir
27 | }
--------------------------------------------------------------------------------
/CustomView/gradle.properties:
--------------------------------------------------------------------------------
1 | # Project-wide Gradle settings.
2 | # IDE (e.g. Android Studio) users:
3 | # Gradle settings configured through the IDE *will override*
4 | # any settings specified in this file.
5 | # For more details on how to configure your build environment visit
6 | # http://www.gradle.org/docs/current/userguide/build_environment.html
7 | # Specifies the JVM arguments used for the daemon process.
8 | # The setting is particularly useful for tweaking memory settings.
9 | org.gradle.jvmargs=-Xmx2048m
10 | # When configured, Gradle will run in incubating parallel mode.
11 | # This option should only be used with decoupled projects. More details, visit
12 | # http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects
13 | # org.gradle.parallel=true
14 | # AndroidX package structure to make it clearer which packages are bundled with the
15 | # Android operating system, and which are packaged with your app"s APK
16 | # https://developer.android.com/topic/libraries/support-library/androidx-rn
17 | android.useAndroidX=true
18 | # Automatically convert third-party libraries to use AndroidX
19 | android.enableJetifier=true
--------------------------------------------------------------------------------
/CustomView/gradle/wrapper/gradle-wrapper.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/CustomView/gradle/wrapper/gradle-wrapper.jar
--------------------------------------------------------------------------------
/CustomView/gradle/wrapper/gradle-wrapper.properties:
--------------------------------------------------------------------------------
1 | #Mon Jun 22 21:59:46 CST 2020
2 | distributionBase=GRADLE_USER_HOME
3 | distributionPath=wrapper/dists
4 | zipStoreBase=GRADLE_USER_HOME
5 | zipStorePath=wrapper/dists
6 | distributionUrl=https\://services.gradle.org/distributions/gradle-6.1.1-all.zip
7 |
--------------------------------------------------------------------------------
/CustomView/gradlew.bat:
--------------------------------------------------------------------------------
1 | @if "%DEBUG%" == "" @echo off
2 | @rem ##########################################################################
3 | @rem
4 | @rem Gradle startup script for Windows
5 | @rem
6 | @rem ##########################################################################
7 |
8 | @rem Set local scope for the variables with windows NT shell
9 | if "%OS%"=="Windows_NT" setlocal
10 |
11 | set DIRNAME=%~dp0
12 | if "%DIRNAME%" == "" set DIRNAME=.
13 | set APP_BASE_NAME=%~n0
14 | set APP_HOME=%DIRNAME%
15 |
16 | @rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
17 | set DEFAULT_JVM_OPTS=
18 |
19 | @rem Find java.exe
20 | if defined JAVA_HOME goto findJavaFromJavaHome
21 |
22 | set JAVA_EXE=java.exe
23 | %JAVA_EXE% -version >NUL 2>&1
24 | if "%ERRORLEVEL%" == "0" goto init
25 |
26 | echo.
27 | echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
28 | echo.
29 | echo Please set the JAVA_HOME variable in your environment to match the
30 | echo location of your Java installation.
31 |
32 | goto fail
33 |
34 | :findJavaFromJavaHome
35 | set JAVA_HOME=%JAVA_HOME:"=%
36 | set JAVA_EXE=%JAVA_HOME%/bin/java.exe
37 |
38 | if exist "%JAVA_EXE%" goto init
39 |
40 | echo.
41 | echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
42 | echo.
43 | echo Please set the JAVA_HOME variable in your environment to match the
44 | echo location of your Java installation.
45 |
46 | goto fail
47 |
48 | :init
49 | @rem Get command-line arguments, handling Windows variants
50 |
51 | if not "%OS%" == "Windows_NT" goto win9xME_args
52 |
53 | :win9xME_args
54 | @rem Slurp the command line arguments.
55 | set CMD_LINE_ARGS=
56 | set _SKIP=2
57 |
58 | :win9xME_args_slurp
59 | if "x%~1" == "x" goto execute
60 |
61 | set CMD_LINE_ARGS=%*
62 |
63 | :execute
64 | @rem Setup the command line
65 |
66 | set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
67 |
68 | @rem Execute Gradle
69 | "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%
70 |
71 | :end
72 | @rem End local scope for the variables with windows NT shell
73 | if "%ERRORLEVEL%"=="0" goto mainEnd
74 |
75 | :fail
76 | rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
77 | rem the _cmd.exe /c_ return code!
78 | if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
79 | exit /b 1
80 |
81 | :mainEnd
82 | if "%OS%"=="Windows_NT" endlocal
83 |
84 | :omega
85 |
--------------------------------------------------------------------------------
/CustomView/settings.gradle:
--------------------------------------------------------------------------------
1 | include ':app'
2 | rootProject.name = "CustomProgressView"
--------------------------------------------------------------------------------
/DrawingBasis.jpeg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/DrawingBasis.jpeg
--------------------------------------------------------------------------------
/Heartbeat1647.svga:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/Heartbeat1647.svga
--------------------------------------------------------------------------------
/Heartbeat1701.svga:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/Heartbeat1701.svga
--------------------------------------------------------------------------------
/Heartbeat1717.svga:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/Heartbeat1717.svga
--------------------------------------------------------------------------------
/Heartbeat1746.svga:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/Heartbeat1746.svga
--------------------------------------------------------------------------------
/HeartbeatText.svga:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/HeartbeatText.svga
--------------------------------------------------------------------------------
/HeartbeatText1-3.svga:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/HeartbeatText1-3.svga
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # CustomView
2 | CustomView
3 |
4 |
5 | 欢迎关注微信公众号:Android技术堆栈
6 |
7 | 
8 |
9 |
10 | 
11 |
12 |
13 | 
14 |
15 |
16 |
--------------------------------------------------------------------------------
/SVG2VECTOR.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/SVG2VECTOR.png
--------------------------------------------------------------------------------
/Video_20200819_071634_945.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/Video_20200819_071634_945.gif
--------------------------------------------------------------------------------
/Video_20200819_073506_981.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/Video_20200819_073506_981.gif
--------------------------------------------------------------------------------
/Video_20200819_073636_929.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/Video_20200819_073636_929.gif
--------------------------------------------------------------------------------
/ic_sing_single.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/ic_sing_single.png
--------------------------------------------------------------------------------
/ic_week_star_frame_new.9.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/ic_week_star_frame_new.9.png
--------------------------------------------------------------------------------
/svga_nihongdeng:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/svga_nihongdeng
--------------------------------------------------------------------------------
/tween.jpeg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/tween.jpeg
--------------------------------------------------------------------------------
/公众号.bmp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/公众号.bmp
--------------------------------------------------------------------------------
/抛物动画.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/抛物动画.gif
--------------------------------------------------------------------------------
/插值器.jpeg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/插值器.jpeg
--------------------------------------------------------------------------------
/电话响铃动画.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/电话响铃动画.gif
--------------------------------------------------------------------------------
/菜单动画.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/菜单动画.gif
--------------------------------------------------------------------------------
/逐帧动画.jpeg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chaozhouzhang/CustomView/c053299b3201a268c4c3571f985dab92f91815e9/逐帧动画.jpeg
--------------------------------------------------------------------------------