第一次提交

This commit is contained in:
xuhuixiang
2026-03-21 10:50:34 +08:00
commit b68b389cd4
91 changed files with 3527 additions and 0 deletions

1
library/.gitignore vendored Normal file
View File

@@ -0,0 +1 @@
/build

37
library/build.gradle Normal file
View File

@@ -0,0 +1,37 @@
plugins {
id 'com.android.library'
}
android {
namespace 'com.miraclegarden.library'
compileSdk 32
defaultConfig {
minSdk 21
targetSdk 32
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
consumerProguardFiles "consumer-rules.pro"
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
}
}
compileOptions {
sourceCompatibility JavaVersion.VERSION_17
targetCompatibility JavaVersion.VERSION_17
}
}
dependencies {
implementation 'androidx.databinding:viewbinding:7.3.0'
implementation 'androidx.appcompat:appcompat:1.5.0'
implementation 'com.google.android.material:material:1.6.1'
testImplementation 'junit:junit:4.13.2'
androidTestImplementation 'androidx.test.ext:junit:1.1.3'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0'
}

View File

21
library/proguard-rules.pro vendored Normal file
View File

@@ -0,0 +1,21 @@
# Add project specific ProGuard rules here.
# You can control the set of applied configuration files using the
# proguardFiles setting in build.gradle.
#
# For more details, see
# http://developer.android.com/guide/developing/tools/proguard.html
# If your project uses WebView with JS, uncomment the following
# and specify the fully qualified class name to the JavaScript interface
# class:
#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
# public *;
#}
# Uncomment this to preserve the line number information for
# debugging stack traces.
#-keepattributes SourceFile,LineNumberTable
# If you keep the line number information, uncomment this to
# hide the original source file name.
#-renamesourcefileattribute SourceFile

View File

@@ -0,0 +1,26 @@
package com.miraclegarden.library;
import android.content.Context;
import androidx.test.platform.app.InstrumentationRegistry;
import androidx.test.ext.junit.runners.AndroidJUnit4;
import org.junit.Test;
import org.junit.runner.RunWith;
import static org.junit.Assert.*;
/**
* Instrumented test, which will execute on an Android device.
*
* @see <a href="http://d.android.com/tools/testing">Testing documentation</a>
*/
@RunWith(AndroidJUnit4.class)
public class ExampleInstrumentedTest {
@Test
public void useAppContext() {
// Context of the app under test.
Context appContext = InstrumentationRegistry.getInstrumentation().getTargetContext();
assertEquals("com.miraclegarden.library.test", appContext.getPackageName());
}
}

View File

@@ -0,0 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
</manifest>

View File

@@ -0,0 +1,57 @@
package com.miraclegarden.library.app;
import android.os.Bundle;
import android.view.View;
import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;
import androidx.appcompat.widget.Toolbar;
import androidx.viewbinding.ViewBinding;
import com.miraclegarden.library.app.utils.ViewBindingUtil;
public class MiracleGardenActivity<Binding extends ViewBinding> extends AppCompatActivity implements View.OnClickListener, Runnable {
public Binding binding;
public Binding getBinding() {
return binding;
}
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
try {
//实体化
binding = ViewBindingUtil.inflate(getClass(), getLayoutInflater());
setContentView(binding.getRoot());
} catch (Exception e) {
e.printStackTrace();
}
}
//快速设置
public void setToolbar_Finish(Toolbar toolbar) {
toolbar.setNavigationOnClickListener(v -> finish());
}
@Override
public void onClick(View v) {
}
@Override
protected void onResume() {
super.onResume();
addResume();
}
protected void addResume() {
}
@Override
public void run() {
}
}

View File

@@ -0,0 +1,22 @@
package com.miraclegarden.library.app.listener;
import android.app.Activity;
import androidx.viewbinding.ViewBinding;
import java.util.List;
public interface OnBindViewHolderListener<Binding extends ViewBinding> {
Activity getActivity();
List<?> getList();
/**
* 每一个子item通知
*
* @param binding item
* @param position
*/
void onBindViewHolder(Binding binding, int position);
}

View File

@@ -0,0 +1,111 @@
package com.miraclegarden.library.app.utils;
import android.app.Activity;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import androidx.annotation.NonNull;
import androidx.viewbinding.ViewBinding;
import java.lang.reflect.Method;
import java.lang.reflect.ParameterizedType;
import java.lang.reflect.Type;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
public class ViewBindingUtil {
private static final String TAG = "ViewBindingUtil";
@SuppressWarnings("unchecked")
@NonNull
public static <Binding extends ViewBinding> Binding bind(Class<?> clazz, View rootView) {
Class<?> bindingClass = getBindingClass(clazz);
Binding binding = null;
if (bindingClass != null) {
try {
Method method = bindingClass.getMethod("bind", View.class);
binding = (Binding) method.invoke(null, rootView);
} catch (Exception e) {
e.printStackTrace();
}
}
return binding;
}
public static <Binding extends ViewBinding> Binding inflate(Class<?> clazz, LayoutInflater inflater) {
return inflate(clazz, inflater, null);
}
public static <Binding extends ViewBinding> Binding inflate(Class<?> clazz, LayoutInflater inflater, ViewGroup root) {
return inflate(clazz, inflater, root, false);
}
@SuppressWarnings("unchecked")
@NonNull
public static <Binding extends ViewBinding> Binding inflate(Class<?> clazz, LayoutInflater inflater, ViewGroup root, boolean attachToRoot) {
Class<?> bindingClass = getBindingClass(clazz);
Binding binding = null;
if (bindingClass != null) {
try {
Method method = bindingClass.getMethod("inflate", LayoutInflater.class, ViewGroup.class, boolean.class);
binding = (Binding) method.invoke(null, inflater, root, attachToRoot);
} catch (Exception e) {
e.printStackTrace();
}
}
return Objects.requireNonNull(binding);
}
public static Class<?> getBindingClass(Class<?> clazz) {
Type[] types = null;
Class<?> bindingClass = null;
if (clazz.getGenericSuperclass() instanceof ParameterizedType) {
ParameterizedType parameterizedType = (ParameterizedType) clazz.getGenericSuperclass();
types = Objects.requireNonNull(parameterizedType).getActualTypeArguments();
} else {
Type[] genericInterfaces = clazz.getGenericInterfaces();
for (Type anInterface : genericInterfaces) {
// 判断是否是参数化的类型
}
}
if (types == null) {
return null;
}
for (Type type : types) {
if (type instanceof Class<?>) {
Class<?> temp = (Class<?>) type;
if (ViewBinding.class.isAssignableFrom(temp)) {
bindingClass = temp;
}
}
}
return bindingClass;
}
//-----------------获取 activity中的所有view
private List<View> getAllViews(Activity act) {
return getAllChildViews(act.getWindow().getDecorView());
}
private List<View> getAllChildViews(View view) {
List<View> allchildren = new ArrayList();
if (view instanceof ViewGroup) {
ViewGroup vp = (ViewGroup) view;
for (int i = 0; i < vp.getChildCount(); i++) {
View viewchild = vp.getChildAt(i);
allchildren.add(viewchild);
//再次 调用本身(递归)
allchildren.addAll(getAllChildViews(viewchild));
}
}
return allchildren;
}
}

View File

@@ -0,0 +1,17 @@
package com.miraclegarden.library;
import org.junit.Test;
import static org.junit.Assert.*;
/**
* Example local unit test, which will execute on the development machine (host).
*
* @see <a href="http://d.android.com/tools/testing">Testing documentation</a>
*/
public class ExampleUnitTest {
@Test
public void addition_isCorrect() {
assertEquals(4, 2 + 2);
}
}