Changes to temporarily keep both chat bubbles designs

This commit is contained in:
Sylvain Berfini 2018-11-27 15:33:39 +01:00
parent c1c6915481
commit b194374bff
12 changed files with 773 additions and 47 deletions

View file

@ -66,6 +66,8 @@ import org.linphone.LinphoneManager.AddressType;
import org.linphone.chat.ChatMessagesFragment;
import org.linphone.chat.ChatRoomCreationFragment;
import org.linphone.chat.ChatRoomsFragment;
import org.linphone.chat.ImdnFragment;
import org.linphone.chat.ImdnOldFragment;
import org.linphone.settings.LinphonePreferences;
import org.linphone.assistant.AssistantActivity;
import org.linphone.assistant.RemoteProvisioningLoginActivity;
@ -74,7 +76,6 @@ import org.linphone.call.CallIncomingActivity;
import org.linphone.call.CallOutgoingActivity;
import org.linphone.chat.DevicesFragment;
import org.linphone.chat.GroupInfoFragment;
import org.linphone.chat.ImdnFragment;
import org.linphone.compatibility.Compatibility;
import org.linphone.contacts.ContactAddress;
import org.linphone.contacts.ContactDetailsFragment;
@ -423,7 +424,11 @@ public class LinphoneActivity extends LinphoneGenericActivity implements OnClick
fragment = new ChatMessagesFragment();
break;
case MESSAGE_IMDN:
fragment = new ImdnFragment();
if (getResources().getBoolean(R.bool.use_new_chat_bubbles_layout)) {
fragment = new ImdnFragment();
} else {
fragment = new ImdnOldFragment();
}
break;
case CONTACT_DEVICES:
fragment = new DevicesFragment();

View file

@ -1,3 +1,5 @@
package org.linphone.chat;
/*
ChatMessageViewHolder.java
Copyright (C) 2017 Belledonne Communications, Grenoble, France
@ -17,10 +19,9 @@ along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
package org.linphone.chat;
import android.content.Context;
import android.support.v7.widget.RecyclerView;
import androidx.recyclerview.widget.RecyclerView;
import android.view.View;
import android.widget.Button;
import android.widget.CheckBox;
@ -63,9 +64,9 @@ public class ChatMessageOldViewHolder extends RecyclerView.ViewHolder implements
public Button openFileButton;
public CheckBox delete;
private ClickListener mListener;
private ChatMessageViewHolderClickListener mListener;
public ChatMessageOldViewHolder(Context context, View view, ClickListener listener) {
public ChatMessageOldViewHolder(Context context, View view, ChatMessageViewHolderClickListener listener) {
this(view);
mContext = context;
mListener = listener;
@ -109,8 +110,4 @@ public class ChatMessageOldViewHolder extends RecyclerView.ViewHolder implements
mListener.onItemClicked(getAdapterPosition());
}
}
public interface ClickListener {
void onItemClicked(int position);
}
}

View file

@ -91,9 +91,9 @@ public class ChatMessageViewHolder extends RecyclerView.ViewHolder implements Vi
public CheckBox deleteEvent;
public CheckBox deleteMessage;
private ClickListener mListener;
private ChatMessageViewHolderClickListener mListener;
public ChatMessageViewHolder(Context context, View view, ClickListener listener) {
public ChatMessageViewHolder(Context context, View view, ChatMessageViewHolderClickListener listener) {
this(view);
mContext = context;
mListener = listener;
@ -131,10 +131,6 @@ public class ChatMessageViewHolder extends RecyclerView.ViewHolder implements Vi
}
}
public interface ClickListener {
void onItemClicked(int position);
}
public void bindMessage(final ChatMessage message, LinphoneContact contact) {
eventLayout.setVisibility(View.GONE);
securityEventLayout.setVisibility(View.GONE);

View file

@ -0,0 +1,24 @@
package org.linphone.chat;
/*
ChatMessageViewHolderClickListener.java
Copyright (C) 2018 Belledonne Communications, Grenoble, France
This program is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 2
of the License, or (at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
public interface ChatMessageViewHolderClickListener {
void onItemClicked(int position);
}

View file

@ -1,3 +1,5 @@
package org.linphone.chat;
/*
ChatMessagesAdapter.java
Copyright (C) 2017 Belledonne Communications, Grenoble, France
@ -17,8 +19,6 @@ along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
package org.linphone.chat;
import android.content.Context;
import androidx.annotation.NonNull;
import android.view.LayoutInflater;
@ -50,9 +50,9 @@ public class ChatMessagesAdapter extends SelectableAdapter<ChatMessageViewHolder
private int mItemResource;
private ChatMessagesFragment mFragment;
private ChatMessageViewHolder.ClickListener mClickListener;
private ChatMessageViewHolderClickListener mClickListener;
public ChatMessagesAdapter(ChatMessagesFragment fragment, SelectableHelper helper, int itemResource, EventLog[] history, ArrayList<LinphoneContact> participants, ChatMessageViewHolder.ClickListener clickListener) {
public ChatMessagesAdapter(ChatMessagesFragment fragment, SelectableHelper helper, int itemResource, EventLog[] history, ArrayList<LinphoneContact> participants, ChatMessageViewHolderClickListener clickListener) {
super(helper);
mFragment = fragment;
mContext = mFragment.getActivity();

View file

@ -1,3 +1,5 @@
package org.linphone.chat;
/*
ChatMessagesFragment.java
Copyright (C) 2017 Belledonne Communications, Grenoble, France
@ -17,8 +19,6 @@ along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
package org.linphone.chat;
import android.app.Activity;
import android.app.Dialog;
import android.app.Fragment;
@ -48,6 +48,7 @@ import android.view.ViewGroup;
import android.view.ViewTreeObserver;
import android.view.WindowManager;
import android.view.inputmethod.InputMethodManager;
import android.widget.Adapter;
import android.widget.Button;
import android.widget.CheckBox;
import android.widget.EditText;
@ -56,7 +57,6 @@ import android.widget.LinearLayout;
import android.widget.TextView;
import org.linphone.LinphoneManager;
import org.linphone.core.ChatMessageListenerStub;
import org.linphone.settings.LinphonePreferences;
import org.linphone.LinphoneService;
import org.linphone.utils.FileUtils;
@ -93,7 +93,7 @@ import java.util.List;
import static android.content.Context.INPUT_METHOD_SERVICE;
import static org.linphone.fragments.FragmentsAvailable.CHAT;
public class ChatMessagesFragment extends Fragment implements ChatRoomListener, ContactsUpdatedListener, ChatMessageViewHolder.ClickListener, SelectableHelper.DeleteListener {
public class ChatMessagesFragment extends Fragment implements ChatRoomListener, ContactsUpdatedListener, ChatMessageViewHolderClickListener, SelectableHelper.DeleteListener {
private static final int ADD_PHOTO = 1337;
private static final int MESSAGES_PER_PAGE = 20;
@ -110,6 +110,7 @@ public class ChatMessagesFragment extends Fragment implements ChatRoomListener,
private ViewTreeObserver.OnGlobalLayoutListener mKeyboardListener;
private Uri mImageToUploadUri;
private ChatMessagesAdapter mEventsAdapter;
private ChatMessagesOldAdapter mOldEventsAdapter;
private String mRemoteSipUri;
private Address mRemoteSipAddress, mRemoteParticipantAddress;
private ChatRoom mChatRoom;
@ -419,8 +420,13 @@ public class ChatMessagesFragment extends Fragment implements ChatRoomListener,
public void onCreateContextMenu(ContextMenu menu, View v, ContextMenu.ContextMenuInfo menuInfo) {
super.onCreateContextMenu(menu, v, menuInfo);
ChatMessageViewHolder holder = (ChatMessageViewHolder) v.getTag();
mContextMenuMessagePosition = holder.getAdapterPosition();
if (mContext.getResources().getBoolean(R.bool.use_new_chat_bubbles_layout)) {
ChatMessageViewHolder holder = (ChatMessageViewHolder) v.getTag();
mContextMenuMessagePosition = holder.getAdapterPosition();
} else {
ChatMessageOldViewHolder holder = (ChatMessageOldViewHolder) v.getTag();
mContextMenuMessagePosition = holder.getAdapterPosition();
}
EventLog event = (EventLog) mEventsAdapter.getItem(mContextMenuMessagePosition);
if (event.getType() != EventLog.Type.ConferenceChatMessage) {
@ -679,11 +685,18 @@ public class ChatMessagesFragment extends Fragment implements ChatRoomListener,
if (mChatRoom == null) return;
if (mChatRoom.hasCapability(ChatRoomCapabilities.OneToOne.toInt())) {
mEventsAdapter = new ChatMessagesAdapter(this, mSelectionHelper, R.layout.chat_bubble, mChatRoom.getHistoryMessageEvents(MESSAGES_PER_PAGE), mParticipants, this);
mOldEventsAdapter = new ChatMessagesOldAdapter(this, mSelectionHelper, R.layout.chat_bubble_old, mChatRoom.getHistoryMessageEvents(MESSAGES_PER_PAGE), mParticipants, this);
} else {
mEventsAdapter = new ChatMessagesAdapter(this, mSelectionHelper, R.layout.chat_bubble, mChatRoom.getHistoryEvents(MESSAGES_PER_PAGE), mParticipants, this);
mOldEventsAdapter = new ChatMessagesOldAdapter(this, mSelectionHelper, R.layout.chat_bubble_old, mChatRoom.getHistoryEvents(MESSAGES_PER_PAGE), mParticipants, this);
}
if (mContext.getResources().getBoolean(R.bool.use_new_chat_bubbles_layout)) {
mSelectionHelper.setAdapter(mEventsAdapter);
mChatEventsList.setAdapter(mEventsAdapter);
} else {
mSelectionHelper.setAdapter(mOldEventsAdapter);
mChatEventsList.setAdapter(mOldEventsAdapter);
}
mSelectionHelper.setAdapter(mEventsAdapter);
mChatEventsList.setAdapter(mEventsAdapter);
scrollToBottom();
}

View file

@ -1,3 +1,5 @@
package org.linphone.chat;
/*
ChatMessagesAdapter.java
Copyright (C) 2017 Belledonne Communications, Grenoble, France
@ -17,8 +19,6 @@ along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
package org.linphone.chat;
import android.Manifest;
import android.content.Context;
import android.content.Intent;
@ -33,8 +33,8 @@ import android.media.ExifInterface;
import android.net.Uri;
import android.os.AsyncTask;
import android.provider.MediaStore;
import android.support.annotation.NonNull;
import android.support.v4.content.FileProvider;
import androidx.annotation.NonNull;
import androidx.core.content.FileProvider;
import android.text.Spanned;
import android.text.method.LinkMovementMethod;
import android.view.LayoutInflater;
@ -74,7 +74,7 @@ import java.util.List;
import static android.content.Intent.FLAG_GRANT_READ_URI_PERMISSION;
public class ChatMessagesOldAdapter extends SelectableAdapter<ChatMessageViewHolder> {
public class ChatMessagesOldAdapter extends SelectableAdapter<ChatMessageOldViewHolder> {
private static int MARGIN_BETWEEN_MESSAGES = 10;
private static int SIDE_MARGIN = 100;
@ -86,9 +86,9 @@ public class ChatMessagesOldAdapter extends SelectableAdapter<ChatMessageViewHol
private ChatMessagesFragment mFragment;
private ChatMessageListenerStub mListener;
private ChatMessageViewHolder.ClickListener mClickListener;
private ChatMessageViewHolderClickListener mClickListener;
public ChatMessagesOldAdapter(ChatMessagesFragment fragment, SelectableHelper helper, int itemResource, EventLog[] history, ArrayList<LinphoneContact> participants, ChatMessageViewHolder.ClickListener clickListener) {
public ChatMessagesOldAdapter(ChatMessagesFragment fragment, SelectableHelper helper, int itemResource, EventLog[] history, ArrayList<LinphoneContact> participants, ChatMessageViewHolderClickListener clickListener) {
super(helper);
mFragment = fragment;
mContext = mFragment.getActivity();
@ -100,7 +100,7 @@ public class ChatMessagesOldAdapter extends SelectableAdapter<ChatMessageViewHol
mListener = new ChatMessageListenerStub() {
@Override
public void onFileTransferProgressIndication(ChatMessage message, Content content, int offset, int total) {
ChatMessageViewHolder holder = (ChatMessageViewHolder) message.getUserData();
ChatMessageOldViewHolder holder = (ChatMessageOldViewHolder) message.getUserData();
if (holder == null) return;
if (offset == total) {
@ -136,10 +136,10 @@ public class ChatMessagesOldAdapter extends SelectableAdapter<ChatMessageViewHol
}
@Override
public ChatMessageViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
public ChatMessageOldViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View v = LayoutInflater.from(parent.getContext())
.inflate(mItemResource, parent, false);
ChatMessageViewHolder VH = new ChatMessageViewHolder(mContext, v, mClickListener);
ChatMessageOldViewHolder VH = new ChatMessageOldViewHolder(mContext, v, mClickListener);
//Allows onLongClick ContextMenu on bubbles
mFragment.registerForContextMenu(v);
@ -148,7 +148,7 @@ public class ChatMessagesOldAdapter extends SelectableAdapter<ChatMessageViewHol
}
@Override
public void onBindViewHolder(@NonNull final ChatMessageViewHolder holder, int position) {
public void onBindViewHolder(@NonNull final ChatMessageOldViewHolder holder, int position) {
final EventLog event = mHistory.get(position);
holder.eventLayout.setVisibility(View.GONE);
holder.bubbleLayout.setVisibility(View.GONE);
@ -528,7 +528,7 @@ public class ChatMessagesOldAdapter extends SelectableAdapter<ChatMessageViewHol
mContext.startActivity(intent);
}
private void displayAttachedFile(ChatMessage message, ChatMessageViewHolder holder) {
private void displayAttachedFile(ChatMessage message, ChatMessageOldViewHolder holder) {
holder.fileName.setVisibility(View.VISIBLE);
String appData = message.getAppdata();

View file

@ -1,5 +1,5 @@
/*
ImdnFragment.java
ImdnOldFragment.java
Copyright (C) 2010-2018 Belledonne Communications, Grenoble, France
This program is free software; you can redistribute it and/or
@ -21,7 +21,6 @@ package org.linphone.chat;
import android.app.Fragment;
import android.os.Bundle;
import androidx.annotation.Nullable;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
@ -29,11 +28,9 @@ import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;
import org.linphone.LinphoneManager;
import org.linphone.mediastream.Log;
import org.linphone.utils.LinphoneUtils;
import org.linphone.R;
import org.linphone.LinphoneActivity;
import org.linphone.LinphoneManager;
import org.linphone.R;
import org.linphone.contacts.ContactsManager;
import org.linphone.contacts.LinphoneContact;
import org.linphone.core.Address;
@ -43,8 +40,11 @@ import org.linphone.core.ChatRoom;
import org.linphone.core.Core;
import org.linphone.core.ParticipantImdnState;
import org.linphone.fragments.FragmentsAvailable;
import org.linphone.utils.LinphoneUtils;
import org.linphone.views.ContactAvatar;
import androidx.annotation.Nullable;
public class ImdnFragment extends Fragment {
private LayoutInflater mInflater;
private LinearLayout mRead, mReadHeader, mDelivered, mDeliveredHeader, mSent, mSentHeader, mUndelivered, mUndeliveredHeader;

View file

@ -0,0 +1,288 @@
package org.linphone.chat;
/*
ImdnOldFragment.java
Copyright (C) 2010-2018 Belledonne Communications, Grenoble, France
This program is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 2
of the License, or (at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
import android.app.Fragment;
import android.os.Bundle;
import androidx.annotation.Nullable;
import android.text.Spanned;
import android.text.method.LinkMovementMethod;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.RelativeLayout;
import android.widget.TextView;
import org.linphone.LinphoneManager;
import org.linphone.utils.FileUtils;
import org.linphone.utils.LinphoneUtils;
import org.linphone.R;
import org.linphone.LinphoneActivity;
import org.linphone.compatibility.Compatibility;
import org.linphone.contacts.ContactsManager;
import org.linphone.contacts.LinphoneContact;
import org.linphone.core.Address;
import org.linphone.core.ChatMessage;
import org.linphone.core.ChatMessageListenerStub;
import org.linphone.core.ChatRoom;
import org.linphone.core.Core;
import org.linphone.core.ParticipantImdnState;
import org.linphone.fragments.FragmentsAvailable;
import org.linphone.views.ContactAvatar;
public class ImdnOldFragment extends Fragment {
private LayoutInflater mInflater;
private LinearLayout mRead, mReadHeader, mDelivered, mDeliveredHeader, mSent, mSentHeader, mUndelivered, mUndeliveredHeader;
private ImageView mBackButton;
private ChatMessageOldViewHolder mBubble;
private ViewGroup mContainer;
private String mRoomUri, mMessageId;
private Address mRoomAddr;
private ChatRoom mRoom;
private ChatMessage mMessage;
private ChatMessageListenerStub mListener;
@Nullable
@Override
public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
if (getArguments() != null) {
mRoomUri = getArguments().getString("SipUri");
mRoomAddr = LinphoneManager.getLc().createAddress(mRoomUri);
mMessageId = getArguments().getString("MessageId");
}
Core core = LinphoneManager.getLcIfManagerNotDestroyedOrNull();
mRoom = core.getChatRoomFromUri(mRoomAddr.asStringUriOnly());
mInflater = inflater;
mContainer = container;
View view = mInflater.inflate(R.layout.chat_imdn_old, container, false);
mBackButton = view.findViewById(R.id.back);
mBackButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
if (LinphoneActivity.instance().isTablet()) {
LinphoneActivity.instance().goToChat(mRoomUri, null);
} else {
LinphoneActivity.instance().onBackPressed();
}
}
});
mRead = view.findViewById(R.id.read_layout);
mDelivered = view.findViewById(R.id.delivered_layout);
mSent = view.findViewById(R.id.sent_layout);
mUndelivered = view.findViewById(R.id.undelivered_layout);
mReadHeader = view.findViewById(R.id.read_layout_header);
mDeliveredHeader = view.findViewById(R.id.delivered_layout_header);
mSentHeader = view.findViewById(R.id.sent_layout_header);
mUndeliveredHeader = view.findViewById(R.id.undelivered_layout_header);
mBubble = new ChatMessageOldViewHolder(view.findViewById(R.id.bubble));
mBubble.eventLayout.setVisibility(View.GONE);
mBubble.bubbleLayout.setVisibility(View.VISIBLE);
mBubble.delete.setVisibility(View.GONE);
mBubble.messageText.setVisibility(View.GONE);
mBubble.messageImage.setVisibility(View.GONE);
mBubble.fileTransferLayout.setVisibility(View.GONE);
mBubble.fileName.setVisibility(View.GONE);
mBubble.openFileButton.setVisibility(View.GONE);
mBubble.messageStatus.setVisibility(View.INVISIBLE);
mBubble.messageSendingInProgress.setVisibility(View.GONE);
mBubble.imdmLayout.setVisibility(View.INVISIBLE);
mMessage = mRoom.findMessage(mMessageId);
mListener = new ChatMessageListenerStub() {
@Override
public void onParticipantImdnStateChanged(ChatMessage msg, ParticipantImdnState state) {
refreshInfo();
}
};
if (mMessage == null) return null;
mMessage.setListener(mListener);
RelativeLayout.LayoutParams layoutParams = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
layoutParams.addRule(RelativeLayout.ALIGN_PARENT_RIGHT);
layoutParams.setMargins(100, 10, 10, 10);
if (mMessage.isOutgoing()) {
mBubble.background.setBackgroundResource(R.drawable.resizable_chat_bubble_outgoing);
Compatibility.setTextAppearance(mBubble.contactName, getActivity(), R.style.font3);
Compatibility.setTextAppearance(mBubble.fileTransferAction, getActivity(), R.style.font15);
mBubble.fileTransferAction.setBackgroundResource(R.drawable.resizable_confirm_delete_button);
ContactAvatar.setAvatarMask(mBubble.avatarLayout, R.drawable.avatar_chat_mask_outgoing);
} else {
mBubble.background.setBackgroundResource(R.drawable.resizable_chat_bubble_incoming);
Compatibility.setTextAppearance(mBubble.contactName, getActivity(), R.style.font9);
Compatibility.setTextAppearance(mBubble.fileTransferAction, getActivity(), R.style.font8);
mBubble.fileTransferAction.setBackgroundResource(R.drawable.resizable_assistant_button);
ContactAvatar.setAvatarMask(mBubble.avatarLayout, R.drawable.avatar_chat_mask);
}
return view;
}
@Override
public void onResume() {
super.onResume();
if (LinphoneActivity.isInstanciated()) {
LinphoneActivity.instance().selectMenu(FragmentsAvailable.MESSAGE_IMDN);
}
refreshInfo();
}
private void refreshInfo() {
Address remoteSender = mMessage.getFromAddress();
LinphoneContact contact = ContactsManager.getInstance().findContactFromAddress(remoteSender);
String displayName;
if (contact != null) {
if (contact.getFullName() != null) {
displayName = contact.getFullName();
} else {
displayName = LinphoneUtils.getAddressDisplayName(remoteSender);
}
ContactAvatar.displayAvatar(contact, mBubble.avatarLayout);
} else {
displayName = LinphoneUtils.getAddressDisplayName(remoteSender);
ContactAvatar.displayAvatar(displayName, mBubble.avatarLayout);
}
mBubble.contactName.setText(LinphoneUtils.timestampToHumanDate(getActivity(), mMessage.getTime(), R.string.messages_date_format) + " - " + displayName);
if (mMessage.hasTextContent()) {
String msg = mMessage.getTextContent();
Spanned text = LinphoneUtils.getTextWithHttpLinks(msg);
mBubble.messageText.setText(text);
mBubble.messageText.setMovementMethod(LinkMovementMethod.getInstance());
mBubble.messageText.setVisibility(View.VISIBLE);
}
String appData = mMessage.getAppdata();
if (appData != null) { // Something to display
mBubble.fileName.setVisibility(View.VISIBLE);
mBubble.fileName.setText(FileUtils.getNameFromFilePath(appData));
// We purposely chose not to display the image
}
mRead.removeAllViews();
mDelivered.removeAllViews();
mSent.removeAllViews();
mUndelivered.removeAllViews();
ParticipantImdnState[] participants = mMessage.getParticipantsByImdnState(ChatMessage.State.Displayed);
mReadHeader.setVisibility(participants.length == 0 ? View.GONE : View.VISIBLE);
boolean first = true;
for (ParticipantImdnState participant : participants) {
Address address = participant.getParticipant().getAddress();
LinphoneContact participantContact = ContactsManager.getInstance().findContactFromAddress(address);
String participantDisplayName = participantContact != null ? participantContact.getFullName() : LinphoneUtils.getAddressDisplayName(address);
View v = mInflater.inflate(R.layout.chat_imdn_cell, mContainer, false);
v.findViewById(R.id.separator).setVisibility(first ? View.GONE : View.VISIBLE);
((TextView) v.findViewById(R.id.time)).setText(LinphoneUtils.timestampToHumanDate(getActivity(), participant.getStateChangeTime(), R.string.messages_date_format));
((TextView) v.findViewById(R.id.name)).setText(participantDisplayName);
if (participantContact != null) {
ContactAvatar.displayAvatar(participantContact, v.findViewById(R.id.avatar_layout));
} else {
ContactAvatar.displayAvatar(participantDisplayName, v.findViewById(R.id.avatar_layout));
}
mRead.addView(v);
first = false;
}
participants = mMessage.getParticipantsByImdnState(ChatMessage.State.DeliveredToUser);
mDeliveredHeader.setVisibility(participants.length == 0 ? View.GONE : View.VISIBLE);
first = true;
for (ParticipantImdnState participant : participants) {
Address address = participant.getParticipant().getAddress();
LinphoneContact participantContact = ContactsManager.getInstance().findContactFromAddress(address);
String participantDisplayName = participantContact != null ? participantContact.getFullName() : LinphoneUtils.getAddressDisplayName(address);
View v = mInflater.inflate(R.layout.chat_imdn_cell, mContainer, false);
v.findViewById(R.id.separator).setVisibility(first ? View.GONE : View.VISIBLE);
((TextView) v.findViewById(R.id.time)).setText(LinphoneUtils.timestampToHumanDate(getActivity(), participant.getStateChangeTime(), R.string.messages_date_format));
((TextView) v.findViewById(R.id.name)).setText(participantDisplayName);
if (participantContact != null) {
ContactAvatar.displayAvatar(participantContact, v.findViewById(R.id.avatar_layout));
} else {
ContactAvatar.displayAvatar(participantDisplayName, v.findViewById(R.id.avatar_layout));
}
mDelivered.addView(v);
first = false;
}
participants = mMessage.getParticipantsByImdnState(ChatMessage.State.Delivered);
mSentHeader.setVisibility(participants.length == 0 ? View.GONE : View.VISIBLE);
first = true;
for (ParticipantImdnState participant : participants) {
Address address = participant.getParticipant().getAddress();
LinphoneContact participantContact = ContactsManager.getInstance().findContactFromAddress(address);
String participantDisplayName = participantContact != null ? participantContact.getFullName() : LinphoneUtils.getAddressDisplayName(address);
View v = mInflater.inflate(R.layout.chat_imdn_cell, mContainer, false);
v.findViewById(R.id.separator).setVisibility(first ? View.GONE : View.VISIBLE);
((TextView) v.findViewById(R.id.time)).setText(LinphoneUtils.timestampToHumanDate(getActivity(), participant.getStateChangeTime(), R.string.messages_date_format));
((TextView) v.findViewById(R.id.name)).setText(participantDisplayName);
if (participantContact != null) {
ContactAvatar.displayAvatar(participantContact, v.findViewById(R.id.avatar_layout));
} else {
ContactAvatar.displayAvatar(participantDisplayName, v.findViewById(R.id.avatar_layout));
}
mSent.addView(v);
first = false;
}
participants = mMessage.getParticipantsByImdnState(ChatMessage.State.NotDelivered);
mUndeliveredHeader.setVisibility(participants.length == 0 ? View.GONE : View.VISIBLE);
first = true;
for (ParticipantImdnState participant : participants) {
Address address = participant.getParticipant().getAddress();
LinphoneContact participantContact = ContactsManager.getInstance().findContactFromAddress(address);
String participantDisplayName = participantContact != null ? participantContact.getFullName() : LinphoneUtils.getAddressDisplayName(address);
View v = mInflater.inflate(R.layout.chat_imdn_cell, mContainer, false);
v.findViewById(R.id.separator).setVisibility(first ? View.GONE : View.VISIBLE);
((TextView) v.findViewById(R.id.name)).setText(participantDisplayName);
if (participantContact != null) {
ContactAvatar.displayAvatar(participantContact, v.findViewById(R.id.avatar_layout));
} else {
ContactAvatar.displayAvatar(participantDisplayName, v.findViewById(R.id.avatar_layout));
}
mUndelivered.addView(v);
first = false;
}
}
}

View file

@ -0,0 +1,211 @@
<?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="wrap_content">
<CheckBox
android:id="@+id/delete_message"
android:button="@drawable/checkbox"
android:contentDescription="@string/content_description_delete"
android:layout_marginLeft="5dp"
android:layout_width="30dp"
android:layout_height="30dp"
android:adjustViewBounds="true"
android:clickable="false"
android:layout_alignParentRight="true"/>
<LinearLayout
android:id="@+id/event"
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_toLeftOf="@id/delete_message"
android:layout_marginTop="5dp"
android:layout_marginBottom="5dp"
android:gravity="center"
android:background="@drawable/event_decoration_gray">
<TextView
android:id="@+id/event_text"
android:textAppearance="@style/font_group_chat_event"
android:background="@color/colorH"
android:paddingLeft="10dp"
android:paddingRight="10dp"
android:layout_width="wrap_content"
android:layout_height="wrap_content"/>
</LinearLayout>
<RelativeLayout
android:id="@+id/bubble"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_toLeftOf="@id/delete_message">
<LinearLayout
android:id="@+id/separator"
android:layout_width="100dp"
android:layout_height="10dp"
android:orientation="horizontal"/>
<LinearLayout
android:id="@+id/background"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_below="@id/separator"
android:orientation="horizontal">
<RelativeLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:paddingLeft="10dp"
android:paddingTop="10dp">
<include layout="@layout/contact_avatar"/>
</RelativeLayout>
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical"
android:paddingTop="10dp"
android:paddingRight="10dp">
<TextView
android:id="@+id/contact_header"
android:maxLines="1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"/>
<RelativeLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content">
<TextView
android:id="@+id/file_name"
style="@style/chat_bubble_file_name_font"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<ImageView
android:id="@+id/image"
android:layout_width="wrap_content"
android:layout_height="150dp"
android:layout_below="@id/file_name"
android:layout_centerHorizontal="true"
android:adjustViewBounds="true"/>
<Button
android:id="@+id/open_file"
android:textAppearance="@style/font8"
android:text="@string/open"
android:background="@drawable/resizable_assistant_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_below="@id/file_name"
android:layout_centerVertical="true"
android:visibility="gone"/>
</RelativeLayout>
<TextView
android:id="@+id/message"
style="@style/font11"
android:autoLink="web"
android:linksClickable="true"
android:layout_width="wrap_content"
android:layout_height="wrap_content"/>
<RelativeLayout
android:id="@+id/file_transfer_layout"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:visibility="gone">
<ProgressBar
android:id="@+id/progress_bar"
style="@android:style/Widget.ProgressBar.Horizontal"
android:paddingRight="5dp"
android:layout_marginTop="10dp"
android:layout_marginBottom="10dp"
android:layout_width="150dp"
android:layout_height="5dp"/>
<Button
android:id="@+id/file_transfer_action"
android:textAppearance="@style/font8"
android:background="@drawable/resizable_assistant_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_below="@id/progress_bar"/>
</RelativeLayout>
<LinearLayout
android:id="@+id/imdmLayout"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_marginTop="2dp"
android:layout_marginBottom="2dp"
android:orientation="horizontal"
android:layout_gravity="right"
android:gravity="right"
android:visibility="invisible">
<TextView
android:id="@+id/imdmText"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Displayed"
android:textSize="12sp"
android:paddingRight="3dp"/>
<ImageView
android:id="@+id/imdmIcon"
android:layout_width="10dp"
android:layout_height="10dp"
android:src="@drawable/valid"
android:scaleType="fitCenter"
android:layout_marginTop="2dp" />
</LinearLayout>
</LinearLayout>
</LinearLayout>
<RelativeLayout
android:layout_alignRight="@id/background"
android:layout_alignTop="@id/background"
android:layout_width="15dp"
android:layout_height="15dp"
android:paddingTop="5dp"
android:paddingBottom="3dp">
<ImageView
android:id="@+id/status"
android:contentDescription="@string/content_description_message_status"
android:visibility="invisible"
android:layout_alignParentTop="true"
android:layout_alignParentRight="true"
android:paddingRight="5dp"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:adjustViewBounds="true" />
<ProgressBar
android:id="@+id/inprogress"
android:progressTint="@color/colorB"
android:layout_alignParentTop="true"
android:layout_alignParentRight="true"
android:paddingRight="5dp"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
</RelativeLayout>
</RelativeLayout>
</RelativeLayout>

View file

@ -0,0 +1,191 @@
<?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="match_parent"
android:background="@color/colorH" >
<RelativeLayout
android:id="@+id/top"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<LinearLayout
android:id="@+id/top_bar"
android:orientation="horizontal"
android:background="@color/colorF"
android:layout_width="match_parent"
android:layout_height="60dp">
<ImageView
android:id="@+id/back"
android:src="@drawable/back"
android:background="@drawable/toolbar_button"
android:contentDescription="@string/content_description_back"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="0.2"
android:padding="18dp"/>
<TextView
android:text="@string/imdn_info"
style="@style/font6"
android:gravity="center"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="0.6"
android:padding="15dp"/>
<ImageView
android:visibility="invisible"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="0.2"
android:padding="15dp"/>
</LinearLayout>
</RelativeLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:gravity="center_horizontal"
android:layout_below="@id/top">
<ScrollView
android:layout_width="match_parent"
android:layout_height="match_parent">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<include
android:id="@+id/bubble"
layout="@layout/chat_bubble_old"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="20dp"/>
<LinearLayout
android:id="@+id/read_layout_header"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:gravity="center"
android:background="@color/colorG">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
style="@style/imdn_read_font"
android:text="@string/displayed"/>
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/message_read"/>
</LinearLayout>
<LinearLayout
android:id="@+id/read_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"/>
<LinearLayout
android:id="@+id/delivered_layout_header"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:gravity="center"
android:background="@color/colorG">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
style="@style/imdn_delivered_sent_font"
android:text="@string/delivered"/>
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/message_delivered"/>
</LinearLayout>
<LinearLayout
android:id="@+id/delivered_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"/>
<LinearLayout
android:id="@+id/sent_layout_header"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:gravity="center"
android:background="@color/colorG">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
style="@style/imdn_delivered_sent_font"
android:text="@string/sent"/>
<ImageView
android:visibility="invisible"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/message_delivered"/>
</LinearLayout>
<LinearLayout
android:id="@+id/sent_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"/>
<LinearLayout
android:id="@+id/undelivered_layout_header"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:gravity="center"
android:background="@color/colorG">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
style="@style/imdn_undelivered_font"
android:text="@string/error"/>
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/message_undelivered"/>
</LinearLayout>
<LinearLayout
android:id="@+id/undelivered_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"/>
</LinearLayout>
</ScrollView>
</LinearLayout>
</RelativeLayout>

View file

@ -90,6 +90,7 @@
<bool name="lower_space_between_chat_bubbles_if_same_person">true</bool>
<bool name="allow_multiple_images_and_text">true</bool>
<bool name="send_text_and_images_as_different_messages">true</bool>
<bool name="use_new_chat_bubbles_layout">false</bool>
<!-- Contacts -->
<bool name="hide_contact_phone_numbers">false</bool>