diff --git a/.idea/misc.xml b/.idea/misc.xml index cc72de3..ad53516 100644 --- a/.idea/misc.xml +++ b/.idea/misc.xml @@ -24,7 +24,7 @@ - + diff --git a/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailAdapter.java b/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailAdapter.java index c5f2cfd..684cfcd 100644 --- a/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailAdapter.java +++ b/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailAdapter.java @@ -1,12 +1,24 @@ package de.sebse.fuplanner.fragments.moddetails; +import android.content.Context; +import android.content.res.Resources; import android.support.v4.app.Fragment; import android.support.v4.app.FragmentManager; -import android.support.v4.app.FragmentPagerAdapter; +import android.support.v4.app.FragmentStatePagerAdapter; -class ModDetailAdapter extends FragmentPagerAdapter { - public ModDetailAdapter(FragmentManager fm) { +import de.sebse.fuplanner.R; +import de.sebse.fuplanner.tools.logging.Logger; + +class ModDetailAdapter extends FragmentStatePagerAdapter { + private final int mItemPos; + private final Context mContext; + private Logger log = new Logger(this); + + public ModDetailAdapter(FragmentManager fm, int itemPosition, Context context) { super(fm); + this.mContext = context; + this.mItemPos = itemPosition; + log.d("constructor"); } @@ -19,11 +31,12 @@ class ModDetailAdapter extends FragmentPagerAdapter { // Returns the fragment to display for that page @Override public Fragment getItem(int position) { + log.d("getItem"); switch (position) { case 0: // Fragment # 0 - This will show FirstFragment - return ModDetailOverviewFragment.newInstance("1", "Page # 1"); + return ModDetailOverviewFragment.newInstance(mItemPos); case 1: // Fragment # 0 - This will show FirstFragment different title - return ModDetailAnnounceFragment.newInstance("2", "Page # 2"); + return ModDetailAnnounceFragment.newInstance(mItemPos); default: return null; } @@ -32,7 +45,14 @@ class ModDetailAdapter extends FragmentPagerAdapter { // Returns the page title for the top indicator @Override public CharSequence getPageTitle(int position) { - return "Page " + position; + switch (position) { + case 0: + return this.mContext.getResources().getString(R.string.overview); + case 1: + return this.mContext.getResources().getString(R.string.announcements); + default: + return ""; + } } } diff --git a/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailAnnounceFragment.java b/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailAnnounceFragment.java index e6efa2a..6c1596f 100644 --- a/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailAnnounceFragment.java +++ b/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailAnnounceFragment.java @@ -8,6 +8,7 @@ import android.view.View; import android.view.ViewGroup; import de.sebse.fuplanner.R; +import de.sebse.fuplanner.tools.logging.Logger; /** * A simple {@link Fragment} subclass. @@ -17,12 +18,11 @@ import de.sebse.fuplanner.R; public class ModDetailAnnounceFragment extends Fragment { // TODO: Rename parameter arguments, choose names that match // the fragment initialization parameters, e.g. ARG_ITEM_NUMBER - private static final String ARG_PARAM1 = "param1"; - private static final String ARG_PARAM2 = "param2"; + private static final String ARG_POSITION = "itemPosition"; // TODO: Rename and change types of parameters - private String mParam1; - private String mParam2; + private int mItemPos; + private Logger log = new Logger(this); public ModDetailAnnounceFragment() { @@ -33,16 +33,14 @@ public class ModDetailAnnounceFragment extends Fragment { * Use this factory method to create a new instance of * this fragment using the provided parameters. * - * @param param1 Parameter 1. - * @param param2 Parameter 2. + * @param itemPosition Item position in module list. * @return A new instance of fragment ModDetailAnnounceFragment. */ // TODO: Rename and change types and number of parameters - public static ModDetailAnnounceFragment newInstance(String param1, String param2) { + public static ModDetailAnnounceFragment newInstance(int itemPosition) { ModDetailAnnounceFragment fragment = new ModDetailAnnounceFragment(); Bundle args = new Bundle(); - args.putString(ARG_PARAM1, param1); - args.putString(ARG_PARAM2, param2); + args.putInt(ARG_POSITION, itemPosition); fragment.setArguments(args); return fragment; } @@ -51,8 +49,7 @@ public class ModDetailAnnounceFragment extends Fragment { public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); if (getArguments() != null) { - mParam1 = getArguments().getString(ARG_PARAM1); - mParam2 = getArguments().getString(ARG_PARAM2); + mItemPos = getArguments().getInt(ARG_POSITION); } } diff --git a/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailFragment.java b/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailFragment.java index c2d4d49..1bf6fda 100644 --- a/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailFragment.java +++ b/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailFragment.java @@ -3,13 +3,16 @@ package de.sebse.fuplanner.fragments.moddetails; import android.content.Context; import android.net.Uri; import android.os.Bundle; +import android.support.annotation.NonNull; import android.support.v4.app.Fragment; import android.support.v4.view.ViewPager; +import android.util.Log; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import de.sebse.fuplanner.R; +import de.sebse.fuplanner.tools.logging.Logger; /** * A simple {@link Fragment} subclass. @@ -24,11 +27,12 @@ public class ModDetailFragment extends Fragment { // the fragment initialization parameters, e.g. ARG_ITEM_NUMBER private static final String ARG_POSITION = "itemPosition"; - // TODO: Rename and change types of parameters + // Parameters private int mItemPos; private OnModuleDetailFragmentInteractionListener mListener; private ModDetailAdapter adapterViewPager; + private Logger log = new Logger(this); public ModDetailFragment() { // Required empty public constructor @@ -47,6 +51,7 @@ public class ModDetailFragment extends Fragment { Bundle args = new Bundle(); args.putInt(ARG_POSITION, itemPosition); fragment.setArguments(args); + Log.d("ModDetailFragment", "newInstance"); return fragment; } @@ -56,17 +61,18 @@ public class ModDetailFragment extends Fragment { if (getArguments() != null) { mItemPos = getArguments().getInt(ARG_POSITION); } - + log.d("on create"); } @Override - public View onCreateView(LayoutInflater inflater, ViewGroup container, + public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { // Inflate the layout for this fragment + log.d("on create view"); View v = inflater.inflate(R.layout.fragment_mod_detail, container, false); ViewPager vpPager = (ViewPager) v.findViewById(R.id.vpPager); - adapterViewPager = new ModDetailAdapter(getFragmentManager()); + adapterViewPager = new ModDetailAdapter(getFragmentManager(), mItemPos, getContext()); vpPager.setAdapter(adapterViewPager); return v; } diff --git a/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailOverviewFragment.java b/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailOverviewFragment.java index ff4aaf5..13130c5 100644 --- a/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailOverviewFragment.java +++ b/app/src/main/java/de/sebse/fuplanner/fragments/moddetails/ModDetailOverviewFragment.java @@ -2,12 +2,21 @@ package de.sebse.fuplanner.fragments.moddetails; import android.os.Bundle; +import android.support.annotation.NonNull; import android.support.v4.app.Fragment; +import android.util.Log; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; +import de.sebse.fuplanner.MainActivity; import de.sebse.fuplanner.R; +import de.sebse.fuplanner.services.KVV.KVV; +import de.sebse.fuplanner.services.KVV.Modules; +import de.sebse.fuplanner.tools.logging.Logger; +import de.sebse.fuplanner.tools.network.NetworkCallback; +import de.sebse.fuplanner.tools.network.NetworkError; +import de.sebse.fuplanner.tools.network.NetworkErrorCallback; /** * A simple {@link Fragment} subclass. @@ -17,12 +26,11 @@ import de.sebse.fuplanner.R; public class ModDetailOverviewFragment extends Fragment { // TODO: Rename parameter arguments, choose names that match // the fragment initialization parameters, e.g. ARG_ITEM_NUMBER - private static final String ARG_PARAM1 = "param1"; - private static final String ARG_PARAM2 = "param2"; + private static final String ARG_POSITION = "itemPosition"; // TODO: Rename and change types of parameters - private String mParam1; - private String mParam2; + private int mItemPos; + private Logger log = new Logger(this); public ModDetailOverviewFragment() { @@ -33,34 +41,52 @@ public class ModDetailOverviewFragment extends Fragment { * Use this factory method to create a new instance of * this fragment using the provided parameters. * - * @param param1 Parameter 1. - * @param param2 Parameter 2. + * @param itemPosition Item position in module list. * @return A new instance of fragment ModDetailOverviewFragment. */ // TODO: Rename and change types and number of parameters - public static ModDetailOverviewFragment newInstance(String param1, String param2) { + public static ModDetailOverviewFragment newInstance(int itemPosition) { ModDetailOverviewFragment fragment = new ModDetailOverviewFragment(); Bundle args = new Bundle(); - args.putString(ARG_PARAM1, param1); - args.putString(ARG_PARAM2, param2); + args.putInt(ARG_POSITION, itemPosition); fragment.setArguments(args); + String s = "ModDetailOverviewFragment".toString(); + Log.d(s, "new Instance"); return fragment; } @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); + log.d("on create"); if (getArguments() != null) { - mParam1 = getArguments().getString(ARG_PARAM1); - mParam2 = getArguments().getString(ARG_PARAM2); + mItemPos = getArguments().getInt(ARG_POSITION); } } @Override - public View onCreateView(LayoutInflater inflater, ViewGroup container, + public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { // Inflate the layout for this fragment - return inflater.inflate(R.layout.fragment_mod_detail_overview, container, false); + log.d("on create"); + MainActivity activity = (MainActivity) getActivity(); + View view = inflater.inflate(R.layout.fragment_mod_detail_overview, container, false); + if (activity != null) { + KVV kvv = activity.getKVV(); + kvv.getModuleDetails(mItemPos, new NetworkCallback() { + @Override + public void onResponse(@NonNull Modules.UpgradeModule success) { + log.d(success); + success.description = "Neue Beschreibung"; + } + }, new NetworkErrorCallback() { + @Override + public void onError(NetworkError error) { + log.e(error); + } + }); + } + return view; } } diff --git a/app/src/main/java/de/sebse/fuplanner/services/KVV/KVV.java b/app/src/main/java/de/sebse/fuplanner/services/KVV/KVV.java index 7faf40c..6a07a5a 100644 --- a/app/src/main/java/de/sebse/fuplanner/services/KVV/KVV.java +++ b/app/src/main/java/de/sebse/fuplanner/services/KVV/KVV.java @@ -56,6 +56,20 @@ public class KVV { }); } + public void getModuleDetails(final int index, final NetworkCallback callback, final NetworkErrorCallback error) { + this.getLastToken(new LastTokenCallback() { + @Override + public void onReceived(LoginToken token) { + KVVModuleList modules = (KVVModuleList) addons.get("modules"); + if (modules == null) { + modules = new KVVModuleList(KVV.this.context, token); + addons.put("modules", modules); + } + modules.getModuleDetails(index, callback, error); + } + }); + } + private void getLastToken(LastTokenCallback lastTokenCallback) { if (this.isUpdating) { this.updatingList.add(lastTokenCallback); diff --git a/app/src/main/java/de/sebse/fuplanner/services/KVV/KVVModuleList.java b/app/src/main/java/de/sebse/fuplanner/services/KVV/KVVModuleList.java index dc868f1..5d538ec 100644 --- a/app/src/main/java/de/sebse/fuplanner/services/KVV/KVVModuleList.java +++ b/app/src/main/java/de/sebse/fuplanner/services/KVV/KVVModuleList.java @@ -6,6 +6,10 @@ import android.support.annotation.NonNull; import com.android.volley.Response; import com.android.volley.VolleyError; +import org.json.JSONArray; +import org.json.JSONException; +import org.json.JSONObject; + import java.util.HashMap; import java.util.HashSet; import java.util.Iterator; @@ -14,6 +18,7 @@ import java.util.regex.MatchResult; import java.util.regex.Matcher; import java.util.regex.Pattern; +import de.sebse.fuplanner.tools.AsyncQueue; import de.sebse.fuplanner.tools.network.HTTPService; import de.sebse.fuplanner.tools.network.NetworkCallback; import de.sebse.fuplanner.tools.network.NetworkError; @@ -27,128 +32,199 @@ import de.sebse.fuplanner.tools.network.Result; public class KVVModuleList extends HTTPService { private final LoginToken token; private Modules moduleList; + //private AsyncQueue, NetworkErrorCallback> queueUpgradeModule = new AsyncQueue<>(); + private AsyncQueue queueModuleDetails = new AsyncQueue(); public KVVModuleList(Context context, LoginToken token) { super(context); this.token = token; } - public void getModuleList(final NetworkCallback callback, final NetworkErrorCallback errorCallback) { + /*public void getModuleList(final NetworkCallback callback, final NetworkErrorCallback errorCallback) { if (moduleList != null) { callback.onResponse(moduleList); return; } - get("https://kvv.imp.fu-berlin.de/portal/site/~" + token.getUsername() + "/tool/9df8c796-7d6b-4416-8ba1-f505ea6b8224/", token.getCookies(), new Response.Listener() { + get("https://kvv.imp.fu-berlin.de/portal/site/~" + token.getUsername(), token.getCookies(), new Response.Listener() { @Override public void onResponse(Result response) { - String location = response.getHeaders().get("Location"); - get("https://kvv.imp.fu-berlin.de/portal/site/~"+token.getUsername()+"/tool/9df8c796-7d6b-4416-8ba1-f505ea6b8224/"+location, token.getCookies(), new Response.Listener() { + // tool/([0-9a-f-]*)"(.|\n|\r){0,200}icon-sakai--fu-berlin-joinablecoursebrowser + String body = response.getParsed(); + log.d("FIRST STEP", body); + log.d("FIRST STEP", response.getHeaders().get("Location")); + final String id; + try { + //language=RegExp + id = regex("tool/([0-9a-f-]*)\"(.|\\n|\\r){0,200}icon-sakai--fu-berlin-joinablecoursebrowser", body); + } catch (NoSuchFieldException e) { + errorCallback.onError(new NetworkError(101105, -1, "Cannot parse module list!")); + return; + } + get("https://kvv.imp.fu-berlin.de/portal/site/~" + token.getUsername() + "/tool/9df8c796-7d6b-4416-8ba1-f505ea6b8224/", token.getCookies(), new Response.Listener() { @Override public void onResponse(Result response) { - String body = response.getParsed(); - //largeLog("KVVModules", body); - Pattern pattern = Pattern.compile("(.*)", Pattern.DOTALL); - Matcher matcher = pattern.matcher(body); - if (!matcher.find()) { - errorCallback.onError(new NetworkError(101101, -1, "Cannot parse module list!")); - return; - } - //largeLog("KVVGroup", matcher.group(1)); - Modules modules = new Modules(); - //(.|\n)+? - for (MatchResult match: allMatches(Pattern.compile(".+?", Pattern.DOTALL), matcher.group(1))) { - try { - // Instructors - HashSet instructs = new HashSet<>(); - String instructors = regex(".+?
(.+?)
.+?", match.group()); - for (MatchResult match2: allMatches(Pattern.compile(".*(?=,)"), instructors)) { - if (match2.group()!=null && match2.group().length()>0) - instructs.add(match2.group()); + String location = response.getHeaders().get("Location"); + get("https://kvv.imp.fu-berlin.de/portal/site/~"+token.getUsername()+"/tool/9df8c796-7d6b-4416-8ba1-f505ea6b8224/"+location, token.getCookies(), new Response.Listener() { + @Override + public void onResponse(Result response) { + String body = response.getParsed(); + //largeLog("KVVModules", body); + Pattern pattern = Pattern.compile("(.*)", Pattern.DOTALL); + Matcher matcher = pattern.matcher(body); + if (!matcher.find()) { + errorCallback.onError(new NetworkError(101104, -1, "Cannot parse module list!")); + return; } - for (MatchResult match2: allMatches(Pattern.compile(".*(?=\\s+$|$)"), instructors)) { - if (match2.group()!=null && match2.group().length()>0) - instructs.add(match2.group()); + //largeLog("KVVGroup", matcher.group(1)); + Modules modules = new Modules(); + //(.|\n)+? + for (MatchResult match: allMatches(Pattern.compile(".+?", Pattern.DOTALL), matcher.group(1))) { + try { + // Instructors + HashSet instructs = new HashSet<>(); + String instructors = regex(".+?
(.+?)
.+?", match.group()); + for (MatchResult match2: allMatches(Pattern.compile(".*(?=,)"), instructors)) { + if (match2.group()!=null && match2.group().length()>0) + instructs.add(match2.group()); + } + for (MatchResult match2: allMatches(Pattern.compile(".*(?=\\s+$|$)"), instructors)) { + if (match2.group()!=null && match2.group().length()>0) + instructs.add(match2.group()); + } + + // Semester + String semester = regex("
((Winter|Sommer)semester.*?)
", match.group()); + + // lvNumber + HashSet lvNumbers = new HashSet<>(); + String numbers = regex(".*?
(.*?)0) + lvNumbers.add(match2.group()); + } + + // Title + //language=RegExp + String title = regex("(.+?)", match.group()); + + // Type + //language=RegExp + String type = regex(".*?
(.*?)
", match.group()); + + // Upgrade URI + //language=RegExp + String upgradeURI = regex(".+?", match.group()); + + modules.addModule(semester, lvNumbers, title, instructs, type, upgradeURI); + } catch (NoSuchFieldException e) { + errorCallback.onError(new NetworkError(101102, -1, "Cannot parse module list!")); + return; + } } - - // Semester - String semester = regex("
((Winter|Sommer)semester.*?)
", match.group()); - - // lvNumber - HashSet lvNumbers = new HashSet<>(); - String numbers = regex(".*?
(.*?)0) - lvNumbers.add(match2.group()); - } - - // Title - //language=RegExp - String title = regex("(.+?)", match.group()); - - // Type - //language=RegExp - String type = regex(".*?
(.*?)
", match.group()); - - // Upgrade URI - //language=RegExp - String upgradeURI = regex(".+?", match.group()); - - modules.addModule(semester, lvNumbers, title, instructs, type, upgradeURI); - } catch (NoSuchFieldException e) { - errorCallback.onError(new NetworkError(101102, -1, "Cannot parse module list!")); - return; + KVVModuleList.this.moduleList = modules; + callback.onResponse(modules); } - } - KVVModuleList.this.moduleList = modules; - callback.onResponse(modules); + }, new Response.ErrorListener() { + @Override + public void onErrorResponse(VolleyError error) { + errorCallback.onError(new NetworkError(101101, error.networkResponse.statusCode, "Cannot get module list!")); + } + }); } }, new Response.ErrorListener() { @Override public void onErrorResponse(VolleyError error) { - errorCallback.onError(new NetworkError(101102, error.networkResponse.statusCode, "Cannot get module list!")); + errorCallback.onError(new NetworkError(101100, error.networkResponse.statusCode, "Cannot get module list!")); } }); } }, new Response.ErrorListener() { @Override public void onErrorResponse(VolleyError error) { - errorCallback.onError(new NetworkError(101100, error.networkResponse.statusCode, "Cannot get module list!")); + errorCallback.onError(new NetworkError(101103, error.networkResponse.statusCode, "Cannot get module list!")); + } + }); + } +*/ + public void getModuleList(NetworkCallback callback, final NetworkErrorCallback errorCallback) { + get("https://kvv.imp.fu-berlin.de/direct/site.json", token.getCookies(), new Response.Listener() { + @Override + public void onResponse(Result response) { + String body = response.getParsed(); + if (body == null) { + errorCallback.onError(new NetworkError(101101, 403, "No module list retreived!")); + return; + } + try { + JSONObject json = new JSONObject(body); + JSONArray sites = json.getJSONArray("site_collection"); + + for (int i = 0; i < sites.length(); i++) { + JSONObject site = sites.getJSONObject(i); + moduleList = new Modules(); + String semester = site.getJSONObject("props").getString("term_eid"); + HashSet lvNumbers = new HashSet<>(); + for (MatchResult matchResult: allMatches("[0-9]*", site.getJSONObject("props").getString("kvv_lvnumbers"))) { + lvNumbers.add(matchResult.group()); + } + String title = site.getJSONObject("props").getString("entityTitle"); + HashSet lecturers = new HashSet<>(); + for (String lecturer : site.getJSONObject("props").getString("kvv_lecturers").split("#")) { + lecturers.add(new Lecturer(lecturer)); + } + moduleList.addModule(semester, lvNumbers, title, lecturers, "", ""); + } + } catch (JSONException e) { + errorCallback.onError(new NetworkError(101102, 403, "Cannot parse module list!")); + return; + } catch (NoSuchFieldException e) { + errorCallback.onError(new NetworkError(101103, 403, "Cannot parse module list!")); + return; + } + } + }, new Response.ErrorListener() { + @Override + public void onErrorResponse(VolleyError error) { + errorCallback.onError(new NetworkError(101103, error.networkResponse.statusCode, "Cannot get module list!")); } }); } - public void getModuleDetails(final int index, final NetworkCallback callback, final NetworkErrorCallback errorCallback) { - if (moduleList == null) { - this.getModuleList(new NetworkCallback() { - @Override - public void onResponse(@NonNull Modules success) { - getModuleDetails(index, callback, errorCallback); + queueModuleDetails.add(new AsyncQueue.AsyncQueueCallback() { + @Override + public void run() { + if (moduleList == null) { + KVVModuleList.this.getModuleList(new NetworkCallback() { + @Override + public void onResponse(@NonNull Modules success) { + getModuleDetails(index, callback, errorCallback); + queueModuleDetails.next(); + } + }, queueModuleDetails.check(errorCallback)); + return; } - }, errorCallback); - } else { - Modules.Module m = moduleList.get(index); - if (m instanceof Modules.SimpleModule) { - upgradeModule((Modules.SimpleModule) m, new NetworkCallback>() { + final Modules.Module m = moduleList.get(index); + if (m instanceof Modules.UpgradeModule) { + callback.onResponse((Modules.UpgradeModule) m); + queueModuleDetails.next(); + return; + } + upgradeModule((Modules.SimpleModule) m, new NetworkCallback() { @Override - public void onResponse(@NonNull HashMap success) { - moduleList.upgradeItem(index, success.get("moduleID"), success.get("description")); - callback.onResponse((Modules.UpgradeModule) moduleList.get(index)); + public void onResponse(@NonNull String success) { + callback.onResponse(moduleList.upgradeItem(index, success)); + queueModuleDetails.next(); } - }, errorCallback); - } else { - callback.onResponse((Modules.UpgradeModule) moduleList.get(index)); + }, queueModuleDetails.check(errorCallback)); } - } + }); } - private void upgradeModule(Modules.SimpleModule module, final NetworkCallback> callback, final NetworkErrorCallback errorCallback) { - HashMap success = new HashMap<>(); - success.put("moduleID", "cool ID"); - success.put("desctiption", "cool desctiption"); - callback.onResponse(success); + private void upgradeModule(Modules.SimpleModule module, final NetworkCallback callback, final NetworkErrorCallback errorCallback) { + callback.onResponse("cool ID"); } diff --git a/app/src/main/java/de/sebse/fuplanner/services/KVV/Lecturer.java b/app/src/main/java/de/sebse/fuplanner/services/KVV/Lecturer.java new file mode 100644 index 0000000..0fbb8c9 --- /dev/null +++ b/app/src/main/java/de/sebse/fuplanner/services/KVV/Lecturer.java @@ -0,0 +1,33 @@ +package de.sebse.fuplanner.services.KVV; + +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +class Lecturer { + private final String firstname; + private final String surname; + private final String mail; + + public Lecturer(String parsableString) throws NoSuchFieldException { + Pattern pattern = Pattern.compile("([^|]*)\\|([^|]*)\\|([^|]*)\\|\\|", Pattern.DOTALL); + Matcher matcher = pattern.matcher(parsableString); + if (!matcher.find()) { + throw new NoSuchFieldException(); + } + this.firstname = matcher.group(1); + this.surname = matcher.group(2); + this.mail = matcher.group(3); + } + + public String getFirstname() { + return firstname; + } + + public String getSurname() { + return surname; + } + + public String getMail() { + return mail; + } +} diff --git a/app/src/main/java/de/sebse/fuplanner/services/KVV/Modules.java b/app/src/main/java/de/sebse/fuplanner/services/KVV/Modules.java index 8e42ece..f23ebaf 100644 --- a/app/src/main/java/de/sebse/fuplanner/services/KVV/Modules.java +++ b/app/src/main/java/de/sebse/fuplanner/services/KVV/Modules.java @@ -1,16 +1,20 @@ package de.sebse.fuplanner.services.KVV; import android.support.annotation.NonNull; +import android.util.Pair; import java.util.ArrayList; import java.util.HashSet; import java.util.Iterator; +import de.sebse.fuplanner.tools.EventEmitter; +import de.sebse.fuplanner.tools.Triplet; + /** * Created by sebastian on 29.10.17. */ -public class Modules implements Iterable { +public class Modules extends EventEmitter>> implements Iterable { private final ArrayList list; Modules() { @@ -23,10 +27,10 @@ public class Modules implements Iterable { return m; } - UpgradeModule upgradeItem(int index, String moduleID, String description) { + UpgradeModule upgradeItem(int index, String moduleID) { Module sm = list.get(index); if (sm instanceof SimpleModule) { - UpgradeModule um = new UpgradeModule((SimpleModule) sm, moduleID, description); + UpgradeModule um = new UpgradeModule((SimpleModule) sm, moduleID); list.set(index, um); return um; } else { @@ -34,6 +38,15 @@ public class Modules implements Iterable { } } + public void setDescription(int index, String description) { + Module entry = this.list.get(index); + if (!(entry instanceof UpgradeModule)) { + return; + } + ((UpgradeModule) entry).description = description; + emit(new Triplet<>(index, ((UpgradeModule) entry), new ArrayList())); + } + @NonNull @Override public Iterator iterator() { @@ -98,7 +111,7 @@ public class Modules implements Iterable { } public class SimpleModule extends Module { - public final String upgradeURI; + final String upgradeURI; private SimpleModule(String semester, HashSet lvNumber, String title, HashSet lecturer, String type, String upgradeURI) { super(semester, lvNumber, title, lecturer, type); @@ -113,13 +126,12 @@ public class Modules implements Iterable { } public class UpgradeModule extends Module { - public final String moduleID; - public final String description; + final String moduleID; + public String description = null; - private UpgradeModule(SimpleModule module, String moduleID, String description) { + private UpgradeModule(SimpleModule module, String moduleID) { super(module.semester, module.lvNumber, module.title, module.lecturer, module.type); this.moduleID = moduleID; - this.description = description; } @Override diff --git a/app/src/main/java/de/sebse/fuplanner/tools/AsyncQueue.java b/app/src/main/java/de/sebse/fuplanner/tools/AsyncQueue.java new file mode 100644 index 0000000..f637f73 --- /dev/null +++ b/app/src/main/java/de/sebse/fuplanner/tools/AsyncQueue.java @@ -0,0 +1,107 @@ +package de.sebse.fuplanner.tools; + +import android.support.annotation.NonNull; + +import java.util.LinkedList; + +import de.sebse.fuplanner.tools.network.NetworkCallback; +import de.sebse.fuplanner.tools.network.NetworkError; +import de.sebse.fuplanner.tools.network.NetworkErrorCallback; + +public class AsyncQueue { + private LinkedList mQueue = new LinkedList<>(); + private boolean mRunning = false; + + public void add(AsyncQueueCallback callback) { + if (mRunning) + mQueue.addLast(callback); + else { + mRunning = true; + callback.run(); + } + } + + public void next() { + AsyncQueueCallback callback = mQueue.pollFirst(); + if (callback == null) + mRunning = false; + else + callback.run(); + } + + public interface AsyncQueueCallback { + void run(); + } + + public NetworkErrorCallback check(final NetworkErrorCallback value) { + return new NetworkErrorCallback() { + @Override + public void onError(NetworkError error) { + value.onError(error); + next(); + } + }; + } + + public NetworkCallback check(final NetworkCallback value) { + return new NetworkCallback() { + @Override + public void onResponse(@NonNull T success) { + value.onResponse(success); + next(); + } + }; + } +} + +/*public class AsyncQueue { + private ArrayList successes = new ArrayList<>(); + private ArrayList errors = new ArrayList<>(); + private boolean isRequesting = false; + + public void add(T successFunc, U errorFunc) { + this.successes.add(successFunc); + this.errors.add(errorFunc); + } + + public void add(T successFunc, U errorFunc, AsyncQueueCallback request) { + this.add(successFunc, errorFunc); + request(request); + } + + public void forEachSuccess(AsyncQueueCallbackValue forEach) { + isRequesting = false; + for (T success: this.successes) { + forEach.run(success); + } + this.clear(); + } + + public void forEachError(AsyncQueueCallbackValue forEach) { + isRequesting = false; + for (U error: this.errors) { + forEach.run(error); + } + this.clear(); + } + + public void clear() { + this.successes.clear(); + this.errors.clear(); + } + + public void request(AsyncQueueCallback request) { + if (!this.isRequesting) { + this.isRequesting = true; + request.run(); + } + } + + public interface AsyncQueueCallbackValue { + public void run(T value); + } + + public interface AsyncQueueCallback { + public void run(); + } +}*/ diff --git a/app/src/main/java/de/sebse/fuplanner/tools/EventEmitter.java b/app/src/main/java/de/sebse/fuplanner/tools/EventEmitter.java new file mode 100644 index 0000000..d3ce34c --- /dev/null +++ b/app/src/main/java/de/sebse/fuplanner/tools/EventEmitter.java @@ -0,0 +1,41 @@ +package de.sebse.fuplanner.tools; + + +import java.util.HashSet; + +public class EventEmitter { + private T lastValue = null; + private HashSet> list = new HashSet<>(); + + public EventEmitter() { + this(null); + } + + protected EventEmitter(T value) { + this.lastValue = value; + } + + public boolean emitterAdd(EventListener listener) { + return list.add(listener); + } + + public boolean emitterAddEmit(EventListener listener) { + listener.onResponse(this.lastValue); + return list.add(listener); + } + + public boolean emitterRemove(EventListener listener) { + return list.remove(listener); + } + + protected void emit(T value) { + this.lastValue = value; + for (EventListener emitter: list) { + emitter.onResponse(value); + } + } + + public interface EventListener { + void onResponse(T value); + } +} diff --git a/app/src/main/java/de/sebse/fuplanner/tools/Triplet.java b/app/src/main/java/de/sebse/fuplanner/tools/Triplet.java new file mode 100644 index 0000000..81d2d85 --- /dev/null +++ b/app/src/main/java/de/sebse/fuplanner/tools/Triplet.java @@ -0,0 +1,18 @@ +package de.sebse.fuplanner.tools; + +public class Triplet { + + private final T first; + private final U second; + private final V third; + + public Triplet(T first, U second, V third) { + this.first = first; + this.second = second; + this.third = third; + } + + public T getFirst() { return first; } + public U getSecond() { return second; } + public V getThird() { return third; } +} \ No newline at end of file diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 4c80f10..604a10c 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -8,4 +8,6 @@ Hello blank fragment + Overview + Announcements