public
interface
Settings {
int
getLastPosition();
void
setLastPosition(
int
value);
}
public
class
AppSettings
implements
Settings {
private
static
final
String KEY_LAST_POSITION =
"lastPosition"
;
private
final
Storage storage;
public
AppSettings(Storage storage) {
this
.storage = storage;
}
@Override
public
int
getLastPosition() {
return
storage.geInt(KEY_LAST_POSITION,
0
);
}
@Override
public
void
setLastPosition(
int
value) {
storage.putInt(KEY_LAST_POSITION, value);
}
}
public
interface
Storage {
int
geInt(String key,
int
defaultValue);
void
putInt(String key,
int
value);
}
public
class
PrefsStorage
implements
Storage {
private
final
SharedPreferences prefs;
public
PrefsStorage(SharedPreferences prefs) {
this
.prefs = prefs;
}
@Override
public
int
geInt(String key,
int
defaultValue) {
return
prefs.getInt(key, defaultValue);
}
@Override
public
void
putInt(String key,
int
value) {
prefs.edit()
.putInt(key, value)
.apply();
}
}
public
class
CircularIterator<T> {
private
int
currentPosition =
0
;
private
final
List<T> items;
public
CircularIterator(List<T> items) {
this
.items = items;
}
private
int
lastIndex() {
return
items.size() -
1
;
}
public
T currentItem() {
return
items.get(currentPosition);
}
public
boolean
hasNext() {
return
currentPosition < lastIndex();
}
public
T next() {
if
(hasNext()) {
currentPosition++;
return
currentItem();
}
currentPosition =
0
;
return
currentItem();
}
public
boolean
hasPrevious() {
return
currentPosition >
0
;
}
public
T previous() {
if
(hasPrevious()) {
currentPosition--;
return
currentItem();
}
currentPosition = lastIndex();
return
currentItem();
}
public
int
getCurrentPosition() {
return
currentPosition;
}
public
void
setCurrentPosition(
int
position) {
boolean
outOfBound = position <
0
|| position > lastIndex();
if
(outOfBound) {
throw
new
IllegalArgumentException(
"Invalid position "
+ position);
}
currentPosition = position;
}
}
public
class
TextManager {
private
final
CircularIterator<String> textIt;
private
final
Settings settings;
private
final
TextManagerListener listener;
public
TextManager(CircularIterator<String> textIt, Settings settings, TextManagerListener listener) {
this
.textIt = textIt;
this
.settings = settings;
this
.listener = listener;
restoreStatus();
}
public
void
restoreStatus() {
int
savedPosition = settings.getLastPosition();
textIt.setCurrentPosition(savedPosition);
listener.onPositionRestored(textIt.currentItem(), savedPosition);
}
public
void
saveStatus() {
int
lastPosition = textIt.getCurrentPosition();
settings.setLastPosition(lastPosition);
listener.onPositionSaved(lastPosition);
}
public
String currentItem() {
return
textIt.currentItem();
}
public
String next() {
return
textIt.next();
}
public
String previous() {
return
textIt.previous();
}
}
public
interface
TextManagerListener {
void
onPositionRestored(String text,
int
position);
void
onPositionSaved(
int
position);
}
public
class
MainActivity
extends
AppCompatActivity {
private
static
final
String PREFS_NAME =
"my_prefs"
;
@Override
protected
void
onCreate(Bundle savedInstanceState) {
super
.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
setupView();
setupDependencies();
}
private
TextView numberTxt;
private
void
setupView() {
numberTxt = findViewById(R.id.numberTxt);
findViewById(R.id.leftBtn).setOnClickListener(v -> {
updateText(textManager.previous());
});
findViewById(R.id.rightBtn).setOnClickListener(v -> {
updateText(textManager.next());
});
}
private
TextManager textManager;
private
void
setupDependencies() {
final
CircularIterator<String> textIterator =
new
CircularIterator<>(
Arrays.asList(getResources().getStringArray(R.array.numbers))
);
final
PrefsStorage storage =
new
PrefsStorage(getSharedPreferences(PREFS_NAME, Context.MODE_PRIVATE));
final
AppSettings settings =
new
AppSettings(storage);
textManager =
new
TextManager(textIterator, settings,
new
TextManagerListener() {
@Override
public
void
onPositionRestored(String text,
int
position) {
try
{
numberTxt.setText(text);
}
catch
(IllegalArgumentException e) {
}
}
@Override
public
void
onPositionSaved(
int
position) {
}
});
}
private
void
updateText(String next) {
numberTxt.setText(next);
}
@Override
protected
void
onStop() {
super
.onStop();
textManager.saveStatus();
}
}