This commit is contained in:
metacryst
2026-01-09 11:14:27 -06:00
parent cf03c95664
commit 637c9e4674
2149 changed files with 527743 additions and 0 deletions

View File

@@ -0,0 +1,81 @@
ext {
capacitorVersion = System.getenv('CAPACITOR_VERSION')
junitVersion = project.hasProperty('junitVersion') ? rootProject.ext.junitVersion : '4.13.2'
androidxAppCompatVersion = project.hasProperty('androidxAppCompatVersion') ? rootProject.ext.androidxAppCompatVersion : '1.7.0'
androidxJunitVersion = project.hasProperty('androidxJunitVersion') ? rootProject.ext.androidxJunitVersion : '1.2.1'
androidxEspressoCoreVersion = project.hasProperty('androidxEspressoCoreVersion') ? rootProject.ext.androidxEspressoCoreVersion : '3.6.1'
coreSplashScreenVersion = project.hasProperty('coreSplashScreenVersion') ? rootProject.ext.coreSplashScreenVersion : '1.0.1'
}
buildscript {
repositories {
google()
mavenCentral()
maven {
url "https://plugins.gradle.org/m2/"
}
}
dependencies {
classpath 'com.android.tools.build:gradle:8.7.2'
if (System.getenv("CAP_PLUGIN_PUBLISH") == "true") {
classpath 'io.github.gradle-nexus:publish-plugin:1.3.0'
}
}
}
apply plugin: 'com.android.library'
if (System.getenv("CAP_PLUGIN_PUBLISH") == "true") {
apply plugin: 'io.github.gradle-nexus.publish-plugin'
apply from: file('../../scripts/android/publish-root.gradle')
apply from: file('../../scripts/android/publish-module.gradle')
}
android {
namespace "com.capacitorjs.plugins.splashscreen"
compileSdk project.hasProperty('compileSdkVersion') ? rootProject.ext.compileSdkVersion : 35
defaultConfig {
minSdkVersion project.hasProperty('minSdkVersion') ? rootProject.ext.minSdkVersion : 23
targetSdkVersion project.hasProperty('targetSdkVersion') ? rootProject.ext.targetSdkVersion : 35
versionCode 1
versionName "1.0"
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
lintOptions {
abortOnError false
}
compileOptions {
sourceCompatibility JavaVersion.VERSION_21
targetCompatibility JavaVersion.VERSION_21
}
publishing {
singleVariant("release")
}
}
repositories {
google()
mavenCentral()
}
dependencies {
implementation fileTree(dir: 'libs', include: ['*.jar'])
if (System.getenv("CAP_PLUGIN_PUBLISH") == "true") {
implementation "com.capacitorjs:core:$capacitorVersion"
} else {
implementation project(':capacitor-android')
}
implementation "androidx.appcompat:appcompat:$androidxAppCompatVersion"
testImplementation "junit:junit:$junitVersion"
androidTestImplementation "androidx.test.ext:junit:$androidxJunitVersion"
androidTestImplementation "androidx.test.espresso:espresso-core:$androidxEspressoCoreVersion"
implementation "androidx.core:core-splashscreen:$coreSplashScreenVersion"
}

View File

@@ -0,0 +1,2 @@
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
</manifest>

View File

@@ -0,0 +1,6 @@
package com.capacitorjs.plugins.splashscreen;
public interface SplashListener {
void completed();
void error();
}

View File

@@ -0,0 +1,689 @@
package com.capacitorjs.plugins.splashscreen;
import android.animation.Animator;
import android.animation.AnimatorListenerAdapter;
import android.animation.ObjectAnimator;
import android.app.Activity;
import android.app.Dialog;
import android.content.Context;
import android.content.res.ColorStateList;
import android.content.res.Resources;
import android.graphics.PixelFormat;
import android.graphics.drawable.Animatable;
import android.graphics.drawable.Drawable;
import android.graphics.drawable.LayerDrawable;
import android.os.Build;
import android.os.Handler;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.view.ViewTreeObserver;
import android.view.ViewTreeObserver.OnPreDrawListener;
import android.view.Window;
import android.view.WindowInsetsController;
import android.view.WindowManager;
import android.view.animation.LinearInterpolator;
import android.widget.FrameLayout;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.ProgressBar;
import androidx.appcompat.app.AppCompatActivity;
import androidx.core.view.WindowCompat;
import androidx.core.view.WindowInsetsCompat;
import com.getcapacitor.Logger;
/**
* A Splash Screen service for showing and hiding a splash screen in the app.
*/
public class SplashScreen {
private Dialog dialog;
private View splashImage;
private ProgressBar spinnerBar;
private WindowManager windowManager;
private boolean isVisible = false;
private boolean isHiding = false;
private Context context;
private View content;
private SplashScreenConfig config;
private OnPreDrawListener onPreDrawListener;
SplashScreen(Context context, SplashScreenConfig config) {
this.context = context;
this.config = config;
}
/**
* Show the splash screen on launch without fading in
*
* @param activity
*/
public void showOnLaunch(final AppCompatActivity activity) {
if (config.getLaunchShowDuration() == 0) {
return;
}
SplashScreenSettings settings = new SplashScreenSettings();
settings.setShowDuration(config.getLaunchShowDuration());
settings.setAutoHide(config.isLaunchAutoHide());
// Method can fail if styles are incorrectly set...
// If it fails, log error & fallback to old method
try {
showWithAndroid12API(activity, settings);
return;
} catch (Exception e) {
Logger.warn("Android 12 Splash API failed... using previous method.");
this.onPreDrawListener = null;
}
settings.setFadeInDuration(config.getLaunchFadeInDuration());
if (config.isUsingDialog()) {
showDialog(activity, settings, null, true);
} else {
show(activity, settings, null, true);
}
}
/**
* Show the Splash Screen using the Android 12 API (31+)
* Uses Compat Library for backwards compatibility
*
* @param activity
* @param settings Settings used to show the Splash Screen
*/
private void showWithAndroid12API(final AppCompatActivity activity, final SplashScreenSettings settings) {
if (activity == null || activity.isFinishing()) return;
activity.runOnUiThread(
() -> {
androidx.core.splashscreen.SplashScreen windowSplashScreen = androidx.core.splashscreen.SplashScreen.installSplashScreen(
activity
);
windowSplashScreen.setKeepOnScreenCondition(() -> isVisible || isHiding);
if (config.getLaunchFadeOutDuration() > 0) {
// Set Fade Out Animation
windowSplashScreen.setOnExitAnimationListener(
windowSplashScreenView -> {
final ObjectAnimator fadeAnimator = ObjectAnimator.ofFloat(
windowSplashScreenView.getView(),
View.ALPHA,
1f,
0f
);
fadeAnimator.setInterpolator(new LinearInterpolator());
fadeAnimator.setDuration(config.getLaunchFadeOutDuration());
fadeAnimator.addListener(
new AnimatorListenerAdapter() {
@Override
public void onAnimationEnd(Animator animation) {
isHiding = false;
windowSplashScreenView.remove();
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
activity.getSplashScreen().clearOnExitAnimationListener();
}
}
}
);
fadeAnimator.start();
isHiding = true;
isVisible = false;
}
);
}
// Set Pre Draw Listener & Delay Drawing Until Duration Elapses
content = activity.findViewById(android.R.id.content);
this.onPreDrawListener =
new ViewTreeObserver.OnPreDrawListener() {
@Override
public boolean onPreDraw() {
// Start Timer On First Run
if (!isVisible && !isHiding) {
isVisible = true;
new Handler(context.getMainLooper())
.postDelayed(
() -> {
// Splash screen is done... start drawing content.
if (settings.isAutoHide()) {
isVisible = false;
onPreDrawListener = null;
content.getViewTreeObserver().removeOnPreDrawListener(this);
}
},
settings.getShowDuration()
);
}
// Not ready to dismiss splash screen
return false;
}
};
content.getViewTreeObserver().addOnPreDrawListener(this.onPreDrawListener);
}
);
}
/**
* Show the Splash Screen
*
* @param activity
* @param settings Settings used to show the Splash Screen
* @param splashListener A listener to handle the finish of the animation (if any)
*/
public void show(final AppCompatActivity activity, final SplashScreenSettings settings, final SplashListener splashListener) {
if (config.isUsingDialog()) {
showDialog(activity, settings, splashListener, false);
} else {
show(activity, settings, splashListener, false);
}
}
private void showDialog(
final AppCompatActivity activity,
final SplashScreenSettings settings,
final SplashListener splashListener,
final boolean isLaunchSplash
) {
if (activity == null || activity.isFinishing()) return;
if (isVisible) {
splashListener.completed();
return;
}
activity.runOnUiThread(
() -> {
if (config.isImmersive()) {
dialog = new Dialog(activity, R.style.capacitor_immersive_style);
} else if (config.isFullScreen()) {
dialog = new Dialog(activity, R.style.capacitor_full_screen_style);
} else {
dialog = new Dialog(activity, R.style.capacitor_default_style);
}
int splashId = 0;
if (config.getLayoutName() != null) {
splashId = context.getResources().getIdentifier(config.getLayoutName(), "layout", context.getPackageName());
if (splashId == 0) {
Logger.warn("Layout not found, using default");
}
}
if (splashId != 0) {
dialog.setContentView(splashId);
} else {
Drawable splash = getSplashDrawable();
LinearLayout parent = new LinearLayout(context);
parent.setLayoutParams(
new LinearLayout.LayoutParams(LinearLayout.LayoutParams.MATCH_PARENT, LinearLayout.LayoutParams.WRAP_CONTENT)
);
parent.setOrientation(LinearLayout.VERTICAL);
if (splash != null) {
parent.setBackground(splash);
}
dialog.setContentView(parent);
}
dialog.setCancelable(false);
if (!dialog.isShowing()) {
dialog.show();
}
isVisible = true;
if (settings.isAutoHide()) {
new Handler(context.getMainLooper())
.postDelayed(
() -> {
hideDialog(activity, isLaunchSplash);
if (splashListener != null) {
splashListener.completed();
}
},
settings.getShowDuration()
);
} else {
// If no autoHide, call complete
if (splashListener != null) {
splashListener.completed();
}
}
}
);
}
/**
* Hide the Splash Screen
*
* @param settings Settings used to hide the Splash Screen
*/
public void hide(SplashScreenSettings settings) {
hide(settings.getFadeOutDuration(), false);
}
/**
* Hide the Splash Screen when showing it as a dialog
*
* @param activity the activity showing the dialog
*/
public void hideDialog(final AppCompatActivity activity) {
hideDialog(activity, false);
}
public void onPause() {
tearDown(true);
}
public void onDestroy() {
tearDown(true);
}
private void buildViews() {
if (splashImage == null) {
int splashId = 0;
Drawable splash;
if (config.getLayoutName() != null) {
splashId = context.getResources().getIdentifier(config.getLayoutName(), "layout", context.getPackageName());
if (splashId == 0) {
Logger.warn("Layout not found, defaulting to ImageView");
}
}
if (splashId != 0) {
Activity activity = (Activity) context;
LayoutInflater inflator = activity.getLayoutInflater();
ViewGroup root = new FrameLayout(context);
root.setLayoutParams(
new FrameLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT)
);
splashImage = inflator.inflate(splashId, root, false);
} else {
splash = getSplashDrawable();
if (splash != null) {
if (splash instanceof Animatable) {
((Animatable) splash).start();
}
if (splash instanceof LayerDrawable) {
LayerDrawable layeredSplash = (LayerDrawable) splash;
for (int i = 0; i < layeredSplash.getNumberOfLayers(); i++) {
Drawable layerDrawable = layeredSplash.getDrawable(i);
if (layerDrawable instanceof Animatable) {
((Animatable) layerDrawable).start();
}
}
}
splashImage = new ImageView(context);
// Stops flickers dead in their tracks
// https://stackoverflow.com/a/21847579/32140
ImageView imageView = (ImageView) splashImage;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
imageView.setLayerType(View.LAYER_TYPE_SOFTWARE, null);
} else {
legacyStopFlickers(imageView);
}
imageView.setScaleType(config.getScaleType());
imageView.setImageDrawable(splash);
} else {
return;
}
}
splashImage.setFitsSystemWindows(true);
if (config.getBackgroundColor() != null) {
splashImage.setBackgroundColor(config.getBackgroundColor());
}
}
if (spinnerBar == null) {
if (config.getSpinnerStyle() != null) {
int spinnerBarStyle = config.getSpinnerStyle();
spinnerBar = new ProgressBar(context, null, spinnerBarStyle);
} else {
spinnerBar = new ProgressBar(context);
}
spinnerBar.setIndeterminate(true);
Integer spinnerBarColor = config.getSpinnerColor();
if (spinnerBarColor != null) {
int[][] states = new int[][] {
new int[] { android.R.attr.state_enabled }, // enabled
new int[] { -android.R.attr.state_enabled }, // disabled
new int[] { -android.R.attr.state_checked }, // unchecked
new int[] { android.R.attr.state_pressed } // pressed
};
int[] colors = new int[] { spinnerBarColor, spinnerBarColor, spinnerBarColor, spinnerBarColor };
ColorStateList colorStateList = new ColorStateList(states, colors);
spinnerBar.setIndeterminateTintList(colorStateList);
}
}
}
@SuppressWarnings("deprecation")
private void legacyStopFlickers(ImageView imageView) {
imageView.setDrawingCacheEnabled(true);
}
private Drawable getSplashDrawable() {
int splashId = context.getResources().getIdentifier(config.getResourceName(), "drawable", context.getPackageName());
try {
Drawable drawable = context.getResources().getDrawable(splashId, context.getTheme());
return drawable;
} catch (Resources.NotFoundException ex) {
Logger.warn("No splash screen found, not displaying");
return null;
}
}
private void show(
final AppCompatActivity activity,
final SplashScreenSettings settings,
final SplashListener splashListener,
final boolean isLaunchSplash
) {
windowManager = (WindowManager) activity.getSystemService(Context.WINDOW_SERVICE);
if (activity.isFinishing()) {
return;
}
buildViews();
if (isVisible) {
splashListener.completed();
return;
}
final Animator.AnimatorListener listener = new Animator.AnimatorListener() {
@Override
public void onAnimationEnd(Animator animator) {
isVisible = true;
if (settings.isAutoHide()) {
new Handler(context.getMainLooper())
.postDelayed(
() -> {
hide(settings.getFadeOutDuration(), isLaunchSplash);
if (splashListener != null) {
splashListener.completed();
}
},
settings.getShowDuration()
);
} else {
// If no autoHide, call complete
if (splashListener != null) {
splashListener.completed();
}
}
}
@Override
public void onAnimationCancel(Animator animator) {}
@Override
public void onAnimationRepeat(Animator animator) {}
@Override
public void onAnimationStart(Animator animator) {}
};
Handler mainHandler = new Handler(context.getMainLooper());
mainHandler.post(
() -> {
WindowManager.LayoutParams params = new WindowManager.LayoutParams();
params.gravity = Gravity.CENTER;
params.flags = activity.getWindow().getAttributes().flags;
// Required to enable the view to actually fade
params.format = PixelFormat.TRANSLUCENT;
try {
windowManager.addView(splashImage, params);
} catch (IllegalStateException | IllegalArgumentException ex) {
Logger.debug("Could not add splash view");
return;
}
if (config.isImmersive()) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
activity.runOnUiThread(
() -> {
Window window = activity.getWindow();
WindowCompat.setDecorFitsSystemWindows(window, false);
WindowInsetsController controller = splashImage.getWindowInsetsController();
controller.hide(WindowInsetsCompat.Type.systemBars());
controller.setSystemBarsBehavior(WindowInsetsController.BEHAVIOR_SHOW_TRANSIENT_BARS_BY_SWIPE);
}
);
} else {
legacyImmersive();
}
} else if (config.isFullScreen()) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
activity.runOnUiThread(
() -> {
Window window = activity.getWindow();
WindowCompat.setDecorFitsSystemWindows(window, false);
WindowInsetsController controller = splashImage.getWindowInsetsController();
controller.hide(WindowInsetsCompat.Type.statusBars());
}
);
} else {
legacyFullscreen();
}
}
splashImage.setAlpha(0f);
splashImage
.animate()
.alpha(1f)
.setInterpolator(new LinearInterpolator())
.setDuration(settings.getFadeInDuration())
.setListener(listener)
.start();
splashImage.setVisibility(View.VISIBLE);
if (spinnerBar != null) {
spinnerBar.setVisibility(View.INVISIBLE);
if (spinnerBar.getParent() != null) {
windowManager.removeView(spinnerBar);
}
params.height = WindowManager.LayoutParams.WRAP_CONTENT;
params.width = WindowManager.LayoutParams.WRAP_CONTENT;
windowManager.addView(spinnerBar, params);
if (config.isShowSpinner()) {
spinnerBar.setAlpha(0f);
spinnerBar
.animate()
.alpha(1f)
.setInterpolator(new LinearInterpolator())
.setDuration(settings.getFadeInDuration())
.start();
spinnerBar.setVisibility(View.VISIBLE);
}
}
}
);
}
@SuppressWarnings("deprecation")
private void legacyImmersive() {
final int flags =
View.SYSTEM_UI_FLAG_LAYOUT_STABLE |
View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION |
View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN |
View.SYSTEM_UI_FLAG_HIDE_NAVIGATION |
View.SYSTEM_UI_FLAG_FULLSCREEN |
View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY;
splashImage.setSystemUiVisibility(flags);
}
@SuppressWarnings("deprecation")
private void legacyFullscreen() {
splashImage.setSystemUiVisibility(View.SYSTEM_UI_FLAG_FULLSCREEN);
}
private void hide(final int fadeOutDuration, boolean isLaunchSplash) {
// Warn the user if the splash was hidden automatically, which means they could be experiencing an app
// that feels slower than it actually is.
if (isLaunchSplash && isVisible) {
Logger.debug(
"SplashScreen was automatically hidden after the launch timeout. " +
"You should call `SplashScreen.hide()` as soon as your web app is loaded (or increase the timeout)." +
"Read more at https://capacitorjs.com/docs/apis/splash-screen#hiding-the-splash-screen"
);
}
if (isHiding) {
return;
}
// Hide with Android 12 API
if (null != this.onPreDrawListener) {
if (fadeOutDuration != 200) {
Logger.warn(
"fadeOutDuration parameter doesn't work on initial splash screen, use launchFadeOutDuration configuration option"
);
}
this.isVisible = false;
if (null != content) {
content.getViewTreeObserver().removeOnPreDrawListener(this.onPreDrawListener);
}
this.onPreDrawListener = null;
return;
}
if (splashImage == null || splashImage.getParent() == null) {
return;
}
isHiding = true;
final Animator.AnimatorListener listener = new Animator.AnimatorListener() {
@Override
public void onAnimationEnd(Animator animator) {
tearDown(false);
}
@Override
public void onAnimationCancel(Animator animator) {
tearDown(false);
}
@Override
public void onAnimationStart(Animator animator) {}
@Override
public void onAnimationRepeat(Animator animator) {}
};
Handler mainHandler = new Handler(context.getMainLooper());
mainHandler.post(
() -> {
if (spinnerBar != null) {
spinnerBar.setAlpha(1f);
spinnerBar.animate().alpha(0).setInterpolator(new LinearInterpolator()).setDuration(fadeOutDuration).start();
}
splashImage.setAlpha(1f);
splashImage
.animate()
.alpha(0)
.setInterpolator(new LinearInterpolator())
.setDuration(fadeOutDuration)
.setListener(listener)
.start();
}
);
}
private void hideDialog(final AppCompatActivity activity, boolean isLaunchSplash) {
// Warn the user if the splash was hidden automatically, which means they could be experiencing an app
// that feels slower than it actually is.
if (isLaunchSplash && isVisible) {
Logger.debug(
"SplashScreen was automatically hidden after the launch timeout. " +
"You should call `SplashScreen.hide()` as soon as your web app is loaded (or increase the timeout)." +
"Read more at https://capacitorjs.com/docs/apis/splash-screen#hiding-the-splash-screen"
);
}
if (isHiding) {
return;
}
// Hide with Android 12 API
if (null != this.onPreDrawListener) {
this.isVisible = false;
if (null != content) {
content.getViewTreeObserver().removeOnPreDrawListener(this.onPreDrawListener);
}
this.onPreDrawListener = null;
return;
}
isHiding = true;
activity.runOnUiThread(
() -> {
if (dialog != null && dialog.isShowing()) {
if (!activity.isFinishing() && !activity.isDestroyed()) {
dialog.dismiss();
}
dialog = null;
isHiding = false;
isVisible = false;
}
}
);
}
private void tearDown(boolean removeSpinner) {
if (spinnerBar != null && spinnerBar.getParent() != null) {
spinnerBar.setVisibility(View.INVISIBLE);
if (removeSpinner) {
windowManager.removeView(spinnerBar);
}
}
if (splashImage != null && splashImage.getParent() != null) {
splashImage.setVisibility(View.INVISIBLE);
windowManager.removeView(splashImage);
}
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R && config.isFullScreen() || config.isImmersive()) {
// Exit fullscreen mode
Window window = ((Activity) context).getWindow();
WindowCompat.setDecorFitsSystemWindows(window, true);
}
isHiding = false;
isVisible = false;
}
}

View File

@@ -0,0 +1,129 @@
package com.capacitorjs.plugins.splashscreen;
import android.widget.ImageView.ScaleType;
public class SplashScreenConfig {
private Integer backgroundColor;
private Integer spinnerStyle;
private Integer spinnerColor;
private boolean showSpinner = false;
private Integer launchShowDuration = 500;
private boolean launchAutoHide = true;
private Integer launchFadeInDuration = 0;
private Integer launchFadeOutDuration = 200;
private String resourceName = "splash";
private boolean immersive = false;
private boolean fullScreen = false;
private ScaleType scaleType = ScaleType.FIT_XY;
private boolean usingDialog = false;
private String layoutName;
public Integer getBackgroundColor() {
return backgroundColor;
}
public void setBackgroundColor(Integer backgroundColor) {
this.backgroundColor = backgroundColor;
}
public Integer getSpinnerStyle() {
return spinnerStyle;
}
public void setSpinnerStyle(Integer spinnerStyle) {
this.spinnerStyle = spinnerStyle;
}
public Integer getSpinnerColor() {
return spinnerColor;
}
public void setSpinnerColor(Integer spinnerColor) {
this.spinnerColor = spinnerColor;
}
public boolean isShowSpinner() {
return showSpinner;
}
public void setShowSpinner(boolean showSpinner) {
this.showSpinner = showSpinner;
}
public Integer getLaunchShowDuration() {
return launchShowDuration;
}
public void setLaunchShowDuration(Integer launchShowDuration) {
this.launchShowDuration = launchShowDuration;
}
public boolean isLaunchAutoHide() {
return launchAutoHide;
}
public void setLaunchAutoHide(boolean launchAutoHide) {
this.launchAutoHide = launchAutoHide;
}
public Integer getLaunchFadeInDuration() {
return launchFadeInDuration;
}
public String getResourceName() {
return resourceName;
}
public void setResourceName(String resourceName) {
this.resourceName = resourceName;
}
public boolean isImmersive() {
return immersive;
}
public void setImmersive(boolean immersive) {
this.immersive = immersive;
}
public boolean isFullScreen() {
return fullScreen;
}
public void setFullScreen(boolean fullScreen) {
this.fullScreen = fullScreen;
}
public ScaleType getScaleType() {
return scaleType;
}
public void setScaleType(ScaleType scaleType) {
this.scaleType = scaleType;
}
public boolean isUsingDialog() {
return usingDialog;
}
public void setUsingDialog(boolean usingDialog) {
this.usingDialog = usingDialog;
}
public String getLayoutName() {
return layoutName;
}
public void setLayoutName(String layoutName) {
this.layoutName = layoutName;
}
public Integer getLaunchFadeOutDuration() {
return launchFadeOutDuration;
}
public void setLaunchFadeOutDuration(Integer launchFadeOutDuration) {
this.launchFadeOutDuration = launchFadeOutDuration;
}
}

View File

@@ -0,0 +1,166 @@
package com.capacitorjs.plugins.splashscreen;
import android.widget.ImageView;
import com.getcapacitor.Logger;
import com.getcapacitor.Plugin;
import com.getcapacitor.PluginCall;
import com.getcapacitor.PluginMethod;
import com.getcapacitor.annotation.CapacitorPlugin;
import com.getcapacitor.util.WebColor;
import java.util.Locale;
@CapacitorPlugin(name = "SplashScreen")
public class SplashScreenPlugin extends Plugin {
private SplashScreen splashScreen;
private SplashScreenConfig config;
public void load() {
config = getSplashScreenConfig();
splashScreen = new SplashScreen(getContext(), config);
if (!bridge.isMinimumWebViewInstalled() && bridge.getConfig().getErrorPath() != null && !config.isLaunchAutoHide()) {
return;
} else {
splashScreen.showOnLaunch(getActivity());
}
}
@PluginMethod
public void show(final PluginCall call) {
splashScreen.show(
getActivity(),
getSettings(call),
new SplashListener() {
@Override
public void completed() {
call.resolve();
}
@Override
public void error() {
call.reject("An error occurred while showing splash");
}
}
);
}
@PluginMethod
public void hide(PluginCall call) {
if (config.isUsingDialog()) {
splashScreen.hideDialog(getActivity());
} else {
splashScreen.hide(getSettings(call));
}
call.resolve();
}
@Override
protected void handleOnPause() {
splashScreen.onPause();
}
@Override
protected void handleOnDestroy() {
splashScreen.onDestroy();
}
private SplashScreenSettings getSettings(PluginCall call) {
SplashScreenSettings settings = new SplashScreenSettings();
if (call.getInt("showDuration") != null) {
settings.setShowDuration(call.getInt("showDuration"));
}
if (call.getInt("fadeInDuration") != null) {
settings.setFadeInDuration(call.getInt("fadeInDuration"));
}
if (call.getInt("fadeOutDuration") != null) {
settings.setFadeOutDuration(call.getInt("fadeOutDuration"));
}
if (call.getBoolean("autoHide") != null) {
settings.setAutoHide(call.getBoolean("autoHide"));
}
return settings;
}
private SplashScreenConfig getSplashScreenConfig() {
SplashScreenConfig config = new SplashScreenConfig();
String backgroundColor = getConfig().getString("backgroundColor");
if (backgroundColor != null) {
try {
config.setBackgroundColor(WebColor.parseColor(backgroundColor));
} catch (IllegalArgumentException ex) {
Logger.debug("Background color not applied");
}
}
Integer duration = getConfig().getInt("launchShowDuration", config.getLaunchShowDuration());
config.setLaunchShowDuration(duration);
Integer fadeOutDuration = getConfig().getInt("launchFadeOutDuration", config.getLaunchFadeOutDuration());
config.setLaunchFadeOutDuration(fadeOutDuration);
Boolean autohide = getConfig().getBoolean("launchAutoHide", config.isLaunchAutoHide());
config.setLaunchAutoHide(autohide);
if (getConfig().getString("androidSplashResourceName") != null) {
config.setResourceName(getConfig().getString("androidSplashResourceName"));
}
Boolean immersive = getConfig().getBoolean("splashImmersive", config.isImmersive());
config.setImmersive(immersive);
Boolean fullScreen = getConfig().getBoolean("splashFullScreen", config.isFullScreen());
config.setFullScreen(fullScreen);
String spinnerStyle = getConfig().getString("androidSpinnerStyle");
if (spinnerStyle != null) {
int spinnerBarStyle = android.R.attr.progressBarStyleLarge;
switch (spinnerStyle.toLowerCase(Locale.ROOT)) {
case "horizontal":
spinnerBarStyle = android.R.attr.progressBarStyleHorizontal;
break;
case "small":
spinnerBarStyle = android.R.attr.progressBarStyleSmall;
break;
case "large":
spinnerBarStyle = android.R.attr.progressBarStyleLarge;
break;
case "inverse":
spinnerBarStyle = android.R.attr.progressBarStyleInverse;
break;
case "smallinverse":
spinnerBarStyle = android.R.attr.progressBarStyleSmallInverse;
break;
case "largeinverse":
spinnerBarStyle = android.R.attr.progressBarStyleLargeInverse;
break;
}
config.setSpinnerStyle(spinnerBarStyle);
}
String spinnerColor = getConfig().getString("spinnerColor");
if (spinnerColor != null) {
try {
config.setSpinnerColor(WebColor.parseColor(spinnerColor));
} catch (IllegalArgumentException ex) {
Logger.debug("Spinner color not applied");
}
}
String scaleTypeName = getConfig().getString("androidScaleType");
if (scaleTypeName != null) {
ImageView.ScaleType scaleType = null;
try {
scaleType = ImageView.ScaleType.valueOf(scaleTypeName);
} catch (IllegalArgumentException ex) {
scaleType = ImageView.ScaleType.FIT_XY;
}
config.setScaleType(scaleType);
}
Boolean showSpinner = getConfig().getBoolean("showSpinner", config.isShowSpinner());
config.setShowSpinner(showSpinner);
Boolean useDialog = getConfig().getBoolean("useDialog", config.isUsingDialog());
config.setUsingDialog(useDialog);
if (getConfig().getString("layoutName") != null) {
config.setLayoutName(getConfig().getString("layoutName"));
}
return config;
}
}

View File

@@ -0,0 +1,41 @@
package com.capacitorjs.plugins.splashscreen;
public class SplashScreenSettings {
private Integer showDuration = 3000;
private Integer fadeInDuration = 200;
private Integer fadeOutDuration = 200;
private boolean autoHide = true;
public Integer getShowDuration() {
return showDuration;
}
public void setShowDuration(Integer showDuration) {
this.showDuration = showDuration;
}
public Integer getFadeInDuration() {
return fadeInDuration;
}
public void setFadeInDuration(Integer fadeInDuration) {
this.fadeInDuration = fadeInDuration;
}
public Integer getFadeOutDuration() {
return fadeOutDuration;
}
public void setFadeOutDuration(Integer fadeOutDuration) {
this.fadeOutDuration = fadeOutDuration;
}
public boolean isAutoHide() {
return autoHide;
}
public void setAutoHide(boolean autoHide) {
this.autoHide = autoHide;
}
}

View File

View File

@@ -0,0 +1,11 @@
<?xml version="1.0" encoding="utf-8"?>
<resources>
<style name="capacitor_default_style" parent="AppTheme.NoActionBar">
</style>
<style name="capacitor_full_screen_style" parent="AppTheme.NoActionBar">
<item name="android:windowFullscreen">true</item>
</style>
<style name="capacitor_immersive_style" parent="capacitor_full_screen_style">
<item name="android:windowTranslucentNavigation">true</item>
</style>
</resources>