Skip to content

Commit

Permalink
Create ViewAction1 to weakly refer to views.
Browse files Browse the repository at this point in the history
  • Loading branch information
ronshapiro committed Oct 13, 2014
1 parent 12e8015 commit 602deb7
Show file tree
Hide file tree
Showing 8 changed files with 146 additions and 41 deletions.
53 changes: 53 additions & 0 deletions src/main/java/rx/functions/ViewAction1.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
/**
* Copyright 2014 Netflix, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package rx.android.functions;

import android.view.View;

import rx.functions.Action1;

import java.lang.ref.WeakReference;

/**
* An {@link Action1} implementation specific for {@link View}s.
*
* @param <V> the type of {@link View} upon which to perform the action.
* @param <T> the type being observed
*/
public abstract class ViewAction1<V extends View, T> implements Action1<T> {

private final WeakReference<V> viewReference;

public ViewAction1(V view) {
viewReference = new WeakReference<V>(view);
}

@Override
public final void call(T t) {
V view = viewReference.get();
if (view != null) {
call(view, t);
}
}

/**
* Implement this instead of {@link Action1#call(Object)}.
* @param view the view given in the constructor.
* @param t the object being observed
*/
public abstract void call(V view, T t);

}
10 changes: 3 additions & 7 deletions src/main/java/rx/functions/ViewActionSetActivated.java
Original file line number Diff line number Diff line change
Expand Up @@ -17,18 +17,14 @@

import android.view.View;

import rx.functions.Action1;

public class ViewActionSetActivated implements Action1<Boolean> {

private final View view;
public class ViewActionSetActivated extends ViewAction1<View, Boolean> {

public ViewActionSetActivated(View view) {
this.view = view;
super(view);
}

@Override
public void call(Boolean aBoolean) {
public void call(View view, Boolean aBoolean) {
view.setActivated(aBoolean);
}
}
Expand Down
10 changes: 3 additions & 7 deletions src/main/java/rx/functions/ViewActionSetClickable.java
Original file line number Diff line number Diff line change
Expand Up @@ -17,18 +17,14 @@

import android.view.View;

import rx.functions.Action1;

public class ViewActionSetClickable implements Action1<Boolean> {

private final View view;
public class ViewActionSetClickable extends ViewAction1<View, Boolean> {

public ViewActionSetClickable(View view) {
this.view = view;
super(view);
}

@Override
public void call(Boolean aBoolean) {
public void call(View view, Boolean aBoolean) {
view.setClickable(aBoolean);
}
}
Expand Down
10 changes: 3 additions & 7 deletions src/main/java/rx/functions/ViewActionSetEnabled.java
Original file line number Diff line number Diff line change
Expand Up @@ -17,18 +17,14 @@

import android.view.View;

import rx.functions.Action1;

public class ViewActionSetEnabled implements Action1<Boolean> {

private final View view;
public class ViewActionSetEnabled extends ViewAction1<View, Boolean> {

public ViewActionSetEnabled(View view) {
this.view = view;
super(view);
}

@Override
public void call(Boolean aBoolean) {
public void call(View view, Boolean aBoolean) {
view.setEnabled(aBoolean);
}
}
Expand Down
10 changes: 3 additions & 7 deletions src/main/java/rx/functions/ViewActionSetFocusable.java
Original file line number Diff line number Diff line change
Expand Up @@ -17,18 +17,14 @@

import android.view.View;

import rx.functions.Action1;

public class ViewActionSetFocusable implements Action1<Boolean> {

private final View view;
public class ViewActionSetFocusable extends ViewAction1<View, Boolean> {

public ViewActionSetFocusable(View view) {
this.view = view;
super(view);
}

@Override
public void call(Boolean aBoolean) {
public void call(View view, Boolean aBoolean) {
view.setFocusable(aBoolean);
}
}
Expand Down
10 changes: 3 additions & 7 deletions src/main/java/rx/functions/ViewActionSetSelected.java
Original file line number Diff line number Diff line change
Expand Up @@ -17,18 +17,14 @@

import android.view.View;

import rx.functions.Action1;

public class ViewActionSetSelected implements Action1<Boolean> {

private final View view;
public class ViewActionSetSelected extends ViewAction1<View, Boolean> {

public ViewActionSetSelected(View view) {
this.view = view;
super(view);
}

@Override
public void call(Boolean aBoolean) {
public void call(View view, Boolean aBoolean) {
view.setSelected(aBoolean);
}
}
Expand Down
9 changes: 3 additions & 6 deletions src/main/java/rx/functions/ViewActionSetVisibility.java
Original file line number Diff line number Diff line change
Expand Up @@ -17,30 +17,27 @@

import android.view.View;

import rx.functions.Action1;
public class ViewActionSetVisibility extends ViewAction1<View, Boolean> {

public class ViewActionSetVisibility implements Action1<Boolean> {

private final View view;
private final int visibilityOnFalse;

public ViewActionSetVisibility(View view) {
this(view, View.GONE);
}

public ViewActionSetVisibility(View view, int visibilityOnFalse) {
super(view);
if (visibilityOnFalse != View.GONE &&
visibilityOnFalse != View.INVISIBLE &&
visibilityOnFalse != View.VISIBLE) {
throw new IllegalArgumentException(visibilityOnFalse +
" is not a valid visibility value. See android.view.View VISIBLE, GONE, and INVISIBLE");
}
this.view = view;
this.visibilityOnFalse = visibilityOnFalse;
}

@Override
public void call(Boolean aBoolean) {
public void call(View view, Boolean aBoolean) {
int visibility = aBoolean ? View.VISIBLE : visibilityOnFalse;
view.setVisibility(visibility);
}
Expand Down
75 changes: 75 additions & 0 deletions src/test/java/rx/functions/ViewAction1Test.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
/**
* Copyright 2014 Netflix, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package rx.android.functions;

import android.view.View;

import org.junit.Test;
import org.junit.runner.RunWith;
import org.robolectric.Robolectric;
import org.robolectric.RobolectricTestRunner;

import rx.subjects.PublishSubject;

import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
import static rx.android.TestUtil.createView;

@RunWith(RobolectricTestRunner.class)
public class ViewAction1Test {

@Test
@SuppressWarnings("unchecked")
public void callIsNotExecutedWithAReleasedReference() {
final View view = null; // simulate a released WeakReference
final PublishSubject<Boolean> subject = PublishSubject.create();
final ViewAction1Impl action = new ViewAction1Impl(view);
subject.subscribe(action);

assertFalse(action.wasCalled);
subject.onNext(true);
assertFalse(action.wasCalled);
}

@Test
@SuppressWarnings("unchecked")
public void callIsExecutedWithARetainedReference() {
final View view = createView();
final PublishSubject<Boolean> subject = PublishSubject.create();
final ViewAction1Impl action = new ViewAction1Impl(view);
subject.subscribe(action);

assertFalse(action.wasCalled);
subject.onNext(true);
assertTrue(action.wasCalled);
}

private static class ViewAction1Impl extends ViewAction1<View, Boolean> {

boolean wasCalled = false;

ViewAction1Impl(View view) {
super(view);
}

@Override
public void call(View view, Boolean aBoolean) {
wasCalled = true;
}

}

}

0 comments on commit 602deb7

Please sign in to comment.