Files
arcanechat-android/MessengerProj/src/main/java/com/b44t/messenger/MrMsg.java
T
2017-11-22 14:34:41 +01:00

282 lines
12 KiB
Java

/*******************************************************************************
*
* Delta Chat Android
* (C) 2017 Björn Petersen
* Contact: r10s@b44t.com, http://b44t.com
*
* 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 3 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, see http://www.gnu.org/licenses/ .
*
*******************************************************************************
*
* File: MrMsg.java
* Purpose: Wrap around mrmsg_t
*
******************************************************************************/
package com.b44t.messenger;
import android.graphics.Bitmap;
import android.media.ThumbnailUtils;
import android.provider.MediaStore;
import java.io.File;
public class MrMsg {
private static final String TAG = "MrMsg";
public final static int MR_MSG_UNDEFINED = 0;
public final static int MR_MSG_TEXT = 10;
public final static int MR_MSG_IMAGE = 20;
public final static int MR_MSG_GIF = 21;
public final static int MR_MSG_AUDIO = 40;
public final static int MR_MSG_VOICE = 41;
public final static int MR_MSG_VIDEO = 50;
public final static int MR_MSG_FILE = 60;
public final static int MR_STATE_UNDEFINED = 0;
public final static int MR_IN_FRESH = 10;
public final static int MR_IN_NOTICED = 13;
public final static int MR_OUT_PENDING = 20;
public final static int MR_OUT_ERROR = 24;
public final static int MR_OUT_DELIVERED = 26;
public final static int MR_OUT_MDN_RCVD = 28;
public final static int MR_MSG_ID_MARKER1 = 1;
public final static int MR_MSG_ID_DAYMARKER = 9;
public MrMsg(long hMsg) {
m_hMsg = hMsg;
}
@Override protected void finalize() throws Throwable {
super.finalize();
MrMsgUnref(m_hMsg);
}
public int getId() {
return MrMsgGetId(m_hMsg);
}
public String getText() {
return MrMsgGetText(m_hMsg);
}
public long getTimestamp() {
return MrMsgGetTimestamp(m_hMsg);
}
public int getType() {
return MrMsgGetType(m_hMsg);
}
public int getState() {
return MrMsgGetState(m_hMsg);
}
public int getChatId() {
return MrMsgGetChatId(m_hMsg);
}
public int getFromId() {
return MrMsgGetFromId(m_hMsg);
}
public int getToId() {
return MrMsgGetToId(m_hMsg);
}
public native String getMsgParam(int key, String def);
public native int getMsgParamInt(int key, int def);
public native void setMsgParamInt(int key, int def);
public native void saveMsgParamToDisk();
public native int getBytes();
public MrPoortext getSummary(MrChat chat) { return new MrPoortext(getSummaryCPtr(chat.getCPtr())); }
private native long getSummaryCPtr(long hChat);
public native String getSummarytext(int approx_characters);
public native int showPadlock();
public MrPoortext getMediainfo() { return new MrPoortext(getMediainfoCPtr()); }
private native long getMediainfoCPtr();
public native String getFilename();
public native boolean isIncreation();
public native boolean isSystemcmd();
private long m_hMsg; // must not be renamed as referenced by JNI under the name "m_hMsg"
private native static void MrMsgUnref (long hMsg);
private native static int MrMsgGetId (long hMsg);
private native static String MrMsgGetText (long hMsg);
private native static long MrMsgGetTimestamp (long hMsg);
private native static int MrMsgGetType (long hMsg);
private native static int MrMsgGetState (long hMsg);
private native static int MrMsgGetChatId (long hMsg);
private native static int MrMsgGetFromId (long hMsg);
private native static int MrMsgGetToId (long hMsg);
/* additional functions that are not 1:1 available in the backend
**********************************************************************************************/
public TLRPC.Message get_TLRPC_Message()
{
TLRPC.Message ret = new TLRPC.TL_message(); // the class derived from TLRPC.Message defines the basic type:
// TLRPC.TL_messageService is used to display messages as "You joined the group"
// TLRPC.TL_message is a normal message (also photos?)
int state = getState();
int type = getType();
switch( state ) {
case MR_OUT_DELIVERED: ret.send_state = MessageObject.MESSAGE_SEND_STATE_SENT; break;
case MR_OUT_ERROR: ret.send_state = MessageObject.MESSAGE_SEND_STATE_SEND_ERROR; break;
case MR_OUT_PENDING: ret.send_state = MessageObject.MESSAGE_SEND_STATE_SENDING; break;
case MR_OUT_MDN_RCVD: ret.send_state = MessageObject.MESSAGE_SEND_STATE_SENT; break;
}
ret.id = getId();
ret.from_id = getFromId();
ret.to_id = new TLRPC.TL_peerUser();
ret.to_id.user_id = getToId();
ret.date = (int)getTimestamp();
ret.dialog_id = getChatId();
ret.unread = state!=MR_OUT_MDN_RCVD; // the state of outgoing messages
ret.media_unread = ret.unread;
ret.flags = 0; // posible flags: MESSAGE_FLAG_HAS_FROM_ID, however, this seems to be read only
ret.out = ret.from_id==MrContact.MR_CONTACT_ID_SELF; // true=outgoing message, read eg. in MessageObject.isOutOwner()
ret.created_by_mr = true;
ret.show_padlock = showPadlock()!=0;
ret.is_system_cmd = isSystemcmd();
if( type == MR_MSG_TEXT ) {
ret.message = getText();
}
else if( type == MR_MSG_IMAGE ) {
String path = getMsgParam('f', "");
TLRPC.TL_photo photo = null;
if( !path.isEmpty() ) {
try {
TLRPC.TL_photoSize photoSize = new TLRPC.TL_photoSize();
photoSize.w = getMsgParamInt('w', 800);
photoSize.h = getMsgParamInt('h', 800);
photoSize.size = 0; // not sure what to use here, maybe `getBytes();`?
photoSize.location = new TLRPC.TL_fileLocation();
photoSize.location.mr_path = path;
photoSize.location.local_id = -ret.id; // this forces the document to be searched in the cache dir
if (photoSize.w <= 100 && photoSize.h <= 100) {
photoSize.type = "s";
} else if (photoSize.w <= 320 && photoSize.h <= 320) {
photoSize.type = "m";
} else if (photoSize.w <= 800 && photoSize.h <= 800) {
photoSize.type = "x";
} else if (photoSize.w <= 1280 && photoSize.h <= 1280) {
photoSize.type = "y";
} else {
photoSize.type = "w";
}
photo = new TLRPC.TL_photo();
photo.sizes.add(photoSize);
} catch (Exception e) {
// the most common reason is a simple "file not found error"
}
}
if(photo!=null) {
ret.message = "-1";
ret.media = new TLRPC.TL_messageMediaPhoto();
ret.media.photo = photo;
ret.attachPath = path; // ret.attachPathExists set later in MessageObject.checkMediaExistance()
}
else {
ret.message = "<cannot load image>";
}
}
else if( type == MR_MSG_GIF || type == MR_MSG_AUDIO || type == MR_MSG_VOICE || type == MR_MSG_VIDEO || type == MR_MSG_FILE ) {
String path = getMsgParam('f', "");
if( !path.isEmpty()) {
ret.message = "-1"; // may be misused for video editing information
ret.media = new TLRPC.TL_messageMediaDocument();
ret.media.caption = "";
ret.media.document = new TLRPC.TL_document();
ret.media.document.file_name = getFilename();
ret.media.document.mr_path = path;
ret.media.document.size = getBytes();
if( type == MR_MSG_GIF ) {
ret.media.document.mime_type = getMsgParam('m', "image/gif");
TLRPC.PhotoSize size = new TLRPC.PhotoSize();
size.location = new TLRPC.TL_fileLocation();
size.location.mr_path = path;
size.location.local_id = -ret.id;
size.w = getMsgParamInt('w', 320);
size.h = getMsgParamInt('h', 240);
size.type = "s";
ret.media.document.thumb = size;
}
else if( type == MR_MSG_AUDIO || type == MR_MSG_VOICE ) {
TLRPC.TL_documentAttributeAudio attr = new TLRPC.TL_documentAttributeAudio();
attr.voice = type == MR_MSG_VOICE;
attr.duration = getMsgParamInt('d', 0) / 1000;
ret.media.document.attributes.add(attr);
}
else if( type == MR_MSG_VIDEO ) {
File vfile = new File(path);
File tfile = new File(MrMailbox.getBlobdir(), vfile.getName()+"-preview.jpg");
if( !tfile.exists() ) {
try {
Bitmap thumb = ThumbnailUtils.createVideoThumbnail(path, MediaStore.Video.Thumbnails.MINI_KIND);
TLRPC.PhotoSize size = ImageLoader.scaleAndSaveImage(tfile, thumb, 90, 90, 55, false);
size.location.mr_path = tfile.getAbsolutePath();
size.type = "s";
ret.media.document.thumb = size;
setMsgParamInt('w', size.w);
setMsgParamInt('h', size.h);
saveMsgParamToDisk();
}
catch (Exception e) {}
}
else {
TLRPC.PhotoSize size = new TLRPC.PhotoSize();
size.location = new TLRPC.TL_fileLocation();
size.location.mr_path = tfile.getAbsolutePath();
size.location.local_id = -ret.id;
size.w = getMsgParamInt('w', 320);
size.h = getMsgParamInt('h', 240);
size.type = "s";
ret.media.document.thumb = size;
}
TLRPC.TL_documentAttributeVideo attr = new TLRPC.TL_documentAttributeVideo();
attr.duration = getMsgParamInt('d', 0) / 1000;
attr.w = getMsgParamInt('w', 320);
attr.h = getMsgParamInt('h', 240);
ret.media.document.attributes.add(attr);
}
else {
ret.media.document.mime_type = getMsgParam('m', "application/octet-stream");
}
}
else {
ret.message = "<file path missing>";
}
}
else {
ret.message = String.format("<unsupported message type #%d for id #%d>", type, ret.id);
}
if( !getMsgParam('a', "").equals("") ) {
ret.flags |= TLRPC.MESSAGE_FLAG_FWD;
}
return ret;
}
};