Commit 9ca5a167a3f21818c5bd8e2cd4914ec59f0a4667
Merge branch 'master' of bj.gitlab.cnlive.com:cnlive-team/newModuleStrike
# Conflicts: # app/strike/src/main/AndroidManifest.xml # app/strike/src/main/java/com/cnlive/strike/MainActivity.java # app/strike/src/main/res/layout/activity_main.xml
Showing
27 changed files
with
2701 additions
and
2 deletions
app/strike/build.gradle
| @@ -158,6 +158,7 @@ dependencies { | @@ -158,6 +158,7 @@ dependencies { | ||
| 158 | implementation project(path: ':core:base') | 158 | implementation project(path: ':core:base') |
| 159 | implementation project(path: ':cloud:user') | 159 | implementation project(path: ':cloud:user') |
| 160 | 160 | ||
| 161 | + implementation project(path: ':core:imageload') | ||
| 161 | // implementation project(path: ':core:util') | 162 | // implementation project(path: ':core:util') |
| 162 | // implementation project(path: ':core:encipher') | 163 | // implementation project(path: ':core:encipher') |
| 163 | // implementation project(path: ':cloud:user') | 164 | // implementation project(path: ':cloud:user') |
app/strike/src/main/java/com/cnlive/strike/imgutil/ImgActivity.java
0 → 100644
| 1 | +package com.cnlive.strike.imgutil; | ||
| 2 | + | ||
| 3 | +import androidx.appcompat.app.AppCompatActivity; | ||
| 4 | + | ||
| 5 | +import android.animation.ObjectAnimator; | ||
| 6 | +import android.os.Bundle; | ||
| 7 | +import android.view.View; | ||
| 8 | +import android.view.ViewPropertyAnimator; | ||
| 9 | +import android.widget.ImageView; | ||
| 10 | + | ||
| 11 | +import com.bumptech.glide.request.transition.ViewPropertyTransition; | ||
| 12 | +import com.cnlive.core.imageload.loader.ImageLoader; | ||
| 13 | +import com.cnlive.strike.R; | ||
| 14 | + | ||
| 15 | +public class ImgActivity extends AppCompatActivity { | ||
| 16 | + | ||
| 17 | + private ImageView iv_test1; | ||
| 18 | + private ImageView iv_test2; | ||
| 19 | + private ImageView iv_test02; | ||
| 20 | + private ImageView iv_test3; | ||
| 21 | + private ImageView iv_test4; | ||
| 22 | + private ImageView iv_test5; | ||
| 23 | + private ImageView iv_test6; | ||
| 24 | + private ImageView iv_test7; | ||
| 25 | + private ImageView iv_test8; | ||
| 26 | + private ImageView iv_test9; | ||
| 27 | + private ImageView iv_test10; | ||
| 28 | + private ImageView iv_test11; | ||
| 29 | + private ImageView iv_test12; | ||
| 30 | + private ImageView iv_test13; | ||
| 31 | + private ImageView iv_test14; | ||
| 32 | + private ImageView iv_test15; | ||
| 33 | + | ||
| 34 | + String URL1 = "https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1574403931080&di=ea10bd1adb20025f02e296d8694f7bb4&imgtype=0&src=http%3A%2F%2Fimg3.duitang.com%2Fuploads%2Fitem%2F201506%2F23%2F20150623164841_jtvR3.thumb.700_0.jpeg"; | ||
| 35 | + | ||
| 36 | + @Override | ||
| 37 | + protected void onCreate(Bundle savedInstanceState) { | ||
| 38 | + super.onCreate(savedInstanceState); | ||
| 39 | + setContentView(R.layout.activity_img); | ||
| 40 | + ImageLoader.init(this); | ||
| 41 | + findview(); | ||
| 42 | + load(); | ||
| 43 | + } | ||
| 44 | + | ||
| 45 | + private void findview() { | ||
| 46 | + iv_test1 = findViewById(R.id.iv_test1); | ||
| 47 | + iv_test2 = findViewById(R.id.iv_test2); | ||
| 48 | + iv_test02 = findViewById(R.id.iv_test02); | ||
| 49 | + iv_test3 = findViewById(R.id.iv_test3); | ||
| 50 | + iv_test4 = findViewById(R.id.iv_test4); | ||
| 51 | + iv_test5 = findViewById(R.id.iv_test5); | ||
| 52 | + iv_test6 =findViewById(R.id.iv_test6); | ||
| 53 | + iv_test7 = findViewById(R.id.iv_test7); | ||
| 54 | + iv_test8 = findViewById(R.id.iv_test8); | ||
| 55 | + iv_test9 = findViewById(R.id.iv_test9); | ||
| 56 | + iv_test10 = findViewById(R.id.iv_test10); | ||
| 57 | + iv_test11 = findViewById(R.id.iv_test11); | ||
| 58 | + iv_test12 = findViewById(R.id.iv_test12); | ||
| 59 | + iv_test13 = findViewById(R.id.iv_test13); | ||
| 60 | + iv_test14 = findViewById(R.id.iv_test14); | ||
| 61 | + iv_test15 = findViewById(R.id.iv_test15); | ||
| 62 | + } | ||
| 63 | + | ||
| 64 | + | ||
| 65 | + private void load(){ | ||
| 66 | + ViewPropertyTransition.Animator animation = new ViewPropertyTransition.Animator(){ | ||
| 67 | + | ||
| 68 | + @Override | ||
| 69 | + public void animate(View view) { | ||
| 70 | + view.setAlpha( 0f ); | ||
| 71 | + ObjectAnimator fadeAnim = ObjectAnimator.ofFloat( view, "alpha", 0f, 1f ); | ||
| 72 | + fadeAnim.setDuration( 2500 ); | ||
| 73 | + fadeAnim.start(); | ||
| 74 | + } | ||
| 75 | + }; | ||
| 76 | + | ||
| 77 | + ImageLoader.with(this) | ||
| 78 | + .url(URL1) | ||
| 79 | + .animate(animation) | ||
| 80 | + .into(iv_test1); | ||
| 81 | + | ||
| 82 | + ImageLoader.with(this) | ||
| 83 | + .url(URL1) | ||
| 84 | + .scale(1)//缩放几倍 | ||
| 85 | + .into(iv_test02); | ||
| 86 | + | ||
| 87 | + ImageLoader.with(this) | ||
| 88 | + .url(URL1) | ||
| 89 | + .scale(3) | ||
| 90 | + .into(iv_test2); | ||
| 91 | + | ||
| 92 | + | ||
| 93 | + } | ||
| 94 | +} |
app/strike/src/main/res/layout/activity_img.xml
0 → 100644
| 1 | +<ScrollView xmlns:android="http://schemas.android.com/apk/res/android" | ||
| 2 | + android:layout_width="match_parent" | ||
| 3 | + android:layout_height="match_parent" | ||
| 4 | + xmlns:lb="http://schemas.android.com/apk/res-auto"> | ||
| 5 | + | ||
| 6 | + <LinearLayout | ||
| 7 | + android:layout_width="match_parent" | ||
| 8 | + android:layout_height="match_parent" | ||
| 9 | + android:orientation="vertical"> | ||
| 10 | + | ||
| 11 | + <TextView | ||
| 12 | + android:layout_width="wrap_content" | ||
| 13 | + android:layout_height="wrap_content" | ||
| 14 | + android:text="加载动效自定义:" | ||
| 15 | + /> | ||
| 16 | + <ImageView | ||
| 17 | + android:id="@+id/iv_test1" | ||
| 18 | + android:layout_width="300dp" | ||
| 19 | + android:layout_height="300dp" | ||
| 20 | + android:padding="10dp" /> | ||
| 21 | + <TextView | ||
| 22 | + android:layout_width="wrap_content" | ||
| 23 | + android:layout_height="wrap_content" | ||
| 24 | + android:text="放大缩小:" | ||
| 25 | + /> | ||
| 26 | + <LinearLayout | ||
| 27 | + android:layout_width="wrap_content" | ||
| 28 | + android:layout_height="wrap_content" | ||
| 29 | + android:orientation="vertical"> | ||
| 30 | + <ImageView | ||
| 31 | + android:id="@+id/iv_test02" | ||
| 32 | + android:layout_width="300dp" | ||
| 33 | + android:layout_height="300dp" | ||
| 34 | + android:padding="10dp" /> | ||
| 35 | + <ImageView | ||
| 36 | + android:id="@+id/iv_test2" | ||
| 37 | + android:layout_width="300dp" | ||
| 38 | + android:layout_height="300dp" | ||
| 39 | + android:padding="10dp" /> | ||
| 40 | + </LinearLayout> | ||
| 41 | + | ||
| 42 | + <ImageView | ||
| 43 | + android:id="@+id/iv_test3" | ||
| 44 | + android:layout_width="300dp" | ||
| 45 | + android:layout_height="300dp" | ||
| 46 | + android:padding="30dp" /> | ||
| 47 | + | ||
| 48 | + <ImageView | ||
| 49 | + android:id="@+id/iv_test4" | ||
| 50 | + android:layout_width="300dp" | ||
| 51 | + android:layout_height="300dp" | ||
| 52 | + android:padding="30dp" /> | ||
| 53 | + | ||
| 54 | + <ImageView | ||
| 55 | + android:id="@+id/iv_test5" | ||
| 56 | + android:layout_width="300dp" | ||
| 57 | + android:layout_height="300dp" | ||
| 58 | + android:padding="30dp" /> | ||
| 59 | + | ||
| 60 | + <ImageView | ||
| 61 | + android:id="@+id/iv_test6" | ||
| 62 | + android:layout_width="300dp" | ||
| 63 | + android:layout_height="300dp" | ||
| 64 | + android:padding="30dp" /> | ||
| 65 | + | ||
| 66 | + <ImageView | ||
| 67 | + android:id="@+id/iv_test7" | ||
| 68 | + android:layout_width="300dp" | ||
| 69 | + android:layout_height="300dp" | ||
| 70 | + android:padding="30dp" /> | ||
| 71 | + | ||
| 72 | + <ImageView | ||
| 73 | + android:id="@+id/iv_test8" | ||
| 74 | + android:layout_width="300dp" | ||
| 75 | + android:layout_height="300dp" | ||
| 76 | + android:padding="30dp" /> | ||
| 77 | + | ||
| 78 | + <ImageView | ||
| 79 | + android:id="@+id/iv_test9" | ||
| 80 | + android:layout_width="300dp" | ||
| 81 | + android:layout_height="300dp" | ||
| 82 | + android:padding="30dp" /> | ||
| 83 | + | ||
| 84 | + <ImageView | ||
| 85 | + android:id="@+id/iv_test10" | ||
| 86 | + android:layout_width="300dp" | ||
| 87 | + android:layout_height="300dp" | ||
| 88 | + android:padding="30dp" /> | ||
| 89 | + | ||
| 90 | + <ImageView | ||
| 91 | + android:id="@+id/iv_test11" | ||
| 92 | + android:layout_width="300dp" | ||
| 93 | + android:layout_height="300dp" | ||
| 94 | + android:padding="30dp" /> | ||
| 95 | + | ||
| 96 | + <ImageView | ||
| 97 | + android:id="@+id/iv_test12" | ||
| 98 | + android:layout_width="300dp" | ||
| 99 | + android:layout_height="300dp" | ||
| 100 | + android:padding="30dp" /> | ||
| 101 | + | ||
| 102 | + <ImageView | ||
| 103 | + android:id="@+id/iv_test13" | ||
| 104 | + android:layout_width="300dp" | ||
| 105 | + android:layout_height="300dp" | ||
| 106 | + android:padding="30dp" /> | ||
| 107 | + | ||
| 108 | + <ImageView | ||
| 109 | + android:id="@+id/iv_test14" | ||
| 110 | + android:layout_width="300dp" | ||
| 111 | + android:layout_height="300dp" | ||
| 112 | + android:padding="30dp" /> | ||
| 113 | + | ||
| 114 | + <ImageView | ||
| 115 | + android:id="@+id/iv_test15" | ||
| 116 | + android:layout_width="300dp" | ||
| 117 | + android:layout_height="300dp" | ||
| 118 | + android:padding="30dp" /> | ||
| 119 | + | ||
| 120 | + | ||
| 121 | + <com.cnlive.core.imageload.util.MultiView | ||
| 122 | + android:layout_width="300dp" | ||
| 123 | + android:layout_height="300dp" | ||
| 124 | + android:layout_margin="30dp" | ||
| 125 | + lb:angleCount="5" | ||
| 126 | + lb:type="multi" | ||
| 127 | + /> | ||
| 128 | + | ||
| 129 | + <com.cnlive.core.imageload.util.MultiView | ||
| 130 | + android:layout_width="200dp" | ||
| 131 | + android:layout_height="200dp" | ||
| 132 | + android:layout_margin="30dp" | ||
| 133 | + android:layout_gravity="center" | ||
| 134 | + lb:borderRadius="10dp" | ||
| 135 | + lb:type="round" | ||
| 136 | + /> | ||
| 137 | + | ||
| 138 | + <com.cnlive.core.imageload.util.MultiView | ||
| 139 | + android:layout_margin="30dp" | ||
| 140 | + android:layout_width="200dp" | ||
| 141 | + android:layout_height="200dp" | ||
| 142 | + android:layout_gravity="center" | ||
| 143 | + lb:type="circle" | ||
| 144 | + /> | ||
| 145 | + | ||
| 146 | + </LinearLayout> | ||
| 147 | +</ScrollView> |
core/imageload/.gitignore
0 → 100644
| 1 | +/build |
core/imageload/build.gradle
0 → 100644
| 1 | +apply plugin: 'com.android.library' | ||
| 2 | + | ||
| 3 | +android { | ||
| 4 | + compileSdkVersion 29 | ||
| 5 | + buildToolsVersion "29.0.2" | ||
| 6 | + | ||
| 7 | + | ||
| 8 | + defaultConfig { | ||
| 9 | + minSdkVersion 16 | ||
| 10 | + targetSdkVersion 29 | ||
| 11 | + versionCode 1 | ||
| 12 | + versionName "1.0" | ||
| 13 | + | ||
| 14 | + testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" | ||
| 15 | + consumerProguardFiles 'consumer-rules.pro' | ||
| 16 | + } | ||
| 17 | + | ||
| 18 | + buildTypes { | ||
| 19 | + release { | ||
| 20 | + minifyEnabled false | ||
| 21 | + proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro' | ||
| 22 | + } | ||
| 23 | + } | ||
| 24 | + | ||
| 25 | +} | ||
| 26 | + | ||
| 27 | +dependencies { | ||
| 28 | + implementation fileTree(dir: 'libs', include: ['*.jar']) | ||
| 29 | + | ||
| 30 | + implementation 'androidx.appcompat:appcompat:1.1.0' | ||
| 31 | + testImplementation 'junit:junit:4.12' | ||
| 32 | + androidTestImplementation 'androidx.test:runner:1.1.1' | ||
| 33 | + androidTestImplementation 'androidx.test.espresso:espresso-core:3.2.0' | ||
| 34 | + | ||
| 35 | + implementation 'com.github.bumptech.glide:glide:4.10.0' | ||
| 36 | + implementation 'com.squareup.okhttp3:okhttp:3.14.2' | ||
| 37 | + implementation 'jp.wasabeef:glide-transformations:3.0.1' | ||
| 38 | + //滤镜 | ||
| 39 | + implementation 'jp.co.cyberagent.android.gpuimage:gpuimage-library:1.4.1' | ||
| 40 | +} |
core/imageload/consumer-rules.pro
0 → 100644
core/imageload/proguard-rules.pro
0 → 100644
| 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 |
core/imageload/src/androidTest/java/com/mm999/imageload/ExampleInstrumentedTest.java
0 → 100644
| 1 | +package com.mm999.imageload; | ||
| 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 <a href="http://d.android.com/tools/testing">Testing documentation</a> | ||
| 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 | + | ||
| 25 | + assertEquals("com.mm999.imageload.test", appContext.getPackageName()); | ||
| 26 | + } | ||
| 27 | +} |
core/imageload/src/main/AndroidManifest.xml
0 → 100644
core/imageload/src/main/java/com/cnlive/core/imageload/callback/ImageDownLoadCallBack.java
0 → 100644
core/imageload/src/main/java/com/cnlive/core/imageload/config/AnimationMode.java
0 → 100644
core/imageload/src/main/java/com/cnlive/core/imageload/config/Contants.java
0 → 100644
| 1 | +package com.cnlive.core.imageload.config; | ||
| 2 | + | ||
| 3 | +/** | ||
| 4 | + * created by hanyayun | ||
| 5 | + * on 2019/11/19 | ||
| 6 | + */ | ||
| 7 | +public interface Contants { | ||
| 8 | + String FOREWARD_SLASH = "/"; | ||
| 9 | + String ASSERTS_PATH ="file:///android_asset/" ; | ||
| 10 | + String ANDROID_RESOURCE ="android.resource://" ; | ||
| 11 | + String RAW ="/raw/" ; | ||
| 12 | +} |
core/imageload/src/main/java/com/cnlive/core/imageload/config/GlobalConfig.java
0 → 100644
| 1 | +package com.cnlive.core.imageload.config; | ||
| 2 | + | ||
| 3 | +import android.content.Context; | ||
| 4 | +import android.content.res.Configuration; | ||
| 5 | +import android.os.Handler; | ||
| 6 | +import android.os.Looper; | ||
| 7 | +import android.view.WindowManager; | ||
| 8 | + | ||
| 9 | +import com.bumptech.glide.MemoryCategory; | ||
| 10 | +import com.cnlive.core.imageload.loader.GlideLoader; | ||
| 11 | +import com.cnlive.core.imageload.loader.ILoader; | ||
| 12 | + | ||
| 13 | +/** | ||
| 14 | + * created by hanyayun | ||
| 15 | + * on 2019/11/19 | ||
| 16 | + */ | ||
| 17 | +public class GlobalConfig { | ||
| 18 | + | ||
| 19 | + public static String baseUrl; | ||
| 20 | + public static Context context; | ||
| 21 | + | ||
| 22 | + /** | ||
| 23 | + * 屏幕高度 | ||
| 24 | + */ | ||
| 25 | + private static int winHeight; | ||
| 26 | + | ||
| 27 | + /** | ||
| 28 | + * 屏幕宽度 | ||
| 29 | + */ | ||
| 30 | + private static int winWidth; | ||
| 31 | + | ||
| 32 | + /** | ||
| 33 | + * lrucache 最大值 | ||
| 34 | + */ | ||
| 35 | + public static int cacheMaxSize; | ||
| 36 | + | ||
| 37 | + /** | ||
| 38 | + * https是否忽略校验,默认不忽略 | ||
| 39 | + */ | ||
| 40 | + public static boolean ignoreCertificateVerify = false; | ||
| 41 | + | ||
| 42 | + private static Handler mainHandler; | ||
| 43 | + public static Handler getMainHandler() { | ||
| 44 | + if (mainHandler == null) { | ||
| 45 | + mainHandler = new Handler(Looper.getMainLooper()); | ||
| 46 | + } | ||
| 47 | + return mainHandler; | ||
| 48 | + } | ||
| 49 | + | ||
| 50 | + public static void init(Context context, int cacheSizeInM, MemoryCategory memoryCategory, boolean isInternalCD) { | ||
| 51 | + | ||
| 52 | + GlobalConfig.context = context; | ||
| 53 | + GlobalConfig.cacheMaxSize = cacheSizeInM; | ||
| 54 | + WindowManager wm = (WindowManager) context | ||
| 55 | + .getSystemService(Context.WINDOW_SERVICE); | ||
| 56 | + | ||
| 57 | + GlobalConfig.winWidth = wm.getDefaultDisplay().getWidth(); | ||
| 58 | + GlobalConfig.winHeight = wm.getDefaultDisplay().getHeight(); | ||
| 59 | + getLoader().init(context, cacheSizeInM, memoryCategory, isInternalCD); | ||
| 60 | + | ||
| 61 | + } | ||
| 62 | + | ||
| 63 | + private static ILoader loader; | ||
| 64 | + | ||
| 65 | + public static ILoader getLoader() { | ||
| 66 | + | ||
| 67 | + if (loader == null) { | ||
| 68 | + loader = new GlideLoader(); | ||
| 69 | + } | ||
| 70 | + | ||
| 71 | + return loader; | ||
| 72 | + } | ||
| 73 | + | ||
| 74 | + public static int getWinHeight() { | ||
| 75 | + if (context.getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { | ||
| 76 | + return winHeight < winWidth ? winHeight : winWidth; | ||
| 77 | + } else if (context.getResources().getConfiguration().orientation == Configuration.ORIENTATION_PORTRAIT) { | ||
| 78 | + return winHeight > winWidth ? winHeight : winWidth; | ||
| 79 | + } | ||
| 80 | + return winHeight; | ||
| 81 | + } | ||
| 82 | + | ||
| 83 | + public static int getWinWidth() { | ||
| 84 | + if (context.getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { | ||
| 85 | + return winHeight > winWidth ? winHeight : winWidth; | ||
| 86 | + } else if (context.getResources().getConfiguration().orientation == Configuration.ORIENTATION_PORTRAIT) { | ||
| 87 | + return winHeight < winWidth ? winHeight : winWidth; | ||
| 88 | + } | ||
| 89 | + return winWidth; | ||
| 90 | + } | ||
| 91 | +} |
core/imageload/src/main/java/com/cnlive/core/imageload/config/PriorityMode.java
0 → 100644
core/imageload/src/main/java/com/cnlive/core/imageload/config/ScaleMode.java
0 → 100644
| 1 | +package com.cnlive.core.imageload.config; | ||
| 2 | + | ||
| 3 | +/** | ||
| 4 | + * created by hanyayun | ||
| 5 | + * on 2019/11/20 | ||
| 6 | + */ | ||
| 7 | +public interface ScaleMode { | ||
| 8 | + /** | ||
| 9 | + * 等比例缩放图片,直到图片的狂高都大于等于ImageView的宽度,然后截取中间的显示 | ||
| 10 | + */ | ||
| 11 | + int CENTER_CROP = 1; | ||
| 12 | + /** | ||
| 13 | + * 等比例缩放图片,宽或者是高等于ImageView的宽或者是高 | ||
| 14 | + */ | ||
| 15 | + int FIT_CENTER = 2; | ||
| 16 | +} |
core/imageload/src/main/java/com/cnlive/core/imageload/config/ShapeMode.java
0 → 100644
| 1 | +package com.cnlive.core.imageload.config; | ||
| 2 | + | ||
| 3 | +/** | ||
| 4 | + * created by hanyayun | ||
| 5 | + * on 2019/11/19 | ||
| 6 | + */ | ||
| 7 | +public interface ShapeMode { | ||
| 8 | + | ||
| 9 | + /** | ||
| 10 | + * 直角矩形 | ||
| 11 | + */ | ||
| 12 | + int RECT = 0; | ||
| 13 | + | ||
| 14 | + /** | ||
| 15 | + * 圆角矩形 | ||
| 16 | + */ | ||
| 17 | + int RECT_ROUND = 1; | ||
| 18 | + | ||
| 19 | + /** | ||
| 20 | + * 椭圆/圆 | ||
| 21 | + */ | ||
| 22 | + int OVAL = 2; | ||
| 23 | + | ||
| 24 | + /** | ||
| 25 | + *正方形 | ||
| 26 | + */ | ||
| 27 | + int SQUARE = 3; | ||
| 28 | +} |
core/imageload/src/main/java/com/cnlive/core/imageload/config/SingleConfig.java
0 → 100644
| 1 | +package com.cnlive.core.imageload.config; | ||
| 2 | + | ||
| 3 | +import android.content.Context; | ||
| 4 | +import android.graphics.Bitmap; | ||
| 5 | +import android.util.Log; | ||
| 6 | +import android.view.View; | ||
| 7 | +import android.view.animation.Animation; | ||
| 8 | + | ||
| 9 | +import com.bumptech.glide.load.engine.DiskCacheStrategy; | ||
| 10 | +import com.bumptech.glide.request.transition.ViewPropertyAnimationFactory; | ||
| 11 | +import com.bumptech.glide.request.transition.ViewPropertyTransition; | ||
| 12 | +import com.cnlive.core.imageload.util.ImageUtil; | ||
| 13 | + | ||
| 14 | +import java.io.File; | ||
| 15 | + | ||
| 16 | +/** | ||
| 17 | + * created by hanyayun | ||
| 18 | + * on 2019/11/19 | ||
| 19 | + */ | ||
| 20 | +public class SingleConfig { | ||
| 21 | + private Context context; | ||
| 22 | + private boolean ignoreCertificateVerify; //https是否忽略校验 | ||
| 23 | + private String url; | ||
| 24 | + | ||
| 25 | + private float thumbnail; //缩略图缩放倍数 | ||
| 26 | + private String filePath; //文件路径 | ||
| 27 | + | ||
| 28 | + private File file; //文件路径 | ||
| 29 | + private int resId; //资源id | ||
| 30 | + private String rawPath; //raw路径 | ||
| 31 | + private String assertspath; //asserts路径 | ||
| 32 | + private String contentProvider; //内容提供者 | ||
| 33 | + private boolean isGif; //是否是GIF图 | ||
| 34 | + private View target; | ||
| 35 | + private int width; | ||
| 36 | + private int height; | ||
| 37 | + private int oWidth; | ||
| 38 | + private int oHeight; | ||
| 39 | + | ||
| 40 | + //滤镜 | ||
| 41 | + private boolean isNeedVignette; //是否需要晕映 | ||
| 42 | + private boolean isNeedSketch; //是否需要素描 | ||
| 43 | + private float pixelationLevel; //是否需要马赛克 | ||
| 44 | + private boolean isNeedPixelation; //是否需要马赛克 | ||
| 45 | + private boolean isNeedInvert; //是否需要胶片 | ||
| 46 | + public float contrastLevel; //锐化等级 | ||
| 47 | + private boolean isNeedContrast; //是否需要锐化 | ||
| 48 | + private boolean isNeedSepia; //是否需要墨画 | ||
| 49 | + private boolean isNeedToon; //是否需要油画 | ||
| 50 | + private boolean isNeedSwirl; // 是否需要漩涡 | ||
| 51 | + private boolean isNeedGrayscale; //是否需要黑色 | ||
| 52 | + private boolean isNeedBrightness; //是否需要亮度 | ||
| 53 | + private float brightnessLeve; //是否需要亮度 | ||
| 54 | + private boolean needBlur;//是否需要模糊 | ||
| 55 | + private boolean needFilteColor;//是否需要模糊 | ||
| 56 | + | ||
| 57 | + private int filteColor;//滤镜颜色 | ||
| 58 | + private int priority;//请求优先级 | ||
| 59 | + | ||
| 60 | + private int animationType;//动画资源Type | ||
| 61 | + private int animationId;//动画资源id | ||
| 62 | + private ViewPropertyTransition.Animator animation;//动画资源 | ||
| 63 | + | ||
| 64 | + private ViewPropertyAnimationFactory animator;//动画资源id | ||
| 65 | + | ||
| 66 | + private int blurRadius;//是否需要高斯模糊 | ||
| 67 | + private int placeHolderResId; //占位图 | ||
| 68 | + private int errorResId; //error图 | ||
| 69 | + | ||
| 70 | + private int shapeMode;//默认矩形,可选直角矩形,圆形/椭圆 | ||
| 71 | + private int rectRoundRadius;//圆角矩形时圆角的半径 | ||
| 72 | + private DiskCacheStrategy diskCacheStrategy;//是否跳过磁盘存储 | ||
| 73 | + private int scaleMode;//填充模式,默认centercrop,可选fitXY,centerInside... | ||
| 74 | + | ||
| 75 | + private BitmapListener bitmapListener; | ||
| 76 | + private boolean asBitmap;//只获取bitmap | ||
| 77 | + | ||
| 78 | + public SingleConfig(ConfigBuilder builder) { | ||
| 79 | + this.url = builder.url; | ||
| 80 | + this.thumbnail = builder.thumbnail; | ||
| 81 | + this.filePath = builder.filePath; | ||
| 82 | + this.file = builder.file; | ||
| 83 | + this.resId = builder.resId; | ||
| 84 | + this.rawPath = builder.rawPath; | ||
| 85 | + this.assertspath = builder.assertspath; | ||
| 86 | + this.contentProvider = builder.contentProvider; | ||
| 87 | + | ||
| 88 | + this.ignoreCertificateVerify = builder.ignoreCertificateVerify; | ||
| 89 | + | ||
| 90 | + this.target = builder.target; | ||
| 91 | + | ||
| 92 | + this.width = builder.width; | ||
| 93 | + this.height = builder.height; | ||
| 94 | + | ||
| 95 | + this.oWidth = builder.oWidth; | ||
| 96 | + this.oHeight = builder.oHeight; | ||
| 97 | + | ||
| 98 | + this.shapeMode = builder.shapeMode; | ||
| 99 | + if (shapeMode == ShapeMode.RECT_ROUND) { | ||
| 100 | + this.rectRoundRadius = builder.rectRoundRadius; | ||
| 101 | + } | ||
| 102 | + this.scaleMode = builder.scaleMode; | ||
| 103 | + | ||
| 104 | + this.diskCacheStrategy = builder.diskCacheStrategy; | ||
| 105 | + | ||
| 106 | + this.animationId = builder.animationId; | ||
| 107 | + this.animationType = builder.animationType; | ||
| 108 | + this.animator = builder.animator; | ||
| 109 | + this.animation = builder.animation; | ||
| 110 | + | ||
| 111 | + this.priority = builder.priority; | ||
| 112 | + //滤镜 | ||
| 113 | + this.isNeedVignette = builder.isNeedVignette; //是否需要晕映 | ||
| 114 | + this.isNeedSketch = builder.isNeedSketch; //是否需要素描 | ||
| 115 | + this.pixelationLevel = builder.pixelationLevel; //是否需要马赛克 | ||
| 116 | + this.isNeedPixelation = builder.isNeedPixelation; //是否需要马赛克 | ||
| 117 | + this.isNeedInvert = builder.isNeedInvert; //是否需要胶片 | ||
| 118 | + this.contrastLevel = builder.contrastLevel; //锐化等级 | ||
| 119 | + this.isNeedContrast = builder.isNeedContrast; //是否需要锐化 | ||
| 120 | + this.isNeedSepia = builder.isNeedSepia; //是否需要亮度 | ||
| 121 | + this.isNeedToon = builder.isNeedToon; //是否需要亮度 | ||
| 122 | + this.isNeedSwirl = builder.isNeedSwirl; //是否需要亮度 | ||
| 123 | + this.isNeedGrayscale = builder.isNeedGrayscale; //是否需要黑色 | ||
| 124 | + this.isNeedBrightness = builder.isNeedBrightness; //是否需要亮度 | ||
| 125 | + this.brightnessLeve = builder.brightnessLeve; //是否需要亮度 | ||
| 126 | + this.filteColor = builder.filteColor; | ||
| 127 | + this.needBlur = builder.needBlur; | ||
| 128 | + this.needFilteColor = builder.needFilteColor; | ||
| 129 | + this.placeHolderResId = builder.placeHolderResId; | ||
| 130 | + | ||
| 131 | + this.asBitmap = builder.asBitmap; | ||
| 132 | + this.bitmapListener = builder.bitmapListener; | ||
| 133 | + this.isGif = builder.isGif; | ||
| 134 | + this.blurRadius = builder.blurRadius; | ||
| 135 | + this.errorResId = builder.errorResId; | ||
| 136 | + } | ||
| 137 | + | ||
| 138 | + | ||
| 139 | + public Context getContext() { | ||
| 140 | + if (context == null) { | ||
| 141 | + context = GlobalConfig.context; | ||
| 142 | + } | ||
| 143 | + return context; | ||
| 144 | + } | ||
| 145 | + | ||
| 146 | + public DiskCacheStrategy getDiskCacheStrategy() { | ||
| 147 | + return diskCacheStrategy; | ||
| 148 | + } | ||
| 149 | + | ||
| 150 | + public String getContentProvider() { | ||
| 151 | + return contentProvider; | ||
| 152 | + } | ||
| 153 | + | ||
| 154 | + public int getErrorResId() { | ||
| 155 | + return errorResId; | ||
| 156 | + } | ||
| 157 | + | ||
| 158 | + public String getFilePath() { | ||
| 159 | + return filePath; | ||
| 160 | + } | ||
| 161 | + | ||
| 162 | + public File getFile() { | ||
| 163 | + return file; | ||
| 164 | + } | ||
| 165 | + | ||
| 166 | + public boolean isIgnoreCertificateVerify() { | ||
| 167 | + return ignoreCertificateVerify; | ||
| 168 | + } | ||
| 169 | + | ||
| 170 | + public String getUrl() { | ||
| 171 | + return url; | ||
| 172 | + } | ||
| 173 | + | ||
| 174 | + public float getThumbnail() { | ||
| 175 | + return thumbnail; | ||
| 176 | + } | ||
| 177 | + | ||
| 178 | + public int getResId() { | ||
| 179 | + return resId; | ||
| 180 | + } | ||
| 181 | + | ||
| 182 | + public String getRawPath() { | ||
| 183 | + return rawPath; | ||
| 184 | + } | ||
| 185 | + | ||
| 186 | + public String getAssertspath() { | ||
| 187 | + return assertspath; | ||
| 188 | + } | ||
| 189 | + | ||
| 190 | + public boolean isGif() { | ||
| 191 | + return isGif; | ||
| 192 | + } | ||
| 193 | + | ||
| 194 | + public View getTarget() { | ||
| 195 | + return target; | ||
| 196 | + } | ||
| 197 | + | ||
| 198 | + public int getWidth() { | ||
| 199 | + if (width <= 0) { | ||
| 200 | + //先去imageview里取,如果为0,则赋值成matchparent | ||
| 201 | + if (target != null) { | ||
| 202 | + width = target.getMeasuredWidth(); | ||
| 203 | + } | ||
| 204 | + if (width <= 0) { | ||
| 205 | + width = GlobalConfig.getWinWidth(); | ||
| 206 | + } | ||
| 207 | + } | ||
| 208 | + return width; | ||
| 209 | + } | ||
| 210 | + | ||
| 211 | + public int getHeight() { | ||
| 212 | + if (height <= 0) { | ||
| 213 | + //先去imageview里取,如果为0,则赋值成matchparent | ||
| 214 | + if (target != null) { | ||
| 215 | + height = target.getMeasuredWidth(); | ||
| 216 | + } | ||
| 217 | + if (height <= 0) { | ||
| 218 | + height = GlobalConfig.getWinHeight(); | ||
| 219 | + } | ||
| 220 | + } | ||
| 221 | + return height; | ||
| 222 | + } | ||
| 223 | + | ||
| 224 | + public int getoWidth() { | ||
| 225 | + return oWidth; | ||
| 226 | + } | ||
| 227 | + | ||
| 228 | + public int getoHeight() { | ||
| 229 | + return oHeight; | ||
| 230 | + } | ||
| 231 | + | ||
| 232 | + public boolean isNeedVignette() { | ||
| 233 | + return isNeedVignette; | ||
| 234 | + } | ||
| 235 | + | ||
| 236 | + public boolean isNeedSketch() { | ||
| 237 | + return isNeedSketch; | ||
| 238 | + } | ||
| 239 | + | ||
| 240 | + public float getPixelationLevel() { | ||
| 241 | + return pixelationLevel; | ||
| 242 | + } | ||
| 243 | + | ||
| 244 | + public boolean isNeedPixelation() { | ||
| 245 | + return isNeedPixelation; | ||
| 246 | + } | ||
| 247 | + | ||
| 248 | + public boolean isNeedInvert() { | ||
| 249 | + return isNeedInvert; | ||
| 250 | + } | ||
| 251 | + | ||
| 252 | + public float getContrastLevel() { | ||
| 253 | + return contrastLevel; | ||
| 254 | + } | ||
| 255 | + | ||
| 256 | + public boolean isNeedContrast() { | ||
| 257 | + return isNeedContrast; | ||
| 258 | + } | ||
| 259 | + | ||
| 260 | + public boolean isNeedSepia() { | ||
| 261 | + return isNeedSepia; | ||
| 262 | + } | ||
| 263 | + | ||
| 264 | + public boolean isNeedToon() { | ||
| 265 | + return isNeedToon; | ||
| 266 | + } | ||
| 267 | + | ||
| 268 | + public boolean isNeedSwirl() { | ||
| 269 | + return isNeedSwirl; | ||
| 270 | + } | ||
| 271 | + | ||
| 272 | + public boolean isNeedGrayscale() { | ||
| 273 | + return isNeedGrayscale; | ||
| 274 | + } | ||
| 275 | + | ||
| 276 | + public boolean isNeedBrightness() { | ||
| 277 | + return isNeedBrightness; | ||
| 278 | + } | ||
| 279 | + | ||
| 280 | + public float getBrightnessLeve() { | ||
| 281 | + return brightnessLeve; | ||
| 282 | + } | ||
| 283 | + | ||
| 284 | + public boolean isNeedBlur() { | ||
| 285 | + return needBlur; | ||
| 286 | + } | ||
| 287 | + | ||
| 288 | + public boolean isNeedFilteColor() { | ||
| 289 | + return needFilteColor; | ||
| 290 | + } | ||
| 291 | + | ||
| 292 | + public int getFilteColor() { | ||
| 293 | + return filteColor; | ||
| 294 | + } | ||
| 295 | + | ||
| 296 | + public int getPriority() { | ||
| 297 | + return priority; | ||
| 298 | + } | ||
| 299 | + | ||
| 300 | + public int getAnimationType() { | ||
| 301 | + return animationType; | ||
| 302 | + } | ||
| 303 | + | ||
| 304 | + public int getAnimationId() { | ||
| 305 | + return animationId; | ||
| 306 | + } | ||
| 307 | + | ||
| 308 | + public ViewPropertyTransition.Animator getAnimation() { | ||
| 309 | + return animation; | ||
| 310 | + } | ||
| 311 | + | ||
| 312 | + public ViewPropertyAnimationFactory getAnimator() { | ||
| 313 | + return animator; | ||
| 314 | + } | ||
| 315 | + | ||
| 316 | + public int getBlurRadius() { | ||
| 317 | + return blurRadius; | ||
| 318 | + } | ||
| 319 | + | ||
| 320 | + public int getPlaceHolderResId() { | ||
| 321 | + return placeHolderResId; | ||
| 322 | + } | ||
| 323 | + | ||
| 324 | + public int getShapeMode() { | ||
| 325 | + return shapeMode; | ||
| 326 | + } | ||
| 327 | + | ||
| 328 | + public int getRectRoundRadius() { | ||
| 329 | + return rectRoundRadius; | ||
| 330 | + } | ||
| 331 | + | ||
| 332 | + public int getScaleMode() { | ||
| 333 | + return scaleMode; | ||
| 334 | + } | ||
| 335 | + | ||
| 336 | + public BitmapListener getBitmapListener() { | ||
| 337 | + return bitmapListener; | ||
| 338 | + } | ||
| 339 | + | ||
| 340 | + public boolean isAsBitmap() { | ||
| 341 | + return asBitmap; | ||
| 342 | + } | ||
| 343 | + | ||
| 344 | + public interface BitmapListener { | ||
| 345 | + void onSuccess(Bitmap bitmap); | ||
| 346 | + | ||
| 347 | + void onFail(); | ||
| 348 | + } | ||
| 349 | + | ||
| 350 | + public void setBitmapListener(BitmapListener bitmapListener) { | ||
| 351 | + this.bitmapListener = ImageUtil.getBitmapListenerProxy(bitmapListener); | ||
| 352 | + } | ||
| 353 | + | ||
| 354 | + private void show() { | ||
| 355 | + GlobalConfig.getLoader().request(this); | ||
| 356 | + } | ||
| 357 | + | ||
| 358 | + public static class ConfigBuilder { | ||
| 359 | + private Context context; | ||
| 360 | + | ||
| 361 | + private boolean ignoreCertificateVerify = GlobalConfig.ignoreCertificateVerify; | ||
| 362 | + | ||
| 363 | + /** | ||
| 364 | + * 图片源 | ||
| 365 | + * 类型 SCHEME 示例 | ||
| 366 | + * 远程图片 http://, https:// HttpURLConnection 或者参考 使用其他网络加载方案 | ||
| 367 | + * 本地文件 file:// FileInputStream | ||
| 368 | + * Content provider content:// ContentResolver | ||
| 369 | + * asset目录下的资源 asset:// AssetManager | ||
| 370 | + * res目录下的资源 res:// Resources.openRawResource | ||
| 371 | + * Uri中指定图片数据 data:mime/type;base64, 数据类型必须符合 rfc2397规定 (仅支持 UTF-8) | ||
| 372 | + * | ||
| 373 | + * @param config | ||
| 374 | + * @return | ||
| 375 | + */ | ||
| 376 | + private String url; | ||
| 377 | + private float thumbnail; | ||
| 378 | + private String filePath; | ||
| 379 | + private File file; | ||
| 380 | + private int resId; | ||
| 381 | + private String rawPath; | ||
| 382 | + private String assertspath; | ||
| 383 | + private String contentProvider; | ||
| 384 | + private boolean isGif = false; | ||
| 385 | + | ||
| 386 | + private View target; | ||
| 387 | + private boolean asBitmap;//只获取bitmap | ||
| 388 | + private BitmapListener bitmapListener; | ||
| 389 | + | ||
| 390 | + // TODO: 2017/4/24 宽高的获取 | ||
| 391 | + private int width; | ||
| 392 | + private int height; | ||
| 393 | + | ||
| 394 | + private int oWidth; //选择加载分辨率的宽 | ||
| 395 | + private int oHeight; //选择加载分辨率的高 | ||
| 396 | + | ||
| 397 | + //滤镜 | ||
| 398 | + private boolean isNeedVignette; //是否需要晕映 | ||
| 399 | + private boolean isNeedSketch; //是否需要素描 | ||
| 400 | + private float pixelationLevel; //是否需要马赛克 | ||
| 401 | + private boolean isNeedPixelation; //是否需要马赛克 | ||
| 402 | + private boolean isNeedInvert; //是否需要胶片 | ||
| 403 | + private float contrastLevel; //是否需要墨画 | ||
| 404 | + private boolean isNeedContrast = false; //是否需要墨画 | ||
| 405 | + private boolean isNeedSepia = false; //是否需要墨画 | ||
| 406 | + private boolean isNeedToon = false; //是否需要油画 | ||
| 407 | + private boolean isNeedSwirl = false; //是否需要漩涡 | ||
| 408 | + private boolean isNeedGrayscale = false; //是否需要亮度 | ||
| 409 | + private boolean isNeedBrightness = false; //是否需要亮度 | ||
| 410 | + private float brightnessLeve; //亮度等级 | ||
| 411 | + private boolean needBlur = false;//是否需要模糊 | ||
| 412 | + private boolean needFilteColor = false;//是否需要滤镜颜色 | ||
| 413 | + private int blurRadius; | ||
| 414 | + | ||
| 415 | + //UI: | ||
| 416 | + private int placeHolderResId; | ||
| 417 | + | ||
| 418 | + private int errorResId; | ||
| 419 | + | ||
| 420 | + private int shapeMode;//默认矩形,可选直角矩形,圆形/椭圆 | ||
| 421 | + private int rectRoundRadius;//圆角矩形时圆角的半径 | ||
| 422 | + | ||
| 423 | + private DiskCacheStrategy diskCacheStrategy; | ||
| 424 | + | ||
| 425 | + private int scaleMode;//填充模式,默认centercrop,可选fitXY,centerInside... | ||
| 426 | + | ||
| 427 | + private int priority; //请求优先级 | ||
| 428 | + | ||
| 429 | + private int filteColor; //滤镜颜色 | ||
| 430 | + | ||
| 431 | + public int animationId; //动画资源id | ||
| 432 | + public int animationType; //动画资源Type | ||
| 433 | + public ViewPropertyTransition.Animator animation; //动画资源 | ||
| 434 | + public ViewPropertyAnimationFactory animator; //动画资源id | ||
| 435 | + | ||
| 436 | + public ConfigBuilder(Context context) { | ||
| 437 | + this.context = context; | ||
| 438 | + } | ||
| 439 | + | ||
| 440 | + public ConfigBuilder ignoreCertificateVerify(boolean ignoreCertificateVerify) { | ||
| 441 | + this.ignoreCertificateVerify = ignoreCertificateVerify; | ||
| 442 | + return this; | ||
| 443 | + } | ||
| 444 | + | ||
| 445 | + /** | ||
| 446 | + * 缩略图 | ||
| 447 | + * | ||
| 448 | + * @param thumbnail | ||
| 449 | + * @return | ||
| 450 | + */ | ||
| 451 | + public ConfigBuilder thumbnail(float thumbnail) { | ||
| 452 | + this.thumbnail = thumbnail; | ||
| 453 | + return this; | ||
| 454 | + } | ||
| 455 | + | ||
| 456 | + /** | ||
| 457 | + * error图 | ||
| 458 | + * | ||
| 459 | + * @param errorResId | ||
| 460 | + * @return | ||
| 461 | + */ | ||
| 462 | + public ConfigBuilder error(int errorResId) { | ||
| 463 | + this.errorResId = errorResId; | ||
| 464 | + return this; | ||
| 465 | + } | ||
| 466 | + | ||
| 467 | + /** | ||
| 468 | + * 设置网络路径 | ||
| 469 | + * | ||
| 470 | + * @param url | ||
| 471 | + * @return | ||
| 472 | + */ | ||
| 473 | + public ConfigBuilder url(String url) { | ||
| 474 | + this.url = url; | ||
| 475 | + if (url.contains("gif")) { | ||
| 476 | + isGif = true; | ||
| 477 | + } | ||
| 478 | + return this; | ||
| 479 | + } | ||
| 480 | + | ||
| 481 | + /** | ||
| 482 | + * 加载SD卡资源 | ||
| 483 | + * | ||
| 484 | + * @param filePath | ||
| 485 | + * @return | ||
| 486 | + */ | ||
| 487 | + public ConfigBuilder file(String filePath) { | ||
| 488 | + if (filePath.startsWith("file:")) { | ||
| 489 | + this.filePath = filePath; | ||
| 490 | + return this; | ||
| 491 | + } | ||
| 492 | + | ||
| 493 | + if (!new File(filePath).exists()) { | ||
| 494 | + //throw new RuntimeException("文件不存在"); | ||
| 495 | + Log.e("imageloader", "文件不存在"); | ||
| 496 | + return this; | ||
| 497 | + } | ||
| 498 | + | ||
| 499 | + this.filePath = filePath; | ||
| 500 | + if (filePath.contains("gif")) { | ||
| 501 | + isGif = true; | ||
| 502 | + } | ||
| 503 | + return this; | ||
| 504 | + } | ||
| 505 | + | ||
| 506 | + /** | ||
| 507 | + * 加载SD卡资源 | ||
| 508 | + * | ||
| 509 | + * @param file | ||
| 510 | + * @return | ||
| 511 | + */ | ||
| 512 | + public ConfigBuilder file(File file) { | ||
| 513 | + this.file = file; | ||
| 514 | + | ||
| 515 | + return this; | ||
| 516 | + } | ||
| 517 | + | ||
| 518 | + /** | ||
| 519 | + * 加载drawable资源 | ||
| 520 | + * | ||
| 521 | + * @param resId | ||
| 522 | + * @return | ||
| 523 | + */ | ||
| 524 | + public ConfigBuilder res(int resId) { | ||
| 525 | + this.resId = resId; | ||
| 526 | + return this; | ||
| 527 | + } | ||
| 528 | + | ||
| 529 | + /** | ||
| 530 | + * 加载ContentProvider资源 | ||
| 531 | + * | ||
| 532 | + * @param contentProvider | ||
| 533 | + * @return | ||
| 534 | + */ | ||
| 535 | + public ConfigBuilder content(String contentProvider) { | ||
| 536 | + if (contentProvider.startsWith("content:")) { | ||
| 537 | + this.contentProvider = contentProvider; | ||
| 538 | + return this; | ||
| 539 | + } | ||
| 540 | + | ||
| 541 | + if (contentProvider.contains("gif")) { | ||
| 542 | + isGif = true; | ||
| 543 | + } | ||
| 544 | + | ||
| 545 | + return this; | ||
| 546 | + } | ||
| 547 | + | ||
| 548 | + /** | ||
| 549 | + * 加载raw资源 | ||
| 550 | + * | ||
| 551 | + * @param rawPath | ||
| 552 | + * @return | ||
| 553 | + */ | ||
| 554 | + public ConfigBuilder raw(String rawPath) { | ||
| 555 | + | ||
| 556 | + this.rawPath = rawPath; | ||
| 557 | + | ||
| 558 | + if (rawPath.contains("gif")) { | ||
| 559 | + isGif = true; | ||
| 560 | + } | ||
| 561 | + | ||
| 562 | + return this; | ||
| 563 | + } | ||
| 564 | + | ||
| 565 | + /** | ||
| 566 | + * 加载asserts资源 | ||
| 567 | + * | ||
| 568 | + * @param assertspath | ||
| 569 | + * @return | ||
| 570 | + */ | ||
| 571 | + public ConfigBuilder asserts(String assertspath) { | ||
| 572 | + this.assertspath = assertspath; | ||
| 573 | + | ||
| 574 | + if (assertspath.contains("gif")) { | ||
| 575 | + isGif = true; | ||
| 576 | + } | ||
| 577 | + | ||
| 578 | + return this; | ||
| 579 | + } | ||
| 580 | + | ||
| 581 | + public void into(View targetView) { | ||
| 582 | + this.target = targetView; | ||
| 583 | + new SingleConfig(this).show(); | ||
| 584 | + } | ||
| 585 | + | ||
| 586 | + public void asBitmap(BitmapListener bitmapListener) { | ||
| 587 | + this.bitmapListener = ImageUtil.getBitmapListenerProxy(bitmapListener); | ||
| 588 | + this.asBitmap = true; | ||
| 589 | + new SingleConfig(this).show(); | ||
| 590 | + } | ||
| 591 | + | ||
| 592 | + /** | ||
| 593 | + * 加载图片的分辨率 | ||
| 594 | + * | ||
| 595 | + * @param oWidth | ||
| 596 | + * @param oHeight | ||
| 597 | + * @return | ||
| 598 | + */ | ||
| 599 | + public ConfigBuilder override(int oWidth, int oHeight) { | ||
| 600 | + this.oWidth = ImageUtil.dip2px(oWidth); | ||
| 601 | + this.oHeight = ImageUtil.dip2px(oHeight); | ||
| 602 | + return this; | ||
| 603 | + } | ||
| 604 | + | ||
| 605 | + /** | ||
| 606 | + * 占位图 | ||
| 607 | + * | ||
| 608 | + * @param placeHolderResId | ||
| 609 | + * @return | ||
| 610 | + */ | ||
| 611 | + public ConfigBuilder placeHolder(int placeHolderResId) { | ||
| 612 | + this.placeHolderResId = placeHolderResId; | ||
| 613 | + return this; | ||
| 614 | + } | ||
| 615 | + | ||
| 616 | + | ||
| 617 | + /** | ||
| 618 | + * 是否需要高斯模糊 | ||
| 619 | + * | ||
| 620 | + * @return | ||
| 621 | + */ | ||
| 622 | + public ConfigBuilder blur(int blurRadius) { | ||
| 623 | + this.needBlur = true; | ||
| 624 | + this.blurRadius = blurRadius; | ||
| 625 | + return this; | ||
| 626 | + } | ||
| 627 | + | ||
| 628 | + /** | ||
| 629 | + * 圆角 | ||
| 630 | + | ||
| 631 | + * @return | ||
| 632 | + */ | ||
| 633 | + public ConfigBuilder asCircle() { | ||
| 634 | + this.shapeMode = ShapeMode.OVAL; | ||
| 635 | + return this; | ||
| 636 | + } | ||
| 637 | + | ||
| 638 | + /** | ||
| 639 | + * 形状为圆角矩形时的圆角半径 | ||
| 640 | + * | ||
| 641 | + * @param rectRoundRadius | ||
| 642 | + * @return | ||
| 643 | + */ | ||
| 644 | + public ConfigBuilder rectRoundCorner(int rectRoundRadius) { | ||
| 645 | + this.rectRoundRadius = ImageUtil.dip2px(rectRoundRadius); | ||
| 646 | + this.shapeMode = ShapeMode.RECT_ROUND; | ||
| 647 | + return this; | ||
| 648 | + } | ||
| 649 | + | ||
| 650 | + | ||
| 651 | + /** | ||
| 652 | + * 正方形 | ||
| 653 | + * | ||
| 654 | + * @return | ||
| 655 | + */ | ||
| 656 | + public ConfigBuilder asSquare() { | ||
| 657 | + this.shapeMode = ShapeMode.SQUARE; | ||
| 658 | + return this; | ||
| 659 | + } | ||
| 660 | + | ||
| 661 | + | ||
| 662 | + /** | ||
| 663 | + * 磁盘缓存 | ||
| 664 | + */ | ||
| 665 | + public ConfigBuilder diskCacheStrategy(DiskCacheStrategy diskCacheStrategy) { | ||
| 666 | + this.diskCacheStrategy = diskCacheStrategy; | ||
| 667 | + return this; | ||
| 668 | + } | ||
| 669 | + | ||
| 670 | + /** | ||
| 671 | + * 拉伸/裁剪模式 | ||
| 672 | + * | ||
| 673 | + * @param scaleMode 取值ScaleMode | ||
| 674 | + * @return | ||
| 675 | + */ | ||
| 676 | + public ConfigBuilder scale(int scaleMode) { | ||
| 677 | + this.scaleMode = scaleMode; | ||
| 678 | + return this; | ||
| 679 | + } | ||
| 680 | + | ||
| 681 | + | ||
| 682 | + public ConfigBuilder animate(int animationId) { | ||
| 683 | + this.animationType = AnimationMode.ANIMATIONID; | ||
| 684 | + this.animationId = animationId; | ||
| 685 | + return this; | ||
| 686 | + } | ||
| 687 | + | ||
| 688 | + public ConfigBuilder animate(ViewPropertyAnimationFactory animator) { | ||
| 689 | + this.animationType = AnimationMode.ANIMATOR; | ||
| 690 | + this.animator = animator; | ||
| 691 | + return this; | ||
| 692 | + } | ||
| 693 | + | ||
| 694 | + public ConfigBuilder animate(ViewPropertyTransition.Animator animation) { | ||
| 695 | + this.animationType = AnimationMode.ANIMATION; | ||
| 696 | + this.animation = animation; | ||
| 697 | + return this; | ||
| 698 | + } | ||
| 699 | + | ||
| 700 | + public ConfigBuilder priority(int priority) { | ||
| 701 | + this.priority = priority; | ||
| 702 | + | ||
| 703 | + return this; | ||
| 704 | + } | ||
| 705 | + | ||
| 706 | + public ConfigBuilder colorFilter(int filteColor) { | ||
| 707 | + this.filteColor = filteColor; | ||
| 708 | + this.needFilteColor = true; | ||
| 709 | + return this; | ||
| 710 | + } | ||
| 711 | + | ||
| 712 | + public ConfigBuilder brightnessFilter(float level) { | ||
| 713 | + this.isNeedBrightness = true; | ||
| 714 | + this.brightnessLeve = level; | ||
| 715 | + return this; | ||
| 716 | + } | ||
| 717 | + | ||
| 718 | + public ConfigBuilder grayscaleFilter() { | ||
| 719 | + this.isNeedGrayscale = true; | ||
| 720 | + return this; | ||
| 721 | + } | ||
| 722 | + | ||
| 723 | + public ConfigBuilder swirlFilter() { | ||
| 724 | + this.isNeedSwirl = true; | ||
| 725 | + return this; | ||
| 726 | + } | ||
| 727 | + | ||
| 728 | + public ConfigBuilder toonFilter() { | ||
| 729 | + this.isNeedToon = true; | ||
| 730 | + return this; | ||
| 731 | + } | ||
| 732 | + | ||
| 733 | + public ConfigBuilder sepiaFilter() { | ||
| 734 | + this.isNeedSepia = true; | ||
| 735 | + return this; | ||
| 736 | + } | ||
| 737 | + | ||
| 738 | + public ConfigBuilder contrastFilter(float constrasrLevel) { | ||
| 739 | + this.contrastLevel = constrasrLevel; | ||
| 740 | + this.isNeedContrast = true; | ||
| 741 | + return this; | ||
| 742 | + } | ||
| 743 | + | ||
| 744 | + public ConfigBuilder invertFilter() { | ||
| 745 | + this.isNeedInvert = true; | ||
| 746 | + return this; | ||
| 747 | + } | ||
| 748 | + | ||
| 749 | + public ConfigBuilder pixelationFilter(float pixelationLevel) { | ||
| 750 | + this.pixelationLevel = pixelationLevel; | ||
| 751 | + this.isNeedPixelation = true; | ||
| 752 | + return this; | ||
| 753 | + } | ||
| 754 | + | ||
| 755 | + public ConfigBuilder sketchFilter() { | ||
| 756 | + this.isNeedSketch = true; | ||
| 757 | + return this; | ||
| 758 | + } | ||
| 759 | + | ||
| 760 | + public ConfigBuilder vignetteFilter() { | ||
| 761 | + this.isNeedVignette = true; | ||
| 762 | + return this; | ||
| 763 | + } | ||
| 764 | + | ||
| 765 | + | ||
| 766 | + } | ||
| 767 | + | ||
| 768 | + | ||
| 769 | +} |
core/imageload/src/main/java/com/cnlive/core/imageload/loader/GlideLoader.java
0 → 100644
| 1 | +package com.cnlive.core.imageload.loader; | ||
| 2 | + | ||
| 3 | +import android.content.Context; | ||
| 4 | +import android.graphics.Bitmap; | ||
| 5 | +import android.graphics.PointF; | ||
| 6 | +import android.graphics.drawable.Drawable; | ||
| 7 | +import android.net.Uri; | ||
| 8 | +import android.text.TextUtils; | ||
| 9 | +import android.util.Log; | ||
| 10 | +import android.view.View; | ||
| 11 | +import android.widget.ImageView; | ||
| 12 | + | ||
| 13 | +import com.bumptech.glide.GenericTransitionOptions; | ||
| 14 | +import com.bumptech.glide.Glide; | ||
| 15 | +import com.bumptech.glide.GlideBuilder; | ||
| 16 | +import com.bumptech.glide.MemoryCategory; | ||
| 17 | +import com.bumptech.glide.Priority; | ||
| 18 | +import com.bumptech.glide.RequestBuilder; | ||
| 19 | +import com.bumptech.glide.RequestManager; | ||
| 20 | +import com.bumptech.glide.load.Transformation; | ||
| 21 | +import com.bumptech.glide.load.engine.cache.ExternalCacheDiskCacheFactory; | ||
| 22 | +import com.bumptech.glide.load.engine.cache.InternalCacheDiskCacheFactory; | ||
| 23 | +import com.bumptech.glide.request.RequestOptions; | ||
| 24 | +import com.bumptech.glide.request.target.SimpleTarget; | ||
| 25 | +import com.bumptech.glide.request.transition.Transition; | ||
| 26 | +import com.bumptech.glide.request.transition.ViewPropertyTransition; | ||
| 27 | +import com.cnlive.core.imageload.R; | ||
| 28 | +import com.cnlive.core.imageload.config.AnimationMode; | ||
| 29 | +import com.cnlive.core.imageload.config.GlobalConfig; | ||
| 30 | +import com.cnlive.core.imageload.config.PriorityMode; | ||
| 31 | +import com.cnlive.core.imageload.config.ScaleMode; | ||
| 32 | +import com.cnlive.core.imageload.config.ShapeMode; | ||
| 33 | +import com.cnlive.core.imageload.config.SingleConfig; | ||
| 34 | +import com.cnlive.core.imageload.util.DownLoadImageService; | ||
| 35 | +import com.cnlive.core.imageload.util.ImageUtil; | ||
| 36 | +import com.cnlive.libs.base.application.GlideApp; | ||
| 37 | + | ||
| 38 | +import androidx.annotation.Nullable; | ||
| 39 | +import jp.wasabeef.glide.transformations.BlurTransformation; | ||
| 40 | +import jp.wasabeef.glide.transformations.ColorFilterTransformation; | ||
| 41 | +import jp.wasabeef.glide.transformations.CropCircleTransformation; | ||
| 42 | +import jp.wasabeef.glide.transformations.CropSquareTransformation; | ||
| 43 | +import jp.wasabeef.glide.transformations.GrayscaleTransformation; | ||
| 44 | +import jp.wasabeef.glide.transformations.RoundedCornersTransformation; | ||
| 45 | +import jp.wasabeef.glide.transformations.gpu.BrightnessFilterTransformation; | ||
| 46 | +import jp.wasabeef.glide.transformations.gpu.ContrastFilterTransformation; | ||
| 47 | +import jp.wasabeef.glide.transformations.gpu.InvertFilterTransformation; | ||
| 48 | +import jp.wasabeef.glide.transformations.gpu.PixelationFilterTransformation; | ||
| 49 | +import jp.wasabeef.glide.transformations.gpu.SepiaFilterTransformation; | ||
| 50 | +import jp.wasabeef.glide.transformations.gpu.SketchFilterTransformation; | ||
| 51 | +import jp.wasabeef.glide.transformations.gpu.SwirlFilterTransformation; | ||
| 52 | +import jp.wasabeef.glide.transformations.gpu.ToonFilterTransformation; | ||
| 53 | +import jp.wasabeef.glide.transformations.gpu.VignetteFilterTransformation; | ||
| 54 | + | ||
| 55 | +/** | ||
| 56 | + * created by hanyayun | ||
| 57 | + * on 2019/11/19 | ||
| 58 | + */ | ||
| 59 | +public class GlideLoader implements ILoader{ | ||
| 60 | + | ||
| 61 | + /** | ||
| 62 | + * @param context 上下文 | ||
| 63 | + * @param cacheSizeInM Glide默认磁盘缓存最大容量250MB | ||
| 64 | + * @param memoryCategory 调整内存缓存的大小 LOW(0.5f) / NORMAL(1f) / HIGH(1.5f); | ||
| 65 | + * @param isInternalCD true 磁盘缓存到应用的内部目录 / false 磁盘缓存到外部存 | ||
| 66 | + */ | ||
| 67 | + @Override | ||
| 68 | + public void init(Context context, int cacheSizeInM, MemoryCategory memoryCategory, boolean isInternalCD) { | ||
| 69 | + Glide.get(context).setMemoryCategory(memoryCategory); //如果在应用当中想要调整内存缓存的大小,开发者可以通过如下方式: | ||
| 70 | + GlideBuilder builder = new GlideBuilder(); | ||
| 71 | + if (isInternalCD) { | ||
| 72 | + builder.setDiskCache(new InternalCacheDiskCacheFactory(context, cacheSizeInM * 1024 * 1024)); | ||
| 73 | + } else { | ||
| 74 | + builder.setDiskCache(new ExternalCacheDiskCacheFactory(context, cacheSizeInM * 1024 * 1024)); | ||
| 75 | + } | ||
| 76 | + } | ||
| 77 | + | ||
| 78 | + @Override | ||
| 79 | + public void request(SingleConfig config) { | ||
| 80 | + RequestManager requestManager = Glide.with(config.getContext()); | ||
| 81 | + RequestBuilder<Drawable> request = getDrawableTypeRequest(config, requestManager); | ||
| 82 | + | ||
| 83 | + if (config.isAsBitmap()) { | ||
| 84 | + SimpleTarget target = new SimpleTarget<Bitmap>(config.getWidth(), config.getHeight()) { | ||
| 85 | + @Override | ||
| 86 | + public void onResourceReady(Bitmap bitmap, Transition glideAnimation) { | ||
| 87 | + config.getBitmapListener().onSuccess(bitmap); | ||
| 88 | + } | ||
| 89 | + }; | ||
| 90 | + | ||
| 91 | + setShapeModeAndBlur(config, request); | ||
| 92 | + | ||
| 93 | + if (config.getDiskCacheStrategy() != null) { | ||
| 94 | + request.diskCacheStrategy(config.getDiskCacheStrategy()); | ||
| 95 | + } | ||
| 96 | + | ||
| 97 | + request.into(target); | ||
| 98 | + | ||
| 99 | + } else { | ||
| 100 | + | ||
| 101 | + if (request == null) { | ||
| 102 | + return; | ||
| 103 | + } | ||
| 104 | + | ||
| 105 | + if (ImageUtil.shouldSetPlaceHolder(config)) { | ||
| 106 | + request.placeholder(config.getPlaceHolderResId()); | ||
| 107 | + } | ||
| 108 | + | ||
| 109 | + int scaleMode = config.getScaleMode(); | ||
| 110 | + | ||
| 111 | + switch (scaleMode) { | ||
| 112 | + case ScaleMode.CENTER_CROP: | ||
| 113 | + request.centerCrop(); | ||
| 114 | + break; | ||
| 115 | + case ScaleMode.FIT_CENTER: | ||
| 116 | + request.fitCenter(); | ||
| 117 | + break; | ||
| 118 | + default: | ||
| 119 | + request.fitCenter(); | ||
| 120 | + break; | ||
| 121 | + } | ||
| 122 | + | ||
| 123 | + setShapeModeAndBlur(config, request); | ||
| 124 | + | ||
| 125 | + //设置缩略图 | ||
| 126 | + if (config.getThumbnail() != 0) { | ||
| 127 | + request.thumbnail(config.getThumbnail()); | ||
| 128 | + } | ||
| 129 | + | ||
| 130 | + //设置图片加载的分辨 sp | ||
| 131 | + if (config.getoWidth() != 0 && config.getoHeight() != 0) { | ||
| 132 | + request.override(config.getoWidth(), config.getoHeight()); | ||
| 133 | + } | ||
| 134 | + | ||
| 135 | + //是否跳过磁盘存储 | ||
| 136 | + if (config.getDiskCacheStrategy() != null) { | ||
| 137 | + request.diskCacheStrategy(config.getDiskCacheStrategy()); | ||
| 138 | + } | ||
| 139 | + | ||
| 140 | + //设置图片加载动画 | ||
| 141 | + setAnimator(config, request); | ||
| 142 | + | ||
| 143 | + //设置图片加载优先级 | ||
| 144 | + setPriority(config, request); | ||
| 145 | + | ||
| 146 | + if (config.getErrorResId() > 0) { | ||
| 147 | + request.error(config.getErrorResId()); | ||
| 148 | + } | ||
| 149 | + | ||
| 150 | +// if(config.isGif()){ | ||
| 151 | +// request.asGif(); | ||
| 152 | +// } | ||
| 153 | + | ||
| 154 | + if (config.getTarget() instanceof ImageView) { | ||
| 155 | + request.into((ImageView) config.getTarget()); | ||
| 156 | + | ||
| 157 | + } | ||
| 158 | + } | ||
| 159 | + } | ||
| 160 | + | ||
| 161 | + /** | ||
| 162 | + * 设置加载优先级 | ||
| 163 | + * | ||
| 164 | + * @param config | ||
| 165 | + * @param request | ||
| 166 | + */ | ||
| 167 | + private void setPriority(SingleConfig config, RequestBuilder<Drawable> request) { | ||
| 168 | + switch (config.getPriority()) { | ||
| 169 | + case PriorityMode.PRIORITY_LOW: | ||
| 170 | + request.priority(Priority.LOW); | ||
| 171 | + break; | ||
| 172 | + case PriorityMode.PRIORITY_NORMAL: | ||
| 173 | + request.priority(Priority.NORMAL); | ||
| 174 | + break; | ||
| 175 | + case PriorityMode.PRIORITY_HIGH: | ||
| 176 | + request.priority(Priority.HIGH); | ||
| 177 | + break; | ||
| 178 | + case PriorityMode.PRIORITY_IMMEDIATE: | ||
| 179 | + request.priority(Priority.IMMEDIATE); | ||
| 180 | + break; | ||
| 181 | + default: | ||
| 182 | + request.priority(Priority.IMMEDIATE); | ||
| 183 | + break; | ||
| 184 | + } | ||
| 185 | + } | ||
| 186 | + | ||
| 187 | + /** | ||
| 188 | + * 设置加载进入动画 | ||
| 189 | + * | ||
| 190 | + * @param config | ||
| 191 | + * @param request | ||
| 192 | + */ | ||
| 193 | + private void setAnimator(SingleConfig config, RequestBuilder<Drawable> request) { | ||
| 194 | + if (config.getAnimationType() == AnimationMode.ANIMATIONID) { | ||
| 195 | + request.transition(GenericTransitionOptions.with(config.getAnimationId())); | ||
| 196 | +// request.anaimate(config.getAnimationId()); | ||
| 197 | + } else if (config.getAnimationType() == AnimationMode.ANIMATOR) { | ||
| 198 | + request.transition(GenericTransitionOptions.with(config.getAnimator())); | ||
| 199 | +// request.animate(config.getAnimator()); | ||
| 200 | + } else if (config.getAnimationType() == AnimationMode.ANIMATION) { | ||
| 201 | + request.transition(GenericTransitionOptions.with(config.getAnimation())); | ||
| 202 | +// request.animate(config.getAnimation()); | ||
| 203 | + } | ||
| 204 | + } | ||
| 205 | + | ||
| 206 | + @Nullable | ||
| 207 | + private RequestBuilder<Drawable> getDrawableTypeRequest(SingleConfig config, RequestManager requestManager) { | ||
| 208 | + RequestBuilder<Drawable> request = null; | ||
| 209 | + if (!TextUtils.isEmpty(config.getUrl())) { | ||
| 210 | + request = requestManager.load(ImageUtil.appendUrl(config.getUrl())); | ||
| 211 | + Log.e("TAG","getUrl : "+config.getUrl()); | ||
| 212 | + } else if (!TextUtils.isEmpty(config.getFilePath())) { | ||
| 213 | + request = requestManager.load(ImageUtil.appendUrl(config.getFilePath())); | ||
| 214 | + Log.e("TAG","getFilePath : "+config.getFilePath()); | ||
| 215 | + } else if (!TextUtils.isEmpty(config.getContentProvider())) { | ||
| 216 | + request = requestManager.load(Uri.parse(config.getContentProvider())); | ||
| 217 | + Log.e("TAG","getContentProvider : "+config.getContentProvider()); | ||
| 218 | + } else if (config.getResId() > 0) { | ||
| 219 | + request = requestManager.load(config.getResId()); | ||
| 220 | + Log.e("TAG","getResId : "+config.getResId()); | ||
| 221 | + } else if(config.getFile() != null){ | ||
| 222 | + request = requestManager.load(config.getFile()); | ||
| 223 | + Log.e("TAG","getFile : "+config.getFile()); | ||
| 224 | + } else if(!TextUtils.isEmpty(config.getAssertspath())){ | ||
| 225 | + request = requestManager.load(config.getAssertspath()); | ||
| 226 | + Log.e("TAG","getAssertspath : "+config.getAssertspath()); | ||
| 227 | + } else if(!TextUtils.isEmpty(config.getRawPath())){ | ||
| 228 | + request = requestManager.load(config.getRawPath()); | ||
| 229 | + Log.e("TAG","getRawPath : "+config.getRawPath()); | ||
| 230 | + } | ||
| 231 | + return request; | ||
| 232 | + } | ||
| 233 | + | ||
| 234 | + /** | ||
| 235 | + * 设置图片滤镜和形状 | ||
| 236 | + * | ||
| 237 | + * @param config | ||
| 238 | + * @param request | ||
| 239 | + */ | ||
| 240 | + private void setShapeModeAndBlur(SingleConfig config, RequestBuilder<Drawable> request) { | ||
| 241 | + | ||
| 242 | + int count = 0; | ||
| 243 | + | ||
| 244 | + Transformation[] transformation = new Transformation[statisticsCount(config)]; | ||
| 245 | + | ||
| 246 | + if (config.isNeedBlur()) { | ||
| 247 | + transformation[count] = new BlurTransformation(config.getBlurRadius()); | ||
| 248 | + count++; | ||
| 249 | + } | ||
| 250 | + | ||
| 251 | + if (config.isNeedBrightness()) { | ||
| 252 | + transformation[count] = new BrightnessFilterTransformation(config.getBrightnessLeve()); //亮度 | ||
| 253 | + count++; | ||
| 254 | + } | ||
| 255 | + | ||
| 256 | + if (config.isNeedGrayscale()) { | ||
| 257 | + transformation[count] = new GrayscaleTransformation(); //黑白效果 | ||
| 258 | + count++; | ||
| 259 | + } | ||
| 260 | + | ||
| 261 | + if (config.isNeedFilteColor()) { | ||
| 262 | + transformation[count] = new ColorFilterTransformation(config.getFilteColor()); | ||
| 263 | + count++; | ||
| 264 | + } | ||
| 265 | + | ||
| 266 | + if (config.isNeedSwirl()) { | ||
| 267 | + transformation[count] = new SwirlFilterTransformation( 0.5f, 1.0f, new PointF(0.5f, 0.5f)); //漩涡 | ||
| 268 | + count++; | ||
| 269 | + } | ||
| 270 | + | ||
| 271 | + if (config.isNeedToon()) { | ||
| 272 | + transformation[count] = new ToonFilterTransformation(); //油画 | ||
| 273 | + count++; | ||
| 274 | + } | ||
| 275 | + | ||
| 276 | + if (config.isNeedSepia()) { | ||
| 277 | + transformation[count] = new SepiaFilterTransformation(); //墨画 | ||
| 278 | + count++; | ||
| 279 | + } | ||
| 280 | + | ||
| 281 | + if (config.isNeedContrast()) { | ||
| 282 | + transformation[count] = new ContrastFilterTransformation( config.getContrastLevel()); //锐化 | ||
| 283 | + count++; | ||
| 284 | + } | ||
| 285 | + | ||
| 286 | + if (config.isNeedInvert()) { | ||
| 287 | + transformation[count] = new InvertFilterTransformation(); //胶片 | ||
| 288 | + count++; | ||
| 289 | + } | ||
| 290 | + | ||
| 291 | + if (config.isNeedPixelation()) { | ||
| 292 | + transformation[count] =new PixelationFilterTransformation(config.getPixelationLevel()); //马赛克 | ||
| 293 | + count++; | ||
| 294 | + } | ||
| 295 | + | ||
| 296 | + if (config.isNeedSketch()) { | ||
| 297 | + transformation[count] =new SketchFilterTransformation(); //素描 | ||
| 298 | + count++; | ||
| 299 | + } | ||
| 300 | + | ||
| 301 | + if (config.isNeedVignette()) { | ||
| 302 | + transformation[count] =new VignetteFilterTransformation(new PointF(0.5f, 0.5f), | ||
| 303 | + new float[] { 0.0f, 0.0f, 0.0f }, 0f, 0.75f);//晕映 | ||
| 304 | + count++; | ||
| 305 | + } | ||
| 306 | + | ||
| 307 | + switch (config.getShapeMode()) { | ||
| 308 | + case ShapeMode.RECT: | ||
| 309 | + | ||
| 310 | + break; | ||
| 311 | + case ShapeMode.RECT_ROUND: | ||
| 312 | + transformation[count] = new RoundedCornersTransformation | ||
| 313 | + (config.getRectRoundRadius(), 0, RoundedCornersTransformation.CornerType.ALL); | ||
| 314 | + count++; | ||
| 315 | + break; | ||
| 316 | + case ShapeMode.OVAL: | ||
| 317 | + transformation[count] = new CropCircleTransformation(); | ||
| 318 | + count++; | ||
| 319 | + break; | ||
| 320 | + | ||
| 321 | + case ShapeMode.SQUARE: | ||
| 322 | + transformation[count] = new CropSquareTransformation(); | ||
| 323 | + count++; | ||
| 324 | + break; | ||
| 325 | + } | ||
| 326 | + | ||
| 327 | + if (transformation.length != 0) { | ||
| 328 | + request.transform(transformation); | ||
| 329 | + | ||
| 330 | + } | ||
| 331 | + | ||
| 332 | + } | ||
| 333 | + | ||
| 334 | + | ||
| 335 | + private int statisticsCount(SingleConfig config) { | ||
| 336 | + int count = 0; | ||
| 337 | + | ||
| 338 | + if (config.getShapeMode() == ShapeMode.OVAL || config.getShapeMode() == ShapeMode.RECT_ROUND || config.getShapeMode() == ShapeMode.SQUARE) { | ||
| 339 | + count++; | ||
| 340 | + } | ||
| 341 | + | ||
| 342 | + if (config.isNeedBlur()) { | ||
| 343 | + count++; | ||
| 344 | + } | ||
| 345 | + | ||
| 346 | + if (config.isNeedFilteColor()) { | ||
| 347 | + count++; | ||
| 348 | + } | ||
| 349 | + | ||
| 350 | + if (config.isNeedBrightness()) { | ||
| 351 | + count++; | ||
| 352 | + } | ||
| 353 | + | ||
| 354 | + if (config.isNeedGrayscale()) { | ||
| 355 | + count++; | ||
| 356 | + } | ||
| 357 | + | ||
| 358 | + if (config.isNeedSwirl()) { | ||
| 359 | + count++; | ||
| 360 | + } | ||
| 361 | + | ||
| 362 | + if (config.isNeedToon()) { | ||
| 363 | + count++; | ||
| 364 | + } | ||
| 365 | + | ||
| 366 | + if (config.isNeedSepia()) { | ||
| 367 | + count++; | ||
| 368 | + } | ||
| 369 | + | ||
| 370 | + if (config.isNeedContrast()) { | ||
| 371 | + count++; | ||
| 372 | + } | ||
| 373 | + | ||
| 374 | + if (config.isNeedInvert()) { | ||
| 375 | + count++; | ||
| 376 | + } | ||
| 377 | + | ||
| 378 | + if (config.isNeedPixelation()) { | ||
| 379 | + count++; | ||
| 380 | + } | ||
| 381 | + | ||
| 382 | + if (config.isNeedSketch()) { | ||
| 383 | + count++; | ||
| 384 | + } | ||
| 385 | + | ||
| 386 | + if (config.isNeedVignette()) { | ||
| 387 | + count++; | ||
| 388 | + } | ||
| 389 | + | ||
| 390 | + return count; | ||
| 391 | + } | ||
| 392 | + | ||
| 393 | + @Override | ||
| 394 | + public void pause() { | ||
| 395 | + Glide.with(GlobalConfig.context).pauseRequestsRecursive(); | ||
| 396 | + } | ||
| 397 | + | ||
| 398 | + @Override | ||
| 399 | + public void resume() { | ||
| 400 | + Glide.with(GlobalConfig.context).resumeRequestsRecursive(); | ||
| 401 | + } | ||
| 402 | + | ||
| 403 | + @Override | ||
| 404 | + public void clearDiskCache() { | ||
| 405 | + Glide.get(GlobalConfig.context).clearDiskCache(); | ||
| 406 | + } | ||
| 407 | + | ||
| 408 | + @Override | ||
| 409 | + public void clearMomoryCache(Context context,View view) { | ||
| 410 | + Glide.with(context).clear(view); | ||
| 411 | + } | ||
| 412 | + | ||
| 413 | + @Override | ||
| 414 | + public void clearMomory() { | ||
| 415 | + Glide.get(GlobalConfig.context).clearMemory(); | ||
| 416 | + } | ||
| 417 | + | ||
| 418 | + @Override | ||
| 419 | + public boolean isCached(String url) { | ||
| 420 | + return false; | ||
| 421 | + } | ||
| 422 | + | ||
| 423 | + @Override | ||
| 424 | + public void trimMemory(int level) { | ||
| 425 | + Glide.with(GlobalConfig.context).onTrimMemory(level); | ||
| 426 | + } | ||
| 427 | + | ||
| 428 | + @Override | ||
| 429 | + public void clearAllMemoryCaches() { | ||
| 430 | + Glide.with(GlobalConfig.context).onLowMemory(); | ||
| 431 | + } | ||
| 432 | + | ||
| 433 | + @Override | ||
| 434 | + public void saveImageIntoGallery(DownLoadImageService downLoadImageService) { | ||
| 435 | + new Thread(downLoadImageService).start(); | ||
| 436 | + } | ||
| 437 | +} |
core/imageload/src/main/java/com/cnlive/core/imageload/loader/ILoader.java
0 → 100644
| 1 | +package com.cnlive.core.imageload.loader; | ||
| 2 | + | ||
| 3 | +import android.content.Context; | ||
| 4 | +import android.view.View; | ||
| 5 | + | ||
| 6 | +import com.bumptech.glide.MemoryCategory; | ||
| 7 | +import com.cnlive.core.imageload.config.SingleConfig; | ||
| 8 | +import com.cnlive.core.imageload.util.DownLoadImageService; | ||
| 9 | + | ||
| 10 | +/** | ||
| 11 | + * created by hanyayun | ||
| 12 | + * on 2019/11/19 | ||
| 13 | + */ | ||
| 14 | +public interface ILoader { | ||
| 15 | + | ||
| 16 | + void init(Context context, int cacheSizeInM, MemoryCategory memoryCategory, boolean isInternalCD); | ||
| 17 | + | ||
| 18 | + void request(SingleConfig config); | ||
| 19 | + | ||
| 20 | + void pause(); | ||
| 21 | + | ||
| 22 | + void resume(); | ||
| 23 | + | ||
| 24 | + void clearDiskCache(); | ||
| 25 | + | ||
| 26 | + void clearMomoryCache(Context context,View view); | ||
| 27 | + | ||
| 28 | + void clearMomory(); | ||
| 29 | + | ||
| 30 | + boolean isCached(String url); | ||
| 31 | + | ||
| 32 | + void trimMemory(int level); | ||
| 33 | + | ||
| 34 | + void clearAllMemoryCaches(); | ||
| 35 | + | ||
| 36 | + void saveImageIntoGallery(DownLoadImageService downLoadImageService); | ||
| 37 | +} |
core/imageload/src/main/java/com/cnlive/core/imageload/loader/ImageLoader.java
0 → 100644
| 1 | +package com.cnlive.core.imageload.loader; | ||
| 2 | + | ||
| 3 | +import android.content.Context; | ||
| 4 | +import android.view.View; | ||
| 5 | + | ||
| 6 | +import com.bumptech.glide.MemoryCategory; | ||
| 7 | +import com.cnlive.core.imageload.config.GlobalConfig; | ||
| 8 | +import com.cnlive.core.imageload.config.SingleConfig; | ||
| 9 | +import com.cnlive.core.imageload.util.DownLoadImageService; | ||
| 10 | + | ||
| 11 | + | ||
| 12 | +/** | ||
| 13 | + * created by hanyayun | ||
| 14 | + * on 2019/11/22 | ||
| 15 | + */ | ||
| 16 | +public class ImageLoader { | ||
| 17 | + | ||
| 18 | + public static Context context; | ||
| 19 | + /** | ||
| 20 | + * 默认最大缓存 | ||
| 21 | + */ | ||
| 22 | + public static int CACHE_IMAGE_SIZE = 250; | ||
| 23 | + | ||
| 24 | + public static void init(final Context context) { | ||
| 25 | + init(context, CACHE_IMAGE_SIZE); | ||
| 26 | + } | ||
| 27 | + | ||
| 28 | + public static void init(final Context context, int cacheSizeInM) { | ||
| 29 | + init(context, cacheSizeInM, MemoryCategory.NORMAL); | ||
| 30 | + } | ||
| 31 | + | ||
| 32 | + public static void init(final Context context, int cacheSizeInM, MemoryCategory memoryCategory) { | ||
| 33 | + init(context, cacheSizeInM, memoryCategory, true); | ||
| 34 | + } | ||
| 35 | + | ||
| 36 | + /** | ||
| 37 | + * @param context 上下文 | ||
| 38 | + * @param cacheSizeInM Glide默认磁盘缓存最大容量250MB | ||
| 39 | + * @param memoryCategory 调整内存缓存的大小 LOW(0.5f) / NORMAL(1f) / HIGH(1.5f); | ||
| 40 | + * @param isInternalCD true 磁盘缓存到应用的内部目录 / false 磁盘缓存到外部存 | ||
| 41 | + */ | ||
| 42 | + public static void init(final Context context, int cacheSizeInM, MemoryCategory memoryCategory, boolean isInternalCD) { | ||
| 43 | + ImageLoader.context = context; | ||
| 44 | + GlobalConfig.init(context, cacheSizeInM, memoryCategory, isInternalCD); | ||
| 45 | + } | ||
| 46 | + | ||
| 47 | + /** | ||
| 48 | + * 获取当前的Loader | ||
| 49 | + * @return | ||
| 50 | + */ | ||
| 51 | + public static ILoader getActualLoader() { | ||
| 52 | + return GlobalConfig.getLoader(); | ||
| 53 | + } | ||
| 54 | + | ||
| 55 | + /** | ||
| 56 | + * 加载普通图片 | ||
| 57 | + * | ||
| 58 | + * @param context | ||
| 59 | + * @return | ||
| 60 | + */ | ||
| 61 | + public static SingleConfig.ConfigBuilder with(Context context) { | ||
| 62 | + return new SingleConfig.ConfigBuilder(context); | ||
| 63 | + } | ||
| 64 | + | ||
| 65 | + public static void trimMemory(int level) { | ||
| 66 | + getActualLoader().trimMemory(level); | ||
| 67 | + } | ||
| 68 | + | ||
| 69 | + public static void clearAllMemoryCaches() { | ||
| 70 | + getActualLoader().clearAllMemoryCaches(); | ||
| 71 | + } | ||
| 72 | + | ||
| 73 | + public static void pauseRequests() { | ||
| 74 | + getActualLoader().pause(); | ||
| 75 | + | ||
| 76 | + } | ||
| 77 | + | ||
| 78 | + public static void resumeRequests() { | ||
| 79 | + getActualLoader().resume(); | ||
| 80 | + } | ||
| 81 | + | ||
| 82 | + /** | ||
| 83 | + *Cancel any pending loads Glide may have for the view and free any resources that may have been loaded for the view. | ||
| 84 | + * @param view | ||
| 85 | + */ | ||
| 86 | + public static void clearMomoryCache(Context context,View view) { | ||
| 87 | + getActualLoader().clearMomoryCache(context,view); | ||
| 88 | + } | ||
| 89 | + | ||
| 90 | + | ||
| 91 | + /** | ||
| 92 | + * Clears disk cache. | ||
| 93 | + * | ||
| 94 | + * <p> | ||
| 95 | + * This method should always be called on a background thread, since it is a blocking call. | ||
| 96 | + * </p> | ||
| 97 | + */ | ||
| 98 | + public static void clearDiskCache() { | ||
| 99 | + getActualLoader().clearDiskCache(); | ||
| 100 | + } | ||
| 101 | + | ||
| 102 | + /** | ||
| 103 | + * Clears as much memory as possible. | ||
| 104 | + */ | ||
| 105 | + public static void clearMomory() { | ||
| 106 | + getActualLoader().clearMomory(); | ||
| 107 | + } | ||
| 108 | + | ||
| 109 | + /** | ||
| 110 | + * 图片保存到相册 | ||
| 111 | + * | ||
| 112 | + * @param downLoadImageService | ||
| 113 | + */ | ||
| 114 | + public static void saveImageIntoGallery(DownLoadImageService downLoadImageService) { | ||
| 115 | + getActualLoader().saveImageIntoGallery(downLoadImageService); | ||
| 116 | + } | ||
| 117 | + | ||
| 118 | +} |
core/imageload/src/main/java/com/cnlive/core/imageload/util/DownLoadImageService.java
0 → 100644
| 1 | +package com.cnlive.core.imageload.util; | ||
| 2 | + | ||
| 3 | +import android.content.Context; | ||
| 4 | +import android.content.Intent; | ||
| 5 | +import android.graphics.Bitmap; | ||
| 6 | +import android.net.Uri; | ||
| 7 | +import android.os.Build; | ||
| 8 | +import android.os.Environment; | ||
| 9 | +import android.provider.MediaStore; | ||
| 10 | + | ||
| 11 | +import com.bumptech.glide.Glide; | ||
| 12 | +import com.bumptech.glide.request.target.Target; | ||
| 13 | +import com.cnlive.core.imageload.callback.ImageDownLoadCallBack; | ||
| 14 | + | ||
| 15 | +import java.io.File; | ||
| 16 | +import java.io.FileNotFoundException; | ||
| 17 | +import java.io.FileOutputStream; | ||
| 18 | +import java.io.IOException; | ||
| 19 | + | ||
| 20 | +/** | ||
| 21 | + * 图片下载 | ||
| 22 | + * created by hanyayun | ||
| 23 | + * on 2019/11/19 | ||
| 24 | + */ | ||
| 25 | +public class DownLoadImageService implements Runnable{ | ||
| 26 | + | ||
| 27 | + private String url; | ||
| 28 | + private Context context; | ||
| 29 | + private ImageDownLoadCallBack callBack; | ||
| 30 | + private File currentFile; | ||
| 31 | + private String fileName; | ||
| 32 | + | ||
| 33 | + private boolean isSetMediaStore; | ||
| 34 | + | ||
| 35 | + public DownLoadImageService(Context context, String url,boolean isSetMediaStore , String fileName, ImageDownLoadCallBack callBack) { | ||
| 36 | + this.url = url; | ||
| 37 | + this.callBack = callBack; | ||
| 38 | + this.context = context; | ||
| 39 | + this.isSetMediaStore = isSetMediaStore; | ||
| 40 | + this.fileName = fileName; | ||
| 41 | + } | ||
| 42 | + | ||
| 43 | + @Override | ||
| 44 | + public void run() { | ||
| 45 | + | ||
| 46 | + Bitmap bitmap = null; | ||
| 47 | + try { | ||
| 48 | + bitmap = Glide.with(context) | ||
| 49 | + .asBitmap() | ||
| 50 | + .load(url) | ||
| 51 | + .into(Target.SIZE_ORIGINAL, Target.SIZE_ORIGINAL) | ||
| 52 | + .get(); | ||
| 53 | + if (bitmap != null){ | ||
| 54 | + // 在这里执行图片保存方法 | ||
| 55 | + saveImageToGallery(context,bitmap); | ||
| 56 | + } | ||
| 57 | + } catch (Exception e) { | ||
| 58 | + e.printStackTrace(); | ||
| 59 | + } finally { | ||
| 60 | + if (bitmap != null && currentFile.exists()) { | ||
| 61 | + callBack.onDownLoadSuccess(bitmap); | ||
| 62 | + } else { | ||
| 63 | + callBack.onDownLoadFailed(); | ||
| 64 | + } | ||
| 65 | + } | ||
| 66 | + } | ||
| 67 | + | ||
| 68 | + public void saveImageToGallery(Context context, Bitmap bmp) { | ||
| 69 | + // 首先保存图片 | ||
| 70 | + | ||
| 71 | + File file = Build.VERSION.SDK_INT > 28?context.getExternalFilesDir(Environment.DIRECTORY_PICTURES).getAbsoluteFile():Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES).getAbsoluteFile();//注意小米手机必须这样获得public绝对路径 | ||
| 72 | + | ||
| 73 | + File appDir = new File(file ,fileName); | ||
| 74 | + if (!appDir.exists()) { | ||
| 75 | + appDir.mkdirs(); | ||
| 76 | + } | ||
| 77 | + fileName = System.currentTimeMillis() + ".jpg"; | ||
| 78 | + currentFile = new File(appDir, fileName); | ||
| 79 | + | ||
| 80 | + FileOutputStream fos = null; | ||
| 81 | + try { | ||
| 82 | + fos = new FileOutputStream(currentFile); | ||
| 83 | + bmp.compress(Bitmap.CompressFormat.JPEG, 100, fos); | ||
| 84 | + fos.flush(); | ||
| 85 | + } catch (FileNotFoundException e) { | ||
| 86 | + e.printStackTrace(); | ||
| 87 | + } catch (IOException e) { | ||
| 88 | + e.printStackTrace(); | ||
| 89 | + } finally { | ||
| 90 | + try { | ||
| 91 | + if (fos != null) { | ||
| 92 | + fos.close(); | ||
| 93 | + } | ||
| 94 | + } catch (IOException e) { | ||
| 95 | + e.printStackTrace(); | ||
| 96 | + } | ||
| 97 | + } | ||
| 98 | + | ||
| 99 | + if(isSetMediaStore){ | ||
| 100 | + setMediaDtore(fileName); | ||
| 101 | + } | ||
| 102 | + | ||
| 103 | + // 最后通知图库更新 | ||
| 104 | + context.sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, | ||
| 105 | + Uri.fromFile(new File(currentFile.getPath())))); | ||
| 106 | + } | ||
| 107 | + | ||
| 108 | + /** | ||
| 109 | + * 加入到系统图库 | ||
| 110 | + * @param fileName | ||
| 111 | + */ | ||
| 112 | + public void setMediaDtore(String fileName){ | ||
| 113 | + try { | ||
| 114 | + MediaStore.Images.Media.insertImage(context.getContentResolver(), | ||
| 115 | + currentFile.getAbsolutePath(), fileName, null); | ||
| 116 | + } catch (FileNotFoundException e) { | ||
| 117 | + e.printStackTrace(); | ||
| 118 | + } | ||
| 119 | + } | ||
| 120 | +} |
core/imageload/src/main/java/com/cnlive/core/imageload/util/ImageUtil.java
0 → 100644
| 1 | +package com.cnlive.core.imageload.util; | ||
| 2 | + | ||
| 3 | +import android.content.Context; | ||
| 4 | +import android.graphics.Bitmap; | ||
| 5 | +import android.graphics.Matrix; | ||
| 6 | +import android.net.Uri; | ||
| 7 | +import android.text.TextUtils; | ||
| 8 | +import android.util.Log; | ||
| 9 | + | ||
| 10 | +import com.cnlive.core.imageload.config.GlobalConfig; | ||
| 11 | +import com.cnlive.core.imageload.config.SingleConfig; | ||
| 12 | + | ||
| 13 | +import java.io.File; | ||
| 14 | +import java.io.FileInputStream; | ||
| 15 | +import java.io.IOException; | ||
| 16 | +import java.lang.reflect.InvocationHandler; | ||
| 17 | +import java.lang.reflect.InvocationTargetException; | ||
| 18 | +import java.lang.reflect.Method; | ||
| 19 | +import java.lang.reflect.Proxy; | ||
| 20 | +import java.security.KeyManagementException; | ||
| 21 | +import java.security.NoSuchAlgorithmException; | ||
| 22 | +import java.security.SecureRandom; | ||
| 23 | +import java.security.cert.X509Certificate; | ||
| 24 | +import java.util.concurrent.TimeUnit; | ||
| 25 | + | ||
| 26 | +import javax.net.ssl.HostnameVerifier; | ||
| 27 | +import javax.net.ssl.SSLContext; | ||
| 28 | +import javax.net.ssl.SSLSession; | ||
| 29 | +import javax.net.ssl.TrustManager; | ||
| 30 | +import javax.net.ssl.X509TrustManager; | ||
| 31 | + | ||
| 32 | +import okhttp3.OkHttpClient; | ||
| 33 | + | ||
| 34 | +import static com.cnlive.core.imageload.config.Contants.ANDROID_RESOURCE; | ||
| 35 | +import static com.cnlive.core.imageload.config.Contants.FOREWARD_SLASH; | ||
| 36 | + | ||
| 37 | +/** | ||
| 38 | + * created by hanyayun | ||
| 39 | + * on 2019/11/19 | ||
| 40 | + */ | ||
| 41 | +public class ImageUtil { | ||
| 42 | + | ||
| 43 | + public static SingleConfig.BitmapListener getBitmapListenerProxy(final SingleConfig.BitmapListener listener) { | ||
| 44 | + return (SingleConfig.BitmapListener) Proxy.newProxyInstance(SingleConfig.class.getClassLoader(), | ||
| 45 | + listener.getClass().getInterfaces(), new InvocationHandler() { | ||
| 46 | + @Override | ||
| 47 | + public Object invoke(Object proxy, final Method method, final Object[] args) throws Throwable { | ||
| 48 | + | ||
| 49 | + runOnUIThread(new Runnable() { | ||
| 50 | + @Override | ||
| 51 | + public void run() { | ||
| 52 | + try { | ||
| 53 | + Object object = method.invoke(listener, args); | ||
| 54 | + } catch (IllegalAccessException e) { | ||
| 55 | + e.printStackTrace(); | ||
| 56 | + } catch (InvocationTargetException e) { | ||
| 57 | + e.printStackTrace(); | ||
| 58 | + } | ||
| 59 | + } | ||
| 60 | + }); | ||
| 61 | + return null; | ||
| 62 | + } | ||
| 63 | + }); | ||
| 64 | + } | ||
| 65 | + | ||
| 66 | + public static void runOnUIThread(Runnable runnable) { | ||
| 67 | + GlobalConfig.getMainHandler().post(runnable); | ||
| 68 | + } | ||
| 69 | + | ||
| 70 | + public static boolean shouldSetPlaceHolder(SingleConfig config) { | ||
| 71 | + if (config.getPlaceHolderResId() <= 0) { | ||
| 72 | + return false; | ||
| 73 | + } | ||
| 74 | + | ||
| 75 | + if (config.getResId() > 0 || !TextUtils.isEmpty(config.getFilePath()) || GlobalConfig.getLoader().isCached(config.getUrl())) { | ||
| 76 | + return false; | ||
| 77 | + } else {//只有在图片源为网络图片,并且图片没有缓存到本地时,才给显示placeholder | ||
| 78 | + return true; | ||
| 79 | + } | ||
| 80 | + } | ||
| 81 | + | ||
| 82 | + public static int dip2px(float dipValue) { | ||
| 83 | + final float scale = GlobalConfig.context.getResources().getDisplayMetrics().density; | ||
| 84 | + return (int) (dipValue * scale + 0.5f); | ||
| 85 | + } | ||
| 86 | + | ||
| 87 | + | ||
| 88 | + /** | ||
| 89 | + * 等比压缩(宽高等比缩放) | ||
| 90 | + * | ||
| 91 | + * @param bitmap | ||
| 92 | + * @param needRecycle | ||
| 93 | + * @param targetWidth | ||
| 94 | + * @param targeHeight | ||
| 95 | + * @return | ||
| 96 | + */ | ||
| 97 | + public static Bitmap compressBitmap(Bitmap bitmap, boolean needRecycle, int targetWidth, int targeHeight) { | ||
| 98 | + float sourceWidth = bitmap.getWidth(); | ||
| 99 | + float sourceHeight = bitmap.getHeight(); | ||
| 100 | + | ||
| 101 | + float scaleWidth = targetWidth / sourceWidth; | ||
| 102 | + float scaleHeight = targeHeight / sourceHeight; | ||
| 103 | + | ||
| 104 | + Matrix matrix = new Matrix(); | ||
| 105 | + matrix.postScale(scaleWidth, scaleHeight); //长和宽放大缩小的比例 | ||
| 106 | + Bitmap bm = Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(), bitmap.getHeight(), matrix, true); | ||
| 107 | + if (needRecycle) { | ||
| 108 | + bitmap.recycle(); | ||
| 109 | + } | ||
| 110 | + bitmap = bm; | ||
| 111 | + return bitmap; | ||
| 112 | + } | ||
| 113 | + | ||
| 114 | + public static String getRealType(File file) { | ||
| 115 | + FileInputStream is = null; | ||
| 116 | + try { | ||
| 117 | + is = new FileInputStream(file); | ||
| 118 | + byte[] b = new byte[4]; | ||
| 119 | + try { | ||
| 120 | + is.read(b, 0, b.length); | ||
| 121 | + } catch (IOException e) { | ||
| 122 | + e.printStackTrace(); | ||
| 123 | + return ""; | ||
| 124 | + } | ||
| 125 | + String type = bytesToHexString(b).toUpperCase(); | ||
| 126 | + if (type.contains("FFD8FF")) { | ||
| 127 | + return "jpg"; | ||
| 128 | + } else if (type.contains("89504E47")) { | ||
| 129 | + return "png"; | ||
| 130 | + } else if (type.contains("47494638")) { | ||
| 131 | + return "gif"; | ||
| 132 | + } else if (type.contains("49492A00")) { | ||
| 133 | + return "tif"; | ||
| 134 | + } else if (type.contains("424D")) { | ||
| 135 | + return "bmp"; | ||
| 136 | + } | ||
| 137 | + return type; | ||
| 138 | + } catch (Exception e) { | ||
| 139 | + e.printStackTrace(); | ||
| 140 | + return ""; | ||
| 141 | + } finally { | ||
| 142 | + try { | ||
| 143 | + is.close(); | ||
| 144 | + } catch (IOException e) { | ||
| 145 | + e.printStackTrace(); | ||
| 146 | + } | ||
| 147 | + } | ||
| 148 | + | ||
| 149 | + } | ||
| 150 | + | ||
| 151 | + public static String bytesToHexString(byte[] src) { | ||
| 152 | + StringBuilder stringBuilder = new StringBuilder(); | ||
| 153 | + if (src == null || src.length <= 0) { | ||
| 154 | + return null; | ||
| 155 | + } | ||
| 156 | + for (int i = 0; i < src.length; i++) { | ||
| 157 | + int v = src[i] & 0xFF; | ||
| 158 | + String hv = Integer.toHexString(v); | ||
| 159 | + if (hv.length() < 2) { | ||
| 160 | + stringBuilder.append(0); | ||
| 161 | + } | ||
| 162 | + stringBuilder.append(hv); | ||
| 163 | + } | ||
| 164 | + return stringBuilder.toString(); | ||
| 165 | + } | ||
| 166 | + | ||
| 167 | + | ||
| 168 | + /** | ||
| 169 | + * 类型 SCHEME 示例 | ||
| 170 | + * 远程图片 http://, https:// HttpURLConnection 或者参考 使用其他网络加载方案 | ||
| 171 | + * 本地文件 file:// FileInputStream | ||
| 172 | + * Content provider content:// ContentResolver | ||
| 173 | + * asset目录下的资源 asset:// AssetManager | ||
| 174 | + * res目录下的资源 res:// Resources.openRawResource | ||
| 175 | + * Uri中指定图片数据 data:mime/type;base64, 数据类型必须符合 rfc2397规定 (仅支持 UTF-8) | ||
| 176 | + * | ||
| 177 | + * @param config | ||
| 178 | + * @return | ||
| 179 | + */ | ||
| 180 | + public static Uri buildUriByType(SingleConfig config) { | ||
| 181 | + | ||
| 182 | + Log.e("builduri:", "url: " + config.getUrl() + " ---filepath:" + config.getFilePath() + "--content:" + config.getContentProvider()); | ||
| 183 | + | ||
| 184 | + if (!TextUtils.isEmpty(config.getUrl())) { | ||
| 185 | + String url = ImageUtil.appendUrl(config.getUrl()); | ||
| 186 | + return Uri.parse(url); | ||
| 187 | + } | ||
| 188 | + | ||
| 189 | + if (config.getResId() > 0) { | ||
| 190 | + return Uri.parse("res://imageloader/" + config.getResId()); | ||
| 191 | + } | ||
| 192 | + | ||
| 193 | + if (!TextUtils.isEmpty(config.getFilePath())) { | ||
| 194 | + | ||
| 195 | + File file = new File(config.getFilePath()); | ||
| 196 | + if (file.exists()) { | ||
| 197 | + return Uri.fromFile(file); | ||
| 198 | + } | ||
| 199 | + } | ||
| 200 | + | ||
| 201 | + if (!TextUtils.isEmpty(config.getContentProvider())) { | ||
| 202 | + String content = config.getContentProvider(); | ||
| 203 | + if (!content.startsWith("content")) { | ||
| 204 | + content = "content://" + content; | ||
| 205 | + } | ||
| 206 | + return Uri.parse(content); | ||
| 207 | + } | ||
| 208 | + | ||
| 209 | + | ||
| 210 | + return null; | ||
| 211 | + } | ||
| 212 | + | ||
| 213 | + | ||
| 214 | + public static String appendUrl(String url) { | ||
| 215 | + String newUrl = url; | ||
| 216 | + if (TextUtils.isEmpty(newUrl)) { | ||
| 217 | + return newUrl; | ||
| 218 | + } | ||
| 219 | + boolean hasHost = url.contains("http:") || url.contains("https:"); | ||
| 220 | + if (!hasHost) { | ||
| 221 | + if (!TextUtils.isEmpty(GlobalConfig.baseUrl)) { | ||
| 222 | + newUrl = GlobalConfig.baseUrl + url; | ||
| 223 | + } | ||
| 224 | + } | ||
| 225 | + | ||
| 226 | + return newUrl; | ||
| 227 | + } | ||
| 228 | + | ||
| 229 | + public static OkHttpClient getClient(boolean ignoreCertificateVerify) { | ||
| 230 | + if (ignoreCertificateVerify) { | ||
| 231 | + return getAllPassClient(); | ||
| 232 | + } else { | ||
| 233 | + return getNormalClient(); | ||
| 234 | + } | ||
| 235 | + } | ||
| 236 | + | ||
| 237 | + /** | ||
| 238 | + * 不校验证书 | ||
| 239 | + * | ||
| 240 | + * @return | ||
| 241 | + */ | ||
| 242 | + private static OkHttpClient getAllPassClient() { | ||
| 243 | + | ||
| 244 | + X509TrustManager xtm = new X509TrustManager() { | ||
| 245 | + @Override | ||
| 246 | + public void checkClientTrusted(X509Certificate[] chain, String authType) { | ||
| 247 | + } | ||
| 248 | + | ||
| 249 | + @Override | ||
| 250 | + public void checkServerTrusted(X509Certificate[] chain, String authType) { | ||
| 251 | + } | ||
| 252 | + | ||
| 253 | + @Override | ||
| 254 | + public X509Certificate[] getAcceptedIssuers() { | ||
| 255 | + X509Certificate[] x509Certificates = new X509Certificate[]{}; | ||
| 256 | + return x509Certificates; | ||
| 257 | + // return null; | ||
| 258 | + } | ||
| 259 | + }; | ||
| 260 | + | ||
| 261 | + SSLContext sslContext = null; | ||
| 262 | + try { | ||
| 263 | + sslContext = SSLContext.getInstance("SSL"); | ||
| 264 | + | ||
| 265 | + sslContext.init(null, new TrustManager[]{xtm}, new SecureRandom()); | ||
| 266 | + | ||
| 267 | + } catch (NoSuchAlgorithmException e) { | ||
| 268 | + e.printStackTrace(); | ||
| 269 | + } catch (KeyManagementException e) { | ||
| 270 | + e.printStackTrace(); | ||
| 271 | + } | ||
| 272 | + | ||
| 273 | + | ||
| 274 | + HostnameVerifier DO_NOT_VERIFY = new HostnameVerifier() { | ||
| 275 | + @Override | ||
| 276 | + public boolean verify(String hostname, SSLSession session) { | ||
| 277 | + return true; | ||
| 278 | + } | ||
| 279 | + }; | ||
| 280 | + | ||
| 281 | + OkHttpClient client = new OkHttpClient.Builder() | ||
| 282 | + .sslSocketFactory(sslContext.getSocketFactory()) | ||
| 283 | + .hostnameVerifier(DO_NOT_VERIFY) | ||
| 284 | + .readTimeout(0, TimeUnit.SECONDS) | ||
| 285 | + .connectTimeout(30, TimeUnit.SECONDS).writeTimeout(0, TimeUnit.SECONDS) //设置超时 | ||
| 286 | + .build(); | ||
| 287 | + | ||
| 288 | + return client; | ||
| 289 | + } | ||
| 290 | + | ||
| 291 | + private static OkHttpClient getNormalClient() { | ||
| 292 | + OkHttpClient client = new OkHttpClient.Builder() | ||
| 293 | + //.sslSocketFactory(sslContext.getSocketFactory()) | ||
| 294 | + //.hostnameVerifier(DO_NOT_VERIFY) | ||
| 295 | + .readTimeout(0, TimeUnit.SECONDS) | ||
| 296 | + .connectTimeout(30, TimeUnit.SECONDS).writeTimeout(0, TimeUnit.SECONDS) //设置超时 | ||
| 297 | + .build(); | ||
| 298 | + return client; | ||
| 299 | + } | ||
| 300 | + | ||
| 301 | + private static Uri resourceIdToUri(Context context, int resourceId) { | ||
| 302 | + return Uri.parse(ANDROID_RESOURCE + context.getPackageName() + FOREWARD_SLASH + resourceId); | ||
| 303 | + } | ||
| 304 | + | ||
| 305 | +} |
core/imageload/src/main/java/com/cnlive/core/imageload/util/MultiView.java
0 → 100644
| 1 | +package com.cnlive.core.imageload.util; | ||
| 2 | + | ||
| 3 | +import android.annotation.SuppressLint; | ||
| 4 | +import android.content.Context; | ||
| 5 | +import android.content.res.TypedArray; | ||
| 6 | +import android.graphics.Bitmap; | ||
| 7 | +import android.graphics.BitmapShader; | ||
| 8 | +import android.graphics.Canvas; | ||
| 9 | +import android.graphics.Matrix; | ||
| 10 | +import android.graphics.Paint; | ||
| 11 | +import android.graphics.Path; | ||
| 12 | +import android.graphics.PointF; | ||
| 13 | +import android.graphics.RectF; | ||
| 14 | +import android.graphics.Shader; | ||
| 15 | +import android.graphics.drawable.BitmapDrawable; | ||
| 16 | +import android.graphics.drawable.Drawable; | ||
| 17 | +import android.os.Bundle; | ||
| 18 | +import android.os.Parcelable; | ||
| 19 | +import android.util.AttributeSet; | ||
| 20 | +import android.util.TypedValue; | ||
| 21 | +import android.widget.ImageView; | ||
| 22 | + | ||
| 23 | +import com.cnlive.core.imageload.R; | ||
| 24 | + | ||
| 25 | +import java.util.ArrayList; | ||
| 26 | +import java.util.List; | ||
| 27 | + | ||
| 28 | +import androidx.annotation.Nullable; | ||
| 29 | + | ||
| 30 | +/** | ||
| 31 | + * created by hanyayun | ||
| 32 | + * on 2019/11/22 | ||
| 33 | + */ | ||
| 34 | +public class MultiView extends ImageView { | ||
| 35 | + | ||
| 36 | + /** | ||
| 37 | + * 图片的类型,圆形or圆角or多边形 | ||
| 38 | + */ | ||
| 39 | + private Context mContext; | ||
| 40 | + | ||
| 41 | + /** | ||
| 42 | + * 传输类型 | ||
| 43 | + */ | ||
| 44 | + private int type; | ||
| 45 | + | ||
| 46 | + /** | ||
| 47 | + * 圆形 | ||
| 48 | + */ | ||
| 49 | + public static final int TYPE_CIRCLE = 0; | ||
| 50 | + | ||
| 51 | + /** | ||
| 52 | + * 圆角 | ||
| 53 | + */ | ||
| 54 | + public static final int TYPE_ROUND = 1; | ||
| 55 | + | ||
| 56 | + /** | ||
| 57 | + * 多边形 | ||
| 58 | + */ | ||
| 59 | + public static final int TYPE_MULTI = 3; | ||
| 60 | + | ||
| 61 | + /** | ||
| 62 | + *默认多边形角的个数 | ||
| 63 | + */ | ||
| 64 | + public static final int ANGLECOUNT = 5; | ||
| 65 | + | ||
| 66 | + /** | ||
| 67 | + * 默认开始绘制的角度 | ||
| 68 | + */ | ||
| 69 | + public static final int CURRENTANGLE = 180; | ||
| 70 | + | ||
| 71 | + /** | ||
| 72 | + * 多边形的半径 | ||
| 73 | + */ | ||
| 74 | + private int startRadius; | ||
| 75 | + | ||
| 76 | + /** | ||
| 77 | + * 多边形角的个数 | ||
| 78 | + */ | ||
| 79 | + private int angleCount ; | ||
| 80 | + | ||
| 81 | + private int[] angles; | ||
| 82 | + | ||
| 83 | + /** | ||
| 84 | + * 开始绘制的角度 | ||
| 85 | + */ | ||
| 86 | + private int currentAngle; | ||
| 87 | + | ||
| 88 | + /** | ||
| 89 | + * 存储角位置的集合 | ||
| 90 | + */ | ||
| 91 | + private List<PointF> pointFList = new ArrayList<>(); | ||
| 92 | + | ||
| 93 | + /** | ||
| 94 | + * 圆角大小的默认值 | ||
| 95 | + */ | ||
| 96 | + private static final int BODER_RADIUS_DEFAULT = 10; | ||
| 97 | + | ||
| 98 | + /** | ||
| 99 | + * 圆角的大小 | ||
| 100 | + */ | ||
| 101 | + private int mBorderRadius; | ||
| 102 | + | ||
| 103 | + /** | ||
| 104 | + * 绘图的Paint | ||
| 105 | + */ | ||
| 106 | + private Paint mBitmapPaint; | ||
| 107 | + | ||
| 108 | + /** | ||
| 109 | + * 圆角的半径 | ||
| 110 | + */ | ||
| 111 | + private int mRadius; | ||
| 112 | + | ||
| 113 | + /** | ||
| 114 | + * 3x3 矩阵,主要用于缩小放大 | ||
| 115 | + */ | ||
| 116 | + private Matrix mMatrix; | ||
| 117 | + | ||
| 118 | + /** | ||
| 119 | + * 渲染图像,使用图像为绘制图形着色 | ||
| 120 | + */ | ||
| 121 | + private BitmapShader mBitmapShader; | ||
| 122 | + | ||
| 123 | + /** | ||
| 124 | + * view的宽度 | ||
| 125 | + */ | ||
| 126 | + private int mWidth; | ||
| 127 | + private RectF mRoundRect; | ||
| 128 | + | ||
| 129 | + public MultiView(Context context) { | ||
| 130 | + this(context, null); | ||
| 131 | + } | ||
| 132 | + | ||
| 133 | + public MultiView(Context context, AttributeSet attrs) { | ||
| 134 | + | ||
| 135 | + this(context, attrs, 0); | ||
| 136 | + | ||
| 137 | + } | ||
| 138 | + | ||
| 139 | + public MultiView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) { | ||
| 140 | + super(context, attrs, defStyleAttr); | ||
| 141 | + | ||
| 142 | + this.mContext = context; | ||
| 143 | + | ||
| 144 | + init(context, attrs); | ||
| 145 | + | ||
| 146 | + } | ||
| 147 | + | ||
| 148 | + public void init(Context context, AttributeSet attrs) { | ||
| 149 | + mMatrix = new Matrix(); | ||
| 150 | + mBitmapPaint = new Paint(); | ||
| 151 | + mBitmapPaint.setAntiAlias(true); | ||
| 152 | + | ||
| 153 | + TypedArray typedArray = context.obtainStyledAttributes(attrs, | ||
| 154 | + R.styleable.RoundImageView); | ||
| 155 | + | ||
| 156 | + mBorderRadius = typedArray.getDimensionPixelSize( | ||
| 157 | + R.styleable.RoundImageView_borderRadius, (int) TypedValue | ||
| 158 | + .applyDimension(TypedValue.COMPLEX_UNIT_DIP, | ||
| 159 | + BODER_RADIUS_DEFAULT, getResources() | ||
| 160 | + .getDisplayMetrics()));// 默认为10dp | ||
| 161 | + type = typedArray.getInt(R.styleable.RoundImageView_type, TYPE_CIRCLE);// 默认为Circle | ||
| 162 | + angleCount = typedArray.getInt(R.styleable.RoundImageView_angleCount, ANGLECOUNT); | ||
| 163 | + currentAngle = typedArray.getInt(R.styleable.RoundImageView_currentAngle, currentAngle); | ||
| 164 | + | ||
| 165 | + typedArray.recycle(); //回收之后对象可以重用 | ||
| 166 | + } | ||
| 167 | + @Override | ||
| 168 | + protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { | ||
| 169 | + super.onMeasure(widthMeasureSpec, heightMeasureSpec); | ||
| 170 | + | ||
| 171 | + /** | ||
| 172 | + * 如果类型是圆形或多边形,则强制改变view的宽高一致,以小值为准 | ||
| 173 | + */ | ||
| 174 | + if (type == TYPE_CIRCLE) { | ||
| 175 | + mWidth = Math.min(getMeasuredWidth(), getMeasuredHeight()); | ||
| 176 | + mRadius = mWidth / 2; | ||
| 177 | + setMeasuredDimension(mWidth, mWidth); | ||
| 178 | + } | ||
| 179 | + | ||
| 180 | + if (type == TYPE_MULTI) { | ||
| 181 | + mWidth = Math.min(getMeasuredWidth(), getMeasuredHeight()); | ||
| 182 | + | ||
| 183 | + setMeasuredDimension(mWidth, mWidth); | ||
| 184 | + | ||
| 185 | + angles = new int[angleCount]; | ||
| 186 | + | ||
| 187 | + for (int i = 0; i < angleCount; i++) { | ||
| 188 | + int partOfAngle = 360 / angleCount; //每个顶点的角度 | ||
| 189 | + angles[i] = currentAngle + partOfAngle * i; | ||
| 190 | + | ||
| 191 | + startRadius = mWidth / 2; | ||
| 192 | + float x = (float) (Math.sin(Math.toRadians(angles[i])) * startRadius); | ||
| 193 | + float y = (float) (Math.cos(Math.toRadians(angles[i])) * startRadius); | ||
| 194 | + pointFList.add(new PointF(x, y)); | ||
| 195 | + } | ||
| 196 | + } | ||
| 197 | + | ||
| 198 | + } | ||
| 199 | + | ||
| 200 | + /** | ||
| 201 | + * 初始化BitmapShader | ||
| 202 | + */ | ||
| 203 | + private void setUpShader() { | ||
| 204 | + Drawable drawable = getDrawable(); | ||
| 205 | + if (drawable == null) { | ||
| 206 | + return; | ||
| 207 | + } | ||
| 208 | + | ||
| 209 | + Bitmap bmp = drawableToBitamp(drawable); | ||
| 210 | + // 将bmp作为着色器,就是在指定区域内绘制bmp | ||
| 211 | + mBitmapShader = new BitmapShader(bmp, Shader.TileMode.REPEAT, Shader.TileMode.REPEAT); | ||
| 212 | + float scale = 1.0f; | ||
| 213 | + if (type == TYPE_CIRCLE) { | ||
| 214 | + // 拿到bitmap宽或高的小值 | ||
| 215 | + int bSize = Math.min(bmp.getWidth(), bmp.getHeight()); | ||
| 216 | + scale = mWidth * 1.0f / bSize; | ||
| 217 | + | ||
| 218 | + } else if (type == TYPE_ROUND) { | ||
| 219 | + if (!(bmp.getWidth() == getWidth() && bmp.getHeight() == getHeight())) { | ||
| 220 | + // 如果图片的宽或者高与view的宽高不匹配,计算出需要缩放的比例;缩放后的图片的宽高,一定要大于我们view的宽高;所以我们这里取大值; | ||
| 221 | + scale = Math.max(getWidth() * 1.0f / bmp.getWidth(), getHeight() * 1.0f / bmp.getHeight()); | ||
| 222 | + } | ||
| 223 | + | ||
| 224 | + } else if (type == TYPE_MULTI) { | ||
| 225 | + // 拿到bitmap宽或高的小值 | ||
| 226 | + int bSize = Math.min(bmp.getWidth(), bmp.getHeight()); | ||
| 227 | + scale = mWidth * 1.0f / bSize; | ||
| 228 | + } | ||
| 229 | + // shader的变换矩阵,我们这里主要用于放大或者缩小 | ||
| 230 | + mMatrix.setScale(scale, scale); | ||
| 231 | + | ||
| 232 | + // 设置变换矩阵 | ||
| 233 | + mBitmapShader.setLocalMatrix(mMatrix); | ||
| 234 | + // 设置shader | ||
| 235 | + mBitmapPaint.setShader(mBitmapShader); | ||
| 236 | + } | ||
| 237 | + | ||
| 238 | + @Override | ||
| 239 | + protected void onDraw(Canvas canvas) { | ||
| 240 | + if (getDrawable() == null) { | ||
| 241 | + return; | ||
| 242 | + } | ||
| 243 | + setUpShader(); | ||
| 244 | + | ||
| 245 | + if (type == TYPE_ROUND) { | ||
| 246 | + canvas.drawRoundRect(mRoundRect, mBorderRadius, mBorderRadius, | ||
| 247 | + mBitmapPaint); | ||
| 248 | + } else if (type == TYPE_MULTI) { | ||
| 249 | + //canvas.translate(startRadius,startRadius); | ||
| 250 | + | ||
| 251 | + Path mPath = drawPath(); | ||
| 252 | + | ||
| 253 | + canvas.drawPath(mPath, mBitmapPaint); | ||
| 254 | + } else { | ||
| 255 | + canvas.drawCircle(mRadius, mRadius, mRadius, mBitmapPaint); | ||
| 256 | + } | ||
| 257 | + } | ||
| 258 | + | ||
| 259 | + /** | ||
| 260 | + * @return 多边形路径 | ||
| 261 | + */ | ||
| 262 | + private Path drawPath() { | ||
| 263 | + Path mPath = new Path(); | ||
| 264 | + mPath.moveTo(pointFList.get(0).x, pointFList.get(0).y); | ||
| 265 | + for (int i = 2; i < angleCount; i++) { | ||
| 266 | + if (i % 2 == 0) {// 除以二取余数,余数为0则为偶数,否则奇数 | ||
| 267 | + mPath.lineTo(pointFList.get(i).x, pointFList.get(i).y); | ||
| 268 | + } | ||
| 269 | + | ||
| 270 | + } | ||
| 271 | + | ||
| 272 | + if (angleCount % 2 == 0) { //偶数,moveTo | ||
| 273 | + mPath.moveTo(pointFList.get(1).x, pointFList.get(1).y); | ||
| 274 | + } else { //奇数,lineTo | ||
| 275 | + mPath.lineTo(pointFList.get(1).x, pointFList.get(1).y); | ||
| 276 | + } | ||
| 277 | + | ||
| 278 | + for (int i = 3; i < angleCount; i++) { | ||
| 279 | + if (i % 2 != 0) { | ||
| 280 | + mPath.lineTo(pointFList.get(i).x, pointFList.get(i).y); | ||
| 281 | + } | ||
| 282 | + } | ||
| 283 | + | ||
| 284 | + mPath.offset(startRadius, startRadius); | ||
| 285 | + return mPath; | ||
| 286 | + } | ||
| 287 | + | ||
| 288 | + @Override | ||
| 289 | + protected void onSizeChanged(int w, int h, int oldw, int oldh) { | ||
| 290 | + super.onSizeChanged(w, h, oldw, oldh); | ||
| 291 | + | ||
| 292 | + // 圆角图片的范围 | ||
| 293 | + if (type == TYPE_ROUND) | ||
| 294 | + mRoundRect = new RectF(0, 0, w, h); | ||
| 295 | + } | ||
| 296 | + | ||
| 297 | + /** | ||
| 298 | + * drawable转bitmap | ||
| 299 | + * | ||
| 300 | + * @param drawable | ||
| 301 | + * @return | ||
| 302 | + */ | ||
| 303 | + private Bitmap drawableToBitamp(Drawable drawable) { | ||
| 304 | + if (drawable instanceof BitmapDrawable) { | ||
| 305 | + BitmapDrawable bd = (BitmapDrawable) drawable; | ||
| 306 | + return bd.getBitmap(); | ||
| 307 | + } | ||
| 308 | + int w = drawable.getIntrinsicWidth(); | ||
| 309 | + int h = drawable.getIntrinsicHeight(); | ||
| 310 | + Bitmap bitmap = Bitmap.createBitmap(w, h, Bitmap.Config.ARGB_8888); | ||
| 311 | + Canvas canvas = new Canvas(bitmap); | ||
| 312 | + drawable.setBounds(0, 0, w, h); | ||
| 313 | + drawable.draw(canvas); | ||
| 314 | + return bitmap; | ||
| 315 | + } | ||
| 316 | + | ||
| 317 | + private static final String STATE_INSTANCE = "state_instance"; | ||
| 318 | + private static final String STATE_TYPE = "state_type"; | ||
| 319 | + private static final String STATE_BORDER_RADIUS = "state_border_radius"; | ||
| 320 | + | ||
| 321 | + @Override | ||
| 322 | + protected Parcelable onSaveInstanceState() { | ||
| 323 | + Bundle bundle = new Bundle(); | ||
| 324 | + bundle.putParcelable(STATE_INSTANCE, super.onSaveInstanceState()); | ||
| 325 | + bundle.putInt(STATE_TYPE, type); | ||
| 326 | + bundle.putInt(STATE_BORDER_RADIUS, mBorderRadius); | ||
| 327 | + return bundle; | ||
| 328 | + } | ||
| 329 | + | ||
| 330 | + @Override | ||
| 331 | + protected void onRestoreInstanceState(Parcelable state) { | ||
| 332 | + if (state instanceof Bundle) { | ||
| 333 | + Bundle bundle = (Bundle) state; | ||
| 334 | + super.onRestoreInstanceState(((Bundle) state) | ||
| 335 | + .getParcelable(STATE_INSTANCE)); | ||
| 336 | + this.type = bundle.getInt(STATE_TYPE); | ||
| 337 | + this.mBorderRadius = bundle.getInt(STATE_BORDER_RADIUS); | ||
| 338 | + } else { | ||
| 339 | + super.onRestoreInstanceState(state); | ||
| 340 | + } | ||
| 341 | + | ||
| 342 | + } | ||
| 343 | + | ||
| 344 | + public void setType(int type) { | ||
| 345 | + if (this.type != type) { | ||
| 346 | + this.type = type; | ||
| 347 | + if (this.type != TYPE_ROUND && this.type != TYPE_CIRCLE && this.type != TYPE_MULTI) { | ||
| 348 | + this.type = TYPE_CIRCLE; | ||
| 349 | + } | ||
| 350 | + requestLayout(); | ||
| 351 | + } | ||
| 352 | + | ||
| 353 | + } | ||
| 354 | + | ||
| 355 | +} | ||
| 356 | + |
core/imageload/src/main/res/values/strings.xml
0 → 100644
core/imageload/src/main/res/values/style.xml
0 → 100644
| 1 | +<?xml version="1.0" encoding="utf-8"?> | ||
| 2 | +<resources> | ||
| 3 | + <declare-styleable name="RoundImageView"> | ||
| 4 | + <attr name="borderRadius" format="dimension" /> | ||
| 5 | + <attr name="type"> | ||
| 6 | + <enum name="circle" value="0" /> | ||
| 7 | + <enum name="round" value="1" /> | ||
| 8 | + <enum name="multi" value="3" /> | ||
| 9 | + </attr> | ||
| 10 | + <attr name="angleCount" format="integer" /> | ||
| 11 | + <attr name="currentAngle" format="integer" /> | ||
| 12 | + </declare-styleable> | ||
| 13 | + | ||
| 14 | +</resources> | ||
| 0 | \ No newline at end of file | 15 | \ No newline at end of file |
core/imageload/src/test/java/com/mm999/imageload/ExampleUnitTest.java
0 → 100644
| 1 | +package com.mm999.imageload; | ||
| 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 <a href="http://d.android.com/tools/testing">Testing documentation</a> | ||
| 11 | + */ | ||
| 12 | +public class ExampleUnitTest { | ||
| 13 | + @Test | ||
| 14 | + public void addition_isCorrect() { | ||
| 15 | + assertEquals(4, 2 + 2); | ||
| 16 | + } | ||
| 17 | +} | ||
| 0 | \ No newline at end of file | 18 | \ No newline at end of file |
settings.gradle
| 1 | -include ':app:strike', ':network', ':user' | 1 | +include ':app:strike', ':network' |
| 2 | //基础库 | 2 | //基础库 |
| 3 | -include ':core:base',':core:network' | 3 | +include ':core:base',':core:network',':core:imageload' |
| 4 | include ':cloud:user' | 4 | include ':cloud:user' |
| 5 | 5 | ||
| 6 | rootProject.name='ModuleStrike' | 6 | rootProject.name='ModuleStrike' |