summaryrefslogtreecommitdiff
path: root/vdrmanager
diff options
context:
space:
mode:
Diffstat (limited to 'vdrmanager')
-rw-r--r--vdrmanager/res/drawable/folder.pngbin0 -> 4865 bytes
-rw-r--r--vdrmanager/res/layout-land/vdrmanager.xml33
-rw-r--r--vdrmanager/res/layout/folder_item.xml22
-rw-r--r--vdrmanager/res/layout/header_item.xml4
-rw-r--r--vdrmanager/res/layout/vdrmanager.xml35
-rw-r--r--vdrmanager/src/de/bjusystems/vdrmanager/data/Channel.java1
-rw-r--r--vdrmanager/src/de/bjusystems/vdrmanager/data/Recording.java95
-rw-r--r--vdrmanager/src/de/bjusystems/vdrmanager/data/RecordingListItem.java33
-rw-r--r--vdrmanager/src/de/bjusystems/vdrmanager/gui/BaseActivity.java3
-rw-r--r--vdrmanager/src/de/bjusystems/vdrmanager/gui/BaseEventAdapter.java354
-rw-r--r--vdrmanager/src/de/bjusystems/vdrmanager/gui/BaseEventListActivity.java2
-rw-r--r--vdrmanager/src/de/bjusystems/vdrmanager/gui/ChannelEventAdapter.java7
-rw-r--r--vdrmanager/src/de/bjusystems/vdrmanager/gui/RecordingAdapter.java81
-rw-r--r--vdrmanager/src/de/bjusystems/vdrmanager/gui/RecordingListActivity.java157
-rw-r--r--vdrmanager/src/de/bjusystems/vdrmanager/gui/TimeEventAdapter.java3
15 files changed, 740 insertions, 90 deletions
diff --git a/vdrmanager/res/drawable/folder.png b/vdrmanager/res/drawable/folder.png
new file mode 100644
index 0000000..5b3fcec
--- /dev/null
+++ b/vdrmanager/res/drawable/folder.png
Binary files differ
diff --git a/vdrmanager/res/layout-land/vdrmanager.xml b/vdrmanager/res/layout-land/vdrmanager.xml
index 52cc9c6..8f5b86e 100644
--- a/vdrmanager/res/layout-land/vdrmanager.xml
+++ b/vdrmanager/res/layout-land/vdrmanager.xml
@@ -8,13 +8,13 @@
<ImageView android:id="@+id/main_logo" android:layout_width="fill_parent"
android:layout_height="80dip" android:src="@drawable/vdr_logo" android:paddingBottom="5dip" />
- <!-- <ListView android:id="@+id/vdrmanager_menu" android:layout_width="fill_parent"
+ <!-- <ListView android:id="@+id/vdrmanager_menu" android:layout_width="fill_parent"
android:layout_height="wrap_content" android:layout_below="@id/main_logo"/> -->
<LinearLayout android:layout_width="fill_parent"
android:layout_height="wrap_content" android:orientation="horizontal" android:padding="3dip">
<Button android:text="@string/action_menu_channels"
- xmlns:android="http://schemas.android.com/apk/res/android"
+
android:drawableTop="@drawable/btn_channels" android:layout_width="wrap_content"
android:id="@+id/action_menu_channels" android:layout_height="wrap_content"
android:textColor="#FFF" android:layout_weight="1"
@@ -23,17 +23,17 @@
<Button android:text="@string/action_menu_recordings"
- xmlns:android="http://schemas.android.com/apk/res/android" android:padding="3dip"
+ android:padding="3dip"
android:drawableTop="@drawable/btn_recordings" android:layout_width="wrap_content"
android:id="@+id/action_menu_recordings" android:layout_height="wrap_content"
android:layout_weight="1"
android:cacheColorHint="?android:attr/colorBackground"
android:background="@android:drawable/list_selector_background"
- android:textColor="#FFF"
+ android:textColor="#FFF"
/>
<Button
- xmlns:android="http://schemas.android.com/apk/res/android"
+
android:id="@+id/action_menu_timers"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
@@ -46,27 +46,8 @@
android:textColor="#FFF" />
</LinearLayout>
- <LinearLayout android:layout_width="fill_parent"
+ <LinearLayout android:layout_width="fill_parent"
android:layout_height="wrap_content" android:orientation="horizontal">
- <Button android:text="@string/action_menu_epg"
- xmlns:android="http://schemas.android.com/apk/res/android"
- android:drawableTop="@drawable/btn_epglist" android:layout_width="wrap_content"
- android:id="@+id/action_menu_epg" android:layout_height="wrap_content"
- android:layout_weight="1"
- android:cacheColorHint="?android:attr/colorBackground"
- android:padding="3dip"
- android:background="@android:drawable/list_selector_background"
- android:textColor="#FFF" />
-
- <Button android:text="@string/action_menu_search"
- xmlns:android="http://schemas.android.com/apk/res/android"
- android:drawableTop="@drawable/btn_search" android:layout_width="wrap_content"
- android:id="@+id/action_menu_search" android:layout_height="wrap_content"
- android:layout_weight="1"
- android:cacheColorHint="?android:attr/colorBackground"
- android:background="@android:drawable/list_selector_background"
- android:padding="3dip"
- android:textColor="#FFF" />
<Button android:text="@string/action_menu_wakeup"
xmlns:android="http://schemas.android.com/apk/res/android" android:layout_weight="1"
@@ -77,6 +58,6 @@
android:background="@android:drawable/list_selector_background"
android:textColor="#FFF" />
</LinearLayout>
-
+
</LinearLayout>
</ScrollView> \ No newline at end of file
diff --git a/vdrmanager/res/layout/folder_item.xml b/vdrmanager/res/layout/folder_item.xml
new file mode 100644
index 0000000..fa2f8ab
--- /dev/null
+++ b/vdrmanager/res/layout/folder_item.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="utf-8"?>
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="fill_parent"
+ android:orientation="horizontal"
+ android:padding="5dip"
+ android:layout_height="wrap_content" >
+
+ <ImageView
+ android:layout_width="24dp"
+ android:layout_height="24dp"
+ android:src="@drawable/folder" />
+
+ <TextView
+ android:id="@+id/header_item"
+ android:textAppearance="?android:textAppearanceMedium"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:paddingLeft="5dip"
+ android:layout_gravity="center_vertical"
+ android:text="House of Cards" />
+
+</LinearLayout> \ No newline at end of file
diff --git a/vdrmanager/res/layout/header_item.xml b/vdrmanager/res/layout/header_item.xml
index 0ca07d6..0821980 100644
--- a/vdrmanager/res/layout/header_item.xml
+++ b/vdrmanager/res/layout/header_item.xml
@@ -1,8 +1,8 @@
<?xml version="1.0" encoding="utf-8"?>
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
-android:text="Header"
+android:text="Header"
android:layout_margin="2dip" android:paddingLeft="4dip" android:paddingRight="4dip"
android:background="#444444"
android:textAppearance="?android:textAppearanceMedium"
android:layout_width="fill_parent" android:layout_height="wrap_content" android:id="@+id/header_item"/>
-
+
diff --git a/vdrmanager/res/layout/vdrmanager.xml b/vdrmanager/res/layout/vdrmanager.xml
index d963d70..8fdf062 100644
--- a/vdrmanager/res/layout/vdrmanager.xml
+++ b/vdrmanager/res/layout/vdrmanager.xml
@@ -6,7 +6,7 @@
android:layout_height="wrap_content"
>
-
+
<LinearLayout
android:layout_width="fill_parent" android:layout_height="fill_parent"
android:orientation="vertical" android:padding="10dip">
@@ -15,7 +15,7 @@
android:clickable="true"
android:layout_height="80dip" android:src="@drawable/vdr_logo" android:padding="10dip" />
- <!-- <ListView android:id="@+id/vdrmanager_menu" android:layout_width="fill_parent"
+ <!-- <ListView android:id="@+id/vdrmanager_menu" android:layout_width="fill_parent"
android:layout_height="wrap_content" android:layout_below="@id/main_logo"/> -->
<LinearLayout android:layout_width="fill_parent"
@@ -26,9 +26,8 @@
android:textColor="#FFF" android:layout_weight="1"
android:cacheColorHint="?android:attr/colorBackground"
android:background="@android:drawable/list_selector_background"/>
-
+
<Button android:text="@string/action_menu_epg"
- xmlns:android="http://schemas.android.com/apk/res/android"
android:drawableTop="@drawable/btn_epglist" android:layout_width="wrap_content"
android:id="@+id/action_menu_epg" android:layout_height="wrap_content"
android:layout_weight="1"
@@ -37,22 +36,20 @@
android:textColor="#FFF" />
</LinearLayout>
-
+
<LinearLayout android:layout_width="fill_parent" android:padding="10dip"
android:layout_height="wrap_content" android:orientation="horizontal">
-
+
<Button android:text="@string/action_menu_recordings"
- xmlns:android="http://schemas.android.com/apk/res/android"
android:drawableTop="@drawable/btn_recordings" android:layout_width="wrap_content"
android:id="@+id/action_menu_recordings" android:layout_height="wrap_content"
android:layout_weight="1"
android:cacheColorHint="?android:attr/colorBackground"
android:background="@android:drawable/list_selector_background"
- android:textColor="#FFF"
+ android:textColor="#FFF"
/>
-
+
<Button android:text="@string/action_menu_timers"
- xmlns:android="http://schemas.android.com/apk/res/android"
android:drawableTop="@drawable/btn_timer" android:layout_width="wrap_content"
android:id="@+id/action_menu_timers" android:layout_height="wrap_content"
android:layout_weight="1"
@@ -63,29 +60,17 @@
<LinearLayout android:layout_width="fill_parent" android:padding="10dip"
android:layout_height="wrap_content" android:orientation="horizontal">
-
-
-
- <Button android:text="@string/action_menu_search"
- xmlns:android="http://schemas.android.com/apk/res/android"
- android:drawableTop="@drawable/btn_search" android:layout_width="wrap_content"
- android:id="@+id/action_menu_search" android:layout_height="wrap_content"
- android:layout_weight="1"
- android:cacheColorHint="?android:attr/colorBackground"
- android:background="@android:drawable/list_selector_background"
-
- android:textColor="#FFF" />
<Button android:text="@string/action_menu_wakeup"
- xmlns:android="http://schemas.android.com/apk/res/android" android:layout_weight="1"
+ android:layout_weight="1"
android:padding="5dip"
android:drawableTop="@drawable/btn_wakeup" android:layout_width="wrap_content"
android:id="@+id/action_menu_wakeup" android:layout_height="wrap_content"
-
+
android:cacheColorHint="?android:attr/colorBackground"
android:background="@android:drawable/list_selector_background"
android:textColor="#FFF" />
</LinearLayout>
-
+
</LinearLayout>
</ScrollView> \ No newline at end of file
diff --git a/vdrmanager/src/de/bjusystems/vdrmanager/data/Channel.java b/vdrmanager/src/de/bjusystems/vdrmanager/data/Channel.java
index d8ca9ec..2b7b0d1 100644
--- a/vdrmanager/src/de/bjusystems/vdrmanager/data/Channel.java
+++ b/vdrmanager/src/de/bjusystems/vdrmanager/data/Channel.java
@@ -63,6 +63,7 @@ public class Channel implements Parcelable {
}
public Channel(final String channelData) {
+ System.err.println(channelData);
String[] words = StringUtils.splitPreserveAllTokens(channelData,
C.DATA_SEPARATOR);
this.number = Integer.valueOf(words[0].substring(1));
diff --git a/vdrmanager/src/de/bjusystems/vdrmanager/data/Recording.java b/vdrmanager/src/de/bjusystems/vdrmanager/data/Recording.java
index f2ad445..f510011 100644
--- a/vdrmanager/src/de/bjusystems/vdrmanager/data/Recording.java
+++ b/vdrmanager/src/de/bjusystems/vdrmanager/data/Recording.java
@@ -1,15 +1,60 @@
package de.bjusystems.vdrmanager.data;
-import java.util.Date;
+import static de.bjusystems.vdrmanager.gui.Utils.mapSpecialChars;
+import java.util.Date;
import de.bjusystems.vdrmanager.StringUtils;
import de.bjusystems.vdrmanager.app.C;
-import static de.bjusystems.vdrmanager.gui.Utils.mapSpecialChars;
-
public class Recording extends Event{
+ public static String ROOT_FOLDER = "";
+ public static final String FOLDERDELIMCHAR = "~";
+
+ public class Folder {
+
+ public String name;
+
+ public Folder parent;
+
+ private String path;
+
+ public boolean isRoot(){
+ return parent == null;
+ }
+
+ public String getFullPath(){
+ if(this.path != null){
+ return this.path;
+ }
+ if(isRoot()){
+ this.path = "";
+ } else {
+ this.path = parent.getFullPath() + "/" + name;
+ }
+
+ return path;
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if(o == this){
+ return true;
+ }
+ return ((Folder)o).name.equals(this.name);
+ }
+ @Override
+ public int hashCode() {
+ return name.hashCode();
+ }
+
+ @Override
+ public String toString() {
+ return name + "("+path+")";
+ }
+ };
+
public Recording(String line) {
final String[] words = StringUtils.splitPreserveAllTokens(line, C.DATA_SEPARATOR);
int idx = 0;
@@ -17,7 +62,7 @@ public class Recording extends Event{
start = new Date(Long.parseLong(words[idx++]) * 1000);
stop = new Date(Long.parseLong(words[idx++]) * 1000);
channelName = mapSpecialChars(words[idx++]);
- title = mapSpecialChars(words[idx++]);
+ eventTitle = mapSpecialChars(words[idx++]);
shortText = mapSpecialChars(words[idx++]);
description = mapSpecialChars(words[idx++]);
fileName = mapSpecialChars(words[idx++]);
@@ -39,8 +84,27 @@ public class Recording extends Event{
timerStopTime = new Date(Long.parseLong(data) * 1000L);
}
}
+
+ if(idx < words.length) { //name
+ String titleRaw = words[idx];
+ int idxdel = titleRaw.lastIndexOf(FOLDERDELIMCHAR);
+ if(idxdel == -1){
+ title = titleRaw;
+ folder = ROOT_FOLDER;
+ } else {
+ title = titleRaw.substring(idxdel+1);
+
+ String foldersRaw = titleRaw.substring(0, idxdel);
+
+ folder = foldersRaw;
+
+ }
+ }
+
}
+ private String folder;
+
private String fileName;
private int fileSize;
@@ -51,11 +115,21 @@ public class Recording extends Event{
private String devInode = null;
+ private String eventTitle = null;
+
/**
* If it is not null, recording is on going or will be on going until this date;
*/
private Date timerStopTime = null;
+ public String getEventTitle() {
+ return eventTitle;
+ }
+
+ public void setEventTitle(String eventTitle) {
+ this.eventTitle = eventTitle;
+ }
+
public Date getTimerStopTime() {
return timerStopTime;
}
@@ -123,4 +197,15 @@ public class Recording extends Event{
public String toString() {
return title;
}
-}
+
+
+ public String getFolder() {
+ return folder;
+ }
+
+ public void setFolder(String folder) {
+ this.folder = folder;
+ }
+
+
+} \ No newline at end of file
diff --git a/vdrmanager/src/de/bjusystems/vdrmanager/data/RecordingListItem.java b/vdrmanager/src/de/bjusystems/vdrmanager/data/RecordingListItem.java
new file mode 100644
index 0000000..b3137e3
--- /dev/null
+++ b/vdrmanager/src/de/bjusystems/vdrmanager/data/RecordingListItem.java
@@ -0,0 +1,33 @@
+package de.bjusystems.vdrmanager.data;
+
+
+public class RecordingListItem extends EventListItem {
+
+ public String folder;
+
+ public RecordingListItem(Recording rec) {
+ super(rec);
+ }
+
+ public RecordingListItem(String dailyHeader) {
+ super(dailyHeader);
+ }
+
+
+
+ public boolean isFolder() {
+
+ return folder != null;
+
+ }
+
+ @Override
+ public String getHeader() {
+ if (isFolder()) {
+ return folder;
+ } else {
+ return super.getHeader();
+ }
+ }
+
+} \ No newline at end of file
diff --git a/vdrmanager/src/de/bjusystems/vdrmanager/gui/BaseActivity.java b/vdrmanager/src/de/bjusystems/vdrmanager/gui/BaseActivity.java
index d9dc70f..fc53833 100644
--- a/vdrmanager/src/de/bjusystems/vdrmanager/gui/BaseActivity.java
+++ b/vdrmanager/src/de/bjusystems/vdrmanager/gui/BaseActivity.java
@@ -387,7 +387,8 @@ public abstract class BaseActivity<Result, T extends ListView> extends
@Override
public void svdrpEvent(SvdrpEvent event, Throwable t) {
- Utils.say(this, t.getLocalizedMessage());
+ progress.dismiss();
+ Utils.say(this, t.getMessage());
}
protected void addListener(SvdrpAsyncTask<Result, SvdrpClient<Result>> task) {
diff --git a/vdrmanager/src/de/bjusystems/vdrmanager/gui/BaseEventAdapter.java b/vdrmanager/src/de/bjusystems/vdrmanager/gui/BaseEventAdapter.java
new file mode 100644
index 0000000..297dfe0
--- /dev/null
+++ b/vdrmanager/src/de/bjusystems/vdrmanager/gui/BaseEventAdapter.java
@@ -0,0 +1,354 @@
+package de.bjusystems.vdrmanager.gui;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import android.content.Context;
+import android.util.Pair;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.ArrayAdapter;
+import android.widget.Filter;
+import android.widget.Filterable;
+import android.widget.ImageView;
+import android.widget.ProgressBar;
+import android.widget.TextView;
+import de.bjusystems.vdrmanager.R;
+import de.bjusystems.vdrmanager.data.Event;
+import de.bjusystems.vdrmanager.data.EventFormatter;
+import de.bjusystems.vdrmanager.data.EventListItem;
+import de.bjusystems.vdrmanager.data.Recording;
+import de.bjusystems.vdrmanager.data.TimerMatch;
+import de.bjusystems.vdrmanager.data.Timerable;
+
+abstract class BaseEventAdapter<T extends EventListItem> extends ArrayAdapter<T> implements
+ Filterable
+// , SectionIndexer
+{
+
+ protected final static int TYPE_ITEM = 0;
+ protected final static int TYPE_HEADER = 1;
+ protected final int layout;
+ protected final LayoutInflater inflater;
+ protected final List<T> items = new ArrayList<T>();
+
+ protected boolean hideDescription = true;
+
+ protected boolean hideChannelName = false;
+
+ String highlight;
+
+ /**
+ * Lock used to modify the content of {@link #mObjects}. Any write operation
+ * performed on the array should be synchronized on this lock. This lock is
+ * also used by the filter (see {@link #getFilter()} to make a synchronized
+ * copy of the original array of data.
+ */
+ private final Object _Lock = new Object();
+
+ public BaseEventAdapter(final Context context, int layout) {
+ super(context, layout);
+ this.layout = layout;
+ inflater = LayoutInflater.from(context);
+ }
+
+ @Override
+ public int getViewTypeCount() {
+ return 2;
+ }
+
+ @Override
+ public void add(T object) {
+ items.add(object);
+ // if (object.isHeader()) {
+ // sections.add(object.getHeader());
+ // }
+ super.add(object);
+ }
+
+ @Override
+ public int getItemViewType(int position) {
+
+ // get item
+ final EventListItem item = getItem(position);
+
+ if (item.isHeader()) {
+ return TYPE_HEADER;
+ }
+ return TYPE_ITEM;
+ }
+
+ private boolean canReuseConvertView(View convertView, int itemViewType){
+ if(convertView == null){
+ return false;
+ }
+ Object o = convertView.getTag();
+ if(itemViewType == TYPE_ITEM){
+ return o instanceof EventListItemHolder;
+ }
+
+ if(itemViewType == TYPE_HEADER){
+ return o instanceof de.bjusystems.vdrmanager.gui.EventAdapter.EventListItemHeaderHolder;
+ }
+
+ return false;
+
+ }
+
+ @Override
+ public View getView(final int position, View convertView,
+ final ViewGroup parent) {
+
+ // get item
+ final EventListItem item = getItem(position);
+
+ Object holder = null;
+ int type = getItemViewType(position);
+ if (canReuseConvertView(convertView, type) == false) {
+ switch (type) {
+ case TYPE_ITEM:
+ convertView = inflater.inflate(layout, null);
+ holder = getEventViewHolder(item, convertView);
+ break;
+ case TYPE_HEADER:
+ convertView = inflater.inflate(R.layout.header_item, null);
+ holder = getHeaderViewHolder(item, convertView);
+ break;
+ }
+ convertView.setTag(holder);
+ } else {
+ holder = convertView.getTag();
+ }
+
+ if (type == TYPE_ITEM) {
+ fillEventViewHolder((EventListItemHolder) holder, item);
+ } else {
+ ((EventListItemHeaderHolder) holder).header.setText(item
+ .getHeader());
+ }
+ return convertView;
+ }
+
+ protected EventListItemHolder getEventViewHolder(EventListItem item, View view) {
+
+ EventListItemHolder itemHolder = new EventListItemHolder();
+
+ itemHolder = new EventListItemHolder();
+
+ itemHolder.state = (ImageView) view.findViewById(R.id.timer_item_state);
+ itemHolder.time = (TextView) view.findViewById(R.id.timer_item_time);
+ itemHolder.channel = (TextView) view
+ .findViewById(R.id.timer_item_channel);
+ itemHolder.title = (TextView) view.findViewById(R.id.timer_item_title);
+ itemHolder.progress = (ProgressBar) view
+ .findViewById(R.id.timer_progress);
+ itemHolder.shortText = (TextView) view
+ .findViewById(R.id.timer_item_shorttext);
+ itemHolder.duration = (TextView) view
+ .findViewById(R.id.timer_item_duration);
+ itemHolder.description = (TextView) view
+ .findViewById(R.id.event_item_description);
+ return itemHolder;
+ }
+
+ public void fillEventViewHolder(EventListItemHolder itemHolder,
+ EventListItem item) {
+
+ itemHolder.state.setVisibility(View.VISIBLE);
+
+ if (item.getEvent() instanceof Recording) {
+ Recording r = (Recording) item.getEvent();
+ if (r.getTimerStopTime() != null) {
+ itemHolder.state.setImageResource(R.drawable.timer_recording);
+ }
+ } else if (item.getEvent() instanceof Timerable == true) {
+ TimerMatch match = ((Timerable) item.getEvent()).getTimerMatch();
+ switch (((Timerable) item.getEvent()).getTimerState()) {
+ case Active:
+ itemHolder.state.setImageResource(Utils.getTimerStateDrawable(
+ match, R.drawable.timer_active,
+ R.drawable.timer_active_begin,
+ R.drawable.timer_active_end));
+ break;
+ case Inactive:
+ itemHolder.state.setImageResource(Utils.getTimerStateDrawable(
+ match, R.drawable.timer_inactive,
+ R.drawable.timer_inactive_begin,
+ R.drawable.timer_inactive_end));
+ break;
+ case Recording:
+ itemHolder.state.setImageResource(Utils.getTimerStateDrawable(
+ match, R.drawable.timer_recording,
+ R.drawable.timer_recording_begin,
+ R.drawable.timer_recording_end));
+ break;
+ case None:
+ itemHolder.state.setImageResource(R.drawable.timer_none);
+ break;
+ }
+ } else {
+ itemHolder.state.setImageResource(R.drawable.timer_none);
+ }
+
+ final EventFormatter formatter = getEventFormatter(item);
+ itemHolder.time.setText(formatter.getTime());
+ if (hideChannelName) {
+ itemHolder.channel.setVisibility(View.GONE);
+ } else {
+ itemHolder.channel.setText(item.getChannelName());
+ }
+
+ CharSequence title = Utils.highlight(formatter.getTitle(), highlight);
+ CharSequence shortText = Utils.highlight(formatter.getShortText(),
+ highlight);
+ itemHolder.title.setText(title);
+ itemHolder.shortText.setText(shortText);
+
+ if (hideDescription == false) {
+ Pair<Boolean, CharSequence> desc = Utils.highlight2(
+ formatter.getDescription(), highlight);
+ if (desc.first == true) {
+ itemHolder.description.setVisibility(View.VISIBLE);
+ itemHolder.description.setText(desc.second);
+ }
+ }
+
+ // TODO better render of duration
+ int p = Utils.getProgress(item.getEvent());
+ if (p == -1) {
+ itemHolder.progress.setVisibility(View.GONE);
+ int dura = Utils.getDuration(item);
+ itemHolder.duration.setText(getContext().getString(
+ R.string.epg_duration_template, dura));
+ } else {
+ itemHolder.progress.setVisibility(View.VISIBLE);
+ itemHolder.progress.setProgress(p);
+ int dura = Utils.getDuration(item.getEvent());
+ int rest = dura - (dura * p / 100);
+ // on live recordings the amount of already recorded time
+ if (item.getEvent() instanceof Recording) {
+ rest = dura - rest;
+ }
+ itemHolder.duration.setText(getContext().getString(
+ R.string.epg_duration_template_live, rest, dura));
+ }
+ }
+
+ class EventListItemHeaderHolder {
+ public TextView header;
+ }
+
+
+ protected EventListItemHeaderHolder getHeaderViewHolder(EventListItem item,
+ View view) {
+ EventListItemHeaderHolder itemHolder = new EventListItemHeaderHolder();
+ itemHolder.header = (TextView) view.findViewById(R.id.header_item);
+ return itemHolder;
+ }
+
+ protected EventFormatter getEventFormatter(Event event) {
+ return new EventFormatter(event);
+ }
+
+ protected void addSuper(T item) {
+ super.add(item);
+ }
+
+ protected void clearSuper() {
+ super.clear();
+ }
+
+ public boolean isHideDescription() {
+ return hideDescription;
+ }
+
+ public void setHideDescription(boolean hideDescription) {
+ this.hideDescription = hideDescription;
+ }
+
+ public boolean isHideChannelName() {
+ return hideChannelName;
+ }
+
+ public void setHideChannelName(boolean hideChannelName) {
+ this.hideChannelName = hideChannelName;
+ }
+
+ // TODO implement locking in performFiltering, check the parent class
+ // http://stackoverflow.com/questions/5846385/how-to-update-android-listview-with-dynamic-data-in-real-time
+ public Filter getFilter() {
+ return new Filter() {
+ /**
+ *
+ */
+ EventListItem prevHead = null;
+
+ @Override
+ protected FilterResults performFiltering(CharSequence arg0) {
+ highlight = arg0.toString().toLowerCase();
+ ArrayList<EventListItem> result = new ArrayList<EventListItem>();
+ for (EventListItem event : items) {
+ if (event.isHeader()) {
+ prevHead = event;
+ // result.add(event);
+ continue;
+ }
+ if (event.getTitle().toLowerCase()
+ .indexOf(String.valueOf(arg0).toLowerCase()) != -1
+ || event.getShortText()
+ .toLowerCase()
+ .indexOf(String.valueOf(arg0).toLowerCase()) != -1) {
+ if (prevHead != null) {
+ result.add(prevHead);
+ prevHead = null;
+ }
+ result.add(event);
+ }
+ }
+
+ FilterResults fr = new FilterResults();
+ fr.count = result.size();
+ fr.values = result;
+ return fr;
+ }
+
+ @Override
+ protected void publishResults(CharSequence arg0, FilterResults arg1) {
+ clearSuper();
+ for (T item : (ArrayList<T>) arg1.values) {
+ addSuper(item);
+ }
+ notifyDataSetChanged();
+ }
+ };
+ }
+
+ // @Override
+ // public int getPositionForSection(int section) {
+ // return 0;
+ // }
+
+ // @Override
+ // public int getSectionForPosition(int position) {
+ // TODO Auto-generated method stub
+ // return 0;
+ // }
+
+ // ArrayList<String> sections = new ArrayList<String>();
+
+ // @Override
+ // public Object[] getSections() {
+ // try {
+ // return sections.toArray();
+ // } finally {
+ // sections.clear();
+ // }
+ // }
+
+ @Override
+ public void clear() {
+ super.clear();
+ items.clear();
+ }
+}
diff --git a/vdrmanager/src/de/bjusystems/vdrmanager/gui/BaseEventListActivity.java b/vdrmanager/src/de/bjusystems/vdrmanager/gui/BaseEventListActivity.java
index be1e17d..8463063 100644
--- a/vdrmanager/src/de/bjusystems/vdrmanager/gui/BaseEventListActivity.java
+++ b/vdrmanager/src/de/bjusystems/vdrmanager/gui/BaseEventListActivity.java
@@ -51,7 +51,7 @@ public abstract class BaseEventListActivity<T extends Event> extends
private SimpleGestureFilter detector;
- protected EventAdapter adapter;
+ protected BaseEventAdapter<EventListItem> adapter;
protected String highlight = null;
diff --git a/vdrmanager/src/de/bjusystems/vdrmanager/gui/ChannelEventAdapter.java b/vdrmanager/src/de/bjusystems/vdrmanager/gui/ChannelEventAdapter.java
index 7e3d575..475f3e6 100644
--- a/vdrmanager/src/de/bjusystems/vdrmanager/gui/ChannelEventAdapter.java
+++ b/vdrmanager/src/de/bjusystems/vdrmanager/gui/ChannelEventAdapter.java
@@ -4,16 +4,17 @@ import android.content.Context;
import de.bjusystems.vdrmanager.R;
import de.bjusystems.vdrmanager.data.Event;
import de.bjusystems.vdrmanager.data.EventFormatter;
+import de.bjusystems.vdrmanager.data.EventListItem;
-class ChannelEventAdapter extends EventAdapter
+class ChannelEventAdapter extends BaseEventAdapter<EventListItem>
{
-
+
public ChannelEventAdapter(final Context context) {
super(context, R.layout.epg_event_item);
hideChannelName = true;
}
-
+
@Override
protected EventFormatter getEventFormatter(Event event) {
return new EventFormatter(event,true);
diff --git a/vdrmanager/src/de/bjusystems/vdrmanager/gui/RecordingAdapter.java b/vdrmanager/src/de/bjusystems/vdrmanager/gui/RecordingAdapter.java
index 3645596..d2fed1f 100644
--- a/vdrmanager/src/de/bjusystems/vdrmanager/gui/RecordingAdapter.java
+++ b/vdrmanager/src/de/bjusystems/vdrmanager/gui/RecordingAdapter.java
@@ -1,13 +1,19 @@
package de.bjusystems.vdrmanager.gui;
import android.content.Context;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.TextView;
import de.bjusystems.vdrmanager.R;
import de.bjusystems.vdrmanager.data.Event;
import de.bjusystems.vdrmanager.data.EventFormatter;
+import de.bjusystems.vdrmanager.data.EventListItem;
+import de.bjusystems.vdrmanager.data.RecordingListItem;
-class RecordingAdapter extends EventAdapter
-{
+class RecordingAdapter extends BaseEventAdapter<EventListItem> {
+
+ protected final static int TYPE_FOLDER = 2;
public RecordingAdapter(final Context context) {
super(context, R.layout.epg_event_item);
@@ -16,8 +22,77 @@ class RecordingAdapter extends EventAdapter
@Override
protected EventFormatter getEventFormatter(Event event) {
- return new EventFormatter(event, true);
+ return new EventFormatter(event, true);
+ }
+
+ @Override
+ public int getViewTypeCount() {
+ return 3;
+ }
+
+ @Override
+ public void add(EventListItem object) {
+ items.add(object);
+ // if (object.isHeader()) {
+ // sections.add(object.getHeader());
+ // }
+ super.add(object);
}
+ @Override
+ public int getItemViewType(int position) {
+
+ // get item
+ final RecordingListItem item = (RecordingListItem) getItem(position);
+
+ if (item.isHeader()) {
+ return TYPE_HEADER;
+ } else if (item.isFolder()) {
+ return TYPE_FOLDER;
+ }
+ return TYPE_ITEM;
+ }
+
+
+ class EventListItemFolderHolder {
+ public TextView folder;
+ }
+
+ protected EventListItemFolderHolder getFolderViewHolder(EventListItem item,
+ View view) {
+ EventListItemFolderHolder itemHolder = new EventListItemFolderHolder();
+ itemHolder.folder = (TextView) view.findViewById(R.id.header_item);
+ return itemHolder;
+ }
+
+
+ @Override
+ public View getView(final int position, View convertView,
+ final ViewGroup parent) {
+
+ // get item
+ final RecordingListItem item = (RecordingListItem) getItem(position);
+
+ if (item.isFolder() == false) {
+ return super.getView(position, convertView, parent);
+ }
+
+ Object holder = null;
+ if (convertView == null || (convertView != null && convertView.getTag() instanceof EventListItemFolderHolder) == false) {
+ convertView = inflater.inflate(R.layout.folder_item, null);
+ holder = getHeaderViewHolder(item, convertView);
+ convertView.setTag(holder);
+ } else {
+ holder = convertView.getTag();
+ }
+
+ ((EventListItemHeaderHolder) holder).header.setText(item.getHeader());
+ return convertView;
+ }
+
+ @Override
+ public RecordingListItem getItem(int position) {
+ return (RecordingListItem) super.getItem(position);
+ }
} \ No newline at end of file
diff --git a/vdrmanager/src/de/bjusystems/vdrmanager/gui/RecordingListActivity.java b/vdrmanager/src/de/bjusystems/vdrmanager/gui/RecordingListActivity.java
index 27ec91b..d3cb81a 100644
--- a/vdrmanager/src/de/bjusystems/vdrmanager/gui/RecordingListActivity.java
+++ b/vdrmanager/src/de/bjusystems/vdrmanager/gui/RecordingListActivity.java
@@ -4,6 +4,11 @@ import java.util.ArrayList;
import java.util.Calendar;
import java.util.Collections;
import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.Stack;
+import java.util.TreeMap;
+import java.util.TreeSet;
import android.os.Bundle;
import android.view.ContextMenu;
@@ -20,6 +25,8 @@ import de.bjusystems.vdrmanager.data.EventFormatter;
import de.bjusystems.vdrmanager.data.EventListItem;
import de.bjusystems.vdrmanager.data.Preferences;
import de.bjusystems.vdrmanager.data.Recording;
+import de.bjusystems.vdrmanager.data.RecordingListItem;
+import de.bjusystems.vdrmanager.data.Recording.Folder;
import de.bjusystems.vdrmanager.tasks.DeleteRecordingTask;
import de.bjusystems.vdrmanager.utils.date.DateFormatter;
import de.bjusystems.vdrmanager.utils.svdrp.RecordingClient;
@@ -35,24 +42,33 @@ import de.bjusystems.vdrmanager.utils.svdrp.SvdrpEvent;
public class RecordingListActivity extends BaseEventListActivity<Recording>
implements OnItemLongClickListener {
- //RecordingClient recordingClient;
+ // RecordingClient recordingClient;
- //public static final int MENU_GROUP_CHANNEL = 2;
+ // public static final int MENU_GROUP_CHANNEL = 2;
public static final int ASC = 0;
public static final int DESC = 1;
- protected static ArrayList<Recording> CACHE = new ArrayList<Recording>();
+ // protected static ArrayList<Recording> CACHE = new ArrayList<Recording>();
+ private static Map<String, List<Recording>> CACHE = new TreeMap<String, List<Recording>>();
+
+ public static final Map<String, Set<String>> FOLDERS = new TreeMap<String, Set<String>>();
+
+ private String currentFolder = Recording.ROOT_FOLDER;
private int ASC_DESC = ASC;
+ private static final List<Recording> EMPTY = new ArrayList<Recording>(0);
+
+ private Stack<String> stack = new Stack<String>();
+
@Override
protected void onCreate(final Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
- // create an adapter
+
adapter = new RecordingAdapter(this);
// attach adapter to ListView
@@ -115,6 +131,25 @@ public class RecordingListActivity extends BaseEventListActivity<Recording>
// }
// }
+ @Override
+ public void onItemClick(AdapterView<?> parent, View view, int position,
+ long id) {
+
+ final RecordingListItem item = (RecordingListItem) adapter
+ .getItem(position);
+ if (item.isFolder()) {
+ if(currentFolder.equals(Recording.ROOT_FOLDER)){
+ currentFolder = item.folder;
+ } else {
+ currentFolder = currentFolder + Recording.FOLDERDELIMCHAR + item.folder;
+ }
+ stack.push(currentFolder);
+ fillAdapter();
+ } else {
+ super.onItemClick(parent, view, position, id);
+ }
+ }
+
/*
* (non-Javadoc)
*
@@ -138,7 +173,7 @@ public class RecordingListActivity extends BaseEventListActivity<Recording>
@Override
protected void prepareDetailsViewData(EventListItem event) {
getApp().setCurrentEvent(event.getEvent());
- getApp().setCurrentEpgList(CACHE);
+ getApp().setCurrentEpgList(CACHE.get(currentFolder));
}
@Override
@@ -167,9 +202,9 @@ public class RecordingListActivity extends BaseEventListActivity<Recording>
super.onCreateContextMenu(menu, v, menuInfo);
//
// http://projects.vdr-developer.org/issues/863
- //if (Utils.isLive(item)) {
- menu.removeItem(R.id.epg_item_menu_live_tv);
- //}
+ // if (Utils.isLive(item)) {
+ menu.removeItem(R.id.epg_item_menu_live_tv);
+ // }
}
@Override
@@ -212,7 +247,7 @@ public class RecordingListActivity extends BaseEventListActivity<Recording>
}
// get timer client
- RecordingClient recordingClient = new RecordingClient();
+ RecordingClient recordingClient = new RecordingClient();
// create backgound task
final SvdrpAsyncTask<Recording, SvdrpClient<Recording>> task = new SvdrpAsyncTask<Recording, SvdrpClient<Recording>>(
@@ -248,16 +283,16 @@ public class RecordingListActivity extends BaseEventListActivity<Recording>
/* */
switch (sortBy) {
case MENU_GROUP_DEFAULT: {
- sortItemsByTime(CACHE, true);
+ sortItemsByTime(CACHE.get(currentFolder), true);
break;
}
case MENU_GROUP_ALPHABET: {
- Collections.sort(CACHE, new TitleComparator());
+ Collections.sort(CACHE.get(currentFolder), new TitleComparator());
break;
}
- //case MENU_GROUP_CHANNEL: {
- //sortItemsByChannel(results);
- //}
+ // case MENU_GROUP_CHANNEL: {
+ // sortItemsByChannel(results);
+ // }
}
}
@@ -265,8 +300,8 @@ public class RecordingListActivity extends BaseEventListActivity<Recording>
protected void fillAdapter() {
adapter.clear();
-
- if (CACHE.isEmpty()) {
+ List<Recording> list = CACHE.get(currentFolder);
+ if (list == null || list.isEmpty()) {
return;
}
@@ -275,30 +310,95 @@ public class RecordingListActivity extends BaseEventListActivity<Recording>
Calendar cal = Calendar.getInstance();
int day = -1;
- for (final Event rec : CACHE) {
+ Set<String> folders = FOLDERS.get(currentFolder);
+ if (folders != null) {
+ for (String f : folders) {
+ RecordingListItem recordingListItem = new RecordingListItem(f);
+ recordingListItem.folder = f;
+ adapter.add(recordingListItem);
+ }
+ }
+
+ for (final Event rec : CACHE.get(currentFolder)) {
cal.setTime(rec.getStart());
int eday = cal.get(Calendar.DAY_OF_YEAR);
if (eday != day) {
day = eday;
- adapter.add(new EventListItem(new DateFormatter(cal)
+ adapter.add(new RecordingListItem(new DateFormatter(cal)
.getDailyHeader()));
}
- adapter.add(new EventListItem((Recording) rec));
+ adapter.add(new RecordingListItem((Recording) rec));
adapter.notifyDataSetChanged();
}
}
@Override
+ public void onBackPressed() {
+ if (stack.isEmpty()) {
+ super.onBackPressed();
+ } else {
+ stack.pop();
+ if (stack.isEmpty()) {
+ currentFolder = "";
+ } else {
+ currentFolder = stack.peek();
+ }
+ fillAdapter();
+ }
+
+ }
+
+ @Override
protected boolean finishedSuccessImpl(List<Recording> results) {
clearCache();
- for(Recording r :results){
- CACHE.add(r);
+ for (Recording r : results) {
+ String folder = r.getFolder();
+ if (folder.length() > 0) {
+ String[] split = folder.split(Recording.FOLDERDELIMCHAR);
+ String key = null;
+ String value = null;
+ if(split.length == 1){
+ key = Recording.ROOT_FOLDER ;
+ value = split[0];
+ } else {
+ value = split[split.length - 1];
+ //StringBuilder sb = new StringBuilder();
+ //String sep = "";
+ //for(int i = 0; i < split.length - 1; ++i){
+ //sb.append(sep).append(split[i]);
+ //sep = Recording.FOLDERDELIMCHAR;
+ //}
+ key = folder.subSequence(0, folder.length() - (value.length()+1) ).toString();
+
+ }
+
+ Set<String> list = FOLDERS.get(key);
+ if(list == null){
+ list = new TreeSet<String>();
+ FOLDERS.put(key, list);
+ }
+
+ list.add(value);
+
+ //a b
+ //a
+ //c
+ //a~b > k
+
+
+ }
+ List<Recording> list = CACHE.get(folder);
+ if (list == null) {
+ list = new ArrayList<Recording>();
+ CACHE.put(folder, list);
+ }
+ list.add(r);
}
+
pushResultCountToTitle();
fillAdapter();
return adapter.isEmpty() == false;
-
}
public boolean onItemLongClick(AdapterView<?> arg0, View arg1, int arg2,
@@ -312,9 +412,20 @@ public class RecordingListActivity extends BaseEventListActivity<Recording>
return LIST_NAVIGATION_RECORDINGS;
}
+ public void clearCache() {
+ CACHE.clear();
+ FOLDERS.clear();
+ }
+
@Override
protected List<Recording> getCACHE() {
- return CACHE;
+
+ List<Recording> list = CACHE.get(currentFolder);
+
+ if (list != null) {
+ return list;
+ }
+ return EMPTY;
}
}
diff --git a/vdrmanager/src/de/bjusystems/vdrmanager/gui/TimeEventAdapter.java b/vdrmanager/src/de/bjusystems/vdrmanager/gui/TimeEventAdapter.java
index dc7545e..f5cca64 100644
--- a/vdrmanager/src/de/bjusystems/vdrmanager/gui/TimeEventAdapter.java
+++ b/vdrmanager/src/de/bjusystems/vdrmanager/gui/TimeEventAdapter.java
@@ -4,8 +4,9 @@ import android.content.Context;
import de.bjusystems.vdrmanager.R;
import de.bjusystems.vdrmanager.data.Event;
import de.bjusystems.vdrmanager.data.EventFormatter;
+import de.bjusystems.vdrmanager.data.EventListItem;
-public class TimeEventAdapter extends EventAdapter {
+public class TimeEventAdapter extends BaseEventAdapter<EventListItem> {
public TimeEventAdapter(final Context context) {
super(context, R.layout.epg_event_item);