Skip to content

Commit 459a27c

Browse files
committed
MVP plus Clean
0 parents  commit 459a27c

34 files changed

+1114
-0
lines changed

.gitignore

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
.gradle
2+
/local.properties
3+
/.idea/
4+
*.iml
5+
.DS_Store
6+
/build

app/.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
/build

app/build.gradle

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
apply plugin: 'com.android.application'
2+
3+
android {
4+
compileSdkVersion 21
5+
buildToolsVersion "21.1.2"
6+
7+
defaultConfig {
8+
applicationId "mvp.sample.io.mercury.mvpexample"
9+
minSdkVersion 14
10+
targetSdkVersion 21
11+
versionCode 1
12+
versionName "1.0"
13+
}
14+
buildTypes {
15+
release {
16+
minifyEnabled false
17+
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
18+
}
19+
}
20+
}
21+
22+
dependencies {
23+
compile fileTree(dir: 'libs', include: ['*.jar'])
24+
compile 'com.android.support:appcompat-v7:21.0.3'
25+
}

app/proguard-rules.pro

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
# Add project specific ProGuard rules here.
2+
# By default, the flags in this file are appended to flags specified
3+
# in /android-sdk-macosx/tools/proguard/proguard-android.txt
4+
# You can edit the include path and order by changing the proguardFiles
5+
# directive in build.gradle.
6+
#
7+
# For more details, see
8+
# http://developer.android.com/guide/developing/tools/proguard.html
9+
10+
# Add any project specific keep options here:
11+
12+
# If your project uses WebView with JS, uncomment the following
13+
# and specify the fully qualified class name to the JavaScript interface
14+
# class:
15+
#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
16+
# public *;
17+
#}
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
package mvp.sample.io.mercury.mvpexample;
2+
3+
import android.app.Application;
4+
import android.test.ApplicationTestCase;
5+
6+
/**
7+
* <a href="http://d.android.com/tools/testing/testing_android.html">Testing Fundamentals</a>
8+
*/
9+
public class ApplicationTest extends ApplicationTestCase<Application> {
10+
public ApplicationTest() {
11+
super(Application.class);
12+
}
13+
}

app/src/main/AndroidManifest.xml

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
<?xml version="1.0" encoding="utf-8"?>
2+
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
3+
package="mvp.sample.io.mercury.mvpexample" >
4+
5+
<application
6+
android:allowBackup="true"
7+
android:icon="@drawable/ic_launcher"
8+
android:label="@string/app_name"
9+
android:theme="@style/AppTheme" >
10+
<activity
11+
android:name=".FavoriteCrudActivity"
12+
android:label="@string/title_activity_main" >
13+
<intent-filter>
14+
<action android:name="android.intent.action.MAIN" />
15+
<category android:name="android.intent.category.LAUNCHER" />
16+
</intent-filter>
17+
</activity>
18+
</application>
19+
20+
</manifest>
Lines changed: 169 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,169 @@
1+
package mvp.sample.io.mercury.mvpexample;
2+
3+
import android.annotation.SuppressLint;
4+
import android.os.Bundle;
5+
import android.support.v4.app.Fragment;
6+
import android.support.v4.app.FragmentManager;
7+
import android.support.v7.app.ActionBarActivity;
8+
import android.view.LayoutInflater;
9+
import android.view.View;
10+
import android.view.ViewGroup;
11+
import android.widget.ArrayAdapter;
12+
import android.widget.ListView;
13+
import android.widget.Toast;
14+
15+
import java.util.Collection;
16+
17+
import mvp.sample.io.mercury.mvpexample.di.Container;
18+
import mvp.sample.io.mercury.mvpexample.entity.Favorite;
19+
import mvp.sample.io.mercury.mvpexample.interactor.FavoriteAdder;
20+
import mvp.sample.io.mercury.mvpexample.interactor.FavoriteRemover;
21+
import mvp.sample.io.mercury.mvpexample.interactor.FavoritesGetter;
22+
import mvp.sample.io.mercury.mvpexample.view.FavoriteCrudItem;
23+
import mvp.sample.io.mercury.mvpexample.view.FavoriteCrudPresenter;
24+
25+
26+
public class FavoriteCrudActivity extends ActionBarActivity implements FavoriteCrudPresenter.FavoriteCrudView {
27+
28+
private static final String FRAG_TAG_PRESENTER_HOLDER = "presenterHolder";
29+
30+
private FavoriteAdder favoriteAdder = Container.getInstance().getFavoriteAdder();
31+
private FavoritesGetter favoritesGetter = Container.getInstance().getFavoritesGetter();
32+
private FavoriteRemover favoritesRemover = Container.getInstance().getFavoritesRemover();
33+
34+
private ArrayAdapter<Favorite> listAdapter;
35+
private View add1Btn;
36+
private View add2Btn;
37+
private View add3Btn;
38+
private View loading;
39+
private ListView list;
40+
41+
@Override
42+
protected void onCreate(Bundle savedInstanceState) {
43+
super.onCreate(savedInstanceState);
44+
setContentView(R.layout.activity_main);
45+
46+
FragmentManager fm = getSupportFragmentManager();
47+
PresenterHolderFragment phf = (PresenterHolderFragment) fm.findFragmentByTag(FRAG_TAG_PRESENTER_HOLDER);
48+
49+
final FavoriteCrudPresenter presenter;
50+
if (phf == null) {
51+
presenter = new FavoriteCrudPresenter(favoriteAdder, favoritesGetter, favoritesRemover);
52+
fm.beginTransaction().add(new PresenterHolderFragment(presenter), FRAG_TAG_PRESENTER_HOLDER).commit();
53+
} else {
54+
presenter = phf.presenter;
55+
}
56+
presenter.setView(this);
57+
58+
59+
final FavoriteCrudItem.OnRemoveClickListener removeClickListener = new FavoriteCrudItem.OnRemoveClickListener() {
60+
@Override
61+
public void onRemoveClicked(Favorite favorite) {
62+
presenter.removeFavorite(favorite);
63+
}
64+
};
65+
66+
list = (ListView) findViewById(R.id.list);
67+
listAdapter = new ArrayAdapter<Favorite>(this, -1) {
68+
@Override
69+
public View getView(int position, View convertView, ViewGroup parent) {
70+
FavoriteCrudItem view = (FavoriteCrudItem) convertView;
71+
if (view == null) {
72+
view = (FavoriteCrudItem) LayoutInflater.from(getContext()).inflate(R.layout.favorite_item, parent, false);
73+
}
74+
75+
view.bind(getItem(position));
76+
view.setOnRemoveClickListener(removeClickListener);
77+
78+
return view;
79+
}
80+
};
81+
82+
list.setAdapter(listAdapter);
83+
84+
add1Btn = findViewById(R.id.add_1_btn);
85+
add1Btn.setOnClickListener(new View.OnClickListener() {
86+
@Override
87+
public void onClick(View v) {
88+
presenter.addFavorite(new Favorite(1));
89+
}
90+
});
91+
92+
add2Btn = findViewById(R.id.add_2_btn);
93+
add2Btn.setOnClickListener(new View.OnClickListener() {
94+
@Override
95+
public void onClick(View v) {
96+
presenter.addFavorite(new Favorite(2));
97+
}
98+
});
99+
100+
add3Btn = findViewById(R.id.add_3_btn);
101+
add3Btn.setOnClickListener(new View.OnClickListener() {
102+
@Override
103+
public void onClick(View v) {
104+
presenter.addFavorite(new Favorite(3));
105+
}
106+
});
107+
108+
loading = findViewById(R.id.loading);
109+
110+
presenter.present();
111+
}
112+
113+
@Override
114+
public void loadFavorites(Collection<Favorite> favorites) {
115+
listAdapter.clear();
116+
listAdapter.addAll(favorites);
117+
}
118+
119+
@Override
120+
public void notifyAddSuccessful(Favorite favorite) {
121+
Toast.makeText(this, String.format("%s was added", favorite.getId()), Toast.LENGTH_SHORT).show();
122+
}
123+
124+
@Override
125+
public void notifyRemoveSuccessful(Favorite favorite) {
126+
Toast.makeText(this, String.format("%s was removed", favorite.getId()), Toast.LENGTH_SHORT).show();
127+
}
128+
129+
@Override
130+
public void notifyFavoriteAlreadyExists(Favorite favorite) {
131+
Toast.makeText(this, String.format("%s was already added", favorite.getId()), Toast.LENGTH_SHORT).show();
132+
}
133+
134+
@Override
135+
public void disableAddControls() {
136+
add1Btn.setEnabled(false);
137+
add2Btn.setEnabled(false);
138+
add3Btn.setEnabled(false);
139+
}
140+
141+
@Override
142+
public void enableAddControls() {
143+
add1Btn.setEnabled(true);
144+
add2Btn.setEnabled(true);
145+
add3Btn.setEnabled(true);
146+
}
147+
148+
@Override
149+
public void showLoading() {
150+
list.setVisibility(View.GONE);
151+
loading.setVisibility(View.VISIBLE);
152+
}
153+
154+
@Override
155+
public void hideLoading() {
156+
loading.setVisibility(View.GONE);
157+
list.setVisibility(View.VISIBLE);
158+
}
159+
160+
@SuppressLint("ValidFragment")
161+
private class PresenterHolderFragment extends Fragment {
162+
final FavoriteCrudPresenter presenter;
163+
164+
public PresenterHolderFragment(FavoriteCrudPresenter presenter) {
165+
this.presenter = presenter;
166+
setRetainInstance(true);
167+
}
168+
}
169+
}
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
package mvp.sample.io.mercury.mvpexample.di;
2+
3+
import mvp.sample.io.mercury.mvpexample.interactor.FavoriteAdder;
4+
import mvp.sample.io.mercury.mvpexample.interactor.FavoriteRemover;
5+
import mvp.sample.io.mercury.mvpexample.interactor.FavoritesGetter;
6+
import mvp.sample.io.mercury.mvpexample.repository.FavoriteRepo;
7+
import mvp.sample.io.mercury.mvpexample.repository.InMemoryFavoriteRepo;
8+
import mvp.sample.io.mercury.mvpexample.repository.SlowFavoriteRepoWrapper;
9+
10+
public class Container {
11+
12+
private static Container instance;
13+
private FavoriteAdder favoriteAdder;
14+
private FavoriteRepo favoriteRepo;
15+
private FavoritesGetter favoritesGetter;
16+
private FavoriteRemover favoritesRemover;
17+
18+
private Container() {}
19+
20+
public static Container getInstance() {
21+
if (instance == null) {
22+
instance = new Container();
23+
}
24+
return instance;
25+
}
26+
27+
public FavoriteAdder getFavoriteAdder() {
28+
if (favoriteAdder == null) {
29+
favoriteAdder = new FavoriteAdder(getFavoriteRepo());
30+
}
31+
return favoriteAdder;
32+
}
33+
34+
public FavoritesGetter getFavoritesGetter() {
35+
if (favoritesGetter == null) {
36+
favoritesGetter = new FavoritesGetter(getFavoriteRepo());
37+
}
38+
return favoritesGetter;
39+
}
40+
41+
public FavoriteRemover getFavoritesRemover() {
42+
if (favoritesRemover == null) {
43+
favoritesRemover = new FavoriteRemover(getFavoriteRepo());
44+
}
45+
return favoritesRemover;
46+
}
47+
48+
public FavoriteRepo getFavoriteRepo() {
49+
if (favoriteRepo == null) {
50+
favoriteRepo = new SlowFavoriteRepoWrapper(new InMemoryFavoriteRepo(), 1000);
51+
}
52+
return favoriteRepo;
53+
}
54+
}
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
package mvp.sample.io.mercury.mvpexample.entity;
2+
3+
public class Favorite {
4+
private final int id;
5+
6+
public Favorite(int i) {
7+
id = i;
8+
}
9+
10+
public int getId() {
11+
return id;
12+
}
13+
14+
@Override
15+
public boolean equals(Object o) {
16+
if (this == o) return true;
17+
if (o == null || getClass() != o.getClass()) return false;
18+
19+
Favorite favorite = (Favorite) o;
20+
21+
return id == favorite.id;
22+
23+
}
24+
25+
@Override
26+
public int hashCode() {
27+
return id;
28+
}
29+
}
Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
package mvp.sample.io.mercury.mvpexample.interactor;
2+
3+
import mvp.sample.io.mercury.mvpexample.entity.Favorite;
4+
import mvp.sample.io.mercury.mvpexample.repository.FavoriteRepo;
5+
6+
public class FavoriteAdder {
7+
8+
private final FavoriteRepo repo;
9+
10+
public FavoriteAdder(FavoriteRepo repo) {
11+
this.repo = repo;
12+
}
13+
14+
public Response execute(Favorite favorite) {
15+
// Application specific logic regarding adding a favorite that was already added
16+
boolean alreadyExisted = repo.exists(favorite);
17+
if (!alreadyExisted) {
18+
repo.put(favorite);
19+
}
20+
21+
return new Response(favorite, alreadyExisted);
22+
}
23+
24+
public class Response {
25+
private final Favorite favorite;
26+
27+
private final boolean alreadyExisted;
28+
29+
public Response(Favorite favorite, boolean alreadyExisted) {
30+
this.favorite = favorite;
31+
this.alreadyExisted = alreadyExisted;
32+
}
33+
34+
public boolean alreadyExisted() {
35+
return alreadyExisted;
36+
}
37+
38+
public Favorite getFavorite() {
39+
return favorite;
40+
}
41+
}
42+
}

0 commit comments

Comments
 (0)