error: method setCurrentItemInternal in class - java

When I update my Code to androidx I get this error
"error: method setCurrentItemInternal in class ViewPager cannot be applied to given types;
required: int,boolean,boolean,int
found: int,boolean,boolean
reason: actual and formal argument lists differ in length"
Code:
public class NonRestoringViewPager extends ViewPager implements setCurrentItemInternal {
private boolean isRestoring = false;
private final boolean useDefaultImplementation;
public NonRestoringViewPager(Context context) {
super(context);
useDefaultImplementation =
!QuranUtils.isDualPagesInLandscape(context, QuranScreenInfo.getOrMakeInstance(context));
}
public NonRestoringViewPager(Context context, AttributeSet attrs) {
super(context, attrs);
useDefaultImplementation =
!QuranUtils.isDualPagesInLandscape(context, QuranScreenInfo.getOrMakeInstance(context));
}
#Override
public void setCurrentItemInternal(int item, boolean smoothScroll, boolean always) {
if (useDefaultImplementation || !isRestoring) {
super.setCurrentItemInternal(item, smoothScroll, always);
}
}
#Override
public void setCurrentItemInternal(int item, boolean smoothScroll, boolean always, int velocity) {
if (useDefaultImplementation || !isRestoring) {
super.setCurrentItemInternal(item, smoothScroll, always, velocity);
}
}
#Override
public void onRestoreInstanceState(Parcelable state) {
isRestoring = true;
super.onRestoreInstanceState(state);
isRestoring = false;
}
#Override
public boolean onTouchEvent(MotionEvent ev) {
try {
return super.onTouchEvent(ev);
} catch (IllegalArgumentException e) {
return false;
}
}
}

Function signature might have changed in androidx dependencies. So check the function signature and pass required params values.

Related

Inconsistency: Invalid view holder adapter when using FirestorePagingAdapter with custom wrapper

I wrote a wrapper around FirestorePagingAdapter. This works fine most of the times. But there are occasions where this crashes with
java.lang.IndexOutOfBoundsException: Inconsistency detected. Invalid view holder adapter
I will show you the complete wrapper. Also the last log message I see before the crash is
[Paging adapter] Data loading finished.
I also noticed, when I slowly scroll the list it works fine. Only if I scroll the list fast it crashes eventually.
So here is the code. I cannot figure out where the problem is. Any help is highly appreciated
public abstract class PagingAdapter<T extends RecyclerItem> extends FirestorePagingAdapter<T, RecyclerViewHolder<T, ? extends ViewBinding>> implements Function1<CombinedLoadStates, Unit> {
protected final String TAG = this.getClass().getSimpleName();
private final SnapshotParser<T> mParser;
private SortedList<T> mListItems;
private int mTryCount;
private boolean mReverseFill = false;
private PagingAdapter(#NonNull FirestorePagingOptions<T> options, PagingAdapterCallback<T> callback) {
super(options);
mListItems = new SortedList(RecyclerItem.class, new SortedListAdapterCallback<T>(this) {
#Override
public int compare(T o1, T o2) {
return callback.compare(o1, o2);
}
#Override
public boolean areContentsTheSame(T oldItem, T newItem) {
return callback.areContentsTheSame(oldItem, newItem);
}
#Override
public boolean areItemsTheSame(T item1, T item2) {
return callback.areContentsTheSame(item1, item2);
}
});
mParser = options.getParser();
this.mTryCount = 0;
}
public void setReverseFill(boolean reverseFill) {
this.mReverseFill = reverseFill;
}
#Override
public int getItemViewType(int position) {
return getList().get(position).getRecyclerItemType().getId();
}
public SortedList<T> getList() {
return mListItems;
}
#NonNull
#Override
public RecyclerViewHolder<T, ? extends ViewBinding> onCreateViewHolder(#NonNull ViewGroup parent, int viewType) {
RecyclerViewHolder<T, ? extends ViewBinding> viewHolder = onCreateViewHolder(parent, RecyclerItemType
.get(viewType));
if (viewHolder == null) {
throw new NullPointerException("Your list contains items for that you did not specify a view holder for");
}
return viewHolder;
}
public abstract RecyclerViewHolder<T, ? extends ViewBinding> onCreateViewHolder(#NonNull ViewGroup parent, RecyclerItemType itemType);
#Override
public void onBindViewHolder(RecyclerViewHolder<T, ? extends ViewBinding> holder, int position) {
try {
//and trigger the paging to load around with the correct "position"
super.onBindViewHolder(holder, getPagingPosition(position)); //<--Needed to page the list, be we do not really use it (see below)
} catch (Exception ignore) {
//If this fails, because there are less items in the list, do not crash, this is fine
Log.d(TAG, "onBindViewHolder: ");
}
holder.bind(getList().get(position));
}
protected int getPagingPosition(int requestedPosition) {
return requestedPosition;
}
#Override
protected void onBindViewHolder(#NonNull RecyclerViewHolder<T, ? extends ViewBinding> holder, int position, #NonNull T model) {
//We do not use this method
}
#Override
public int getItemCount() {
return getList().size();
}
#Override
public Unit invoke(CombinedLoadStates states) {
LoadState refresh = states.getRefresh();
LoadState append = states.getAppend();
if (refresh instanceof LoadState.Error || append instanceof LoadState.Error) {
//The previous load (either initial or additional) failed
Log.d(TAG, "[Paging adapter] An error occurred while loading the data");
if (mTryCount < 3) {
mTryCount += 1;
retry();
}
}
if (refresh instanceof LoadState.Loading) {
Log.d(TAG, "[Paging adapter] Loading initial data");
}
if (append instanceof LoadState.Loading) {
Log.d(TAG, "[Paging adapter] Loading more data");
}
if (append instanceof LoadState.NotLoading) {
LoadState.NotLoading notLoading = (LoadState.NotLoading) append;
if (notLoading.getEndOfPaginationReached()) {
Log.d(TAG, "[Paging adapter] No further documents");
mTryCount = 0;
return null;
}
if (refresh instanceof LoadState.NotLoading) {
Log.d(TAG, "[Paging adapter] Data loading finished");
mTryCount = 0;
List<T> items = new ArrayList<>();
if (mReverseFill) {
for (int i = snapshot().size() - 1; i >= 0; i--) {
T currentItem = mParser.parseSnapshot(snapshot().get(i));
if (getList().indexOf(currentItem) == SortedList.INVALID_POSITION)
items.add(currentItem);
}
} else {
for (DocumentSnapshot snapshot : snapshot()) {
T currentItem = mParser.parseSnapshot(snapshot);
if (getList().indexOf(currentItem) == SortedList.INVALID_POSITION)
items.add(currentItem);
}
}
addAll(items);
return null;
}
}
return null;
}
public void addAll(Collection<T> items) {
getList().beginBatchedUpdates();
getList().addAll(items);
getList().endBatchedUpdates();
}
public abstract static class PagingAdapterCallback<T extends RecyclerItem> {
public abstract int compare(T o1, T o2);
public abstract boolean areContentsTheSame(T oldItem, T newItem);
public abstract boolean areItemsTheSame(T item1, T item2);
}
}
Just in case you wonder. These are the other two wrapper:
public abstract class RecyclerViewHolder<T extends RecyclerItem, E extends ViewBinding> extends RecyclerView.ViewHolder {
public final String TAG = this.getClass().getSimpleName();
protected final E b;
private final Context mContext;
protected RecyclerViewHolder(#NonNull E b) {
super(b.getRoot());
this.b = b;
this.mContext = b.getRoot().getContext();
}
public abstract void bind(T item);
protected Context getContext() {
return mContext;
}
protected Context requireContext() {
return getContext();
}
protected String getString(int resId) {
return mContext.getString(resId);
}
protected String getString(int resId, Object... args) {
return mContext.getString(resId, args);
}
}
and
public interface RecyclerItem {
#NonNull
RecyclerItemType getRecyclerItemType();
default void setRecyclerItemType(RecyclerItemType type){
//Does not do anything per default
}
}

How to solve this multi selection issues in android?

This is my Multi selection code.
public class CheckableLayout1 extends ImageView implements Checkable {
private boolean mChecked;
public CheckableLayout1(Context context) {
super(context);
}
#SuppressWarnings("deprecation")
public void setChecked(boolean checked) {
mChecked = checked;
setForeground(checked ? getResources().getDrawable(R.drawable.ic_select) : null);
refreshDrawableState();
}
#Override
public int[] onCreateDrawableState(final int extraSpace) {
final int[] drawableState = super.onCreateDrawableState(extraSpace + 1);
if (isChecked())
mergeDrawableStates(drawableState, CHECKED_STATE_SET);
return drawableState;
}
public boolean isChecked() {
return mChecked;
}
public void toggle() {
setChecked(!mChecked);
}
}
It works in android nougat but not in any lower version of android. What is wrong with it?

Java 8: Observable List - Invalidation Listener nor Change Listener is called in case of property change

I build a custom property and add it to a observable list. But no listener is called if property content is changed. The following code snippets shows you the 'building':
public static final class TestObject {
private final ReadOnlyStringWrapper title = new ReadOnlyStringWrapper();
private final BooleanProperty selected = new SimpleBooleanProperty(false);
public TestObject(String title) {
this.title.set(title);
}
public String getTitle() {
return title.get();
}
public ReadOnlyStringProperty titleProperty() {
return title.getReadOnlyProperty();
}
public boolean getSelected() {
return selected.get();
}
public BooleanProperty selectedProperty() {
return selected;
}
public void setSelected(boolean selected) {
this.selected.set(selected);
}
#Override
public int hashCode() {
return Objects.hash(title.get());
}
#Override
public boolean equals(Object obj) {
if (this == obj) {
return true;
}
if (obj == null || getClass() != obj.getClass()) {
return false;
}
final TestObject other = (TestObject) obj;
return Objects.equals(this.title.get(), other.title.get());
}
#Override
public String toString() {
return "TestObject{" +
"title=" + title.get() +
", selected=" + selected.get() +
'}';
}
}
This is my POJO class with my internal property values like name and selected.
public static final class TestProperty extends SimpleObjectProperty<TestObject> {
public TestProperty(String name) {
super(new TestObject(name));
init();
}
public TestProperty(TestObject testObject) {
super(testObject);
init();
}
public String getTitle() {
return getValue().getTitle();
}
public void setSelected(boolean selected) {
getValue().setSelected(selected);
}
public boolean getSelected() {
return getValue().getSelected();
}
public BooleanProperty selectedProperty() {
return getValue().selectedProperty();
}
public ReadOnlyStringProperty titleProperty() {
return getValue().titleProperty();
}
#Override
public void set(TestObject testObject) {
super.set(testObject);
init();
}
#Override
public void setValue(TestObject testObject) {
super.setValue(testObject);
init();
}
private void init() {
if (get() == null)
return;
get().titleProperty().addListener((v, o, n) -> fireValueChangedEvent());
get().selectedProperty().addListener((v, o, n) -> {
fireValueChangedEvent();
});
}
}
This is my custom property based on the POJO. All property changes will fire a change event for my custom property.
#Test
public void testSimple() {
final AtomicInteger counter = new AtomicInteger(0);
final TestProperty testProperty = new TestProperty("Test");
testProperty.addListener(observable -> {
System.out.println("New state: " + testProperty.get().toString());
counter.incrementAndGet();
});
testProperty.setSelected(true);
testProperty.setSelected(false);
Assert.assertEquals(2, counter.intValue());
}
In this test you can see that the property change event works fine.
#Test
public void testList() {
final AtomicInteger counter = new AtomicInteger(0);
final ObservableList<TestProperty> observableList = new ObservableListWrapper<>(new ArrayList<>());
observableList.add(new TestProperty("Test 1"));
observableList.add(new TestProperty("Test 2"));
observableList.add(new TestProperty("Test 3"));
observableList.addListener(new ListChangeListener<TestProperty>() {
#Override
public void onChanged(Change<? extends TestProperty> change) {
System.out.println("**************");
}
});
observableList.addListener((Observable observable) -> {
System.out.println("New state: " + ((TestProperty) observable).get().toString());
counter.incrementAndGet();
});
observableList.get(1).setSelected(true);
observableList.get(2).setSelected(true);
observableList.get(1).setSelected(false);
observableList.get(2).setSelected(false);
Assert.assertEquals(4, counter.intValue());
}
But in this code you see that the observable list not called the invalidation listener nor the change listener if a property value has changed in list.
What is wrong?
Thanks.
To create an observable list that will send "list updated" notifications if properties of elements of the list change, you need to create the list with an extractor. The extractor is a Callback that maps each element of the list to an array of Observables. If any of the Observables changes, InvalidationListeners and ListChangeListeners registered with the list will be notified.
So in your testList() method, you can do
final ObservableList<TestProperty> observableList = FXCollections.observableList(
new ArrayList<>(),
(TestProperty tp) -> new Observable[]{tp.selectedProperty()});
If the title were able to change, and you also wanted the list to receive notifications when that happened, you could do that too:
final ObservableList<TestProperty> observableList = FXCollections.observableList(
new ArrayList<>(),
(TestProperty tp) -> new Observable[]{tp.selectedProperty(), tp.titleProperty()});
Note that because the extractor is a Callback (essentially a function), the implementation can be arbitrarily complex (observe one property conditionally based on the value of another, etc).
The following code shows a simple implementation for a observable list with observable values:
public class ObservableValueListWrapper<E extends ObservableValue<E>> extends ObservableListWrapper<E> {
public ObservableValueListWrapper(List<E> list) {
super(list, o -> new Observable[] {o});}}
Or you must create your list with a POJO:
final ObservableList<MyPOJO> list = new ObservableListWrapper<>(new ArrayList(), o -> new Observable[] { new MyPOJOProperty(o) });
Or you use it so:
final ObservableList<MyPOJO> list = new ObservableListWrapper<>(new ArrayList(), o -> { return new Observable[] {
o.value1Property(),
o.value2Property(),
...};});
That is it! Thanks.
The ObservableList isn't notifying the listeners whenever a property contained within the list is modified, it notifies when the list is notified.
This can be seen when you modify your test:
#Test
public void testList() {
final AtomicInteger counter = new AtomicInteger(0);
final ObservableList<TestProperty> observableList = new ObservableListWrapper<>(new ArrayList<>());
observableList.addListener(new ListChangeListener<TestProperty>() {
#Override
public void onChanged(Change<? extends TestProperty> change) {
System.out.println("**************");
counter.incrementAndGet();
}
});
observableList.add(new TestProperty("Test 1"));
observableList.add(new TestProperty("Test 2"));
observableList.add(new TestProperty("Test 3"));
observableList.get(1).setSelected(true);
observableList.get(2).setSelected(true);
observableList.get(1).setSelected(false);
observableList.get(2).setSelected(false);
Assert.assertEquals(3, counter.intValue());
}
EDIT: Added an example ObserverListener decorator which provides the auto registration/deregistration of the ObservableValue change listener as desired by the OP.
/**
* Decorates an {#link ObservableList} and auto-registers the provided
* listener to all new observers, and auto-unregisters listeners when the
* item is removed from the list.
*
* #param <T>
*/
public class ObservableValueList<T extends ObservableValue> implements ObservableList<T> {
private final ObservableList<T> list;
private final ChangeListener<T> valueListener;
public ObservableValueList(ObservableList<T> list, ChangeListener<T> valueListener) {
this.list = list;
//list to existing contents of list
this.list.stream().forEach((item) -> item.addListener(valueListener));
//register listener which will add/remove listner on change to list
this.list.addListener((Change<? extends T> change) -> {
change.getAddedSubList().stream().forEach(
(item) -> item.addListener(valueListener));
change.getRemoved().stream().forEach(
(item) -> item.removeListener(valueListener));
});
this.valueListener = valueListener;
}
/* What follows is all the required delegate methods */
#Override
public int size() {
return list.size();
}
#Override
public boolean isEmpty() {
return list.isEmpty();
}
#Override
public boolean contains(Object o) {
return list.contains(o);
}
#Override
public Iterator<T> iterator() {
return list.iterator();
}
#Override
public Object[] toArray() {
return list.toArray();
}
#Override
public <T> T[] toArray(T[] ts) {
return list.toArray(ts);
}
#Override
public boolean add(T e) {
return list.add(e);
}
#Override
public boolean remove(Object o) {
return list.remove(o);
}
#Override
public boolean containsAll(Collection<?> clctn) {
return list.containsAll(clctn);
}
#Override
public boolean addAll(Collection<? extends T> clctn) {
return list.addAll(clctn);
}
#Override
public boolean addAll(int i, Collection<? extends T> clctn) {
return list.addAll(i, clctn);
}
#Override
public boolean removeAll(Collection<?> clctn) {
return list.removeAll(clctn);
}
#Override
public boolean retainAll(Collection<?> clctn) {
return list.retainAll(clctn);
}
#Override
public void replaceAll(UnaryOperator<T> uo) {
list.replaceAll(uo);
}
#Override
public void sort(Comparator<? super T> cmprtr) {
list.sort(cmprtr);
}
#Override
public void clear() {
list.clear();
}
#Override
public T get(int i) {
return list.get(i);
}
#Override
public T set(int i, T e) {
return list.set(i, e);
}
#Override
public void add(int i, T e) {
list.add(i, e);
}
#Override
public T remove(int i) {
return list.remove(i);
}
#Override
public int indexOf(Object o) {
return list.indexOf(o);
}
#Override
public int lastIndexOf(Object o) {
return list.lastIndexOf(o);
}
#Override
public ListIterator<T> listIterator() {
return list.listIterator();
}
#Override
public ListIterator<T> listIterator(int i) {
return list.listIterator(i);
}
#Override
public List<T> subList(int i, int i1) {
return list.subList(i, i1);
}
#Override
public Spliterator<T> spliterator() {
return list.spliterator();
}
#Override
public void addListener(ListChangeListener<? super T> ll) {
list.addListener(ll);
}
#Override
public void removeListener(ListChangeListener<? super T> ll) {
list.removeListener(ll);
}
#Override
public boolean addAll(T... es) {
return list.addAll(es);
}
#Override
public boolean setAll(T... es) {
return list.setAll(es);
}
#Override
public boolean setAll(Collection<? extends T> clctn) {
return list.setAll(clctn);
}
#Override
public boolean removeAll(T... es) {
return list.removeAll(es);
}
#Override
public boolean retainAll(T... es) {
return list.retainAll(es);
}
#Override
public void remove(int i, int i1) {
list.remove(i, i1);
}
#Override
public FilteredList<T> filtered(Predicate<T> prdct) {
return list.filtered(prdct);
}
#Override
public SortedList<T> sorted(Comparator<T> cmprtr) {
return list.sorted(cmprtr);
}
#Override
public SortedList<T> sorted() {
return list.sorted();
}
#Override
public void addListener(InvalidationListener il) {
list.addListener(il);
}
#Override
public void removeListener(InvalidationListener il) {
list.removeListener(il);
}
}

Limit the touch event of the SlidingPaneLayout to the very left edge of the screen

Is it possibble to Limit the touch event of the SlidingPaneLayout to the very left edge of the screen link happens in the DrawerLayout?
Yes, but you want to create your own implementation of SlidingPaneLayout and override onTouchEvent(MotionEvent ev) method, like this
public class SlidingPaneLayoutExtended extends SlidingPaneLayout {
public static final int DEFAULT_DRAGGING_START_X = -1;
public static final int SLIDE_FROM_LEFT_EDGE = 0;
private int startDraggingX = DEFAULT_DRAGGING_START_X;
public SlidingPaneLayoutExtended(Context context, AttributeSet attrs) {
super(context, attrs);
}
public int getStartDraggingX() {
return startDraggingX;
}
public void setStartDraggingX(int startX) {
this.startDraggingX = startX;
}
#Override
public boolean onTouchEvent(MotionEvent ev) {
if (startDraggingX > DEFAULT_DRAGGING_START_X) {
if ((startDraggingX == SLIDE_FROM_LEFT_EDGE && ev.getAction() == )
|| ev.getX() <= DEFAULT_DRAGGING_START_X) {
return super.onTouchEvent(ev);
} else {
return false;
}
}
return super.onTouchEvent(ev);
}
}

Android: boolean not working correclty - Strange

I was building a surfaceView class to display an image from the camera. It took me a while to get it working but I added some toasts, dialogs and some boolean variables to debug it in the AnnotateSurface class and the Activity class. I was using one of these in an if statement to run the thread to draw the image to the surface if it was true (this was what was stopping it from working).
if(bitmapState){
drawSomething(canvas);
}
I have got it working but only after I figured out that the boolean value, bitmapState , was being reset to false. it is initalised to false but I change it to true after in the getBitmap method. This is the only method that edits that boolean variable.
The toast in the setBitmap method displays "true", but when I call the getStuff method from the activity class it displays it as false and the if statement in the run method will also not work when I use the following:
if (surfaceState == bitmapState == true) {
drawSomething(canvas);
}
This is really confusing as all other boolean values are behaving correctly. If anyone has any insight I would love to hear it.
public class AnnotateSurface extends SurfaceView implements Callback, Runnable {
// create a holder to manage the surface of the view
SurfaceHolder ourHolder;
// Create a thread
Thread ourThread = null;
// Create a boolean to determine when to stop the animation
boolean isRunning = false;
boolean surfaceState = false;
boolean bitmapState = false;
public static Bitmap bmpIm = null;
Context c;
Canvas canvas;
int ws, hs;
public AnnotateSurface(Context context) {...
}
public AnnotateSurface(Context context, AttributeSet attrs) {...
}
public AnnotateSurface(Context context, AttributeSet attrs, int defStyle) {...
}
// create a method to pause the thread
public void pause() {...
}
public void resume() {...
}
// create a method to resume the thread
public void setBitmap(Bitmap b) {
bmpIm = b;
// bmpIm = AnnotateImage.bmpAnnotate;
// isRunning = true;
bitmapState = true;
Toast toast = new Toast(c);
Toast.makeText(c, Boolean.toString(bitmapState), Toast.LENGTH_LONG)
.show();
}
#Override
public void surfaceChanged(SurfaceHolder holder, int format, int width,
int height) {...
}
#Override
public void surfaceCreated(SurfaceHolder holder) {...
}
#Override
public void surfaceDestroyed(SurfaceHolder holder) {
// TODO Auto-generated method stub
surfaceState = false;
}
// #Override
public void drawSomething(Canvas canvas) {...
}
public String getstuff() {
String Data = "not drawing" + Boolean.toString(this.bitmapState)
+ Boolean.toString(surfaceState) + Boolean.toString(isRunning)
+ Integer.toString(ws) + Integer.toString(hs);
return Data;
}
public Bitmap getstuffImage() {...
}
#Override
public void run() {...
}
}
I have had problems with booleans and "if" statements in the past, the best way to deal with it is to be more explicit with them, for example:
if (surfaceState == bitmapState && bitmapState == true) {
drawSomething(canvas);
}
Cheers!
Mike

Categories

Resources