Merge pull request #1104 from BrianBlade/feature/swipe_out_conversation

Enable end-conversation by swipe gesture
This commit is contained in:
Daniel Gultsch 2015-04-09 10:46:26 +02:00
commit f880473435
9 changed files with 185 additions and 71 deletions

View file

@ -34,6 +34,7 @@ dependencies {
compile 'com.google.zxing:core:3.1.0' compile 'com.google.zxing:core:3.1.0'
compile 'com.google.zxing:android-integration:3.1.0' compile 'com.google.zxing:android-integration:3.1.0'
compile 'de.measite.minidns:minidns:0.1.3' compile 'de.measite.minidns:minidns:0.1.3'
compile 'de.timroes.android:EnhancedListView:0.3.4'
} }
android { android {

View file

@ -1129,6 +1129,7 @@ public class XmppConnectionService extends Service implements OnPhoneContactsLoa
} }
public void archiveConversation(Conversation conversation) { public void archiveConversation(Conversation conversation) {
getNotificationService().clear(conversation);
conversation.setStatus(Conversation.STATUS_ARCHIVED); conversation.setStatus(Conversation.STATUS_ARCHIVED);
conversation.setNextEncryption(-1); conversation.setNextEncryption(-1);
synchronized (this.conversations) { synchronized (this.conversations) {

View file

@ -22,12 +22,12 @@ import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener; import android.widget.AdapterView.OnItemClickListener;
import android.widget.ArrayAdapter; import android.widget.ArrayAdapter;
import android.widget.CheckBox; import android.widget.CheckBox;
import android.widget.ListView;
import android.widget.PopupMenu; import android.widget.PopupMenu;
import android.widget.PopupMenu.OnMenuItemClickListener; import android.widget.PopupMenu.OnMenuItemClickListener;
import android.widget.Toast; import android.widget.Toast;
import net.java.otr4j.session.SessionStatus; import net.java.otr4j.session.SessionStatus;
import de.timroes.android.listview.EnhancedListView;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
@ -76,8 +76,9 @@ public class ConversationActivity extends XmppActivity
private View mContentView; private View mContentView;
private List<Conversation> conversationList = new ArrayList<>(); private List<Conversation> conversationList = new ArrayList<>();
private Conversation swipedConversation = null;
private Conversation mSelectedConversation = null; private Conversation mSelectedConversation = null;
private ListView listView; private EnhancedListView listView;
private ConversationFragment mConversationFragment; private ConversationFragment mConversationFragment;
private ArrayAdapter<Conversation> listAdapter; private ArrayAdapter<Conversation> listAdapter;
@ -156,7 +157,7 @@ public class ConversationActivity extends XmppActivity
transaction.replace(R.id.selected_conversation, this.mConversationFragment, "conversation"); transaction.replace(R.id.selected_conversation, this.mConversationFragment, "conversation");
transaction.commit(); transaction.commit();
listView = (ListView) findViewById(R.id.list); listView = (EnhancedListView) findViewById(R.id.list);
this.listAdapter = new ConversationAdapter(this, conversationList); this.listAdapter = new ConversationAdapter(this, conversationList);
listView.setAdapter(this.listAdapter); listView.setAdapter(this.listAdapter);
@ -178,6 +179,73 @@ public class ConversationActivity extends XmppActivity
openConversation(); openConversation();
} }
}); });
listView.setDismissCallback(new EnhancedListView.OnDismissCallback() {
@Override
public EnhancedListView.Undoable onDismiss(final EnhancedListView enhancedListView, final int position) {
final int index = listView.getFirstVisiblePosition();
View v = listView.getChildAt(0);
final int top = (v == null) ? 0 : (v.getTop() - listView.getPaddingTop());
swipedConversation = listAdapter.getItem(position);
listAdapter.remove(swipedConversation);
swipedConversation.markRead();
xmppConnectionService.getNotificationService().clear(swipedConversation);
final boolean formerlySelected = (getSelectedConversation() == swipedConversation);
if (position == 0 && listAdapter.getCount() == 0) {
endConversation(swipedConversation, false, true);
return null;
} else if (formerlySelected) {
setSelectedConversation(listAdapter.getItem(0));
ConversationActivity.this.mConversationFragment
.reInit(getSelectedConversation());
}
return new EnhancedListView.Undoable() {
@Override
public void undo() {
listAdapter.insert(swipedConversation, position);
if (formerlySelected) {
setSelectedConversation(swipedConversation);
ConversationActivity.this.mConversationFragment
.reInit(getSelectedConversation());
}
swipedConversation = null;
listView.setSelectionFromTop(index + (listView.getChildCount() < position ? 1 : 0), top);
}
@Override
public void discard() {
if (!swipedConversation.isRead()
&& swipedConversation.getMode() == Conversation.MODE_SINGLE) {
swipedConversation = null;
return;
}
endConversation(swipedConversation, false, false);
swipedConversation = null;
}
@Override
public String getTitle() {
if (swipedConversation.getMode() == Conversation.MODE_MULTI) {
return getResources().getString(R.string.title_undo_swipe_out_muc);
} else {
return getResources().getString(R.string.title_undo_swipe_out_conversation);
}
}
};
}
});
listView.enableSwipeToDismiss();
listView.setSwipingLayout(R.id.swipeable_item);
listView.setUndoStyle(EnhancedListView.UndoStyle.SINGLE_POPUP);
listView.setUndoHideDelay(3000);
listView.setRequireTouchBeforeDismiss(false);
mContentView = findViewById(R.id.content_view_spl); mContentView = findViewById(R.id.content_view_spl);
if (mContentView == null) { if (mContentView == null) {
mContentView = findViewById(R.id.content_view_ll); mContentView = findViewById(R.id.content_view_ll);
@ -204,6 +272,7 @@ public class ConversationActivity extends XmppActivity
@Override @Override
public void onPanelClosed(View arg0) { public void onPanelClosed(View arg0) {
listView.discardUndo();
openConversation(); openConversation();
} }
@ -485,8 +554,15 @@ public class ConversationActivity extends XmppActivity
} }
public void endConversation(Conversation conversation) { public void endConversation(Conversation conversation) {
endConversation(conversation, true, true);
}
public void endConversation(Conversation conversation, boolean showOverview, boolean reinit) {
if (showOverview) {
showConversationsOverview(); showConversationsOverview();
}
xmppConnectionService.archiveConversation(conversation); xmppConnectionService.archiveConversation(conversation);
if (reinit) {
if (conversationList.size() > 0) { if (conversationList.size() > 0) {
setSelectedConversation(conversationList.get(0)); setSelectedConversation(conversationList.get(0));
this.mConversationFragment.reInit(getSelectedConversation()); this.mConversationFragment.reInit(getSelectedConversation());
@ -494,6 +570,7 @@ public class ConversationActivity extends XmppActivity
setSelectedConversation(null); setSelectedConversation(null);
} }
} }
}
@SuppressLint("InflateParams") @SuppressLint("InflateParams")
protected void clearHistoryDialog(final Conversation conversation) { protected void clearHistoryDialog(final Conversation conversation) {
@ -744,6 +821,7 @@ public class ConversationActivity extends XmppActivity
@Override @Override
public void onPause() { public void onPause() {
listView.discardUndo();
super.onPause(); super.onPause();
this.mActivityPaused = true; this.mActivityPaused = true;
if (this.xmppConnectionServiceBound) { if (this.xmppConnectionServiceBound) {
@ -1013,6 +1091,13 @@ public class ConversationActivity extends XmppActivity
public void updateConversationList() { public void updateConversationList() {
xmppConnectionService xmppConnectionService
.populateWithOrderedConversations(conversationList); .populateWithOrderedConversations(conversationList);
if (swipedConversation != null) {
if (swipedConversation.isRead()) {
conversationList.remove(swipedConversation);
} else {
listView.discardUndo();
}
}
listAdapter.notifyDataSetChanged(); listAdapter.notifyDataSetChanged();
} }

View file

@ -12,7 +12,7 @@
android:background="@color/primarybackground" android:background="@color/primarybackground"
android:orientation="vertical" > android:orientation="vertical" >
<ListView <de.timroes.android.listview.EnhancedListView
android:id="@+id/list" android:id="@+id/list"
android:layout_width="fill_parent" android:layout_width="fill_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"

View file

@ -1,6 +1,23 @@
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent" android:layout_width="fill_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:descendantFocusability="blocksDescendants">
<View
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:background="@color/divider"/>
<FrameLayout
android:id="@+id/swipeable_item"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:background="@color/primarybackground">
<RelativeLayout
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:background="?android:selectableItemBackground"
android:orientation="horizontal" android:orientation="horizontal"
android:padding="8dp" > android:padding="8dp" >
@ -64,5 +81,6 @@
android:textColor="@color/secondarytext" android:textColor="@color/secondarytext"
android:textSize="?attr/TextSizeInfo" /> android:textSize="?attr/TextSizeInfo" />
</RelativeLayout> </RelativeLayout>
</RelativeLayout> </RelativeLayout>
</FrameLayout>
</FrameLayout>

View file

@ -10,7 +10,7 @@
android:background="@color/primarybackground" android:background="@color/primarybackground"
android:orientation="vertical" > android:orientation="vertical" >
<ListView <de.timroes.android.listview.EnhancedListView
android:id="@+id/list" android:id="@+id/list"
android:layout_width="fill_parent" android:layout_width="fill_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"

View file

@ -427,6 +427,8 @@
<string name="no_application_found_to_display_location">Keine App für die Standort-Anzeige gefunden</string> <string name="no_application_found_to_display_location">Keine App für die Standort-Anzeige gefunden</string>
<string name="location">Standort</string> <string name="location">Standort</string>
<string name="received_location">Standort empfangen</string> <string name="received_location">Standort empfangen</string>
<string name="title_undo_swipe_out_conversation">Unterhaltung beendet</string>
<string name="title_undo_swipe_out_muc">Konferenz verlassen</string>
<plurals name="select_contact"> <plurals name="select_contact">
<item quantity="one">%d Kontakt ausgewählt</item> <item quantity="one">%d Kontakt ausgewählt</item>
<item quantity="other">%d Kontakte ausgewählt</item> <item quantity="other">%d Kontakte ausgewählt</item>

View file

@ -0,0 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<resources>
<dimen name="elv_undo_bottom_offset">63dp</dimen> <!-- 48dp + 15dp -->
</resources>

View file

@ -296,6 +296,7 @@
\n\nhttps://developer.android.com/tools/support-library\n(Apache License, Version 2.0) \n\nhttps://developer.android.com/tools/support-library\n(Apache License, Version 2.0)
\n\nhttps://github.com/zxing/zxing\n(Apache License, Version 2.0) \n\nhttps://github.com/zxing/zxing\n(Apache License, Version 2.0)
\n\nhttps://github.com/google/material-design-icons\n(CC BY 4.0) \n\nhttps://github.com/google/material-design-icons\n(CC BY 4.0)
\n\nhttps://github.com/timroes/EnhancedListView\n(Apache License, Version 2.0)
</string> </string>
<string name="title_pref_quiet_hours">Quiet Hours</string> <string name="title_pref_quiet_hours">Quiet Hours</string>
<string name="title_pref_quiet_hours_start_time">Start time</string> <string name="title_pref_quiet_hours_start_time">Start time</string>
@ -454,6 +455,8 @@
<string name="no_application_found_to_display_location">No application found to display location</string> <string name="no_application_found_to_display_location">No application found to display location</string>
<string name="location">Location</string> <string name="location">Location</string>
<string name="received_location">Received location</string> <string name="received_location">Received location</string>
<string name="title_undo_swipe_out_conversation">Conversation closed</string>
<string name="title_undo_swipe_out_muc">Left conference</string>
<plurals name="select_contact"> <plurals name="select_contact">
<item quantity="one">Select %d contact</item> <item quantity="one">Select %d contact</item>
<item quantity="other">Select %d contacts</item> <item quantity="other">Select %d contacts</item>