Skip to content

Commit

Permalink
Now internally ensures that ControllerChangeHandlers aren't reused, u…
Browse files Browse the repository at this point in the history
…nless they're specifically designed to be safe for reuse

Made ControllerChangeHandler's copy() method public
Fixes #179
  • Loading branch information
EricKuck committed Dec 15, 2016
1 parent 23a4dbb commit e7c195d
Show file tree
Hide file tree
Showing 11 changed files with 87 additions and 18 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,8 @@ public abstract class ControllerChangeHandler {

private boolean forceRemoveViewOnPush;

boolean hasBeenUsed;

/**
* Responsible for swapping Views from one Controller to another.
*
Expand Down Expand Up @@ -73,6 +75,16 @@ public void onAbortPush(@NonNull ControllerChangeHandler newHandler, @Nullable C
*/
public void completeImmediately() { }

/**
* Returns a copy of this ControllerChangeHandler. This method is internally used by the library, so
* ensure it will return an exact copy of your handler if overriding. If not overriding, the handler
* will be saved and restored from the Bundle format.
*/
@NonNull
public ControllerChangeHandler copy() {
return fromBundle(toBundle());
}

@NonNull
final Bundle toBundle() {
Bundle bundle = new Bundle();
Expand All @@ -85,11 +97,6 @@ final Bundle toBundle() {
return bundle;
}

@NonNull
final ControllerChangeHandler copy() {
return fromBundle(toBundle());
}

private void ensureDefaultConstructor() {
try {
getClass().getConstructor();
Expand Down Expand Up @@ -135,7 +142,15 @@ public static void executeChange(@Nullable final Controller to, @Nullable final

public static void executeChange(@Nullable final Controller to, @Nullable final Controller from, final boolean isPush, @Nullable final ViewGroup container, @Nullable final ControllerChangeHandler inHandler, @NonNull final List<ControllerChangeListener> listeners) {
if (container != null) {
final ControllerChangeHandler handler = inHandler != null ? inHandler : new SimpleSwapChangeHandler();
final ControllerChangeHandler handler;
if (inHandler == null) {
handler = new SimpleSwapChangeHandler();
} else if (inHandler.hasBeenUsed) {
handler = inHandler.copy();
} else {
handler = inHandler;
}
handler.hasBeenUsed = true;

if (isPush && to != null) {
inProgressPushHandlers.put(to.getInstanceId(), handler);
Expand Down
13 changes: 5 additions & 8 deletions conductor/src/main/java/com/bluelinelabs/conductor/Router.java
Original file line number Diff line number Diff line change
Expand Up @@ -172,7 +172,7 @@ public void replaceTopController(@NonNull RouterTransaction transaction) {
final boolean newHandlerRemovesViews = handler == null || handler.removesFromViewOnPush();
if (!oldHandlerRemovedViews && newHandlerRemovesViews) {
for (RouterTransaction visibleTransaction : getVisibleTransactions(backstack.iterator())) {
performControllerChange(null, visibleTransaction.controller, true, handler != null ? handler.copy() : new SimpleSwapChangeHandler());
performControllerChange(null, visibleTransaction.controller, true, handler);
}
}
}
Expand Down Expand Up @@ -368,22 +368,19 @@ public void setBackstack(@NonNull List<RouterTransaction> newBackstack, @Nullabl
}

if (visibleTransactionsChanged) {
ControllerChangeHandler handler = changeHandler != null ? changeHandler : new SimpleSwapChangeHandler();

Controller rootController = oldVisibleTransactions.size() > 0 ? oldVisibleTransactions.get(0).controller : null;
performControllerChange(newVisibleTransactions.get(0).controller, rootController, true, handler);
performControllerChange(newVisibleTransactions.get(0).controller, rootController, true, changeHandler);

for (int i = oldVisibleTransactions.size() - 1; i > 0; i--) {
RouterTransaction transaction = oldVisibleTransactions.get(i);
ControllerChangeHandler localHandler = handler.copy();
ControllerChangeHandler localHandler = changeHandler != null ? changeHandler.copy() : new SimpleSwapChangeHandler();
localHandler.setForceRemoveViewOnPush(true);
performControllerChange(null, transaction.controller, true, localHandler);
}

for (int i = 1; i < newVisibleTransactions.size(); i++) {
RouterTransaction transaction = newVisibleTransactions.get(i);
handler = transaction.pushChangeHandler() != null ? transaction.pushChangeHandler().copy() : new SimpleSwapChangeHandler();
performControllerChange(transaction.controller, newVisibleTransactions.get(i - 1).controller, true, handler);
performControllerChange(transaction.controller, newVisibleTransactions.get(i - 1).controller, true, transaction.pushChangeHandler());
}
}
}
Expand Down Expand Up @@ -631,7 +628,7 @@ private void performControllerChange(@Nullable RouterTransaction to, @Nullable R
} else if (from != null) {
changeHandler = from.popChangeHandler();
} else {
changeHandler = new SimpleSwapChangeHandler();
changeHandler = null;
}

Controller toController = to != null ? to.controller : null;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@
import android.view.View;
import android.view.ViewGroup;

import com.bluelinelabs.conductor.ControllerChangeHandler;

/**
* A change handler that will use an AutoTransition.
*/
Expand All @@ -20,4 +22,9 @@ protected Transition getTransition(@NonNull ViewGroup container, @Nullable View
return new AutoTransition();
}

@Override @NonNull
public ControllerChangeHandler copy() {
return new AutoTransitionChangeHandler();
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@
import android.view.View;
import android.view.ViewGroup;

import com.bluelinelabs.conductor.ControllerChangeHandler;

/**
* An {@link AnimatorChangeHandler} that will cross fade two views
*/
Expand Down Expand Up @@ -45,4 +47,10 @@ protected Animator getAnimator(@NonNull ViewGroup container, @Nullable View from
protected void resetFromView(@NonNull View from) {
from.setAlpha(1);
}

@Override @NonNull
public ControllerChangeHandler copy() {
return new FadeChangeHandler(getAnimationDuration(), removesFromViewOnPush());
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@
import android.view.View;
import android.view.ViewGroup;

import com.bluelinelabs.conductor.ControllerChangeHandler;

/**
* An {@link AnimatorChangeHandler} that will slide the views left or right, depending on if it's a push or pop.
*/
Expand Down Expand Up @@ -54,4 +56,10 @@ protected Animator getAnimator(@NonNull ViewGroup container, @Nullable View from
protected void resetFromView(@NonNull View from) {
from.setTranslationX(0);
}

@Override @NonNull
public ControllerChangeHandler copy() {
return new HorizontalChangeHandler(getAnimationDuration(), removesFromViewOnPush());
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -102,4 +102,10 @@ public void onViewAttachedToWindow(@NonNull View v) {

@Override
public void onViewDetachedFromWindow(@NonNull View v) { }

@Override @NonNull
public ControllerChangeHandler copy() {
return new SimpleSwapChangeHandler(removesFromViewOnPush());
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -81,4 +81,5 @@ public void onTransitionResume(Transition transition) { }
public final boolean removesFromViewOnPush() {
return true;
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -69,4 +69,13 @@ public boolean removesFromViewOnPush() {
return changeHandler.removesFromViewOnPush();
}

@Override @NonNull
public ControllerChangeHandler copy() {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
return new TransitionChangeHandlerCompat((TransitionChangeHandler)changeHandler.copy(), null);
} else {
return new TransitionChangeHandlerCompat(null, changeHandler.copy());
}
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@
import android.view.View;
import android.view.ViewGroup;

import com.bluelinelabs.conductor.ControllerChangeHandler;

import java.util.ArrayList;
import java.util.List;

Expand Down Expand Up @@ -49,4 +51,9 @@ protected Animator getAnimator(@NonNull ViewGroup container, @Nullable View from
@Override
protected void resetFromView(@NonNull View from) { }

@Override @NonNull
public ControllerChangeHandler copy() {
return new VerticalChangeHandler(getAnimationDuration(), removesFromViewOnPush());
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -14,4 +14,9 @@ public void performChange(@NonNull ViewGroup container, @Nullable View from, @Nu
changeListener.onChangeCompleted();
}

@NonNull
@Override
public ControllerChangeHandler copy() {
return new NoOpControllerChangeHandler();
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package com.bluelinelabs.conductor.demo.controllers;

import android.os.Bundle;
import android.support.annotation.NonNull;
import android.view.LayoutInflater;
import android.view.View;
Expand All @@ -8,6 +9,7 @@

import com.bluelinelabs.conductor.demo.R;
import com.bluelinelabs.conductor.demo.controllers.base.BaseController;
import com.bluelinelabs.conductor.demo.util.BundleBuilder;

import butterknife.BindView;

Expand All @@ -18,10 +20,14 @@ public class TextController extends BaseController {
@BindView(R.id.text_view) TextView textView;

public TextController(String text) {
// this(new BundleBuilder(new Bundle())
// .putString(KEY_TEXT, text)
// .build()
// );
this(new BundleBuilder(new Bundle())
.putString(KEY_TEXT, text)
.build()
);
}

public TextController(Bundle args) {
super(args);
}

@NonNull
Expand Down

0 comments on commit e7c195d

Please sign in to comment.