Compare commits

...

1 Commits

Author SHA1 Message Date
Mieszko
c39310a9c1 Add user list 2018-08-28 21:39:13 +02:00
32 changed files with 521 additions and 190 deletions

View File

@ -35,6 +35,14 @@ dependencies {
implementation 'com.squareup.retrofit2:converter-gson:2.3.0' implementation 'com.squareup.retrofit2:converter-gson:2.3.0'
implementation "io.swagger:swagger-annotations:1.5.15" implementation "io.swagger:swagger-annotations:1.5.15"
implementation "org.threeten:threetenbp:1.3.5" implementation "org.threeten:threetenbp:1.3.5"
implementation "com.squareup.okhttp3:logging-interceptor:3.10.0"
implementation 'com.mapbox.mapboxsdk:mapbox-android-sdk:6.4.0' implementation 'com.mapbox.mapboxsdk:mapbox-android-sdk:6.4.0'
implementation 'io.reactivex.rxjava2:rxjava:2.2.0'
implementation 'com.android.support:recyclerview-v7:27.1.1'
implementation 'io.reactivex.rxjava2:rxandroid:2.1.0'
implementation "com.jakewharton:butterknife:8.8.1"
annotationProcessor "com.jakewharton:butterknife-compiler:8.8.1"
implementation "com.jakewharton.retrofit:retrofit2-rxjava2-adapter:1.0.0"
implementation "com.squareup.okhttp3:okhttp:3.0.1"
implementation "com.squareup.okhttp3:okhttp-urlconnection:3.0.1"
implementation "com.squareup.okhttp3:logging-interceptor:3.11.0"
} }

View File

@ -8,7 +8,8 @@
<uses-permission android:name="android.permission.READ_CONTACTS" /> <uses-permission android:name="android.permission.READ_CONTACTS" />
<uses-permission android:name="android.permission.INTERNET" /> <uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" /> <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_LOCATION_EXTRA_COMMANDS" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<application <application

View File

@ -320,7 +320,7 @@ public class LoginActivity extends AppCompatActivity implements LoaderCallbacks<
protected Boolean doInBackground(Void... params) { protected Boolean doInBackground(Void... params) {
LdapService service = RetrofitClientInstance.createService(LdapService.class); LdapService service = RetrofitClientInstance.createService(LdapService.class);
LdapUser user = new LdapUser("string",mPassword,"string","string","string","string",mEmail); LdapUser user = new LdapUser("string",mPassword,"string","tutor","string","string",mEmail);
Log.e("Login", "jwt token: " + user); Log.e("Login", "jwt token: " + user);

View File

@ -1,153 +1,95 @@
package com.uam.wmi.findmytutor.activity; package com.uam.wmi.findmytutor.activity;
import android.content.Context; import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences; import android.content.SharedPreferences;
import android.os.Bundle; import android.os.Bundle;
import android.support.design.widget.FloatingActionButton; import android.support.design.widget.CoordinatorLayout;
import android.support.v7.app.AppCompatActivity; import android.support.v7.app.AppCompatActivity;
import android.support.v7.widget.DefaultItemAnimator;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.util.Log; import android.util.Log;
import android.view.View; import android.view.View;
import android.widget.Button;
import android.widget.Toast;
import com.mapbox.mapboxsdk.Mapbox;
import com.mapbox.mapboxsdk.maps.MapView;
import com.uam.wmi.findmytutor.R; import com.uam.wmi.findmytutor.R;
import com.uam.wmi.findmytutor.model.Coordinate; import com.uam.wmi.findmytutor.model.PagedResult;
import com.uam.wmi.findmytutor.model.User;
import com.uam.wmi.findmytutor.network.RetrofitClientInstance; import com.uam.wmi.findmytutor.network.RetrofitClientInstance;
import com.uam.wmi.findmytutor.service.Coordinates; import com.uam.wmi.findmytutor.service.UserService;
import com.uam.wmi.findmytutor.utils.MyDividerItemDecoration;
import com.uam.wmi.findmytutor.view.TutorsAdapter;
import java.util.ArrayList;
import java.util.List; import java.util.List;
import retrofit2.Call; import butterknife.BindView;
import retrofit2.Callback; import butterknife.ButterKnife;
import retrofit2.Response; import io.reactivex.android.schedulers.AndroidSchedulers;
import io.reactivex.disposables.CompositeDisposable;
import io.reactivex.observers.DisposableSingleObserver;
import io.reactivex.schedulers.Schedulers;
public class MainActivity extends AppCompatActivity { public class MainActivity extends AppCompatActivity {
private MapView mapView; private static final String TAG = MainActivity.class.getSimpleName();
private UserService apiService;
private CompositeDisposable disposable = new CompositeDisposable();
private TutorsAdapter mAdapter;
private List<User> tutorsList = new ArrayList<>();
public List<Coordinate> getCoordinates() { @BindView(R.id.coordinator_layout)
return this.coordinates; CoordinatorLayout coordinatorLayout;
}
public void setCoordinates(List<Coordinate> coordinates) { @BindView(R.id.recycler_view)
this.coordinates = coordinates; RecyclerView recyclerView;
}
public List<Coordinate> coordinates;
@Override @Override
protected void onCreate(Bundle savedInstanceState) { protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState); super.onCreate(savedInstanceState);
Mapbox.getInstance(this, getString(R.string.access_token)); getWindow().getDecorView().setSystemUiVisibility(View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR);
setContentView(R.layout.activity_main); setContentView(R.layout.activity_main);
final FloatingActionButton button = findViewById(R.id.logoutButton); ButterKnife.bind(this);
button.setOnClickListener(new View.OnClickListener(){
@Override
public void onClick(View view) {
SharedPreferences preferences =getSharedPreferences("fmtPrefs",Context.MODE_PRIVATE);
SharedPreferences.Editor editor = preferences.edit();
editor.clear().commit();
Intent i = getBaseContext().getPackageManager()
.getLaunchIntentForPackage( getBaseContext().getPackageName() );
i.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
startActivity(i);
finish();
}
});
mapView = (MapView) findViewById(R.id.mapView);
mapView.onCreate(savedInstanceState);
final SharedPreferences sharedPref = getSharedPreferences("fmtPrefs", Context.MODE_PRIVATE); final SharedPreferences sharedPref = getSharedPreferences("fmtPrefs", Context.MODE_PRIVATE);
final String authToken = sharedPref.getString("authToken",null); final String authToken = sharedPref.getString("authToken",null);
Coordinates service = RetrofitClientInstance.createService(Coordinates.class,authToken); apiService = RetrofitClientInstance.createService(UserService.class,authToken);
Call<List<Coordinate>> call = service.getOnlineCoordinates(); mAdapter = new TutorsAdapter(this, tutorsList);
RecyclerView.LayoutManager mLayoutManager = new LinearLayoutManager(getApplicationContext());
recyclerView.setLayoutManager(mLayoutManager);
recyclerView.setItemAnimator(new DefaultItemAnimator());
recyclerView.addItemDecoration(new MyDividerItemDecoration(this, LinearLayoutManager.VERTICAL, 16));
recyclerView.setAdapter(mAdapter);
fetchAllTutors();
}
call.enqueue(new Callback<List<Coordinate>>() { private void fetchAllTutors() {
@Override disposable.add(
public void onResponse(Call<List<Coordinate>> call, Response<List<Coordinate>> response) { apiService.getPagedTutors("1")
Log.e("MainActivity", "rsp: " + response.body()); .subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
setCoordinates(response.body()); .subscribeWith(new DisposableSingleObserver <PagedResult>() {
/* mapView.getMapAsync(new OnMapReadyCallback() {
@Override @Override
public void onMapReady(MapboxMap mapboxMap,List<Coordinate> response) { public void onSuccess(PagedResult pagedResult) {
tutorsList.clear();
// Add the custom icon marker to the map tutorsList.addAll(pagedResult.getResults());
for(Coordinate coord: response.body()){ mAdapter.notifyDataSetChanged();
mapboxMap.addMarker(new MarkerOptions()
.position(new LatLng(coord.getLatitude(), coord.getLongitude()))
}
} }
});*/
}
@Override @Override
public void onFailure(Call<List<Coordinate>> call, Throwable t) { public void onError(Throwable e) {
Toast.makeText(MainActivity.this, "Something went wrong...Error message: " + t.getMessage(), Toast.LENGTH_SHORT).show(); Log.e("Error",e.toString());
} }
}));
});
}
@Override
public void onStart() {
super.onStart();
mapView.onStart();
}
@Override
public void onResume() {
super.onResume();
mapView.onResume();
}
@Override
public void onPause() {
super.onPause();
mapView.onPause();
}
@Override
public void onStop() {
super.onStop();
mapView.onStop();
}
@Override
public void onLowMemory() {
super.onLowMemory();
mapView.onLowMemory();
} }
@Override @Override
protected void onDestroy() { protected void onDestroy() {
super.onDestroy(); super.onDestroy();
mapView.onDestroy(); disposable.dispose();
} }
}
@Override
protected void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
mapView.onSaveInstanceState(outState);
}
}

View File

@ -0,0 +1,9 @@
package com.uam.wmi.findmytutor.model;
public class BaseResponse {
String error;
public String getError() {
return error;
}
}

View File

@ -11,7 +11,7 @@ import io.swagger.annotations.ApiModelProperty;
* Coordinate * Coordinate
*/ */
public class Coordinate { public class Coordinate extends BaseResponse{
@SerializedName("coordinateId") @SerializedName("coordinateId")
private UUID coordinateId = null; private UUID coordinateId = null;

View File

@ -11,7 +11,7 @@ import io.swagger.annotations.ApiModelProperty;
* DutyHour * DutyHour
*/ */
public class DutyHour { public class DutyHour extends BaseResponse {
@SerializedName("dutyHourId") @SerializedName("dutyHourId")
private UUID dutyHourId = null; private UUID dutyHourId = null;

View File

@ -3,7 +3,7 @@ package com.uam.wmi.findmytutor.model;
import com.google.gson.annotations.Expose; import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName; import com.google.gson.annotations.SerializedName;
public class IsUsingListBool { public class IsUsingListBool extends BaseResponse{
@SerializedName("isUsing") @SerializedName("isUsing")
@Expose @Expose

View File

@ -10,7 +10,7 @@ import io.swagger.annotations.ApiModelProperty;
* IsUsingListBoolModel * IsUsingListBoolModel
*/ */
public class IsUsingListBoolModel { public class IsUsingListBoolModel extends BaseResponse {
@SerializedName("isUsing") @SerializedName("isUsing")
private Boolean isUsing = null; private Boolean isUsing = null;

View File

@ -11,7 +11,7 @@ import io.swagger.annotations.ApiModelProperty;
* LdapUser * LdapUser
*/ */
public class LdapUser { public class LdapUser extends BaseResponse{
@SerializedName("login") @SerializedName("login")
private String login = null; private String login = null;

View File

@ -0,0 +1,16 @@
package com.uam.wmi.findmytutor.model;
import com.google.gson.annotations.SerializedName;
public class Model
{
@SerializedName("data")
private PagedResult data;
public PagedResult getData ()
{
return data;
}
}

View File

@ -1,14 +1,15 @@
package com.uam.wmi.findmytutor.model; package com.uam.wmi.findmytutor.model;
import java.util.List;
import com.google.gson.annotations.Expose; import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName; import com.google.gson.annotations.SerializedName;
public class PagedResult { import java.util.List;
public class PagedResult {
@SerializedName("results") @SerializedName("results")
@Expose @Expose
private List<Result> results = null; private List<User> results = null;
@SerializedName("currentPage") @SerializedName("currentPage")
@Expose @Expose
private Integer currentPage; private Integer currentPage;
@ -28,11 +29,11 @@ public class PagedResult {
@Expose @Expose
private Integer lastRowOnPage; private Integer lastRowOnPage;
public List<Result> getResults() { public List<User> getResults() {
return results; return results;
} }
public void setResults(List<Result> results) { public void setResults(List<User> results) {
this.results = results; this.results = results;
} }

View File

@ -12,7 +12,7 @@ import io.swagger.annotations.ApiModelProperty;
* PagedResultUserResponseModel * PagedResultUserResponseModel
*/ */
public class PagedResultUserResponseModel { public class PagedResultUserResponseModel extends BaseResponse {
@SerializedName("results") @SerializedName("results")
private List<UserResponseModel> results = null; private List<UserResponseModel> results = null;

View File

@ -1,9 +1,10 @@
package com.uam.wmi.findmytutor.model; package com.uam.wmi.findmytutor.model;
import java.util.List;
import com.google.gson.annotations.Expose; import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName; import com.google.gson.annotations.SerializedName;
public class Result { import java.util.List;
public class Result extends BaseResponse {
@SerializedName("id") @SerializedName("id")
@Expose @Expose

View File

@ -11,7 +11,7 @@ import io.swagger.annotations.ApiModelProperty;
* StudentIdModel * StudentIdModel
*/ */
public class StudentIdModel { public class StudentIdModel extends BaseResponse{
@SerializedName("studentId") @SerializedName("studentId")
private String studentId = null; private String studentId = null;

View File

@ -15,7 +15,7 @@ import io.swagger.annotations.ApiModelProperty;
* TutorTab * TutorTab
*/ */
public class TutorTab { public class TutorTab extends BaseResponse{
@SerializedName("tutorTabId") @SerializedName("tutorTabId")
private UUID tutorTabId = null; private UUID tutorTabId = null;

View File

@ -15,7 +15,7 @@ import io.swagger.annotations.ApiModelProperty;
* User * User
*/ */
public class User { public class User extends BaseResponse{
@SerializedName("isOnline") @SerializedName("isOnline")
private Boolean isOnline = null; private Boolean isOnline = null;

View File

@ -12,7 +12,7 @@ import io.swagger.annotations.ApiModelProperty;
* UserResponseModel * UserResponseModel
*/ */
public class UserResponseModel { public class UserResponseModel extends BaseResponse{
@SerializedName("id") @SerializedName("id")
private String id = null; private String id = null;

View File

@ -1,5 +1,7 @@
package com.uam.wmi.findmytutor.network; package com.uam.wmi.findmytutor.network;
import com.jakewharton.retrofit2.adapter.rxjava2.RxJava2CallAdapterFactory;
import okhttp3.OkHttpClient; import okhttp3.OkHttpClient;
import okhttp3.Request; import okhttp3.Request;
import okhttp3.logging.HttpLoggingInterceptor; import okhttp3.logging.HttpLoggingInterceptor;
@ -13,6 +15,7 @@ public class RetrofitClientInstance {
private static Retrofit.Builder builder private static Retrofit.Builder builder
= new Retrofit.Builder() = new Retrofit.Builder()
.baseUrl(BASE_URL) .baseUrl(BASE_URL)
.addCallAdapterFactory(RxJava2CallAdapterFactory.create())
.addConverterFactory(GsonConverterFactory.create()); .addConverterFactory(GsonConverterFactory.create());
private static Retrofit retrofit = builder.build(); private static Retrofit retrofit = builder.build();

View File

@ -13,7 +13,7 @@ import retrofit2.http.POST;
import retrofit2.http.PUT; import retrofit2.http.PUT;
import retrofit2.http.Path; import retrofit2.http.Path;
public interface Coordinates { public interface CoordinateService {
@GET("api/coordinates") @GET("api/coordinates")
Call<List<Coordinate>> getAllCoordinates(); Call<List<Coordinate>> getAllCoordinates();

View File

@ -1,77 +1,77 @@
package com.uam.wmi.findmytutor.service; package com.uam.wmi.findmytutor.service;
import com.uam.wmi.findmytutor.model.JwtToken;
import com.uam.wmi.findmytutor.model.PagedResult;
import com.uam.wmi.findmytutor.model.User;
import com.uam.wmi.findmytutor.model.IsUsingListBool; import com.uam.wmi.findmytutor.model.IsUsingListBool;
import com.uam.wmi.findmytutor.model.PagedResult;
import com.uam.wmi.findmytutor.model.StudentIdModel; import com.uam.wmi.findmytutor.model.StudentIdModel;
import com.uam.wmi.findmytutor.model.User;
import java.util.List; import java.util.List;
import okhttp3.ResponseBody; import io.reactivex.Completable;
import retrofit2.Call; import io.reactivex.Single;
import retrofit2.http.Body; import retrofit2.http.Body;
import retrofit2.http.DELETE; import retrofit2.http.DELETE;
import retrofit2.http.GET; import retrofit2.http.GET;
import retrofit2.http.PUT;
import retrofit2.http.POST; import retrofit2.http.POST;
import retrofit2.http.PUT;
import retrofit2.http.Path; import retrofit2.http.Path;
import retrofit2.http.Header;
public interface UserService { public interface UserService {
@GET("api/users") @GET("api/users")
Call<List<User>> getAllUsers(); Single <List<User>> getAllUsers();
@POST("api/users") @POST("api/users")
Call<ResponseBody> createUser(@Body User user); Completable createUser(@Body User user);
@GET("api/users/page/{pageNum}") @GET("api/users/page/{pageNum}")
Call<PagedResult> getPagedUsers(@Path("pageNum") String pageNum ); Single <PagedResult> getPagedUsers(@Path("pageNum") String pageNum );
@GET("/api/users/tutors/page/{pageNum}") @GET("api/users/tutors/page/{pageNum}")
Call<PagedResult> getPagedTutors(@Path("pageNum") String pageNum); Single <PagedResult> getPagedTutors(@Path("pageNum") String pageNum);
@GET("/api/users/students/page/{pageNum}") @GET("api/users/students/page/{pageNum}")
Call<PagedResult> getPagedStudents(@Path("pageNum") String pageNum); Single<PagedResult> getPagedStudents(@Path("pageNum") String pageNum);
@GET("api/users/{id}") @GET("api/users/{id}")
Call<User> getUserByID(@Path("id") String userID); Single<User> getUserByID(@Path("id") String userID);
@PUT("api/users/{id}") @PUT("api/users/{id}")
Call<User> updateUserByID(@Path("id") String userID, @Body User user); Completable updateUserByID(@Path("id") String userID, @Body User user);
@DELETE("api/users/{id}") @DELETE("api/users/{id}")
Call<User> deleteUserByID(@Path("id") String userID); Completable deleteUserByID(@Path("id") String userID);
@GET("api/users/userLogin/{ldapLogin}") @GET("api/users/userLogin/{ldapLogin}")
Call<String> getUserLdapLogin(@Path("ldapLogin") String ldapLogin); Single<String> getUserLdapLogin(@Path("ldapLogin") String ldapLogin);
@PUT("api/users/setActive/{userID}") @PUT("api/users/setActive/{userID}")
Call<User> setUserActive(@Path("userID") String userID); Completable setUserActive(@Path("userID") String userID);
@PUT("api/users/setInActive/{userID}") @PUT("api/users/setInActive/{userID}")
Call<User> setUserInActive(@Path("userID") String userID); Completable setUserInActive(@Path("userID") String userID);
@GET("api/users/blacklist/{tutorID}") @GET("api/users/blacklist/{tutorID}")
Call<List<User>> getTutorBlacklistedByID(@Path("tutorID") String tutorID); Single<List<User>> getTutorBlacklistedByID(@Path("tutorID") String tutorID);
@PUT("api/users/blacklist/{tutorID}") @PUT("api/users/blacklist/{tutorID}")
Call<User> setTutorBlacklist(@Path("tutorID") String tutorID, @Body IsUsingListBool isUsing); Completable setTutorBlacklist(@Path("tutorID") String tutorID, @Body IsUsingListBool isUsing);
@POST("api/users/blacklist/{tutorID}") @POST("api/users/blacklist/{tutorID}")
Call<ResponseBody> addStudentToBlacklist(@Path("tutorID") String tutorID, @Body StudentIdModel student); Completable addStudentToBlacklist(@Path("tutorID") String tutorID, @Body StudentIdModel student);
@DELETE("api/users/blacklist/{tutorID}") @DELETE("api/users/blacklist/{tutorID}")
Call<List<User>> removeStudentFromBlacklist(@Path("tutorID") String tutorID, @Body StudentIdModel student); Completable removeStudentFromBlacklist(@Path("tutorID") String tutorID, @Body StudentIdModel student);
@GET("api/users/whitelist/{tutorID}") @GET("api/users/whitelist/{tutorID}")
Call<List<User>> getTutorwhitelistedByID(@Path("tutorID") String tutorID); Single<List<User>> getTutorwhitelistedByID(@Path("tutorID") String tutorID);
@PUT("api/users/whitelist/{tutorID}") @PUT("api/users/whitelist/{tutorID}")
Call<User> setTutorWhitelist(@Path("tutorID") String tutorID, @Body IsUsingListBool isUsing); Completable setTutorWhitelist(@Path("tutorID") String tutorID, @Body IsUsingListBool isUsing);
@POST("api/users/whitelist/{tutorID}") @POST("api/users/whitelist/{tutorID}")
Call<ResponseBody> addStudentTowhitelist(@Path("tutorID") String tutorID, @Body StudentIdModel student); Completable addStudentTowhitelist(@Path("tutorID") String tutorID, @Body StudentIdModel student);
@DELETE("api/users/whitelist/{tutorID}") @DELETE("api/users/whitelist/{tutorID}")
Call<List<User>> removeStudentFromWhitelist(@Path("tutorID") String tutorID, @Body StudentIdModel student); Completable removeStudentFromWhitelist(@Path("tutorID") String tutorID, @Body StudentIdModel student);
} }

View File

@ -0,0 +1,98 @@
package com.uam.wmi.findmytutor.utils;
import android.content.Context;
import android.content.res.Resources;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.graphics.Rect;
import android.graphics.drawable.Drawable;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.util.TypedValue;
import android.view.View;
public class MyDividerItemDecoration extends RecyclerView.ItemDecoration {
private static final int[] ATTRS = new int[]{
android.R.attr.listDivider
};
public static final int HORIZONTAL_LIST = LinearLayoutManager.HORIZONTAL;
public static final int VERTICAL_LIST = LinearLayoutManager.VERTICAL;
private Drawable mDivider;
private int mOrientation;
private Context context;
private int margin;
public MyDividerItemDecoration(Context context, int orientation, int margin) {
this.context = context;
this.margin = margin;
final TypedArray a = context.obtainStyledAttributes(ATTRS);
mDivider = a.getDrawable(0);
a.recycle();
setOrientation(orientation);
}
public void setOrientation(int orientation) {
if (orientation != HORIZONTAL_LIST && orientation != VERTICAL_LIST) {
throw new IllegalArgumentException("invalid orientation");
}
mOrientation = orientation;
}
@Override
public void onDrawOver(Canvas c, RecyclerView parent, RecyclerView.State state) {
if (mOrientation == VERTICAL_LIST) {
drawVertical(c, parent);
} else {
drawHorizontal(c, parent);
}
}
public void drawVertical(Canvas c, RecyclerView parent) {
final int left = parent.getPaddingLeft();
final int right = parent.getWidth() - parent.getPaddingRight();
final int childCount = parent.getChildCount();
for (int i = 0; i < childCount; i++) {
final View child = parent.getChildAt(i);
final RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child
.getLayoutParams();
final int top = child.getBottom() + params.bottomMargin;
final int bottom = top + mDivider.getIntrinsicHeight();
mDivider.setBounds(left + dpToPx(margin), top, right - dpToPx(margin), bottom);
mDivider.draw(c);
}
}
public void drawHorizontal(Canvas c, RecyclerView parent) {
final int top = parent.getPaddingTop();
final int bottom = parent.getHeight() - parent.getPaddingBottom();
final int childCount = parent.getChildCount();
for (int i = 0; i < childCount; i++) {
final View child = parent.getChildAt(i);
final RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child
.getLayoutParams();
final int left = child.getRight() + params.rightMargin;
final int right = left + mDivider.getIntrinsicHeight();
mDivider.setBounds(left, top + dpToPx(margin), right, bottom - dpToPx(margin));
mDivider.draw(c);
}
}
@Override
public void getItemOffsets(Rect outRect, View view, RecyclerView parent, RecyclerView.State state) {
if (mOrientation == VERTICAL_LIST) {
outRect.set(0, 0, 0, mDivider.getIntrinsicHeight());
} else {
outRect.set(0, 0, mDivider.getIntrinsicWidth(), 0);
}
}
private int dpToPx(int dp) {
Resources r = context.getResources();
return Math.round(TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, dp, r.getDisplayMetrics()));
}
}

View File

@ -0,0 +1,27 @@
package com.uam.wmi.findmytutor.utils;
import android.content.Context;
import android.content.SharedPreferences;
public class PrefUtils {
/**
* Storing API Key in shared preferences to
* add it in header part of every retrofit request
*/
public PrefUtils() {
}
private static SharedPreferences getSharedPreferences(Context context) {
return context.getSharedPreferences("APP_PREF", Context.MODE_PRIVATE);
}
public static void storeApiKey(Context context, String apiKey) {
SharedPreferences.Editor editor = getSharedPreferences(context).edit();
editor.putString("API_KEY", apiKey);
editor.commit();
}
public static String getApiKey(Context context) {
return getSharedPreferences(context).getString("API_KEY", null);
}
}

View File

@ -0,0 +1,54 @@
package com.uam.wmi.findmytutor.utils;
import android.content.Context;
import android.support.v7.widget.RecyclerView;
import android.view.GestureDetector;
import android.view.MotionEvent;
import android.view.View;
public class RecyclerTouchListener implements RecyclerView.OnItemTouchListener {
private ClickListener clicklistener;
private GestureDetector gestureDetector;
public RecyclerTouchListener(Context context, final RecyclerView recycleView, final ClickListener clicklistener) {
this.clicklistener = clicklistener;
gestureDetector = new GestureDetector(context, new GestureDetector.SimpleOnGestureListener() {
@Override
public boolean onSingleTapUp(MotionEvent e) {
return true;
}
@Override
public void onLongPress(MotionEvent e) {
View child = recycleView.findChildViewUnder(e.getX(), e.getY());
if (child != null && clicklistener != null) {
clicklistener.onLongClick(child, recycleView.getChildAdapterPosition(child));
}
}
});
}
@Override
public boolean onInterceptTouchEvent(RecyclerView rv, MotionEvent e) {
View child = rv.findChildViewUnder(e.getX(), e.getY());
if (child != null && clicklistener != null && gestureDetector.onTouchEvent(e)) {
clicklistener.onClick(child, rv.getChildAdapterPosition(child));
}
return false;
}
@Override
public void onTouchEvent(RecyclerView rv, MotionEvent e) {
}
@Override
public void onRequestDisallowInterceptTouchEvent(boolean disallowIntercept) {
}
public interface ClickListener {
void onClick(View view, int position);
void onLongClick(View view, int position);
}
}

View File

@ -0,0 +1,72 @@
package com.uam.wmi.findmytutor.view;
import android.content.Context;
import android.support.v7.widget.RecyclerView;
import android.text.Html;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;
import com.uam.wmi.findmytutor.R;
import com.uam.wmi.findmytutor.model.User;
import java.util.List;
import butterknife.BindView;
import butterknife.ButterKnife;
public class TutorsAdapter extends RecyclerView.Adapter<TutorsAdapter.MyViewHolder> {
private Context context;
private List<User> tutorsList;
public class MyViewHolder extends RecyclerView.ViewHolder {
@BindView(R.id.firstName)
TextView firstName;
@BindView(R.id.lastName)
TextView lastName;
@BindView(R.id.isOnline)
TextView isOnline;
public MyViewHolder(View view) {
super(view);
ButterKnife.bind(this, view);
}
}
public TutorsAdapter(Context context, List<User> notesList) {
this.context = context;
this.tutorsList = notesList;
}
@Override
public MyViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View itemView = LayoutInflater.from(parent.getContext())
.inflate(R.layout.tutor_list_row, parent, false);
return new MyViewHolder(itemView);
}
@Override
public void onBindViewHolder(MyViewHolder holder, int position) {
User tutor = tutorsList.get(position);
Log.e("tutor", tutor.toString());
holder.firstName.setText(tutor.getFirstName());
holder.isOnline.setText(Html.fromHtml("&#8226;"));
holder.lastName.setText(tutor.getLastName());
}
@Override
public int getItemCount() {
return tutorsList.size();
}
}

View File

@ -1,37 +1,19 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android" <android.support.design.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/coordinator_layout"
xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools" xmlns:tools="http://schemas.android.com/tools"
xmlns:mapbox="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="match_parent" android:layout_height="match_parent"
tools:context=".activity.MainActivity"> tools:context=".activity.MainActivity">
<android.support.design.widget.AppBarLayout <android.support.design.widget.AppBarLayout
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:theme="@style/AppTheme.AppBarOverlay"> android:theme="@style/AppTheme.AppBarOverlay">
</android.support.design.widget.AppBarLayout> </android.support.design.widget.AppBarLayout>
<include layout="@layout/content_main" /> <include layout="@layout/content_main" />
<android.support.design.widget.FloatingActionButton
android:id="@+id/logoutButton"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="bottom|end"
android:layout_margin="@dimen/fab_margin"
app:backgroundTint="@android:color/holo_red_dark"
app:srcCompat="@android:drawable/ic_lock_power_off" />
<com.mapbox.mapboxsdk.maps.MapView
android:id="@+id/mapView"
android:layout_width="match_parent"
android:layout_height="match_parent"
mapbox:mapbox_cameraTargetLng="16.927002"
mapbox:mapbox_cameraTargetLat="52.466799"
mapbox:mapbox_styleUrl="mapbox://styles/domagalsky/cjiyzrqjp05l72rmj6ntvv2n8"
mapbox:mapbox_cameraZoom="17" />
</android.support.design.widget.CoordinatorLayout> </android.support.design.widget.CoordinatorLayout>

View File

@ -1,11 +1,18 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_behavior="@string/appbar_scrolling_view_behavior"
tools:context=".activity.MainActivity"
tools:showIn="@layout/activity_main">
</android.support.constraint.ConstraintLayout> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_behavior="@string/appbar_scrolling_view_behavior"
tools:context=".activity.MainActivity"
tools:showIn="@layout/activity_main">
<android.support.v7.widget.RecyclerView
android:id="@+id/recycler_view"
android:layout_width="match_parent"
android:layout_height="match_parent" />
</RelativeLayout>

View File

@ -0,0 +1,42 @@
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="80dp"
android:clickable="true"
android:paddingBottom="@dimen/dimen_10"
android:paddingLeft="@dimen/activity_margin"
android:paddingRight="@dimen/activity_margin"
android:paddingTop="@dimen/dimen_10">
<TextView
android:id="@+id/firstName"
android:layout_width="match_parent"
android:layout_height="14dp"
android:layout_alignParentTop="true"
android:layout_centerHorizontal="true"
android:layout_marginTop="13dp"
android:textColor="@color/note_list_text"
android:textSize="@dimen/note_list_text" />
<TextView
android:id="@+id/lastName"
android:layout_width="match_parent"
android:layout_height="14dp"
android:layout_below="@+id/firstName"
android:layout_centerHorizontal="true"
android:textColor="@color/note_list_text"
android:textSize="@dimen/note_list_text" />
<TextView
android:id="@+id/isOnline"
android:layout_width="match_parent"
android:layout_height="14dp"
android:layout_below="@+id/lastName"
android:layout_centerHorizontal="true"
android:textColor="@color/note_list_text"
android:textSize="@dimen/note_list_text" />
</RelativeLayout>

View File

@ -0,0 +1,43 @@
<?xml version="1.0" encoding="utf-8"?>
<resources>
<array name="mdcolor_400">
<item name="red_400" type="color">#e84e40</item>
<item name="pink_400" type="color">#ec407a</item>
<item name="purple_400" type="color">#ab47bc</item>
<item name="deep_purple_400" type="color">#7e57c2</item>
<item name="indigo_400" type="color">#5c6bc0</item>
<item name="blue_400" type="color">#738ffe</item>
<item name="light_blue_400" type="color">#29b6f6</item>
<item name="cyan_400" type="color">#26c6da</item>
<item name="teal_400" type="color">#26a69a</item>
<item name="green_400" type="color">#2baf2b</item>
<item name="light_green_400" type="color">#9ccc65</item>
<item name="lime_400" type="color">#d4e157</item>
<item name="yellow_400" type="color">#ffee58</item>
<item name="orange_400" type="color">#ffa726</item>
<item name="deep_orange_400" type="color">#ff7043</item>
<item name="brown_400" type="color">#8d6e63</item>
<item name="grey_400" type="color">#bdbdbd</item>
<item name="blue_grey_400" type="color">#78909c</item>
</array>
<array name="mdcolor_500">
<item name="red_500" type="color">#e51c23</item>
<item name="pink_500" type="color">#e91e63</item>
<item name="purple_500" type="color">#9c27b0</item>
<item name="deep_purple_500" type="color">#673ab7</item>
<item name="indigo_500" type="color">#3f51b5</item>
<item name="blue_500" type="color">#5677fc</item>
<item name="light_blue_500" type="color">#03a9f4</item>
<item name="cyan_500" type="color">#00bcd4</item>
<item name="teal_500" type="color">#009688</item>
<item name="green_500" type="color">#259b24</item>
<item name="light_green_500" type="color">#8bc34a</item>
<item name="lime_500" type="color">#cddc39</item>
<item name="yellow_500" type="color">#ffeb3b</item>
<item name="orange_500" type="color">#ff9800</item>
<item name="deep_orange_500" type="color">#ff5722</item>
<item name="brown_500" type="color">#795548</item>
<item name="grey_500" type="color">#9e9e9e</item>
<item name="blue_grey_500" type="color">#607d8b</item>
</array>
</resources>

View File

@ -3,4 +3,8 @@
<color name="colorPrimary">#3F51B5</color> <color name="colorPrimary">#3F51B5</color>
<color name="colorPrimaryDark">#303F9F</color> <color name="colorPrimaryDark">#303F9F</color>
<color name="colorAccent">#FF4081</color> <color name="colorAccent">#FF4081</color>
<color name="msg_no_notes">#999</color>
<color name="hint_enter_note">#89c3c3c3</color>
<color name="timestamp">#858585</color>
<color name="note_list_text">#232323</color>
</resources> </resources>

View File

@ -3,4 +3,18 @@
<dimen name="activity_horizontal_margin">16dp</dimen> <dimen name="activity_horizontal_margin">16dp</dimen>
<dimen name="activity_vertical_margin">16dp</dimen> <dimen name="activity_vertical_margin">16dp</dimen>
<dimen name="fab_margin">16dp</dimen> <dimen name="fab_margin">16dp</dimen>
<!-- Tutors list -->
<dimen name="activity_margin">16dp</dimen>
<dimen name="dot_margin_right">10dp</dimen>
<dimen name="msg_no_notes">26sp</dimen>
<dimen name="margin_top_no_notes">120dp</dimen>
<dimen name="lbl_new_note_title">20sp</dimen>
<dimen name="dimen_10">10dp</dimen>
<dimen name="input_new_note">20sp</dimen>
<dimen name="dot_height">10dp</dimen>
<dimen name="dot_text_size">40sp</dimen>
<dimen name="timestamp">14sp</dimen>
<dimen name="note_list_text">13sp</dimen>
</resources> </resources>

View File

@ -3,6 +3,13 @@
<string name="title_activity_login">Sign in</string> <string name="title_activity_login">Sign in</string>
<string name="title_activity_startup" translatable="false">StartUp Activity</string> <string name="title_activity_startup" translatable="false">StartUp Activity</string>
<!-- Tutors list -->
<string name="action_settings">Settings</string>
<string name="activity_title_home">Notes</string>
<string name="msg_no_notes">No notes found!</string>
<string name="lbl_new_note_title">New Note</string>
<string name="hint_enter_note">Enter your note!</string>
<!-- Strings related to login --> <!-- Strings related to login -->
<string name="prompt_email" translatable="false">Email</string> <string name="prompt_email" translatable="false">Email</string>