Inflate necessary previews upon user interaction instead of

inflating everything on creation of the screen. This will
improve the speed of opening the screen and refreshing screen upon
commiting change.

Test: Manually tested by interacting with ViewPager and SeekBar.
Bug: 30697309
Change-Id: Ieb2fac95696b8be33fd508f3b75741529b68e946
(cherry picked from commit 5666ddfe5d)
This commit is contained in:
Noah Wang
2016-08-23 14:56:27 -07:00
parent 465e926542
commit ff23df19ba

View File

@@ -23,6 +23,8 @@ import android.support.v4.view.PagerAdapter;
import android.view.LayoutInflater; import android.view.LayoutInflater;
import android.view.View; import android.view.View;
import android.view.ViewGroup; import android.view.ViewGroup;
import android.view.ViewStub;
import android.view.ViewStub.OnInflateListener;
import android.view.animation.AccelerateInterpolator; import android.view.animation.AccelerateInterpolator;
import android.view.animation.DecelerateInterpolator; import android.view.animation.DecelerateInterpolator;
import android.view.animation.Interpolator; import android.view.animation.Interpolator;
@@ -53,10 +55,13 @@ public class PreviewPagerAdapter extends PagerAdapter {
private int mAnimationCounter; private int mAnimationCounter;
private boolean[][] mViewStubInflated;
public PreviewPagerAdapter(Context context, boolean isLayoutRtl, public PreviewPagerAdapter(Context context, boolean isLayoutRtl,
int[] previewSampleResIds, Configuration[] configurations) { int[] previewSampleResIds, Configuration[] configurations) {
mIsLayoutRtl = isLayoutRtl; mIsLayoutRtl = isLayoutRtl;
mPreviewFrames = new FrameLayout[previewSampleResIds.length]; mPreviewFrames = new FrameLayout[previewSampleResIds.length];
mViewStubInflated = new boolean[previewSampleResIds.length][configurations.length];
for (int i = 0; i < previewSampleResIds.length; ++i) { for (int i = 0; i < previewSampleResIds.length; ++i) {
int p = mIsLayoutRtl ? previewSampleResIds.length - 1 - i : i; int p = mIsLayoutRtl ? previewSampleResIds.length - 1 - i : i;
@@ -65,18 +70,25 @@ public class PreviewPagerAdapter extends PagerAdapter {
LinearLayout.LayoutParams.MATCH_PARENT, LinearLayout.LayoutParams.MATCH_PARENT,
LinearLayout.LayoutParams.MATCH_PARENT)); LinearLayout.LayoutParams.MATCH_PARENT));
for (Configuration configuration : configurations) { for (int j = 0; j < configurations.length; ++j) {
// Create a new configuration for the specified value. It won't // Create a new configuration for the specified value. It won't
// have any theme set, so manually apply the current theme. // have any theme set, so manually apply the current theme.
final Context configContext = context.createConfigurationContext(configuration); final Context configContext = context.createConfigurationContext(configurations[j]);
configContext.setTheme(context.getThemeResId()); configContext.setTheme(context.getThemeResId());
final LayoutInflater configInflater = LayoutInflater.from(configContext); final LayoutInflater configInflater = LayoutInflater.from(configContext);
final View sampleView = configInflater.inflate(previewSampleResIds[i], final ViewStub sampleViewStub = new ViewStub(configContext);
mPreviewFrames[p], false); sampleViewStub.setLayoutResource(previewSampleResIds[i]);
sampleView.setAlpha(0); final int fi = i, fj = j;
sampleView.setVisibility(View.INVISIBLE); sampleViewStub.setOnInflateListener(new OnInflateListener() {
mPreviewFrames[p].addView(sampleView); @Override
public void onInflate(ViewStub stub, View inflated) {
inflated.setVisibility(stub.getVisibility());
mViewStubInflated[fi][fj] = true;
}
});
mPreviewFrames[p].addView(sampleViewStub);
} }
} }
} }
@@ -110,44 +122,71 @@ public class PreviewPagerAdapter extends PagerAdapter {
mAnimationEndAction = action; mAnimationEndAction = action;
} }
void setPreviewLayer(int newIndex, int currentIndex, int currentItem, boolean animate) { void setPreviewLayer(int newLayerIndex, int currentLayerIndex, int currentFrameIndex,
final boolean animate) {
for (FrameLayout previewFrame : mPreviewFrames) { for (FrameLayout previewFrame : mPreviewFrames) {
if (currentIndex >= 0) { if (currentLayerIndex >= 0) {
final View lastLayer = previewFrame.getChildAt(currentIndex); final View lastLayer = previewFrame.getChildAt(currentLayerIndex);
if (animate && previewFrame == mPreviewFrames[currentItem]) { if (mViewStubInflated[currentFrameIndex][currentLayerIndex]) {
lastLayer.animate() // Explicitly set to INVISIBLE only when the stub has
.alpha(0) // already been inflated.
.setInterpolator(FADE_OUT_INTERPOLATOR) if (previewFrame == mPreviewFrames[currentFrameIndex]) {
.setDuration(CROSS_FADE_DURATION_MS) setVisibility(lastLayer, View.INVISIBLE, animate);
.setListener(new PreviewFrameAnimatorListener()) } else {
.withEndAction(new Runnable() { setVisibility(lastLayer, View.INVISIBLE, false);
@Override }
public void run() {
lastLayer.setVisibility(View.INVISIBLE);
}
});
} else {
lastLayer.setAlpha(0);
lastLayer.setVisibility(View.INVISIBLE);
} }
} }
final View nextLayer = previewFrame.getChildAt(newIndex); // Set next layer visible, as well as inflate necessary views.
if (animate && previewFrame == mPreviewFrames[currentItem]) { View nextLayer = previewFrame.getChildAt(newLayerIndex);
nextLayer.animate() if (previewFrame == mPreviewFrames[currentFrameIndex]) {
.alpha(1) // Inflate immediately if the stub has not yet been inflated.
.setInterpolator(FADE_IN_INTERPOLATOR) if (!mViewStubInflated[currentFrameIndex][newLayerIndex]) {
.setDuration(CROSS_FADE_DURATION_MS) nextLayer = ((ViewStub) nextLayer).inflate();
.setListener(new PreviewFrameAnimatorListener()) nextLayer.setAlpha(0.0f);
.withStartAction(new Runnable() { }
@Override setVisibility(nextLayer, View.VISIBLE, animate);
public void run() {
nextLayer.setVisibility(View.VISIBLE);
}
});
} else { } else {
nextLayer.setVisibility(View.VISIBLE); setVisibility(nextLayer, View.VISIBLE, false);
nextLayer.setAlpha(1); }
}
}
private void setVisibility(final View view, final int visibility, boolean animate) {
final float alpha = (visibility == View.VISIBLE ? 1.0f : 0.0f);
if (!animate) {
view.setAlpha(alpha);
view.setVisibility(visibility);
} else {
final Interpolator interpolator = (visibility == View.VISIBLE ? FADE_IN_INTERPOLATOR
: FADE_OUT_INTERPOLATOR);
if (visibility == View.VISIBLE) {
// Fade in animation.
view.animate()
.alpha(alpha)
.setInterpolator(FADE_IN_INTERPOLATOR)
.setDuration(CROSS_FADE_DURATION_MS)
.setListener(new PreviewFrameAnimatorListener())
.withStartAction(new Runnable() {
@Override
public void run() {
view.setVisibility(visibility);
}
});
} else {
// Fade out animation.
view.animate()
.alpha(alpha)
.setInterpolator(FADE_OUT_INTERPOLATOR)
.setDuration(CROSS_FADE_DURATION_MS)
.setListener(new PreviewFrameAnimatorListener())
.withEndAction(new Runnable() {
@Override
public void run() {
view.setVisibility(visibility);
}
});
} }
} }
} }