diff --git a/TMessagesProj/build.gradle b/TMessagesProj/build.gradle index 20dcbe4c3..ad4fa662b 100644 --- a/TMessagesProj/build.gradle +++ b/TMessagesProj/build.gradle @@ -3,10 +3,10 @@ buildscript { mavenCentral() } dependencies { - classpath 'com.android.tools.build:gradle:0.11.+' + classpath 'com.android.tools.build:gradle:0.12.+' } } -apply plugin: 'android' +apply plugin: 'com.android.application' repositories { mavenCentral() @@ -20,13 +20,15 @@ dependencies { compile 'com.android.support:support-v4:19.0.+' compile 'com.google.android.gms:play-services:4.1.+' compile 'net.hockeyapp.android:HockeySDK:3.0.1' + compile 'com.googlecode.mp4parser:isoparser:1.0.+' } android { compileSdkVersion 19 buildToolsVersion '19.1.0' - aaptOptions.useAaptPngCruncher = true + useAaptPngCruncher = true + useOldManifestMerger true signingConfigs { debug { @@ -81,7 +83,7 @@ android { defaultConfig { minSdkVersion 8 targetSdkVersion 19 - versionCode 267 - versionName "1.5.7" + versionCode 288 + versionName "1.6.1" } } diff --git a/TMessagesProj/config/debug/AndroidManifest.xml b/TMessagesProj/config/debug/AndroidManifest.xml index 8a10bfb38..6a08d6c12 100644 --- a/TMessagesProj/config/debug/AndroidManifest.xml +++ b/TMessagesProj/config/debug/AndroidManifest.xml @@ -33,7 +33,7 @@ diff --git a/TMessagesProj/config/release/AndroidManifest.xml b/TMessagesProj/config/release/AndroidManifest.xml index af9751457..a1ee70d33 100644 --- a/TMessagesProj/config/release/AndroidManifest.xml +++ b/TMessagesProj/config/release/AndroidManifest.xml @@ -33,7 +33,7 @@ diff --git a/TMessagesProj/jni/Android.mk b/TMessagesProj/jni/Android.mk index a45cb8de3..33857ab90 100755 --- a/TMessagesProj/jni/Android.mk +++ b/TMessagesProj/jni/Android.mk @@ -234,6 +234,7 @@ LOCAL_SRC_FILES += \ ./audio.c \ ./gif.c \ ./utils.c \ -./image.c +./image.c \ +./fake.c include $(BUILD_SHARED_LIBRARY) \ No newline at end of file diff --git a/TMessagesProj/jni/audio.c b/TMessagesProj/jni/audio.c index 70b6e2fc2..3ca0f1fb2 100644 --- a/TMessagesProj/jni/audio.c +++ b/TMessagesProj/jni/audio.c @@ -504,7 +504,7 @@ int writeFrame(uint8_t *framePcmBytes, unsigned int frameByteCount) { return 1; } -JNIEXPORT int Java_org_telegram_messenger_MediaController_startRecord(JNIEnv *env, jclass class, jstring path) { +JNIEXPORT int Java_org_telegram_android_MediaController_startRecord(JNIEnv *env, jclass class, jstring path) { const char *pathStr = (*env)->GetStringUTFChars(env, path, 0); int result = initRecorder(pathStr); @@ -516,12 +516,12 @@ JNIEXPORT int Java_org_telegram_messenger_MediaController_startRecord(JNIEnv *en return result; } -JNIEXPORT int Java_org_telegram_messenger_MediaController_writeFrame(JNIEnv *env, jclass class, jobject frame, jint len) { +JNIEXPORT int Java_org_telegram_android_MediaController_writeFrame(JNIEnv *env, jclass class, jobject frame, jint len) { jbyte *frameBytes = (*env)->GetDirectBufferAddress(env, frame); return writeFrame(frameBytes, len); } -JNIEXPORT void Java_org_telegram_messenger_MediaController_stopRecord(JNIEnv *env, jclass class) { +JNIEXPORT void Java_org_telegram_android_MediaController_stopRecord(JNIEnv *env, jclass class) { cleanupRecorder(); } @@ -618,22 +618,22 @@ void fillBuffer(uint8_t *buffer, int capacity, int *args) { } } -JNIEXPORT jlong Java_org_telegram_messenger_MediaController_getTotalPcmDuration(JNIEnv *env, jclass class) { +JNIEXPORT jlong Java_org_telegram_android_MediaController_getTotalPcmDuration(JNIEnv *env, jclass class) { return _totalPcmDuration; } -JNIEXPORT void Java_org_telegram_messenger_MediaController_readOpusFile(JNIEnv *env, jclass class, jobject buffer, jint capacity, jintArray args) { +JNIEXPORT void Java_org_telegram_android_MediaController_readOpusFile(JNIEnv *env, jclass class, jobject buffer, jint capacity, jintArray args) { jint *argsArr = (*env)->GetIntArrayElements(env, args, 0); jbyte *bufferBytes = (*env)->GetDirectBufferAddress(env, buffer); fillBuffer(bufferBytes, capacity, argsArr); (*env)->ReleaseIntArrayElements(env, args, argsArr, 0); } -JNIEXPORT int Java_org_telegram_messenger_MediaController_seekOpusFile(JNIEnv *env, jclass class, jfloat position) { +JNIEXPORT int Java_org_telegram_android_MediaController_seekOpusFile(JNIEnv *env, jclass class, jfloat position) { return seekPlayer(position); } -JNIEXPORT int Java_org_telegram_messenger_MediaController_openOpusFile(JNIEnv *env, jclass class, jstring path) { +JNIEXPORT int Java_org_telegram_android_MediaController_openOpusFile(JNIEnv *env, jclass class, jstring path) { const char *pathStr = (*env)->GetStringUTFChars(env, path, 0); int result = initPlayer(pathStr); @@ -645,11 +645,11 @@ JNIEXPORT int Java_org_telegram_messenger_MediaController_openOpusFile(JNIEnv *e return result; } -JNIEXPORT void Java_org_telegram_messenger_MediaController_closeOpusFile(JNIEnv *env, jclass class) { +JNIEXPORT void Java_org_telegram_android_MediaController_closeOpusFile(JNIEnv *env, jclass class) { cleanupPlayer(); } -JNIEXPORT int Java_org_telegram_messenger_MediaController_isOpusFile(JNIEnv *env, jclass class, jstring path) { +JNIEXPORT int Java_org_telegram_android_MediaController_isOpusFile(JNIEnv *env, jclass class, jstring path) { const char *pathStr = (*env)->GetStringUTFChars(env, path, 0); int result = 0; diff --git a/TMessagesProj/jni/fake.c b/TMessagesProj/jni/fake.c new file mode 100644 index 000000000..95b86f6fe --- /dev/null +++ b/TMessagesProj/jni/fake.c @@ -0,0 +1,6 @@ +#include + +void fakeFunction() { + printf("some androids has buggy native loader, so i should check size of libs in java to know that native library is correct. So each changed native library should has diffrent size in different app versions. This function will increase lib size for few bytes :)"); + printf("bla blablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablablabla"); +} diff --git a/TMessagesProj/jni/jni.c b/TMessagesProj/jni/jni.c index 66a7976e3..4a43f84dc 100644 --- a/TMessagesProj/jni/jni.c +++ b/TMessagesProj/jni/jni.c @@ -30,67 +30,21 @@ void JNI_OnUnload(JavaVM *vm, void *reserved) { gifOnJNIUnload(vm, reserved); } -JNIEXPORT jbyteArray Java_org_telegram_messenger_Utilities_aesIgeEncryption(JNIEnv *env, jclass class, jbyteArray _what, jbyteArray _key, jbyteArray _iv, jboolean encrypt, jboolean changeIv, jint l) { - unsigned char *what = (unsigned char *)(*env)->GetByteArrayElements(env, _what, NULL); - unsigned char *key = (unsigned char *)(*env)->GetByteArrayElements(env, _key, NULL); - unsigned char *__iv = (unsigned char *)(*env)->GetByteArrayElements(env, _iv, NULL); - unsigned char *iv = 0; - - if (!changeIv) { - iv = (unsigned char *)malloc((*env)->GetArrayLength(env, _iv)); - memcpy(iv, __iv, (*env)->GetArrayLength(env, _iv)); - } else { - iv = __iv; - } - - int len = l == 0 ? (*env)->GetArrayLength(env, _what) : l; - AES_KEY akey; - if (!encrypt) { - AES_set_decrypt_key(key, (*env)->GetArrayLength(env, _key) * 8, &akey); - AES_ige_encrypt(what, what, len, &akey, iv, AES_DECRYPT); - } else { - AES_set_encrypt_key(key, (*env)->GetArrayLength(env, _key) * 8, &akey); - AES_ige_encrypt(what, what, len, &akey, iv, AES_ENCRYPT); - } - (*env)->ReleaseByteArrayElements(env, _what, what, 0); - (*env)->ReleaseByteArrayElements(env, _key, key, JNI_ABORT); - if (!changeIv) { - (*env)->ReleaseByteArrayElements(env, _iv, __iv, JNI_ABORT); - free(iv); - } else { - (*env)->ReleaseByteArrayElements(env, _iv, __iv, 0); - } - return _what; -} - -JNIEXPORT void Java_org_telegram_messenger_Utilities_aesIgeEncryption2(JNIEnv *env, jclass class, jobject _what, jbyteArray _key, jbyteArray _iv, jboolean encrypt, jboolean changeIv, jint l) { - jbyte *what = (*env)->GetDirectBufferAddress(env, _what); - unsigned char *key = (unsigned char *)(*env)->GetByteArrayElements(env, _key, NULL); - unsigned char *__iv = (unsigned char *)(*env)->GetByteArrayElements(env, _iv, NULL); - unsigned char *iv = 0; - - if (!changeIv) { - iv = (unsigned char *)malloc((*env)->GetArrayLength(env, _iv)); - memcpy(iv, __iv, (*env)->GetArrayLength(env, _iv)); - } else { - iv = __iv; - } +JNIEXPORT void Java_org_telegram_messenger_Utilities_aesIgeEncryption(JNIEnv *env, jclass class, jobject buffer, jbyteArray key, jbyteArray iv, jboolean encrypt, int offset, int length) { + jbyte *what = (*env)->GetDirectBufferAddress(env, buffer) + offset; + unsigned char *keyBuff = (unsigned char *)(*env)->GetByteArrayElements(env, key, NULL); + unsigned char *ivBuff = (unsigned char *)(*env)->GetByteArrayElements(env, iv, NULL); AES_KEY akey; if (!encrypt) { - AES_set_decrypt_key(key, (*env)->GetArrayLength(env, _key) * 8, &akey); - AES_ige_encrypt(what, what, l, &akey, iv, AES_DECRYPT); + AES_set_decrypt_key(keyBuff, 32 * 8, &akey); + AES_ige_encrypt(what, what, length, &akey, ivBuff, AES_DECRYPT); } else { - AES_set_encrypt_key(key, (*env)->GetArrayLength(env, _key) * 8, &akey); - AES_ige_encrypt(what, what, l, &akey, iv, AES_ENCRYPT); - } - (*env)->ReleaseByteArrayElements(env, _key, key, JNI_ABORT); - if (!changeIv) { - (*env)->ReleaseByteArrayElements(env, _iv, __iv, JNI_ABORT); - free(iv); - } else { - (*env)->ReleaseByteArrayElements(env, _iv, __iv, 0); + AES_set_encrypt_key(keyBuff, 32 * 8, &akey); + AES_ige_encrypt(what, what, length, &akey, ivBuff, AES_ENCRYPT); } + (*env)->ReleaseByteArrayElements(env, key, keyBuff, JNI_ABORT); + (*env)->ReleaseByteArrayElements(env, iv, ivBuff, 0); } uint64_t gcd(uint64_t a, uint64_t b){ diff --git a/TMessagesProj/jni/sqlite_cursor.c b/TMessagesProj/jni/sqlite_cursor.c index 655876d9c..de3f7469d 100755 --- a/TMessagesProj/jni/sqlite_cursor.c +++ b/TMessagesProj/jni/sqlite_cursor.c @@ -48,7 +48,7 @@ jstring Java_org_telegram_SQLite_SQLiteCursor_columnStringValue(JNIEnv *env, job } jbyteArray Java_org_telegram_SQLite_SQLiteCursor_columnByteArrayValue(JNIEnv *env, jobject object, int statementHandle, int columnIndex) { - sqlite3_stmt *handle = (sqlite3_stmt *)statementHandle; + sqlite3_stmt *handle = (sqlite3_stmt *)statementHandle; void *buf = sqlite3_column_blob(handle, columnIndex); int length = sqlite3_column_bytes(handle, columnIndex); if (buf != 0 && length > 0) { @@ -58,3 +58,22 @@ jbyteArray Java_org_telegram_SQLite_SQLiteCursor_columnByteArrayValue(JNIEnv *en } return 0; } + +int Java_org_telegram_SQLite_SQLiteCursor_columnByteArrayLength(JNIEnv *env, jobject object, int statementHandle, int columnIndex) { + return sqlite3_column_bytes((sqlite3_stmt *)statementHandle, columnIndex); +} + +int Java_org_telegram_SQLite_SQLiteCursor_columnByteBufferValue(JNIEnv *env, jobject object, int statementHandle, int columnIndex, jobject buffer) { + if (!buffer) { + return 0; + } + sqlite3_stmt *handle = (sqlite3_stmt *)statementHandle; + void *buf = sqlite3_column_blob(handle, columnIndex); + int length = sqlite3_column_bytes(handle, columnIndex); + if (buf != 0 && length > 0) { + jbyte *byteBuff = (*env)->GetDirectBufferAddress(env, buffer); + memcpy(byteBuff, buf, length); + return length; + } + return 0; +} diff --git a/TMessagesProj/jni/sqlite_statement.c b/TMessagesProj/jni/sqlite_statement.c index f3d110030..1090de3db 100755 --- a/TMessagesProj/jni/sqlite_statement.c +++ b/TMessagesProj/jni/sqlite_statement.c @@ -62,20 +62,14 @@ void Java_org_telegram_SQLite_SQLitePreparedStatement_finalize(JNIEnv *env, jobj } } -void Java_org_telegram_SQLite_SQLitePreparedStatement_bindByteArray(JNIEnv *env, jobject object, int statementHandle, int index, jbyteArray value) { +void Java_org_telegram_SQLite_SQLitePreparedStatement_bindByteBuffer(JNIEnv *env, jobject object, int statementHandle, int index, jobject value, int length) { sqlite3_stmt *handle = (sqlite3_stmt *)statementHandle; - - const void *buf = (*env)->GetByteArrayElements(env, value, 0); - int length = (*env)->GetArrayLength(env, value); - + jbyte *buf = (*env)->GetDirectBufferAddress(env, value); + int errcode = sqlite3_bind_blob(handle, index, buf, length, SQLITE_STATIC); if (SQLITE_OK != errcode) { throw_sqlite3_exception(env, sqlite3_db_handle(handle), errcode); } - - if (buf != 0) { - (*env)->ReleaseByteArrayElements(env, value, buf, 0); - } } void Java_org_telegram_SQLite_SQLitePreparedStatement_bindString(JNIEnv *env, jobject object, int statementHandle, int index, jstring value) { diff --git a/TMessagesProj/libs/armeabi-v7a/libtmessages.so b/TMessagesProj/libs/armeabi-v7a/libtmessages.so index 9d9f73384..8ffd1fbc4 100755 Binary files a/TMessagesProj/libs/armeabi-v7a/libtmessages.so and b/TMessagesProj/libs/armeabi-v7a/libtmessages.so differ diff --git a/TMessagesProj/libs/armeabi/libtmessages.so b/TMessagesProj/libs/armeabi/libtmessages.so index 13a6c5a3c..f24065136 100755 Binary files a/TMessagesProj/libs/armeabi/libtmessages.so and b/TMessagesProj/libs/armeabi/libtmessages.so differ diff --git a/TMessagesProj/libs/x86/libtmessages.so b/TMessagesProj/libs/x86/libtmessages.so index 963e616ec..f251e2320 100755 Binary files a/TMessagesProj/libs/x86/libtmessages.so and b/TMessagesProj/libs/x86/libtmessages.so differ diff --git a/TMessagesProj/src/main/AndroidManifest.xml b/TMessagesProj/src/main/AndroidManifest.xml index 71e7bb9cc..894e88eea 100644 --- a/TMessagesProj/src/main/AndroidManifest.xml +++ b/TMessagesProj/src/main/AndroidManifest.xml @@ -58,6 +58,7 @@ + @@ -100,14 +101,23 @@ android:configChanges="keyboard|keyboardHidden|orientation|screenSize" android:screenOrientation="portrait"> + + - + - @@ -116,7 +126,7 @@ android:resource="@xml/auth"/> - @@ -127,15 +137,22 @@ android:resource="@xml/contacts" /> - + - + + + + + + + + diff --git a/TMessagesProj/src/main/java/org/telegram/SQLite/SQLiteCursor.java b/TMessagesProj/src/main/java/org/telegram/SQLite/SQLiteCursor.java index d03d52ebe..48bd87778 100755 --- a/TMessagesProj/src/main/java/org/telegram/SQLite/SQLiteCursor.java +++ b/TMessagesProj/src/main/java/org/telegram/SQLite/SQLiteCursor.java @@ -10,6 +10,8 @@ package org.telegram.SQLite; import org.telegram.messenger.FileLog; +import java.nio.ByteBuffer; + public class SQLiteCursor { public static final int FIELD_TYPE_INT = 1; @@ -55,28 +57,21 @@ public class SQLiteCursor { return columnByteArrayValue(preparedStatement.getStatementHandle(), columnIndex); } + public int byteArrayLength(int columnIndex) throws SQLiteException { + checkRow(); + return columnByteArrayLength(preparedStatement.getStatementHandle(), columnIndex); + } + + public int byteBufferValue(int columnIndex, ByteBuffer buffer) throws SQLiteException { + checkRow(); + return columnByteBufferValue(preparedStatement.getStatementHandle(), columnIndex, buffer); + } + public int getTypeOf(int columnIndex) throws SQLiteException { checkRow(); return columnType(preparedStatement.getStatementHandle(), columnIndex); } - public Object objectValue(int columnIndex) throws SQLiteException { - checkRow(); - - int type = columnType(preparedStatement.getStatementHandle(), columnIndex); - switch (type) { - case FIELD_TYPE_INT: - return intValue(columnIndex); - case FIELD_TYPE_BYTEARRAY: - return byteArrayValue(columnIndex); - case FIELD_TYPE_FLOAT: - return doubleValue(columnIndex); - case FIELD_TYPE_STRING: - return stringValue(columnIndex); - } - return null; - } - public boolean next() throws SQLiteException { int res = preparedStatement.step(preparedStatement.getStatementHandle()); if(res == -1) { @@ -122,4 +117,6 @@ public class SQLiteCursor { native double columnDoubleValue(int statementHandle, int columnIndex); native String columnStringValue(int statementHandle, int columnIndex); native byte[] columnByteArrayValue(int statementHandle, int columnIndex); + native int columnByteArrayLength(int statementHandle, int columnIndex); + native int columnByteBufferValue(int statementHandle, int columnIndex, ByteBuffer buffer); } diff --git a/TMessagesProj/src/main/java/org/telegram/SQLite/SQLitePreparedStatement.java b/TMessagesProj/src/main/java/org/telegram/SQLite/SQLitePreparedStatement.java index dc208834d..6335d93b8 100755 --- a/TMessagesProj/src/main/java/org/telegram/SQLite/SQLitePreparedStatement.java +++ b/TMessagesProj/src/main/java/org/telegram/SQLite/SQLitePreparedStatement.java @@ -10,6 +10,8 @@ package org.telegram.SQLite; import org.telegram.messenger.FileLog; +import java.nio.ByteBuffer; + public class SQLitePreparedStatement { private boolean isFinalized = false; private int sqliteStatementHandle; @@ -26,35 +28,34 @@ public class SQLitePreparedStatement { sqliteStatementHandle = prepare(db.getSQLiteHandle(), sql); } - public SQLiteCursor query(Object[] args) throws SQLiteException { - if (args == null || args.length != queryArgsCount) { - throw new IllegalArgumentException(); - } - checkFinalized(); + public SQLiteCursor query(Object[] args) throws SQLiteException { + if (args == null || args.length != queryArgsCount) { + throw new IllegalArgumentException(); + } - reset(sqliteStatementHandle); + checkFinalized(); - int i = 1; - for (Object obj : args) { - if (obj == null) { - bindNull(sqliteStatementHandle, i); - } else if (obj instanceof Integer) { - bindInt(sqliteStatementHandle, i, (Integer)obj); - } else if (obj instanceof Double) { - bindDouble(sqliteStatementHandle, i, (Double)obj); - } else if (obj instanceof String) { - bindString(sqliteStatementHandle, i, (String)obj); - } else if (obj instanceof byte[]) { - bindByteArray(sqliteStatementHandle, i, (byte[])obj); - } else { - throw new IllegalArgumentException(); - } - i++; - } + reset(sqliteStatementHandle); - return new SQLiteCursor(this); - } + int i = 1; + for (Object obj : args) { + if (obj == null) { + bindNull(sqliteStatementHandle, i); + } else if (obj instanceof Integer) { + bindInt(sqliteStatementHandle, i, (Integer)obj); + } else if (obj instanceof Double) { + bindDouble(sqliteStatementHandle, i, (Double)obj); + } else if (obj instanceof String) { + bindString(sqliteStatementHandle, i, (String)obj); + } else { + throw new IllegalArgumentException(); + } + i++; + } + + return new SQLiteCursor(this); + } public int step() throws SQLiteException { return step(sqliteStatementHandle); @@ -102,8 +103,8 @@ public class SQLitePreparedStatement { bindDouble(sqliteStatementHandle, index, value); } - public void bindByteArray(int index, byte[] value) throws SQLiteException { - bindByteArray(sqliteStatementHandle, index, value); + public void bindByteBuffer(int index, ByteBuffer value) throws SQLiteException { + bindByteBuffer(sqliteStatementHandle, index, value, value.limit()); } public void bindString(int index, String value) throws SQLiteException { @@ -114,7 +115,7 @@ public class SQLitePreparedStatement { bindLong(sqliteStatementHandle, index, value); } - native void bindByteArray(int statementHandle, int index, byte[] value) throws SQLiteException; + native void bindByteBuffer(int statementHandle, int index, ByteBuffer value, int length) throws SQLiteException; native void bindString(int statementHandle, int index, String value) throws SQLiteException; native void bindInt(int statementHandle, int index, int value) throws SQLiteException; native void bindLong(int statementHandle, int index, long value) throws SQLiteException; diff --git a/TMessagesProj/src/main/java/org/telegram/android/AndroidUtilities.java b/TMessagesProj/src/main/java/org/telegram/android/AndroidUtilities.java new file mode 100644 index 000000000..65752a19f --- /dev/null +++ b/TMessagesProj/src/main/java/org/telegram/android/AndroidUtilities.java @@ -0,0 +1,224 @@ +/* + * This is the source code of Telegram for Android v. 1.4.x. + * It is licensed under GNU GPL v. 2 or later. + * You should have received a copy of the license in this archive (see LICENSE). + * + * Copyright Nikolai Kudashov, 2013-2014. + */ + +package org.telegram.android; + +import android.app.Activity; +import android.content.Context; +import android.content.pm.ActivityInfo; +import android.content.res.Configuration; +import android.graphics.Point; +import android.graphics.Typeface; +import android.os.Build; +import android.os.Environment; +import android.view.Display; +import android.view.Surface; +import android.view.View; +import android.view.WindowManager; +import android.view.inputmethod.InputMethodManager; + +import org.telegram.messenger.FileLog; +import org.telegram.ui.ApplicationLoader; + +import java.io.File; +import java.util.Hashtable; + +public class AndroidUtilities { + private static final Hashtable typefaceCache = new Hashtable(); + private static int prevOrientation = -10; + private static boolean waitingForSms = false; + private static final Integer smsLock = 2; + public static int externalCacheNotAvailableState = 0; + + public static int statusBarHeight = 0; + public static float density = 1; + public static Point displaySize = new Point(); + + static { + density = ApplicationLoader.applicationContext.getResources().getDisplayMetrics().density; + checkDisplaySize(); + } + + public static void lockOrientation(Activity activity) { + if (prevOrientation != -10) { + return; + } + try { + prevOrientation = activity.getRequestedOrientation(); + WindowManager manager = (WindowManager)activity.getSystemService(Activity.WINDOW_SERVICE); + if (manager != null && manager.getDefaultDisplay() != null) { + int rotation = manager.getDefaultDisplay().getRotation(); + int orientation = activity.getResources().getConfiguration().orientation; + + if (rotation == Surface.ROTATION_270) { + if (orientation == Configuration.ORIENTATION_PORTRAIT) { + activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT); + } else { + if (Build.VERSION.SDK_INT >= 9) { + activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_REVERSE_LANDSCAPE); + } else { + activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE); + } + } + } else if (rotation == Surface.ROTATION_90) { + if (orientation == Configuration.ORIENTATION_PORTRAIT) { + if (Build.VERSION.SDK_INT >= 9) { + activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_REVERSE_PORTRAIT); + } else { + activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT); + } + } else { + activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE); + } + } else if (rotation == Surface.ROTATION_0) { + if (orientation == Configuration.ORIENTATION_LANDSCAPE) { + activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE); + } else { + activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT); + } + } else { + if (orientation == Configuration.ORIENTATION_LANDSCAPE) { + if (Build.VERSION.SDK_INT >= 9) { + activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_REVERSE_LANDSCAPE); + } else { + activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE); + } + } else { + if (Build.VERSION.SDK_INT >= 9) { + activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_REVERSE_PORTRAIT); + } else { + activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT); + } + } + } + } + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + + public static void unlockOrientation(Activity activity) { + try { + if (prevOrientation != -10) { + activity.setRequestedOrientation(prevOrientation); + prevOrientation = -10; + } + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + + public static Typeface getTypeface(String assetPath) { + synchronized (typefaceCache) { + if (!typefaceCache.containsKey(assetPath)) { + try { + Typeface t = Typeface.createFromAsset(ApplicationLoader.applicationContext.getAssets(), assetPath); + typefaceCache.put(assetPath, t); + } catch (Exception e) { + FileLog.e("Typefaces", "Could not get typeface '" + assetPath + "' because " + e.getMessage()); + return null; + } + } + return typefaceCache.get(assetPath); + } + } + + public static boolean isWaitingForSms() { + boolean value = false; + synchronized (smsLock) { + value = waitingForSms; + } + return value; + } + + public static void setWaitingForSms(boolean value) { + synchronized (smsLock) { + waitingForSms = value; + } + } + + public static void showKeyboard(View view) { + if (view == null) { + return; + } + InputMethodManager inputManager = (InputMethodManager)view.getContext().getSystemService(Context.INPUT_METHOD_SERVICE); + inputManager.showSoftInput(view, InputMethodManager.SHOW_IMPLICIT); + + ((InputMethodManager) view.getContext().getSystemService(Context.INPUT_METHOD_SERVICE)).showSoftInput(view, 0); + } + + public static boolean isKeyboardShowed(View view) { + if (view == null) { + return false; + } + InputMethodManager inputManager = (InputMethodManager) view.getContext().getSystemService(Context.INPUT_METHOD_SERVICE); + return inputManager.isActive(view); + } + + public static void hideKeyboard(View view) { + if (view == null) { + return; + } + InputMethodManager imm = (InputMethodManager) view.getContext().getSystemService(Context.INPUT_METHOD_SERVICE); + if (!imm.isActive()) { + return; + } + imm.hideSoftInputFromWindow(view.getWindowToken(), 0); + } + + public static File getCacheDir() { + if (externalCacheNotAvailableState == 1 || externalCacheNotAvailableState == 0 && Environment.getExternalStorageState().startsWith(Environment.MEDIA_MOUNTED)) { + externalCacheNotAvailableState = 1; + try { + File file = ApplicationLoader.applicationContext.getExternalCacheDir(); + if (file != null) { + return file; + } + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + externalCacheNotAvailableState = 2; + try { + File file = ApplicationLoader.applicationContext.getCacheDir(); + if (file != null) { + return file; + } + } catch (Exception e) { + FileLog.e("tmessages", e); + } + return new File(""); + } + + public static int dp(int value) { + return (int)(Math.max(1, density * value)); + } + + public static int dpf(float value) { + return (int)Math.ceil(density * value); + } + + public static void checkDisplaySize() { + try { + WindowManager manager = (WindowManager)ApplicationLoader.applicationContext.getSystemService(Context.WINDOW_SERVICE); + if (manager != null) { + Display display = manager.getDefaultDisplay(); + if (display != null) { + if(android.os.Build.VERSION.SDK_INT < 13) { + displaySize.set(display.getWidth(), display.getHeight()); + } else { + display.getSize(displaySize); + } + FileLog.e("tmessages", "display size = " + displaySize.x + " " + displaySize.y); + } + } + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } +} diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/AppStartReceiver.java b/TMessagesProj/src/main/java/org/telegram/android/AppStartReceiver.java similarity index 90% rename from TMessagesProj/src/main/java/org/telegram/messenger/AppStartReceiver.java rename to TMessagesProj/src/main/java/org/telegram/android/AppStartReceiver.java index d1048d029..aa630862f 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/AppStartReceiver.java +++ b/TMessagesProj/src/main/java/org/telegram/android/AppStartReceiver.java @@ -6,12 +6,13 @@ * Copyright Nikolai Kudashov, 2013-2014. */ -package org.telegram.messenger; +package org.telegram.android; import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; +import org.telegram.messenger.Utilities; import org.telegram.ui.ApplicationLoader; public class AppStartReceiver extends BroadcastReceiver { diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/AuthenticatorService.java b/TMessagesProj/src/main/java/org/telegram/android/AuthenticatorService.java similarity index 98% rename from TMessagesProj/src/main/java/org/telegram/messenger/AuthenticatorService.java rename to TMessagesProj/src/main/java/org/telegram/android/AuthenticatorService.java index e88d46ed2..1d9c4bdcc 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/AuthenticatorService.java +++ b/TMessagesProj/src/main/java/org/telegram/android/AuthenticatorService.java @@ -6,7 +6,7 @@ * Copyright Nikolai Kudashov, 2013. */ -package org.telegram.messenger; +package org.telegram.android; import android.accounts.AbstractAccountAuthenticator; import android.accounts.Account; diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/ContactsController.java b/TMessagesProj/src/main/java/org/telegram/android/ContactsController.java similarity index 98% rename from TMessagesProj/src/main/java/org/telegram/messenger/ContactsController.java rename to TMessagesProj/src/main/java/org/telegram/android/ContactsController.java index f270ab3b5..33d2b4bf1 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/ContactsController.java +++ b/TMessagesProj/src/main/java/org/telegram/android/ContactsController.java @@ -6,7 +6,7 @@ * Copyright Nikolai Kudashov, 2013. */ -package org.telegram.messenger; +package org.telegram.android; import android.accounts.Account; import android.accounts.AccountManager; @@ -20,6 +20,16 @@ import android.provider.ContactsContract; import android.util.SparseArray; import org.telegram.PhoneFormat.PhoneFormat; +import org.telegram.messenger.BuildVars; +import org.telegram.messenger.ConnectionsManager; +import org.telegram.messenger.FileLog; +import org.telegram.messenger.NotificationCenter; +import org.telegram.messenger.R; +import org.telegram.messenger.RPCRequest; +import org.telegram.messenger.TLObject; +import org.telegram.messenger.TLRPC; +import org.telegram.messenger.UserConfig; +import org.telegram.messenger.Utilities; import org.telegram.ui.ApplicationLoader; import java.util.ArrayList; @@ -151,6 +161,18 @@ public class ContactsController { } } + public void deleteAllAppAccounts() { + try { + AccountManager am = AccountManager.get(ApplicationLoader.applicationContext); + Account[] accounts = am.getAccountsByType("org.telegram.account"); + for (Account c : accounts) { + am.removeAccount(c, null, null); + } + } catch (Exception e) { + e.printStackTrace(); + } + } + public void checkContacts() { Utilities.globalQueue.postRunnable(new Runnable() { @Override @@ -720,7 +742,7 @@ public class ContactsController { }); } } - }, null, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors | RPCRequest.RPCRequestClassCanCompress); + }, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors | RPCRequest.RPCRequestClassCanCompress); } } else { Utilities.stageQueue.postRunnable(new Runnable() { @@ -815,7 +837,7 @@ public class ContactsController { processLoadedContacts(res.contacts, res.users, 0); } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }, true, RPCRequest.RPCRequestClassGeneric); } } @@ -1540,7 +1562,7 @@ public class ContactsController { } }); } - }, null, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors | RPCRequest.RPCRequestClassCanCompress); + }, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors | RPCRequest.RPCRequestClassCanCompress); } public void deleteContact(final ArrayList users) { @@ -1607,6 +1629,6 @@ public class ContactsController { } }); } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }, true, RPCRequest.RPCRequestClassGeneric); } } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/ContactsSyncAdapterService.java b/TMessagesProj/src/main/java/org/telegram/android/ContactsSyncAdapterService.java similarity index 96% rename from TMessagesProj/src/main/java/org/telegram/messenger/ContactsSyncAdapterService.java rename to TMessagesProj/src/main/java/org/telegram/android/ContactsSyncAdapterService.java index d6d3ecd32..852a84838 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/ContactsSyncAdapterService.java +++ b/TMessagesProj/src/main/java/org/telegram/android/ContactsSyncAdapterService.java @@ -6,7 +6,7 @@ * Copyright Nikolai Kudashov, 2013. */ -package org.telegram.messenger; +package org.telegram.android; import android.accounts.Account; import android.accounts.OperationCanceledException; @@ -19,6 +19,8 @@ import android.content.SyncResult; import android.os.Bundle; import android.os.IBinder; +import org.telegram.messenger.FileLog; + public class ContactsSyncAdapterService extends Service { private static SyncAdapterImpl sSyncAdapter = null; diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/Emoji.java b/TMessagesProj/src/main/java/org/telegram/android/Emoji.java similarity index 97% rename from TMessagesProj/src/main/java/org/telegram/messenger/Emoji.java rename to TMessagesProj/src/main/java/org/telegram/android/Emoji.java index 5bd32559d..3e7b108e2 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/Emoji.java +++ b/TMessagesProj/src/main/java/org/telegram/android/Emoji.java @@ -6,7 +6,7 @@ * Copyright Nikolai Kudashov, 2013. */ -package org.telegram.messenger; +package org.telegram.android; import java.io.File; import java.io.InputStream; @@ -26,6 +26,9 @@ import android.view.View; import android.view.ViewGroup; import android.widget.TextView; +import org.telegram.messenger.FileLog; +import org.telegram.messenger.NotificationCenter; +import org.telegram.messenger.Utilities; import org.telegram.ui.ApplicationLoader; public class Emoji { @@ -202,17 +205,17 @@ public class Emoji { 0x00000000D83DDD34L, 0x00000000D83DDD35L, 0x00000000D83DDD3BL, 0x00000000D83DDD36L, 0x00000000D83DDD37L, 0x00000000D83DDD38L, 0x00000000D83DDD39L}}; static { - if (Utilities.density <= 1.0f) { + if (AndroidUtilities.density <= 1.0f) { emojiFullSize = 30; - } else if (Utilities.density <= 1.5f) { + } else if (AndroidUtilities.density <= 1.5f) { emojiFullSize = 45; - } else if (Utilities.density <= 2.0f) { + } else if (AndroidUtilities.density <= 2.0f) { emojiFullSize = 60; } else { emojiFullSize = 90; } - drawImgSize = Utilities.dp(20); - bigImgSize = Utilities.dp(30); + drawImgSize = AndroidUtilities.dp(20); + bigImgSize = AndroidUtilities.dp(30); for (int j = 1; j < data.length; j++) { for (int i = 0; i < data[j].length; i++) { @@ -228,13 +231,13 @@ public class Emoji { try { float scale = 1.0f; int imageResize = 1; - if (Utilities.density <= 1.0f) { + if (AndroidUtilities.density <= 1.0f) { scale = 2.0f; imageResize = 2; - } else if (Utilities.density <= 1.5f) { + } else if (AndroidUtilities.density <= 1.5f) { scale = 3.0f; imageResize = 2; - } else if (Utilities.density <= 2.0f) { + } else if (AndroidUtilities.density <= 2.0f) { scale = 2.0f; } else { scale = 3.0f; @@ -466,7 +469,7 @@ public class Emoji { public static class EmojiSpan extends ImageSpan { private Paint.FontMetricsInt fontMetrics = null; - int size = Utilities.dp(20); + int size = AndroidUtilities.dp(20); public EmojiSpan(Drawable d, int verticalAlignment, int s, Paint.FontMetricsInt original) { super(d, verticalAlignment); @@ -474,7 +477,7 @@ public class Emoji { if (original != null) { size = Math.abs(fontMetrics.descent) + Math.abs(fontMetrics.ascent); if (size == 0) { - size = Utilities.dp(20); + size = AndroidUtilities.dp(20); } } } @@ -488,8 +491,8 @@ public class Emoji { if (fontMetrics == null) { int sz = super.getSize(paint, text, start, end, fm); - int offset = Utilities.dp(8); - int w = Utilities.dp(10); + int offset = AndroidUtilities.dp(8); + int w = AndroidUtilities.dp(10); fm.top = -w - offset; fm.bottom = w - offset; fm.ascent = -w - offset; diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/FastDateFormat.java b/TMessagesProj/src/main/java/org/telegram/android/FastDateFormat.java similarity index 99% rename from TMessagesProj/src/main/java/org/telegram/messenger/FastDateFormat.java rename to TMessagesProj/src/main/java/org/telegram/android/FastDateFormat.java index 91b7d0eb9..0d0a029ae 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/FastDateFormat.java +++ b/TMessagesProj/src/main/java/org/telegram/android/FastDateFormat.java @@ -5,7 +5,7 @@ * * Copyright Nikolai Kudashov, 2013. */ -package org.telegram.messenger; +package org.telegram.android; import java.io.IOException; import java.io.ObjectInputStream; diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/GcmBroadcastReceiver.java b/TMessagesProj/src/main/java/org/telegram/android/GcmBroadcastReceiver.java similarity index 95% rename from TMessagesProj/src/main/java/org/telegram/messenger/GcmBroadcastReceiver.java rename to TMessagesProj/src/main/java/org/telegram/android/GcmBroadcastReceiver.java index 763265830..291717aeb 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/GcmBroadcastReceiver.java +++ b/TMessagesProj/src/main/java/org/telegram/android/GcmBroadcastReceiver.java @@ -6,7 +6,7 @@ * Copyright Nikolai Kudashov, 2013. */ -package org.telegram.messenger; +package org.telegram.android; import android.app.Activity; import android.content.BroadcastReceiver; @@ -14,6 +14,9 @@ import android.content.Context; import android.content.Intent; import org.json.JSONObject; +import org.telegram.messenger.ConnectionsManager; +import org.telegram.messenger.FileLog; +import org.telegram.messenger.Utilities; import org.telegram.ui.ApplicationLoader; public class GcmBroadcastReceiver extends BroadcastReceiver { diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/LocaleController.java b/TMessagesProj/src/main/java/org/telegram/android/LocaleController.java similarity index 67% rename from TMessagesProj/src/main/java/org/telegram/messenger/LocaleController.java rename to TMessagesProj/src/main/java/org/telegram/android/LocaleController.java index 3b80c2a19..df53514f4 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/LocaleController.java +++ b/TMessagesProj/src/main/java/org/telegram/android/LocaleController.java @@ -6,7 +6,7 @@ * Copyright Nikolai Kudashov, 2013-2014. */ -package org.telegram.messenger; +package org.telegram.android; import android.app.Activity; import android.content.BroadcastReceiver; @@ -18,6 +18,11 @@ import android.content.res.Configuration; import android.text.format.DateFormat; import android.util.Xml; +import org.telegram.messenger.ConnectionsManager; +import org.telegram.messenger.FileLog; +import org.telegram.messenger.R; +import org.telegram.messenger.TLRPC; +import org.telegram.messenger.Utilities; import org.telegram.ui.ApplicationLoader; import org.xmlpull.v1.XmlPullParser; @@ -34,6 +39,13 @@ import java.util.TimeZone; public class LocaleController { + static final int QUANTITY_OTHER = 0x0000; + static final int QUANTITY_ZERO = 0x0001; + static final int QUANTITY_ONE = 0x0002; + static final int QUANTITY_TWO = 0x0004; + static final int QUANTITY_FEW = 0x0008; + static final int QUANTITY_MANY = 0x0010; + public static boolean isRTL = false; private static boolean is24HourFormat = false; public static FastDateFormat formatterDay; @@ -44,8 +56,11 @@ public class LocaleController { public static FastDateFormat chatDate; public static FastDateFormat chatFullDate; + private HashMap allRules = new HashMap(); + private Locale currentLocale; private Locale systemDefaultLocale; + private PluralRules currentPluralRules; private LocaleInfo currentLocaleInfo; private LocaleInfo defaultLocalInfo; private HashMap localeValues = new HashMap(); @@ -113,6 +128,30 @@ public class LocaleController { } public LocaleController() { + addRules(new String[]{"bem", "brx", "da", "de", "el", "en", "eo", "es", "et", "fi", "fo", "gl", "he", "iw", "it", "nb", + "nl", "nn", "no", "sv", "af", "bg", "bn", "ca", "eu", "fur", "fy", "gu", "ha", "is", "ku", + "lb", "ml", "mr", "nah", "ne", "om", "or", "pa", "pap", "ps", "so", "sq", "sw", "ta", "te", + "tk", "ur", "zu", "mn", "gsw", "chr", "rm", "pt"}, new PluralRules_One()); + addRules(new String[]{"cs", "sk"}, new PluralRules_Czech()); + addRules(new String[]{"ff", "fr", "kab"}, new PluralRules_French()); + addRules(new String[]{"hr", "ru", "sr", "uk", "be", "bs", "sh"}, new PluralRules_Balkan()); + addRules(new String[]{"lv"}, new PluralRules_Latvian()); + addRules(new String[]{"lt"}, new PluralRules_Lithuanian()); + addRules(new String[]{"pl"}, new PluralRules_Polish()); + addRules(new String[]{"ro", "mo"}, new PluralRules_Romanian()); + addRules(new String[]{"sl"}, new PluralRules_Slovenian()); + addRules(new String[]{"ar"}, new PluralRules_Arabic()); + addRules(new String[]{"mk"}, new PluralRules_Macedonian()); + addRules(new String[]{"cy"}, new PluralRules_Welsh()); + addRules(new String[]{"br"}, new PluralRules_Breton()); + addRules(new String[]{"lag"}, new PluralRules_Langi()); + addRules(new String[]{"shi"}, new PluralRules_Tachelhit()); + addRules(new String[]{"mt"}, new PluralRules_Maltese()); + addRules(new String[]{"ga", "se", "sma", "smi", "smj", "smn", "sms"}, new PluralRules_Two()); + addRules(new String[]{"ak", "am", "bh", "fil", "tl", "guw", "hi", "ln", "mg", "nso", "ti", "wa"}, new PluralRules_Zero()); + addRules(new String[]{"az", "bm", "fa", "ig", "hu", "ja", "kde", "kea", "ko", "my", "ses", "sg", "to", + "tr", "vi", "wo", "yo", "zh", "bo", "dz", "id", "jv", "ka", "km", "kn", "ms", "th"}, new PluralRules_None()); + LocaleInfo localeInfo = new LocaleInfo(); localeInfo.name = "English"; localeInfo.nameEnglish = "English"; @@ -215,6 +254,9 @@ public class LocaleController { if (currentInfo == null && systemDefaultLocale.getLanguage() != null) { currentInfo = languagesDict.get(systemDefaultLocale.getLanguage()); } + if (currentInfo == null) { + currentInfo = languagesDict.get(getLocaleString(systemDefaultLocale)); + } if (currentInfo == null) { currentInfo = languagesDict.get("en"); } @@ -231,6 +273,52 @@ public class LocaleController { } } + private void addRules(String[] languages, PluralRules rules) { + for (String language : languages) { + allRules.put(language, rules); + } + } + + private String stringForQuantity(int quantity) { + switch (quantity) { + case QUANTITY_ZERO: + return "zero"; + case QUANTITY_ONE: + return "one"; + case QUANTITY_TWO: + return "two"; + case QUANTITY_FEW: + return "few"; + case QUANTITY_MANY: + return "many"; + default: + return "other"; + } + } + + private String getLocaleString(Locale locale) { + if (locale == null) { + return ""; + } + String languageCode = locale.getLanguage(); + String countryCode = locale.getCountry(); + String variantCode = locale.getVariant(); + if (languageCode.length() == 0 && countryCode.length() == 0) { + return ""; + } + StringBuilder result = new StringBuilder(11); + result.append(languageCode); + if (countryCode.length() > 0 || variantCode.length() > 0) { + result.append('_'); + } + result.append(countryCode); + if (variantCode.length() > 0) { + result.append('_'); + } + result.append(variantCode); + return result.toString(); + } + public boolean applyLanguageFile(File file) { try { HashMap stringMap = getLocaleFileStrings(file); @@ -430,6 +518,7 @@ public class LocaleController { } currentLocale = newLocale; currentLocaleInfo = localeInfo; + currentPluralRules = allRules.get(currentLocale.getLanguage()); changingConfiguration = true; Locale.setDefault(currentLocale); android.content.res.Configuration config = new android.content.res.Configuration(); @@ -460,6 +549,16 @@ public class LocaleController { return value; } + public static String formatPluralString(String key, int plural) { + if (key == null || key.length() == 0 || getInstance().currentPluralRules == null) { + return "LOC_ERR:" + key; + } + String param = getInstance().stringForQuantity(getInstance().currentPluralRules.quantityForNumber(plural)); + param = key + "_" + param; + int resourceId = ApplicationLoader.applicationContext.getResources().getIdentifier(param, "string", ApplicationLoader.applicationContext.getPackageName()); + return formatString(param, resourceId, plural); + } + public static String formatString(String key, int res, Object... args) { String value = getInstance().localeValues.get(key); if (value == null) { @@ -509,6 +608,7 @@ public class LocaleController { recreateFormatters(); } currentLocale = newLocale; + currentPluralRules = allRules.get(currentLocale.getLanguage()); } } } @@ -645,4 +745,253 @@ public class LocaleController { } } } + + + abstract public static class PluralRules { + abstract int quantityForNumber(int n); + } + + public static class PluralRules_Zero extends PluralRules { + public int quantityForNumber(int count) { + if (count == 0 || count == 1) { + return QUANTITY_ONE; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_Welsh extends PluralRules { + public int quantityForNumber(int count) { + if (count == 0) { + return QUANTITY_ZERO; + } else if (count == 1) { + return QUANTITY_ONE; + } else if (count == 2) { + return QUANTITY_TWO; + } else if (count == 3) { + return QUANTITY_FEW; + } else if (count == 6) { + return QUANTITY_MANY; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_Two extends PluralRules { + public int quantityForNumber(int count) { + if (count == 1) { + return QUANTITY_ONE; + } else if (count == 2) { + return QUANTITY_TWO; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_Tachelhit extends PluralRules { + public int quantityForNumber(int count) { + if (count >= 0 && count <= 1) { + return QUANTITY_ONE; + } else if (count >= 2 && count <= 10) { + return QUANTITY_FEW; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_Slovenian extends PluralRules { + public int quantityForNumber(int count) { + int rem100 = count % 100; + if (rem100 == 1) { + return QUANTITY_ONE; + } else if (rem100 == 2) { + return QUANTITY_TWO; + } else if (rem100 >= 3 && rem100 <= 4) { + return QUANTITY_FEW; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_Romanian extends PluralRules { + public int quantityForNumber(int count) { + int rem100 = count % 100; + if (count == 1) { + return QUANTITY_ONE; + } else if ((count == 0 || (rem100 >= 1 && rem100 <= 19))) { + return QUANTITY_FEW; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_Polish extends PluralRules { + public int quantityForNumber(int count) { + int rem100 = count % 100; + int rem10 = count % 10; + if (count == 1) { + return QUANTITY_ONE; + } else if (rem10 >= 2 && rem10 <= 4 && !(rem100 >= 12 && rem100 <= 14) && !(rem100 >= 22 && rem100 <= 24)) { + return QUANTITY_FEW; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_One extends PluralRules { + public int quantityForNumber(int count) { + return count == 1 ? QUANTITY_ONE : QUANTITY_OTHER; + } + } + + public static class PluralRules_None extends PluralRules { + public int quantityForNumber(int count) { + return QUANTITY_OTHER; + } + } + + public static class PluralRules_Maltese extends PluralRules { + public int quantityForNumber(int count) { + int rem100 = count % 100; + if (count == 1) { + return QUANTITY_ONE; + } else if (count == 0 || (rem100 >= 2 && rem100 <= 10)) { + return QUANTITY_FEW; + } else if (rem100 >= 11 && rem100 <= 19) { + return QUANTITY_MANY; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_Macedonian extends PluralRules { + public int quantityForNumber(int count) { + if (count % 10 == 1 && count != 11) { + return QUANTITY_ONE; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_Lithuanian extends PluralRules { + public int quantityForNumber(int count) { + int rem100 = count % 100; + int rem10 = count % 10; + if (rem10 == 1 && !(rem100 >= 11 && rem100 <= 19)) { + return QUANTITY_ONE; + } else if (rem10 >= 2 && rem10 <= 9 && !(rem100 >= 11 && rem100 <= 19)) { + return QUANTITY_FEW; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_Latvian extends PluralRules { + public int quantityForNumber(int count) { + if (count == 0) { + return QUANTITY_ZERO; + } else if (count % 10 == 1 && count % 100 != 11) { + return QUANTITY_ONE; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_Langi extends PluralRules { + public int quantityForNumber(int count) { + if (count == 0) { + return QUANTITY_ZERO; + } else if (count > 0 && count < 2) { + return QUANTITY_ONE; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_French extends PluralRules { + public int quantityForNumber(int count) { + if (count >= 0 && count < 2) { + return QUANTITY_ONE; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_Czech extends PluralRules { + public int quantityForNumber(int count) { + if (count == 1) { + return QUANTITY_ONE; + } else if (count >= 2 && count <= 4) { + return QUANTITY_FEW; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_Breton extends PluralRules { + public int quantityForNumber(int count) { + if (count == 0) { + return QUANTITY_ZERO; + } else if (count == 1) { + return QUANTITY_ONE; + } else if (count == 2) { + return QUANTITY_TWO; + } else if (count == 3) { + return QUANTITY_FEW; + } else if (count == 6) { + return QUANTITY_MANY; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_Balkan extends PluralRules { + public int quantityForNumber(int count) { + int rem100 = count % 100; + int rem10 = count % 10; + if (rem10 == 1 && rem100 != 11) { + return QUANTITY_ONE; + } else if (rem10 >= 2 && rem10 <= 4 && !(rem100 >= 12 && rem100 <= 14)) { + return QUANTITY_FEW; + } else if ((rem10 == 0 || (rem10 >= 5 && rem10 <= 9) || (rem100 >= 11 && rem100 <= 14))) { + return QUANTITY_MANY; + } else { + return QUANTITY_OTHER; + } + } + } + + public static class PluralRules_Arabic extends PluralRules { + public int quantityForNumber(int count) { + int rem100 = count % 100; + if (count == 0) { + return QUANTITY_ZERO; + } else if (count == 1) { + return QUANTITY_ONE; + } else if (count == 2) { + return QUANTITY_TWO; + } else if (rem100 >= 3 && rem100 <= 10) { + return QUANTITY_FEW; + } else if (rem100 >= 11 && rem100 <= 99) { + return QUANTITY_MANY; + } else { + return QUANTITY_OTHER; + } + } + } } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/MediaController.java b/TMessagesProj/src/main/java/org/telegram/android/MediaController.java similarity index 94% rename from TMessagesProj/src/main/java/org/telegram/messenger/MediaController.java rename to TMessagesProj/src/main/java/org/telegram/android/MediaController.java index edd741ede..40e483260 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/MediaController.java +++ b/TMessagesProj/src/main/java/org/telegram/android/MediaController.java @@ -6,7 +6,7 @@ * Copyright Nikolai Kudashov, 2013-2014. */ -package org.telegram.messenger; +package org.telegram.android; import android.app.ProgressDialog; import android.content.Context; @@ -18,7 +18,6 @@ import android.media.AudioRecord; import android.media.AudioTrack; import android.media.MediaPlayer; import android.media.MediaRecorder; -import android.media.audiofx.AutomaticGainControl; import android.net.Uri; import android.os.Environment; import android.os.ParcelFileDescriptor; @@ -26,6 +25,15 @@ import android.os.Vibrator; import android.provider.MediaStore; import android.view.View; +import org.telegram.messenger.ConnectionsManager; +import org.telegram.messenger.DispatchQueue; +import org.telegram.messenger.FileLoader; +import org.telegram.messenger.FileLog; +import org.telegram.messenger.NotificationCenter; +import org.telegram.messenger.R; +import org.telegram.messenger.TLRPC; +import org.telegram.messenger.UserConfig; +import org.telegram.messenger.Utilities; import org.telegram.objects.MessageObject; import org.telegram.ui.ApplicationLoader; import org.telegram.ui.Cells.ChatMediaCell; @@ -129,6 +137,7 @@ public class MediaController implements NotificationCenter.NotificationCenterDel public final static int recordStopped = 50006; public final static int screenshotTook = 50007; public final static int albumsDidLoaded = 50008; + public final static int audioDidSent = 50009; private HashMap>> loadingFileObservers = new HashMap>>(); private HashMap observersByTag = new HashMap(); @@ -155,7 +164,6 @@ public class MediaController implements NotificationCenter.NotificationCenterDel private final Integer progressTimerSync = 1; private AudioRecord audioRecorder = null; - private Object audioGainObj = null; private TLRPC.TL_audio recordingAudio = null; private File recordingAudioFile = null; private long recordStartTime; @@ -497,7 +505,7 @@ public class MediaController implements NotificationCenter.NotificationCenterDel Thread.sleep(1000); } if (bitmapRegionDecoder != null) { - Bitmap bitmap = bitmapRegionDecoder.decodeRegion(new Rect(0, 0, Utilities.dp(44), Utilities.dp(44)), null); + Bitmap bitmap = bitmapRegionDecoder.decodeRegion(new Rect(0, 0, AndroidUtilities.dp(44), AndroidUtilities.dp(44)), null); int w = bitmap.getWidth(); int h = bitmap.getHeight(); for (int y = 0; y < h; y++) { @@ -869,7 +877,9 @@ public class MediaController implements NotificationCenter.NotificationCenterDel if (currentTotalPcmDuration * progress == currentTotalPcmDuration) { return; } - audioTrackPlayer.pause(); + if (!isPaused) { + audioTrackPlayer.pause(); + } audioTrackPlayer.flush(); fileDecodingQueue.postRunnable(new Runnable() { @Override @@ -882,14 +892,15 @@ public class MediaController implements NotificationCenter.NotificationCenterDel Utilities.RunOnUIThread(new Runnable() { @Override public void run() { - ignoreFirstProgress = 3; - //audioTrackPlayer.setNotificationMarkerPosition((int)(currentTotalPcmDuration * (1 - playingMessageObject.audioProgress))); - lastPlayPcm = (long)(currentTotalPcmDuration * progress); - if (audioTrackPlayer != null) { - audioTrackPlayer.play(); + if (!isPaused) { + ignoreFirstProgress = 3; + lastPlayPcm = (long) (currentTotalPcmDuration * progress); + if (audioTrackPlayer != null) { + audioTrackPlayer.play(); + } + lastProgress = (int) (currentTotalPcmDuration / 48.0f * progress); + checkPlayerQueue(); } - lastProgress = (int)(currentTotalPcmDuration / 48.0f * progress); - checkPlayerQueue(); } }); } @@ -926,7 +937,7 @@ public class MediaController implements NotificationCenter.NotificationCenterDel return true; } clenupPlayer(true); - final File cacheFile = new File(Utilities.getCacheDir(), messageObject.getFileName()); + final File cacheFile = new File(AndroidUtilities.getCacheDir(), messageObject.getFileName()); if (isOpusFile(cacheFile.getAbsolutePath()) == 1) { synchronized (playerObjectSync) { @@ -1144,10 +1155,11 @@ public class MediaController implements NotificationCenter.NotificationCenterDel recordingAudio.dc_id = Integer.MIN_VALUE; recordingAudio.id = UserConfig.lastLocalId; recordingAudio.user_id = UserConfig.getClientUserId(); + recordingAudio.mime_type = "audio/ogg"; UserConfig.lastLocalId--; UserConfig.saveConfig(false); - recordingAudioFile = new File(Utilities.getCacheDir(), MessageObject.getAttachFileName(recordingAudio)); + recordingAudioFile = new File(AndroidUtilities.getCacheDir(), MessageObject.getAttachFileName(recordingAudio)); try { if (startRecord(recordingAudioFile.getAbsolutePath()) == 0) { @@ -1165,31 +1177,6 @@ public class MediaController implements NotificationCenter.NotificationCenterDel recordDialogId = dialog_id; fileBuffer.rewind(); - if (android.os.Build.VERSION.SDK_INT >= 16) { - File f = new File("/vendor/lib/libaudioeffect_jni.so"); - File f2 = new File("/system/lib/libaudioeffect_jni.so"); - if (f.exists() || f2.exists()) { - AutomaticGainControl agc = null; - try { - if (AutomaticGainControl.isAvailable()) { - agc = AutomaticGainControl.create(audioRecorder.getAudioSessionId()); - agc.setEnabled(true); - audioGainObj = agc; - } - } catch (Exception e) { - try { - if (agc != null) { - agc.release(); - agc = null; - } - } catch (Exception e2) { - FileLog.e("tmessages", e2); - } - FileLog.e("tmessages", e); - } - } - } - audioRecorder.startRecording(); } catch (Exception e) { FileLog.e("tmessages", e); @@ -1204,18 +1191,6 @@ public class MediaController implements NotificationCenter.NotificationCenterDel FileLog.e("tmessages", e2); } - if (android.os.Build.VERSION.SDK_INT >= 16 && audioGainObj != null) { - AutomaticGainControl agc = (AutomaticGainControl)audioGainObj; - try { - if (agc != null) { - agc.release(); - agc = null; - } - } catch (Exception e2) { - FileLog.e("tmessages", e2); - } - } - Utilities.RunOnUIThread(new Runnable() { @Override public void run() { @@ -1257,6 +1232,7 @@ public class MediaController implements NotificationCenter.NotificationCenterDel } else { recordingAudioFileToSend.delete(); } + NotificationCenter.getInstance().postNotificationName(audioDidSent); } }); } @@ -1267,17 +1243,6 @@ public class MediaController implements NotificationCenter.NotificationCenterDel audioRecorder.release(); audioRecorder = null; } - if (android.os.Build.VERSION.SDK_INT >= 16 && audioGainObj != null) { - AutomaticGainControl agc = (AutomaticGainControl)audioGainObj; - try { - if (agc != null) { - agc.release(); - agc = null; - } - } catch (Exception e2) { - FileLog.e("tmessages", e2); - } - } } catch (Exception e) { FileLog.e("tmessages", e); } @@ -1292,7 +1257,6 @@ public class MediaController implements NotificationCenter.NotificationCenterDel if (audioRecorder == null) { return; } - //recordTimeCount = System.currentTimeMillis() - recordStartTime; try { sendAfterDone = send; audioRecorder.stop(); @@ -1334,7 +1298,7 @@ public class MediaController implements NotificationCenter.NotificationCenterDel } } if (file == null) { - file = new File(Utilities.getCacheDir(), path); + file = new File(AndroidUtilities.getCacheDir(), path); } final File sourceFile = file; @@ -1466,7 +1430,7 @@ public class MediaController implements NotificationCenter.NotificationCenterDel } } if (cacheFile == null) { - cacheFile = new File(Utilities.getCacheDir(), messageObject.getFileName()); + cacheFile = new File(AndroidUtilities.getCacheDir(), messageObject.getFileName()); } try { currentGifDrawable = new GifDrawable(cacheFile); @@ -1545,7 +1509,7 @@ public class MediaController implements NotificationCenter.NotificationCenterDel UserConfig.lastLocalId--; parcelFD = ApplicationLoader.applicationContext.getContentResolver().openFileDescriptor(uri, "r"); input = new FileInputStream(parcelFD.getFileDescriptor()); - File f = new File(Utilities.getCacheDir(), String.format(Locale.US, "%d.%s", id, ext)); + File f = new File(AndroidUtilities.getCacheDir(), String.format(Locale.US, "%d.%s", id, ext)); output = new FileOutputStream(f); input.getChannel().transferTo(0, input.getChannel().size(), output.getChannel()); UserConfig.saveConfig(false); diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/MessagesController.java b/TMessagesProj/src/main/java/org/telegram/android/MessagesController.java similarity index 82% rename from TMessagesProj/src/main/java/org/telegram/messenger/MessagesController.java rename to TMessagesProj/src/main/java/org/telegram/android/MessagesController.java index 0522800fb..0505dd7aa 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/MessagesController.java +++ b/TMessagesProj/src/main/java/org/telegram/android/MessagesController.java @@ -6,37 +6,36 @@ * Copyright Nikolai Kudashov, 2013. */ -package org.telegram.messenger; +package org.telegram.android; -import android.accounts.Account; -import android.accounts.AccountManager; import android.app.Activity; import android.app.AlertDialog; -import android.app.Notification; -import android.app.NotificationManager; -import android.app.PendingIntent; import android.app.ProgressDialog; import android.content.Context; import android.content.DialogInterface; -import android.content.Intent; import android.content.SharedPreferences; import android.content.pm.PackageInfo; import android.graphics.Bitmap; -import android.media.AudioManager; -import android.media.SoundPool; import android.net.Uri; import android.os.Build; -import android.os.Vibrator; -import android.provider.Settings; -import android.support.v4.app.NotificationCompat; import android.text.Html; -import android.util.SparseArray; -import org.json.JSONArray; -import org.json.JSONObject; +import org.telegram.messenger.BuffersStorage; +import org.telegram.messenger.ByteBufferDesc; +import org.telegram.messenger.ConnectionsManager; +import org.telegram.messenger.FileLoader; +import org.telegram.messenger.FileLog; +import org.telegram.messenger.MessageKeyData; +import org.telegram.messenger.NotificationCenter; +import org.telegram.messenger.R; +import org.telegram.messenger.RPCRequest; +import org.telegram.messenger.TLClassStore; +import org.telegram.messenger.TLObject; +import org.telegram.messenger.TLRPC; +import org.telegram.messenger.UserConfig; +import org.telegram.messenger.Utilities; import org.telegram.objects.MessageObject; import org.telegram.objects.PhotoObject; -import org.telegram.ui.LaunchActivity; import org.telegram.ui.ApplicationLoader; import java.io.File; @@ -56,15 +55,15 @@ public class MessagesController implements NotificationCenter.NotificationCenter public ArrayList dialogs = new ArrayList(); public ArrayList dialogsServerOnly = new ArrayList(); public ConcurrentHashMap dialogs_dict = new ConcurrentHashMap(100, 1.0f, 2); - public SparseArray dialogMessage = new SparseArray(); + public HashMap dialogMessage = new HashMap(); public ConcurrentHashMap> printingUsers = new ConcurrentHashMap>(100, 1.0f, 2); public HashMap printingStrings = new HashMap(); private int lastPrintingStringCount = 0; private HashMap> delayedMessages = new HashMap>(); - public SparseArray sendingMessages = new SparseArray(); - public SparseArray hidenAddToContacts = new SparseArray(); - private SparseArray acceptingChats = new SparseArray(); + public HashMap sendingMessages = new HashMap(); + public HashMap hidenAddToContacts = new HashMap(); + private HashMap acceptingChats = new HashMap(); private ArrayList updatesQueue = new ArrayList(); private ArrayList pendingEncMessagesToDelete = new ArrayList(); private long updatesStartWaitTime = 0; @@ -84,18 +83,15 @@ public class MessagesController implements NotificationCenter.NotificationCenter public boolean updatingState = false; public boolean firstGettingTask = false; public boolean registeringForPush = false; - private long lastSoundPlay = 0; + private long lastStatusUpdateTime = 0; private long statusRequest = 0; private int statusSettingState = 0; private boolean offlineSent = false; private String uploadingAvatar = null; - private SoundPool soundPool; - private int sound; - public boolean enableJoined = true; - public int fontSize = Utilities.dp(16); - public MessageObject currentPushMessage; + public boolean enableJoined = true; + public int fontSize = AndroidUtilities.dp(16); private class UserActionUpdates extends TLRPC.Updates { @@ -116,8 +112,6 @@ public class MessagesController implements NotificationCenter.NotificationCenter public static final int UPDATE_MASK_READ_DIALOG_MESSAGE = 256; public static final int UPDATE_MASK_ALL = UPDATE_MASK_AVATAR | UPDATE_MASK_STATUS | UPDATE_MASK_NAME | UPDATE_MASK_CHAT_AVATAR | UPDATE_MASK_CHAT_NAME | UPDATE_MASK_CHAT_MEMBERS | UPDATE_MASK_USER_PRINT | UPDATE_MASK_USER_PHONE | UPDATE_MASK_READ_DIALOG_MESSAGE; - public long openned_dialog_id; - public static class PrintingUser { public long lastTime; public int userId; @@ -168,6 +162,8 @@ public class MessagesController implements NotificationCenter.NotificationCenter public static final int removeAllMessagesFromDialog = 25; + public static final int notificationsSettingsUpdated = 26; + private static volatile MessagesController Instance = null; public static MessagesController getInstance() { MessagesController localInstance = Instance; @@ -192,13 +188,6 @@ public class MessagesController implements NotificationCenter.NotificationCenter enableJoined = preferences.getBoolean("EnableContactJoined", true); preferences = ApplicationLoader.applicationContext.getSharedPreferences("mainconfig", Activity.MODE_PRIVATE); fontSize = preferences.getInt("fons_size", 16); - - try { - soundPool = new SoundPool(1, AudioManager.STREAM_NOTIFICATION, 0); - sound = soundPool.load(ApplicationLoader.applicationContext, R.raw.sound_a, 1); - } catch (Exception e) { - FileLog.e("tmessages", e); - } } public void addSupportUser() { @@ -233,9 +222,136 @@ public class MessagesController implements NotificationCenter.NotificationCenter @Override public void didReceivedNotification(int id, Object... args) { if (id == FileLoader.FileDidUpload) { - fileDidUploaded((String)args[0], (TLRPC.InputFile)args[1], (TLRPC.InputEncryptedFile)args[2]); + final String location = (String)args[0]; + final TLRPC.InputFile file = (TLRPC.InputFile)args[1]; + final TLRPC.InputEncryptedFile encryptedFile = (TLRPC.InputEncryptedFile)args[2]; + + if (uploadingAvatar != null && uploadingAvatar.equals(location)) { + TLRPC.TL_photos_uploadProfilePhoto req = new TLRPC.TL_photos_uploadProfilePhoto(); + req.caption = ""; + req.crop = new TLRPC.TL_inputPhotoCropAuto(); + req.file = file; + req.geo_point = new TLRPC.TL_inputGeoPointEmpty(); + ConnectionsManager.getInstance().performRpc(req, new RPCRequest.RPCRequestDelegate() { + @Override + public void run(TLObject response, TLRPC.TL_error error) { + if (error == null) { + TLRPC.User user = users.get(UserConfig.getClientUserId()); + if (user == null) { + user = UserConfig.getCurrentUser(); + users.put(user.id, user); + } else { + UserConfig.setCurrentUser(user); + } + if (user == null) { + return; + } + TLRPC.TL_photos_photo photo = (TLRPC.TL_photos_photo) response; + ArrayList sizes = photo.photo.sizes; + TLRPC.PhotoSize smallSize = PhotoObject.getClosestPhotoSizeWithSize(sizes, 100, 100); + TLRPC.PhotoSize bigSize = PhotoObject.getClosestPhotoSizeWithSize(sizes, 1000, 1000); + user.photo = new TLRPC.TL_userProfilePhoto(); + user.photo.photo_id = photo.photo.id; + if (smallSize != null) { + user.photo.photo_small = smallSize.location; + } + if (bigSize != null) { + user.photo.photo_big = bigSize.location; + } else if (smallSize != null) { + user.photo.photo_small = smallSize.location; + } + MessagesStorage.getInstance().clearUserPhotos(user.id); + ArrayList users = new ArrayList(); + users.add(user); + MessagesStorage.getInstance().putUsersAndChats(users, null, false, true); + Utilities.RunOnUIThread(new Runnable() { + @Override + public void run() { + NotificationCenter.getInstance().postNotificationName(updateInterfaces, UPDATE_MASK_AVATAR); + UserConfig.saveConfig(true); + } + }); + } + } + }); + } else { + Utilities.RunOnUIThread(new Runnable() { + @Override + public void run() { + ArrayList arr = delayedMessages.get(location); + if (arr != null) { + for (int a = 0; a < arr.size(); a++) { + DelayedMessage message = arr.get(a); + if (file != null && message.sendRequest != null) { + if (message.type == 0) { + message.sendRequest.media.file = file; + performSendMessageRequest(message.sendRequest, message.obj, message.originalPath); + } else if (message.type == 1) { + if (message.sendRequest.media.thumb == null) { + message.sendRequest.media.thumb = file; + performSendDelayedMessage(message); + } else { + message.sendRequest.media.file = file; + performSendMessageRequest(message.sendRequest, message.obj, message.originalPath); + } + } else if (message.type == 2) { + if (message.sendRequest.media.thumb == null && message.location != null) { + message.sendRequest.media.thumb = file; + performSendDelayedMessage(message); + } else { + message.sendRequest.media.file = file; + performSendMessageRequest(message.sendRequest, message.obj, message.originalPath); + } + } else if (message.type == 3) { + message.sendRequest.media.file = file; + performSendMessageRequest(message.sendRequest, message.obj, message.originalPath); + } + arr.remove(a); + a--; + } else if (encryptedFile != null && message.sendEncryptedRequest != null) { + message.sendEncryptedRequest.media.key = encryptedFile.key; + message.sendEncryptedRequest.media.iv = encryptedFile.iv; + performSendEncryptedRequest(message.sendEncryptedRequest, message.obj, message.encryptedChat, encryptedFile, message.originalPath); + arr.remove(a); + a--; + } + } + if (arr.isEmpty()) { + delayedMessages.remove(location); + } + } + } + }); + } } else if (id == FileLoader.FileDidFailUpload) { - fileDidFailedUpload((String) args[0], (Boolean) args[1]); + final String location = (String) args[0]; + final boolean enc = (Boolean) args[1]; + + if (uploadingAvatar != null && uploadingAvatar.equals(location)) { + uploadingAvatar = null; + } else { + Utilities.RunOnUIThread(new Runnable() { + @Override + public void run() { + ArrayList arr = delayedMessages.get(location); + if (arr != null) { + for (int a = 0; a < arr.size(); a++) { + DelayedMessage obj = arr.get(a); + if (enc && obj.sendEncryptedRequest != null || !enc && obj.sendRequest != null) { + obj.obj.messageOwner.send_state = MESSAGE_SEND_STATE_SEND_ERROR; + sendingMessages.remove(obj.obj.messageOwner.id); + arr.remove(a); + a--; + NotificationCenter.getInstance().postNotificationName(messageSendError, obj.obj.messageOwner.id); + } + } + if (arr.isEmpty()) { + delayedMessages.remove(location); + } + } + } + }); + } } else if (id == messageReceivedByServer) { Integer msgId = (Integer)args[0]; MessageObject obj = dialogMessage.get(msgId); @@ -278,6 +394,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter public void cleanUp() { ContactsController.getInstance().cleanup(); MediaController.getInstance().cleanup(); + NotificationsController.getInstance().cleanup(); dialogs_dict.clear(); dialogs.clear(); @@ -382,18 +499,6 @@ public class MessagesController implements NotificationCenter.NotificationCenter }); } - public void deleteAllAppAccounts() { - try { - AccountManager am = AccountManager.get(ApplicationLoader.applicationContext); - Account[] accounts = am.getAccountsByType("org.telegram.account"); - for (Account c : accounts) { - am.removeAccount(c, null, null); - } - } catch (Exception e) { - e.printStackTrace(); - } - } - public void loadUserPhotos(final int uid, final int offset, final int count, final long max_id, final boolean fromCache, final int classGuid) { if (fromCache) { MessagesStorage.getInstance().getUserPhotos(uid, offset, count, max_id, classGuid); @@ -415,13 +520,14 @@ public class MessagesController implements NotificationCenter.NotificationCenter processLoadedUserPhotos(res, uid, offset, count, max_id, fromCache, classGuid); } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); ConnectionsManager.getInstance().bindRequestToGuid(reqId, classGuid); } } public void processLoadedUserPhotos(final TLRPC.photos_Photos res, final int uid, final int offset, final int count, final long max_id, final boolean fromCache, final int classGuid) { if (!fromCache) { + MessagesStorage.getInstance().putUsersAndChats(res.users, null, true, true); MessagesStorage.getInstance().putUserPhotos(uid, res); } else if (res == null || res.photos.isEmpty()) { loadUserPhotos(uid, offset, count, max_id, false, classGuid); @@ -430,6 +536,16 @@ public class MessagesController implements NotificationCenter.NotificationCenter Utilities.RunOnUIThread(new Runnable() { @Override public void run() { + for (TLRPC.User user : res.users) { + if (fromCache) { + users.putIfAbsent(user.id, user); + } else { + users.put(user.id, user); + if (user.id == UserConfig.getClientUserId()) { + UserConfig.setCurrentUser(user); + } + } + } NotificationCenter.getInstance().postNotificationName(userPhotosLoaded, uid, offset, count, fromCache, classGuid, res.photos); } }); @@ -518,7 +634,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter processLoadedMedia(res, uid, offset, count, max_id, false, classGuid); } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); ConnectionsManager.getInstance().bindRequestToGuid(reqId, classGuid); } } @@ -580,14 +696,14 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); ConnectionsManager.getInstance().bindRequestToGuid(reqId, classGuid); } } public void uploadAndApplyUserAvatar(TLRPC.PhotoSize bigPhoto) { if (bigPhoto != null) { - uploadingAvatar = Utilities.getCacheDir() + "/" + bigPhoto.location.volume_id + "_" + bigPhoto.location.local_id + ".jpg"; + uploadingAvatar = AndroidUtilities.getCacheDir() + "/" + bigPhoto.location.volume_id + "_" + bigPhoto.location.local_id + ".jpg"; FileLoader.getInstance().uploadFile(uploadingAvatar, false); } } @@ -623,7 +739,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter public void run(TLObject response, TLRPC.TL_error error) { } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } public void deleteDialog(final long did, int offset, final boolean onlyHistory) { @@ -688,7 +804,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } else { int encId = (int)(did >> 32); if (onlyHistory) { @@ -734,7 +850,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } }); } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } else { Utilities.RunOnUIThread(new Runnable() { @Override @@ -761,7 +877,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter checkDeletingTask(); if (UserConfig.isClientActivated()) { - if (ConnectionsManager.lastPauseTime == 0) { + if (ConnectionsManager.getInstance().getPauseTime() == 0 && ApplicationLoader.isScreenOn) { if (statusSettingState != 1 && (lastStatusUpdateTime == 0 || lastStatusUpdateTime <= System.currentTimeMillis() - 55000 || offlineSent)) { statusSettingState = 1; @@ -785,9 +901,9 @@ public class MessagesController implements NotificationCenter.NotificationCenter } statusRequest = 0; } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } - } else if (statusSettingState != 2 && !offlineSent && ConnectionsManager.lastPauseTime <= System.currentTimeMillis() - 2000) { + } else if (statusSettingState != 2 && !offlineSent && ConnectionsManager.getInstance().getPauseTime() <= System.currentTimeMillis() - 2000) { statusSettingState = 2; if (statusRequest != 0) { ConnectionsManager.getInstance().cancelRpc(statusRequest, true); @@ -806,7 +922,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } statusRequest = 0; } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } if (updatesStartWaitTime != 0 && updatesStartWaitTime + 1500 < currentTime) { @@ -875,7 +991,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter if (label.length() != 0) { if (count > 1) { if (arr.size() > 2) { - newPrintingStrings.put(key, Html.fromHtml(String.format("%s %s %s", label, String.format(LocaleController.getString("AndMoreTyping", R.string.AndMoreTyping), arr.size() - 2), LocaleController.getString("AreTyping", R.string.AreTyping)))); + newPrintingStrings.put(key, Html.fromHtml(String.format("%s %s", label, LocaleController.formatPluralString("AndMoreTyping", arr.size() - 2)))); } else { newPrintingStrings.put(key, Html.fromHtml(String.format("%s %s", label, LocaleController.getString("AreTyping", R.string.AreTyping)))); } @@ -927,7 +1043,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter public void run(TLObject response, TLRPC.TL_error error) { } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors); ConnectionsManager.getInstance().bindRequestToGuid(reqId, classGuid); } else { int encId = (int)(dialog_id >> 32); @@ -943,7 +1059,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter public void run(TLObject response, TLRPC.TL_error error) { } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors); ConnectionsManager.getInstance().bindRequestToGuid(reqId, classGuid); } } @@ -980,7 +1096,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter processLoadedMessages(res, dialog_id, offset, count, max_id, false, classGuid, 0, 0, 0, 0, false); } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); ConnectionsManager.getInstance().bindRequestToGuid(reqId, classGuid); } } @@ -1062,11 +1178,33 @@ public class MessagesController implements NotificationCenter.NotificationCenter processLoadedDialogs(dialogsRes, null, offset, serverOffset, count, false, false); } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } } - public void processDialogsUpdateRead(final HashMapdialogsToUpdate) { + private void applyDialogsNotificationsSettings(ArrayList dialogs) { + SharedPreferences.Editor editor = null; + for (TLRPC.TL_dialog dialog : dialogs) { + if (dialog.peer != null && dialog.notify_settings instanceof TLRPC.TL_peerNotifySettings) { + if (editor == null) { + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Activity.MODE_PRIVATE); + editor = preferences.edit(); + } + int dialog_id = dialog.peer.user_id; + if (dialog_id == 0) { + dialog_id = -dialog.peer.chat_id; + } + if (dialog.notify_settings.mute_until != 0) { + editor.putInt("notify2_" + dialog_id, 2); + } + } + } + if (editor != null) { + editor.commit(); + } + } + + public void processDialogsUpdateRead(final HashMap dialogsToUpdate) { Utilities.RunOnUIThread(new Runnable() { @Override public void run() { @@ -1076,6 +1214,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter currentDialog.unread_count = entry.getValue(); } } + NotificationsController.getInstance().processDialogsUpdateRead(dialogsToUpdate, true); NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); } }); @@ -1088,6 +1227,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter final HashMap new_dialogs_dict = new HashMap(); final HashMap new_dialogMessage = new HashMap(); final HashMap usersLocal = new HashMap(); + final HashMap dialogsToUpdate = new HashMap(); for (TLRPC.User u : dialogsRes.users) { usersLocal.put(u.id, u); @@ -1111,6 +1251,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } new_dialogs_dict.put(d.id, d); + dialogsToUpdate.put(d.id, d.unread_count); } Utilities.RunOnUIThread(new Runnable() { @@ -1172,6 +1313,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter dialogsServerOnly.add(d); } } + NotificationsController.getInstance().processDialogsUpdateRead(dialogsToUpdate, true); NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); } }); @@ -1204,9 +1346,9 @@ public class MessagesController implements NotificationCenter.NotificationCenter loadingDialogs = false; if (resetEnd) { dialogsEndReached = false; - NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); } loadDialogs(offset, serverOffset, count, false); + NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); } }); return; @@ -1255,6 +1397,9 @@ public class MessagesController implements NotificationCenter.NotificationCenter Utilities.RunOnUIThread(new Runnable() { @Override public void run() { + if (!isCache) { + applyDialogsNotificationsSettings(dialogsRes.dialogs); + } for (TLRPC.User u : dialogsRes.users) { if (isCache) { if (u.id == UserConfig.getClientUserId() || u.id / 1000 == 333) { @@ -1350,20 +1495,18 @@ public class MessagesController implements NotificationCenter.NotificationCenter size.type = "s"; sizes.add(size); } - size = FileLoader.scaleAndSaveImage(bitmap, 320, 320, 87, false); + size = FileLoader.scaleAndSaveImage(bitmap, 320, 320, 80, false); if (size != null) { size.type = "m"; sizes.add(size); } - size = FileLoader.scaleAndSaveImage(bitmap, 800, 800, 87, false); + size = FileLoader.scaleAndSaveImage(bitmap, 800, 800, 80, false); if (size != null) { size.type = "x"; sizes.add(size); } - if (Build.VERSION.SDK_INT < 11) { - if (bitmap != null) { - bitmap.recycle(); - } + if (bitmap != null) { + bitmap.recycle(); } if (sizes.isEmpty()) { return null; @@ -1403,7 +1546,26 @@ public class MessagesController implements NotificationCenter.NotificationCenter req.max_id = max_positive_id; req.offset = offset; if (offset == 0) { + NotificationsController.getInstance().processReadMessages(null, dialog_id, 0, max_positive_id); MessagesStorage.getInstance().processPendingRead(dialog_id, max_positive_id, max_date, false); + MessagesStorage.getInstance().storageQueue.postRunnable(new Runnable() { + @Override + public void run() { + Utilities.RunOnUIThread(new Runnable() { + @Override + public void run() { + TLRPC.TL_dialog dialog = dialogs_dict.get(dialog_id); + if (dialog != null) { + dialog.unread_count = 0; + NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); + } + HashMap dialogsToUpdate = new HashMap(); + dialogsToUpdate.put(dialog_id, 0); + NotificationsController.getInstance().processDialogsUpdateRead(dialogsToUpdate, true); + } + }); + } + }); } if (req.max_id != Integer.MAX_VALUE) { ConnectionsManager.getInstance().performRpc(req, new RPCRequest.RPCRequestDelegate() { @@ -1436,26 +1598,9 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } - MessagesStorage.getInstance().storageQueue.postRunnable(new Runnable() { - @Override - public void run() { - Utilities.RunOnUIThread(new Runnable() { - @Override - public void run() { - if (offset == 0) { - TLRPC.TL_dialog dialog = dialogs_dict.get(dialog_id); - if (dialog != null) { - dialog.unread_count = 0; - NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); - } - } - } - }); - } - }); if (offset == 0) { TLRPC.TL_messages_receivedMessages req2 = new TLRPC.TL_messages_receivedMessages(); req2.max_id = max_positive_id; @@ -1464,12 +1609,13 @@ public class MessagesController implements NotificationCenter.NotificationCenter public void run(TLObject response, TLRPC.TL_error error) { } - }, null, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors); + }, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors); } } else { if (max_date == 0) { return; } + NotificationsController.getInstance().processReadMessages(null, dialog_id, max_date, 0); int encId = (int)(dialog_id >> 32); TLRPC.EncryptedChat chat = encryptedChats.get(encId); if (chat.auth_key != null && chat.auth_key.length > 1 && chat instanceof TLRPC.TL_encryptedChat) { @@ -1484,7 +1630,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter public void run(TLObject response, TLRPC.TL_error error) { //MessagesStorage.getInstance().processPendingRead(dialog_id, max_id, max_date, true); } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } MessagesStorage.getInstance().processPendingRead(dialog_id, max_id, max_date, false); @@ -1499,6 +1645,9 @@ public class MessagesController implements NotificationCenter.NotificationCenter dialog.unread_count = 0; NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); } + HashMap dialogsToUpdate = new HashMap(); + dialogsToUpdate.put(dialog_id, 0); + NotificationsController.getInstance().processDialogsUpdateRead(dialogsToUpdate, true); } }); } @@ -1732,7 +1881,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter type = 2; newMsg.message = "-1"; TLRPC.FileLocation location1 = photo.sizes.get(photo.sizes.size() - 1).location; - newMsg.attachPath = Utilities.getCacheDir() + "/" + location1.volume_id + "_" + location1.local_id + ".jpg"; + newMsg.attachPath = AndroidUtilities.getCacheDir() + "/" + location1.volume_id + "_" + location1.local_id + ".jpg"; } else if (video != null) { newMsg = new TLRPC.TL_message(); newMsg.media = new TLRPC.TL_messageMediaVideo(); @@ -1896,6 +2045,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter reqSend.media.duration = video.duration; reqSend.media.w = video.w; reqSend.media.h = video.h; + reqSend.media.mime_type = video.mime_type; DelayedMessage delayedMessage = new DelayedMessage(); delayedMessage.originalPath = originalPath; delayedMessage.sendRequest = reqSend; @@ -1944,14 +2094,24 @@ public class MessagesController implements NotificationCenter.NotificationCenter performSendMessageRequest(reqSend, newMsgObj, null); } } else if (type == 8) { - reqSend.media = new TLRPC.TL_inputMediaUploadedAudio(); - reqSend.media.duration = audio.duration; - DelayedMessage delayedMessage = new DelayedMessage(); - delayedMessage.sendRequest = reqSend; - delayedMessage.type = 3; - delayedMessage.obj = newMsgObj; - delayedMessage.audioLocation = audio; - performSendDelayedMessage(delayedMessage); + if (audio.access_hash == 0) { + reqSend.media = new TLRPC.TL_inputMediaUploadedAudio(); + reqSend.media.duration = audio.duration; + reqSend.media.mime_type = audio.mime_type; + DelayedMessage delayedMessage = new DelayedMessage(); + delayedMessage.sendRequest = reqSend; + delayedMessage.type = 3; + delayedMessage.obj = newMsgObj; + delayedMessage.audioLocation = audio; + performSendDelayedMessage(delayedMessage); + } else { + TLRPC.TL_inputMediaAudio media = new TLRPC.TL_inputMediaAudio(); + media.id = new TLRPC.TL_inputAudio(); + media.id.id = audio.id; + media.id.access_hash = audio.access_hash; + reqSend.media = media; + performSendMessageRequest(reqSend, newMsgObj, null); + } } } else { TLRPC.TL_decryptedMessage reqSend = new TLRPC.TL_decryptedMessage(); @@ -1992,7 +2152,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter performSendEncryptedRequest(reqSend, newMsgObj, encryptedChat, encryptedFile, null); } } else if (type == 3) { - reqSend.media = new TLRPC.TL_decryptedMessageMediaVideo(); + reqSend.media = new TLRPC.TL_decryptedMessageMediaVideo_old(); reqSend.media.duration = video.duration; reqSend.media.size = video.size; reqSend.media.w = video.w; @@ -2000,6 +2160,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter reqSend.media.thumb = video.thumb.bytes; reqSend.media.thumb_h = video.thumb.h; reqSend.media.thumb_w = video.thumb.w; + reqSend.media.mime_type = "video/mp4"; if (video.access_hash == 0) { DelayedMessage delayedMessage = new DelayedMessage(); delayedMessage.originalPath = originalPath; @@ -2056,9 +2217,10 @@ public class MessagesController implements NotificationCenter.NotificationCenter performSendEncryptedRequest(reqSend, newMsgObj, encryptedChat, encryptedFile, null); } } else if (type == 8) { - reqSend.media = new TLRPC.TL_decryptedMessageMediaAudio(); + reqSend.media = new TLRPC.TL_decryptedMessageMediaAudio_old(); reqSend.media.duration = audio.duration; reqSend.media.size = audio.size; + reqSend.media.mime_type = "audio/ogg"; DelayedMessage delayedMessage = new DelayedMessage(); delayedMessage.sendEncryptedRequest = reqSend; @@ -2098,8 +2260,8 @@ public class MessagesController implements NotificationCenter.NotificationCenter if (fileName.equals(fileName2)) { break; } - File cacheFile = new File(Utilities.getCacheDir(), fileName + ".jpg"); - File cacheFile2 = new File(Utilities.getCacheDir(), fileName2 + ".jpg"); + File cacheFile = new File(AndroidUtilities.getCacheDir(), fileName + ".jpg"); + File cacheFile2 = new File(AndroidUtilities.getCacheDir(), fileName2 + ".jpg"); cacheFile.renameTo(cacheFile2); FileLoader.getInstance().replaceImageInCache(fileName, fileName2); size2.location = size.location; @@ -2109,6 +2271,8 @@ public class MessagesController implements NotificationCenter.NotificationCenter } sentMessage.message = newMsg.message; sentMessage.attachPath = newMsg.attachPath; + newMsg.media.photo.id = sentMessage.media.photo.id; + newMsg.media.photo.access_hash = sentMessage.media.photo.access_hash; } else if (sentMessage.media instanceof TLRPC.TL_messageMediaVideo && sentMessage.media.video != null && newMsg.media instanceof TLRPC.TL_messageMediaVideo && newMsg.media.video != null) { MessagesStorage.getInstance().putSentFile(originalPath, sentMessage.media.video, 2); @@ -2118,8 +2282,8 @@ public class MessagesController implements NotificationCenter.NotificationCenter String fileName = size2.location.volume_id + "_" + size2.location.local_id; String fileName2 = size.location.volume_id + "_" + size.location.local_id; if (!fileName.equals(fileName2)) { - File cacheFile = new File(Utilities.getCacheDir(), fileName + ".jpg"); - File cacheFile2 = new File(Utilities.getCacheDir(), fileName2 + ".jpg"); + File cacheFile = new File(AndroidUtilities.getCacheDir(), fileName + ".jpg"); + File cacheFile2 = new File(AndroidUtilities.getCacheDir(), fileName2 + ".jpg"); boolean result = cacheFile.renameTo(cacheFile2); FileLoader.getInstance().replaceImageInCache(fileName, fileName2); size2.location = size.location; @@ -2127,6 +2291,9 @@ public class MessagesController implements NotificationCenter.NotificationCenter } sentMessage.message = newMsg.message; sentMessage.attachPath = newMsg.attachPath; + newMsg.media.video.dc_id = sentMessage.media.video.dc_id; + newMsg.media.video.id = sentMessage.media.video.id; + newMsg.media.video.access_hash = sentMessage.media.video.access_hash; } else if (sentMessage.media instanceof TLRPC.TL_messageMediaDocument && sentMessage.media.document != null && newMsg.media instanceof TLRPC.TL_messageMediaDocument && newMsg.media.document != null) { MessagesStorage.getInstance().putSentFile(originalPath, sentMessage.media.document, 1); @@ -2136,21 +2303,19 @@ public class MessagesController implements NotificationCenter.NotificationCenter String fileName = size2.location.volume_id + "_" + size2.location.local_id; String fileName2 = size.location.volume_id + "_" + size.location.local_id; if (!fileName.equals(fileName2)) { - File cacheFile = new File(Utilities.getCacheDir(), fileName + ".jpg"); - File cacheFile2 = new File(Utilities.getCacheDir(), fileName2 + ".jpg"); + File cacheFile = new File(AndroidUtilities.getCacheDir(), fileName + ".jpg"); + File cacheFile2 = new File(AndroidUtilities.getCacheDir(), fileName2 + ".jpg"); boolean result = cacheFile.renameTo(cacheFile2); FileLoader.getInstance().replaceImageInCache(fileName, fileName2); size2.location = size.location; } } - if (newMsg.attachPath != null && newMsg.attachPath.startsWith(Utilities.getCacheDir().getAbsolutePath())) { + if (newMsg.attachPath != null && newMsg.attachPath.startsWith(AndroidUtilities.getCacheDir().getAbsolutePath())) { File cacheFile = new File(newMsg.attachPath); - File cacheFile2 = new File(Utilities.getCacheDir(), MessageObject.getAttachFileName(sentMessage.media.document)); + File cacheFile2 = new File(AndroidUtilities.getCacheDir(), MessageObject.getAttachFileName(sentMessage.media.document)); boolean result = cacheFile.renameTo(cacheFile2); if (result) { newMsg.attachPath = null; - newMsg.media.document.dc_id = sentMessage.media.document.dc_id; - newMsg.media.document.id = sentMessage.media.document.id; } else { sentMessage.attachPath = newMsg.attachPath; sentMessage.message = newMsg.message; @@ -2159,6 +2324,9 @@ public class MessagesController implements NotificationCenter.NotificationCenter sentMessage.attachPath = newMsg.attachPath; sentMessage.message = newMsg.message; } + newMsg.media.document.dc_id = sentMessage.media.document.dc_id; + newMsg.media.document.id = sentMessage.media.document.id; + newMsg.media.document.access_hash = sentMessage.media.document.access_hash; } else if (sentMessage.media instanceof TLRPC.TL_messageMediaAudio && sentMessage.media.audio != null && newMsg.media instanceof TLRPC.TL_messageMediaAudio && newMsg.media.audio != null) { sentMessage.message = newMsg.message; sentMessage.attachPath = newMsg.attachPath; @@ -2166,12 +2334,13 @@ public class MessagesController implements NotificationCenter.NotificationCenter String fileName = newMsg.media.audio.dc_id + "_" + newMsg.media.audio.id + ".m4a"; String fileName2 = sentMessage.media.audio.dc_id + "_" + sentMessage.media.audio.id + ".m4a"; if (!fileName.equals(fileName2)) { - File cacheFile = new File(Utilities.getCacheDir(), fileName); - File cacheFile2 = new File(Utilities.getCacheDir(), fileName2); + File cacheFile = new File(AndroidUtilities.getCacheDir(), fileName); + File cacheFile2 = new File(AndroidUtilities.getCacheDir(), fileName2); cacheFile.renameTo(cacheFile2); - newMsg.media.audio.dc_id = sentMessage.media.audio.dc_id; - newMsg.media.audio.id = sentMessage.media.audio.id; } + newMsg.media.audio.dc_id = sentMessage.media.audio.dc_id; + newMsg.media.audio.id = sentMessage.media.audio.id; + newMsg.media.audio.access_hash = sentMessage.media.audio.access_hash; } } else if (file != null) { if (newMsg.media instanceof TLRPC.TL_messageMediaPhoto && newMsg.media.photo != null) { @@ -2185,8 +2354,8 @@ public class MessagesController implements NotificationCenter.NotificationCenter size.location.secret = file.access_hash; size.location.local_id = file.key_fingerprint; String fileName2 = size.location.volume_id + "_" + size.location.local_id; - File cacheFile = new File(Utilities.getCacheDir(), fileName + ".jpg"); - File cacheFile2 = new File(Utilities.getCacheDir(), fileName2 + ".jpg"); + File cacheFile = new File(AndroidUtilities.getCacheDir(), fileName + ".jpg"); + File cacheFile2 = new File(AndroidUtilities.getCacheDir(), fileName2 + ".jpg"); boolean result = cacheFile.renameTo(cacheFile2); FileLoader.getInstance().replaceImageInCache(fileName, fileName2); ArrayList arr = new ArrayList(); @@ -2211,6 +2380,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter newMsg.media.video.key = decryptedMessage.media.key; newMsg.media.video.iv = decryptedMessage.media.iv; newMsg.media.video.path = video.path; + newMsg.media.video.mime_type = video.mime_type; ArrayList arr = new ArrayList(); arr.add(newMsg); MessagesStorage.getInstance().putMessages(arr, false, true); @@ -2232,9 +2402,9 @@ public class MessagesController implements NotificationCenter.NotificationCenter newMsg.media.document.thumb = document.thumb; newMsg.media.document.dc_id = file.dc_id; - if (document.path != null && document.path.startsWith(Utilities.getCacheDir().getAbsolutePath())) { + if (document.path != null && document.path.startsWith(AndroidUtilities.getCacheDir().getAbsolutePath())) { File cacheFile = new File(document.path); - File cacheFile2 = new File(Utilities.getCacheDir(), MessageObject.getAttachFileName(newMsg.media.document)); + File cacheFile2 = new File(AndroidUtilities.getCacheDir(), MessageObject.getAttachFileName(newMsg.media.document)); cacheFile.renameTo(cacheFile2); } @@ -2256,12 +2426,13 @@ public class MessagesController implements NotificationCenter.NotificationCenter newMsg.media.audio.key = decryptedMessage.media.key; newMsg.media.audio.iv = decryptedMessage.media.iv; newMsg.media.audio.path = audio.path; + newMsg.media.audio.mime_type = audio.mime_type; String fileName = audio.dc_id + "_" + audio.id + ".m4a"; String fileName2 = newMsg.media.audio.dc_id + "_" + newMsg.media.audio.id + ".m4a"; if (!fileName.equals(fileName2)) { - File cacheFile = new File(Utilities.getCacheDir(), fileName); - File cacheFile2 = new File(Utilities.getCacheDir(), fileName2); + File cacheFile = new File(AndroidUtilities.getCacheDir(), fileName); + File cacheFile2 = new File(AndroidUtilities.getCacheDir(), fileName2); cacheFile.renameTo(cacheFile2); } @@ -2276,44 +2447,44 @@ public class MessagesController implements NotificationCenter.NotificationCenter if (req == null || chat.auth_key == null || chat instanceof TLRPC.TL_encryptedChatRequested || chat instanceof TLRPC.TL_encryptedChatWaiting) { return; } - //TLRPC.decryptedMessageLayer messageLayer = new TLRPC.decryptedMessageLayer(); - //messageLayer.layer = 8; - //messageLayer.message = req; - SerializedData data = new SerializedData(); - req.serializeToStream(data); + int len = req.getObjectSize(); + ByteBufferDesc toEncrypt = BuffersStorage.getInstance().getFreeBuffer(4 + len); + toEncrypt.writeInt32(len); + req.serializeToStream(toEncrypt); - SerializedData toEncrypt = new SerializedData(); - toEncrypt.writeInt32(data.length()); - toEncrypt.writeRaw(data.toByteArray()); - - byte[] innerData = toEncrypt.toByteArray(); - - byte[] messageKeyFull = Utilities.computeSHA1(innerData); + byte[] messageKeyFull = Utilities.computeSHA1(toEncrypt.buffer); byte[] messageKey = new byte[16]; System.arraycopy(messageKeyFull, messageKeyFull.length - 16, messageKey, 0, 16); MessageKeyData keyData = Utilities.generateMessageKeyData(chat.auth_key, messageKey, false); - SerializedData dataForEncryption = new SerializedData(); - dataForEncryption.writeRaw(innerData); - byte[] b = new byte[1]; - while (dataForEncryption.length() % 16 != 0) { + len = toEncrypt.length(); + int extraLen = len % 16 != 0 ? 16 - len % 16 : 0; + ByteBufferDesc dataForEncryption = BuffersStorage.getInstance().getFreeBuffer(len + extraLen); + toEncrypt.position(0); + dataForEncryption.writeRaw(toEncrypt); + if (extraLen != 0) { + byte[] b = new byte[extraLen]; Utilities.random.nextBytes(b); - dataForEncryption.writeByte(b[0]); + dataForEncryption.writeRaw(b); } + BuffersStorage.getInstance().reuseFreeBuffer(toEncrypt); - byte[] encryptedData = Utilities.aesIgeEncryption(dataForEncryption.toByteArray(), keyData.aesKey, keyData.aesIv, true, false, 0); + Utilities.aesIgeEncryption(dataForEncryption.buffer, keyData.aesKey, keyData.aesIv, true, false, 0, dataForEncryption.limit()); - data = new SerializedData(); + ByteBufferDesc data = BuffersStorage.getInstance().getFreeBuffer(8 + messageKey.length + dataForEncryption.length()); + dataForEncryption.position(0); data.writeInt64(chat.key_fingerprint); data.writeRaw(messageKey); - data.writeRaw(encryptedData); + data.writeRaw(dataForEncryption); + BuffersStorage.getInstance().reuseFreeBuffer(dataForEncryption); + data.position(0); - TLObject reqToSend; + TLObject reqToSend = null; if (encryptedFile == null) { TLRPC.TL_messages_sendEncrypted req2 = new TLRPC.TL_messages_sendEncrypted(); - req2.data = data.toByteArray(); + req2.data = data; req2.random_id = req.random_id; req2.peer = new TLRPC.TL_inputEncryptedChat(); req2.peer.chat_id = chat.id; @@ -2321,7 +2492,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter reqToSend = req2; } else { TLRPC.TL_messages_sendEncryptedFile req2 = new TLRPC.TL_messages_sendEncryptedFile(); - req2.data = data.toByteArray(); + req2.data = data; req2.random_id = req.random_id; req2.peer = new TLRPC.TL_inputEncryptedChat(); req2.peer.chat_id = chat.id; @@ -2334,15 +2505,15 @@ public class MessagesController implements NotificationCenter.NotificationCenter public void run(TLObject response, TLRPC.TL_error error) { if (newMsgObj != null) { if (error == null) { - TLRPC.messages_SentEncryptedMessage res = (TLRPC.messages_SentEncryptedMessage) response; + final TLRPC.messages_SentEncryptedMessage res = (TLRPC.messages_SentEncryptedMessage) response; newMsgObj.messageOwner.date = res.date; if (res.file instanceof TLRPC.TL_encryptedFile) { processSentMessage(newMsgObj.messageOwner, null, res.file, req, originalPath); } - MessagesStorage.getInstance().updateMessageStateAndId(newMsgObj.messageOwner.random_id, newMsgObj.messageOwner.id, newMsgObj.messageOwner.id, res.date, true); MessagesStorage.getInstance().storageQueue.postRunnable(new Runnable() { @Override public void run() { + MessagesStorage.getInstance().updateMessageStateAndId(newMsgObj.messageOwner.random_id, newMsgObj.messageOwner.id, newMsgObj.messageOwner.id, res.date, false); Utilities.RunOnUIThread(new Runnable() { @Override public void run() { @@ -2365,7 +2536,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } } - }, null, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassCanCompress); + }); } private void performSendMessageRequest(TLObject req, final MessageObject newMsgObj, final String originalPath) { @@ -2374,7 +2545,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter public void run(TLObject response, TLRPC.TL_error error) { if (error == null) { final int oldId = newMsgObj.messageOwner.id; - ArrayList sentMessages = new ArrayList(); + final ArrayList sentMessages = new ArrayList(); if (response instanceof TLRPC.TL_messages_sentMessage) { TLRPC.TL_messages_sentMessage res = (TLRPC.TL_messages_sentMessage) response; @@ -2449,13 +2620,11 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } } - MessagesStorage.getInstance().updateMessageStateAndId(newMsgObj.messageOwner.random_id, oldId, newMsgObj.messageOwner.id, 0, true); - if (!sentMessages.isEmpty()) { - MessagesStorage.getInstance().putMessages(sentMessages, true, true); - } MessagesStorage.getInstance().storageQueue.postRunnable(new Runnable() { @Override public void run() { + MessagesStorage.getInstance().updateMessageStateAndId(newMsgObj.messageOwner.random_id, oldId, newMsgObj.messageOwner.id, 0, false); + MessagesStorage.getInstance().putMessages(sentMessages, true, false); Utilities.RunOnUIThread(new Runnable() { @Override public void run() { @@ -2477,7 +2646,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter }); } } - }, null, (req instanceof TLRPC.TL_messages_forwardMessages ? null : new RPCRequest.RPCQuickAckDelegate() { + }, (req instanceof TLRPC.TL_messages_forwardMessages ? null : new RPCRequest.RPCQuickAckDelegate() { @Override public void quickAck() { final int msg_id = newMsgObj.messageOwner.id; @@ -2489,7 +2658,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } }); } - }), true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors | RPCRequest.RPCRequestClassCanCompress, ConnectionsManager.DEFAULT_DATACENTER_ID); + }), true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassCanCompress, ConnectionsManager.DEFAULT_DATACENTER_ID); } private void putToDelayedMessages(String location, DelayedMessage message) { @@ -2503,7 +2672,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter private void performSendDelayedMessage(final DelayedMessage message) { if (message.type == 0) { - String location = Utilities.getCacheDir() + "/" + message.location.volume_id + "_" + message.location.local_id + ".jpg"; + String location = AndroidUtilities.getCacheDir() + "/" + message.location.volume_id + "_" + message.location.local_id + ".jpg"; putToDelayedMessages(location, message); if (message.sendRequest != null) { FileLoader.getInstance().uploadFile(location, false); @@ -2513,13 +2682,13 @@ public class MessagesController implements NotificationCenter.NotificationCenter } else if (message.type == 1) { if (message.sendRequest != null) { if (message.sendRequest.media.thumb == null) { - String location = Utilities.getCacheDir() + "/" + message.location.volume_id + "_" + message.location.local_id + ".jpg"; + String location = AndroidUtilities.getCacheDir() + "/" + message.location.volume_id + "_" + message.location.local_id + ".jpg"; putToDelayedMessages(location, message); FileLoader.getInstance().uploadFile(location, false); } else { String location = message.videoLocation.path; if (location == null) { - location = Utilities.getCacheDir() + "/" + message.videoLocation.id + ".mp4"; + location = AndroidUtilities.getCacheDir() + "/" + message.videoLocation.id + ".mp4"; } putToDelayedMessages(location, message); FileLoader.getInstance().uploadFile(location, false); @@ -2527,14 +2696,14 @@ public class MessagesController implements NotificationCenter.NotificationCenter } else { String location = message.videoLocation.path; if (location == null) { - location = Utilities.getCacheDir() + "/" + message.videoLocation.id + ".mp4"; + location = AndroidUtilities.getCacheDir() + "/" + message.videoLocation.id + ".mp4"; } putToDelayedMessages(location, message); FileLoader.getInstance().uploadFile(location, true); } } else if (message.type == 2) { if (message.sendRequest != null && message.sendRequest.media.thumb == null && message.location != null) { - String location = Utilities.getCacheDir() + "/" + message.location.volume_id + "_" + message.location.local_id + ".jpg"; + String location = AndroidUtilities.getCacheDir() + "/" + message.location.volume_id + "_" + message.location.local_id + ".jpg"; putToDelayedMessages(location, message); FileLoader.getInstance().uploadFile(location, false); } else { @@ -2557,134 +2726,6 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } - public void fileDidFailedUpload(final String location, final boolean enc) { - if (uploadingAvatar != null && uploadingAvatar.equals(location)) { - uploadingAvatar = null; - } else { - Utilities.RunOnUIThread(new Runnable() { - @Override - public void run() { - ArrayList arr = delayedMessages.get(location); - if (arr != null) { - for (int a = 0; a < arr.size(); a++) { - DelayedMessage obj = arr.get(a); - if (enc && obj.sendEncryptedRequest != null || !enc && obj.sendRequest != null) { - obj.obj.messageOwner.send_state = MESSAGE_SEND_STATE_SEND_ERROR; - sendingMessages.remove(obj.obj.messageOwner.id); - arr.remove(a); - a--; - NotificationCenter.getInstance().postNotificationName(messageSendError, obj.obj.messageOwner.id); - } - } - if (arr.isEmpty()) { - delayedMessages.remove(location); - } - } - } - }); - } - } - - public void fileDidUploaded(final String location, final TLRPC.InputFile file, final TLRPC.InputEncryptedFile encryptedFile) { - if (uploadingAvatar != null && uploadingAvatar.equals(location)) { - TLRPC.TL_photos_uploadProfilePhoto req = new TLRPC.TL_photos_uploadProfilePhoto(); - req.caption = ""; - req.crop = new TLRPC.TL_inputPhotoCropAuto(); - req.file = file; - req.geo_point = new TLRPC.TL_inputGeoPointEmpty(); - ConnectionsManager.getInstance().performRpc(req, new RPCRequest.RPCRequestDelegate() { - @Override - public void run(TLObject response, TLRPC.TL_error error) { - if (error == null) { - TLRPC.User user = users.get(UserConfig.getClientUserId()); - if (user == null) { - user = UserConfig.getCurrentUser(); - users.put(user.id, user); - } else { - UserConfig.setCurrentUser(user); - } - if (user == null) { - return; - } - TLRPC.TL_photos_photo photo = (TLRPC.TL_photos_photo) response; - ArrayList sizes = photo.photo.sizes; - TLRPC.PhotoSize smallSize = PhotoObject.getClosestPhotoSizeWithSize(sizes, 100, 100); - TLRPC.PhotoSize bigSize = PhotoObject.getClosestPhotoSizeWithSize(sizes, 1000, 1000); - user.photo = new TLRPC.TL_userProfilePhoto(); - user.photo.photo_id = photo.photo.id; - if (smallSize != null) { - user.photo.photo_small = smallSize.location; - } - if (bigSize != null) { - user.photo.photo_big = bigSize.location; - } else if (smallSize != null) { - user.photo.photo_small = smallSize.location; - } - MessagesStorage.getInstance().clearUserPhotos(user.id); - ArrayList users = new ArrayList(); - users.add(user); - MessagesStorage.getInstance().putUsersAndChats(users, null, false, true); - Utilities.RunOnUIThread(new Runnable() { - @Override - public void run() { - NotificationCenter.getInstance().postNotificationName(updateInterfaces, UPDATE_MASK_AVATAR); - UserConfig.saveConfig(true); - } - }); - } - } - }, null, true, RPCRequest.RPCRequestClassGeneric); - } else { - Utilities.RunOnUIThread(new Runnable() { - @Override - public void run() { - ArrayList arr = delayedMessages.get(location); - if (arr != null) { - for (int a = 0; a < arr.size(); a++) { - DelayedMessage message = arr.get(a); - if (file != null && message.sendRequest != null) { - if (message.type == 0) { - message.sendRequest.media.file = file; - performSendMessageRequest(message.sendRequest, message.obj, message.originalPath); - } else if (message.type == 1) { - if (message.sendRequest.media.thumb == null) { - message.sendRequest.media.thumb = file; - performSendDelayedMessage(message); - } else { - message.sendRequest.media.file = file; - performSendMessageRequest(message.sendRequest, message.obj, message.originalPath); - } - } else if (message.type == 2) { - if (message.sendRequest.media.thumb == null && message.location != null) { - message.sendRequest.media.thumb = file; - performSendDelayedMessage(message); - } else { - message.sendRequest.media.file = file; - performSendMessageRequest(message.sendRequest, message.obj, message.originalPath); - } - } else if (message.type == 3) { - message.sendRequest.media.file = file; - performSendMessageRequest(message.sendRequest, message.obj, message.originalPath); - } - arr.remove(a); - a--; - } else if (encryptedFile != null && message.sendEncryptedRequest != null) { - message.sendEncryptedRequest.media.key = encryptedFile.key; - message.sendEncryptedRequest.media.iv = encryptedFile.iv; - performSendEncryptedRequest(message.sendEncryptedRequest, message.obj, message.encryptedChat, encryptedFile, message.originalPath); - arr.remove(a); - a--; - } - } - if (arr.isEmpty()) { - delayedMessages.remove(location); - } - } - } - }); - } - } - public long createChat(String title, ArrayList selectedContacts, final TLRPC.InputFile uploadedAvatar) { TLRPC.TL_messages_createChat req = new TLRPC.TL_messages_createChat(); req.title = title; @@ -2756,17 +2797,17 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } - public void addUserToChat(int chat_id, final TLRPC.User user, final TLRPC.ChatParticipants info) { + public void addUserToChat(int chat_id, final TLRPC.User user, final TLRPC.ChatParticipants info, int count_fwd) { if (user == null) { return; } TLRPC.TL_messages_addChatUser req = new TLRPC.TL_messages_addChatUser(); req.chat_id = chat_id; - req.fwd_limit = 50; + req.fwd_limit = count_fwd; req.user_id = getInputUser(user); ConnectionsManager.getInstance().performRpc(req, new RPCRequest.RPCRequestDelegate() { @@ -2838,7 +2879,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } public void deleteUserFromChat(int chat_id, final TLRPC.User user, final TLRPC.ChatParticipants info) { @@ -2920,7 +2961,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } public void changeChatTitle(int chat_id, String title) { @@ -2980,7 +3021,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } public void changeChatAvatar(int chat_id, TLRPC.InputFile uploadedAvatar) { @@ -3046,7 +3087,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } public void unregistedPush() { @@ -3059,7 +3100,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter public void run(TLObject response, TLRPC.TL_error error) { } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } } @@ -3070,7 +3111,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter public void run(TLObject response, TLRPC.TL_error error) { ConnectionsManager.getInstance().cleanUp(); } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } public void registerForPush(final String regid) { @@ -3136,7 +3177,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } }); } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } } @@ -3163,7 +3204,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } private int getUpdateSeq(TLRPC.Updates updates) { @@ -3221,7 +3262,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter FileLog.e("tmessages", "UPDATES QUEUE PROCEED - OK"); updatesStartWaitTime = 0; if (getDifference) { - final int stateCopy = ConnectionsManager.getInstance().connectionState; + final int stateCopy = ConnectionsManager.getInstance().getConnectionState(); Utilities.RunOnUIThread(new Runnable() { @Override public void run() { @@ -3231,7 +3272,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } else { if (getDifference) { - final int stateCopy = ConnectionsManager.getInstance().connectionState; + final int stateCopy = ConnectionsManager.getInstance().getConnectionState(); Utilities.RunOnUIThread(new Runnable() { @Override public void run() { @@ -3263,9 +3304,9 @@ public class MessagesController implements NotificationCenter.NotificationCenter req.date = MessagesStorage.lastDateValue; req.qts = MessagesStorage.lastQtsValue; FileLog.e("tmessages", "start getDifference with date = " + MessagesStorage.lastDateValue + " pts = " + MessagesStorage.lastPtsValue + " seq = " + MessagesStorage.lastSeqValue); - if (ConnectionsManager.getInstance().connectionState == 0) { - ConnectionsManager.getInstance().connectionState = 3; - final int stateCopy = ConnectionsManager.getInstance().connectionState; + if (ConnectionsManager.getInstance().getConnectionState() == 0) { + ConnectionsManager.getInstance().setConnectionState(3); + final int stateCopy = ConnectionsManager.getInstance().getConnectionState(); Utilities.RunOnUIThread(new Runnable() { @Override public void run() { @@ -3286,7 +3327,6 @@ public class MessagesController implements NotificationCenter.NotificationCenter usersDict.put(user.id, user); } - final ArrayList readMessages = new ArrayList(); final ArrayList msgUpdates = new ArrayList(); if (!res.other_updates.isEmpty()) { for (int a = 0; a < res.other_updates.size(); a++) { @@ -3295,8 +3335,6 @@ public class MessagesController implements NotificationCenter.NotificationCenter msgUpdates.add((TLRPC.TL_updateMessageID) upd); res.other_updates.remove(a); a--; - } else if (upd instanceof TLRPC.TL_updateReadMessages) { - readMessages.addAll(upd.messages); } } } @@ -3313,12 +3351,6 @@ public class MessagesController implements NotificationCenter.NotificationCenter for (TLRPC.Chat chat : res.chats) { chats.put(chat.id, chat); } - - if (currentPushMessage != null && readMessages.contains(currentPushMessage.messageOwner.id)) { - NotificationManager mNotificationManager = (NotificationManager) ApplicationLoader.applicationContext.getSystemService(Context.NOTIFICATION_SERVICE); - mNotificationManager.cancel(1); - currentPushMessage = null; - } } }); @@ -3361,7 +3393,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } - MessageObject lastMessage = null; + final ArrayList pushMessages = new ArrayList(); for (TLRPC.Message message : res.new_messages) { MessageObject obj = new MessageObject(message, usersDict); @@ -3374,13 +3406,10 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } - if (!(res instanceof TLRPC.TL_updates_differenceSlice)) { - if ((dialog_id != openned_dialog_id || ConnectionsManager.lastPauseTime != 0) && !obj.isOut() && obj.messageOwner.unread && (lastMessage == null || lastMessage.messageOwner.date < obj.messageOwner.date)) { - if (!readMessages.contains(obj.messageOwner.id)) { - lastMessage = obj; - } - } + if (!obj.isFromMe() && obj.isUnread()) { + pushMessages.add(obj); } + long uid; if (message.dialog_id != 0) { uid = message.dialog_id; @@ -3404,7 +3433,6 @@ public class MessagesController implements NotificationCenter.NotificationCenter processPendingEncMessages(); - final MessageObject object = lastMessage; Utilities.RunOnUIThread(new Runnable() { @Override public void run() { @@ -3414,8 +3442,8 @@ public class MessagesController implements NotificationCenter.NotificationCenter updateInterfaceWithMessages(key, value); } NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); - if (object != null) { - showInAppNotification(object); + if (!pushMessages.isEmpty()) { + NotificationsController.getInstance().processNewMessages(pushMessages, !(res instanceof TLRPC.TL_updates_differenceSlice)); } } }); @@ -3440,7 +3468,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter MessagesStorage.lastDateValue = res.state.date; MessagesStorage.lastPtsValue = res.state.pts; MessagesStorage.lastQtsValue = res.state.qts; - ConnectionsManager.getInstance().connectionState = 0; + ConnectionsManager.getInstance().setConnectionState(0); processUpdatesQueue(true); } else if (res instanceof TLRPC.TL_updates_differenceSlice) { MessagesStorage.lastDateValue = res.intermediate_state.date; @@ -3451,7 +3479,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } else if (res instanceof TLRPC.TL_updates_differenceEmpty) { MessagesStorage.lastSeqValue = res.seq; MessagesStorage.lastDateValue = res.date; - ConnectionsManager.getInstance().connectionState = 0; + ConnectionsManager.getInstance().setConnectionState(0); processUpdatesQueue(true); } MessagesStorage.getInstance().saveDiffParams(MessagesStorage.lastSeqValue, MessagesStorage.lastPtsValue, MessagesStorage.lastDateValue, MessagesStorage.lastQtsValue); @@ -3463,8 +3491,8 @@ public class MessagesController implements NotificationCenter.NotificationCenter }); } else { gettingDifference = false; - ConnectionsManager.getInstance().connectionState = 0; - final int stateCopy = ConnectionsManager.getInstance().connectionState; + ConnectionsManager.getInstance().setConnectionState(0); + final int stateCopy = ConnectionsManager.getInstance().getConnectionState(); Utilities.RunOnUIThread(new Runnable() { @Override public void run() { @@ -3473,7 +3501,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter }); } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } public void processUpdates(final TLRPC.Updates updates, boolean fromQueue) { @@ -3516,16 +3544,8 @@ public class MessagesController implements NotificationCenter.NotificationCenter if (printUpdate) { NotificationCenter.getInstance().postNotificationName(updateInterfaces, UPDATE_MASK_USER_PRINT); } - if (obj.messageOwner.from_id != UserConfig.getClientUserId()) { - long dialog_id; - if (obj.messageOwner.to_id.chat_id != 0) { - dialog_id = -obj.messageOwner.to_id.chat_id; - } else { - dialog_id = obj.messageOwner.to_id.user_id; - } - if (dialog_id != openned_dialog_id || ConnectionsManager.lastPauseTime != 0 || !ApplicationLoader.isScreenOn) { - showInAppNotification(obj); - } + if (!obj.isFromMe() && obj.isUnread()) { + NotificationsController.getInstance().processNewMessages(objArr, true); } updateInterfaceWithMessages(-updates.chat_id, objArr); NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); @@ -3579,16 +3599,8 @@ public class MessagesController implements NotificationCenter.NotificationCenter if (printUpdate) { NotificationCenter.getInstance().postNotificationName(updateInterfaces, UPDATE_MASK_USER_PRINT); } - if (obj.messageOwner.from_id != UserConfig.getClientUserId()) { - long dialog_id; - if (obj.messageOwner.to_id.chat_id != 0) { - dialog_id = -obj.messageOwner.to_id.chat_id; - } else { - dialog_id = obj.messageOwner.to_id.user_id; - } - if (dialog_id != openned_dialog_id || ConnectionsManager.lastPauseTime != 0 || !ApplicationLoader.isScreenOn) { - showInAppNotification(obj); - } + if (!obj.isFromMe() && obj.isUnread()) { + NotificationsController.getInstance().processNewMessages(objArr, true); } updateInterfaceWithMessages(updates.from_id, objArr); NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); @@ -3690,7 +3702,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter public void run(TLObject response, TLRPC.TL_error error) { } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } MessagesStorage.getInstance().saveDiffParams(MessagesStorage.lastSeqValue, MessagesStorage.lastPtsValue, MessagesStorage.lastDateValue, MessagesStorage.lastQtsValue); } @@ -3702,6 +3714,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter long currentTime = System.currentTimeMillis(); final HashMap> messages = new HashMap>(); + final ArrayList pushMessages = new ArrayList(); final ArrayList messagesArr = new ArrayList(); final ArrayList markAsReadMessages = new ArrayList(); final HashMap markAsReadEncrypted = new HashMap(); @@ -3711,7 +3724,6 @@ public class MessagesController implements NotificationCenter.NotificationCenter final ArrayList updatesOnMainThread = new ArrayList(); final ArrayList tasks = new ArrayList(); final ArrayList contactsIds = new ArrayList(); - MessageObject lastMessage = null; boolean checkForUsers = true; ConcurrentHashMap usersDict; @@ -3789,13 +3801,9 @@ public class MessagesController implements NotificationCenter.NotificationCenter } arr.add(obj); MessagesStorage.lastPtsValue = update.pts; - if (upd.message.from_id != UserConfig.getClientUserId() && upd.message.to_id != null) { - if (uid != openned_dialog_id || ConnectionsManager.lastPauseTime != 0) { - lastMessage = obj; - } + if (!obj.isFromMe() && obj.isUnread()) { + pushMessages.add(obj); } - } else if (update instanceof TLRPC.TL_updateMessageID) { - //can't be here } else if (update instanceof TLRPC.TL_updateReadMessages) { markAsReadMessages.addAll(update.messages); MessagesStorage.lastPtsValue = update.pts; @@ -3843,37 +3851,6 @@ public class MessagesController implements NotificationCenter.NotificationCenter } else if (update instanceof TLRPC.TL_updateUserPhoto) { interfaceUpdateMask |= UPDATE_MASK_AVATAR; MessagesStorage.getInstance().clearUserPhotos(update.user_id); - /*if (!(update.photo instanceof TLRPC.TL_userProfilePhotoEmpty)) { DEPRECATED - if (usersDict.containsKey(update.user_id)) { - TLRPC.TL_messageService newMessage = new TLRPC.TL_messageService(); - newMessage.action = new TLRPC.TL_messageActionUserUpdatedPhoto(); - newMessage.action.newUserPhoto = update.photo; - newMessage.local_id = newMessage.id = UserConfig.getNewMessageId(); - UserConfig.saveConfig(false); - newMessage.unread = true; - newMessage.date = update.date; - newMessage.from_id = update.user_id; - newMessage.to_id = new TLRPC.TL_peerUser(); - newMessage.to_id.user_id = UserConfig.clientUserId; - newMessage.out = false; - newMessage.dialog_id = update.user_id; - - messagesArr.add(newMessage); - MessageObject obj = new MessageObject(newMessage, usersDict); - ArrayList arr = messages.get(newMessage.dialog_id); - if (arr == null) { - arr = new ArrayList(); - messages.put(newMessage.dialog_id, arr); - } - arr.add(obj); - if (newMessage.from_id != UserConfig.clientUserId && newMessage.to_id != null) { - if (newMessage.dialog_id != openned_dialog_id || ApplicationLoader.lastPauseTime != 0) { - lastMessage = obj; - } - } - } - }*/ - updatesOnMainThread.add(update); } else if (update instanceof TLRPC.TL_updateContactRegistered) { if (enableJoined && usersDict.containsKey(update.user_id)) { @@ -3897,11 +3874,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter messages.put(newMessage.dialog_id, arr); } arr.add(obj); - if (newMessage.from_id != UserConfig.getClientUserId() && newMessage.to_id != null) { - if (newMessage.dialog_id != openned_dialog_id || ConnectionsManager.lastPauseTime != 0) { - lastMessage = obj; - } - } + pushMessages.add(obj); } } else if (update instanceof TLRPC.TL_updateContactLink) { if (update.my_link instanceof TLRPC.TL_contacts_myLinkContact || update.my_link instanceof TLRPC.TL_contacts_myLinkRequested && update.my_link.contact) { @@ -3946,11 +3919,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter messages.put(newMessage.dialog_id, arr); } arr.add(obj); - if (newMessage.from_id != UserConfig.getClientUserId() && newMessage.to_id != null) { - if (newMessage.dialog_id != openned_dialog_id || ConnectionsManager.lastPauseTime != 0) { - lastMessage = obj; - } - } + pushMessages.add(obj); } else if (update instanceof TLRPC.TL_updateNewGeoChatMessage) { //DEPRECATED } else if (update instanceof TLRPC.TL_updateNewEncryptedMessage) { @@ -3967,11 +3936,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter messages.put(uid, arr); } arr.add(obj); - if (message.from_id != UserConfig.getClientUserId() && message.to_id != null) { - if (uid != openned_dialog_id || ConnectionsManager.lastPauseTime != 0) { - lastMessage = obj; - } - } + pushMessages.add(obj); } } else if (update instanceof TLRPC.TL_updateEncryptedChatTyping) { TLRPC.EncryptedChat encryptedChat = getEncryptedChat(update.chat_id); @@ -4082,6 +4047,10 @@ public class MessagesController implements NotificationCenter.NotificationCenter } }); } + } else if (update instanceof TLRPC.TL_updateUserBlocked) { + //TODO + } else if (update instanceof TLRPC.TL_updateNotifySettings) { + updatesOnMainThread.add(update); } } if (!messages.isEmpty()) { @@ -4098,7 +4067,6 @@ public class MessagesController implements NotificationCenter.NotificationCenter updatePrintingStrings(); } - final MessageObject lastMessageArg = lastMessage; final int interfaceUpdateMaskFinal = interfaceUpdateMask; final boolean printChangedArg = printChanged; @@ -4112,116 +4080,146 @@ public class MessagesController implements NotificationCenter.NotificationCenter MessagesStorage.getInstance().putMessages(messagesArr, true, true); } - if (!messages.isEmpty() || !markAsReadMessages.isEmpty() || !deletedMessages.isEmpty() || printChanged || !chatInfoToUpdate.isEmpty() || !updatesOnMainThread.isEmpty() || !markAsReadEncrypted.isEmpty() || !contactsIds.isEmpty()) { - Utilities.RunOnUIThread(new Runnable() { - @Override - public void run() { - int updateMask = interfaceUpdateMaskFinal; + Utilities.RunOnUIThread(new Runnable() { + @Override + public void run() { + int updateMask = interfaceUpdateMaskFinal; - boolean avatarsUpdate = false; - if (!updatesOnMainThread.isEmpty()) { - ArrayList dbUsers = new ArrayList(); - ArrayList dbUsersStatus = new ArrayList(); - for (TLRPC.Update update : updatesOnMainThread) { - TLRPC.User toDbUser = new TLRPC.User(); - toDbUser.id = update.user_id; - TLRPC.User currentUser = users.get(update.user_id); - if (update instanceof TLRPC.TL_updateUserStatus) { - if (currentUser != null) { - currentUser.id = update.user_id; - currentUser.status = update.status; + boolean avatarsUpdate = false; + if (!updatesOnMainThread.isEmpty()) { + ArrayList dbUsers = new ArrayList(); + ArrayList dbUsersStatus = new ArrayList(); + SharedPreferences.Editor editor = null; + for (TLRPC.Update update : updatesOnMainThread) { + TLRPC.User toDbUser = new TLRPC.User(); + toDbUser.id = update.user_id; + TLRPC.User currentUser = users.get(update.user_id); + if (update instanceof TLRPC.TL_updateUserStatus) { + if (currentUser != null) { + currentUser.id = update.user_id; + currentUser.status = update.status; + } + toDbUser.status = update.status; + dbUsersStatus.add(toDbUser); + } else if (update instanceof TLRPC.TL_updateUserName) { + if (currentUser != null) { + currentUser.first_name = update.first_name; + currentUser.last_name = update.last_name; + } + toDbUser.first_name = update.first_name; + toDbUser.last_name = update.last_name; + dbUsers.add(toDbUser); + } else if (update instanceof TLRPC.TL_updateUserPhoto) { + if (currentUser != null) { + currentUser.photo = update.photo; + } + avatarsUpdate = true; + toDbUser.photo = update.photo; + dbUsers.add(toDbUser); + } else if (update instanceof TLRPC.TL_updateNotifySettings) { + if (update.notify_settings instanceof TLRPC.TL_peerNotifySettings && update.peer instanceof TLRPC.TL_notifyPeer) { + if (editor == null) { + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Activity.MODE_PRIVATE); + editor = preferences.edit(); } - toDbUser.status = update.status; - dbUsersStatus.add(toDbUser); - } else if (update instanceof TLRPC.TL_updateUserName) { - if (currentUser != null) { - currentUser.first_name = update.first_name; - currentUser.last_name = update.last_name; + int dialog_id = update.peer.peer.user_id; + if (dialog_id == 0) { + dialog_id = -update.peer.peer.chat_id; } - toDbUser.first_name = update.first_name; - toDbUser.last_name = update.last_name; - dbUsers.add(toDbUser); - } else if (update instanceof TLRPC.TL_updateUserPhoto) { - if (currentUser != null) { - currentUser.photo = update.photo; + if (update.notify_settings.mute_until != 0) { + editor.putInt("notify2_" + dialog_id, 2); + } else { + editor.remove("notify2_" + dialog_id); } - avatarsUpdate = true; - toDbUser.photo = update.photo; - dbUsers.add(toDbUser); + } else if (update.peer instanceof TLRPC.TL_notifyChats) { + if (editor == null) { + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Activity.MODE_PRIVATE); + editor = preferences.edit(); + } + editor.putBoolean("EnableGroup", update.notify_settings.mute_until == 0); + editor.putBoolean("EnablePreviewGroup", update.notify_settings.show_previews); + } else if (update.peer instanceof TLRPC.TL_notifyUsers) { + if (editor == null) { + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Activity.MODE_PRIVATE); + editor = preferences.edit(); + } + editor.putBoolean("EnableAll", update.notify_settings.mute_until == 0); + editor.putBoolean("EnablePreviewAll", update.notify_settings.show_previews); } } - MessagesStorage.getInstance().updateUsers(dbUsersStatus, true, true, true); - MessagesStorage.getInstance().updateUsers(dbUsers, false, true, true); } + if (editor != null) { + editor.commit(); + NotificationCenter.getInstance().postNotificationName(notificationsSettingsUpdated); + } + MessagesStorage.getInstance().updateUsers(dbUsersStatus, true, true, true); + MessagesStorage.getInstance().updateUsers(dbUsers, false, true, true); + } - if (!messages.isEmpty()) { - for (HashMap.Entry> entry : messages.entrySet()) { - Long key = entry.getKey(); - ArrayList value = entry.getValue(); - updateInterfaceWithMessages(key, value); - } - NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); + if (!messages.isEmpty()) { + for (HashMap.Entry> entry : messages.entrySet()) { + Long key = entry.getKey(); + ArrayList value = entry.getValue(); + updateInterfaceWithMessages(key, value); } - if (!markAsReadMessages.isEmpty()) { - for (Integer id : markAsReadMessages) { - MessageObject obj = dialogMessage.get(id); - if (obj != null) { - obj.messageOwner.unread = false; + NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); + } + if (!pushMessages.isEmpty()) { + NotificationsController.getInstance().processNewMessages(pushMessages, true); + } + if (!markAsReadMessages.isEmpty()) { + for (Integer id : markAsReadMessages) { + MessageObject obj = dialogMessage.get(id); + if (obj != null) { + obj.messageOwner.unread = false; + updateMask |= UPDATE_MASK_READ_DIALOG_MESSAGE; + } + } + } + if (!markAsReadEncrypted.isEmpty()) { + for (HashMap.Entry entry : markAsReadEncrypted.entrySet()) { + NotificationCenter.getInstance().postNotificationName(messagesReadedEncrypted, entry.getKey(), entry.getValue()); + long dialog_id = (long)(entry.getKey()) << 32; + TLRPC.TL_dialog dialog = dialogs_dict.get(dialog_id); + if (dialog != null) { + MessageObject message = dialogMessage.get(dialog.top_message); + if (message != null && message.messageOwner.date <= entry.getValue()) { + message.messageOwner.unread = false; updateMask |= UPDATE_MASK_READ_DIALOG_MESSAGE; } } - - if (currentPushMessage != null && markAsReadMessages.contains(currentPushMessage.messageOwner.id)) { - NotificationManager mNotificationManager = (NotificationManager)ApplicationLoader.applicationContext.getSystemService(Context.NOTIFICATION_SERVICE); - mNotificationManager.cancel(1); - currentPushMessage = null; - } - } - if (!markAsReadEncrypted.isEmpty()) { - for (HashMap.Entry entry : markAsReadEncrypted.entrySet()) { - NotificationCenter.getInstance().postNotificationName(messagesReadedEncrypted, entry.getKey(), entry.getValue()); - long dialog_id = (long)(entry.getKey()) << 32; - TLRPC.TL_dialog dialog = dialogs_dict.get(dialog_id); - if (dialog != null) { - MessageObject message = dialogMessage.get(dialog.top_message); - if (message != null && message.messageOwner.date <= entry.getValue()) { - message.messageOwner.unread = false; - updateMask |= UPDATE_MASK_READ_DIALOG_MESSAGE; - } - } - } - } - if (!deletedMessages.isEmpty()) { - NotificationCenter.getInstance().postNotificationName(messagesDeleted, deletedMessages); - for (Integer id : deletedMessages) { - MessageObject obj = dialogMessage.get(id); - if (obj != null) { - obj.deleted = true; - } - } - } - if (printChangedArg) { - updateMask |= UPDATE_MASK_USER_PRINT; - } - if (!contactsIds.isEmpty()) { - updateMask |= UPDATE_MASK_NAME; - updateMask |= UPDATE_MASK_USER_PHONE; - } - if (!chatInfoToUpdate.isEmpty()) { - for (TLRPC.ChatParticipants info : chatInfoToUpdate) { - MessagesStorage.getInstance().updateChatInfo(info.chat_id, info, true); - NotificationCenter.getInstance().postNotificationName(chatInfoDidLoaded, info.chat_id, info); - } - } - if (updateMask != 0) { - NotificationCenter.getInstance().postNotificationName(updateInterfaces, updateMask); - } - if (lastMessageArg != null) { - showInAppNotification(lastMessageArg); } } - }); - } + if (!markAsReadMessages.isEmpty()) { + NotificationsController.getInstance().processReadMessages(markAsReadMessages, 0, 0, 0); + } + if (!deletedMessages.isEmpty()) { + NotificationCenter.getInstance().postNotificationName(messagesDeleted, deletedMessages); + for (Integer id : deletedMessages) { + MessageObject obj = dialogMessage.get(id); + if (obj != null) { + obj.deleted = true; + } + } + } + if (printChangedArg) { + updateMask |= UPDATE_MASK_USER_PRINT; + } + if (!contactsIds.isEmpty()) { + updateMask |= UPDATE_MASK_NAME; + updateMask |= UPDATE_MASK_USER_PHONE; + } + if (!chatInfoToUpdate.isEmpty()) { + for (TLRPC.ChatParticipants info : chatInfoToUpdate) { + MessagesStorage.getInstance().updateChatInfo(info.chat_id, info, true); + NotificationCenter.getInstance().postNotificationName(chatInfoDidLoaded, info.chat_id, info); + } + } + if (updateMask != 0) { + NotificationCenter.getInstance().postNotificationName(updateInterfaces, updateMask); + } + } + }); if (!markAsReadMessages.isEmpty() || !markAsReadEncrypted.isEmpty()) { MessagesStorage.getInstance().storageQueue.postRunnable(new Runnable() { @@ -4297,324 +4295,6 @@ public class MessagesController implements NotificationCenter.NotificationCenter return false; } - private void playNotificationSound() { - if (lastSoundPlay > System.currentTimeMillis() - 1800) { - return; - } - try { - lastSoundPlay = System.currentTimeMillis(); - soundPool.play(sound, 1, 1, 1, 0, 1); - } catch (Exception e) { - FileLog.e("tmessages", e); - } - } - - private void showInAppNotification(MessageObject messageObject) { - if (!UserConfig.isClientActivated()) { - return; - } - if (ConnectionsManager.lastPauseTime != 0) { - ConnectionsManager.lastPauseTime = System.currentTimeMillis(); - FileLog.e("tmessages", "reset sleep timeout by received message"); - } - if (messageObject == null) { - return; - } - SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Context.MODE_PRIVATE); - boolean globalEnabled = preferences.getBoolean("EnableAll", true); - boolean groupEnabled = preferences.getBoolean("EnableGroup", true); - - long dialog_id = messageObject.messageOwner.dialog_id; - int chat_id = messageObject.messageOwner.to_id.chat_id; - int user_id = messageObject.messageOwner.to_id.user_id; - if (user_id == 0) { - user_id = messageObject.messageOwner.from_id; - } else if (user_id == UserConfig.getClientUserId()) { - user_id = messageObject.messageOwner.from_id; - } - - if (dialog_id == 0) { - if (chat_id != 0) { - dialog_id = -chat_id; - } else if (user_id != 0) { - dialog_id = user_id; - } - } - - int notify_override = preferences.getInt("notify2_" + dialog_id, 0); - if (notify_override == 2 || (!globalEnabled || chat_id != 0 && !groupEnabled) && notify_override == 0) { - return; - } - - TLRPC.User user = users.get(user_id); - if (user == null) { - return; - } - TLRPC.Chat chat = null; - if (chat_id != 0) { - chat = chats.get(chat_id); - if (chat == null) { - return; - } - } - - int vibrate_override = preferences.getInt("vibrate_" + dialog_id, 0); - - if (ConnectionsManager.lastPauseTime == 0 && ApplicationLoader.isScreenOn) { - boolean inAppSounds = preferences.getBoolean("EnableInAppSounds", true); - boolean inAppVibrate = preferences.getBoolean("EnableInAppVibrate", true); - boolean inAppPreview = preferences.getBoolean("EnableInAppPreview", true); - - if (inAppSounds || inAppVibrate || inAppPreview) { - if ((int)dialog_id == 0) { - TLRPC.EncryptedChat encChat = encryptedChats.get((int)(dialog_id >> 32)); - if (encChat == null) { - return; - } - } - - if (inAppPreview) { - NotificationCenter.getInstance().postNotificationName(701, messageObject); - } - if (inAppVibrate && vibrate_override == 0 || vibrate_override == 1) { - Vibrator v = (Vibrator)ApplicationLoader.applicationContext.getSystemService(Context.VIBRATOR_SERVICE); - v.vibrate(100); - } - if (inAppSounds) { - playNotificationSound(); - } - } - } else { - TLRPC.FileLocation photoPath = null; - String defaultPath = Settings.System.DEFAULT_NOTIFICATION_URI.getPath(); - - NotificationManager mNotificationManager = (NotificationManager)ApplicationLoader.applicationContext.getSystemService(Context.NOTIFICATION_SERVICE); - Intent intent = new Intent(ApplicationLoader.applicationContext, LaunchActivity.class); - String msg = null; - - if ((int)dialog_id != 0) { - if (chat_id != 0) { - intent.putExtra("chatId", chat_id); - } else if (user_id != 0) { - intent.putExtra("userId", user_id); - } - - if (user.photo != null && user.photo.photo_small != null && user.photo.photo_small.volume_id != 0 && user.photo.photo_small.local_id != 0) { - photoPath = user.photo.photo_small; - } - - if (chat_id == 0 && user_id != 0) { - if (preferences.getBoolean("EnablePreviewAll", true)) { - if (messageObject.messageOwner instanceof TLRPC.TL_messageService) { - if (messageObject.messageOwner.action instanceof TLRPC.TL_messageActionUserJoined) { - msg = LocaleController.formatString("NotificationContactJoined", R.string.NotificationContactJoined, Utilities.formatName(user.first_name, user.last_name)); - } else if (messageObject.messageOwner.action instanceof TLRPC.TL_messageActionUserUpdatedPhoto) { - msg = LocaleController.formatString("NotificationContactNewPhoto", R.string.NotificationContactNewPhoto, Utilities.formatName(user.first_name, user.last_name)); - } else if (messageObject.messageOwner.action instanceof TLRPC.TL_messageActionLoginUnknownLocation) { - String date = String.format("%s %s %s", LocaleController.formatterYear.format(((long)messageObject.messageOwner.date) * 1000), LocaleController.getString("OtherAt", R.string.OtherAt), LocaleController.formatterDay.format(((long)messageObject.messageOwner.date) * 1000)); - msg = LocaleController.formatString("NotificationUnrecognizedDevice", R.string.NotificationUnrecognizedDevice, UserConfig.getCurrentUser().first_name, date, messageObject.messageOwner.action.title, messageObject.messageOwner.action.address); - } - } else { - if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaEmpty) { - if (messageObject.messageOwner.message != null && messageObject.messageOwner.message.length() != 0) { - msg = LocaleController.formatString("NotificationMessageText", R.string.NotificationMessageText, Utilities.formatName(user.first_name, user.last_name), messageObject.messageOwner.message); - } else { - msg = LocaleController.formatString("NotificationMessageNoText", R.string.NotificationMessageNoText, Utilities.formatName(user.first_name, user.last_name)); - } - } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaPhoto) { - msg = LocaleController.formatString("NotificationMessagePhoto", R.string.NotificationMessagePhoto, Utilities.formatName(user.first_name, user.last_name)); - } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaVideo) { - msg = LocaleController.formatString("NotificationMessageVideo", R.string.NotificationMessageVideo, Utilities.formatName(user.first_name, user.last_name)); - } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaContact) { - msg = LocaleController.formatString("NotificationMessageContact", R.string.NotificationMessageContact, Utilities.formatName(user.first_name, user.last_name)); - } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaGeo) { - msg = LocaleController.formatString("NotificationMessageMap", R.string.NotificationMessageMap, Utilities.formatName(user.first_name, user.last_name)); - } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaDocument) { - msg = LocaleController.formatString("NotificationMessageDocument", R.string.NotificationMessageDocument, Utilities.formatName(user.first_name, user.last_name)); - } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaAudio) { - msg = LocaleController.formatString("NotificationMessageAudio", R.string.NotificationMessageAudio, Utilities.formatName(user.first_name, user.last_name)); - } - } - } else { - msg = LocaleController.formatString("NotificationMessageNoText", R.string.NotificationMessageNoText, Utilities.formatName(user.first_name, user.last_name)); - } - } else if (chat_id != 0) { - if (preferences.getBoolean("EnablePreviewGroup", true)) { - if (messageObject.messageOwner instanceof TLRPC.TL_messageService) { - if (messageObject.messageOwner.action instanceof TLRPC.TL_messageActionChatAddUser) { - if (messageObject.messageOwner.action.user_id == UserConfig.getClientUserId()) { - msg = LocaleController.formatString("NotificationInvitedToGroup", R.string.NotificationInvitedToGroup, Utilities.formatName(user.first_name, user.last_name), chat.title); - } else { - TLRPC.User u2 = users.get(messageObject.messageOwner.action.user_id); - if (u2 == null) { - return; - } - msg = LocaleController.formatString("NotificationGroupAddMember", R.string.NotificationGroupAddMember, Utilities.formatName(user.first_name, user.last_name), chat.title, Utilities.formatName(u2.first_name, u2.last_name)); - } - } else if (messageObject.messageOwner.action instanceof TLRPC.TL_messageActionChatEditTitle) { - msg = LocaleController.formatString("NotificationEditedGroupName", R.string.NotificationEditedGroupName, Utilities.formatName(user.first_name, user.last_name), messageObject.messageOwner.action.title); - } else if (messageObject.messageOwner.action instanceof TLRPC.TL_messageActionChatEditPhoto || messageObject.messageOwner.action instanceof TLRPC.TL_messageActionChatDeletePhoto) { - msg = LocaleController.formatString("NotificationEditedGroupPhoto", R.string.NotificationEditedGroupPhoto, Utilities.formatName(user.first_name, user.last_name), chat.title); - } else if (messageObject.messageOwner.action instanceof TLRPC.TL_messageActionChatDeleteUser) { - if (messageObject.messageOwner.action.user_id == UserConfig.getClientUserId()) { - msg = LocaleController.formatString("NotificationGroupKickYou", R.string.NotificationGroupKickYou, Utilities.formatName(user.first_name, user.last_name), chat.title); - } else if (messageObject.messageOwner.action.user_id == user.id) { - msg = LocaleController.formatString("NotificationGroupLeftMember", R.string.NotificationGroupLeftMember, Utilities.formatName(user.first_name, user.last_name), chat.title); - } else { - TLRPC.User u2 = users.get(messageObject.messageOwner.action.user_id); - if (u2 == null) { - return; - } - msg = LocaleController.formatString("NotificationGroupKickMember", R.string.NotificationGroupKickMember, Utilities.formatName(user.first_name, user.last_name), chat.title, Utilities.formatName(u2.first_name, u2.last_name)); - } - } - } else { - if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaEmpty) { - if (messageObject.messageOwner.message != null && messageObject.messageOwner.message.length() != 0) { - msg = LocaleController.formatString("NotificationMessageGroupText", R.string.NotificationMessageGroupText, Utilities.formatName(user.first_name, user.last_name), chat.title, messageObject.messageOwner.message); - } else { - msg = LocaleController.formatString("NotificationMessageGroupNoText", R.string.NotificationMessageGroupNoText, Utilities.formatName(user.first_name, user.last_name), chat.title); - } - } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaPhoto) { - msg = LocaleController.formatString("NotificationMessageGroupPhoto", R.string.NotificationMessageGroupPhoto, Utilities.formatName(user.first_name, user.last_name), chat.title); - } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaVideo) { - msg = LocaleController.formatString("NotificationMessageGroupVideo", R.string.NotificationMessageGroupVideo, Utilities.formatName(user.first_name, user.last_name), chat.title); - } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaContact) { - msg = LocaleController.formatString("NotificationMessageGroupContact", R.string.NotificationMessageGroupContact, Utilities.formatName(user.first_name, user.last_name), chat.title); - } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaGeo) { - msg = LocaleController.formatString("NotificationMessageGroupMap", R.string.NotificationMessageGroupMap, Utilities.formatName(user.first_name, user.last_name), chat.title); - } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaDocument) { - msg = LocaleController.formatString("NotificationMessageGroupDocument", R.string.NotificationMessageGroupDocument, Utilities.formatName(user.first_name, user.last_name), chat.title); - } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaAudio) { - msg = LocaleController.formatString("NotificationMessageGroupAudio", R.string.NotificationMessageGroupAudio, Utilities.formatName(user.first_name, user.last_name), chat.title); - } - } - } else { - msg = LocaleController.formatString("NotificationMessageGroupNoText", R.string.NotificationMessageGroupNoText, Utilities.formatName(user.first_name, user.last_name), chat.title); - } - } - } else { - msg = LocaleController.getString("YouHaveNewMessage", R.string.YouHaveNewMessage); - int enc_id = (int)(dialog_id >> 32); - intent.putExtra("encId", enc_id); - } - if (msg == null) { - return; - } - - boolean needVibrate = false; - String choosenSoundPath = null; - int ledColor = 0xff00ff00; - - choosenSoundPath = preferences.getString("sound_path_" + dialog_id, null); - - if (chat_id != 0) { - if (choosenSoundPath != null && choosenSoundPath.equals(defaultPath)) { - choosenSoundPath = null; - } else if (choosenSoundPath == null) { - choosenSoundPath = preferences.getString("GroupSoundPath", defaultPath); - } - needVibrate = preferences.getBoolean("EnableVibrateGroup", true); - ledColor = preferences.getInt("GroupLed", 0xff00ff00); - } else if (user_id != 0) { - if (choosenSoundPath != null && choosenSoundPath.equals(defaultPath)) { - choosenSoundPath = null; - } else if (choosenSoundPath == null) { - choosenSoundPath = preferences.getString("GlobalSoundPath", defaultPath); - } - needVibrate = preferences.getBoolean("EnableVibrateAll", true); - ledColor = preferences.getInt("MessagesLed", 0xff00ff00); - } - if (preferences.contains("color_" + dialog_id)) { - ledColor = preferences.getInt("color_" + dialog_id, 0); - } - - if (!needVibrate && vibrate_override == 1) { - needVibrate = true; - } else if (needVibrate && vibrate_override == 2) { - needVibrate = false; - } - - String name = Utilities.formatName(user.first_name, user.last_name); - if ((int)dialog_id == 0) { - name = LocaleController.getString("AppName", R.string.AppName); - } - String msgShort = msg.replace(name + ": ", "").replace(name + " ", ""); - - intent.setAction("com.tmessages.openchat" + Math.random() + Integer.MAX_VALUE); - intent.setFlags(32768); - PendingIntent contentIntent = PendingIntent.getActivity(ApplicationLoader.applicationContext, 0, intent, PendingIntent.FLAG_ONE_SHOT); - - NotificationCompat.Builder mBuilder = new NotificationCompat.Builder(ApplicationLoader.applicationContext) - .setContentTitle(name) - .setSmallIcon(R.drawable.notification) - .setStyle(new NotificationCompat.BigTextStyle().bigText(msgShort)) - .setContentText(msgShort) - .setAutoCancel(true) - .setTicker(msg); - - if (photoPath != null) { - Bitmap img = FileLoader.getInstance().getImageFromMemory(photoPath, null, null, "50_50", false); - if (img != null) { - mBuilder.setLargeIcon(img); - } - } - - if (choosenSoundPath != null && !choosenSoundPath.equals("NoSound")) { - if (choosenSoundPath.equals(defaultPath)) { - mBuilder.setSound(Settings.System.DEFAULT_NOTIFICATION_URI, AudioManager.STREAM_NOTIFICATION); - } else { - mBuilder.setSound(Uri.parse(choosenSoundPath), AudioManager.STREAM_NOTIFICATION); - } - } - - currentPushMessage = null; - mBuilder.setContentIntent(contentIntent); - mNotificationManager.cancel(1); - Notification notification = mBuilder.build(); - if (ledColor != 0) { - notification.ledARGB = ledColor; - } - notification.ledOnMS = 1000; - notification.ledOffMS = 1000; - if (needVibrate) { - notification.vibrate = new long[]{0, 100, 0, 100}; - } else { - notification.vibrate = new long[]{0, 0}; - } - notification.flags |= Notification.FLAG_SHOW_LIGHTS; - try { - mNotificationManager.notify(1, notification); - if (preferences.getBoolean("EnablePebbleNotifications", false)) { - sendAlertToPebble(msg); - } - currentPushMessage = messageObject; - } catch (Exception e) { - FileLog.e("tmessages", e); - } - } - } - - public void sendAlertToPebble(String message) { - try { - final Intent i = new Intent("com.getpebble.action.SEND_NOTIFICATION"); - - final HashMap data = new HashMap(); - data.put("title", LocaleController.getString("AppName", R.string.AppName)); - data.put("body", message); - final JSONObject jsonData = new JSONObject(data); - final String notificationData = new JSONArray().put(jsonData).toString(); - - i.putExtra("messageType", "PEBBLE_ALERT"); - i.putExtra("sender", LocaleController.formatString("AppName", R.string.AppName)); - i.putExtra("notificationData", notificationData); - - ApplicationLoader.applicationContext.sendBroadcast(i); - } catch (Exception e) { - FileLog.e("tmessages", e); - } - } - public void dialogsUnreadCountIncr(final HashMap values) { Utilities.RunOnUIThread(new Runnable() { @Override @@ -4625,6 +4305,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter dialog.unread_count += entry.getValue(); } } + NotificationsController.getInstance().processDialogsUpdateRead(values, false); NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); } }); @@ -4716,18 +4397,19 @@ public class MessagesController implements NotificationCenter.NotificationCenter if (chat == null) { return null; } - SerializedData is = new SerializedData(message.bytes); + ByteBufferDesc is = BuffersStorage.getInstance().getFreeBuffer(message.bytes.length); + is.writeRaw(message.bytes); + is.position(0); long fingerprint = is.readInt64(); if (chat.key_fingerprint == fingerprint) { byte[] messageKey = is.readData(16); MessageKeyData keyData = Utilities.generateMessageKeyData(chat.auth_key, messageKey, false); - byte[] messageData = is.readData(message.bytes.length - 24); - messageData = Utilities.aesIgeEncryption(messageData, keyData.aesKey, keyData.aesIv, false, false, 0); + Utilities.aesIgeEncryption(is.buffer, keyData.aesKey, keyData.aesIv, false, false, 24, is.limit() - 24); - is = new SerializedData(messageData); int len = is.readInt32(); TLObject object = TLClassStore.Instance().TLdeserialize(is, is.readInt32()); + BuffersStorage.getInstance().reuseFreeBuffer(is); if (object != null) { int from_id = chat.admin_id; @@ -4825,6 +4507,10 @@ public class MessagesController implements NotificationCenter.NotificationCenter newMessage.media.video.access_hash = message.file.access_hash; newMessage.media.video.key = decryptedMessage.media.key; newMessage.media.video.iv = decryptedMessage.media.iv; + newMessage.media.video.mime_type = decryptedMessage.media.mime_type; + if (newMessage.media.video.mime_type == null) { + newMessage.media.video.mime_type = "video/mp4"; + } } else if (decryptedMessage.media instanceof TLRPC.TL_decryptedMessageMediaDocument) { if (decryptedMessage.media.key == null || decryptedMessage.media.key.length != 32 || decryptedMessage.media.iv == null || decryptedMessage.media.iv.length != 32) { return null; @@ -4867,6 +4553,10 @@ public class MessagesController implements NotificationCenter.NotificationCenter newMessage.media.audio.iv = decryptedMessage.media.iv; newMessage.media.audio.dc_id = message.file.dc_id; newMessage.media.audio.duration = decryptedMessage.media.duration; + newMessage.media.audio.mime_type = decryptedMessage.media.mime_type; + if (newMessage.media.audio.mime_type == null) { + newMessage.media.audio.mime_type = "audio/ogg"; + } } else { return null; } @@ -4925,6 +4615,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } else { FileLog.e("tmessages", "fingerprint mismatch"); } + BuffersStorage.getInstance().reuseFreeBuffer(is); return null; } @@ -4991,7 +4682,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter public void run(TLObject response, TLRPC.TL_error error) { } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } public void acceptSecretChat(final TLRPC.EncryptedChat encryptedChat) { @@ -5086,12 +4777,12 @@ public class MessagesController implements NotificationCenter.NotificationCenter }); } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } else { acceptingChats.remove(encryptedChat.id); } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } public void startSecretChat(final Context context, final TLRPC.User user) { @@ -5194,8 +4885,8 @@ public class MessagesController implements NotificationCenter.NotificationCenter dialogsServerOnly.add(d); } } - NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); MessagesStorage.getInstance().putEncryptedChat(chat, user, dialog); + NotificationCenter.getInstance().postNotificationName(dialogsNeedReload); NotificationCenter.getInstance().postNotificationName(encryptedChatCreated, chat); Utilities.stageQueue.postRunnable(new Runnable() { @Override @@ -5230,7 +4921,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter }); } } - }, null, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors); + }, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors); } else { delayedEncryptedChatUpdates.clear(); Utilities.RunOnUIThread(new Runnable() { @@ -5248,7 +4939,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter }); } } - }, null, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors); + }, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors); progressDialog.setButton(DialogInterface.BUTTON_NEGATIVE, LocaleController.getString("Cancel", R.string.Cancel), new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/MessagesStorage.java b/TMessagesProj/src/main/java/org/telegram/android/MessagesStorage.java similarity index 88% rename from TMessagesProj/src/main/java/org/telegram/messenger/MessagesStorage.java rename to TMessagesProj/src/main/java/org/telegram/android/MessagesStorage.java index 1448f6ff1..35378986a 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/MessagesStorage.java +++ b/TMessagesProj/src/main/java/org/telegram/android/MessagesStorage.java @@ -6,7 +6,7 @@ * Copyright Nikolai Kudashov, 2013. */ -package org.telegram.messenger; +package org.telegram.android; import android.text.Html; import android.util.SparseArray; @@ -15,6 +15,17 @@ import org.telegram.PhoneFormat.PhoneFormat; import org.telegram.SQLite.SQLiteCursor; import org.telegram.SQLite.SQLiteDatabase; import org.telegram.SQLite.SQLitePreparedStatement; +import org.telegram.messenger.BuffersStorage; +import org.telegram.messenger.ByteBufferDesc; +import org.telegram.messenger.ConnectionsManager; +import org.telegram.messenger.DispatchQueue; +import org.telegram.messenger.FileLog; +import org.telegram.messenger.NotificationCenter; +import org.telegram.messenger.TLClassStore; +import org.telegram.messenger.TLObject; +import org.telegram.messenger.TLRPC; +import org.telegram.messenger.UserConfig; +import org.telegram.messenger.Utilities; import org.telegram.objects.MessageObject; import org.telegram.ui.ApplicationLoader; @@ -28,6 +39,7 @@ public class MessagesStorage { public DispatchQueue storageQueue = new DispatchQueue("storageQueue"); private SQLiteDatabase database; private File cacheFile; + private BuffersStorage buffersStorage = new BuffersStorage(false); public static int lastDateValue = 0; public static int lastPtsValue = 0; public static int lastQtsValue = 0; @@ -63,8 +75,6 @@ public class MessagesStorage { } public void openDatabase() { - NativeLoader.initNativeLibs(ApplicationLoader.applicationContext); - cacheFile = new File(ApplicationLoader.applicationContext.getFilesDir(), "cache4.db"); boolean createTable = false; @@ -106,6 +116,7 @@ public class MessagesStorage { database.executeFast("CREATE INDEX IF NOT EXISTS date_idx_dialogs ON dialogs(date);").stepThis().dispose(); database.executeFast("CREATE INDEX IF NOT EXISTS date_idx_enc_tasks ON enc_tasks(date);").stepThis().dispose(); database.executeFast("CREATE INDEX IF NOT EXISTS last_mid_idx_dialogs ON dialogs(last_mid);").stepThis().dispose(); + database.executeFast("CREATE INDEX IF NOT EXISTS unread_count_idx_dialogs ON dialogs(unread_count);").stepThis().dispose(); database.executeFast("CREATE INDEX IF NOT EXISTS uid_mid_idx_media ON media(uid, mid);").stepThis().dispose(); database.executeFast("CREATE INDEX IF NOT EXISTS mid_idx_media ON media(mid);").stepThis().dispose(); @@ -170,6 +181,10 @@ public class MessagesStorage { database.executeFast("CREATE INDEX IF NOT EXISTS mid_idx_randoms ON randoms(mid);").stepThis().dispose(); database.executeFast("CREATE TABLE IF NOT EXISTS sent_files_v2(uid TEXT, type INTEGER, data BLOB, PRIMARY KEY (uid, type))").stepThis().dispose(); + + database.executeFast("CREATE INDEX IF NOT EXISTS unread_count_idx_dialogs ON dialogs(unread_count);").stepThis().dispose(); + + loadUnreadMessages(); } } catch (Exception e) { FileLog.e("tmessages", e); @@ -216,13 +231,14 @@ public class MessagesStorage { SQLitePreparedStatement state = database.executeFast("UPDATE params SET lsv = ?, sg = ?, pbytes = ? WHERE id = 1"); state.bindInteger(1, lsv); state.bindInteger(2, sg); + ByteBufferDesc data = buffersStorage.getFreeBuffer(pbytes != null ? pbytes.length : 1); if (pbytes != null) { - state.bindByteArray(3, pbytes); - } else { - state.bindByteArray(3, new byte[1]); + data.writeRaw(pbytes); } + state.bindByteBuffer(3, data.buffer); state.step(); state.dispose(); + buffersStorage.reuseFreeBuffer(data); } catch (Exception e) { FileLog.e("tmessages", e); } @@ -256,23 +272,50 @@ public class MessagesStorage { }); } + public void loadUnreadMessages() { + storageQueue.postRunnable(new Runnable() { + @Override + public void run() { + try { + final HashMap pushDialogs = new HashMap(); + SQLiteCursor cursor = database.queryFinalized("SELECT did, unread_count FROM dialogs WHERE unread_count != 0"); + while (cursor.next()) { + long did = cursor.longValue(0); + int count = cursor.intValue(1); + pushDialogs.put(did, count); + } + cursor.dispose(); + Utilities.RunOnUIThread(new Runnable() { + @Override + public void run() { + NotificationsController.getInstance().processLoadedUnreadMessages(pushDialogs); + } + }); + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + }); + } + public void putWallpapers(final ArrayList wallPapers) { storageQueue.postRunnable(new Runnable() { @Override public void run() { try { + int num = 0; database.executeFast("DELETE FROM wallpapers WHERE 1").stepThis().dispose(); database.beginTransaction(); SQLitePreparedStatement state = database.executeFast("REPLACE INTO wallpapers VALUES(?, ?)"); - int num = 0; for (TLRPC.WallPaper wallPaper : wallPapers) { state.requery(); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(wallPaper.getObjectSize()); wallPaper.serializeToStream(data); state.bindInteger(1, num); - state.bindByteArray(2, data.toByteArray()); + state.bindByteBuffer(2, data.buffer); state.step(); num++; + buffersStorage.reuseFreeBuffer(data); } state.dispose(); database.commitTransaction(); @@ -291,12 +334,12 @@ public class MessagesStorage { SQLiteCursor cursor = database.queryFinalized("SELECT data FROM wallpapers WHERE 1"); ArrayList wallPapers = new ArrayList(); while (cursor.next()) { - byte[] bytes = cursor.byteArrayValue(0); - if (bytes != null) { - SerializedData data = new SerializedData(bytes); - TLRPC.WallPaper wallPaper = (TLRPC.WallPaper)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { + TLRPC.WallPaper wallPaper = (TLRPC.WallPaper) TLClassStore.Instance().TLdeserialize(data, data.readInt32()); wallPapers.add(wallPaper); } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); NotificationCenter.getInstance().postNotificationName(wallpapersDidLoaded, wallPapers); @@ -342,12 +385,12 @@ public class MessagesStorage { final TLRPC.photos_Photos res = new TLRPC.photos_Photos(); while (cursor.next()) { - byte[] messageData = cursor.byteArrayValue(0); - if (messageData != null) { - SerializedData data = new SerializedData(messageData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.Photo photo = (TLRPC.Photo)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); res.photos.add(photo); } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); @@ -392,13 +435,13 @@ public class MessagesStorage { continue; } state.requery(); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(photo.getObjectSize()); photo.serializeToStream(data); state.bindInteger(1, uid); state.bindLong(2, photo.id); - byte[] bytes = data.toByteArray(); - state.bindByteArray(3, bytes); + state.bindByteBuffer(3, data.buffer); state.step(); + buffersStorage.reuseFreeBuffer(data); } state.dispose(); } catch (Exception e) { @@ -423,13 +466,16 @@ public class MessagesStorage { if (cursor.next()) { taskId = cursor.longValue(0); date = cursor.intValue(1); - byte[] data = cursor.byteArrayValue(2); - SerializedData serializedData = new SerializedData(data); - arr = new ArrayList(); - int count = data.length / 4; - for (int a = 0; a < count; a++) { - arr.add(serializedData.readInt32()); + + int length = 0; + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(2)); + if ((length = cursor.byteBufferValue(2, data.buffer)) != 0) { + arr = new ArrayList(); + for (int a = 0; a < length / 4; a++) { + arr.add(data.readInt32()); + } } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); MessagesController.getInstance().processLoadedDeleteTask(taskId, date, arr); @@ -473,22 +519,22 @@ public class MessagesStorage { for (int a = 0; a < messages.size(); a++) { int key = messages.keyAt(a); ArrayList arr = messages.get(key); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(404); + int count = 0; for (int b = 0; b < arr.size(); b++) { int mid = arr.get(b); data.writeInt32(mid); + count++; if (b == arr.size() - 1 || b != 0 && b % 100 == 0) { state.requery(); - byte[] toDb = data.toByteArray(); + data.limit(count * 4); state.bindInteger(1, key); - state.bindByteArray(2, toDb); + state.bindByteBuffer(2, data.buffer); state.step(); - - if (b != arr.size() - 1) { - data = new SerializedData(); - } + count = 0; } } + buffersStorage.reuseFreeBuffer(data); } state.dispose(); database.commitTransaction(); @@ -613,12 +659,13 @@ public class MessagesStorage { } } SQLitePreparedStatement state = database.executeFast("REPLACE INTO chat_settings VALUES(?, ?)"); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(info.getObjectSize()); info.serializeToStream(data); state.bindInteger(1, chat_id); - state.bindByteArray(2, data.toByteArray()); + state.bindByteBuffer(2, data.buffer); state.step(); state.dispose(); + buffersStorage.reuseFreeBuffer(data); } catch (Exception e) { FileLog.e("tmessages", e); } @@ -635,11 +682,11 @@ public class MessagesStorage { TLRPC.ChatParticipants info = null; ArrayList loadedUsers = new ArrayList(); if (cursor.next()) { - byte[] userData = cursor.byteArrayValue(0); - if (userData != null) { - SerializedData data = new SerializedData(userData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { info = (TLRPC.ChatParticipants)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); if (info != null) { @@ -669,12 +716,13 @@ public class MessagesStorage { }); SQLitePreparedStatement state = database.executeFast("REPLACE INTO chat_settings VALUES(?, ?)"); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(info.getObjectSize()); info.serializeToStream(data); state.bindInteger(1, chat_id); - state.bindByteArray(2, data.toByteArray()); + state.bindByteBuffer(2, data.buffer); state.step(); state.dispose(); + buffersStorage.reuseFreeBuffer(data); } } catch (Exception e) { FileLog.e("tmessages", e); @@ -692,11 +740,11 @@ public class MessagesStorage { TLRPC.ChatParticipants info = null; ArrayList loadedUsers = new ArrayList(); if (cursor.next()) { - byte[] userData = cursor.byteArrayValue(0); - if (userData != null) { - SerializedData data = new SerializedData(userData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { info = (TLRPC.ChatParticipants)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); @@ -711,15 +759,15 @@ public class MessagesStorage { if (usersToLoad.length() != 0) { cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", usersToLoad)); while (cursor.next()) { - byte[] userData = cursor.byteArrayValue(0); - if (userData != null) { - SerializedData data = new SerializedData(userData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.User user = (TLRPC.User)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); loadedUsers.add(user); if (user.status != null) { user.status.expires = cursor.intValue(1); } } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); } @@ -741,7 +789,7 @@ public class MessagesStorage { //database.executeFast("DELETE FROM pending_read WHERE uid = " + dialog_id).stepThis().dispose(); } else { database.beginTransaction(); - SQLitePreparedStatement state;/*) = database.executeFast("REPLACE INTO pending_read VALUES(?, ?)"); + SQLitePreparedStatement state;/* = database.executeFast("REPLACE INTO pending_read VALUES(?, ?)"); state.requery(); state.bindLong(1, dialog_id); state.bindInteger(2, max_id); @@ -801,19 +849,18 @@ public class MessagesStorage { String[] args = name.split(" "); for (String str : args) { if (str.startsWith(q)) { - byte[] userData = cursor.byteArrayValue(0); - if (userData != null) { - SerializedData data = new SerializedData(userData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.User user = (TLRPC.User)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); - if (user.id == UserConfig.getClientUserId()) { - continue; + if (user.id != UserConfig.getClientUserId()) { + if (user.status != null) { + user.status.expires = cursor.intValue(1); + } + resultArrayNames.add(Utilities.generateSearchName(user.first_name, user.last_name, q)); + resultArray.add(user); } - if (user.status != null) { - user.status.expires = cursor.intValue(1); - } - resultArrayNames.add(Utilities.generateSearchName(user.first_name, user.last_name, q)); - resultArray.add(user); } + buffersStorage.reuseFreeBuffer(data); break; } } @@ -827,17 +874,15 @@ public class MessagesStorage { String[] args = name.split(" "); for (String arg : args) { if (arg.startsWith(q)) { - byte[] chatData = cursor.byteArrayValue(0); - byte[] userData = cursor.byteArrayValue(6); - if (chatData != null && userData != null) { - SerializedData data = new SerializedData(chatData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + ByteBufferDesc data2 = buffersStorage.getFreeBuffer(cursor.byteArrayLength(6)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0 && cursor.byteBufferValue(6, data2.buffer) != 0) { TLRPC.EncryptedChat chat = (TLRPC.EncryptedChat) TLClassStore.Instance().TLdeserialize(data, data.readInt32()); chat.user_id = cursor.intValue(2); chat.a_or_b = cursor.byteArrayValue(3); chat.auth_key = cursor.byteArrayValue(4); chat.ttl = cursor.intValue(5); - SerializedData data2 = new SerializedData(userData); TLRPC.User user = (TLRPC.User)TLClassStore.Instance().TLdeserialize(data2, data2.readInt32()); if (user.status != null) { user.status.expires = cursor.intValue(7); @@ -846,6 +891,8 @@ public class MessagesStorage { resultArray.add(chat); encUsers.add(user); } + buffersStorage.reuseFreeBuffer(data); + buffersStorage.reuseFreeBuffer(data2); break; } } @@ -859,13 +906,13 @@ public class MessagesStorage { String[] args = name.split(" "); for (String arg : args) { if (arg.startsWith(q)) { - byte[] chatData = cursor.byteArrayValue(0); - if (chatData != null) { - SerializedData data = new SerializedData(chatData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.Chat chat = (TLRPC.Chat) TLClassStore.Instance().TLdeserialize(data, data.readInt32()); resultArrayNames.add(Utilities.generateSearchName(chat.title, null, q)); resultArray.add(chat); } + buffersStorage.reuseFreeBuffer(data); break; } } @@ -1059,15 +1106,15 @@ public class MessagesStorage { if (uids.length() != 0) { cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", uids)); while (cursor.next()) { - byte[] userData = cursor.byteArrayValue(0); - if (userData != null) { - SerializedData data = new SerializedData(userData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.User user = (TLRPC.User)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); users.add(user); if (user.status != null) { user.status.expires = cursor.intValue(1); } } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); } @@ -1155,15 +1202,15 @@ public class MessagesStorage { } while (cursor.next()) { - byte[] messageData = cursor.byteArrayValue(0); - if (messageData != null) { - SerializedData data = new SerializedData(messageData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.Message message = (TLRPC.Message)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); message.id = cursor.intValue(1); message.dialog_id = uid; res.messages.add(message); fromUser.add(message.from_id); } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); @@ -1180,9 +1227,8 @@ public class MessagesStorage { if (usersToLoad.length() != 0) { cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", usersToLoad)); while (cursor.next()) { - byte[] userData = cursor.byteArrayValue(0); - if (userData != null) { - SerializedData data = new SerializedData(userData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.User user = (TLRPC.User)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); loadedUsers.add(user.id); if (user.status != null) { @@ -1190,6 +1236,7 @@ public class MessagesStorage { } res.users.add(user); } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); } @@ -1215,13 +1262,14 @@ public class MessagesStorage { for (TLRPC.Message message : messages) { if (message.media instanceof TLRPC.TL_messageMediaVideo || message.media instanceof TLRPC.TL_messageMediaPhoto) { state2.requery(); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(message.getObjectSize()); message.serializeToStream(data); state2.bindInteger(1, message.id); state2.bindLong(2, uid); state2.bindInteger(3, message.date); - state2.bindByteArray(4, data.toByteArray()); + state2.bindByteBuffer(4, data.buffer); state2.step(); + buffersStorage.reuseFreeBuffer(data); } } state2.dispose(); @@ -1333,9 +1381,8 @@ public class MessagesStorage { } } while (cursor.next()) { - byte[] messageData = cursor.byteArrayValue(1); - if (messageData != null) { - SerializedData data = new SerializedData(messageData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(1)); + if (data != null && cursor.byteBufferValue(1, data.buffer) != 0) { TLRPC.Message message = (TLRPC.Message)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); int read_state = cursor.intValue(0); message.unread = (cursor.intValue(0) != 1); @@ -1364,6 +1411,7 @@ public class MessagesStorage { message.random_id = cursor.longValue(5); } } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); @@ -1380,9 +1428,8 @@ public class MessagesStorage { if (usersToLoad.length() != 0) { cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", usersToLoad)); while (cursor.next()) { - byte[] userData = cursor.byteArrayValue(0); - if (userData != null) { - SerializedData data = new SerializedData(userData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.User user = (TLRPC.User)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); loadedUsers.add(user.id); if (user.status != null) { @@ -1390,6 +1437,7 @@ public class MessagesStorage { } res.users.add(user); } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); } @@ -1453,14 +1501,14 @@ public class MessagesStorage { if (id != null) { SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT data FROM sent_files_v2 WHERE uid = '%s' AND type = %d", id, type)); if (cursor.next()) { - byte[] fileData = cursor.byteArrayValue(0); - if (fileData != null) { - SerializedData data = new SerializedData(fileData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLObject file = TLClassStore.Instance().TLdeserialize(data, data.readInt32()); if (file != null) { result.add(file); } } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); } @@ -1491,13 +1539,14 @@ public class MessagesStorage { if (id != null) { SQLitePreparedStatement state = database.executeFast("REPLACE INTO sent_files_v2 VALUES(?, ?, ?)"); state.requery(); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(file.getObjectSize()); file.serializeToStream(data); state.bindString(1, id); state.bindInteger(2, type); - state.bindByteArray(3, data.toByteArray()); + state.bindByteBuffer(3, data.buffer); state.step(); state.dispose(); + buffersStorage.reuseFreeBuffer(data); } } catch (Exception e) { FileLog.e("tmessages", e); @@ -1540,22 +1589,25 @@ public class MessagesStorage { SQLitePreparedStatement state = null; try { state = database.executeFast("UPDATE enc_chats SET data = ?, g = ?, authkey = ?, ttl = ? WHERE uid = ?"); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(chat.getObjectSize()); + ByteBufferDesc data2 = buffersStorage.getFreeBuffer(chat.a_or_b != null ? chat.a_or_b.length : 1); + ByteBufferDesc data3 = buffersStorage.getFreeBuffer(chat.auth_key != null ? chat.auth_key.length : 1); chat.serializeToStream(data); - state.bindByteArray(1, data.toByteArray()); + state.bindByteBuffer(1, data.buffer); if (chat.a_or_b != null) { - state.bindByteArray(2, chat.a_or_b); - } else { - state.bindByteArray(2, new byte[1]); + data2.writeRaw(chat.a_or_b); } if (chat.auth_key != null) { - state.bindByteArray(3, chat.auth_key); - } else { - state.bindByteArray(3, new byte[1]); + data3.writeRaw(chat.auth_key); } + state.bindByteBuffer(2, data2.buffer); + state.bindByteBuffer(3, data3.buffer); state.bindInteger(4, chat.ttl); state.bindInteger(5, chat.id); state.step(); + buffersStorage.reuseFreeBuffer(data); + buffersStorage.reuseFreeBuffer(data2); + buffersStorage.reuseFreeBuffer(data3); } catch (Exception e) { FileLog.e("tmessages", e); } finally { @@ -1578,9 +1630,8 @@ public class MessagesStorage { int userToLoad = 0; SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, user, g, authkey, ttl FROM enc_chats WHERE uid = %d", chat_id)); if (cursor.next()) { - byte[] chatData = cursor.byteArrayValue(0); - if (chatData != null) { - SerializedData data = new SerializedData(chatData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.EncryptedChat chat = (TLRPC.EncryptedChat)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); result.add(chat); chat.user_id = cursor.intValue(1); @@ -1589,20 +1640,21 @@ public class MessagesStorage { chat.auth_key = cursor.byteArrayValue(3); chat.ttl = cursor.intValue(4); } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); if (userToLoad != 0) { cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid = %d", userToLoad)); if (cursor.next()) { - byte[] userData = cursor.byteArrayValue(0); - if (userData != null) { - SerializedData data = new SerializedData(userData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.User user = (TLRPC.User)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); if (user.status != null) { user.status.expires = cursor.intValue(1); } result.add(user); } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); @@ -1628,7 +1680,10 @@ public class MessagesStorage { public void run() { try { SQLitePreparedStatement state = database.executeFast("REPLACE INTO enc_chats VALUES(?, ?, ?, ?, ?, ?, ?)"); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(chat.getObjectSize()); + ByteBufferDesc data2 = buffersStorage.getFreeBuffer(chat.a_or_b != null ? chat.a_or_b.length : 1); + ByteBufferDesc data3 = buffersStorage.getFreeBuffer(chat.auth_key != null ? chat.auth_key.length : 1); + chat.serializeToStream(data); state.bindInteger(1, chat.id); state.bindInteger(2, user.id); @@ -1638,20 +1693,21 @@ public class MessagesStorage { } else { state.bindString(3, ""); } - state.bindByteArray(4, data.toByteArray()); + state.bindByteBuffer(4, data.buffer); if (chat.a_or_b != null) { - state.bindByteArray(5, chat.a_or_b); - } else { - state.bindByteArray(5, new byte[1]); + data2.writeRaw(chat.a_or_b); } if (chat.auth_key != null) { - state.bindByteArray(6, chat.auth_key); - } else { - state.bindByteArray(6, new byte[1]); + data3.writeRaw(chat.auth_key); } + state.bindByteBuffer(5, data2.buffer); + state.bindByteBuffer(6, data3.buffer); state.bindInteger(7, chat.ttl); state.step(); state.dispose(); + buffersStorage.reuseFreeBuffer(data); + buffersStorage.reuseFreeBuffer(data2); + buffersStorage.reuseFreeBuffer(data3); if (dialog != null) { state = database.executeFast("REPLACE INTO dialogs VALUES(?, ?, ?, ?)"); @@ -1681,7 +1737,7 @@ public class MessagesStorage { SQLitePreparedStatement state = database.executeFast("REPLACE INTO users VALUES(?, ?, ?, ?)"); for (TLRPC.User user : users) { state.requery(); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(user.getObjectSize()); user.serializeToStream(data); state.bindInteger(1, user.id); if (user.first_name != null && user.last_name != null) { @@ -1695,8 +1751,9 @@ public class MessagesStorage { } else { state.bindInteger(3, 0); } - state.bindByteArray(4, data.toByteArray()); + state.bindByteBuffer(4, data.buffer); state.step(); + buffersStorage.reuseFreeBuffer(data); } state.dispose(); } @@ -1704,7 +1761,7 @@ public class MessagesStorage { SQLitePreparedStatement state = database.executeFast("REPLACE INTO chats VALUES(?, ?, ?)"); for (TLRPC.Chat chat : chats) { state.requery(); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(chat.getObjectSize()); chat.serializeToStream(data); state.bindInteger(1, chat.id); if (chat.title != null) { @@ -1713,8 +1770,9 @@ public class MessagesStorage { } else { state.bindString(2, ""); } - state.bindByteArray(3, data.toByteArray()); + state.bindByteBuffer(3, data.buffer); state.step(); + buffersStorage.reuseFreeBuffer(data); } state.dispose(); } @@ -1743,9 +1801,6 @@ public class MessagesStorage { } private void putMessagesInternal(final ArrayList messages, final boolean withTransaction) { - if (Thread.currentThread().getId() != storageQueue.getId()) { - throw new RuntimeException("wrong db thread"); - } try { if (withTransaction) { database.beginTransaction(); @@ -1850,7 +1905,7 @@ public class MessagesStorage { messageId = message.local_id; } - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(message.getObjectSize()); message.serializeToStream(data); TLRPC.Message lastMessage = messagesMap.get(dialog_id); if (lastMessage == null || message.date > lastMessage.date) { @@ -1861,8 +1916,7 @@ public class MessagesStorage { state.bindInteger(3, (message.unread ? 0 : 1)); state.bindInteger(4, message.send_state); state.bindInteger(5, message.date); - byte[] bytes = data.toByteArray(); - state.bindByteArray(6, bytes); + state.bindByteBuffer(6, data.buffer); state.bindInteger(7, (message.out ? 1 : 0)); state.bindInteger(8, message.ttl); state.step(); @@ -1879,9 +1933,10 @@ public class MessagesStorage { state2.bindInteger(1, messageId); state2.bindLong(2, dialog_id); state2.bindInteger(3, message.date); - state2.bindByteArray(4, bytes); + state2.bindByteBuffer(4, data.buffer); state2.step(); } + buffersStorage.reuseFreeBuffer(data); } state.dispose(); state2.dispose(); @@ -2094,9 +2149,8 @@ public class MessagesStorage { ArrayList loadedUsers = new ArrayList(); SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", ids)); while (cursor.next()) { - byte[] userData = cursor.byteArrayValue(0); - if (userData != null) { - SerializedData data = new SerializedData(userData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.User user = (TLRPC.User)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); loadedUsers.add(user); if (user.status != null) { @@ -2110,6 +2164,7 @@ public class MessagesStorage { user.photo = updateUser.photo; } } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); if (!loadedUsers.isEmpty()) { @@ -2119,7 +2174,7 @@ public class MessagesStorage { SQLitePreparedStatement state = database.executeFast("REPLACE INTO users VALUES(?, ?, ?, ?)"); for (TLRPC.User user : loadedUsers) { state.requery(); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(user.getObjectSize()); user.serializeToStream(data); state.bindInteger(1, user.id); if (user.first_name != null && user.last_name != null) { @@ -2133,8 +2188,9 @@ public class MessagesStorage { } else { state.bindInteger(3, 0); } - state.bindByteArray(4, data.toByteArray()); + state.bindByteBuffer(4, data.buffer); state.step(); + buffersStorage.reuseFreeBuffer(data); } state.dispose(); if (withTransaction) { @@ -2325,9 +2381,8 @@ public class MessagesStorage { dialog.last_message_date = cursor.intValue(3); dialogs.dialogs.add(dialog); - byte[] messageData = cursor.byteArrayValue(4); - if (messageData != null) { - SerializedData data = new SerializedData(messageData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(4)); + if (data != null && cursor.byteBufferValue(4, data.buffer) != 0) { TLRPC.Message message = (TLRPC.Message)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); message.unread = (cursor.intValue(5) != 1); message.id = cursor.intValue(6); @@ -2348,6 +2403,7 @@ public class MessagesStorage { } } } + buffersStorage.reuseFreeBuffer(data); int lower_id = (int)dialog.id; if (lower_id != 0) { @@ -2379,9 +2435,8 @@ public class MessagesStorage { } cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, user, g, authkey, ttl FROM enc_chats WHERE uid IN(%s)", toLoad)); while (cursor.next()) { - byte[] chatData = cursor.byteArrayValue(0); - if (chatData != null) { - SerializedData data = new SerializedData(chatData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.EncryptedChat chat = (TLRPC.EncryptedChat)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); encryptedChats.add(chat); chat.user_id = cursor.intValue(1); @@ -2392,6 +2447,7 @@ public class MessagesStorage { chat.auth_key = cursor.byteArrayValue(3); chat.ttl = cursor.intValue(4); } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); } @@ -2406,12 +2462,12 @@ public class MessagesStorage { } cursor = database.queryFinalized(String.format(Locale.US, "SELECT data FROM chats WHERE uid IN(%s)", toLoad)); while (cursor.next()) { - byte[] chatData = cursor.byteArrayValue(0); - if (chatData != null) { - SerializedData data = new SerializedData(chatData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.Chat chat = (TLRPC.Chat)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); dialogs.chats.add(chat); } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); } @@ -2426,15 +2482,15 @@ public class MessagesStorage { } cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", toLoad)); while (cursor.next()) { - byte[] userData = cursor.byteArrayValue(0); - if (userData != null) { - SerializedData data = new SerializedData(userData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.User user = (TLRPC.User)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); if (user.status != null) { user.status.expires = cursor.intValue(1); } dialogs.users.add(user); } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); } @@ -2493,15 +2549,14 @@ public class MessagesStorage { SQLitePreparedStatement state2 = database.executeFast("REPLACE INTO media VALUES(?, ?, ?, ?)"); for (TLRPC.Message message : messages.messages) { state.requery(); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(message.getObjectSize()); message.serializeToStream(data); state.bindInteger(1, message.id); state.bindLong(2, dialog_id); state.bindInteger(3, (message.unread ? 0 : 1)); state.bindInteger(4, message.send_state); state.bindInteger(5, message.date); - byte[] bytes = data.toByteArray(); - state.bindByteArray(6, bytes); + state.bindByteBuffer(6, data.buffer); state.bindInteger(7, (message.out ? 1 : 0)); state.bindInteger(8, 0); state.step(); @@ -2511,9 +2566,10 @@ public class MessagesStorage { state2.bindInteger(1, message.id); state2.bindLong(2, dialog_id); state2.bindInteger(3, message.date); - state2.bindByteArray(4, bytes); + state2.bindByteBuffer(4, data.buffer); state2.step(); } + buffersStorage.reuseFreeBuffer(data); } state.dispose(); state2.dispose(); @@ -2522,7 +2578,7 @@ public class MessagesStorage { SQLitePreparedStatement state = database.executeFast("REPLACE INTO users VALUES(?, ?, ?, ?)"); for (TLRPC.User user : messages.users) { state.requery(); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(user.getObjectSize()); user.serializeToStream(data); state.bindInteger(1, user.id); if (user.first_name != null && user.last_name != null) { @@ -2536,8 +2592,9 @@ public class MessagesStorage { } else { state.bindInteger(3, 0); } - state.bindByteArray(4, data.toByteArray()); + state.bindByteBuffer(4, data.buffer); state.step(); + buffersStorage.reuseFreeBuffer(data); } state.dispose(); } @@ -2545,7 +2602,7 @@ public class MessagesStorage { SQLitePreparedStatement state = database.executeFast("REPLACE INTO chats VALUES(?, ?, ?)"); for (TLRPC.Chat chat : messages.chats) { state.requery(); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(chat.getObjectSize()); chat.serializeToStream(data); state.bindInteger(1, chat.id); if (chat.title != null) { @@ -2554,8 +2611,9 @@ public class MessagesStorage { } else { state.bindString(2, ""); } - state.bindByteArray(3, data.toByteArray()); + state.bindByteBuffer(3, data.buffer); state.step(); + buffersStorage.reuseFreeBuffer(data); } state.dispose(); } @@ -2588,9 +2646,8 @@ public class MessagesStorage { dialog.last_message_date = cursor.intValue(3); dialogs.dialogs.add(dialog); - byte[] messageData = cursor.byteArrayValue(4); - if (messageData != null) { - SerializedData data = new SerializedData(messageData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(4)); + if (data != null && cursor.byteBufferValue(4, data.buffer) != 0) { TLRPC.Message message = (TLRPC.Message)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); if (message != null) { message.unread = (cursor.intValue(5) != 1); @@ -2613,6 +2670,7 @@ public class MessagesStorage { } } } + buffersStorage.reuseFreeBuffer(data); int lower_id = (int)dialog.id; if (lower_id != 0) { @@ -2645,9 +2703,8 @@ public class MessagesStorage { cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, user, g, authkey, ttl FROM enc_chats WHERE uid IN(%s)", toLoad)); while (cursor.next()) { try { - byte[] chatData = cursor.byteArrayValue(0); - if (chatData != null) { - SerializedData data = new SerializedData(chatData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.EncryptedChat chat = (TLRPC.EncryptedChat)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); if (chat != null) { encryptedChats.add(chat); @@ -2660,6 +2717,7 @@ public class MessagesStorage { chat.ttl = cursor.intValue(4); } } + buffersStorage.reuseFreeBuffer(data); } catch (Exception e) { FileLog.e("tmessages", e); } @@ -2678,14 +2736,14 @@ public class MessagesStorage { cursor = database.queryFinalized(String.format(Locale.US, "SELECT data FROM chats WHERE uid IN(%s)", toLoad)); while (cursor.next()) { try { - byte[] chatData = cursor.byteArrayValue(0); - if (chatData != null) { - SerializedData data = new SerializedData(chatData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.Chat chat = (TLRPC.Chat)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); if (chat != null) { dialogs.chats.add(chat); } } + buffersStorage.reuseFreeBuffer(data); } catch (Exception e) { FileLog.e("tmessages", e); } @@ -2704,9 +2762,8 @@ public class MessagesStorage { cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", toLoad)); while (cursor.next()) { try { - byte[] userData = cursor.byteArrayValue(0); - if (userData != null) { - SerializedData data = new SerializedData(userData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.User user = (TLRPC.User)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); if (user != null) { if (user.status != null) { @@ -2715,6 +2772,7 @@ public class MessagesStorage { dialogs.users.add(user); } } + buffersStorage.reuseFreeBuffer(data); } catch (Exception e) { FileLog.e("tmessages", e); } @@ -2766,7 +2824,7 @@ public class MessagesStorage { uid = -dialog.peer.chat_id; } TLRPC.Message message = new_dialogMessage.get(dialog.top_message); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(message.getObjectSize()); message.serializeToStream(data); state.bindInteger(1, message.id); @@ -2774,8 +2832,7 @@ public class MessagesStorage { state.bindInteger(3, (message.unread ? 0 : 1)); state.bindInteger(4, message.send_state); state.bindInteger(5, message.date); - byte[] bytes = data.toByteArray(); - state.bindByteArray(6, bytes); + state.bindByteBuffer(6, data.buffer); state.bindInteger(7, (message.out ? 1 : 0)); state.bindInteger(8, 0); state.step(); @@ -2791,9 +2848,10 @@ public class MessagesStorage { state3.bindLong(1, message.id); state3.bindInteger(2, uid); state3.bindInteger(3, message.date); - state3.bindByteArray(4, bytes); + state3.bindByteBuffer(4, data.buffer); state3.step(); } + buffersStorage.reuseFreeBuffer(data); } state.dispose(); state2.dispose(); @@ -2804,7 +2862,7 @@ public class MessagesStorage { SQLitePreparedStatement state = database.executeFast("REPLACE INTO users VALUES(?, ?, ?, ?)"); for (TLRPC.User user : dialogs.users) { state.requery(); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(user.getObjectSize()); user.serializeToStream(data); state.bindInteger(1, user.id); if (user.first_name != null && user.last_name != null) { @@ -2818,8 +2876,9 @@ public class MessagesStorage { } else { state.bindInteger(3, 0); } - state.bindByteArray(4, data.toByteArray()); + state.bindByteBuffer(4, data.buffer); state.step(); + buffersStorage.reuseFreeBuffer(data); } state.dispose(); } @@ -2828,7 +2887,7 @@ public class MessagesStorage { SQLitePreparedStatement state = database.executeFast("REPLACE INTO chats VALUES(?, ?, ?)"); for (TLRPC.Chat chat : dialogs.chats) { state.requery(); - SerializedData data = new SerializedData(); + ByteBufferDesc data = buffersStorage.getFreeBuffer(chat.getObjectSize()); chat.serializeToStream(data); state.bindInteger(1, chat.id); if (chat.title != null) { @@ -2837,13 +2896,16 @@ public class MessagesStorage { } else { state.bindString(2, ""); } - state.bindByteArray(3, data.toByteArray()); + state.bindByteBuffer(3, data.buffer); state.step(); + buffersStorage.reuseFreeBuffer(data); } state.dispose(); } database.commitTransaction(); + + loadUnreadMessages(); } catch (Exception e) { FileLog.e("tmessages", e); } @@ -2856,9 +2918,8 @@ public class MessagesStorage { try { SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid = %d", user_id)); if (cursor.next()) { - byte[] userData = cursor.byteArrayValue(0); - if (userData != null) { - SerializedData data = new SerializedData(userData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { user = (TLRPC.User) TLClassStore.Instance().TLdeserialize(data, data.readInt32()); if (user != null) { if (user.status != null) { @@ -2866,6 +2927,7 @@ public class MessagesStorage { } } } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); } catch (Exception e) { @@ -2888,9 +2950,8 @@ public class MessagesStorage { SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN (%s)", uidsStr)); while (cursor.next()) { - byte[] userData = cursor.byteArrayValue(0); - if (userData != null) { - SerializedData data = new SerializedData(userData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { TLRPC.User user = (TLRPC.User) TLClassStore.Instance().TLdeserialize(data, data.readInt32()); if (user != null) { if (user.status != null) { @@ -2899,12 +2960,15 @@ public class MessagesStorage { users.add(user); } else { error[0] = true; + buffersStorage.reuseFreeBuffer(data); break; } } else { error[0] = true; + buffersStorage.reuseFreeBuffer(data); break; } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); } catch (Exception e) { @@ -2919,11 +2983,11 @@ public class MessagesStorage { try { SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT data FROM chats WHERE uid = %d", chat_id)); if (cursor.next()) { - byte[] chatData = cursor.byteArrayValue(0); - if (chatData != null) { - SerializedData data = new SerializedData(chatData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { chat = (TLRPC.Chat) TLClassStore.Instance().TLdeserialize(data, data.readInt32()); } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); } catch (Exception e) { @@ -2937,9 +3001,8 @@ public class MessagesStorage { try { SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, user, g, authkey, ttl FROM enc_chats WHERE uid = %d", chat_id)); if (cursor.next()) { - byte[] chatData = cursor.byteArrayValue(0); - if (chatData != null) { - SerializedData data = new SerializedData(chatData); + ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0)); + if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) { chat = (TLRPC.EncryptedChat) TLClassStore.Instance().TLdeserialize(data, data.readInt32()); if (chat != null) { chat.user_id = cursor.intValue(1); @@ -2948,6 +3011,7 @@ public class MessagesStorage { chat.ttl = cursor.intValue(4); } } + buffersStorage.reuseFreeBuffer(data); } cursor.dispose(); } catch (Exception e) { diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/NativeLoader.java b/TMessagesProj/src/main/java/org/telegram/android/NativeLoader.java similarity index 97% rename from TMessagesProj/src/main/java/org/telegram/messenger/NativeLoader.java rename to TMessagesProj/src/main/java/org/telegram/android/NativeLoader.java index 58a966076..970facb40 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/NativeLoader.java +++ b/TMessagesProj/src/main/java/org/telegram/android/NativeLoader.java @@ -6,12 +6,14 @@ * Copyright Nikolai Kudashov, 2013-2014. */ -package org.telegram.messenger; +package org.telegram.android; import android.content.Context; import android.content.pm.ApplicationInfo; import android.os.Build; +import org.telegram.messenger.FileLog; + import java.io.File; import java.io.FileOutputStream; import java.io.InputStream; @@ -22,9 +24,9 @@ import java.util.zip.ZipFile; public class NativeLoader { private static final long sizes[] = new long[] { - 795280, //armeabi - 844452, //armeabi-v7a - 1242164, //x86 + 799376, //armeabi + 848548, //armeabi-v7a + 1246260, //x86 0, //mips }; diff --git a/TMessagesProj/src/main/java/org/telegram/android/NotificationsController.java b/TMessagesProj/src/main/java/org/telegram/android/NotificationsController.java new file mode 100644 index 000000000..419d82f9a --- /dev/null +++ b/TMessagesProj/src/main/java/org/telegram/android/NotificationsController.java @@ -0,0 +1,672 @@ +/* + * This is the source code of Telegram for Android v. 1.4.x. + * It is licensed under GNU GPL v. 2 or later. + * You should have received a copy of the license in this archive (see LICENSE). + * + * Copyright Nikolai Kudashov, 2013-2014. + */ + +package org.telegram.android; + +import android.app.NotificationManager; +import android.app.PendingIntent; +import android.content.Context; +import android.content.Intent; +import android.content.SharedPreferences; +import android.content.pm.PackageManager; +import android.content.pm.ResolveInfo; +import android.graphics.Bitmap; +import android.media.AudioManager; +import android.net.Uri; +import android.provider.Settings; +import android.support.v4.app.NotificationCompat; + +import org.json.JSONArray; +import org.json.JSONObject; +import org.telegram.messenger.ConnectionsManager; +import org.telegram.messenger.FileLoader; +import org.telegram.messenger.FileLog; +import org.telegram.messenger.NotificationCenter; +import org.telegram.messenger.R; +import org.telegram.messenger.TLRPC; +import org.telegram.messenger.UserConfig; +import org.telegram.messenger.Utilities; +import org.telegram.objects.MessageObject; +import org.telegram.ui.ApplicationLoader; +import org.telegram.ui.LaunchActivity; +import org.telegram.ui.PopupNotificationActivity; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; + +public class NotificationsController { + + private ArrayList pushMessages = new ArrayList(); + private HashMap pushMessagesDict = new HashMap(); + private NotificationManager notificationManager = null; + private HashMap pushDialogs = new HashMap(); + public ArrayList popupMessages = new ArrayList(); + private long openned_dialog_id = 0; + private int total_unread_count = 0; + private boolean notifyCheck = false; + + public static final int pushMessagesUpdated = 27; + + private static volatile NotificationsController Instance = null; + public static NotificationsController getInstance() { + NotificationsController localInstance = Instance; + if (localInstance == null) { + synchronized (MessagesController.class) { + localInstance = Instance; + if (localInstance == null) { + Instance = localInstance = new NotificationsController(); + } + } + } + return localInstance; + } + + public NotificationsController() { + notificationManager = (NotificationManager)ApplicationLoader.applicationContext.getSystemService(Context.NOTIFICATION_SERVICE); + } + + public void cleanup() { + openned_dialog_id = 0; + total_unread_count = 0; + pushMessages.clear(); + pushMessagesDict.clear(); + pushDialogs.clear(); + popupMessages.clear(); + notifyCheck = false; + } + + public void setOpennedDialogId(long dialog_id) { + openned_dialog_id = dialog_id; + } + + private String getStringForMessage(MessageObject messageObject) { + long dialog_id = messageObject.messageOwner.dialog_id; + int chat_id = messageObject.messageOwner.to_id.chat_id; + int user_id = messageObject.messageOwner.to_id.user_id; + if (user_id == 0) { + user_id = messageObject.messageOwner.from_id; + } else if (user_id == UserConfig.getClientUserId()) { + user_id = messageObject.messageOwner.from_id; + } + + if (dialog_id == 0) { + if (chat_id != 0) { + dialog_id = -chat_id; + } else if (user_id != 0) { + dialog_id = user_id; + } + } + + TLRPC.User user = MessagesController.getInstance().users.get(user_id); + if (user == null) { + return null; + } + TLRPC.Chat chat = null; + if (chat_id != 0) { + chat = MessagesController.getInstance().chats.get(chat_id); + if (chat == null) { + return null; + } + } + + String msg = null; + if ((int)dialog_id != 0) { + if (chat_id == 0 && user_id != 0) { + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Context.MODE_PRIVATE); + if (preferences.getBoolean("EnablePreviewAll", true)) { + if (messageObject.messageOwner instanceof TLRPC.TL_messageService) { + if (messageObject.messageOwner.action instanceof TLRPC.TL_messageActionUserJoined) { + msg = LocaleController.formatString("NotificationContactJoined", R.string.NotificationContactJoined, Utilities.formatName(user.first_name, user.last_name)); + } else if (messageObject.messageOwner.action instanceof TLRPC.TL_messageActionUserUpdatedPhoto) { + msg = LocaleController.formatString("NotificationContactNewPhoto", R.string.NotificationContactNewPhoto, Utilities.formatName(user.first_name, user.last_name)); + } else if (messageObject.messageOwner.action instanceof TLRPC.TL_messageActionLoginUnknownLocation) { + String date = String.format("%s %s %s", LocaleController.formatterYear.format(((long)messageObject.messageOwner.date) * 1000), LocaleController.getString("OtherAt", R.string.OtherAt), LocaleController.formatterDay.format(((long)messageObject.messageOwner.date) * 1000)); + msg = LocaleController.formatString("NotificationUnrecognizedDevice", R.string.NotificationUnrecognizedDevice, UserConfig.getCurrentUser().first_name, date, messageObject.messageOwner.action.title, messageObject.messageOwner.action.address); + } + } else { + if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaEmpty) { + if (messageObject.messageOwner.message != null && messageObject.messageOwner.message.length() != 0) { + msg = LocaleController.formatString("NotificationMessageText", R.string.NotificationMessageText, Utilities.formatName(user.first_name, user.last_name), messageObject.messageOwner.message); + } else { + msg = LocaleController.formatString("NotificationMessageNoText", R.string.NotificationMessageNoText, Utilities.formatName(user.first_name, user.last_name)); + } + } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaPhoto) { + msg = LocaleController.formatString("NotificationMessagePhoto", R.string.NotificationMessagePhoto, Utilities.formatName(user.first_name, user.last_name)); + } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaVideo) { + msg = LocaleController.formatString("NotificationMessageVideo", R.string.NotificationMessageVideo, Utilities.formatName(user.first_name, user.last_name)); + } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaContact) { + msg = LocaleController.formatString("NotificationMessageContact", R.string.NotificationMessageContact, Utilities.formatName(user.first_name, user.last_name)); + } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaGeo) { + msg = LocaleController.formatString("NotificationMessageMap", R.string.NotificationMessageMap, Utilities.formatName(user.first_name, user.last_name)); + } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaDocument) { + msg = LocaleController.formatString("NotificationMessageDocument", R.string.NotificationMessageDocument, Utilities.formatName(user.first_name, user.last_name)); + } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaAudio) { + msg = LocaleController.formatString("NotificationMessageAudio", R.string.NotificationMessageAudio, Utilities.formatName(user.first_name, user.last_name)); + } + } + } else { + msg = LocaleController.formatString("NotificationMessageNoText", R.string.NotificationMessageNoText, Utilities.formatName(user.first_name, user.last_name)); + } + } else if (chat_id != 0) { + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Context.MODE_PRIVATE); + if (preferences.getBoolean("EnablePreviewGroup", true)) { + if (messageObject.messageOwner instanceof TLRPC.TL_messageService) { + if (messageObject.messageOwner.action instanceof TLRPC.TL_messageActionChatAddUser) { + if (messageObject.messageOwner.action.user_id == UserConfig.getClientUserId()) { + msg = LocaleController.formatString("NotificationInvitedToGroup", R.string.NotificationInvitedToGroup, Utilities.formatName(user.first_name, user.last_name), chat.title); + } else { + TLRPC.User u2 = MessagesController.getInstance().users.get(messageObject.messageOwner.action.user_id); + if (u2 == null) { + return null; + } + msg = LocaleController.formatString("NotificationGroupAddMember", R.string.NotificationGroupAddMember, Utilities.formatName(user.first_name, user.last_name), chat.title, Utilities.formatName(u2.first_name, u2.last_name)); + } + } else if (messageObject.messageOwner.action instanceof TLRPC.TL_messageActionChatEditTitle) { + msg = LocaleController.formatString("NotificationEditedGroupName", R.string.NotificationEditedGroupName, Utilities.formatName(user.first_name, user.last_name), messageObject.messageOwner.action.title); + } else if (messageObject.messageOwner.action instanceof TLRPC.TL_messageActionChatEditPhoto || messageObject.messageOwner.action instanceof TLRPC.TL_messageActionChatDeletePhoto) { + msg = LocaleController.formatString("NotificationEditedGroupPhoto", R.string.NotificationEditedGroupPhoto, Utilities.formatName(user.first_name, user.last_name), chat.title); + } else if (messageObject.messageOwner.action instanceof TLRPC.TL_messageActionChatDeleteUser) { + if (messageObject.messageOwner.action.user_id == UserConfig.getClientUserId()) { + msg = LocaleController.formatString("NotificationGroupKickYou", R.string.NotificationGroupKickYou, Utilities.formatName(user.first_name, user.last_name), chat.title); + } else if (messageObject.messageOwner.action.user_id == user.id) { + msg = LocaleController.formatString("NotificationGroupLeftMember", R.string.NotificationGroupLeftMember, Utilities.formatName(user.first_name, user.last_name), chat.title); + } else { + TLRPC.User u2 = MessagesController.getInstance().users.get(messageObject.messageOwner.action.user_id); + if (u2 == null) { + return null; + } + msg = LocaleController.formatString("NotificationGroupKickMember", R.string.NotificationGroupKickMember, Utilities.formatName(user.first_name, user.last_name), chat.title, Utilities.formatName(u2.first_name, u2.last_name)); + } + } + } else { + if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaEmpty) { + if (messageObject.messageOwner.message != null && messageObject.messageOwner.message.length() != 0) { + msg = LocaleController.formatString("NotificationMessageGroupText", R.string.NotificationMessageGroupText, Utilities.formatName(user.first_name, user.last_name), chat.title, messageObject.messageOwner.message); + } else { + msg = LocaleController.formatString("NotificationMessageGroupNoText", R.string.NotificationMessageGroupNoText, Utilities.formatName(user.first_name, user.last_name), chat.title); + } + } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaPhoto) { + msg = LocaleController.formatString("NotificationMessageGroupPhoto", R.string.NotificationMessageGroupPhoto, Utilities.formatName(user.first_name, user.last_name), chat.title); + } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaVideo) { + msg = LocaleController.formatString("NotificationMessageGroupVideo", R.string.NotificationMessageGroupVideo, Utilities.formatName(user.first_name, user.last_name), chat.title); + } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaContact) { + msg = LocaleController.formatString("NotificationMessageGroupContact", R.string.NotificationMessageGroupContact, Utilities.formatName(user.first_name, user.last_name), chat.title); + } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaGeo) { + msg = LocaleController.formatString("NotificationMessageGroupMap", R.string.NotificationMessageGroupMap, Utilities.formatName(user.first_name, user.last_name), chat.title); + } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaDocument) { + msg = LocaleController.formatString("NotificationMessageGroupDocument", R.string.NotificationMessageGroupDocument, Utilities.formatName(user.first_name, user.last_name), chat.title); + } else if (messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaAudio) { + msg = LocaleController.formatString("NotificationMessageGroupAudio", R.string.NotificationMessageGroupAudio, Utilities.formatName(user.first_name, user.last_name), chat.title); + } + } + } else { + msg = LocaleController.formatString("NotificationMessageGroupNoText", R.string.NotificationMessageGroupNoText, Utilities.formatName(user.first_name, user.last_name), chat.title); + } + } + } else { + msg = LocaleController.getString("YouHaveNewMessage", R.string.YouHaveNewMessage); + } + return msg; + } + + private void showOrUpdateNotification(boolean notifyAboutLast) { + if (!UserConfig.isClientActivated() || pushMessages.isEmpty()) { + dismissNotification(); + return; + } + try { + ConnectionsManager.getInstance().resumeNetworkMaybe(); + + MessageObject lastMessageObject = pushMessages.get(0); + + long dialog_id = lastMessageObject.getDialogId(); + int chat_id = lastMessageObject.messageOwner.to_id.chat_id; + int user_id = lastMessageObject.messageOwner.to_id.user_id; + if (user_id == 0) { + user_id = lastMessageObject.messageOwner.from_id; + } else if (user_id == UserConfig.getClientUserId()) { + user_id = lastMessageObject.messageOwner.from_id; + } + + TLRPC.User user = MessagesController.getInstance().users.get(user_id); + TLRPC.Chat chat = null; + if (chat_id != 0) { + chat = MessagesController.getInstance().chats.get(chat_id); + } + TLRPC.FileLocation photoPath = null; + + boolean notifyDisabled = false; + boolean needVibrate = false; + String choosenSoundPath = null; + int ledColor = 0xff00ff00; + boolean inAppSounds = false; + boolean inAppVibrate = false; + boolean inAppPreview = false; + int vibrate_override = 0; + + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Context.MODE_PRIVATE); + int notify_override = preferences.getInt("notify2_" + dialog_id, 0); + if (!notifyAboutLast || notify_override == 2 || (!preferences.getBoolean("EnableAll", true) || chat_id != 0 && !preferences.getBoolean("EnableGroup", true)) && notify_override == 0) { + notifyDisabled = true; + } + + String defaultPath = Settings.System.DEFAULT_NOTIFICATION_URI.getPath(); + if (!notifyDisabled) { + inAppSounds = preferences.getBoolean("EnableInAppSounds", true); + inAppVibrate = preferences.getBoolean("EnableInAppVibrate", true); + inAppPreview = preferences.getBoolean("EnableInAppPreview", true); + vibrate_override = preferences.getInt("vibrate_" + dialog_id, 0); + + + choosenSoundPath = preferences.getString("sound_path_" + dialog_id, null); + if (chat_id != 0) { + if (choosenSoundPath != null && choosenSoundPath.equals(defaultPath)) { + choosenSoundPath = null; + } else if (choosenSoundPath == null) { + choosenSoundPath = preferences.getString("GroupSoundPath", defaultPath); + } + needVibrate = preferences.getBoolean("EnableVibrateGroup", true); + ledColor = preferences.getInt("GroupLed", 0xff00ff00); + } else if (user_id != 0) { + if (choosenSoundPath != null && choosenSoundPath.equals(defaultPath)) { + choosenSoundPath = null; + } else if (choosenSoundPath == null) { + choosenSoundPath = preferences.getString("GlobalSoundPath", defaultPath); + } + needVibrate = preferences.getBoolean("EnableVibrateAll", true); + ledColor = preferences.getInt("MessagesLed", 0xff00ff00); + } + if (preferences.contains("color_" + dialog_id)) { + ledColor = preferences.getInt("color_" + dialog_id, 0); + } + + if (!needVibrate && vibrate_override == 1) { + needVibrate = true; + } else if (needVibrate && vibrate_override == 2) { + needVibrate = false; + } + if (!ApplicationLoader.mainInterfacePaused) { + if (!inAppSounds) { + choosenSoundPath = null; + } + if (!inAppVibrate) { + needVibrate = false; + } + } + } + + Intent intent = new Intent(ApplicationLoader.applicationContext, LaunchActivity.class); + intent.setAction("com.tmessages.openchat" + Math.random() + Integer.MAX_VALUE); + intent.setFlags(32768); + if ((int)dialog_id != 0) { + if (chat_id != 0) { + intent.putExtra("chatId", chat_id); + } else if (user_id != 0) { + intent.putExtra("userId", user_id); + } + if (pushDialogs.size() == 1) { + if (chat != null) { + if (chat.photo != null && chat.photo.photo_small != null && chat.photo.photo_small.volume_id != 0 && chat.photo.photo_small.local_id != 0) { + photoPath = chat.photo.photo_small; + } + } else { + if (user.photo != null && user.photo.photo_small != null && user.photo.photo_small.volume_id != 0 && user.photo.photo_small.local_id != 0) { + photoPath = user.photo.photo_small; + } + } + } + } else { + intent.putExtra("encId", (int)(dialog_id >> 32)); + } + PendingIntent contentIntent = PendingIntent.getActivity(ApplicationLoader.applicationContext, 0, intent, PendingIntent.FLAG_ONE_SHOT); + + String name = null; + boolean replace = true; + if ((int)dialog_id == 0 || pushDialogs.size() > 1) { + name = LocaleController.getString("AppName", R.string.AppName); + replace = false; + } else { + if (chat != null) { + name = chat.title; + } else { + name = Utilities.formatName(user.first_name, user.last_name); + } + } + + String detailText = null; + if (pushDialogs.size() == 1) { + detailText = LocaleController.formatPluralString("NewMessages", total_unread_count); + } else { + detailText = String.format("%s %s", LocaleController.formatPluralString("NewMessages", total_unread_count), LocaleController.formatPluralString("FromContacts", pushDialogs.size())); + } + + NotificationCompat.Builder mBuilder = new NotificationCompat.Builder(ApplicationLoader.applicationContext) + .setContentTitle(name) + .setSmallIcon(R.drawable.notification) + .setAutoCancel(true) + .setContentText(detailText) + .setContentIntent(contentIntent); + + String lastMessage = null; + if (pushMessages.size() == 1) { + String message = lastMessage = getStringForMessage(pushMessages.get(0)); + if (message == null) { + return; + } + if (replace) { + if (chat != null) { + message = message.replace(" @ " + name, ""); + } else { + message = message.replace(name + ": ", "").replace(name + " ", ""); + } + } + mBuilder.setStyle(new NotificationCompat.BigTextStyle().bigText(message)); + } else { + NotificationCompat.InboxStyle inboxStyle = new NotificationCompat.InboxStyle(); + inboxStyle.setBigContentTitle(name); + int count = Math.min(10, pushMessages.size()); + for (int i = 0; i < count; i++) { + String message = getStringForMessage(pushMessages.get(i)); + if (message == null) { + continue; + } + if (i == 0) { + lastMessage = message; + } + if (pushDialogs.size() == 1) { + if (replace) { + if (chat != null) { + message = message.replace(" @ " + name, ""); + } else { + message = message.replace(name + ": ", "").replace(name + " ", ""); + } + } + } + inboxStyle.addLine(message); + } + inboxStyle.setSummaryText(detailText); + mBuilder.setStyle(inboxStyle); + } + + if (photoPath != null) { + Bitmap img = FileLoader.getInstance().getImageFromMemory(photoPath, null, null, "50_50", false); + if (img != null) { + mBuilder.setLargeIcon(img); + } + } + + if (!notifyDisabled) { + if (ApplicationLoader.mainInterfacePaused || inAppPreview) { + mBuilder.setTicker(lastMessage); + } + if (choosenSoundPath != null && !choosenSoundPath.equals("NoSound")) { + if (choosenSoundPath.equals(defaultPath)) { + mBuilder.setSound(Settings.System.DEFAULT_NOTIFICATION_URI, AudioManager.STREAM_NOTIFICATION); + } else { + mBuilder.setSound(Uri.parse(choosenSoundPath), AudioManager.STREAM_NOTIFICATION); + } + } + if (ledColor != 0) { + mBuilder.setLights(ledColor, 1000, 1000); + } + if (needVibrate) { + mBuilder.setVibrate(new long[]{0, 100, 0, 100}); + } + } else { + mBuilder.setVibrate(new long[]{0, 0}); + } + + notificationManager.notify(1, mBuilder.build()); + if (preferences.getBoolean("EnablePebbleNotifications", false)) { + sendAlertToPebble(lastMessage); + } + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + + private void dismissNotification() { + try { + notificationManager.cancel(1); + pushMessages.clear(); + pushMessagesDict.clear(); + NotificationCenter.getInstance().postNotificationName(pushMessagesUpdated); + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + + private void sendAlertToPebble(String message) { + try { + final Intent i = new Intent("com.getpebble.action.SEND_NOTIFICATION"); + + final HashMap data = new HashMap(); + data.put("title", LocaleController.getString("AppName", R.string.AppName)); + data.put("body", message); + final JSONObject jsonData = new JSONObject(data); + final String notificationData = new JSONArray().put(jsonData).toString(); + + i.putExtra("messageType", "PEBBLE_ALERT"); + i.putExtra("sender", LocaleController.formatString("AppName", R.string.AppName)); + i.putExtra("notificationData", notificationData); + + ApplicationLoader.applicationContext.sendBroadcast(i); + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + + public void processReadMessages(ArrayList readMessages, long dialog_id, int max_date, int max_id) { + int oldCount = popupMessages.size(); + int oldCount2 = pushMessages.size(); + if (readMessages != null) { + for (Integer id : readMessages) { + MessageObject messageObject = pushMessagesDict.get(id); + if (messageObject != null) { + pushMessages.remove(messageObject); + popupMessages.remove(messageObject); + pushMessagesDict.remove(id); + } + } + } + if (dialog_id != 0 && (max_id != 0 || max_date != 0)) { + for (int a = 0; a < pushMessages.size(); a++) { + MessageObject messageObject = pushMessages.get(a); + if (messageObject.getDialogId() == dialog_id) { + boolean remove = false; + if (max_date != 0) { + if (messageObject.messageOwner.date <= max_date) { + remove = true; + } + } else { + if (messageObject.messageOwner.id <= max_id) { + remove = true; + } + } + if (remove) { + pushMessages.remove(a); + popupMessages.remove(messageObject); + pushMessagesDict.remove(messageObject.messageOwner.id); + a--; + } + } + } + } + if (oldCount != popupMessages.size()) { + NotificationCenter.getInstance().postNotificationName(pushMessagesUpdated); + } +// if (readMessages != null || oldCount2 != pushMessages.size() || readMessages == null && dialog_id == 0) { +// showOrUpdateNotification(notifyCheck); +// } + } + + public void processNewMessages(ArrayList messageObjects, boolean isLast) { + if (messageObjects.isEmpty()) { + return; + } + boolean added = false; + + int oldCount = popupMessages.size(); + HashMap settingsCache = new HashMap(); + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Context.MODE_PRIVATE); + int popup = 0; + + for (MessageObject messageObject : messageObjects) { + if (pushMessagesDict.containsKey(messageObject.messageOwner.id)) { + continue; + } + long dialog_id = messageObject.getDialogId(); + if (dialog_id == openned_dialog_id && ApplicationLoader.isScreenOn) { + continue; + } + added = true; + + Boolean value = settingsCache.get(dialog_id); + boolean isChat = (int)dialog_id < 0; + popup = preferences.getInt(isChat ? "popupGroup" : "popupAll", 0); + if (value == null) { + int notify_override = preferences.getInt("notify2_" + dialog_id, 0); + value = !(notify_override == 2 || (!preferences.getBoolean("EnableAll", true) || isChat && !preferences.getBoolean("EnableGroup", true)) && notify_override == 0); + settingsCache.put(dialog_id, value); + } + if (value) { + if (popup != 0) { + popupMessages.add(0, messageObject); + } + pushMessagesDict.put(messageObject.messageOwner.id, messageObject); + pushMessages.add(0, messageObject); + } + } + + if (added) { + notifyCheck = isLast; + } + + if (!popupMessages.isEmpty() && oldCount != popupMessages.size()) { + if (ApplicationLoader.mainInterfacePaused || !ApplicationLoader.isScreenOn) { + MessageObject messageObject = messageObjects.get(0); + if (popup == 3 || popup == 1 && ApplicationLoader.isScreenOn || popup == 2 && !ApplicationLoader.isScreenOn) { + Intent popupIntent = new Intent(ApplicationLoader.applicationContext, PopupNotificationActivity.class); + popupIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_NO_ANIMATION | Intent.FLAG_ACTIVITY_NO_USER_ACTION | Intent.FLAG_FROM_BACKGROUND); + ApplicationLoader.applicationContext.startActivity(popupIntent); + } + } + } + } + + public void processDialogsUpdateRead(final HashMap dialogsToUpdate, boolean replace) { + int old_unread_count = total_unread_count; + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Context.MODE_PRIVATE); + for (HashMap.Entry entry : dialogsToUpdate.entrySet()) { + long dialog_id = entry.getKey(); + + int notify_override = preferences.getInt("notify2_" + dialog_id, 0); + boolean isChat = (int)dialog_id < 0; + Integer currentCount = pushDialogs.get(dialog_id); + if (!(notify_override == 2 || (!preferences.getBoolean("EnableAll", true) || isChat && !preferences.getBoolean("EnableGroup", true)) && notify_override == 0)) { + Integer newCount = entry.getValue(); + if (replace) { + if (currentCount != null) { + total_unread_count -= currentCount; + } + if (newCount == 0) { + pushDialogs.remove(dialog_id); + } else { + total_unread_count += newCount; + pushDialogs.put(dialog_id, newCount); + } + } else { + if (currentCount == null) { + currentCount = 0; + } + currentCount += newCount; + total_unread_count += newCount; + pushDialogs.put(dialog_id, currentCount); + } + } + } + if (old_unread_count != total_unread_count) { + showOrUpdateNotification(notifyCheck); + notifyCheck = false; + } + if (preferences.getBoolean("badgeNumber", true)) { + setBadge(ApplicationLoader.applicationContext, total_unread_count); + } + } + + public void processLoadedUnreadMessages(HashMap dialogs) { + pushDialogs.clear(); + total_unread_count = 0; + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Context.MODE_PRIVATE); + String dialogsToLoad = ""; + for (HashMap.Entry entry : dialogs.entrySet()) { + long dialog_id = entry.getKey(); + int notify_override = preferences.getInt("notify2_" + dialog_id, 0); + boolean isChat = (int)dialog_id < 0; + if (!(notify_override == 2 || (!preferences.getBoolean("EnableAll", true) || isChat && !preferences.getBoolean("EnableGroup", true)) && notify_override == 0)) { + pushDialogs.put(dialog_id, entry.getValue()); + total_unread_count += entry.getValue(); + if (dialogsToLoad.length() != 0) { + dialogsToLoad += ","; + } + dialogsToLoad += "" + dialog_id; + } + } + if (total_unread_count == 0) { + pushMessages.clear(); + pushMessagesDict.clear(); + popupMessages.clear(); + showOrUpdateNotification(false); + NotificationCenter.getInstance().postNotificationName(pushMessagesUpdated); + } + if (preferences.getBoolean("badgeNumber", true)) { + setBadge(ApplicationLoader.applicationContext, total_unread_count); + } + } + + public void setBadgeEnabled(boolean enabled) { + setBadge(ApplicationLoader.applicationContext, enabled ? total_unread_count : 0); + } + + private void setBadge(Context context, int count) { + try { + String launcherClassName = getLauncherClassName(context); + if (launcherClassName == null) { + return; + } + Intent intent = new Intent("android.intent.action.BADGE_COUNT_UPDATE"); + intent.putExtra("badge_count", count); + intent.putExtra("badge_count_package_name", context.getPackageName()); + intent.putExtra("badge_count_class_name", launcherClassName); + context.sendBroadcast(intent); + } catch (Throwable e) { + FileLog.e("tmessages", e); + } + } + + public static String getLauncherClassName(Context context) { + try { + PackageManager pm = context.getPackageManager(); + + Intent intent = new Intent(Intent.ACTION_MAIN); + intent.addCategory(Intent.CATEGORY_LAUNCHER); + + List resolveInfos = pm.queryIntentActivities(intent, 0); + for (ResolveInfo resolveInfo : resolveInfos) { + String pkgName = resolveInfo.activityInfo.applicationInfo.packageName; + if (pkgName.equalsIgnoreCase(context.getPackageName())) { + return resolveInfo.activityInfo.name; + } + } + } catch (Throwable e) { + FileLog.e("tmessages", e); + } + return null; + } +} diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/NotificationsService.java b/TMessagesProj/src/main/java/org/telegram/android/NotificationsService.java similarity index 94% rename from TMessagesProj/src/main/java/org/telegram/messenger/NotificationsService.java rename to TMessagesProj/src/main/java/org/telegram/android/NotificationsService.java index 0b8e145db..a790c7983 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/NotificationsService.java +++ b/TMessagesProj/src/main/java/org/telegram/android/NotificationsService.java @@ -6,13 +6,14 @@ * Copyright Nikolai Kudashov, 2013-2014. */ -package org.telegram.messenger; +package org.telegram.android; import android.app.Service; import android.content.Intent; import android.content.SharedPreferences; import android.os.IBinder; +import org.telegram.messenger.FileLog; import org.telegram.ui.ApplicationLoader; public class NotificationsService extends Service { diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/ScreenReceiver.java b/TMessagesProj/src/main/java/org/telegram/android/ScreenReceiver.java similarity index 77% rename from TMessagesProj/src/main/java/org/telegram/messenger/ScreenReceiver.java rename to TMessagesProj/src/main/java/org/telegram/android/ScreenReceiver.java index b557d0e5f..7a357627d 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/ScreenReceiver.java +++ b/TMessagesProj/src/main/java/org/telegram/android/ScreenReceiver.java @@ -6,12 +6,14 @@ * Copyright Nikolai Kudashov, 2013-2014. */ -package org.telegram.messenger; +package org.telegram.android; import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; +import org.telegram.messenger.ConnectionsManager; +import org.telegram.messenger.FileLog; import org.telegram.ui.ApplicationLoader; public class ScreenReceiver extends BroadcastReceiver { @@ -19,13 +21,11 @@ public class ScreenReceiver extends BroadcastReceiver { public void onReceive(Context context, Intent intent) { if (intent.getAction().equals(Intent.ACTION_SCREEN_OFF)) { FileLog.e("tmessages", "screen off"); - if (ConnectionsManager.lastPauseTime == 0) { - ConnectionsManager.lastPauseTime = System.currentTimeMillis(); - } + ConnectionsManager.getInstance().setAppPaused(true, true); ApplicationLoader.isScreenOn = false; } else if (intent.getAction().equals(Intent.ACTION_SCREEN_ON)) { FileLog.e("tmessages", "screen on"); - ConnectionsManager.resetLastPauseTime(); + ConnectionsManager.getInstance().setAppPaused(false, true); ApplicationLoader.isScreenOn = true; } } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/SmsListener.java b/TMessagesProj/src/main/java/org/telegram/android/SmsListener.java similarity index 92% rename from TMessagesProj/src/main/java/org/telegram/messenger/SmsListener.java rename to TMessagesProj/src/main/java/org/telegram/android/SmsListener.java index 1a5a6f46b..6489456b8 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/SmsListener.java +++ b/TMessagesProj/src/main/java/org/telegram/android/SmsListener.java @@ -6,7 +6,7 @@ * Copyright Nikolai Kudashov, 2013. */ -package org.telegram.messenger; +package org.telegram.android; import android.content.BroadcastReceiver; import android.content.Context; @@ -15,6 +15,9 @@ import android.content.SharedPreferences; import android.os.Bundle; import android.telephony.SmsMessage; +import org.telegram.messenger.FileLog; +import org.telegram.messenger.NotificationCenter; + import java.util.regex.Matcher; import java.util.regex.Pattern; @@ -25,7 +28,7 @@ public class SmsListener extends BroadcastReceiver { @Override public void onReceive(Context context, Intent intent) { if(intent.getAction().equals("android.provider.Telephony.SMS_RECEIVED")) { - if (!Utilities.isWaitingForSms()) { + if (!AndroidUtilities.isWaitingForSms()) { return; } Bundle bundle = intent.getExtras(); diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/Action.java b/TMessagesProj/src/main/java/org/telegram/messenger/Action.java index 69fdfca64..61ed9b70d 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/Action.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/Action.java @@ -25,6 +25,4 @@ public class Action { public void cancel() { } - - public int state; } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/BuffersStorage.java b/TMessagesProj/src/main/java/org/telegram/messenger/BuffersStorage.java index d09803789..5c39ae078 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/BuffersStorage.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/BuffersStorage.java @@ -18,6 +18,8 @@ public class BuffersStorage { private final ArrayList freeBuffers16384; private final ArrayList freeBuffers32768; private final ArrayList freeBuffersBig; + private boolean isThreadSafe; + private final static Integer sync = 1; private static volatile BuffersStorage Instance = null; public static BuffersStorage getInstance() { @@ -26,14 +28,15 @@ public class BuffersStorage { synchronized (BuffersStorage.class) { localInstance = Instance; if (localInstance == null) { - Instance = localInstance = new BuffersStorage(); + Instance = localInstance = new BuffersStorage(true); } } } return localInstance; } - public BuffersStorage() { + public BuffersStorage(boolean threadSafe) { + isThreadSafe = threadSafe; freeBuffers128 = new ArrayList(); freeBuffers1024 = new ArrayList(); freeBuffers4096 = new ArrayList(); @@ -44,91 +47,58 @@ public class BuffersStorage { for (int a = 0; a < 5; a++) { freeBuffers128.add(new ByteBufferDesc(128)); } -// for (int a = 0; a < 5; a++) { -// freeBuffers1024.add(new ByteBufferDesc(1024 + 200)); -// } -// for (int a = 0; a < 2; a++) { -// freeBuffers4096.add(new ByteBufferDesc(4096 + 200)); -// } -// for (int a = 0; a < 2; a++) { -// freeBuffers16384.add(new ByteBufferDesc(16384 + 200)); -// } -// for (int a = 0; a < 2; a++) { -// freeBuffers32768.add(new ByteBufferDesc(40000)); -// } } public ByteBufferDesc getFreeBuffer(int size) { + if (size <= 0) { + return null; + } + int byteCount = 0; + ArrayList arrayToGetFrom = null; ByteBufferDesc buffer = null; if (size <= 128) { - synchronized (freeBuffers128) { - if (freeBuffers128.size() > 0) { - buffer = freeBuffers128.get(0); - freeBuffers128.remove(0); - } - } - if (buffer == null) { - buffer = new ByteBufferDesc(128); - FileLog.e("tmessages", "create new 128 buffer"); - } + arrayToGetFrom = freeBuffers128; + byteCount = 128; } else if (size <= 1024 + 200) { - synchronized (freeBuffers1024) { - if (freeBuffers1024.size() > 0) { - buffer = freeBuffers1024.get(0); - freeBuffers1024.remove(0); - } - } - if (buffer == null) { - buffer = new ByteBufferDesc(1024 + 200); - FileLog.e("tmessages", "create new 1024 buffer"); - } + arrayToGetFrom = freeBuffers1024; + byteCount = 1024 + 200; } else if (size <= 4096 + 200) { - synchronized (freeBuffers4096) { - if (freeBuffers4096.size() > 0) { - buffer = freeBuffers4096.get(0); - freeBuffers4096.remove(0); - } - } - if (buffer == null) { - buffer = new ByteBufferDesc(4096 + 200); - FileLog.e("tmessages", "create new 4096 buffer"); - } + arrayToGetFrom = freeBuffers4096; + byteCount = 4096 + 200; } else if (size <= 16384 + 200) { - synchronized (freeBuffers16384) { - if (freeBuffers16384.size() > 0) { - buffer = freeBuffers16384.get(0); - freeBuffers16384.remove(0); - } - } - if (buffer == null) { - buffer = new ByteBufferDesc(16384 + 200); - FileLog.e("tmessages", "create new 16384 buffer"); - } + arrayToGetFrom = freeBuffers16384; + byteCount = 16384 + 200; } else if (size <= 40000) { - synchronized (freeBuffers32768) { - if (freeBuffers32768.size() > 0) { - buffer = freeBuffers32768.get(0); - freeBuffers32768.remove(0); - } - } - if (buffer == null) { - buffer = new ByteBufferDesc(40000); - FileLog.e("tmessages", "create new 40000 buffer"); - } + arrayToGetFrom = freeBuffers32768; + byteCount = 40000; } else if (size <= 280000) { - synchronized (freeBuffersBig) { - if (freeBuffersBig.size() > 0) { - buffer = freeBuffersBig.get(0); - freeBuffersBig.remove(0); - } - } - if (buffer == null) { - buffer = new ByteBufferDesc(280000); - FileLog.e("tmessages", "create new big buffer"); - } + arrayToGetFrom = freeBuffersBig; + byteCount = 280000; } else { buffer = new ByteBufferDesc(size); } + + if (arrayToGetFrom != null) { + if (isThreadSafe) { + synchronized (sync) { + if (arrayToGetFrom.size() > 0) { + buffer = arrayToGetFrom.get(0); + arrayToGetFrom.remove(0); + } + } + } else { + if (arrayToGetFrom.size() > 0) { + buffer = arrayToGetFrom.get(0); + arrayToGetFrom.remove(0); + } + } + + if (buffer == null) { + buffer = new ByteBufferDesc(byteCount); + FileLog.e("tmessages", "create new " + byteCount + " buffer"); + } + } + buffer.buffer.limit(size).rewind(); return buffer; } @@ -137,40 +107,34 @@ public class BuffersStorage { if (buffer == null) { return; } + int maxCount = 10; + ArrayList arrayToReuse = null; if (buffer.buffer.capacity() == 128) { - synchronized (freeBuffers128) { - if (freeBuffers128.size() < 10) { - freeBuffers128.add(buffer); - } - } + arrayToReuse = freeBuffers128; } else if (buffer.buffer.capacity() == 1024 + 200) { - synchronized (freeBuffers1024) { - if (freeBuffers1024.size() < 10) { - freeBuffers1024.add(buffer); - } - } - } else if (buffer.buffer.capacity() == 4096 + 200) { - synchronized (freeBuffers4096) { - if (freeBuffers4096.size() < 10) { - freeBuffers4096.add(buffer); - } - } + arrayToReuse = freeBuffers1024; + } if (buffer.buffer.capacity() == 4096 + 200) { + arrayToReuse = freeBuffers4096; } else if (buffer.buffer.capacity() == 16384 + 200) { - synchronized (freeBuffers16384) { - if (freeBuffers16384.size() < 10) { - freeBuffers16384.add(buffer); - } - } + arrayToReuse = freeBuffers16384; } else if (buffer.buffer.capacity() == 40000) { - synchronized (freeBuffers32768) { - if (freeBuffers32768.size() < 10) { - freeBuffers32768.add(buffer); - } - } + arrayToReuse = freeBuffers32768; } else if (buffer.buffer.capacity() == 280000) { - synchronized (freeBuffersBig) { - if (freeBuffersBig.size() < 4) { - freeBuffersBig.add(buffer); + arrayToReuse = freeBuffersBig; + maxCount = 10; + } + if (arrayToReuse != null) { + if (isThreadSafe) { + synchronized (sync) { + if (arrayToReuse.size() < maxCount) { + arrayToReuse.add(buffer); + } else { + FileLog.e("tmessages", "too more"); + } + } + } else { + if (arrayToReuse.size() < maxCount) { + arrayToReuse.add(buffer); } } } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/ByteBufferDesc.java b/TMessagesProj/src/main/java/org/telegram/messenger/ByteBufferDesc.java index 036539927..f36049bc8 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/ByteBufferDesc.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/ByteBufferDesc.java @@ -25,6 +25,11 @@ public class ByteBufferDesc extends AbsSerializedData { justCalc = calculate; } + public ByteBufferDesc(byte[] bytes) { + buffer = ByteBuffer.wrap(bytes); + buffer.order(ByteOrder.LITTLE_ENDIAN); + } + public int position() { return buffer.position(); } @@ -397,11 +402,13 @@ public class ByteBufferDesc extends AbsSerializedData { sl = 4; } ByteBufferDesc b = BuffersStorage.getInstance().getFreeBuffer(l); - int old = buffer.limit(); - buffer.limit(buffer.position() + l); - b.buffer.put(buffer); - buffer.limit(old); - b.buffer.position(0); + if (b != null) { + int old = buffer.limit(); + buffer.limit(buffer.position() + l); + b.buffer.put(buffer); + buffer.limit(old); + b.buffer.position(0); + } int i = sl; while((l + i) % 4 != 0) { buffer.get(); diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/ConnectionContext.java b/TMessagesProj/src/main/java/org/telegram/messenger/ConnectionContext.java index 38bcba64e..5277acd52 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/ConnectionContext.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/ConnectionContext.java @@ -74,6 +74,9 @@ public class ConnectionContext extends PyroClientAdapter { } public void addMessageToConfirm(long messageId) { + if (messagesIdsForConfirmation.contains(messageId)) { + return; + } messagesIdsForConfirmation.add(messageId); } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/ConnectionsManager.java b/TMessagesProj/src/main/java/org/telegram/messenger/ConnectionsManager.java index a35f25703..8af9e0ec2 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/ConnectionsManager.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/ConnectionsManager.java @@ -14,13 +14,15 @@ import android.content.pm.PackageInfo; import android.net.ConnectivityManager; import android.net.NetworkInfo; import android.os.Build; +import android.os.PowerManager; import android.util.Base64; +import org.telegram.android.ContactsController; +import org.telegram.android.MessagesController; import org.telegram.ui.ApplicationLoader; import java.io.File; import java.util.ArrayList; -import java.util.Arrays; import java.util.HashMap; import java.util.Locale; import java.util.concurrent.ConcurrentHashMap; @@ -34,11 +36,10 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. private ArrayList destroyingSessions = new ArrayList(); private HashMap> quickAckIdToRequestIds = new HashMap>(); - private HashMap pingIdToDate = new HashMap(); private ConcurrentHashMap> requestsByGuids = new ConcurrentHashMap>(100, 1.0f, 2); private ConcurrentHashMap requestsByClass = new ConcurrentHashMap(100, 1.0f, 2); - public volatile int connectionState = 2; + private volatile int connectionState = 2; private ArrayList requestQueue = new ArrayList(); private ArrayList runningRequests = new ArrayList(); @@ -47,17 +48,17 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. private ArrayList unknownDatacenterIds = new ArrayList(); private ArrayList neededDatacenterIds = new ArrayList(); private ArrayList unauthorizedDatacenterIds = new ArrayList(); - final HashMap> genericMessagesToDatacenters = new HashMap>(); + private final HashMap> genericMessagesToDatacenters = new HashMap>(); private TLRPC.TL_auth_exportedAuthorization movingAuthorization; public static final int DEFAULT_DATACENTER_ID = Integer.MAX_VALUE; - public static final int DC_UPDATE_TIME = 60 * 60; - public int currentDatacenterId; - public int movingToDatacenterId; + private static final int DC_UPDATE_TIME = 60 * 60; + protected int currentDatacenterId; + protected int movingToDatacenterId; private long lastOutgoingMessageId = 0; private int isTestBackend = 0; - public int timeDifference = 0; - public int currentPingTime; + private int timeDifference = 0; + private int currentPingTime; private int lastDestroySessionRequestTime; private boolean updatingDcSettings = false; private int updatingDcStartTime = 0; @@ -69,12 +70,17 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. private boolean paused = false; private long lastPingTime = System.currentTimeMillis(); private long lastPushPingTime = 0; + private boolean pushMessagesReceived = true; private boolean sendingPushPing = false; private int nextSleepTimeout = 30000; private long nextPingId = 0; - public static long lastPauseTime = System.currentTimeMillis(); - public static boolean appPaused = true; + private long lastPauseTime = System.currentTimeMillis(); + private boolean appPaused = true; + + private volatile long nextCallToken = 1; + + private PowerManager.WakeLock wakeLock = null; private static volatile ConnectionsManager Instance = null; public static ConnectionsManager getInstance() { @@ -90,20 +96,23 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. return localInstance; } - static long t = System.currentTimeMillis(); private Runnable stageRunnable = new Runnable() { @Override public void run() { Utilities.stageQueue.handler.removeCallbacks(stageRunnable); - t = System.currentTimeMillis(); if (datacenters != null) { - if (sendingPushPing && lastPushPingTime < System.currentTimeMillis() - 30000 || Math.abs(lastPushPingTime - System.currentTimeMillis()) > 60000 * 4) { + Datacenter datacenter = datacenterWithId(currentDatacenterId); + if (sendingPushPing && lastPushPingTime < System.currentTimeMillis() - 30000 || Math.abs(lastPushPingTime - System.currentTimeMillis()) > 60000 * 3 + 10000) { lastPushPingTime = 0; sendingPushPing = false; + if (datacenter != null && datacenter.pushConnection != null) { + datacenter.pushConnection.suspendConnection(true); + } + FileLog.e("tmessages", "push ping timeout"); } if (lastPushPingTime < System.currentTimeMillis() - 60000 * 3) { + FileLog.e("tmessages", "time for push ping"); lastPushPingTime = System.currentTimeMillis(); - Datacenter datacenter = datacenterWithId(currentDatacenterId); if (datacenter != null) { generatePing(datacenter, true); } @@ -112,16 +121,22 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. long currentTime = System.currentTimeMillis(); if (lastPauseTime != 0 && lastPauseTime < currentTime - nextSleepTimeout) { - boolean dontSleep = false; - for (RPCRequest request : runningRequests) { - if (request.retryCount < 10 && (request.runningStartTime + 60 > (int)(currentTime / 1000)) && ((request.flags & RPCRequest.RPCRequestClassDownloadMedia) != 0 || (request.flags & RPCRequest.RPCRequestClassUploadMedia) != 0)) { - dontSleep = true; - break; + boolean dontSleep = !pushMessagesReceived; + if (!dontSleep) { + for (RPCRequest request : runningRequests) { + if (request.rawRequest instanceof TLRPC.TL_get_future_salts) { + dontSleep = true; + } else if (request.retryCount < 10 && (request.runningStartTime + 60 > (int) (currentTime / 1000)) && ((request.flags & RPCRequest.RPCRequestClassDownloadMedia) != 0 || (request.flags & RPCRequest.RPCRequestClassUploadMedia) != 0)) { + dontSleep = true; + break; + } } } if (!dontSleep) { for (RPCRequest request : requestQueue) { - if ((request.flags & RPCRequest.RPCRequestClassDownloadMedia) != 0 || (request.flags & RPCRequest.RPCRequestClassUploadMedia) != 0) { + if (request.rawRequest instanceof TLRPC.TL_get_future_salts) { + dontSleep = true; + } else if ((request.flags & RPCRequest.RPCRequestClassDownloadMedia) != 0 || (request.flags & RPCRequest.RPCRequestClassUploadMedia) != 0) { dontSleep = true; break; } @@ -143,7 +158,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. } } else { lastPauseTime += 30 * 1000; - FileLog.e("tmessages", "don't sleep 30 seconds because of upload or download request"); + FileLog.e("tmessages", "don't sleep 30 seconds because of salt, upload or download request"); } } if (paused) { @@ -199,20 +214,36 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. } Utilities.stageQueue.postRunnable(stageRunnable, 1000); + + PowerManager pm = (PowerManager)ApplicationLoader.applicationContext.getSystemService(Context.POWER_SERVICE); + wakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "lock"); + wakeLock.setReferenceCounted(false); + } + + public int getConnectionState() { + return connectionState; + } + + public void setConnectionState(int state) { + connectionState = state; + } + + private void resumeNetworkInternal() { + if (paused) { + lastPauseTime = System.currentTimeMillis(); + nextSleepTimeout = 30000; + FileLog.e("tmessages", "wakeup network in background"); + } else if (lastPauseTime != 0) { + lastPauseTime = System.currentTimeMillis(); + FileLog.e("tmessages", "reset sleep timeout"); + } } public void resumeNetworkMaybe() { Utilities.stageQueue.postRunnable(new Runnable() { @Override public void run() { - if (paused) { - lastPauseTime = System.currentTimeMillis(); - nextSleepTimeout = 30000; - FileLog.e("tmessages", "wakeup network in background"); - } else if (lastPauseTime != 0) { - lastPauseTime = System.currentTimeMillis(); - FileLog.e("tmessages", "reset sleep timeout"); - } + resumeNetworkInternal(); } }); } @@ -230,26 +261,39 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. }); } - public static void resetLastPauseTime() { - if (appPaused) { - return; - } - FileLog.e("tmessages", "reset app pause time"); - if (lastPauseTime != 0 && System.currentTimeMillis() - lastPauseTime > 5000) { - ContactsController.getInstance().checkContacts(); - } - lastPauseTime = 0; - ConnectionsManager.getInstance().applicationMovedToForeground(); + public void setAppPaused(final boolean value, final boolean byScreenState) { + Utilities.stageQueue.postRunnable(new Runnable() { + @Override + public void run() { + if (!byScreenState) { + appPaused = value; + FileLog.e("tmessages", "app paused = " + value); + } + if (value) { + if (byScreenState) { + if (lastPauseTime == 0) { + lastPauseTime = System.currentTimeMillis(); + } + } else { + lastPauseTime = System.currentTimeMillis(); + } + } else { + if (appPaused) { + return; + } + FileLog.e("tmessages", "reset app pause time"); + if (lastPauseTime != 0 && System.currentTimeMillis() - lastPauseTime > 5000) { + ContactsController.getInstance().checkContacts(); + } + lastPauseTime = 0; + ConnectionsManager.getInstance().applicationMovedToForeground(); + } + } + }); } - public static void setAppPaused(boolean value) { - appPaused = value; - FileLog.e("tmessages", "app paused = " + value); - if (!appPaused) { - resetLastPauseTime(); - } else { - lastPauseTime = System.currentTimeMillis(); - } + public long getPauseTime() { + return lastPauseTime; } //================================================================================ @@ -407,7 +451,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. datacenter = new Datacenter(); datacenter.datacenterId = 4; - datacenter.addAddressAndPort("31.210.235.12", 443); + datacenter.addAddressAndPort("149.154.167.90", 443); datacenters.put(datacenter.datacenterId, datacenter); datacenter = new Datacenter(); @@ -740,21 +784,14 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. } updatingDcSettings = false; } - }, null, true, RPCRequest.RPCRequestClassEnableUnauthorized | RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassWithoutLogin, dcNum == 0 ? currentDatacenterId : dcNum); + }, null, true, RPCRequest.RPCRequestClassEnableUnauthorized | RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassWithoutLogin | RPCRequest.RPCRequestClassTryDifferentDc, dcNum == 0 ? currentDatacenterId : dcNum); } - public long performRpc(final TLObject rpc, final RPCRequest.RPCRequestDelegate completionBlock, final RPCRequest.RPCProgressDelegate progressBlock, boolean requiresCompletion, int requestClass) { - return performRpc(rpc, completionBlock, progressBlock, requiresCompletion, requestClass, DEFAULT_DATACENTER_ID); - } - - public long performRpc(final TLObject rpc, final RPCRequest.RPCRequestDelegate completionBlock, final RPCRequest.RPCProgressDelegate progressBlock, boolean requiresCompletion, int requestClass, int datacenterId) { - return performRpc(rpc, completionBlock, progressBlock, null, requiresCompletion, requestClass, datacenterId); - } - - TLObject wrapInLayer(TLObject object, int datacenterId, RPCRequest request) { + private TLObject wrapInLayer(TLObject object, int datacenterId, RPCRequest request) { if (object.layer() > 0) { Datacenter datacenter = datacenterWithId(datacenterId); if (datacenter == null || datacenter.lastInitVersion != currentAppVersion) { + registerForPush(); request.initRequest = true; TLRPC.initConnection invoke = new TLRPC.initConnection(); invoke.query = object; @@ -792,7 +829,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. } object = invoke; } - TLRPC.invokeWithLayer12 invoke = new TLRPC.invokeWithLayer12(); + TLRPC.invokeWithLayer14 invoke = new TLRPC.invokeWithLayer14(); invoke.query = object; FileLog.d("wrap in layer", "" + object); return invoke; @@ -800,8 +837,19 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. return object; } - public static volatile long nextCallToken = 1; - long performRpc(final TLObject rpc, final RPCRequest.RPCRequestDelegate completionBlock, final RPCRequest.RPCProgressDelegate progressBlock, final RPCRequest.RPCQuickAckDelegate quickAckBlock, final boolean requiresCompletion, final int requestClass, final int datacenterId) { + public long performRpc(final TLObject rpc, final RPCRequest.RPCRequestDelegate completionBlock) { + return performRpc(rpc, completionBlock, null, true, RPCRequest.RPCRequestClassGeneric, DEFAULT_DATACENTER_ID); + } + + public long performRpc(final TLObject rpc, final RPCRequest.RPCRequestDelegate completionBlock, boolean requiresCompletion, int requestClass) { + return performRpc(rpc, completionBlock, null, requiresCompletion, requestClass, DEFAULT_DATACENTER_ID, true); + } + + public long performRpc(final TLObject rpc, final RPCRequest.RPCRequestDelegate completionBlock, final RPCRequest.RPCQuickAckDelegate quickAckBlock, final boolean requiresCompletion, final int requestClass, final int datacenterId) { + return performRpc(rpc, completionBlock, quickAckBlock, requiresCompletion, requestClass, datacenterId, true); + } + + public long performRpc(final TLObject rpc, final RPCRequest.RPCRequestDelegate completionBlock, final RPCRequest.RPCQuickAckDelegate quickAckBlock, final boolean requiresCompletion, final int requestClass, final int datacenterId, final boolean runQueue) { if (!UserConfig.isClientActivated() && (requestClass & RPCRequest.RPCRequestClassWithoutLogin) == 0) { FileLog.e("tmessages", "can't do request without login " + rpc); return 0; @@ -821,19 +869,14 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. request.rawRequest = rpc; request.rpcRequest = wrapInLayer(rpc, datacenterId, request); request.completionBlock = completionBlock; - request.progressBlock = progressBlock; request.quickAckBlock = quickAckBlock; request.requiresCompletion = requiresCompletion; requestQueue.add(request); - if (paused && ((request.flags & RPCRequest.RPCRequestClassDownloadMedia) != 0 || (request.flags & RPCRequest.RPCRequestClassUploadMedia) != 0)) { - lastPauseTime = System.currentTimeMillis(); - nextSleepTimeout = 30000; - FileLog.e("tmessages", "wakeup by download or upload request"); + if (runQueue) { + processRequestQueue(0, 0); } - - processRequestQueue(0, 0); } }); @@ -876,7 +919,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. if (notifyServer) { TLRPC.TL_rpc_drop_answer dropAnswer = new TLRPC.TL_rpc_drop_answer(); dropAnswer.req_msg_id = request.runningMessageId; - performRpc(dropAnswer, null, null, false, request.flags); + performRpc(dropAnswer, null, false, request.flags); } } @@ -956,20 +999,6 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. for (int i = 0; i < runningRequests.size(); i++) { RPCRequest request = runningRequests.get(i); - if (datacenters.size() > 1) { - if (updatingDcSettings && request.rawRequest instanceof TLRPC.TL_help_getConfig) { - if (updatingDcStartTime < currentTime - 60) { - FileLog.e("tmessages", "move TL_help_getConfig to requestQueue"); - requestQueue.add(request); - runningRequests.remove(i); - i--; - continue; - } - } else if (request.rawRequest instanceof TLRPC.TL_auth_sendCode || request.rawRequest instanceof TLRPC.TL_auth_signIn || request.rawRequest instanceof TLRPC.TL_auth_signUp) { - - } - } - int datacenterId = request.runningDatacenterId; if (datacenterId == DEFAULT_DATACENTER_ID) { if (movingToDatacenterId != DEFAULT_DATACENTER_ID) { @@ -978,6 +1007,22 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. datacenterId = currentDatacenterId; } + if (datacenters.size() > 1 && (request.flags & RPCRequest.RPCRequestClassTryDifferentDc) != 0) { + int requestStartTime = request.runningStartTime; + int timeout = 30; + if (updatingDcSettings && request.rawRequest instanceof TLRPC.TL_help_getConfig) { + requestStartTime = updatingDcStartTime; + timeout = 60; + } + if (requestStartTime != 0 && requestStartTime < currentTime - timeout) { + FileLog.e("tmessages", "move " + request.rawRequest + " to requestQueue"); + requestQueue.add(request); + runningRequests.remove(i); + i--; + continue; + } + } + Datacenter requestDatacenter = datacenterWithId(datacenterId); if (!request.initRequest && requestDatacenter.lastInitVersion != currentAppVersion) { request.rpcRequest = wrapInLayer(request.rawRequest, requestDatacenter.datacenterId, request); @@ -1009,8 +1054,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. if ((request.flags & RPCRequest.RPCRequestClassGeneric) != 0) { connection = requestDatacenter.getGenericConnection(this); } else if ((request.flags & RPCRequest.RPCRequestClassDownloadMedia) != 0) { - int num = (request.flags & RPCRequest.RPCRequestClassDownloadMedia2) != 0 ? 1 : 0; - connection = requestDatacenter.getDownloadConnection(num, this); + connection = requestDatacenter.getDownloadConnection(this); } else if ((request.flags & RPCRequest.RPCRequestClassUploadMedia) != 0 ) { connection = requestDatacenter.getUploadConnection(this); } @@ -1026,7 +1070,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. maxTimeout = 30.0f; } - boolean forceThisRequest = (request.flags & requestClass) != 0 && (_datacenterId == Integer.MIN_VALUE || requestDatacenter.datacenterId == _datacenterId); + boolean forceThisRequest = (request.flags & requestClass) != 0 && requestDatacenter.datacenterId == _datacenterId; if (request.rawRequest instanceof TLRPC.TL_get_future_salts || request.rawRequest instanceof TLRPC.TL_destroy_session) { if (request.runningMessageId != 0) { @@ -1051,6 +1095,10 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. } } + if (request.transportChannelToken != 0 && request.transportChannelToken != connection.channelToken) { + request.lastResendTime = 0; + } + request.retryCount++; NetworkMessage networkMessage = new NetworkMessage(); networkMessage.protoMessage = new TLRPC.TL_protoMessage(); @@ -1085,27 +1133,23 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. } } - boolean updatingState = MessagesController.getInstance().updatingState; - if (genericConnection != null && genericConnection.channelToken != 0) { - if (!updatingState) { - Datacenter currentDatacenter = datacenterWithId(currentDatacenterId); + Datacenter currentDatacenter = datacenterWithId(currentDatacenterId); - for (Long it : sessionsToDestroy) { - if (destroyingSessions.contains(it)) { - continue; - } - if (System.currentTimeMillis() / 1000 - lastDestroySessionRequestTime > 2.0) { - lastDestroySessionRequestTime = (int)(System.currentTimeMillis() / 1000); - TLRPC.TL_destroy_session destroySession = new TLRPC.TL_destroy_session(); - destroySession.session_id = it; - destroyingSessions.add(it); + for (Long it : sessionsToDestroy) { + if (destroyingSessions.contains(it)) { + continue; + } + if (System.currentTimeMillis() / 1000 - lastDestroySessionRequestTime > 2.0) { + lastDestroySessionRequestTime = (int)(System.currentTimeMillis() / 1000); + TLRPC.TL_destroy_session destroySession = new TLRPC.TL_destroy_session(); + destroySession.session_id = it; + destroyingSessions.add(it); - NetworkMessage networkMessage = new NetworkMessage(); - networkMessage.protoMessage = wrapMessage(destroySession, currentDatacenter.connection, false); - if (networkMessage.protoMessage != null) { - addMessageToDatacenter(currentDatacenter.datacenterId, networkMessage); - } + NetworkMessage networkMessage = new NetworkMessage(); + networkMessage.protoMessage = wrapMessage(destroySession, currentDatacenter.connection, false); + if (networkMessage.protoMessage != null) { + addMessageToDatacenter(currentDatacenter.datacenterId, networkMessage); } } } @@ -1133,22 +1177,6 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. continue; } - if (updatingDcSettings && datacenters.size() > 1 && request.rawRequest instanceof TLRPC.TL_help_getConfig) { - if (updatingDcStartTime < currentTime - 60) { - updatingDcStartTime = currentTime; - ArrayList allDc = new ArrayList(datacenters.values()); - for (int a = 0; a < allDc.size(); a++) { - Datacenter dc = allDc.get(a); - if (dc.datacenterId == request.runningDatacenterId) { - allDc.remove(a); - break; - } - } - Datacenter newDc = allDc.get(Math.abs(Utilities.random.nextInt() % allDc.size())); - request.runningDatacenterId = newDc.datacenterId; - } - } - int datacenterId = request.runningDatacenterId; if (datacenterId == DEFAULT_DATACENTER_ID) { if (movingToDatacenterId != DEFAULT_DATACENTER_ID && (request.flags & RPCRequest.RPCRequestClassEnableUnauthorized) == 0) { @@ -1157,6 +1185,35 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. datacenterId = currentDatacenterId; } + if (datacenters.size() > 1 && (request.flags & RPCRequest.RPCRequestClassTryDifferentDc) != 0) { + int requestStartTime = request.runningStartTime; + int timeout = 30; + if (updatingDcSettings && request.rawRequest instanceof TLRPC.TL_help_getConfig) { + requestStartTime = updatingDcStartTime; + updatingDcStartTime = currentTime; + timeout = 60; + } else { + request.runningStartTime = 0; + } + if (requestStartTime != 0 && requestStartTime < currentTime - timeout) { + ArrayList allDc = new ArrayList(datacenters.values()); + for (int a = 0; a < allDc.size(); a++) { + Datacenter dc = allDc.get(a); + if (dc.datacenterId == datacenterId) { + allDc.remove(a); + break; + } + } + Datacenter newDc = allDc.get(Math.abs(Utilities.random.nextInt() % allDc.size())); + datacenterId = newDc.datacenterId; + if (!(request.rawRequest instanceof TLRPC.TL_help_getConfig)) { + currentDatacenterId = datacenterId; + } else { + request.runningDatacenterId = datacenterId; + } + } + } + Datacenter requestDatacenter = datacenterWithId(datacenterId); if (!request.initRequest && requestDatacenter.lastInitVersion != currentAppVersion) { request.rpcRequest = wrapInLayer(request.rawRequest, requestDatacenter.datacenterId, request); @@ -1177,8 +1234,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. if ((request.flags & RPCRequest.RPCRequestClassGeneric) != 0) { connection = requestDatacenter.getGenericConnection(this); } else if ((request.flags & RPCRequest.RPCRequestClassDownloadMedia) != 0) { - int num = (request.flags & RPCRequest.RPCRequestClassDownloadMedia2) != 0 ? 1 : 0; - connection = requestDatacenter.getDownloadConnection(num, this); + connection = requestDatacenter.getDownloadConnection(this); } else if ((request.flags & RPCRequest.RPCRequestClassUploadMedia) != 0) { connection = requestDatacenter.getUploadConnection(this); } @@ -1187,10 +1243,6 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. continue; } - if (updatingState && (request.rawRequest instanceof TLRPC.TL_account_updateStatus || request.rawRequest instanceof TLRPC.TL_account_registerDevice)) { - continue; - } - if (request.requiresCompletion) { if ((request.flags & RPCRequest.RPCRequestClassGeneric) != 0) { if (genericRunningRequestCount >= 60) { @@ -1341,29 +1393,14 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. } } - if (datacenter.connection == null) { - datacenter.connection = new TcpConnection(datacenter.datacenterId); - datacenter.connection.delegate = this; - datacenter.connection.transportRequestClass = RPCRequest.RPCRequestClassGeneric; - } - - proceedToSendingMessages(arr, datacenter.connection, hasSendMessage); + proceedToSendingMessages(arr, datacenter.getGenericConnection(this), hasSendMessage); } } if ((requestClass & RPCRequest.RPCRequestClassGeneric) != 0) { - if (_datacenterId == Integer.MIN_VALUE) { - for (Datacenter datacenter : datacenters.values()) { - ArrayList messagesIt = genericMessagesToDatacenters.get(datacenter.datacenterId); - if (messagesIt == null || messagesIt.size() == 0) { - generatePing(datacenter, false); - } - } - } else { - ArrayList messagesIt = genericMessagesToDatacenters.get(_datacenterId); - if (messagesIt == null || messagesIt.size() == 0) { - generatePing(); - } + ArrayList messagesIt = genericMessagesToDatacenters.get(_datacenterId); + if (messagesIt == null || messagesIt.size() == 0) { + generatePing(); } } @@ -1501,7 +1538,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. } } - connection.sendData(null, transportData, reportAck); + connection.sendData(transportData, true, reportAck); } else { FileLog.e("tmessages", "***** Transport data is nil"); } @@ -1527,12 +1564,12 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. TLRPC.TL_protoMessage message = networkMessage.protoMessage; if (BuildVars.DEBUG_VERSION) { - if (message.body instanceof TLRPC.invokeWithLayer12) { - FileLog.d("tmessages", connection.getSissionId() + ":DC" + datacenter.datacenterId + "> Send message (" + message.seqno + ", " + message.msg_id + "): " + ((TLRPC.invokeWithLayer12)message.body).query); + if (message.body instanceof TLRPC.invokeWithLayer14) { + FileLog.d("tmessages", connection.getSissionId() + ":DC" + datacenter.datacenterId + "> Send message (" + message.seqno + ", " + message.msg_id + "): " + ((TLRPC.invokeWithLayer14)message.body).query); } else if (message.body instanceof TLRPC.initConnection) { TLRPC.initConnection r = (TLRPC.initConnection)message.body; - if (r.query instanceof TLRPC.invokeWithLayer12) { - FileLog.d("tmessages", connection.getSissionId() + ":DC" + datacenter.datacenterId + "> Send message (" + message.seqno + ", " + message.msg_id + "): " + ((TLRPC.invokeWithLayer12)r.query).query); + if (r.query instanceof TLRPC.invokeWithLayer14) { + FileLog.d("tmessages", connection.getSissionId() + ":DC" + datacenter.datacenterId + "> Send message (" + message.seqno + ", " + message.msg_id + "): " + ((TLRPC.invokeWithLayer14)r.query).query); } else { FileLog.d("tmessages", connection.getSissionId() + ":DC" + datacenter.datacenterId + "> Send message (" + message.seqno + ", " + message.msg_id + "): " + r.query); } @@ -1567,12 +1604,12 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. TLRPC.TL_protoMessage message = networkMessage.protoMessage; containerMessages.add(message); if (BuildVars.DEBUG_VERSION) { - if (message.body instanceof TLRPC.invokeWithLayer12) { - FileLog.d("tmessages", connection.getSissionId() + ":DC" + datacenter.datacenterId + "> Send message (" + message.seqno + ", " + message.msg_id + "): " + ((TLRPC.invokeWithLayer12)message.body).query); + if (message.body instanceof TLRPC.invokeWithLayer14) { + FileLog.d("tmessages", connection.getSissionId() + ":DC" + datacenter.datacenterId + "> Send message (" + message.seqno + ", " + message.msg_id + "): " + ((TLRPC.invokeWithLayer14)message.body).query); } else if (message.body instanceof TLRPC.initConnection) { TLRPC.initConnection r = (TLRPC.initConnection)message.body; - if (r.query instanceof TLRPC.invokeWithLayer12) { - FileLog.d("tmessages", connection.getSissionId() + ":DC" + datacenter.datacenterId + "> Send message (" + message.seqno + ", " + message.msg_id + "): " + ((TLRPC.invokeWithLayer12)r.query).query); + if (r.query instanceof TLRPC.invokeWithLayer14) { + FileLog.d("tmessages", connection.getSissionId() + ":DC" + datacenter.datacenterId + "> Send message (" + message.seqno + ", " + message.msg_id + "): " + ((TLRPC.invokeWithLayer14)r.query).query); } else { FileLog.d("tmessages", connection.getSissionId() + ":DC" + datacenter.datacenterId + "> Send message (" + message.seqno + ", " + message.msg_id + "): " + r.query); } @@ -1625,13 +1662,14 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. ByteBufferDesc dataForEncryption = BuffersStorage.getInstance().getFreeBuffer(innerOs.limit() + zeroCount); dataForEncryption.writeRaw(innerOs); BuffersStorage.getInstance().reuseFreeBuffer(innerOs); - byte[] b = new byte[1]; - for (int a = 0; a < zeroCount; a++) { + + if (zeroCount != 0) { + byte[] b = new byte[zeroCount]; Utilities.random.nextBytes(b); - dataForEncryption.writeByte(b[0]); + dataForEncryption.writeRaw(b); } - Utilities.aesIgeEncryption2(dataForEncryption.buffer, keyData.aesKey, keyData.aesIv, true, false, dataForEncryption.limit()); + Utilities.aesIgeEncryption(dataForEncryption.buffer, keyData.aesKey, keyData.aesIv, true, false, 0, dataForEncryption.limit()); ByteBufferDesc data = BuffersStorage.getInstance().getFreeBuffer(8 + messageKey.length + dataForEncryption.limit()); data.writeInt64(datacenter.authKeyId); @@ -1643,32 +1681,43 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. } void refillSaltSet(final Datacenter datacenter) { - for (RPCRequest request : requestQueue) { - if (request.rawRequest instanceof TLRPC.TL_get_future_salts) { - return; - } - } - - for (RPCRequest request : runningRequests) { - if (request.rawRequest instanceof TLRPC.TL_get_future_salts) { - return; - } - } - - TLRPC.TL_get_future_salts getFutureSalts = new TLRPC.TL_get_future_salts(); - getFutureSalts.num = 64; - - performRpc(getFutureSalts, new RPCRequest.RPCRequestDelegate() { + Utilities.stageQueue.postRunnable(new Runnable() { @Override - public void run(TLObject response, TLRPC.TL_error error) { - TLRPC.TL_futuresalts res = (TLRPC.TL_futuresalts)response; - if (error == null) { - int currentTime = getCurrentTime(); - datacenter.mergeServerSalts(currentTime, res.salts); - saveSession(); + public void run() { + for (RPCRequest request : requestQueue) { + if (request.rawRequest instanceof TLRPC.TL_get_future_salts) { + Datacenter requestDatacenter = datacenterWithId(request.runningDatacenterId); + if (requestDatacenter.datacenterId == datacenter.datacenterId) { + return; + } + } } + + for (RPCRequest request : runningRequests) { + if (request.rawRequest instanceof TLRPC.TL_get_future_salts) { + Datacenter requestDatacenter = datacenterWithId(request.runningDatacenterId); + if (requestDatacenter.datacenterId == datacenter.datacenterId) { + return; + } + } + } + + TLRPC.TL_get_future_salts getFutureSalts = new TLRPC.TL_get_future_salts(); + getFutureSalts.num = 32; + + performRpc(getFutureSalts, new RPCRequest.RPCRequestDelegate() { + @Override + public void run(TLObject response, TLRPC.TL_error error) { + TLRPC.TL_futuresalts res = (TLRPC.TL_futuresalts)response; + if (error == null) { + int currentTime = getCurrentTime(); + datacenter.mergeServerSalts(currentTime, res.salts); + saveSession(); + } + } + }, null, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassWithoutLogin, datacenter.datacenterId); } - }, null, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassWithoutLogin, datacenter.datacenterId); + }); } void messagesConfirmed(final long requestMsgId) { @@ -1684,7 +1733,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. }); } - void rpcCompleted(final long requestMsgId) { + private void rpcCompleted(final long requestMsgId) { Utilities.stageQueue.postRunnable(new Runnable() { @Override public void run() { @@ -1759,7 +1808,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. } registeringForPush = false; } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }, true, RPCRequest.RPCRequestClassGeneric); } } @@ -1860,6 +1909,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. pingIdToDate.remove(pid); } } else { + FileLog.e("tmessages", "received push ping"); sendingPushPing = false; } } else if (message instanceof TLRPC.TL_futuresalts) { @@ -1874,6 +1924,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. futureSalts.freeResources(); messagesConfirmed(requestMid); + request.completed = true; rpcCompleted(requestMid); break; @@ -2038,6 +2089,17 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. isError = true; request.completionBlock.run(null, implicitError != null ? implicitError : (TLRPC.TL_error) resultContainer.result); } else { + if (resultContainer.result instanceof TLRPC.updates_Difference) { + pushMessagesReceived = true; + Utilities.RunOnUIThread(new Runnable() { + @Override + public void run() { + if (wakeLock.isHeld()) { + wakeLock.release(); + } + } + }); + } request.completionBlock.run(resultContainer.result, null); } } @@ -2078,6 +2140,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. FileLog.e("tmessages", "rpc is init, but init connection already completed"); } } + request.completed = true; rpcCompleted(resultMid); } else { request.runningMessageId = 0; @@ -2160,12 +2223,20 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. TLRPC.MsgDetailedInfo detailedInfo = (TLRPC.MsgDetailedInfo)message; boolean requestResend = false; + boolean confirm = true; if (detailedInfo instanceof TLRPC.TL_msg_detailed_info) { - long requestMid = ((TLRPC.TL_msg_detailed_info)detailedInfo).msg_id; for (RPCRequest request : runningRequests) { - if (request.respondsToMessageId(requestMid)) { - requestResend = true; + if (request.respondsToMessageId(detailedInfo.msg_id)) { + if (request.completed) { + break; + } + if (request.lastResendTime == 0 || request.lastResendTime + 60 < (int)(System.currentTimeMillis() / 1000)) { + request.lastResendTime = (int)(System.currentTimeMillis() / 1000); + requestResend = true; + } else { + confirm = false; + } break; } } @@ -2185,7 +2256,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. ArrayList arr = new ArrayList(); arr.add(networkMessage); sendMessagesToTransport(arr, connection, false); - } else { + } else if (confirm) { connection.addMessageToConfirm(detailedInfo.answer_msg_id); } } else if (message instanceof TLRPC.TL_gzip_packed) { @@ -2195,8 +2266,26 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. } else if (message instanceof TLRPC.Updates) { if ((connection.transportRequestClass & RPCRequest.RPCRequestClassPush) != 0) { FileLog.e("tmessages", "received internal push"); - resumeNetworkMaybe(); + if (paused) { + pushMessagesReceived = false; + } + Utilities.RunOnUIThread(new Runnable() { + @Override + public void run() { + wakeLock.acquire(20000); + } + }); + resumeNetworkInternal(); } else { + pushMessagesReceived = true; + Utilities.RunOnUIThread(new Runnable() { + @Override + public void run() { + if (wakeLock.isHeld()) { + wakeLock.release(); + } + } + }); MessagesController.getInstance().processUpdates((TLRPC.Updates) message, false); } } else { @@ -2255,156 +2344,18 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. ByteBufferDesc transportData = generatePingData(connection); if (transportData != null) { if (push) { + FileLog.e("tmessages", "send push ping"); sendingPushPing = true; } - connection.sendData(null, transportData, false); + connection.sendData(transportData, true, false); } } } - public long needsToDecodeMessageIdFromPartialData(TcpConnection connection, byte[] data) { - if (data == null) { - return -1; - } - - Datacenter datacenter = datacenters.get(connection.getDatacenterId()); - SerializedData is = new SerializedData(data); - - byte[] keyId = is.readData(8); - SerializedData keyIdData = new SerializedData(keyId); - long key = keyIdData.readInt64(); - if (key == 0) { - return -1; - } else { - if (datacenter.authKeyId == 0 || key != datacenter.authKeyId) { - FileLog.e("tmessages", "Error: invalid auth key id " + connection); - return -1; - } - - byte[] messageKey = is.readData(16); - MessageKeyData keyData = Utilities.generateMessageKeyData(datacenter.authKey, messageKey, true); - - byte[] messageData = is.readData(data.length - 24); - messageData = Utilities.aesIgeEncryption(messageData, keyData.aesKey, keyData.aesIv, false, false, 0); - - if (messageData == null) { - return -1; - } - - SerializedData messageIs = new SerializedData(messageData); - long messageServerSalt = messageIs.readInt64(); - long messageSessionId = messageIs.readInt64(); - - if (messageSessionId != connection.getSissionId()) { - FileLog.e("tmessages", String.format("***** Error: invalid message session ID (%d instead of %d)", messageSessionId, connection.getSissionId())); - finishUpdatingState(connection); - return -1; - } - - long messageId = messageIs.readInt64(); - int messageSeqNo = messageIs.readInt32(); - int messageLength = messageIs.readInt32(); - - boolean[] stop = new boolean[1]; - long[] reqMsgId = new long[1]; - stop[0] = false; - reqMsgId[0] = 0; - - while (!stop[0] && reqMsgId[0] == 0) { - int signature = messageIs.readInt32(stop); - if (stop[0]) { - break; - } - findReqMsgId(messageIs, signature, reqMsgId, stop); - } - - return reqMsgId[0]; - } - } - - private void findReqMsgId(SerializedData is, int signature, long[] reqMsgId, boolean[] failed) { - if (signature == 0x73f1f8dc) { - if (is.length() < 4) { - failed[0] = true; - return; - } - int count = is.readInt32(failed); - if (failed[0]) { - return; - } - - for (int i = 0; i < count; i++) { - is.readInt64(failed); - if (failed[0]) { - return; - } - is.readInt32(failed); - if (failed[0]) { - return; - } - is.readInt32(failed); - if (failed[0]) { - return; - } - - int innerSignature = is.readInt32(failed); - if (failed[0]) { - return; - } - - findReqMsgId(is, innerSignature, reqMsgId, failed); - if (failed[0] || reqMsgId[0] != 0) { - return; - } - } - } else if (signature == 0xf35c6d01) { - long value = is.readInt64(failed); - if (failed[0]) { - return; - } - reqMsgId[0] = value; - } else if (signature == 0x62d6b459) { - is.readInt32(failed); - if (failed[0]) { - return; - } - - int count = is.readInt32(failed); - if (failed[0]) { - return; - } - - for (int i = 0; i < count; i++) { - is.readInt32(failed); - if (failed[0]) { - return; - } - } - } else if (signature == 0x347773c5) { - is.readInt64(failed); - if (failed[0]) { - return; - } - is.readInt64(failed); - } - } - //================================================================================ // TCPConnection delegate //================================================================================ - @Override - public void tcpConnectionProgressChanged(TcpConnection connection, long messageId, int currentSize, int length) { - for (RPCRequest request : runningRequests) { - if (request.respondsToMessageId(messageId)) { - if (request.progressBlock != null) { - request.progressBlock.progress(length, currentSize); - } - break; - } - } - } - @Override public void tcpConnectionClosed(TcpConnection connection) { if (connection.getDatacenterId() == currentDatacenterId && (connection.transportRequestClass & RPCRequest.RPCRequestClassGeneric) != 0) { @@ -2428,7 +2379,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. FileLog.e("tmessages", "no network available"); } } catch (Exception e) { - FileLog.e("tmessages", "NETWORK STATE GET ERROR"); + FileLog.e("tmessages", "NETWORK STATE GET ERROR", e); } } final int stateCopy = connectionState; @@ -2440,7 +2391,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. }); } else if ((connection.transportRequestClass & RPCRequest.RPCRequestClassPush) != 0) { sendingPushPing = false; - lastPushPingTime = System.currentTimeMillis() - 60000 * 3 + 5000; + lastPushPingTime = System.currentTimeMillis() - 60000 * 3 + 4000; } } @@ -2450,10 +2401,11 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. if (datacenter.authKey != null) { if ((connection.transportRequestClass & RPCRequest.RPCRequestClassPush) != 0) { sendingPushPing = false; - lastPushPingTime = System.currentTimeMillis() - 60000 * 3 + 10000; + lastPushPingTime = System.currentTimeMillis() - 60000 * 3 + 4000; } else { - if (paused && connection.getDatacenterId() == currentDatacenterId && (connection.transportRequestClass & RPCRequest.RPCRequestClassGeneric) != 0) { - resumeNetworkMaybe(); + if (paused && lastPauseTime != 0) { + lastPauseTime = System.currentTimeMillis(); + nextSleepTimeout = 30000; } processRequestQueue(connection.transportRequestClass, connection.getDatacenterId()); } @@ -2541,11 +2493,8 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. byte[] messageKey = data.readData(16); MessageKeyData keyData = Utilities.generateMessageKeyData(datacenter.authKey, messageKey, true); - data.compact(); - data.limit(data.position()); - data.position(0); - Utilities.aesIgeEncryption2(data.buffer, keyData.aesKey, keyData.aesIv, false, false, length - 24); + Utilities.aesIgeEncryption(data.buffer, keyData.aesKey, keyData.aesIv, false, false, data.position(), length - 24); long messageServerSalt = data.readInt64(); long messageSessionId = data.readInt64(); @@ -2570,14 +2519,12 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. connection.addMessageToConfirm(messageId); } - byte[] realMessageKeyFull = Utilities.computeSHA1(data.buffer, 0, Math.min(messageLength + 32, data.limit())); + byte[] realMessageKeyFull = Utilities.computeSHA1(data.buffer, 24, Math.min(messageLength + 32 + 24, data.limit())); if (realMessageKeyFull == null) { return; } - byte[] realMessageKey = new byte[16]; - System.arraycopy(realMessageKeyFull, realMessageKeyFull.length - 16, realMessageKey, 0, 16); - if (!Arrays.equals(messageKey, realMessageKey)) { + if (!Utilities.arraysEquals(messageKey, 0, realMessageKeyFull, realMessageKeyFull.length - 16)) { FileLog.e("tmessages", "***** Error: invalid message key"); connection.suspendConnection(true); connection.connect(); @@ -2591,6 +2538,7 @@ public class ConnectionsManager implements Action.ActionDelegate, TcpConnection. if (message == null) { FileLog.e("tmessages", "***** Error parsing message: " + constructor); } else { + FileLog.e("tmessages", "received object " + message); processMessage(message, messageId, messageSeqNo, messageServerSalt, connection, 0, 0); connection.addProcessedMessageId(messageId); diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/Datacenter.java b/TMessagesProj/src/main/java/org/telegram/messenger/Datacenter.java index 43fa8428a..4c1914128 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/Datacenter.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/Datacenter.java @@ -35,7 +35,7 @@ public class Datacenter { private volatile int currentAddressNum = 0; public TcpConnection connection; - private ArrayList downloadConnections = new ArrayList(); + private TcpConnection downloadConnection; private TcpConnection uploadConnection; public TcpConnection pushConnection; @@ -327,7 +327,7 @@ public class Datacenter { if (uploadConnection != null) { uploadConnection.suspendConnection(true); } - for (TcpConnection downloadConnection : downloadConnections) { + if (downloadConnection != null) { downloadConnection.suspendConnection(true); } } @@ -339,7 +339,7 @@ public class Datacenter { if (uploadConnection != null) { sessions.add(uploadConnection.getSissionId()); } - for (TcpConnection downloadConnection : downloadConnections) { + if (downloadConnection != null) { sessions.add(downloadConnection.getSissionId()); } } @@ -351,26 +351,21 @@ public class Datacenter { if (uploadConnection != null) { uploadConnection.recreateSession(); } - for (TcpConnection downloadConnection : downloadConnections) { + if (downloadConnection != null) { downloadConnection.recreateSession(); } } - public TcpConnection getDownloadConnection(int num, TcpConnection.TcpConnectionDelegate delegate) { - if (num >= 0 && authKey != null) { - TcpConnection downloadConnection = null; - if (num < downloadConnections.size()) { - downloadConnection = downloadConnections.get(num); - } else { + public TcpConnection getDownloadConnection(TcpConnection.TcpConnectionDelegate delegate) { + if (authKey != null) { + if (downloadConnection == null) { downloadConnection = new TcpConnection(datacenterId); downloadConnection.delegate = delegate; downloadConnection.transportRequestClass = RPCRequest.RPCRequestClassDownloadMedia; - downloadConnections.add(downloadConnection); } downloadConnection.connect(); - return downloadConnection; } - return null; + return downloadConnection; } public TcpConnection getUploadConnection(TcpConnection.TcpConnectionDelegate delegate) { diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/DispatchQueue.java b/TMessagesProj/src/main/java/org/telegram/messenger/DispatchQueue.java index bb260020a..15a573a93 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/DispatchQueue.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/DispatchQueue.java @@ -41,6 +41,24 @@ public class DispatchQueue extends Thread { } } + public void cancelRunnable(Runnable runnable) { + if (handler == null) { + synchronized (handlerSyncObject) { + if (handler == null) { + try { + handlerSyncObject.wait(); + } catch (Throwable t) { + t.printStackTrace(); + } + } + } + } + + if (handler != null) { + handler.removeCallbacks(runnable); + } + } + public void postRunnable(Runnable runnable) { postRunnable(runnable, 0); } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/ExportAuthorizationAction.java b/TMessagesProj/src/main/java/org/telegram/messenger/ExportAuthorizationAction.java index be79765a3..51367696d 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/ExportAuthorizationAction.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/ExportAuthorizationAction.java @@ -54,7 +54,7 @@ public class ExportAuthorizationAction extends Action { } } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } void beginImport() { diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/FileLoadOperation.java b/TMessagesProj/src/main/java/org/telegram/messenger/FileLoadOperation.java index cd577fbae..cf54747f4 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/FileLoadOperation.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/FileLoadOperation.java @@ -10,9 +10,9 @@ package org.telegram.messenger; import android.graphics.Bitmap; import android.graphics.BitmapFactory; -import android.os.Build; import android.provider.MediaStore; +import org.telegram.android.AndroidUtilities; import org.telegram.ui.ApplicationLoader; import java.io.RandomAccessFile; @@ -22,10 +22,19 @@ import java.io.FileInputStream; import java.io.InputStream; import java.net.URLConnection; import java.nio.channels.FileChannel; +import java.util.ArrayList; import java.util.Scanner; public class FileLoadOperation { - private int downloadChunkSize = 1024 * 256; + + private static class RequestInfo { + private long requestToken = 0; + private int offset = 0; + private TLRPC.TL_upload_file response = null; + } + + private final static int downloadChunkSize = 1024 * 32; + private final static int maxDownloadRequests = 3; public int datacenter_id; public TLRPC.InputFileLocation location; @@ -37,14 +46,10 @@ public class FileLoadOperation { public String filter; private byte[] key; private byte[] iv; - private long requestToken = 0; - private long requestToken2 = 0; - private int requestProgress = 0; - private int requestProgress2 = 0; + private int nextDownloadOffset = 0; - private TLRPC.TL_upload_file delayedRes = null; - private int delayedResOffset = 0; - private int delayedResTokenNum = 0; + private ArrayList requestInfos = new ArrayList(maxDownloadRequests); + private ArrayList delayedRequestInfos = new ArrayList(maxDownloadRequests - 1); private File cacheFileTemp; private File cacheFileFinal; @@ -56,7 +61,7 @@ public class FileLoadOperation { public boolean needBitmapCreate = true; private InputStream httpConnectionStream; private RandomAccessFile fileOutputStream; - RandomAccessFile fiv; + private RandomAccessFile fiv; public static interface FileLoadOperationDelegate { public abstract void didFinishLoadingFile(FileLoadOperation operation); @@ -214,7 +219,7 @@ public class FileLoadOperation { if (isLocalFile) { cacheFileFinal = new File(fileNameFinal); } else { - cacheFileFinal = new File(Utilities.getCacheDir(), fileNameFinal); + cacheFileFinal = new File(AndroidUtilities.getCacheDir(), fileNameFinal); } final boolean dontDelete = isLocalFile; final Long mediaIdFinal = mediaId; @@ -245,8 +250,8 @@ public class FileLoadOperation { float h_filter = 0; if (filter != null) { String args[] = filter.split("_"); - w_filter = Float.parseFloat(args[0]) * Utilities.density; - h_filter = Float.parseFloat(args[1]) * Utilities.density; + w_filter = Float.parseFloat(args[0]) * AndroidUtilities.density; + h_filter = Float.parseFloat(args[1]) * AndroidUtilities.density; opts.inJustDecodeBounds = true; if (mediaIdFinal != null) { @@ -289,11 +294,9 @@ public class FileLoadOperation { float bitmapH = image.getHeight(); if (bitmapW != w_filter && bitmapW > w_filter) { float scaleFactor = bitmapW / w_filter; - Bitmap scaledBitmap = Bitmap.createScaledBitmap(image, (int)w_filter, (int)(bitmapH / scaleFactor), false); + Bitmap scaledBitmap = Bitmap.createScaledBitmap(image, (int)w_filter, (int)(bitmapH / scaleFactor), true); if (image != scaledBitmap) { - if (Build.VERSION.SDK_INT < 11) { - image.recycle(); - } + image.recycle(); image = scaledBitmap; } } @@ -339,13 +342,13 @@ public class FileLoadOperation { }); return; } - cacheFileTemp = new File(Utilities.getCacheDir(), fileNameTemp); + cacheFileTemp = new File(AndroidUtilities.getCacheDir(), fileNameTemp); if (cacheFileTemp.exists()) { downloadedBytes = (int)cacheFileTemp.length(); nextDownloadOffset = downloadedBytes = downloadedBytes / 1024 * 1024; } if (fileNameIv != null) { - cacheIvTemp = new File(Utilities.getCacheDir(), fileNameIv); + cacheIvTemp = new File(AndroidUtilities.getCacheDir(), fileNameIv); try { fiv = new RandomAccessFile(cacheIvTemp, "rws"); long len = cacheIvTemp.length(); @@ -383,27 +386,44 @@ public class FileLoadOperation { if (httpUrl != null) { startDownloadHTTPRequest(); } else { - if (totalBytesCount >= 1024 * 1024) { - downloadChunkSize = 1024 * 256; - } else { - downloadChunkSize = 1024 * 32; - } - startDownloadRequest(); + Utilities.stageQueue.postRunnable(new Runnable() { + @Override + public void run() { + if (totalBytesCount != 0 && downloadedBytes == totalBytesCount) { + try { + onFinishLoadingFile(); + } catch (Exception e) { + delegate.didFailedLoadingFile(FileLoadOperation.this); + } + } else { + startDownloadRequest(); + } + } + }); + } } } public void cancel() { - if (state != 1) { - return; - } - state = 2; - cleanup(); - if (httpUrl == null) { - ConnectionsManager.getInstance().cancelRpc(requestToken, true); - ConnectionsManager.getInstance().cancelRpc(requestToken2, true); - } - delegate.didFailedLoadingFile(FileLoadOperation.this); + Utilities.stageQueue.postRunnable(new Runnable() { + @Override + public void run() { + if (state != 1) { + return; + } + state = 2; + cleanup(); + if (httpUrl == null) { + for (RequestInfo requestInfo : requestInfos) { + if (requestInfo.requestToken != 0) { + ConnectionsManager.getInstance().cancelRpc(requestInfo.requestToken, true, true); + } + } + } + delegate.didFailedLoadingFile(FileLoadOperation.this); + } + }); } private void cleanup() { @@ -435,12 +455,13 @@ public class FileLoadOperation { } catch (Exception e) { FileLog.e("tmessages", e); } - - if (delayedRes != null) { - delayedRes.disableFree = false; - delayedRes.freeResources(); - delayedRes = null; + for (RequestInfo requestInfo : delayedRequestInfos) { + if (requestInfo.response != null) { + requestInfo.response.disableFree = false; + requestInfo.response.freeResources(); + } } + delayedRequestInfos.clear(); } } @@ -454,7 +475,6 @@ public class FileLoadOperation { cacheIvTemp.delete(); } final boolean renamed = cacheFileTemp.renameTo(cacheFileFinal); - if (needBitmapCreate) { FileLoader.cacheOutQueue.postRunnable(new Runnable() { @Override @@ -476,8 +496,8 @@ public class FileLoadOperation { float h_filter; if (filter != null) { String args[] = filter.split("_"); - w_filter = Float.parseFloat(args[0]) * Utilities.density; - h_filter = Float.parseFloat(args[1]) * Utilities.density; + w_filter = Float.parseFloat(args[0]) * AndroidUtilities.density; + h_filter = Float.parseFloat(args[1]) * AndroidUtilities.density; opts.inJustDecodeBounds = true; BitmapFactory.decodeFile(cacheFileFinal.getAbsolutePath(), opts); @@ -514,11 +534,9 @@ public class FileLoadOperation { float bitmapH = image.getHeight(); if (bitmapW != w_filter && bitmapW > w_filter) { float scaleFactor = bitmapW / w_filter; - Bitmap scaledBitmap = Bitmap.createScaledBitmap(image, (int) w_filter, (int) (bitmapH / scaleFactor), false); + Bitmap scaledBitmap = Bitmap.createScaledBitmap(image, (int) w_filter, (int) (bitmapH / scaleFactor), true); if (image != scaledBitmap) { - if (Build.VERSION.SDK_INT < 11) { - image.recycle(); - } + image.recycle(); image = scaledBitmap; } } @@ -612,57 +630,51 @@ public class FileLoadOperation { } } - private void processRequestResult(TLRPC.TL_upload_file res, TLRPC.TL_error error, int dowloadOffset, int tokenNum) { + private void processRequestResult(RequestInfo requestInfo, TLRPC.TL_error error) { + requestInfos.remove(requestInfo); if (error == null) { try { - if (downloadedBytes != dowloadOffset) { - if (delayedRes != null) { - FileLog.e("tmessages", "something went wrong!"); + if (downloadedBytes != requestInfo.offset) { + if (state == 1) { + delayedRequestInfos.add(requestInfo); + requestInfo.response.disableFree = true; } - delayedRes = res; - delayedRes.disableFree = true; - delayedResOffset = dowloadOffset; - delayedResTokenNum = tokenNum; return; - } else { - if (tokenNum == 0) { - requestToken = 0; - } else if (tokenNum == 1) { - requestToken2 = 0; - } } - if (res.bytes.limit() == 0) { + if (requestInfo.response.bytes == null || requestInfo.response.bytes.limit() == 0) { onFinishLoadingFile(); return; } if (key != null) { - Utilities.aesIgeEncryption2(res.bytes.buffer, key, iv, false, true, res.bytes.limit()); + Utilities.aesIgeEncryption(requestInfo.response.bytes.buffer, key, iv, false, true, 0, requestInfo.response.bytes.limit()); } if (fileOutputStream != null) { FileChannel channel = fileOutputStream.getChannel(); - channel.write(res.bytes.buffer); + channel.write(requestInfo.response.bytes.buffer); } if (fiv != null) { fiv.seek(0); fiv.write(iv); } - downloadedBytes += res.bytes.limit(); + downloadedBytes += requestInfo.response.bytes.limit(); if (totalBytesCount > 0 && state == 1) { delegate.didChangedLoadProgress(FileLoadOperation.this, Math.min(1.0f, (float)downloadedBytes / (float)totalBytesCount)); } - if(delayedRes != null && res != delayedRes) { - TLRPC.TL_upload_file temp = delayedRes; - processRequestResult(temp, null, delayedResOffset, delayedResTokenNum); - if (delayedRes != null) { - delayedRes.disableFree = false; - delayedRes.freeResources(); - delayedRes = null; + for (int a = 0; a < delayedRequestInfos.size(); a++) { + RequestInfo delayedRequestInfo = delayedRequestInfos.get(a); + if (downloadedBytes == delayedRequestInfo.offset) { + delayedRequestInfos.remove(a); + processRequestResult(delayedRequestInfo, null); + delayedRequestInfo.response.disableFree = false; + delayedRequestInfo.response.freeResources(); + delayedRequestInfo = null; + break; } } - if (downloadedBytes % downloadChunkSize == 0 || totalBytesCount > 0 && totalBytesCount != downloadedBytes) { + if (totalBytesCount != downloadedBytes && downloadedBytes % downloadChunkSize == 0 || totalBytesCount > 0 && totalBytesCount > downloadedBytes) { startDownloadRequest(); } else { onFinishLoadingFile(); @@ -714,69 +726,36 @@ public class FileLoadOperation { } } - private void processRequestProgress() { - delegate.didChangedLoadProgress(FileLoadOperation.this, Math.min(1.0f, (float) (downloadedBytes + requestProgress + requestProgress2) / (float) totalBytesCount)); - } - private void startDownloadRequest() { - if (state != 1) { + if (state != 1 || totalBytesCount > 0 && nextDownloadOffset >= totalBytesCount || requestInfos.size() + delayedRequestInfos.size() >= maxDownloadRequests) { return; } - if (requestToken == 0) { - requestProgress = 0; - if (totalBytesCount > 0 && nextDownloadOffset >= totalBytesCount) { - return; - } - final TLRPC.TL_upload_getFile req = new TLRPC.TL_upload_getFile(); - req.location = location; - req.offset = nextDownloadOffset; - req.limit = downloadChunkSize; - nextDownloadOffset += downloadChunkSize; - final long time = System.currentTimeMillis(); - requestToken = ConnectionsManager.getInstance().performRpc(req, new RPCRequest.RPCRequestDelegate() { - @Override - public void run(TLObject response, TLRPC.TL_error error) { - processRequestResult((TLRPC.TL_upload_file) response, error, req.offset, 0); - } - }, new RPCRequest.RPCProgressDelegate() { - @Override - public void progress(int length, int progress) { - if (state == 1) { - requestProgress = progress; - if (totalBytesCount == -1) { - delegate.didChangedLoadProgress(FileLoadOperation.this, Math.min(1.0f, (float) (progress) / (float) length)); - } else if (totalBytesCount > 0) { - processRequestProgress(); - } - } - } - }, null, true, RPCRequest.RPCRequestClassDownloadMedia, datacenter_id); + int count = 1; + if (totalBytesCount > 0) { + count = Math.max(0, maxDownloadRequests - requestInfos.size() - delayedRequestInfos.size()); } - if (totalBytesCount > 0 && requestToken2 == 0) { - requestProgress2 = 0; + + for (int a = 0; a < count; a++) { if (totalBytesCount > 0 && nextDownloadOffset >= totalBytesCount) { - return; + break; } - final long time = System.currentTimeMillis(); - final TLRPC.TL_upload_getFile req = new TLRPC.TL_upload_getFile(); + boolean isLast = totalBytesCount <= 0 || a == count - 1 || totalBytesCount > 0 && nextDownloadOffset + downloadChunkSize >= totalBytesCount; + TLRPC.TL_upload_getFile req = new TLRPC.TL_upload_getFile(); req.location = location; req.offset = nextDownloadOffset; req.limit = downloadChunkSize; nextDownloadOffset += downloadChunkSize; - requestToken2 = ConnectionsManager.getInstance().performRpc(req, new RPCRequest.RPCRequestDelegate() { + + final RequestInfo requestInfo = new RequestInfo(); + requestInfos.add(requestInfo); + requestInfo.offset = req.offset; + requestInfo.requestToken = ConnectionsManager.getInstance().performRpc(req, new RPCRequest.RPCRequestDelegate() { @Override public void run(TLObject response, TLRPC.TL_error error) { - processRequestResult((TLRPC.TL_upload_file) response, error, req.offset, 1); + requestInfo.response = (TLRPC.TL_upload_file) response; + processRequestResult(requestInfo, error); } - }, new RPCRequest.RPCProgressDelegate() { - @Override - public void progress(int length, int progress) { - if (state == 1) { - requestProgress2 = progress; - processRequestProgress(); - } - } - }, null, true, RPCRequest.RPCRequestClassDownloadMedia | RPCRequest.RPCRequestClassDownloadMedia2, datacenter_id); + }, null, true, RPCRequest.RPCRequestClassDownloadMedia, datacenter_id, isLast); } } } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/FileLoader.java b/TMessagesProj/src/main/java/org/telegram/messenger/FileLoader.java index 9194bb178..fe0659d5e 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/FileLoader.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/FileLoader.java @@ -18,6 +18,7 @@ import android.net.Uri; import android.os.Build; import android.os.ParcelFileDescriptor; +import org.telegram.android.AndroidUtilities; import org.telegram.objects.MessageObject; import org.telegram.ui.ApplicationLoader; import org.telegram.ui.Views.ImageReceiver; @@ -291,10 +292,8 @@ public class FileLoader { if (runtimeHack != null) { runtimeHack.trackAlloc(oldBitmap.getRowBytes() * oldBitmap.getHeight()); } - if (Build.VERSION.SDK_INT < 11) { - if (!oldBitmap.isRecycled()) { - oldBitmap.recycle(); - } + if (!oldBitmap.isRecycled()) { + oldBitmap.recycle(); } } } @@ -466,6 +465,7 @@ public class FileLoader { } FileLoadOperation operation = loadOperationPaths.get(fileName); if (operation != null) { + loadOperationPaths.remove(fileName); if (audio != null) { audioLoadOperationQueue.remove(operation); } else if (photo != null) { @@ -946,8 +946,14 @@ public class FileLoader { } } }; + + boolean isLocalFile = false; + if (httpUrl != null && !httpUrl.startsWith("http")) { + isLocalFile = true; + } + img.loadOperation = loadOperation; - if (runningOperation.size() < maxConcurentLoadingOpertaionsCount) { + if (runningOperation.size() < maxConcurentLoadingOpertaionsCount || isLocalFile) { loadOperation.start(); runningOperation.add(loadOperation); } else { @@ -1119,7 +1125,7 @@ public class FileLoader { try { if (!cache) { String fileName = location.volume_id + "_" + location.local_id + ".jpg"; - final File cacheFile = new File(Utilities.getCacheDir(), fileName); + final File cacheFile = new File(AndroidUtilities.getCacheDir(), fileName); FileOutputStream stream = new FileOutputStream(cacheFile); scaledBitmap.compress(Bitmap.CompressFormat.JPEG, quality, stream); size.size = (int)stream.getChannel().size(); @@ -1129,10 +1135,8 @@ public class FileLoader { size.bytes = stream.toByteArray(); size.size = size.bytes.length; } - if (Build.VERSION.SDK_INT < 11) { - if (scaledBitmap != bitmap) { - scaledBitmap.recycle(); - } + if (scaledBitmap != bitmap) { + scaledBitmap.recycle(); } return size; } catch (Exception e) { diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/FileLog.java b/TMessagesProj/src/main/java/org/telegram/messenger/FileLog.java index 9ba567200..35d460d17 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/FileLog.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/FileLog.java @@ -11,6 +11,7 @@ package org.telegram.messenger; import android.net.Uri; import android.util.Log; +import org.telegram.android.FastDateFormat; import org.telegram.ui.ApplicationLoader; import java.io.File; diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/FileUploadOperation.java b/TMessagesProj/src/main/java/org/telegram/messenger/FileUploadOperation.java index 87e0a1a35..7f8aaadbe 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/FileUploadOperation.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/FileUploadOperation.java @@ -31,7 +31,7 @@ public class FileUploadOperation { private byte[] key; private byte[] iv; private byte[] ivChange; - private int fingerprint; + private int fingerprint = 0; private boolean isBigFile = false; FileInputStream stream; MessageDigest mdEnc = null; @@ -57,11 +57,9 @@ public class FileUploadOperation { System.arraycopy(key, 0, arr, 0, 32); System.arraycopy(iv, 0, arr, 32, 32); byte[] digest = md.digest(arr); - byte[] fingerprintBytes = new byte[4]; for (int a = 0; a < 4; a++) { - fingerprintBytes[a] = (byte)(digest[a] ^ digest[a + 4]); + fingerprint |= ((digest[a] ^ digest[a + 4]) & 0xFF) << (a * 8); } - fingerprint = Utilities.bytesToInt(fingerprintBytes); } catch (Exception e) { FileLog.e("tmessages", e); } @@ -138,7 +136,7 @@ public class FileUploadOperation { for (int a = 0; a < toAdd; a++) { sendBuffer.writeByte(0); } - Utilities.aesIgeEncryption2(sendBuffer.buffer, key, ivChange, true, true, readed + toAdd); + Utilities.aesIgeEncryption(sendBuffer.buffer, key, ivChange, true, true, 0, readed + toAdd); } sendBuffer.rewind(); if (!isBigFile) { @@ -211,11 +209,6 @@ public class FileUploadOperation { delegate.didFailedUploadingFile(FileUploadOperation.this); } } - }, new RPCRequest.RPCProgressDelegate() { - @Override - public void progress(int length, int progress) { - - } }, null, true, RPCRequest.RPCRequestClassUploadMedia, ConnectionsManager.DEFAULT_DATACENTER_ID); } } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/HandshakeAction.java b/TMessagesProj/src/main/java/org/telegram/messenger/HandshakeAction.java index e28cbbbca..49f6cedaf 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/HandshakeAction.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/HandshakeAction.java @@ -12,7 +12,6 @@ import java.math.BigInteger; import java.nio.ByteBuffer; import java.nio.ByteOrder; import java.util.ArrayList; -import java.util.Arrays; import java.util.HashMap; import java.util.Locale; @@ -29,9 +28,9 @@ public class HandshakeAction extends Action implements TcpConnection.TcpConnecti private boolean processedPQRes; - private byte[] reqPQMsgData; - private byte[] reqDHMsgData; - private byte[] setClientDHParamsMsgData; + private ByteBufferDesc reqPQMsgData; + private ByteBufferDesc reqDHMsgData; + private ByteBufferDesc setClientDHParamsMsgData; private boolean wasDisconnect = false; private long lastOutgoingMessageId; @@ -63,9 +62,18 @@ public class HandshakeAction extends Action implements TcpConnection.TcpConnecti authKey = null; authKeyId = 0; processedPQRes = false; - reqPQMsgData = null; - reqDHMsgData = null; - setClientDHParamsMsgData = null; + if (reqPQMsgData != null) { + BuffersStorage.getInstance().reuseFreeBuffer(reqPQMsgData); + reqPQMsgData = null; + } + if (reqDHMsgData != null) { + BuffersStorage.getInstance().reuseFreeBuffer(reqDHMsgData); + reqDHMsgData = null; + } + if (setClientDHParamsMsgData != null) { + BuffersStorage.getInstance().reuseFreeBuffer(setClientDHParamsMsgData); + setClientDHParamsMsgData = null; + } if (dropConnection) { datacenter.connection.suspendConnection(true); @@ -165,23 +173,17 @@ public class HandshakeAction extends Action implements TcpConnection.TcpConnecti return messageId; } - byte[] sendMessageData(TLObject message, long messageId) { - byte[] messageData; - SerializedData innerOs = new SerializedData(); - message.serializeToStream(innerOs); - messageData = innerOs.toByteArray(); - - SerializedData messageOs = new SerializedData(); + ByteBufferDesc sendMessageData(TLObject message, long messageId) { + int messageLength = message.getObjectSize(); + ByteBufferDesc messageOs = BuffersStorage.getInstance().getFreeBuffer(8 + 8 + 4 + messageLength); messageOs.writeInt64(0); messageOs.writeInt64(messageId); - messageOs.writeInt32(messageData.length); - messageOs.writeRaw(messageData); + messageOs.writeInt32(messageLength); + message.serializeToStream(messageOs); + message.freeResources(); - byte[] transportData = messageOs.toByteArray(); - - datacenter.connection.sendData(transportData, null, false); - - return transportData; + datacenter.connection.sendData(messageOs, false, false); + return messageOs; } void processMessage(TLObject message, long messageId) { @@ -196,7 +198,7 @@ public class HandshakeAction extends Action implements TcpConnection.TcpConnecti processedPQRes = true; final TLRPC.TL_resPQ resPq = (TLRPC.TL_resPQ)message; - if (Arrays.equals(authNonce, resPq.nonce)) { + if (Utilities.arraysEquals(authNonce, 0, resPq.nonce, 0)) { final HashMap publicKey = selectPublicKey(resPq.server_public_key_fingerprints); if (publicKey == null) { FileLog.e("tmessages", "***** Couldn't find valid server public key"); @@ -276,7 +278,10 @@ public class HandshakeAction extends Action implements TcpConnection.TcpConnecti msgsAck.msg_ids.add(messageIdf); sendMessageData(msgsAck, generateMessageId()); - reqPQMsgData = null; + if (reqPQMsgData != null) { + BuffersStorage.getInstance().reuseFreeBuffer(reqPQMsgData); + reqPQMsgData = null; + } reqDHMsgData = sendMessageData(reqDH, generateMessageId()); } }); @@ -322,33 +327,33 @@ public class HandshakeAction extends Action implements TcpConnection.TcpConnecti System.arraycopy(authNewNonce, 0, newNonce0_4, 0, 4); tmpAesIv.writeRaw(newNonce0_4); - byte[] answerWithHash = Utilities.aesIgeEncryption(serverDhParams.encrypted_answer, tmpAesKey.toByteArray(), tmpAesIv.toByteArray(), false, false, 0); - byte[] answerHash = new byte[20]; - System.arraycopy(answerWithHash, 0, answerHash, 0, 20); + ByteBufferDesc answerWithHash = BuffersStorage.getInstance().getFreeBuffer(serverDhParams.encrypted_answer.length); + answerWithHash.writeRaw(serverDhParams.encrypted_answer); + answerWithHash.position(0); + + Utilities.aesIgeEncryption(answerWithHash.buffer, tmpAesKey.toByteArray(), tmpAesIv.toByteArray(), false, false, 0, serverDhParams.encrypted_answer.length); + byte[] answerHash = new byte[20]; + answerWithHash.readRaw(answerHash); - byte[] answerData = new byte[answerWithHash.length - 20]; - System.arraycopy(answerWithHash, 20, answerData, 0, answerWithHash.length - 20); boolean hashVerified = false; for (int i = 0; i < 16; i++) { - byte[] computedAnswerHash = Utilities.computeSHA1(answerData); - if (Arrays.equals(computedAnswerHash, answerHash)) { + byte[] computedAnswerHash = Utilities.computeSHA1(answerWithHash.buffer, 20, answerWithHash.limit() - i); + if (Utilities.arraysEquals(computedAnswerHash, 0, answerHash, 0)) { hashVerified = true; break; } - byte[] answerData2 = new byte[answerData.length - 1]; - System.arraycopy(answerData, 0, answerData2, 0, answerData.length - 1); - answerData = answerData2; } if (!hashVerified) { FileLog.e("tmessages", "***** Couldn't decode DH params"); beginHandshake(false); + BuffersStorage.getInstance().reuseFreeBuffer(answerWithHash); return; } - SerializedData answerIs = new SerializedData(answerData); - int constructor = answerIs.readInt32(); - TLRPC.TL_server_DH_inner_data dhInnerData = (TLRPC.TL_server_DH_inner_data)TLClassStore.Instance().TLdeserialize(answerIs, constructor); + int constructor = answerWithHash.readInt32(); + TLRPC.TL_server_DH_inner_data dhInnerData = (TLRPC.TL_server_DH_inner_data)TLClassStore.Instance().TLdeserialize(answerWithHash, constructor); + BuffersStorage.getInstance().reuseFreeBuffer(answerWithHash); if (!(dhInnerData instanceof TLRPC.TL_server_DH_inner_data)) { FileLog.e("tmessages", "***** Couldn't parse decoded DH params"); @@ -360,12 +365,12 @@ public class HandshakeAction extends Action implements TcpConnection.TcpConnecti throw new RuntimeException("bad prime"); } - if (!Arrays.equals(authNonce, dhInnerData.nonce)) { + if (!Utilities.arraysEquals(authNonce, 0, dhInnerData.nonce, 0)) { FileLog.e("tmessages", "***** Invalid DH nonce"); beginHandshake(false); return; } - if (!Arrays.equals(authServerNonce, dhInnerData.server_nonce)) { + if (!Utilities.arraysEquals(authServerNonce, 0, dhInnerData.server_nonce, 0)) { FileLog.e("tmessages", "***** Invalid DH server nonce"); beginHandshake(false); return; @@ -427,50 +432,66 @@ public class HandshakeAction extends Action implements TcpConnection.TcpConnecti clientInnerData.server_nonce = authServerNonce; clientInnerData.g_b = g_b.toByteArray(); clientInnerData.retry_id = 0; - SerializedData os = new SerializedData(); - clientInnerData.serializeToStream(os); - byte[] clientInnerDataBytes = os.toByteArray(); - SerializedData clientDataWithHash = new SerializedData(); - clientDataWithHash.writeRaw(Utilities.computeSHA1(clientInnerDataBytes)); - clientDataWithHash.writeRaw(clientInnerDataBytes); - byte[] bb = new byte[1]; - while (clientDataWithHash.length() % 16 != 0) { + ByteBufferDesc os = BuffersStorage.getInstance().getFreeBuffer(clientInnerData.getObjectSize()); + clientInnerData.serializeToStream(os); + + int len = os.length() + 20; + int extraLen = len % 16 != 0 ? 16 - len % 16 : 0; + ByteBufferDesc clientDataWithHash = BuffersStorage.getInstance().getFreeBuffer(len + extraLen); + clientDataWithHash.writeRaw(Utilities.computeSHA1(os.buffer)); + os.position(0); + clientDataWithHash.writeRaw(os); + if (extraLen != 0) { + byte[] bb = new byte[extraLen]; Utilities.random.nextBytes(bb); - clientDataWithHash.writeByte(bb[0]); + clientDataWithHash.writeRaw(bb); } + BuffersStorage.getInstance().reuseFreeBuffer(os); TLRPC.TL_set_client_DH_params setClientDhParams = new TLRPC.TL_set_client_DH_params(); setClientDhParams.nonce = authNonce; setClientDhParams.server_nonce = authServerNonce; - setClientDhParams.encrypted_data = Utilities.aesIgeEncryption(clientDataWithHash.toByteArray(), tmpAesKey.toByteArray(), tmpAesIv.toByteArray(), true, false, 0); + Utilities.aesIgeEncryption(clientDataWithHash.buffer, tmpAesKey.toByteArray(), tmpAesIv.toByteArray(), true, false, 0, clientDataWithHash.length()); + setClientDhParams.encrypted_data = clientDataWithHash; TLRPC.TL_msgs_ack msgsAck = new TLRPC.TL_msgs_ack(); msgsAck.msg_ids = new ArrayList(); msgsAck.msg_ids.add(messageId); sendMessageData(msgsAck, generateMessageId()); - reqDHMsgData = null; + if (reqDHMsgData != null) { + BuffersStorage.getInstance().reuseFreeBuffer(reqDHMsgData); + reqDHMsgData = null; + } setClientDHParamsMsgData = sendMessageData(setClientDhParams, generateMessageId()); } else { FileLog.e("tmessages", "***** Couldn't set DH params"); beginHandshake(false); } } else if (message instanceof TLRPC.Set_client_DH_params_answer) { + if (setClientDHParamsMsgData != null) { + BuffersStorage.getInstance().reuseFreeBuffer(setClientDHParamsMsgData); + setClientDHParamsMsgData = null; + } + TLRPC.Set_client_DH_params_answer dhAnswer = (TLRPC.Set_client_DH_params_answer)message; - if (!Arrays.equals(authNonce, dhAnswer.nonce)) { + if (!Utilities.arraysEquals(authNonce, 0, dhAnswer.nonce, 0)) { FileLog.e("tmessages", "***** Invalid DH answer nonce"); beginHandshake(false); return; } - if (!Arrays.equals(authServerNonce, dhAnswer.server_nonce)) { + if (!Utilities.arraysEquals(authServerNonce, 0, dhAnswer.server_nonce, 0)) { FileLog.e("tmessages", "***** Invalid DH answer server nonce"); beginHandshake(false); return; } - reqDHMsgData = null; + if (reqDHMsgData != null) { + BuffersStorage.getInstance().reuseFreeBuffer(reqDHMsgData); + reqDHMsgData = null; + } TLRPC.TL_msgs_ack msgsAck = new TLRPC.TL_msgs_ack(); msgsAck.msg_ids = new ArrayList(); @@ -507,7 +528,7 @@ public class HandshakeAction extends Action implements TcpConnection.TcpConnecti if (message instanceof TLRPC.TL_dh_gen_ok) { TLRPC.TL_dh_gen_ok dhGenOk = (TLRPC.TL_dh_gen_ok)message; - if (!Arrays.equals(newNonceHash1, dhGenOk.new_nonce_hash1)) { + if (!Utilities.arraysEquals(newNonceHash1, 0, dhGenOk.new_nonce_hash1, 0)) { FileLog.e("tmessages", "***** Invalid DH answer nonce hash 1"); beginHandshake(false); return; @@ -532,7 +553,7 @@ public class HandshakeAction extends Action implements TcpConnection.TcpConnecti }); } else if (message instanceof TLRPC.TL_dh_gen_retry) { TLRPC.TL_dh_gen_retry dhRetry = (TLRPC.TL_dh_gen_retry)message; - if (!Arrays.equals(newNonceHash2, dhRetry.new_nonce_hash2)) { + if (!Utilities.arraysEquals(newNonceHash2, 0, dhRetry.new_nonce_hash2, 0)) { FileLog.e("tmessages", "***** Invalid DH answer nonce hash 2"); beginHandshake(false); return; @@ -541,7 +562,7 @@ public class HandshakeAction extends Action implements TcpConnection.TcpConnecti beginHandshake(false); } else if (message instanceof TLRPC.TL_dh_gen_fail) { TLRPC.TL_dh_gen_fail dhFail = (TLRPC.TL_dh_gen_fail)message; - if (!Arrays.equals(newNonceHash3, dhFail.new_nonce_hash3)) { + if (!Utilities.arraysEquals(newNonceHash3, 0, dhFail.new_nonce_hash3, 0)) { FileLog.e("tmessages", "***** Invalid DH answer nonce hash 3"); beginHandshake(false); return; @@ -560,11 +581,6 @@ public class HandshakeAction extends Action implements TcpConnection.TcpConnecti } } - @Override - public void tcpConnectionProgressChanged(TcpConnection connection, long messageId, int currentSize, int length) { - - } - @Override public void tcpConnectionClosed(final TcpConnection connection) { wasDisconnect = true; @@ -582,11 +598,11 @@ public class HandshakeAction extends Action implements TcpConnection.TcpConnecti return; } if (reqPQMsgData != null) { - datacenter.connection.sendData(reqPQMsgData, null, false); + datacenter.connection.sendData(reqPQMsgData, false, false); } else if (reqDHMsgData != null) { - datacenter.connection.sendData(reqDHMsgData, null, false); + datacenter.connection.sendData(reqDHMsgData, false, false); } else if (setClientDHParamsMsgData != null) { - datacenter.connection.sendData(setClientDHParamsMsgData, null, false); + datacenter.connection.sendData(setClientDHParamsMsgData, false, false); } } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/RPCRequest.java b/TMessagesProj/src/main/java/org/telegram/messenger/RPCRequest.java index ab6162aed..35ef4d115 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/RPCRequest.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/RPCRequest.java @@ -14,9 +14,6 @@ public class RPCRequest { public interface RPCRequestDelegate { void run(TLObject response, TLRPC.TL_error error); } - public interface RPCProgressDelegate { - void progress(int length, int progress); - } public interface RPCQuickAckDelegate { void quickAck(); } @@ -29,7 +26,7 @@ public class RPCRequest { public static int RPCRequestClassCanCompress = 32; public static int RPCRequestClassPush = 64; public static int RPCRequestClassWithoutLogin = 128; - public static int RPCRequestClassDownloadMedia2 = 256; + public static int RPCRequestClassTryDifferentDc = 256; static int RPCRequestClassTransportMask = (RPCRequestClassGeneric | RPCRequestClassDownloadMedia | RPCRequestClassUploadMedia); @@ -38,14 +35,15 @@ public class RPCRequest { int serverFailureCount; int flags; - public int retryCount = 0; + protected int retryCount = 0; + protected int lastResendTime = 0; + protected boolean completed = false; TLObject rawRequest; TLObject rpcRequest; int serializedLength; RPCRequestDelegate completionBlock; - RPCProgressDelegate progressBlock; RPCQuickAckDelegate quickAckBlock; boolean requiresCompletion; diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/TLClassStore.java b/TMessagesProj/src/main/java/org/telegram/messenger/TLClassStore.java index 2e1895e5c..513417a47 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/TLClassStore.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/TLClassStore.java @@ -412,6 +412,14 @@ public class TLClassStore { classStore.put(TLRPC.TL_decryptedMessageActionFlushHistory.constructor, TLRPC.TL_decryptedMessageActionFlushHistory.class); classStore.put(TLRPC.TL_decryptedMessageActionScreenshotMessages.constructor, TLRPC.TL_decryptedMessageActionScreenshotMessages.class); classStore.put(TLRPC.TL_messageEcryptedAction.constructor, TLRPC.TL_messageEcryptedAction.class); + classStore.put(TLRPC.TL_decryptedMessageActionNotifyLayer.constructor, TLRPC.TL_decryptedMessageActionNotifyLayer.class); + classStore.put(TLRPC.TL_decryptedMessageActionReadMessages.constructor, TLRPC.TL_decryptedMessageActionReadMessages.class); + classStore.put(TLRPC.TL_updateNotifySettings.constructor, TLRPC.TL_updateNotifySettings.class); + classStore.put(TLRPC.TL_updateUserBlocked.constructor, TLRPC.TL_updateUserBlocked.class); + classStore.put(TLRPC.TL_notifyAll.constructor, TLRPC.TL_notifyAll.class); + classStore.put(TLRPC.TL_notifyChats.constructor, TLRPC.TL_notifyChats.class); + classStore.put(TLRPC.TL_notifyUsers.constructor, TLRPC.TL_notifyUsers.class); + classStore.put(TLRPC.TL_notifyPeer.constructor, TLRPC.TL_notifyPeer.class); classStore.put(TLRPC.TL_msg_container.constructor, TLRPC.TL_msg_container.class); classStore.put(TLRPC.TL_fileEncryptedLocation.constructor, TLRPC.TL_fileEncryptedLocation.class); @@ -427,6 +435,10 @@ public class TLClassStore { classStore.put(TLRPC.TL_messageActionLoginUnknownLocation.constructor, TLRPC.TL_messageActionLoginUnknownLocation.class); classStore.put(TLRPC.TL_encryptedChat_old.constructor, TLRPC.TL_encryptedChat_old.class); classStore.put(TLRPC.TL_encryptedChatRequested_old.constructor, TLRPC.TL_encryptedChatRequested_old.class); + classStore.put(TLRPC.TL_decryptedMessageMediaVideo_old.constructor, TLRPC.TL_decryptedMessageMediaVideo_old.class); + classStore.put(TLRPC.TL_decryptedMessageMediaAudio_old.constructor, TLRPC.TL_decryptedMessageMediaAudio_old.class); + classStore.put(TLRPC.TL_audio_old.constructor, TLRPC.TL_audio_old.class); + classStore.put(TLRPC.TL_video_old.constructor, TLRPC.TL_video_old.class); } static TLClassStore store = null; diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/TLObject.java b/TMessagesProj/src/main/java/org/telegram/messenger/TLObject.java index 9c40cb6e4..8ee8bc002 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/TLObject.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/TLObject.java @@ -42,4 +42,10 @@ public class TLObject { public void freeResources() { } + + public int getObjectSize() { + ByteBufferDesc bufferDesc = new ByteBufferDesc(true); + serializeToStream(bufferDesc); + return bufferDesc.length(); + } } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/TLRPC.java b/TMessagesProj/src/main/java/org/telegram/messenger/TLRPC.java index 0cbc8368a..a2dad78c9 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/TLRPC.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/TLRPC.java @@ -140,6 +140,51 @@ public class TLRPC { } } + public static class NotifyPeer extends TLObject { + public Peer peer; + } + + public static class TL_notifyAll extends NotifyPeer { + public static int constructor = 0x74d07c60; + + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + } + } + + public static class TL_notifyChats extends NotifyPeer { + public static int constructor = 0xc007cec3; + + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + } + } + + public static class TL_notifyUsers extends NotifyPeer { + public static int constructor = 0xb4c83b4c; + + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + } + } + + public static class TL_notifyPeer extends NotifyPeer { + public static int constructor = 0x9fd40bd8; + + + public void readParams(AbsSerializedData stream) { + peer = (Peer)TLClassStore.Instance().TLdeserialize(stream, stream.readInt32()); + } + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + peer.serializeToStream(stream); + } + } + public static class TL_auth_checkedPhone extends TLObject { public static int constructor = 0xe300cc3b; @@ -1245,7 +1290,7 @@ public class TLRPC { } public static class TL_audio extends Audio { - public static int constructor = 0x427425e7; + public static int constructor = 0xc7ac6496; public void readParams(AbsSerializedData stream) { @@ -1254,6 +1299,7 @@ public class TLRPC { user_id = stream.readInt32(); date = stream.readInt32(); duration = stream.readInt32(); + mime_type = stream.readString(); size = stream.readInt32(); dc_id = stream.readInt32(); } @@ -1265,6 +1311,7 @@ public class TLRPC { stream.writeInt32(user_id); stream.writeInt32(date); stream.writeInt32(duration); + stream.writeString(mime_type); stream.writeInt32(size); stream.writeInt32(dc_id); } @@ -2515,7 +2562,7 @@ public class TLRPC { } public static class TL_video extends Video { - public static int constructor = 0x5a04a49f; + public static int constructor = 0x388fa391; public void readParams(AbsSerializedData stream) { @@ -2525,6 +2572,7 @@ public class TLRPC { date = stream.readInt32(); caption = stream.readString(); duration = stream.readInt32(); + mime_type = stream.readString(); size = stream.readInt32(); thumb = (PhotoSize)TLClassStore.Instance().TLdeserialize(stream, stream.readInt32()); dc_id = stream.readInt32(); @@ -2540,6 +2588,7 @@ public class TLRPC { stream.writeInt32(date); stream.writeString(caption); stream.writeInt32(duration); + stream.writeString(mime_type); stream.writeInt32(size); thumb.serializeToStream(stream); stream.writeInt32(dc_id); @@ -2820,7 +2869,7 @@ public class TLRPC { } public static class TL_inputMediaUploadedThumbVideo extends InputMedia { - public static int constructor = 0xe628a145; + public static int constructor = 0x9912dabf; public void readParams(AbsSerializedData stream) { @@ -2829,6 +2878,7 @@ public class TLRPC { duration = stream.readInt32(); w = stream.readInt32(); h = stream.readInt32(); + mime_type = stream.readString(); } public void serializeToStream(AbsSerializedData stream) { @@ -2838,6 +2888,7 @@ public class TLRPC { stream.writeInt32(duration); stream.writeInt32(w); stream.writeInt32(h); + stream.writeString(mime_type); } } @@ -2856,23 +2907,25 @@ public class TLRPC { } public static class TL_inputMediaUploadedAudio extends InputMedia { - public static int constructor = 0x61a6d436; + public static int constructor = 0x4e498cab; public void readParams(AbsSerializedData stream) { file = (InputFile)TLClassStore.Instance().TLdeserialize(stream, stream.readInt32()); duration = stream.readInt32(); + mime_type = stream.readString(); } public void serializeToStream(AbsSerializedData stream) { stream.writeInt32(constructor); file.serializeToStream(stream); stream.writeInt32(duration); + stream.writeString(mime_type); } } public static class TL_inputMediaUploadedVideo extends InputMedia { - public static int constructor = 0x4847d92a; + public static int constructor = 0x133ad6f6; public void readParams(AbsSerializedData stream) { @@ -2880,6 +2933,7 @@ public class TLRPC { duration = stream.readInt32(); w = stream.readInt32(); h = stream.readInt32(); + mime_type = stream.readString(); } public void serializeToStream(AbsSerializedData stream) { @@ -2888,6 +2942,7 @@ public class TLRPC { stream.writeInt32(duration); stream.writeInt32(w); stream.writeInt32(h); + stream.writeString(mime_type); } } @@ -3209,9 +3264,10 @@ public class TLRPC { } public static class TL_contacts_importedContacts extends TLObject { - public static int constructor = 0xd1cd0a4c; + public static int constructor = 0xad524315; public ArrayList imported = new ArrayList(); + public ArrayList retry_contacts = new ArrayList(); public ArrayList users = new ArrayList(); public void readParams(AbsSerializedData stream) { @@ -3222,6 +3278,11 @@ public class TLRPC { } stream.readInt32(); count = stream.readInt32(); + for (int a = 0; a < count; a++) { + retry_contacts.add(stream.readInt64()); + } + stream.readInt32(); + count = stream.readInt32(); for (int a = 0; a < count; a++) { users.add((User)TLClassStore.Instance().TLdeserialize(stream, stream.readInt32())); } @@ -3236,6 +3297,12 @@ public class TLRPC { imported.get(a).serializeToStream(stream); } stream.writeInt32(0x1cb5c415); + count = retry_contacts.size(); + stream.writeInt32(count); + for (int a = 0; a < count; a++) { + stream.writeInt64(retry_contacts.get(a)); + } + stream.writeInt32(0x1cb5c415); count = users.size(); stream.writeInt32(count); for (int a = 0; a < count; a++) { @@ -3275,6 +3342,8 @@ public class TLRPC { public ArrayList messages = new ArrayList(); public int pts; public int version; + public NotifyPeer peer; + public PeerNotifySettings notify_settings; public String first_name; public String last_name; public int qts; @@ -3283,6 +3352,7 @@ public class TLRPC { public ArrayList dc_options = new ArrayList(); public ChatParticipants participants; public EncryptedChat chat; + public boolean blocked; public long auth_key_id; public String device; public String location; @@ -3396,6 +3466,22 @@ public class TLRPC { } } + public static class TL_updateNotifySettings extends Update { + public static int constructor = 0xbec268ef; + + + public void readParams(AbsSerializedData stream) { + peer = (NotifyPeer)TLClassStore.Instance().TLdeserialize(stream, stream.readInt32()); + notify_settings = (PeerNotifySettings)TLClassStore.Instance().TLdeserialize(stream, stream.readInt32()); + } + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + peer.serializeToStream(stream); + notify_settings.serializeToStream(stream); + } + } + public static class TL_updateUserTyping extends Update { public static int constructor = 0x6baa8508; @@ -3586,6 +3672,22 @@ public class TLRPC { } } + public static class TL_updateUserBlocked extends Update { + public static int constructor = 0x80ece81a; + + + public void readParams(AbsSerializedData stream) { + user_id = stream.readInt32(); + blocked = stream.readBool(); + } + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + stream.writeInt32(user_id); + stream.writeBool(blocked); + } + } + public static class TL_updateActivation extends Update { public static int constructor = 0x6f690963; @@ -3847,6 +3949,7 @@ public class TLRPC { } public static class DecryptedMessageAction extends TLObject { + public int layer; public int ttl_seconds; public ArrayList random_ids = new ArrayList(); } @@ -3872,6 +3975,43 @@ public class TLRPC { } } + public static class TL_decryptedMessageActionNotifyLayer extends DecryptedMessageAction { + public static int constructor = 0xf3048883; + + + public void readParams(AbsSerializedData stream) { + layer = stream.readInt32(); + } + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + stream.writeInt32(layer); + } + } + + public static class TL_decryptedMessageActionReadMessages extends DecryptedMessageAction { + public static int constructor = 0xc4f40be; + + + public void readParams(AbsSerializedData stream) { + stream.readInt32(); + int count = stream.readInt32(); + for (int a = 0; a < count; a++) { + random_ids.add(stream.readInt64()); + } + } + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + stream.writeInt32(0x1cb5c415); + int count = random_ids.size(); + stream.writeInt32(count); + for (Long random_id : random_ids) { + stream.writeInt64(random_id); + } + } + } + public static class contacts_MyLink extends TLObject { public boolean contact; } @@ -4497,11 +4637,12 @@ public class TLRPC { } public static class TL_decryptedMessageMediaAudio extends DecryptedMessageMedia { - public static int constructor = 0x6080758f; + public static int constructor = 0x57e0a9cb; public void readParams(AbsSerializedData stream) { duration = stream.readInt32(); + mime_type = stream.readString(); size = stream.readInt32(); key = stream.readByteArray(); iv = stream.readByteArray(); @@ -4510,6 +4651,7 @@ public class TLRPC { public void serializeToStream(AbsSerializedData stream) { stream.writeInt32(constructor); stream.writeInt32(duration); + stream.writeString(mime_type); stream.writeInt32(size); stream.writeByteArray(key); stream.writeByteArray(iv); @@ -4517,7 +4659,7 @@ public class TLRPC { } public static class TL_decryptedMessageMediaVideo extends DecryptedMessageMedia { - public static int constructor = 0x4cee6ef3; + public static int constructor = 0x524a415d; public void readParams(AbsSerializedData stream) { @@ -4525,6 +4667,7 @@ public class TLRPC { thumb_w = stream.readInt32(); thumb_h = stream.readInt32(); duration = stream.readInt32(); + mime_type = stream.readString(); w = stream.readInt32(); h = stream.readInt32(); size = stream.readInt32(); @@ -4538,6 +4681,7 @@ public class TLRPC { stream.writeInt32(thumb_w); stream.writeInt32(thumb_h); stream.writeInt32(duration); + stream.writeString(mime_type); stream.writeInt32(w); stream.writeInt32(h); stream.writeInt32(size); @@ -6169,31 +6313,6 @@ public class TLRPC { } } - public static class TL_set_client_DH_params extends TLObject { - public static int constructor = 0xf5045f1f; - - public byte[] nonce; - public byte[] server_nonce; - public byte[] encrypted_data; - - public Class responseClass () { - return Set_client_DH_params_answer.class; - } - - public void readParams(AbsSerializedData stream) { - nonce = stream.readData(16); - server_nonce = stream.readData(16); - encrypted_data = stream.readByteArray(); - } - - public void serializeToStream(AbsSerializedData stream) { - stream.writeInt32(constructor); - stream.writeRaw(nonce); - stream.writeRaw(server_nonce); - stream.writeByteArray(encrypted_data); - } - } - public static class TL_auth_checkPhone extends TLObject { public static int constructor = 0x6fe51dfb; @@ -8000,59 +8119,6 @@ public class TLRPC { } } - public static class TL_messages_sendEncrypted extends TLObject { - public static int constructor = 0xa9776773; - - public TL_inputEncryptedChat peer; - public long random_id; - public byte[] data; - - public Class responseClass () { - return messages_SentEncryptedMessage.class; - } - - public void readParams(AbsSerializedData stream) { - peer = (TL_inputEncryptedChat)TLClassStore.Instance().TLdeserialize(stream, stream.readInt32()); - random_id = stream.readInt64(); - data = stream.readByteArray(); - } - - public void serializeToStream(AbsSerializedData stream) { - stream.writeInt32(constructor); - peer.serializeToStream(stream); - stream.writeInt64(random_id); - stream.writeByteArray(data); - } - } - - public static class TL_messages_sendEncryptedFile extends TLObject { - public static int constructor = 0x9a901b66; - - public TL_inputEncryptedChat peer; - public long random_id; - public byte[] data; - public InputEncryptedFile file; - - public Class responseClass () { - return messages_SentEncryptedMessage.class; - } - - public void readParams(AbsSerializedData stream) { - peer = (TL_inputEncryptedChat)TLClassStore.Instance().TLdeserialize(stream, stream.readInt32()); - random_id = stream.readInt64(); - data = stream.readByteArray(); - file = (InputEncryptedFile)TLClassStore.Instance().TLdeserialize(stream, stream.readInt32()); - } - - public void serializeToStream(AbsSerializedData stream) { - stream.writeInt32(constructor); - peer.serializeToStream(stream); - stream.writeInt64(random_id); - stream.writeByteArray(data); - file.serializeToStream(stream); - } - } - public static class TL_messages_sendEncryptedService extends TLObject { public static int constructor = 0x32d439a4; @@ -8080,6 +8146,98 @@ public class TLRPC { //manually created + public static class TL_set_client_DH_params extends TLObject { + public static int constructor = 0xf5045f1f; + + public byte[] nonce; + public byte[] server_nonce; + public ByteBufferDesc encrypted_data; + + public Class responseClass () { + return Set_client_DH_params_answer.class; + } + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + stream.writeRaw(nonce); + stream.writeRaw(server_nonce); + stream.writeByteBuffer(encrypted_data); + } + + @Override + public void freeResources() { + if (disableFree) { + return; + } + if (encrypted_data != null) { + BuffersStorage.getInstance().reuseFreeBuffer(encrypted_data); + encrypted_data = null; + } + } + } + + public static class TL_messages_sendEncrypted extends TLObject { + public static int constructor = 0xa9776773; + + public TL_inputEncryptedChat peer; + public long random_id; + public ByteBufferDesc data; + + public Class responseClass () { + return messages_SentEncryptedMessage.class; + } + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + peer.serializeToStream(stream); + stream.writeInt64(random_id); + stream.writeByteBuffer(data); + } + + @Override + public void freeResources() { + if (disableFree) { + return; + } + if (data != null) { + BuffersStorage.getInstance().reuseFreeBuffer(data); + data = null; + } + } + } + + public static class TL_messages_sendEncryptedFile extends TLObject { + public static int constructor = 0x9a901b66; + + public TL_inputEncryptedChat peer; + public long random_id; + public ByteBufferDesc data; + public InputEncryptedFile file; + + public Class responseClass () { + return messages_SentEncryptedMessage.class; + } + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + peer.serializeToStream(stream); + stream.writeInt64(random_id); + stream.writeByteBuffer(data); + file.serializeToStream(stream); + } + + @Override + public void freeResources() { + if (disableFree) { + return; + } + if (data != null) { + BuffersStorage.getInstance().reuseFreeBuffer(data); + data = null; + } + } + } + public static class UserStatus extends TLObject { public int expires; } @@ -8313,6 +8471,7 @@ public class TLRPC { for (int a = 0; a < count; a++) { TL_futureSalt salt = new TL_futureSalt(); salt.readParams(stream); + salts.add(salt); } } @@ -8692,11 +8851,12 @@ public class TLRPC { } public static class TL_dialog extends TLObject { - public static int constructor = 0x214a8cdf; + public static int constructor = 0xab3a99ac; public Peer peer; public int top_message; public int unread_count; + public PeerNotifySettings notify_settings; public int last_message_date; public long id; public int last_read; @@ -8705,6 +8865,7 @@ public class TLRPC { peer = (Peer)TLClassStore.Instance().TLdeserialize(stream, stream.readInt32()); top_message = stream.readInt32(); unread_count = stream.readInt32(); + notify_settings = (PeerNotifySettings)TLClassStore.Instance().TLdeserialize(stream, stream.readInt32()); } public void serializeToStream(AbsSerializedData stream) { @@ -8712,6 +8873,7 @@ public class TLRPC { peer.serializeToStream(stream); stream.writeInt32(top_message); stream.writeInt32(unread_count); + notify_settings.serializeToStream(stream); } } @@ -8770,6 +8932,7 @@ public class TLRPC { public int date; public String caption; public int duration; + public String mime_type; public int size; public PhotoSize thumb; public int dc_id; @@ -8801,6 +8964,7 @@ public class TLRPC { public int user_id; public int date; public int duration; + public String mime_type; public int size; public int dc_id; public String path; @@ -8974,8 +9138,8 @@ public class TLRPC { } } - public static class invokeWithLayer12 extends TLObject { - public static int constructor = 0xdda60d3c; + public static class invokeWithLayer14 extends TLObject { + public static int constructor = 0x2b9b08fa; public TLObject query; @@ -9226,4 +9390,114 @@ public class TLRPC { public byte[] key; public byte[] iv; } + + public static class TL_decryptedMessageMediaVideo_old extends TL_decryptedMessageMediaVideo { + public static int constructor = 0x4cee6ef3; + + + public void readParams(AbsSerializedData stream) { + thumb = stream.readByteArray(); + thumb_w = stream.readInt32(); + thumb_h = stream.readInt32(); + duration = stream.readInt32(); + w = stream.readInt32(); + h = stream.readInt32(); + size = stream.readInt32(); + key = stream.readByteArray(); + iv = stream.readByteArray(); + } + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + stream.writeByteArray(thumb); + stream.writeInt32(thumb_w); + stream.writeInt32(thumb_h); + stream.writeInt32(duration); + stream.writeInt32(w); + stream.writeInt32(h); + stream.writeInt32(size); + stream.writeByteArray(key); + stream.writeByteArray(iv); + } + } + + public static class TL_decryptedMessageMediaAudio_old extends TL_decryptedMessageMediaAudio { + public static int constructor = 0x6080758f; + + + public void readParams(AbsSerializedData stream) { + duration = stream.readInt32(); + size = stream.readInt32(); + key = stream.readByteArray(); + iv = stream.readByteArray(); + } + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + stream.writeInt32(duration); + stream.writeInt32(size); + stream.writeByteArray(key); + stream.writeByteArray(iv); + } + } + + public static class TL_audio_old extends TL_audio { + public static int constructor = 0x427425e7; + + + public void readParams(AbsSerializedData stream) { + id = stream.readInt64(); + access_hash = stream.readInt64(); + user_id = stream.readInt32(); + date = stream.readInt32(); + duration = stream.readInt32(); + size = stream.readInt32(); + dc_id = stream.readInt32(); + } + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + stream.writeInt64(id); + stream.writeInt64(access_hash); + stream.writeInt32(user_id); + stream.writeInt32(date); + stream.writeInt32(duration); + stream.writeInt32(size); + stream.writeInt32(dc_id); + } + } + + public static class TL_video_old extends TL_video { + public static int constructor = 0x5a04a49f; + + + public void readParams(AbsSerializedData stream) { + id = stream.readInt64(); + access_hash = stream.readInt64(); + user_id = stream.readInt32(); + date = stream.readInt32(); + caption = stream.readString(); + duration = stream.readInt32(); + size = stream.readInt32(); + thumb = (PhotoSize)TLClassStore.Instance().TLdeserialize(stream, stream.readInt32()); + dc_id = stream.readInt32(); + w = stream.readInt32(); + h = stream.readInt32(); + } + + public void serializeToStream(AbsSerializedData stream) { + stream.writeInt32(constructor); + stream.writeInt64(id); + stream.writeInt64(access_hash); + stream.writeInt32(user_id); + stream.writeInt32(date); + stream.writeString(caption); + stream.writeInt32(duration); + stream.writeInt32(size); + thumb.serializeToStream(stream); + stream.writeInt32(dc_id); + stream.writeInt32(w); + stream.writeInt32(h); + } + } } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/TcpConnection.java b/TMessagesProj/src/main/java/org/telegram/messenger/TcpConnection.java index 717cb3297..263ed8fdc 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/TcpConnection.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/TcpConnection.java @@ -33,7 +33,6 @@ public class TcpConnection extends ConnectionContext { public abstract void tcpConnectionConnected(TcpConnection connection); public abstract void tcpConnectionQuiackAckReceived(TcpConnection connection, int ack); public abstract void tcpConnectionReceivedData(TcpConnection connection, ByteBufferDesc data, int length); - public abstract void tcpConnectionProgressChanged(TcpConnection connection, long messageId, int currentSize, int length); } private static PyroSelector selector; @@ -46,7 +45,6 @@ public class TcpConnection extends ConnectionContext { private int failedConnectionCount; public TcpConnectionDelegate delegate; private ByteBufferDesc restOfTheData; - private long lastMessageId = 0; private boolean hasSomeDataSinceLastConnect = false; private int willRetryConnectCount = 5; private boolean isNextPort = false; @@ -284,8 +282,8 @@ public class TcpConnection extends ConnectionContext { connect(); } - public void sendData(final byte[] data, final ByteBufferDesc buff, final boolean reportAck) { - if (data == null && buff == null) { + public void sendData(final ByteBufferDesc buff, final boolean canReuse, final boolean reportAck) { + if (buff == null) { return; } selector.scheduleTask(new Runnable() { @@ -298,16 +296,13 @@ public class TcpConnection extends ConnectionContext { } if (client == null || client.isDisconnected()) { - BuffersStorage.getInstance().reuseFreeBuffer(buff); + if (canReuse) { + BuffersStorage.getInstance().reuseFreeBuffer(buff); + } return; } - int bufferLen = 0; - if (data != null) { - bufferLen = data.length; - } else if (buff != null) { - bufferLen = buff.limit(); - } + int bufferLen = buff.limit(); int packetLength = bufferLen / 4; if (packetLength < 0x7f) { @@ -336,10 +331,9 @@ public class TcpConnection extends ConnectionContext { } buffer.writeInt32(packetLength); } - if (data != null) { - buffer.writeRaw(data); - } else { - buffer.writeRaw(buff); + + buffer.writeRaw(buff); + if (canReuse) { BuffersStorage.getInstance().reuseFreeBuffer(buff); } @@ -389,19 +383,6 @@ public class TcpConnection extends ConnectionContext { buffer.limit(oldLimit); if (restOfTheData.position() != lastPacketLength) { //FileLog.e("tmessages", this + " don't get much data to restOfTheData"); - if (lastMessageId != -1 && lastMessageId != 0) { - if (delegate != null) { - final TcpConnectionDelegate finalDelegate = delegate; - final int arg2 = restOfTheData.position(); - final int arg3 = lastPacketLength; - Utilities.stageQueue.postRunnable(new Runnable() { - @Override - public void run() { - finalDelegate.tcpConnectionProgressChanged(TcpConnection.this, lastMessageId, arg2, arg3); - } - }); - } - } return; } else { //FileLog.e("tmessages", this + " get much data to restOfTheData - OK!"); @@ -424,7 +405,7 @@ public class TcpConnection extends ConnectionContext { datacenter.storeCurrentAddressAndPortNum(); isNextPort = false; if ((transportRequestClass & RPCRequest.RPCRequestClassPush) != 0) { - client.setTimeout(60000 * 3 + 20000); + client.setTimeout(60000 * 15); } else { client.setTimeout(25000); } @@ -497,32 +478,10 @@ public class TcpConnection extends ConnectionContext { if (currentPacketLength < buffer.remaining()) { FileLog.d("tmessages", TcpConnection.this + " Received message len " + currentPacketLength + " but packet larger " + buffer.remaining()); - lastMessageId = 0; } else if (currentPacketLength == buffer.remaining()) { FileLog.d("tmessages", TcpConnection.this + " Received message len " + currentPacketLength + " equal to packet size"); - lastMessageId = 0; } else { FileLog.d("tmessages", TcpConnection.this + " Received packet size less(" + buffer.remaining() + ") then message size(" + currentPacketLength + ")"); - if (buffer.remaining() >= 152 && (transportRequestClass & RPCRequest.RPCRequestClassDownloadMedia) != 0) { - if (lastMessageId == 0) { - byte[] temp = new byte[152]; - buffer.get(temp); - lastMessageId = ConnectionsManager.getInstance().needsToDecodeMessageIdFromPartialData(TcpConnection.this, temp); - } - if (lastMessageId != -1 && lastMessageId != 0) { - if (delegate != null) { - final TcpConnectionDelegate finalDelegate = delegate; - final int arg2 = buffer.remaining(); - final int arg3 = currentPacketLength; - Utilities.stageQueue.postRunnable(new Runnable() { - @Override - public void run() { - finalDelegate.tcpConnectionProgressChanged(TcpConnection.this, lastMessageId, arg2, arg3); - } - }); - } - } - } ByteBufferDesc reuseLater = null; int len = currentPacketLength + (fByte != 0x7f ? 1 : 4); diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/UserConfig.java b/TMessagesProj/src/main/java/org/telegram/messenger/UserConfig.java index 4869a96f0..34b469785 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/UserConfig.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/UserConfig.java @@ -12,6 +12,7 @@ import android.content.Context; import android.content.SharedPreferences; import android.util.Base64; +import org.telegram.android.MessagesStorage; import org.telegram.ui.ApplicationLoader; import java.io.File; @@ -197,6 +198,5 @@ public class UserConfig { contactsVersion = 1; saveIncomingPhotos = false; saveConfig(true); - MessagesController.getInstance().deleteAllAppAccounts(); } } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/Utilities.java b/TMessagesProj/src/main/java/org/telegram/messenger/Utilities.java index 59b64ffcc..9085e859d 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/Utilities.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/Utilities.java @@ -14,11 +14,8 @@ import android.content.ContentUris; import android.content.Context; import android.content.Intent; import android.content.SharedPreferences; -import android.content.pm.ActivityInfo; import android.content.res.Configuration; import android.database.Cursor; -import android.graphics.Point; -import android.graphics.Typeface; import android.net.Uri; import android.os.Build; import android.os.Environment; @@ -27,16 +24,12 @@ import android.provider.MediaStore; import android.text.Html; import android.text.SpannableStringBuilder; import android.util.Base64; -import android.view.Display; -import android.view.Surface; -import android.view.View; -import android.view.WindowManager; -import android.view.inputmethod.InputMethodManager; import net.hockeyapp.android.CrashManager; import net.hockeyapp.android.CrashManagerListener; import net.hockeyapp.android.UpdateManager; +import org.telegram.android.LocaleController; import org.telegram.ui.ApplicationLoader; import java.io.ByteArrayInputStream; @@ -49,7 +42,6 @@ import java.io.InputStream; import java.io.OutputStream; import java.math.BigInteger; import java.nio.ByteBuffer; -import java.nio.ByteOrder; import java.nio.channels.FileChannel; import java.security.KeyFactory; import java.security.MessageDigest; @@ -59,7 +51,6 @@ import java.security.spec.RSAPublicKeySpec; import java.text.SimpleDateFormat; import java.util.ArrayList; import java.util.Date; -import java.util.Hashtable; import java.util.Locale; import java.util.regex.Matcher; import java.util.regex.Pattern; @@ -69,16 +60,9 @@ import java.util.zip.GZIPOutputStream; import javax.crypto.Cipher; public class Utilities { - public static int statusBarHeight = 0; - public static float density = 1; - public static Point displaySize = new Point(); public static Pattern pattern = Pattern.compile("[0-9]+"); public static SecureRandom random = new SecureRandom(); private final static Integer lock = 1; - private static int prevOrientation = -10; - - private static boolean waitingForSms = false; - private static final Integer smsLock = 2; public static ArrayList goodPrimes = new ArrayList(); @@ -108,12 +92,8 @@ public class Utilities { R.drawable.group_blue, R.drawable.group_yellow}; - public static int externalCacheNotAvailableState = 0; - final protected static char[] hexArray = "0123456789ABCDEF".toCharArray(); - private static final Hashtable cache = new Hashtable(); - public static ProgressDialog progressDialog; static { @@ -128,7 +108,6 @@ public class Utilities { FileLog.e("tmessages", e); } - density = ApplicationLoader.applicationContext.getResources().getDisplayMetrics().density; SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("primes", Context.MODE_PRIVATE); String primes = preferences.getString("primes", null); if (primes == null) { @@ -149,104 +128,26 @@ public class Utilities { goodPrimes.add("C71CAEB9C6B1C9048E6C522F70F13F73980D40238E3E21C14934D037563D930F48198A0AA7C14058229493D22530F4DBFA336F6E0AC925139543AED44CCE7C3720FD51F69458705AC68CD4FE6B6B13ABDC9746512969328454F18FAF8C595F642477FE96BB2A941D5BCD1D4AC8CC49880708FA9B378E3C4F3A9060BEE67CF9A4A4A695811051907E162753B56B0F6B410DBA74D8A84B2A14B3144E0EF1284754FD17ED950D5965B4B9DD46582DB1178D169C6BC465B0D6FF9CA3928FEF5B9AE4E418FC15E83EBEA0F87FA9FF5EED70050DED2849F47BF959D956850CE929851F0D8115F635B105EE2E4E15D04B2454BF6F4FADF034B10403119CD8E3B92FCC5B"); } } - - checkDisplaySize(); } public native static long doPQNative(long _what); - public native static byte[] aesIgeEncryption(byte[] _what, byte[] _key, byte[] _iv, boolean encrypt, boolean changeIv, int len); - public native static void aesIgeEncryption2(ByteBuffer _what, byte[] _key, byte[] _iv, boolean encrypt, boolean changeIv, int len); public native static void loadBitmap(String path, int[] bitmap, int scale, int format, int width, int height); + private native static void aesIgeEncryption(ByteBuffer buffer, byte[] key, byte[] iv, boolean encrypt, int offset, int length); - public static void lockOrientation(Activity activity) { - if (prevOrientation != -10) { - return; - } - try { - prevOrientation = activity.getRequestedOrientation(); - WindowManager manager = (WindowManager)activity.getSystemService(Activity.WINDOW_SERVICE); - if (manager != null && manager.getDefaultDisplay() != null) { - int rotation = manager.getDefaultDisplay().getRotation(); - int orientation = activity.getResources().getConfiguration().orientation; - - if (rotation == Surface.ROTATION_270) { - if (orientation == Configuration.ORIENTATION_PORTRAIT) { - activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT); - } else { - if (Build.VERSION.SDK_INT >= 9) { - activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_REVERSE_LANDSCAPE); - } else { - activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE); - } - } - } else if (rotation == Surface.ROTATION_90) { - if (orientation == Configuration.ORIENTATION_PORTRAIT) { - if (Build.VERSION.SDK_INT >= 9) { - activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_REVERSE_PORTRAIT); - } else { - activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT); - } - } else { - activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE); - } - } else if (rotation == Surface.ROTATION_0) { - if (orientation == Configuration.ORIENTATION_LANDSCAPE) { - activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE); - } else { - activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT); - } - } else { - if (orientation == Configuration.ORIENTATION_LANDSCAPE) { - if (Build.VERSION.SDK_INT >= 9) { - activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_REVERSE_LANDSCAPE); - } else { - activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE); - } - } else { - if (Build.VERSION.SDK_INT >= 9) { - activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_REVERSE_PORTRAIT); - } else { - activity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT); - } - } - } - } - } catch (Exception e) { - FileLog.e("tmessages", e); - } - } - - public static void unlockOrientation(Activity activity) { - try { - if (prevOrientation != -10) { - activity.setRequestedOrientation(prevOrientation); - prevOrientation = -10; - } - } catch (Exception e) { - FileLog.e("tmessages", e); - } - } - - public static boolean isWaitingForSms() { - boolean value = false; - synchronized (smsLock) { - value = waitingForSms; - } - return value; - } - - public static void setWaitingForSms(boolean value) { - synchronized (smsLock) { - waitingForSms = value; - } + public static void aesIgeEncryption(ByteBuffer buffer, byte[] key, byte[] iv, boolean encrypt, boolean changeIv, int offset, int length) { + aesIgeEncryption(buffer, key, changeIv ? iv : iv.clone(), encrypt, offset, length); } public static Integer parseInt(String value) { Integer val = 0; - Matcher matcher = pattern.matcher(value); - if (matcher.find()) { - String num = matcher.group(0); - val = Integer.parseInt(num); + try { + Matcher matcher = pattern.matcher(value); + if (matcher.find()) { + String num = matcher.group(0); + val = Integer.parseInt(num); + } + } catch (Exception e) { + FileLog.e("tmessages", e); } return val; } @@ -259,22 +160,6 @@ public class Utilities { return null; } - public static File getCacheDir() { - if (externalCacheNotAvailableState == 1 || externalCacheNotAvailableState == 0 && Environment.getExternalStorageState().startsWith(Environment.MEDIA_MOUNTED)) { - externalCacheNotAvailableState = 1; - File file = ApplicationLoader.applicationContext.getExternalCacheDir(); - if (file != null) { - return file; - } - } - externalCacheNotAvailableState = 2; - File file = ApplicationLoader.applicationContext.getCacheDir(); - if (file != null) { - return file; - } - return new File(""); - } - public static String bytesToHex(byte[] bytes) { char[] hexChars = new char[bytes.length * 2]; int v; @@ -286,14 +171,6 @@ public class Utilities { return new String(hexChars); } - public static int dp(int value) { - return (int)(Math.max(1, density * value)); - } - - public static int dpf(float value) { - return (int)Math.ceil(density * value); - } - public static boolean isGoodPrime(byte[] prime, int g) { if (!(g >= 2 && g <= 7)) { return false; @@ -401,6 +278,18 @@ public class Utilities { } } + public static boolean arraysEquals(byte[] arr1, int offset1, byte[] arr2, int offset2) { + if (arr1 == null || arr2 == null || arr1.length - offset1 != arr2.length - offset2 || arr1.length - offset1 < 0) { + return false; + } + for (int a = offset1; a < arr1.length; a++) { + if (arr1[a + offset1] != arr2[a + offset2]) { + return false; + } + } + return true; + } + public static byte[] computeSHA1(byte[] convertme, int offset, int len) { try { MessageDigest md = MessageDigest.getInstance("SHA-1"); @@ -413,30 +302,29 @@ public class Utilities { } public static byte[] computeSHA1(ByteBuffer convertme, int offset, int len) { + int oldp = convertme.position(); + int oldl = convertme.limit(); try { MessageDigest md = MessageDigest.getInstance("SHA-1"); - int oldp = convertme.position(); - int oldl = convertme.limit(); convertme.position(offset); convertme.limit(len); md.update(convertme); - convertme.position(oldp); - convertme.limit(oldl); return md.digest(); } catch (Exception e) { FileLog.e("tmessages", e); + } finally { + convertme.limit(oldl); + convertme.position(oldp); } return null; } + public static byte[] computeSHA1(ByteBuffer convertme) { + return computeSHA1(convertme, 0, convertme.limit()); + } + public static byte[] computeSHA1(byte[] convertme) { - try { - MessageDigest md = MessageDigest.getInstance("SHA-1"); - return md.digest(convertme); - } catch (Exception e) { - FileLog.e("tmessages", e); - } - return null; + return computeSHA1(convertme, 0, convertme.length); } public static byte[] encryptWithRSA(BigInteger[] key, byte[] data) { @@ -453,26 +341,9 @@ public class Utilities { return null; } - public static byte[] longToBytes(long x) { - ByteBuffer buffer = ByteBuffer.allocate(8); - buffer.putLong(x); - return buffer.array(); - } - public static long bytesToLong(byte[] bytes) { - ByteBuffer buffer = ByteBuffer.allocate(8); - buffer.order(ByteOrder.LITTLE_ENDIAN); - buffer.put(bytes); - buffer.flip(); - return buffer.getLong(); - } - - public static int bytesToInt(byte[] bytes) { - ByteBuffer buffer = ByteBuffer.allocate(4); - buffer.order(ByteOrder.LITTLE_ENDIAN); - buffer.put(bytes); - buffer.flip(); - return buffer.getInt(); + return ((long) bytes[7] << 56) + (((long) bytes[6] & 0xFF) << 48) + (((long) bytes[5] & 0xFF) << 40) + (((long) bytes[4] & 0xFF) << 32) + + (((long) bytes[3] & 0xFF) << 24) + (((long) bytes[2] & 0xFF) << 16) + (((long) bytes[1] & 0xFF) << 8) + ((long) bytes[0] & 0xFF); } public static MessageKeyData generateMessageKeyData(byte[] authKey, byte[] messageKey, boolean incoming) { @@ -562,51 +433,6 @@ public class Utilities { return packedData; } - public static Typeface getTypeface(String assetPath) { - synchronized (cache) { - if (!cache.containsKey(assetPath)) { - try { - Typeface t = Typeface.createFromAsset(ApplicationLoader.applicationContext.getAssets(), - assetPath); - cache.put(assetPath, t); - } catch (Exception e) { - FileLog.e("Typefaces", "Could not get typeface '" + assetPath + "' because " + e.getMessage()); - return null; - } - } - return cache.get(assetPath); - } - } - - public static void showKeyboard(View view) { - if (view == null) { - return; - } - InputMethodManager inputManager = (InputMethodManager)view.getContext().getSystemService(Context.INPUT_METHOD_SERVICE); - inputManager.showSoftInput(view, InputMethodManager.SHOW_IMPLICIT); - - ((InputMethodManager) view.getContext().getSystemService(Context.INPUT_METHOD_SERVICE)).showSoftInput(view, 0); - } - - public static boolean isKeyboardShowed(View view) { - if (view == null) { - return false; - } - InputMethodManager inputManager = (InputMethodManager) view.getContext().getSystemService(Context.INPUT_METHOD_SERVICE); - return inputManager.isActive(view); - } - - public static void hideKeyboard(View view) { - if (view == null) { - return; - } - InputMethodManager imm = (InputMethodManager) view.getContext().getSystemService(Context.INPUT_METHOD_SERVICE); - if (!imm.isActive()) { - return; - } - imm.hideSoftInputFromWindow(view.getWindowToken(), 0); - } - public static void ShowProgressDialog(final Activity activity, final String message) { activity.runOnUiThread(new Runnable() { @Override @@ -624,25 +450,6 @@ public class Utilities { }); } - public static void checkDisplaySize() { - try { - WindowManager manager = (WindowManager)ApplicationLoader.applicationContext.getSystemService(Context.WINDOW_SERVICE); - if (manager != null) { - Display display = manager.getDefaultDisplay(); - if (display != null) { - if(android.os.Build.VERSION.SDK_INT < 13) { - displaySize.set(display.getWidth(), display.getHeight()); - } else { - display.getSize(displaySize); - } - FileLog.e("tmessages", "display size = " + displaySize.x + " " + displaySize.y); - } - } - } catch (Exception e) { - FileLog.e("tmessages", e); - } - } - public static void HideProgressDialog(Activity activity) { activity.runOnUiThread(new Runnable() { @Override diff --git a/TMessagesProj/src/main/java/org/telegram/objects/MessageObject.java b/TMessagesProj/src/main/java/org/telegram/objects/MessageObject.java index c3a28d8aa..155890350 100644 --- a/TMessagesProj/src/main/java/org/telegram/objects/MessageObject.java +++ b/TMessagesProj/src/main/java/org/telegram/objects/MessageObject.java @@ -16,12 +16,13 @@ import android.text.StaticLayout; import android.text.TextPaint; import android.text.util.Linkify; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.FileLog; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLObject; import org.telegram.messenger.TLRPC; -import org.telegram.messenger.Emoji; -import org.telegram.messenger.MessagesController; +import org.telegram.android.Emoji; +import org.telegram.android.MessagesController; import org.telegram.messenger.R; import org.telegram.messenger.UserConfig; import org.telegram.messenger.Utilities; @@ -68,7 +69,7 @@ public class MessageObject { textPaint.linkColor = 0xff316f9f; } - textPaint.setTextSize(Utilities.dp(MessagesController.getInstance().fontSize)); + textPaint.setTextSize(AndroidUtilities.dp(MessagesController.getInstance().fontSize)); messageOwner = message; @@ -271,7 +272,7 @@ public class MessageObject { } else { messageText = message.message; } - messageText = Emoji.replaceEmoji(messageText, textPaint.getFontMetricsInt(), Utilities.dp(20)); + messageText = Emoji.replaceEmoji(messageText, textPaint.getFontMetricsInt(), AndroidUtilities.dp(20)); if (message instanceof TLRPC.TL_message || (message instanceof TLRPC.TL_messageForwarded && (message.media == null || !(message.media instanceof TLRPC.TL_messageMediaEmpty)))) { if (message.media == null || message.media instanceof TLRPC.TL_messageMediaEmpty) { @@ -397,9 +398,9 @@ public class MessageObject { int maxWidth; if (messageOwner.to_id.chat_id != 0) { - maxWidth = Math.min(Utilities.displaySize.x, Utilities.displaySize.y) - Utilities.dp(122); + maxWidth = Math.min(AndroidUtilities.displaySize.x, AndroidUtilities.displaySize.y) - AndroidUtilities.dp(122); } else { - maxWidth = Math.min(Utilities.displaySize.x, Utilities.displaySize.y) - Utilities.dp(80); + maxWidth = Math.min(AndroidUtilities.displaySize.x, AndroidUtilities.displaySize.y) - AndroidUtilities.dp(80); } StaticLayout textLayout = null; @@ -467,13 +468,11 @@ public class MessageObject { FileLog.e("tmessages", e); } - int linesMaxWidth; + int linesMaxWidth = (int)Math.ceil(lastLine); int lastLineWidthWithLeft; int linesMaxWidthWithLeft; boolean hasNonRTL = false; - linesMaxWidth = (int)Math.ceil(lastLine); - if (a == blocksCount - 1) { lastLineWidth = linesMaxWidth; } @@ -493,6 +492,13 @@ public class MessageObject { lineWidth = 0; } + if (lineWidth > maxWidth + 100) { + int start = block.textLayout.getLineStart(n); + int end = block.textLayout.getLineEnd(n); + CharSequence text = block.textLayout.getText().subSequence(start, end); + continue; + } + try { lineLeft = block.textLayout.getLineLeft(n); } catch (Exception e) { @@ -539,4 +545,22 @@ public class MessageObject { public boolean isFromMe() { return messageOwner.from_id == UserConfig.getClientUserId(); } + + public boolean isUnread () { + return messageOwner.unread; + } + + public long getDialogId() { + if (messageOwner.dialog_id != 0) { + return messageOwner.dialog_id; + } else { + if (messageOwner.to_id.chat_id != 0) { + return -messageOwner.to_id.chat_id; + } else if (isFromMe()) { + return messageOwner.to_id.user_id; + } else { + return messageOwner.from_id; + } + } + } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Adapters/ContactsActivityAdapter.java b/TMessagesProj/src/main/java/org/telegram/ui/Adapters/ContactsActivityAdapter.java index f341e93af..190f99985 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Adapters/ContactsActivityAdapter.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Adapters/ContactsActivityAdapter.java @@ -14,10 +14,10 @@ import android.view.View; import android.view.ViewGroup; import android.widget.TextView; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLRPC; -import org.telegram.messenger.ContactsController; -import org.telegram.messenger.MessagesController; +import org.telegram.android.ContactsController; +import org.telegram.android.MessagesController; import org.telegram.messenger.R; import org.telegram.ui.Cells.ChatOrUserCell; import org.telegram.ui.Views.SectionedBaseAdapter; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Adapters/ContactsActivitySearchAdapter.java b/TMessagesProj/src/main/java/org/telegram/ui/Adapters/ContactsActivitySearchAdapter.java index 0da5808d1..b7436d735 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Adapters/ContactsActivitySearchAdapter.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Adapters/ContactsActivitySearchAdapter.java @@ -13,9 +13,9 @@ import android.view.View; import android.view.ViewGroup; import org.telegram.messenger.TLRPC; -import org.telegram.messenger.ContactsController; +import org.telegram.android.ContactsController; import org.telegram.messenger.FileLog; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.UserConfig; import org.telegram.messenger.Utilities; import org.telegram.ui.Cells.ChatOrUserCell; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/ApplicationLoader.java b/TMessagesProj/src/main/java/org/telegram/ui/ApplicationLoader.java index 52a7660ea..949dced5d 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/ApplicationLoader.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/ApplicationLoader.java @@ -29,14 +29,16 @@ import com.google.android.gms.common.ConnectionResult; import com.google.android.gms.common.GooglePlayServicesUtil; import com.google.android.gms.gcm.GoogleCloudMessaging; -import org.telegram.messenger.NotificationsService; +import org.telegram.android.AndroidUtilities; +import org.telegram.android.ContactsController; +import org.telegram.android.NotificationsService; import org.telegram.messenger.BuildVars; import org.telegram.messenger.ConnectionsManager; import org.telegram.messenger.FileLog; -import org.telegram.messenger.LocaleController; -import org.telegram.messenger.MessagesController; -import org.telegram.messenger.NativeLoader; -import org.telegram.messenger.ScreenReceiver; +import org.telegram.android.LocaleController; +import org.telegram.android.MessagesController; +import org.telegram.android.NativeLoader; +import org.telegram.android.ScreenReceiver; import org.telegram.messenger.UserConfig; import org.telegram.messenger.Utilities; @@ -57,6 +59,7 @@ public class ApplicationLoader extends Application { private static volatile boolean applicationInited = false; public static volatile boolean isScreenOn = false; + public static volatile boolean mainInterfacePaused = true; public static void postInitApplication() { if (applicationInited) { @@ -65,8 +68,6 @@ public class ApplicationLoader extends Application { applicationInited = true; - NativeLoader.initNativeLibs(applicationContext); - try { LocaleController.getInstance(); } catch (Exception e) { @@ -128,12 +129,15 @@ public class ApplicationLoader extends Application { ApplicationLoader app = (ApplicationLoader)ApplicationLoader.applicationContext; app.initPlayServices(); FileLog.e("tmessages", "app initied"); + + ContactsController.getInstance().checkAppAccount(); } @Override public void onCreate() { super.onCreate(); applicationContext = getApplicationContext(); + NativeLoader.initNativeLibs(ApplicationLoader.applicationContext); applicationHandler = new Handler(applicationContext.getMainLooper()); @@ -177,7 +181,7 @@ public class ApplicationLoader extends Application { super.onConfigurationChanged(newConfig); try { LocaleController.getInstance().onDeviceConfigurationChange(newConfig); - Utilities.checkDisplaySize(); + AndroidUtilities.checkDisplaySize(); } catch (Exception e) { e.printStackTrace(); } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatAudioCell.java b/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatAudioCell.java index 10d5c1cda..0c61b173b 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatAudioCell.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatAudioCell.java @@ -16,12 +16,12 @@ import android.text.StaticLayout; import android.text.TextPaint; import android.view.MotionEvent; import android.view.SoundEffectConstants; -import android.view.View; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.FileLoader; -import org.telegram.messenger.MediaController; +import org.telegram.android.MediaController; import org.telegram.messenger.TLRPC; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; import org.telegram.objects.MessageObject; @@ -30,7 +30,6 @@ import org.telegram.ui.Views.ProgressView; import org.telegram.ui.Views.SeekBar; import java.io.File; -import java.lang.ref.WeakReference; public class ChatAudioCell extends ChatBaseCell implements SeekBar.SeekBarDelegate, MediaController.FileDownloadProgressListener { @@ -90,7 +89,7 @@ public class ChatAudioCell extends ChatBaseCell implements SeekBar.SeekBarDelega statesDrawable[7][1] = getResources().getDrawable(R.drawable.audiocancel2_pressed); timePaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - timePaint.setTextSize(Utilities.dp(12)); + timePaint.setTextSize(AndroidUtilities.dp(12)); } } @@ -115,7 +114,7 @@ public class ChatAudioCell extends ChatBaseCell implements SeekBar.SeekBarDelega } invalidate(); } else { - int side = Utilities.dp(36); + int side = AndroidUtilities.dp(36); if (event.getAction() == MotionEvent.ACTION_DOWN) { if (x >= buttonX && x <= buttonX + side && y >= buttonY && y <= buttonY + side) { buttonPressed = 1; @@ -220,7 +219,7 @@ public class ChatAudioCell extends ChatBaseCell implements SeekBar.SeekBarDelega public void updateButtonState() { String fileName = currentMessageObject.getFileName(); - File cacheFile = new File(Utilities.getCacheDir(), fileName); + File cacheFile = new File(AndroidUtilities.getCacheDir(), fileName); if (cacheFile.exists()) { MediaController.getInstance().removeLoadingFileObserver(this); boolean playing = MediaController.getInstance().isPlayingAudio(currentMessageObject); @@ -286,11 +285,11 @@ public class ChatAudioCell extends ChatBaseCell implements SeekBar.SeekBarDelega @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { int width = MeasureSpec.getSize(widthMeasureSpec); - setMeasuredDimension(width, Utilities.dp(68)); + setMeasuredDimension(width, AndroidUtilities.dp(68)); if (isChat) { - backgroundWidth = Math.min(width - Utilities.dp(102), Utilities.dp(300)); + backgroundWidth = Math.min(width - AndroidUtilities.dp(102), AndroidUtilities.dp(300)); } else { - backgroundWidth = Math.min(width - Utilities.dp(50), Utilities.dp(300)); + backgroundWidth = Math.min(width - AndroidUtilities.dp(50), AndroidUtilities.dp(300)); } } @@ -299,33 +298,33 @@ public class ChatAudioCell extends ChatBaseCell implements SeekBar.SeekBarDelega super.onLayout(changed, left, top, right, bottom); if (currentMessageObject.isOut()) { - avatarImage.imageX = layoutWidth - backgroundWidth + Utilities.dp(9); - seekBarX = layoutWidth - backgroundWidth + Utilities.dp(97); - buttonX = layoutWidth - backgroundWidth + Utilities.dp(67); - timeX = layoutWidth - backgroundWidth + Utilities.dp(71); + avatarImage.imageX = layoutWidth - backgroundWidth + AndroidUtilities.dp(9); + seekBarX = layoutWidth - backgroundWidth + AndroidUtilities.dp(97); + buttonX = layoutWidth - backgroundWidth + AndroidUtilities.dp(67); + timeX = layoutWidth - backgroundWidth + AndroidUtilities.dp(71); } else { if (isChat) { - avatarImage.imageX = Utilities.dp(69); - seekBarX = Utilities.dp(158); - buttonX = Utilities.dp(128); - timeX = Utilities.dp(132); + avatarImage.imageX = AndroidUtilities.dp(69); + seekBarX = AndroidUtilities.dp(158); + buttonX = AndroidUtilities.dp(128); + timeX = AndroidUtilities.dp(132); } else { - avatarImage.imageX = Utilities.dp(16); - seekBarX = Utilities.dp(106); - buttonX = Utilities.dp(76); - timeX = Utilities.dp(80); + avatarImage.imageX = AndroidUtilities.dp(16); + seekBarX = AndroidUtilities.dp(106); + buttonX = AndroidUtilities.dp(76); + timeX = AndroidUtilities.dp(80); } } - avatarImage.imageY = Utilities.dp(9); - avatarImage.imageW = Utilities.dp(50); - avatarImage.imageH = Utilities.dp(50); + avatarImage.imageY = AndroidUtilities.dp(9); + avatarImage.imageW = AndroidUtilities.dp(50); + avatarImage.imageH = AndroidUtilities.dp(50); - seekBar.width = backgroundWidth - Utilities.dp(112); - seekBar.height = Utilities.dp(30); - progressView.width = backgroundWidth - Utilities.dp(136); - progressView.height = Utilities.dp(30); - seekBarY = Utilities.dp(13); - buttonY = Utilities.dp(10); + seekBar.width = backgroundWidth - AndroidUtilities.dp(112); + seekBar.height = AndroidUtilities.dp(30); + progressView.width = backgroundWidth - AndroidUtilities.dp(136); + progressView.height = AndroidUtilities.dp(30); + seekBarY = AndroidUtilities.dp(13); + buttonY = AndroidUtilities.dp(10); updateProgress(); } @@ -380,14 +379,14 @@ public class ChatAudioCell extends ChatBaseCell implements SeekBar.SeekBarDelega return; } - avatarImage.draw(canvas, avatarImage.imageX, avatarImage.imageY, Utilities.dp(50), Utilities.dp(50)); + avatarImage.draw(canvas, avatarImage.imageX, avatarImage.imageY, AndroidUtilities.dp(50), AndroidUtilities.dp(50)); canvas.save(); if (buttonState == 0 || buttonState == 1) { canvas.translate(seekBarX, seekBarY); seekBar.draw(canvas); } else { - canvas.translate(seekBarX + Utilities.dp(12), seekBarY); + canvas.translate(seekBarX + AndroidUtilities.dp(12), seekBarY); progressView.draw(canvas); } canvas.restore(); @@ -400,14 +399,14 @@ public class ChatAudioCell extends ChatBaseCell implements SeekBar.SeekBarDelega timePaint.setColor(0xff70b15c); } Drawable buttonDrawable = statesDrawable[state][buttonPressed]; - int side = Utilities.dp(36); + int side = AndroidUtilities.dp(36); int x = (side - buttonDrawable.getIntrinsicWidth()) / 2; int y = (side - buttonDrawable.getIntrinsicHeight()) / 2; setDrawableBounds(buttonDrawable, x + buttonX, y + buttonY); buttonDrawable.draw(canvas); canvas.save(); - canvas.translate(timeX, Utilities.dp(45)); + canvas.translate(timeX, AndroidUtilities.dp(45)); timeLayout.draw(canvas); canvas.restore(); } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatBaseCell.java b/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatBaseCell.java index 552b411fc..cde0be595 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatBaseCell.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatBaseCell.java @@ -22,9 +22,10 @@ import android.view.MotionEvent; import android.view.SoundEffectConstants; import android.view.ViewConfiguration; -import org.telegram.messenger.LocaleController; +import org.telegram.android.AndroidUtilities; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLRPC; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; import org.telegram.objects.MessageObject; @@ -114,6 +115,8 @@ public class ChatBaseCell extends BaseCell { private CheckForLongPress pendingCheckForLongPress = null; private CheckForTap pendingCheckForTap = null; + private int last_send_state = 0; + private final class CheckForTap implements Runnable { public void run() { if (pendingCheckForLongPress == null) { @@ -176,22 +179,22 @@ public class ChatBaseCell extends BaseCell { mediaBackgroundDrawable = getResources().getDrawable(R.drawable.phototime); timePaintIn = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - timePaintIn.setTextSize(Utilities.dp(12)); + timePaintIn.setTextSize(AndroidUtilities.dp(12)); timePaintIn.setColor(0xffa1aab3); timePaintOut = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - timePaintOut.setTextSize(Utilities.dp(12)); + timePaintOut.setTextSize(AndroidUtilities.dp(12)); timePaintOut.setColor(0xff70b15c); timeMediaPaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - timeMediaPaint.setTextSize(Utilities.dp(12)); + timeMediaPaint.setTextSize(AndroidUtilities.dp(12)); timeMediaPaint.setColor(0xffffffff); namePaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - namePaint.setTextSize(Utilities.dp(15)); + namePaint.setTextSize(AndroidUtilities.dp(15)); forwardNamePaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - forwardNamePaint.setTextSize(Utilities.dp(14)); + forwardNamePaint.setTextSize(AndroidUtilities.dp(14)); } } @@ -211,6 +214,10 @@ public class ChatBaseCell extends BaseCell { if (currentMessageObject == null || currentUser == null) { return false; } + if (last_send_state != currentMessageObject.messageOwner.send_state) { + return true; + } + TLRPC.User newUser = MessagesController.getInstance().users.get(currentMessageObject.messageOwner.from_id); TLRPC.FileLocation newPhoto = null; @@ -241,6 +248,7 @@ public class ChatBaseCell extends BaseCell { public void setMessageObject(MessageObject messageObject) { currentMessageObject = messageObject; + last_send_state = messageObject.messageOwner.send_state; isPressed = false; isCheckPressed = true; isAvatarVisible = false; @@ -286,11 +294,11 @@ public class ChatBaseCell extends BaseCell { currentNameString = Utilities.formatName(currentUser.first_name, currentUser.last_name); nameWidth = getMaxNameWidth(); - CharSequence nameStringFinal = TextUtils.ellipsize(currentNameString.replace("\n", " "), namePaint, nameWidth - Utilities.dp(12), TextUtils.TruncateAt.END); + CharSequence nameStringFinal = TextUtils.ellipsize(currentNameString.replace("\n", " "), namePaint, nameWidth - AndroidUtilities.dp(12), TextUtils.TruncateAt.END); nameLayout = new StaticLayout(nameStringFinal, namePaint, nameWidth, Layout.Alignment.ALIGN_NORMAL, 1.0f, 0.0f, false); if (nameLayout.getLineCount() > 0) { nameWidth = (int)Math.ceil(nameLayout.getLineWidth(0)); - namesOffset += Utilities.dp(18); + namesOffset += AndroidUtilities.dp(18); nameOffsetX = nameLayout.getLineLeft(0); } else { nameWidth = 0; @@ -308,12 +316,12 @@ public class ChatBaseCell extends BaseCell { forwardedNameWidth = getMaxNameWidth(); - CharSequence str = TextUtils.ellipsize(currentForwardNameString.replace("\n", " "), forwardNamePaint, forwardedNameWidth - Utilities.dp(40), TextUtils.TruncateAt.END); + CharSequence str = TextUtils.ellipsize(currentForwardNameString.replace("\n", " "), forwardNamePaint, forwardedNameWidth - AndroidUtilities.dp(40), TextUtils.TruncateAt.END); str = Html.fromHtml(String.format("%s
%s %s", LocaleController.getString("ForwardedMessage", R.string.ForwardedMessage), LocaleController.getString("From", R.string.From), str)); forwardedNameLayout = new StaticLayout(str, forwardNamePaint, forwardedNameWidth, Layout.Alignment.ALIGN_NORMAL, 1.0f, 0.0f, false); if (forwardedNameLayout.getLineCount() > 1) { forwardedNameWidth = Math.max((int) Math.ceil(forwardedNameLayout.getLineWidth(0)), (int) Math.ceil(forwardedNameLayout.getLineWidth(1))); - namesOffset += Utilities.dp(36); + namesOffset += AndroidUtilities.dp(36); forwardNameOffsetX = Math.min(forwardedNameLayout.getLineLeft(0), forwardedNameLayout.getLineLeft(1)); } else { forwardedNameWidth = 0; @@ -337,7 +345,7 @@ public class ChatBaseCell extends BaseCell { } protected int getMaxNameWidth() { - return backgroundWidth - Utilities.dp(8); + return backgroundWidth - AndroidUtilities.dp(8); } protected void startCheckLongPress() { @@ -372,7 +380,7 @@ public class ChatBaseCell extends BaseCell { avatarPressed = true; result = true; } else if (drawForwardedName && forwardedNameLayout != null) { - if (x >= forwardNameX && x <= forwardNameX + forwardedNameWidth && y >= forwardNameY && y <= forwardNameY + Utilities.dp(32)) { + if (x >= forwardNameX && x <= forwardNameX + forwardedNameWidth && y >= forwardNameY && y <= forwardNameY + AndroidUtilities.dp(32)) { forwardNamePressed = true; result = true; } @@ -409,7 +417,7 @@ public class ChatBaseCell extends BaseCell { } else if (event.getAction() == MotionEvent.ACTION_CANCEL) { forwardNamePressed = false; } else if (event.getAction() == MotionEvent.ACTION_MOVE) { - if (!(x >= forwardNameX && x <= forwardNameX + forwardedNameWidth && y >= forwardNameY && y <= forwardNameY + Utilities.dp(32))) { + if (!(x >= forwardNameX && x <= forwardNameX + forwardedNameWidth && y >= forwardNameY && y <= forwardNameY + AndroidUtilities.dp(32))) { forwardNamePressed = false; } } @@ -433,23 +441,23 @@ public class ChatBaseCell extends BaseCell { timeLayout = new StaticLayout(currentTimeString, currentTimePaint, timeWidth, Layout.Alignment.ALIGN_NORMAL, 1.0f, 0.0f, false); if (!media) { if (!currentMessageObject.isOut()) { - timeX = backgroundWidth - Utilities.dp(9) - timeWidth + (isChat ? Utilities.dp(52) : 0); + timeX = backgroundWidth - AndroidUtilities.dp(9) - timeWidth + (isChat ? AndroidUtilities.dp(52) : 0); } else { - timeX = layoutWidth - timeWidth - Utilities.dpf(38.5f); + timeX = layoutWidth - timeWidth - AndroidUtilities.dpf(38.5f); } } else { if (!currentMessageObject.isOut()) { - timeX = backgroundWidth - Utilities.dp(4) - timeWidth + (isChat ? Utilities.dp(52) : 0); + timeX = backgroundWidth - AndroidUtilities.dp(4) - timeWidth + (isChat ? AndroidUtilities.dp(52) : 0); } else { - timeX = layoutWidth - timeWidth - Utilities.dpf(42.0f); + timeX = layoutWidth - timeWidth - AndroidUtilities.dpf(42.0f); } } if (isAvatarVisible) { - avatarImage.imageX = Utilities.dp(6); - avatarImage.imageY = layoutHeight - Utilities.dp(45); - avatarImage.imageW = Utilities.dp(42); - avatarImage.imageH = Utilities.dp(42); + avatarImage.imageX = AndroidUtilities.dp(6); + avatarImage.imageY = layoutHeight - AndroidUtilities.dp(45); + avatarImage.imageW = AndroidUtilities.dp(42); + avatarImage.imageH = AndroidUtilities.dp(42); } wasLayout = true; @@ -473,7 +481,7 @@ public class ChatBaseCell extends BaseCell { } if (isAvatarVisible) { - avatarImage.draw(canvas, Utilities.dp(6), layoutHeight - Utilities.dp(45), Utilities.dp(42), Utilities.dp(42)); + avatarImage.draw(canvas, AndroidUtilities.dp(6), layoutHeight - AndroidUtilities.dp(45), AndroidUtilities.dp(42), AndroidUtilities.dp(42)); } Drawable currentBackgroundDrawable = null; @@ -491,7 +499,7 @@ public class ChatBaseCell extends BaseCell { currentBackgroundDrawable = backgroundMediaDrawableOut; } } - setDrawableBounds(currentBackgroundDrawable, layoutWidth - backgroundWidth - (!media ? 0 : Utilities.dp(9)), Utilities.dp(1), backgroundWidth, layoutHeight - Utilities.dp(2)); + setDrawableBounds(currentBackgroundDrawable, layoutWidth - backgroundWidth - (!media ? 0 : AndroidUtilities.dp(9)), AndroidUtilities.dp(1), backgroundWidth, layoutHeight - AndroidUtilities.dp(2)); } else { if (isPressed() && isCheckPressed || !isCheckPressed && isPressed) { if (!media) { @@ -507,9 +515,9 @@ public class ChatBaseCell extends BaseCell { } } if (isChat) { - setDrawableBounds(currentBackgroundDrawable, Utilities.dp(52 + (!media ? 0 : 9)), Utilities.dp(1), backgroundWidth, layoutHeight - Utilities.dp(2)); + setDrawableBounds(currentBackgroundDrawable, AndroidUtilities.dp(52 + (!media ? 0 : 9)), AndroidUtilities.dp(1), backgroundWidth, layoutHeight - AndroidUtilities.dp(2)); } else { - setDrawableBounds(currentBackgroundDrawable, (!media ? 0 : Utilities.dp(9)), Utilities.dp(1), backgroundWidth, layoutHeight - Utilities.dp(2)); + setDrawableBounds(currentBackgroundDrawable, (!media ? 0 : AndroidUtilities.dp(9)), AndroidUtilities.dp(1), backgroundWidth, layoutHeight - AndroidUtilities.dp(2)); } } currentBackgroundDrawable.draw(canvas); @@ -518,7 +526,7 @@ public class ChatBaseCell extends BaseCell { if (drawName && nameLayout != null) { canvas.save(); - canvas.translate(currentBackgroundDrawable.getBounds().left + Utilities.dp(19) - nameOffsetX, Utilities.dp(10)); + canvas.translate(currentBackgroundDrawable.getBounds().left + AndroidUtilities.dp(19) - nameOffsetX, AndroidUtilities.dp(10)); namePaint.setColor(Utilities.getColorForId(currentUser.id)); nameLayout.draw(canvas); canvas.restore(); @@ -528,12 +536,12 @@ public class ChatBaseCell extends BaseCell { canvas.save(); if (currentMessageObject.isOut()) { forwardNamePaint.setColor(0xff4a923c); - forwardNameX = currentBackgroundDrawable.getBounds().left + Utilities.dp(10); - forwardNameY = Utilities.dp(10 + (drawName ? 18 : 0)); + forwardNameX = currentBackgroundDrawable.getBounds().left + AndroidUtilities.dp(10); + forwardNameY = AndroidUtilities.dp(10 + (drawName ? 18 : 0)); } else { forwardNamePaint.setColor(0xff006fc8); - forwardNameX = currentBackgroundDrawable.getBounds().left + Utilities.dp(19); - forwardNameY = Utilities.dp(10 + (drawName ? 18 : 0)); + forwardNameX = currentBackgroundDrawable.getBounds().left + AndroidUtilities.dp(19); + forwardNameY = AndroidUtilities.dp(10 + (drawName ? 18 : 0)); } canvas.translate(forwardNameX - forwardNameOffsetX, forwardNameY); forwardedNameLayout.draw(canvas); @@ -542,16 +550,16 @@ public class ChatBaseCell extends BaseCell { if (drawTime) { if (media) { - setDrawableBounds(mediaBackgroundDrawable, timeX - Utilities.dp(3), layoutHeight - Utilities.dpf(27.5f), timeWidth + Utilities.dp(6 + (currentMessageObject.isOut() ? 20 : 0)), Utilities.dpf(16.5f)); + setDrawableBounds(mediaBackgroundDrawable, timeX - AndroidUtilities.dp(3), layoutHeight - AndroidUtilities.dpf(27.5f), timeWidth + AndroidUtilities.dp(6 + (currentMessageObject.isOut() ? 20 : 0)), AndroidUtilities.dpf(16.5f)); mediaBackgroundDrawable.draw(canvas); canvas.save(); - canvas.translate(timeX, layoutHeight - Utilities.dpf(12.0f) - timeLayout.getHeight()); + canvas.translate(timeX, layoutHeight - AndroidUtilities.dpf(12.0f) - timeLayout.getHeight()); timeLayout.draw(canvas); canvas.restore(); } else { canvas.save(); - canvas.translate(timeX, layoutHeight - Utilities.dpf(6.5f) - timeLayout.getHeight()); + canvas.translate(timeX, layoutHeight - AndroidUtilities.dpf(6.5f) - timeLayout.getHeight()); timeLayout.draw(canvas); canvas.restore(); } @@ -586,45 +594,45 @@ public class ChatBaseCell extends BaseCell { if (drawClock) { if (!media) { - setDrawableBounds(clockDrawable, layoutWidth - Utilities.dpf(18.5f) - clockDrawable.getIntrinsicWidth(), layoutHeight - Utilities.dpf(8.5f) - clockDrawable.getIntrinsicHeight()); + setDrawableBounds(clockDrawable, layoutWidth - AndroidUtilities.dpf(18.5f) - clockDrawable.getIntrinsicWidth(), layoutHeight - AndroidUtilities.dpf(8.5f) - clockDrawable.getIntrinsicHeight()); clockDrawable.draw(canvas); } else { - setDrawableBounds(clockMediaDrawable, layoutWidth - Utilities.dpf(22.0f) - clockMediaDrawable.getIntrinsicWidth(), layoutHeight - Utilities.dpf(13.0f) - clockMediaDrawable.getIntrinsicHeight()); + setDrawableBounds(clockMediaDrawable, layoutWidth - AndroidUtilities.dpf(22.0f) - clockMediaDrawable.getIntrinsicWidth(), layoutHeight - AndroidUtilities.dpf(13.0f) - clockMediaDrawable.getIntrinsicHeight()); clockMediaDrawable.draw(canvas); } } if (drawCheck2) { if (!media) { if (drawCheck1) { - setDrawableBounds(checkDrawable, layoutWidth - Utilities.dpf(22.5f) - checkDrawable.getIntrinsicWidth(), layoutHeight - Utilities.dpf(8.5f) - checkDrawable.getIntrinsicHeight()); + setDrawableBounds(checkDrawable, layoutWidth - AndroidUtilities.dpf(22.5f) - checkDrawable.getIntrinsicWidth(), layoutHeight - AndroidUtilities.dpf(8.5f) - checkDrawable.getIntrinsicHeight()); } else { - setDrawableBounds(checkDrawable, layoutWidth - Utilities.dpf(18.5f) - checkDrawable.getIntrinsicWidth(), layoutHeight - Utilities.dpf(8.5f) - checkDrawable.getIntrinsicHeight()); + setDrawableBounds(checkDrawable, layoutWidth - AndroidUtilities.dpf(18.5f) - checkDrawable.getIntrinsicWidth(), layoutHeight - AndroidUtilities.dpf(8.5f) - checkDrawable.getIntrinsicHeight()); } checkDrawable.draw(canvas); } else { if (drawCheck1) { - setDrawableBounds(checkMediaDrawable, layoutWidth - Utilities.dpf(26.0f) - checkMediaDrawable.getIntrinsicWidth(), layoutHeight - Utilities.dpf(13.0f) - checkMediaDrawable.getIntrinsicHeight()); + setDrawableBounds(checkMediaDrawable, layoutWidth - AndroidUtilities.dpf(26.0f) - checkMediaDrawable.getIntrinsicWidth(), layoutHeight - AndroidUtilities.dpf(13.0f) - checkMediaDrawable.getIntrinsicHeight()); } else { - setDrawableBounds(checkMediaDrawable, layoutWidth - Utilities.dpf(22.0f) - checkMediaDrawable.getIntrinsicWidth(), layoutHeight - Utilities.dpf(13.0f) - checkMediaDrawable.getIntrinsicHeight()); + setDrawableBounds(checkMediaDrawable, layoutWidth - AndroidUtilities.dpf(22.0f) - checkMediaDrawable.getIntrinsicWidth(), layoutHeight - AndroidUtilities.dpf(13.0f) - checkMediaDrawable.getIntrinsicHeight()); } checkMediaDrawable.draw(canvas); } } if (drawCheck1) { if (!media) { - setDrawableBounds(halfCheckDrawable, layoutWidth - Utilities.dp(18) - halfCheckDrawable.getIntrinsicWidth(), layoutHeight - Utilities.dpf(8.5f) - halfCheckDrawable.getIntrinsicHeight()); + setDrawableBounds(halfCheckDrawable, layoutWidth - AndroidUtilities.dp(18) - halfCheckDrawable.getIntrinsicWidth(), layoutHeight - AndroidUtilities.dpf(8.5f) - halfCheckDrawable.getIntrinsicHeight()); halfCheckDrawable.draw(canvas); } else { - setDrawableBounds(halfCheckMediaDrawable, layoutWidth - Utilities.dpf(20.5f) - halfCheckMediaDrawable.getIntrinsicWidth(), layoutHeight - Utilities.dpf(13.0f) - halfCheckMediaDrawable.getIntrinsicHeight()); + setDrawableBounds(halfCheckMediaDrawable, layoutWidth - AndroidUtilities.dpf(20.5f) - halfCheckMediaDrawable.getIntrinsicWidth(), layoutHeight - AndroidUtilities.dpf(13.0f) - halfCheckMediaDrawable.getIntrinsicHeight()); halfCheckMediaDrawable.draw(canvas); } } if (drawError) { if (!media) { - setDrawableBounds(errorDrawable, layoutWidth - Utilities.dp(18) - errorDrawable.getIntrinsicWidth(), layoutHeight - Utilities.dpf(6.5f) - errorDrawable.getIntrinsicHeight()); + setDrawableBounds(errorDrawable, layoutWidth - AndroidUtilities.dp(18) - errorDrawable.getIntrinsicWidth(), layoutHeight - AndroidUtilities.dpf(6.5f) - errorDrawable.getIntrinsicHeight()); errorDrawable.draw(canvas); } else { - setDrawableBounds(errorDrawable, layoutWidth - Utilities.dpf(20.5f) - errorDrawable.getIntrinsicWidth(), layoutHeight - Utilities.dpf(12.5f) - errorDrawable.getIntrinsicHeight()); + setDrawableBounds(errorDrawable, layoutWidth - AndroidUtilities.dpf(20.5f) - errorDrawable.getIntrinsicWidth(), layoutHeight - AndroidUtilities.dpf(12.5f) - errorDrawable.getIntrinsicHeight()); errorDrawable.draw(canvas); } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatMediaCell.java b/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatMediaCell.java index 708c6f09d..a66e30850 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatMediaCell.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatMediaCell.java @@ -18,12 +18,12 @@ import android.text.StaticLayout; import android.text.TextPaint; import android.view.MotionEvent; import android.view.SoundEffectConstants; -import android.view.View; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.ConnectionsManager; import org.telegram.messenger.FileLoader; -import org.telegram.messenger.MediaController; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MediaController; +import org.telegram.android.MessagesController; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; import org.telegram.objects.MessageObject; @@ -34,7 +34,6 @@ import org.telegram.ui.Views.ImageReceiver; import org.telegram.ui.Views.ProgressView; import java.io.File; -import java.lang.ref.WeakReference; import java.util.Locale; public class ChatMediaCell extends ChatBaseCell implements MediaController.FileDownloadProgressListener { @@ -96,7 +95,7 @@ public class ChatMediaCell extends ChatBaseCell implements MediaController.FileD infoPaint = new TextPaint(Paint.ANTI_ALIAS_FLAG); infoPaint.setColor(0xffffffff); - infoPaint.setTextSize(Utilities.dp(12)); + infoPaint.setTextSize(AndroidUtilities.dp(12)); } TAG = MediaController.getInstance().generateObserverTag(); @@ -136,7 +135,7 @@ public class ChatMediaCell extends ChatBaseCell implements MediaController.FileD float y = event.getY(); boolean result = false; - int side = Utilities.dp(44); + int side = AndroidUtilities.dp(44); if (event.getAction() == MotionEvent.ACTION_DOWN) { if (delegate == null || delegate.canPerformActions()) { if (buttonState != -1 && x >= buttonX && x <= buttonX + side && y >= buttonY && y <= buttonY + side) { @@ -285,7 +284,7 @@ public class ChatMediaCell extends ChatBaseCell implements MediaController.FileD } double lat = object.messageOwner.media.geo.lat; double lon = object.messageOwner.media.geo._long; - String url = String.format(Locale.US, "https://maps.googleapis.com/maps/api/staticmap?center=%f,%f&zoom=13&size=100x100&maptype=roadmap&scale=%d&markers=color:red|size:big|%f,%f&sensor=false", lat, lon, Math.min(2, (int)Math.ceil(Utilities.density)), lat, lon); + String url = String.format(Locale.US, "https://maps.googleapis.com/maps/api/staticmap?center=%f,%f&zoom=13&size=100x100&maptype=roadmap&scale=%d&markers=color:red|size:big|%f,%f&sensor=false", lat, lon, Math.min(2, (int)Math.ceil(AndroidUtilities.density)), lat, lon); if (!url.equals(currentUrl)) { return true; } @@ -293,7 +292,7 @@ public class ChatMediaCell extends ChatBaseCell implements MediaController.FileD return true; } else if (currentPhotoObject != null && photoNotSet) { String fileName = MessageObject.getAttachFileName(currentPhotoObject.photoOwner); - File cacheFile = new File(Utilities.getCacheDir(), fileName); + File cacheFile = new File(AndroidUtilities.getCacheDir(), fileName); if (cacheFile.exists()) { return true; } @@ -330,7 +329,7 @@ public class ChatMediaCell extends ChatBaseCell implements MediaController.FileD String str = String.format("%d:%02d, %s", minutes, seconds, Utilities.formatFileSize(messageObject.messageOwner.media.video.size)); if (currentInfoString == null || !currentInfoString.equals(str)) { currentInfoString = str; - infoOffset = videoIconDrawable.getIntrinsicWidth() + Utilities.dp(4); + infoOffset = videoIconDrawable.getIntrinsicWidth() + AndroidUtilities.dp(4); infoWidth = (int) Math.ceil(infoPaint.measureText(currentInfoString)); infoLayout = new StaticLayout(currentInfoString, infoPaint, infoWidth, Layout.Alignment.ALIGN_NORMAL, 1.0f, 0.0f, false); } @@ -340,17 +339,17 @@ public class ChatMediaCell extends ChatBaseCell implements MediaController.FileD } if (messageObject.type == 4) { - photoWidth = Utilities.dp(100); - photoHeight = Utilities.dp(100); - backgroundWidth = photoWidth + Utilities.dp(12); + photoWidth = AndroidUtilities.dp(100); + photoHeight = AndroidUtilities.dp(100); + backgroundWidth = photoWidth + AndroidUtilities.dp(12); double lat = messageObject.messageOwner.media.geo.lat; double lon = messageObject.messageOwner.media.geo._long; - currentUrl = String.format(Locale.US, "https://maps.googleapis.com/maps/api/staticmap?center=%f,%f&zoom=13&size=100x100&maptype=roadmap&scale=%d&markers=color:red|size:big|%f,%f&sensor=false", lat, lon, Math.min(2, (int)Math.ceil(Utilities.density)), lat, lon); + currentUrl = String.format(Locale.US, "https://maps.googleapis.com/maps/api/staticmap?center=%f,%f&zoom=13&size=100x100&maptype=roadmap&scale=%d&markers=color:red|size:big|%f,%f&sensor=false", lat, lon, Math.min(2, (int)Math.ceil(AndroidUtilities.density)), lat, lon); photoImage.setImage(currentUrl, null, messageObject.isOut() ? placeholderOutDrawable : placeholderInDrawable); } else { - photoWidth = (int) (Math.min(Utilities.displaySize.x, Utilities.displaySize.y) * 0.7f); - photoHeight = photoWidth + Utilities.dp(100); + photoWidth = (int) (Math.min(AndroidUtilities.displaySize.x, AndroidUtilities.displaySize.y) * 0.7f); + photoHeight = photoWidth + AndroidUtilities.dp(100); if (photoWidth > 800) { photoWidth = 800; @@ -367,35 +366,35 @@ public class ChatMediaCell extends ChatBaseCell implements MediaController.FileD int h = (int) (currentPhotoObject.photoOwner.h / scale); if (w == 0) { if (messageObject.type == 3) { - w = infoWidth + infoOffset + Utilities.dp(16); + w = infoWidth + infoOffset + AndroidUtilities.dp(16); } else { - w = Utilities.dp(100); + w = AndroidUtilities.dp(100); } } if (h == 0) { - h = Utilities.dp(100); + h = AndroidUtilities.dp(100); } if (h > photoHeight) { float scale2 = h; h = photoHeight; scale2 /= h; w = (int) (w / scale2); - } else if (h < Utilities.dp(120)) { - h = Utilities.dp(120); + } else if (h < AndroidUtilities.dp(120)) { + h = AndroidUtilities.dp(120); float hScale = (float) currentPhotoObject.photoOwner.h / h; if (currentPhotoObject.photoOwner.w / hScale < photoWidth) { w = (int) (currentPhotoObject.photoOwner.w / hScale); } } - int timeWidthTotal = timeWidth + Utilities.dp(14 + (currentMessageObject.isOut() ? 20 : 0)); + int timeWidthTotal = timeWidth + AndroidUtilities.dp(14 + (currentMessageObject.isOut() ? 20 : 0)); if (w < timeWidthTotal) { w = timeWidthTotal; } photoWidth = w; photoHeight = h; - backgroundWidth = w + Utilities.dp(12); - currentPhotoFilter = String.format(Locale.US, "%d_%d", (int) (w / Utilities.density), (int) (h / Utilities.density)); + backgroundWidth = w + AndroidUtilities.dp(12); + currentPhotoFilter = String.format(Locale.US, "%d_%d", (int) (w / AndroidUtilities.density), (int) (h / AndroidUtilities.density)); if (currentPhotoObject.image != null) { photoImage.setImageBitmap(currentPhotoObject.image); @@ -403,7 +402,7 @@ public class ChatMediaCell extends ChatBaseCell implements MediaController.FileD boolean photoExist = true; String fileName = MessageObject.getAttachFileName(currentPhotoObject.photoOwner); if (messageObject.type == 1) { - File cacheFile = new File(Utilities.getCacheDir(), fileName); + File cacheFile = new File(AndroidUtilities.getCacheDir(), fileName); if (!cacheFile.exists()) { photoExist = false; } else { @@ -447,7 +446,7 @@ public class ChatMediaCell extends ChatBaseCell implements MediaController.FileD return; } fileName = MessageObject.getAttachFileName(currentPhotoObject.photoOwner); - cacheFile = new File(Utilities.getCacheDir(), fileName); + cacheFile = new File(AndroidUtilities.getCacheDir(), fileName); } else if (currentMessageObject.type == 8 || currentMessageObject.type == 3) { if (currentMessageObject.messageOwner.attachPath != null && currentMessageObject.messageOwner.attachPath.length() != 0) { File f = new File(currentMessageObject.messageOwner.attachPath); @@ -458,7 +457,7 @@ public class ChatMediaCell extends ChatBaseCell implements MediaController.FileD } if (fileName == null) { fileName = currentMessageObject.getFileName(); - cacheFile = new File(Utilities.getCacheDir(), fileName); + cacheFile = new File(AndroidUtilities.getCacheDir(), fileName); } } if (fileName == null) { @@ -525,7 +524,7 @@ public class ChatMediaCell extends ChatBaseCell implements MediaController.FileD @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { - setMeasuredDimension(MeasureSpec.getSize(widthMeasureSpec), photoHeight + Utilities.dp(14)); + setMeasuredDimension(MeasureSpec.getSize(widthMeasureSpec), photoHeight + AndroidUtilities.dp(14)); } @Override @@ -533,23 +532,23 @@ public class ChatMediaCell extends ChatBaseCell implements MediaController.FileD super.onLayout(changed, left, top, right, bottom); if (currentMessageObject.isOut()) { - photoImage.imageX = layoutWidth - backgroundWidth - Utilities.dp(3); + photoImage.imageX = layoutWidth - backgroundWidth - AndroidUtilities.dp(3); } else { if (isChat) { - photoImage.imageX = Utilities.dp(67); + photoImage.imageX = AndroidUtilities.dp(67); } else { - photoImage.imageX = Utilities.dp(15); + photoImage.imageX = AndroidUtilities.dp(15); } } - photoImage.imageY = Utilities.dp(7); + photoImage.imageY = AndroidUtilities.dp(7); photoImage.imageW = photoWidth; photoImage.imageH = photoHeight; - progressView.width = timeX - photoImage.imageX - Utilities.dpf(23.0f); - progressView.height = Utilities.dp(3); - progressView.progressHeight = Utilities.dp(3); + progressView.width = timeX - photoImage.imageX - AndroidUtilities.dpf(23.0f); + progressView.height = AndroidUtilities.dp(3); + progressView.progressHeight = AndroidUtilities.dp(3); - int size = Utilities.dp(44); + int size = AndroidUtilities.dp(44); buttonX = (int)(photoImage.imageX + (photoWidth - size) / 2.0f); buttonY = (int)(photoImage.imageY + (photoHeight - size) / 2.0f); } @@ -568,11 +567,11 @@ public class ChatMediaCell extends ChatBaseCell implements MediaController.FileD } if (progressVisible) { - setDrawableBounds(mediaBackgroundDrawable, photoImage.imageX + Utilities.dp(4), layoutHeight - Utilities.dpf(27.5f), progressView.width + Utilities.dp(12), Utilities.dpf(16.5f)); + setDrawableBounds(mediaBackgroundDrawable, photoImage.imageX + AndroidUtilities.dp(4), layoutHeight - AndroidUtilities.dpf(27.5f), progressView.width + AndroidUtilities.dp(12), AndroidUtilities.dpf(16.5f)); mediaBackgroundDrawable.draw(canvas); canvas.save(); - canvas.translate(photoImage.imageX + Utilities.dp(10), layoutHeight - Utilities.dpf(21.0f)); + canvas.translate(photoImage.imageX + AndroidUtilities.dp(10), layoutHeight - AndroidUtilities.dpf(21.0f)); progressView.draw(canvas); canvas.restore(); } @@ -584,16 +583,16 @@ public class ChatMediaCell extends ChatBaseCell implements MediaController.FileD } if (infoLayout != null && (buttonState == 1 || buttonState == 0 || buttonState == 3)) { - setDrawableBounds(mediaBackgroundDrawable, photoImage.imageX + Utilities.dp(4), photoImage.imageY + Utilities.dp(4), infoWidth + Utilities.dp(8) + infoOffset, Utilities.dpf(16.5f)); + setDrawableBounds(mediaBackgroundDrawable, photoImage.imageX + AndroidUtilities.dp(4), photoImage.imageY + AndroidUtilities.dp(4), infoWidth + AndroidUtilities.dp(8) + infoOffset, AndroidUtilities.dpf(16.5f)); mediaBackgroundDrawable.draw(canvas); if (currentMessageObject.type == 3) { - setDrawableBounds(videoIconDrawable, photoImage.imageX + Utilities.dp(8), photoImage.imageY + Utilities.dpf(7.5f)); + setDrawableBounds(videoIconDrawable, photoImage.imageX + AndroidUtilities.dp(8), photoImage.imageY + AndroidUtilities.dpf(7.5f)); videoIconDrawable.draw(canvas); } canvas.save(); - canvas.translate(photoImage.imageX + Utilities.dp(8) + infoOffset, photoImage.imageY + Utilities.dpf(5.5f)); + canvas.translate(photoImage.imageX + AndroidUtilities.dp(8) + infoOffset, photoImage.imageY + AndroidUtilities.dpf(5.5f)); infoLayout.draw(canvas); canvas.restore(); } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatMessageCell.java b/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatMessageCell.java index 9396d1aba..77786a70a 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatMessageCell.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatMessageCell.java @@ -14,8 +14,8 @@ import android.text.Spannable; import android.text.style.ClickableSpan; import android.view.MotionEvent; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.FileLog; -import org.telegram.messenger.Utilities; import org.telegram.objects.MessageObject; public class ChatMessageCell extends ChatBaseCell { @@ -132,10 +132,10 @@ public class ChatMessageCell extends ChatBaseCell { pressedLink = null; int maxWidth; if (isChat && !messageObject.isOut()) { - maxWidth = Utilities.displaySize.x - Utilities.dp(122); + maxWidth = AndroidUtilities.displaySize.x - AndroidUtilities.dp(122); drawName = true; } else { - maxWidth = Utilities.displaySize.x - Utilities.dp(80); + maxWidth = AndroidUtilities.displaySize.x - AndroidUtilities.dp(80); drawName = false; } @@ -144,25 +144,25 @@ public class ChatMessageCell extends ChatBaseCell { super.setMessageObject(messageObject); backgroundWidth = messageObject.textWidth; - totalHeight = messageObject.textHeight + Utilities.dpf(19.5f) + namesOffset; + totalHeight = messageObject.textHeight + AndroidUtilities.dpf(19.5f) + namesOffset; int maxChildWidth = Math.max(backgroundWidth, nameWidth); maxChildWidth = Math.max(maxChildWidth, forwardedNameWidth); - int timeMore = timeWidth + Utilities.dp(6); + int timeMore = timeWidth + AndroidUtilities.dp(6); if (messageObject.isOut()) { - timeMore += Utilities.dpf(20.5f); + timeMore += AndroidUtilities.dpf(20.5f); } if (maxWidth - messageObject.lastLineWidth < timeMore) { - totalHeight += Utilities.dp(14); - backgroundWidth = Math.max(maxChildWidth, messageObject.lastLineWidth) + Utilities.dp(29); + totalHeight += AndroidUtilities.dp(14); + backgroundWidth = Math.max(maxChildWidth, messageObject.lastLineWidth) + AndroidUtilities.dp(29); } else { int diff = maxChildWidth - messageObject.lastLineWidth; if (diff >= 0 && diff <= timeMore) { - backgroundWidth = maxChildWidth + timeMore - diff + Utilities.dp(29); + backgroundWidth = maxChildWidth + timeMore - diff + AndroidUtilities.dp(29); } else { - backgroundWidth = Math.max(maxChildWidth, messageObject.lastLineWidth + timeMore) + Utilities.dp(29); + backgroundWidth = Math.max(maxChildWidth, messageObject.lastLineWidth + timeMore) + AndroidUtilities.dp(29); } } } @@ -178,11 +178,11 @@ public class ChatMessageCell extends ChatBaseCell { super.onLayout(changed, left, top, right, bottom); if (currentMessageObject.isOut()) { - textX = layoutWidth - backgroundWidth + Utilities.dp(10); - textY = Utilities.dp(10) + namesOffset; + textX = layoutWidth - backgroundWidth + AndroidUtilities.dp(10); + textY = AndroidUtilities.dp(10) + namesOffset; } else { - textX = Utilities.dp(19) + (isChat ? Utilities.dp(52) : 0); - textY = Utilities.dp(10) + namesOffset; + textX = AndroidUtilities.dp(19) + (isChat ? AndroidUtilities.dp(52) : 0); + textY = AndroidUtilities.dp(10) + namesOffset; } } @@ -194,11 +194,11 @@ public class ChatMessageCell extends ChatBaseCell { } if (currentMessageObject.isOut()) { - textX = layoutWidth - backgroundWidth + Utilities.dp(10); - textY = Utilities.dp(10) + namesOffset; + textX = layoutWidth - backgroundWidth + AndroidUtilities.dp(10); + textY = AndroidUtilities.dp(10) + namesOffset; } else { - textX = Utilities.dp(19) + (isChat ? Utilities.dp(52) : 0); - textY = Utilities.dp(10) + namesOffset; + textX = AndroidUtilities.dp(19) + (isChat ? AndroidUtilities.dp(52) : 0); + textY = AndroidUtilities.dp(10) + namesOffset; } for (int a = firstVisibleBlockNum; a <= lastVisibleBlockNum; a++) { diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatOrUserCell.java b/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatOrUserCell.java index 3a6563775..8aa33a10d 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatOrUserCell.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Cells/ChatOrUserCell.java @@ -17,11 +17,12 @@ import android.text.StaticLayout; import android.text.TextPaint; import android.text.TextUtils; +import org.telegram.android.AndroidUtilities; import org.telegram.PhoneFormat.PhoneFormat; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLRPC; import org.telegram.messenger.ConnectionsManager; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.R; import org.telegram.messenger.UserConfig; import org.telegram.messenger.Utilities; @@ -61,25 +62,25 @@ public class ChatOrUserCell extends BaseCell { private void init() { if (namePaint == null) { namePaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - namePaint.setTextSize(Utilities.dp(18)); + namePaint.setTextSize(AndroidUtilities.dp(18)); namePaint.setColor(0xff222222); } if (nameEncryptedPaint == null) { nameEncryptedPaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - nameEncryptedPaint.setTextSize(Utilities.dp(18)); + nameEncryptedPaint.setTextSize(AndroidUtilities.dp(18)); nameEncryptedPaint.setColor(0xff00a60e); } if (onlinePaint == null) { onlinePaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - onlinePaint.setTextSize(Utilities.dp(15)); + onlinePaint.setTextSize(AndroidUtilities.dp(15)); onlinePaint.setColor(0xff316f9f); } if (offlinePaint == null) { offlinePaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - offlinePaint.setTextSize(Utilities.dp(15)); + offlinePaint.setTextSize(AndroidUtilities.dp(15)); offlinePaint.setColor(0xff999999); } @@ -122,7 +123,7 @@ public class ChatOrUserCell extends BaseCell { @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { - setMeasuredDimension(MeasureSpec.getSize(widthMeasureSpec), Utilities.dp(64)); + setMeasuredDimension(MeasureSpec.getSize(widthMeasureSpec), AndroidUtilities.dp(64)); } @Override @@ -243,14 +244,14 @@ public class ChatOrUserCell extends BaseCell { canvas.restore(); } - avatarImage.draw(canvas, cellLayout.avatarLeft, cellLayout.avatarTop, Utilities.dp(50), Utilities.dp(50)); + avatarImage.draw(canvas, cellLayout.avatarLeft, cellLayout.avatarTop, AndroidUtilities.dp(50), AndroidUtilities.dp(50)); if (useSeparator) { int h = getMeasuredHeight(); if (!usePadding) { canvas.drawLine(0, h - 1, getMeasuredWidth(), h, linePaint); } else { - canvas.drawLine(Utilities.dp(11), h - 1, getMeasuredWidth() - Utilities.dp(11), h, linePaint); + canvas.drawLine(AndroidUtilities.dp(11), h - 1, getMeasuredWidth() - AndroidUtilities.dp(11), h, linePaint); } } } @@ -262,14 +263,14 @@ public class ChatOrUserCell extends BaseCell { private StaticLayout nameLayout; private boolean drawNameLock; private int nameLockLeft; - private int nameLockTop = Utilities.dp(15); + private int nameLockTop = AndroidUtilities.dp(15); private int onlineLeft; - private int onlineTop = Utilities.dp(36); + private int onlineTop = AndroidUtilities.dp(36); private int onlineWidth; private StaticLayout onlineLayout; - private int avatarTop = Utilities.dp(7); + private int avatarTop = AndroidUtilities.dp(7); private int avatarLeft; public void build(int width, int height) { @@ -279,18 +280,18 @@ public class ChatOrUserCell extends BaseCell { if (encryptedChat != null) { drawNameLock = true; if (!LocaleController.isRTL) { - nameLockLeft = Utilities.dp(61 + (usePadding ? 11 : 0)); - nameLeft = Utilities.dp(65 + (usePadding ? 11 : 0)) + lockDrawable.getIntrinsicWidth(); + nameLockLeft = AndroidUtilities.dp(61 + (usePadding ? 11 : 0)); + nameLeft = AndroidUtilities.dp(65 + (usePadding ? 11 : 0)) + lockDrawable.getIntrinsicWidth(); } else { - nameLockLeft = width - Utilities.dp(63 + (usePadding ? 11 : 0)) - lockDrawable.getIntrinsicWidth(); - nameLeft = usePadding ? Utilities.dp(11) : 0; + nameLockLeft = width - AndroidUtilities.dp(63 + (usePadding ? 11 : 0)) - lockDrawable.getIntrinsicWidth(); + nameLeft = usePadding ? AndroidUtilities.dp(11) : 0; } } else { drawNameLock = false; if (!LocaleController.isRTL) { - nameLeft = Utilities.dp(61 + (usePadding ? 11 : 0)); + nameLeft = AndroidUtilities.dp(61 + (usePadding ? 11 : 0)); } else { - nameLeft = usePadding ? Utilities.dp(11) : 0; + nameLeft = usePadding ? AndroidUtilities.dp(11) : 0; } } @@ -306,7 +307,7 @@ public class ChatOrUserCell extends BaseCell { nameString = nameString2.replace("\n", " "); } if (nameString.length() == 0) { - if (user.phone != null && user.phone.length() != 0) { + if (user != null && user.phone != null && user.phone.length() != 0) { nameString = PhoneFormat.getInstance().format("+" + user.phone); } else { nameString = LocaleController.getString("HiddenName", R.string.HiddenName); @@ -319,22 +320,22 @@ public class ChatOrUserCell extends BaseCell { } if (!LocaleController.isRTL) { - onlineWidth = nameWidth = width - nameLeft - Utilities.dp(3 + (usePadding ? 11 : 0)); + onlineWidth = nameWidth = width - nameLeft - AndroidUtilities.dp(3 + (usePadding ? 11 : 0)); } else { - onlineWidth = nameWidth = width - nameLeft - Utilities.dp(61 + (usePadding ? 11 : 0)); + onlineWidth = nameWidth = width - nameLeft - AndroidUtilities.dp(61 + (usePadding ? 11 : 0)); } if (drawNameLock) { - nameWidth -= Utilities.dp(6) + lockDrawable.getIntrinsicWidth(); + nameWidth -= AndroidUtilities.dp(6) + lockDrawable.getIntrinsicWidth(); } - CharSequence nameStringFinal = TextUtils.ellipsize(nameString, currentNamePaint, nameWidth - Utilities.dp(12), TextUtils.TruncateAt.END); + CharSequence nameStringFinal = TextUtils.ellipsize(nameString, currentNamePaint, nameWidth - AndroidUtilities.dp(12), TextUtils.TruncateAt.END); nameLayout = new StaticLayout(nameStringFinal, currentNamePaint, nameWidth, Layout.Alignment.ALIGN_NORMAL, 1.0f, 0.0f, false); if (chat == null) { if (!LocaleController.isRTL) { - onlineLeft = Utilities.dp(61 + (usePadding ? 11 : 0)); + onlineLeft = AndroidUtilities.dp(61 + (usePadding ? 11 : 0)); } else { - onlineLeft = usePadding ? Utilities.dp(11) : 0; + onlineLeft = usePadding ? AndroidUtilities.dp(11) : 0; } String onlineString = ""; @@ -350,23 +351,23 @@ public class ChatOrUserCell extends BaseCell { } } - CharSequence onlineStringFinal = TextUtils.ellipsize(onlineString, currentOnlinePaint, nameWidth - Utilities.dp(12), TextUtils.TruncateAt.END); + CharSequence onlineStringFinal = TextUtils.ellipsize(onlineString, currentOnlinePaint, nameWidth - AndroidUtilities.dp(12), TextUtils.TruncateAt.END); onlineLayout = new StaticLayout(onlineStringFinal, currentOnlinePaint, nameWidth, Layout.Alignment.ALIGN_NORMAL, 1.0f, 0.0f, false); - nameTop = Utilities.dp(12); + nameTop = AndroidUtilities.dp(12); } else { onlineLayout = null; - nameTop = Utilities.dp(22); + nameTop = AndroidUtilities.dp(22); } if (!LocaleController.isRTL) { - avatarLeft = usePadding ? Utilities.dp(11) : 0; + avatarLeft = usePadding ? AndroidUtilities.dp(11) : 0; } else { - avatarLeft = width - Utilities.dp(50 + (usePadding ? 11 : 0)); + avatarLeft = width - AndroidUtilities.dp(50 + (usePadding ? 11 : 0)); } avatarImage.imageX = avatarLeft; avatarImage.imageY = avatarTop; - avatarImage.imageW = Utilities.dp(50); - avatarImage.imageH = Utilities.dp(50); + avatarImage.imageW = AndroidUtilities.dp(50); + avatarImage.imageH = AndroidUtilities.dp(50); double widthpx = 0; float left = 0; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Cells/DialogCell.java b/TMessagesProj/src/main/java/org/telegram/ui/Cells/DialogCell.java index b7a742c9d..25109034d 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Cells/DialogCell.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Cells/DialogCell.java @@ -17,12 +17,13 @@ import android.text.StaticLayout; import android.text.TextPaint; import android.text.TextUtils; +import org.telegram.android.AndroidUtilities; import org.telegram.PhoneFormat.PhoneFormat; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLRPC; -import org.telegram.messenger.ContactsController; -import org.telegram.messenger.Emoji; -import org.telegram.messenger.MessagesController; +import org.telegram.android.ContactsController; +import org.telegram.android.Emoji; +import org.telegram.android.MessagesController; import org.telegram.messenger.R; import org.telegram.messenger.UserConfig; import org.telegram.messenger.Utilities; @@ -58,46 +59,46 @@ public class DialogCell extends BaseCell { private void init() { if (namePaint == null) { namePaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - namePaint.setTextSize(Utilities.dp(19)); + namePaint.setTextSize(AndroidUtilities.dp(19)); namePaint.setColor(0xff222222); - namePaint.setTypeface(Utilities.getTypeface("fonts/rmedium.ttf")); + namePaint.setTypeface(AndroidUtilities.getTypeface("fonts/rmedium.ttf")); } if (nameEncryptedPaint == null) { nameEncryptedPaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - nameEncryptedPaint.setTextSize(Utilities.dp(19)); + nameEncryptedPaint.setTextSize(AndroidUtilities.dp(19)); nameEncryptedPaint.setColor(0xff00a60e); - nameEncryptedPaint.setTypeface(Utilities.getTypeface("fonts/rmedium.ttf")); + nameEncryptedPaint.setTypeface(AndroidUtilities.getTypeface("fonts/rmedium.ttf")); } if (nameUnknownPaint == null) { nameUnknownPaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - nameUnknownPaint.setTextSize(Utilities.dp(19)); + nameUnknownPaint.setTextSize(AndroidUtilities.dp(19)); nameUnknownPaint.setColor(0xff316f9f); - nameUnknownPaint.setTypeface(Utilities.getTypeface("fonts/rmedium.ttf")); + nameUnknownPaint.setTypeface(AndroidUtilities.getTypeface("fonts/rmedium.ttf")); } if (messagePaint == null) { messagePaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - messagePaint.setTextSize(Utilities.dp(16)); + messagePaint.setTextSize(AndroidUtilities.dp(16)); messagePaint.setColor(0xff808080); } if (messagePrintingPaint == null) { messagePrintingPaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - messagePrintingPaint.setTextSize(Utilities.dp(16)); + messagePrintingPaint.setTextSize(AndroidUtilities.dp(16)); messagePrintingPaint.setColor(0xff316f9f); } if (timePaint == null) { timePaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - timePaint.setTextSize(Utilities.dp(14)); + timePaint.setTextSize(AndroidUtilities.dp(14)); timePaint.setColor(0xff9e9e9e); } if (countPaint == null) { countPaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); - countPaint.setTextSize(Utilities.dp(13)); + countPaint.setTextSize(AndroidUtilities.dp(13)); countPaint.setColor(0xffffffff); } @@ -159,7 +160,7 @@ public class DialogCell extends BaseCell { @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { - setMeasuredDimension(MeasureSpec.getSize(widthMeasureSpec), Utilities.dp(70)); + setMeasuredDimension(MeasureSpec.getSize(widthMeasureSpec), AndroidUtilities.dp(70)); } @Override @@ -309,20 +310,20 @@ public class DialogCell extends BaseCell { setDrawableBounds(errorDrawable, cellLayout.errorLeft, cellLayout.errorTop); errorDrawable.draw(canvas); } else if (cellLayout.drawCount) { - setDrawableBounds(countDrawable, cellLayout.countLeft - Utilities.dp(5), cellLayout.countTop, cellLayout.countWidth + Utilities.dp(10), countDrawable.getIntrinsicHeight()); + setDrawableBounds(countDrawable, cellLayout.countLeft - AndroidUtilities.dp(5), cellLayout.countTop, cellLayout.countWidth + AndroidUtilities.dp(10), countDrawable.getIntrinsicHeight()); countDrawable.draw(canvas); canvas.save(); - canvas.translate(cellLayout.countLeft, cellLayout.countTop + Utilities.dp(3)); + canvas.translate(cellLayout.countLeft, cellLayout.countTop + AndroidUtilities.dp(3)); cellLayout.countLayout.draw(canvas); canvas.restore(); } - avatarImage.draw(canvas, cellLayout.avatarLeft, cellLayout.avatarTop, Utilities.dp(54), Utilities.dp(54)); + avatarImage.draw(canvas, cellLayout.avatarLeft, cellLayout.avatarTop, AndroidUtilities.dp(54), AndroidUtilities.dp(54)); } private class DialogCellLayout { private int nameLeft; - private int nameTop = Utilities.dp(10); + private int nameTop = AndroidUtilities.dp(10); private int nameWidth; private StaticLayout nameLayout; private boolean drawNameLock; @@ -331,7 +332,7 @@ public class DialogCell extends BaseCell { private int nameLockTop; private int timeLeft; - private int timeTop = Utilities.dp(13); + private int timeTop = AndroidUtilities.dp(13); private int timeWidth; private StaticLayout timeLayout; @@ -339,25 +340,25 @@ public class DialogCell extends BaseCell { private boolean drawCheck2; private boolean drawClock; private int checkDrawLeft; - private int checkDrawTop = Utilities.dp(15); + private int checkDrawTop = AndroidUtilities.dp(15); private int halfCheckDrawLeft; - private int messageTop = Utilities.dp(40); + private int messageTop = AndroidUtilities.dp(40); private int messageLeft; private int messageWidth; private StaticLayout messageLayout; private boolean drawError; - private int errorTop = Utilities.dp(37); + private int errorTop = AndroidUtilities.dp(37); private int errorLeft; private boolean drawCount; - private int countTop = Utilities.dp(37); + private int countTop = AndroidUtilities.dp(37); private int countLeft; private int countWidth; private StaticLayout countLayout; - private int avatarTop = Utilities.dp(8); + private int avatarTop = AndroidUtilities.dp(8); private int avatarLeft; public void build(int width, int height) { @@ -374,32 +375,32 @@ public class DialogCell extends BaseCell { if (encryptedChat != null) { drawNameLock = true; drawNameGroup = false; - nameLockTop = Utilities.dp(13); + nameLockTop = AndroidUtilities.dp(13); if (!LocaleController.isRTL) { - nameLockLeft = Utilities.dp(77); - nameLeft = Utilities.dp(81) + lockDrawable.getIntrinsicWidth(); + nameLockLeft = AndroidUtilities.dp(77); + nameLeft = AndroidUtilities.dp(81) + lockDrawable.getIntrinsicWidth(); } else { - nameLockLeft = width - Utilities.dp(77) - lockDrawable.getIntrinsicWidth(); - nameLeft = Utilities.dp(14); + nameLockLeft = width - AndroidUtilities.dp(77) - lockDrawable.getIntrinsicWidth(); + nameLeft = AndroidUtilities.dp(14); } } else { drawNameLock = false; if (chat != null) { drawNameGroup = true; - nameLockTop = Utilities.dp(14); + nameLockTop = AndroidUtilities.dp(14); if (!LocaleController.isRTL) { - nameLockLeft = Utilities.dp(77); - nameLeft = Utilities.dp(81) + groupDrawable.getIntrinsicWidth(); + nameLockLeft = AndroidUtilities.dp(77); + nameLeft = AndroidUtilities.dp(81) + groupDrawable.getIntrinsicWidth(); } else { - nameLockLeft = width - Utilities.dp(77) - groupDrawable.getIntrinsicWidth(); - nameLeft = Utilities.dp(14); + nameLockLeft = width - AndroidUtilities.dp(77) - groupDrawable.getIntrinsicWidth(); + nameLeft = AndroidUtilities.dp(14); } } else { drawNameGroup = false; if (!LocaleController.isRTL) { - nameLeft = Utilities.dp(77); + nameLeft = AndroidUtilities.dp(77); } else { - nameLeft = Utilities.dp(14); + nameLeft = AndroidUtilities.dp(14); } } } @@ -476,10 +477,10 @@ public class DialogCell extends BaseCell { checkMessage = false; if (message.messageOwner.media != null && !(message.messageOwner.media instanceof TLRPC.TL_messageMediaEmpty)) { currentMessagePaint = messagePrintingPaint; - messageString = Emoji.replaceEmoji(Html.fromHtml(String.format("%s: %s", name, message.messageText)), messagePaint.getFontMetricsInt(), Utilities.dp(20)); + messageString = Emoji.replaceEmoji(Html.fromHtml(String.format("%s: %s", name, message.messageText)), messagePaint.getFontMetricsInt(), AndroidUtilities.dp(20)); } else { if (message.messageOwner.message != null) { - messageString = Emoji.replaceEmoji(Html.fromHtml(String.format("%s: %s", name, message.messageOwner.message.replace("\n", " ").replace("<", "<").replace(">", ">"))), messagePaint.getFontMetricsInt(), Utilities.dp(20)); + messageString = Emoji.replaceEmoji(Html.fromHtml(String.format("%s: %s", name, message.messageOwner.message.replace("\n", " ").replace("<", "<").replace(">", ">"))), messagePaint.getFontMetricsInt(), AndroidUtilities.dp(20)); } } } else { @@ -538,9 +539,9 @@ public class DialogCell extends BaseCell { timeWidth = (int)Math.ceil(timePaint.measureText(timeString)); timeLayout = new StaticLayout(timeString, timePaint, timeWidth, Layout.Alignment.ALIGN_NORMAL, 1.0f, 0.0f, false); if (!LocaleController.isRTL) { - timeLeft = width - Utilities.dp(11) - timeWidth; + timeLeft = width - AndroidUtilities.dp(11) - timeWidth; } else { - timeLeft = Utilities.dp(11); + timeLeft = AndroidUtilities.dp(11); } if (chat != null) { @@ -569,81 +570,81 @@ public class DialogCell extends BaseCell { } if (!LocaleController.isRTL) { - nameWidth = width - nameLeft - Utilities.dp(14) - timeWidth; + nameWidth = width - nameLeft - AndroidUtilities.dp(14) - timeWidth; } else { - nameWidth = width - nameLeft - Utilities.dp(77) - timeWidth; + nameWidth = width - nameLeft - AndroidUtilities.dp(77) - timeWidth; nameLeft += timeWidth; } if (drawNameLock) { - nameWidth -= Utilities.dp(4) + lockDrawable.getIntrinsicWidth(); + nameWidth -= AndroidUtilities.dp(4) + lockDrawable.getIntrinsicWidth(); } else if (drawNameGroup) { - nameWidth -= Utilities.dp(4) + groupDrawable.getIntrinsicWidth(); + nameWidth -= AndroidUtilities.dp(4) + groupDrawable.getIntrinsicWidth(); } if (drawClock) { - int w = clockDrawable.getIntrinsicWidth() + Utilities.dp(2); + int w = clockDrawable.getIntrinsicWidth() + AndroidUtilities.dp(2); nameWidth -= w; if (!LocaleController.isRTL) { checkDrawLeft = timeLeft - w; } else { - checkDrawLeft = timeLeft + timeWidth + Utilities.dp(2); + checkDrawLeft = timeLeft + timeWidth + AndroidUtilities.dp(2); nameLeft += w; } } else if (drawCheck2) { - int w = checkDrawable.getIntrinsicWidth() + Utilities.dp(2); + int w = checkDrawable.getIntrinsicWidth() + AndroidUtilities.dp(2); nameWidth -= w; if (drawCheck1) { - nameWidth -= halfCheckDrawable.getIntrinsicWidth() - Utilities.dp(5); + nameWidth -= halfCheckDrawable.getIntrinsicWidth() - AndroidUtilities.dp(5); if (!LocaleController.isRTL) { halfCheckDrawLeft = timeLeft - w; - checkDrawLeft = halfCheckDrawLeft - Utilities.dp(5); + checkDrawLeft = halfCheckDrawLeft - AndroidUtilities.dp(5); } else { - checkDrawLeft = timeLeft + timeWidth + Utilities.dp(2); - halfCheckDrawLeft = checkDrawLeft + Utilities.dp(5); - nameLeft += w + halfCheckDrawable.getIntrinsicWidth() - Utilities.dp(5); + checkDrawLeft = timeLeft + timeWidth + AndroidUtilities.dp(2); + halfCheckDrawLeft = checkDrawLeft + AndroidUtilities.dp(5); + nameLeft += w + halfCheckDrawable.getIntrinsicWidth() - AndroidUtilities.dp(5); } } else { if (!LocaleController.isRTL) { checkDrawLeft = timeLeft - w; } else { - checkDrawLeft = timeLeft + timeWidth + Utilities.dp(2); + checkDrawLeft = timeLeft + timeWidth + AndroidUtilities.dp(2); nameLeft += w; } } } - CharSequence nameStringFinal = TextUtils.ellipsize(nameString.replace("\n", " "), currentNamePaint, nameWidth - Utilities.dp(12), TextUtils.TruncateAt.END); + CharSequence nameStringFinal = TextUtils.ellipsize(nameString.replace("\n", " "), currentNamePaint, nameWidth - AndroidUtilities.dp(12), TextUtils.TruncateAt.END); nameLayout = new StaticLayout(nameStringFinal, currentNamePaint, nameWidth, Layout.Alignment.ALIGN_NORMAL, 1.0f, 0.0f, false); - messageWidth = width - Utilities.dp(88); + messageWidth = width - AndroidUtilities.dp(88); if (!LocaleController.isRTL) { - messageLeft = Utilities.dp(77); - avatarLeft = Utilities.dp(11); + messageLeft = AndroidUtilities.dp(77); + avatarLeft = AndroidUtilities.dp(11); } else { - messageLeft = Utilities.dp(11); - avatarLeft = width - Utilities.dp(65); + messageLeft = AndroidUtilities.dp(11); + avatarLeft = width - AndroidUtilities.dp(65); } avatarImage.imageX = avatarLeft; avatarImage.imageY = avatarTop; - avatarImage.imageW = Utilities.dp(54); - avatarImage.imageH = Utilities.dp(54); + avatarImage.imageW = AndroidUtilities.dp(54); + avatarImage.imageH = AndroidUtilities.dp(54); if (drawError) { - int w = errorDrawable.getIntrinsicWidth() + Utilities.dp(8); + int w = errorDrawable.getIntrinsicWidth() + AndroidUtilities.dp(8); messageWidth -= w; if (!LocaleController.isRTL) { - errorLeft = width - errorDrawable.getIntrinsicWidth() - Utilities.dp(11); + errorLeft = width - errorDrawable.getIntrinsicWidth() - AndroidUtilities.dp(11); } else { - errorLeft = Utilities.dp(11); + errorLeft = AndroidUtilities.dp(11); messageLeft += w; } } else if (countString != null) { - countWidth = Math.max(Utilities.dp(12), (int)Math.ceil(countPaint.measureText(countString))); + countWidth = Math.max(AndroidUtilities.dp(12), (int)Math.ceil(countPaint.measureText(countString))); countLayout = new StaticLayout(countString, countPaint, countWidth, Layout.Alignment.ALIGN_CENTER, 1.0f, 0.0f, false); - int w = countWidth + Utilities.dp(18); + int w = countWidth + AndroidUtilities.dp(18); messageWidth -= w; if (!LocaleController.isRTL) { - countLeft = width - countWidth - Utilities.dp(16); + countLeft = width - countWidth - AndroidUtilities.dp(16); } else { - countLeft = Utilities.dp(16); + countLeft = AndroidUtilities.dp(16); messageLeft += w; } drawCount = true; @@ -659,10 +660,10 @@ public class DialogCell extends BaseCell { if (mess.length() > 150) { mess = mess.substring(0, 150); } - messageString = Emoji.replaceEmoji(mess, messagePaint.getFontMetricsInt(), Utilities.dp(20)); + messageString = Emoji.replaceEmoji(mess, messagePaint.getFontMetricsInt(), AndroidUtilities.dp(20)); } - CharSequence messageStringFinal = TextUtils.ellipsize(messageString, currentMessagePaint, messageWidth - Utilities.dp(12), TextUtils.TruncateAt.END); + CharSequence messageStringFinal = TextUtils.ellipsize(messageString, currentMessagePaint, messageWidth - AndroidUtilities.dp(12), TextUtils.TruncateAt.END); messageLayout = new StaticLayout(messageStringFinal, currentMessagePaint, messageWidth, Layout.Alignment.ALIGN_NORMAL, 1.0f, 0.0f, false); double widthpx = 0; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/ChatActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/ChatActivity.java index 74f44d1f5..e9116ba1f 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/ChatActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/ChatActivity.java @@ -8,7 +8,6 @@ package org.telegram.ui; -import android.animation.Animator; import android.app.Activity; import android.app.AlertDialog; import android.content.Context; @@ -26,54 +25,42 @@ import android.media.MediaPlayer; import android.media.ThumbnailUtils; import android.net.Uri; import android.os.Bundle; -import android.os.PowerManager; import android.provider.MediaStore; -import android.text.Editable; import android.text.Html; import android.text.TextUtils; -import android.text.TextWatcher; -import android.text.style.ImageSpan; import android.util.TypedValue; import android.view.Gravity; -import android.view.KeyEvent; import android.view.LayoutInflater; import android.view.MotionEvent; -import android.view.Surface; import android.view.View; import android.view.ViewGroup; import android.view.ViewParent; import android.view.ViewTreeObserver; -import android.view.WindowManager; -import android.view.animation.AccelerateDecelerateInterpolator; -import android.view.inputmethod.EditorInfo; -import android.view.inputmethod.InputMethodManager; import android.webkit.MimeTypeMap; import android.widget.AbsListView; import android.widget.AdapterView; -import android.widget.EditText; import android.widget.FrameLayout; -import android.widget.ImageButton; import android.widget.ImageView; import android.widget.LinearLayout; -import android.widget.PopupWindow; import android.widget.ProgressBar; import android.widget.RelativeLayout; import android.widget.TextView; import android.widget.Toast; +import org.telegram.android.AndroidUtilities; import org.telegram.PhoneFormat.PhoneFormat; -import org.telegram.messenger.LocaleController; -import org.telegram.messenger.MediaController; -import org.telegram.messenger.MessagesStorage; +import org.telegram.android.LocaleController; +import org.telegram.android.MediaController; +import org.telegram.android.MessagesStorage; +import org.telegram.android.NotificationsController; import org.telegram.messenger.TLRPC; -import org.telegram.messenger.ContactsController; +import org.telegram.android.ContactsController; import org.telegram.messenger.FileLog; import org.telegram.objects.MessageObject; import org.telegram.objects.PhotoObject; import org.telegram.messenger.ConnectionsManager; -import org.telegram.messenger.Emoji; import org.telegram.messenger.FileLoader; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.UserConfig; @@ -88,7 +75,7 @@ import org.telegram.ui.Views.ActionBar.ActionBarMenu; import org.telegram.ui.Views.ActionBar.ActionBarMenuItem; import org.telegram.ui.Views.BackupImageView; import org.telegram.ui.Views.ActionBar.BaseFragment; -import org.telegram.ui.Views.EmojiView; +import org.telegram.ui.Views.ChatActivityEnterView; import org.telegram.ui.Views.ImageReceiver; import org.telegram.ui.Views.LayoutListView; import org.telegram.ui.Views.MessageActionLayout; @@ -98,15 +85,14 @@ import org.telegram.ui.Views.TimerButton; import java.io.File; import java.util.ArrayList; import java.util.Collections; -import java.util.Comparator; import java.util.HashMap; import java.util.concurrent.Semaphore; -public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLayout.SizeNotifierRelativeLayoutDelegate, - NotificationCenter.NotificationCenterDelegate, MessagesActivity.MessagesActivityDelegate, - DocumentSelectActivity.DocumentSelectActivityDelegate, PhotoViewer.PhotoViewerProvider, - PhotoPickerActivity.PhotoPickerActivityDelegate { +public class ChatActivity extends BaseFragment implements NotificationCenter.NotificationCenterDelegate, MessagesActivity.MessagesActivityDelegate, + DocumentSelectActivity.DocumentSelectActivityDelegate, PhotoViewer.PhotoViewerProvider, PhotoPickerActivity.PhotoPickerActivityDelegate, + VideoEditorActivity.VideoEditorActivityDelegate { + private ChatActivityEnterView chatActivityEnterView; private View timeItem; private View menuItem; private LayoutListView chatListView; @@ -115,26 +101,15 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa private TLRPC.User currentUser; private TLRPC.EncryptedChat currentEncryptedChat; private ChatAdapter chatAdapter; - private EditText messsageEditText; - private ImageButton sendButton; - private PopupWindow emojiPopup; - private ImageView emojiButton; - private EmojiView emojiView; - private View slideText; - private boolean keyboardVisible; - private int keyboardHeight = 0; - private int keyboardHeightLand = 0; + private View topPanel; private View secretChatPlaceholder; - private View contentView; private View progressView; - private boolean ignoreTextChange = false; private TextView emptyView; private View bottomOverlay; - private View recordPanel; - private TextView recordTimeText; + private TextView bottomOverlayText; - private ImageButton audioSendButton; + private MessageObject selectedObject; private MessageObject forwaringMessage; private TextView secretViewStatusTextView; @@ -142,7 +117,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa private TextView selectedMessagesCountTextView; private boolean paused = true; private boolean readWhenResume = false; - private boolean sendByEnter = false; + private int readWithDate = 0; private int readWithMid = 0; private boolean scrollToTopOnResume = false; @@ -154,7 +129,6 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa private View pagedownButton; private TextView topPanelText; private long dialog_id; - private SizeNotifierRelativeLayout sizeNotifierRelativeLayout; private HashMap selectedMessagesIds = new HashMap(); private HashMap selectedMessagesCanCopyIds = new HashMap(); @@ -167,7 +141,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa private boolean endReached = false; private boolean loading = false; private boolean cacheEndReaced = false; - private long lastTypingTimeSend = 0; + private int minDate = 0; private int progressTag = 0; boolean first = true; @@ -177,11 +151,6 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa private boolean unread_end_reached = true; private boolean loadingForward = false; private MessageObject unreadMessageObject = null; - private boolean recordingAudio = false; - private String lastTimeString = null; - private float startedDraggingX = -1; - private float distCanMove = Utilities.dp(80); - private PowerManager.WakeLock mWakeLock = null; private String currentPicturePath; @@ -317,6 +286,24 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } else { return false; } + chatActivityEnterView = new ChatActivityEnterView(); + chatActivityEnterView.setDialogId(dialog_id); + chatActivityEnterView.setDelegate(new ChatActivityEnterView.ChatActivityEnterViewDelegate() { + @Override + public void onMessageSend() { + chatListView.post(new Runnable() { + @Override + public void run() { + chatListView.setSelectionFromTop(messages.size() - 1, -100000 - chatListView.getPaddingTop()); + } + }); + } + + @Override + public void needSendTyping() { + MessagesController.getInstance().sendTyping(dialog_id, classGuid); + } + }); NotificationCenter.getInstance().addObserver(this, MessagesController.messagesDidLoaded); NotificationCenter.getInstance().addObserver(this, 999); NotificationCenter.getInstance().addObserver(this, MessagesController.updateInterfaces); @@ -338,10 +325,6 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa NotificationCenter.getInstance().addObserver(this, FileLoader.FileLoadProgressChanged); NotificationCenter.getInstance().addObserver(this, MediaController.audioProgressDidChanged); NotificationCenter.getInstance().addObserver(this, MediaController.audioDidReset); - NotificationCenter.getInstance().addObserver(this, MediaController.recordProgressChanged); - NotificationCenter.getInstance().addObserver(this, MediaController.recordStarted); - NotificationCenter.getInstance().addObserver(this, MediaController.recordStartError); - NotificationCenter.getInstance().addObserver(this, MediaController.recordStopped); NotificationCenter.getInstance().addObserver(this, MediaController.screenshotTook); NotificationCenter.getInstance().addObserver(this, 997); @@ -350,16 +333,12 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa loading = true; MessagesController.getInstance().loadMessages(dialog_id, 0, 30, 0, true, 0, classGuid, true, false); SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("mainconfig", Activity.MODE_PRIVATE); - sendByEnter = preferences.getBoolean("send_by_enter", false); if (currentChat != null) { downloadPhotos = preferences.getInt("photo_download_chat2", 0); - } else { - downloadPhotos = preferences.getInt("photo_download_user2", 0); - } - if (currentChat != null) { downloadAudios = preferences.getInt("audio_download_chat2", 0); } else { + downloadPhotos = preferences.getInt("photo_download_user2", 0); downloadAudios = preferences.getInt("audio_download_user2", 0); } @@ -369,6 +348,9 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa @Override public void onFragmentDestroy() { super.onFragmentDestroy(); + if (chatActivityEnterView != null) { + chatActivityEnterView.onDestroy(); + } NotificationCenter.getInstance().removeObserver(this, MessagesController.messagesDidLoaded); NotificationCenter.getInstance().removeObserver(this, 999); NotificationCenter.getInstance().removeObserver(this, MessagesController.updateInterfaces); @@ -390,29 +372,13 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa NotificationCenter.getInstance().removeObserver(this, MessagesController.contactsDidLoaded); NotificationCenter.getInstance().removeObserver(this, MediaController.audioProgressDidChanged); NotificationCenter.getInstance().removeObserver(this, MediaController.audioDidReset); - NotificationCenter.getInstance().removeObserver(this, MediaController.recordProgressChanged); - NotificationCenter.getInstance().removeObserver(this, MediaController.recordStarted); - NotificationCenter.getInstance().removeObserver(this, MediaController.recordStartError); - NotificationCenter.getInstance().removeObserver(this, MediaController.recordStopped); NotificationCenter.getInstance().removeObserver(this, MediaController.screenshotTook); NotificationCenter.getInstance().removeObserver(this, 997); if (currentEncryptedChat != null) { MediaController.getInstance().stopMediaObserver(); } - if (sizeNotifierRelativeLayout != null) { - sizeNotifierRelativeLayout.delegate = null; - sizeNotifierRelativeLayout = null; - } - if (mWakeLock != null) { - try { - mWakeLock.release(); - mWakeLock = null; - } catch (Exception e) { - FileLog.e("tmessages", e); - } - } - Utilities.unlockOrientation(getParentActivity()); + AndroidUtilities.unlockOrientation(getParentActivity()); MediaController.getInstance().stopAudio(); } @@ -561,7 +527,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa updateSubtitle(); if (currentEncryptedChat != null) { - actionBarLayer.setTitleIcon(R.drawable.ic_lock_white, Utilities.dp(4)); + actionBarLayer.setTitleIcon(R.drawable.ic_lock_white, AndroidUtilities.dp(4)); } ActionBarMenu menu = actionBarLayer.createMenu(); @@ -578,7 +544,6 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa item.addSubItem(attach_location, LocaleController.getString("ChatLocation", R.string.ChatLocation), R.drawable.ic_attach_location); menuItem = item; - ActionBarMenu actionMode = actionBarLayer.createActionMode(); actionMode.addItem(-2, R.drawable.ic_ab_done_gray); @@ -586,10 +551,10 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa layout.setBackgroundColor(0xffe5e5e5); actionMode.addView(layout); LinearLayout.LayoutParams layoutParams = (LinearLayout.LayoutParams)layout.getLayoutParams(); - layoutParams.width = Utilities.dp(1); + layoutParams.width = AndroidUtilities.dp(1); layoutParams.height = LinearLayout.LayoutParams.MATCH_PARENT; - layoutParams.topMargin = Utilities.dp(12); - layoutParams.bottomMargin = Utilities.dp(12); + layoutParams.topMargin = AndroidUtilities.dp(12); + layoutParams.bottomMargin = AndroidUtilities.dp(12); layoutParams.gravity = Gravity.CENTER_VERTICAL; layout.setLayoutParams(layoutParams); @@ -599,8 +564,14 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa selectedMessagesCountTextView.setSingleLine(true); selectedMessagesCountTextView.setLines(1); selectedMessagesCountTextView.setEllipsize(TextUtils.TruncateAt.END); - selectedMessagesCountTextView.setPadding(Utilities.dp(6), 0, 0, 0); + selectedMessagesCountTextView.setPadding(AndroidUtilities.dp(6), 0, 0, 0); selectedMessagesCountTextView.setGravity(Gravity.CENTER_VERTICAL); + selectedMessagesCountTextView.setOnTouchListener(new View.OnTouchListener() { + @Override + public boolean onTouch(View v, MotionEvent event) { + return true; + } + }); actionMode.addView(selectedMessagesCountTextView); layoutParams = (LinearLayout.LayoutParams)selectedMessagesCountTextView.getLayoutParams(); layoutParams.weight = 1; @@ -625,10 +596,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa fragmentView = inflater.inflate(R.layout.chat_layout, container, false); - sizeNotifierRelativeLayout = (SizeNotifierRelativeLayout)fragmentView.findViewById(R.id.chat_layout); - sizeNotifierRelativeLayout.delegate = this; - contentView = sizeNotifierRelativeLayout; - + View contentView = fragmentView.findViewById(R.id.chat_layout); emptyView = (TextView)fragmentView.findViewById(R.id.searchEmptyView); emptyView.setText(LocaleController.getString("NoMessages", R.string.NoMessages)); chatListView = (LayoutListView)fragmentView.findViewById(R.id.chat_list_view); @@ -641,9 +609,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa View bottomOverlayChat = fragmentView.findViewById(R.id.bottom_overlay_chat); progressView = fragmentView.findViewById(R.id.progressLayout); pagedownButton = fragmentView.findViewById(R.id.pagedown_button); - audioSendButton = (ImageButton)fragmentView.findViewById(R.id.chat_audio_send_button); - recordPanel = fragmentView.findViewById(R.id.record_panel); - recordTimeText = (TextView)fragmentView.findViewById(R.id.recording_time_text); + View progressViewInner = progressView.findViewById(R.id.progressLayoutInner); updateContactStatus(); @@ -693,8 +659,8 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } else { secretChatPlaceholder.setBackgroundResource(R.drawable.system_blue); } - secretViewStatusTextView = (TextView)contentView.findViewById(R.id.invite_text); - secretChatPlaceholder.setPadding(Utilities.dp(16), Utilities.dp(12), Utilities.dp(16), Utilities.dp(12)); + secretViewStatusTextView = (TextView) contentView.findViewById(R.id.invite_text); + secretChatPlaceholder.setPadding(AndroidUtilities.dp(16), AndroidUtilities.dp(12), AndroidUtilities.dp(16), AndroidUtilities.dp(12)); View v = contentView.findViewById(R.id.secret_placeholder); v.setVisibility(View.VISIBLE); @@ -723,7 +689,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa progressViewInner.setBackgroundResource(R.drawable.system_loader1); emptyView.setBackgroundResource(R.drawable.system_blue); } - emptyView.setPadding(Utilities.dp(7), Utilities.dp(1), Utilities.dp(7), Utilities.dp(1)); + emptyView.setPadding(AndroidUtilities.dp(7), AndroidUtilities.dp(1), AndroidUtilities.dp(7), AndroidUtilities.dp(1)); if (currentUser != null && currentUser.id / 1000 == 333) { emptyView.setText(LocaleController.getString("GotAQuestion", R.string.GotAQuestion)); @@ -783,12 +749,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } }); - messsageEditText = (EditText)fragmentView.findViewById(R.id.chat_text_edit); - messsageEditText.setHint(LocaleController.getString("TypeMessage", R.string.TypeMessage)); - slideText = fragmentView.findViewById(R.id.slideText); - TextView textView = (TextView)fragmentView.findViewById(R.id.slideToCancelTextView); - textView.setText(LocaleController.getString("SlideToCancel", R.string.SlideToCancel)); - textView = (TextView)fragmentView.findViewById(R.id.bottom_overlay_chat_text); + TextView textView = (TextView)fragmentView.findViewById(R.id.bottom_overlay_chat_text); if (currentUser == null) { textView.setText(LocaleController.getString("DeleteThisGroup", R.string.DeleteThisGroup)); } else { @@ -805,11 +766,6 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa textView = (TextView)fragmentView.findViewById(R.id.secret_description4); textView.setText(LocaleController.getString("EncryptedDescription4", R.string.EncryptedDescription4)); - sendButton = (ImageButton)fragmentView.findViewById(R.id.chat_send_button); - sendButton.setEnabled(false); - sendButton.setVisibility(View.INVISIBLE); - emojiButton = (ImageView)fragmentView.findViewById(R.id.chat_smile_button); - if (loading && messages.isEmpty()) { progressView.setVisibility(View.VISIBLE); chatListView.setEmptyView(null); @@ -822,123 +778,6 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } } - emojiButton.setOnClickListener(new View.OnClickListener() { - @Override - public void onClick(View view) { - if (emojiPopup == null) { - showEmojiPopup(true); - } else { - showEmojiPopup(!emojiPopup.isShowing()); - } - } - }); - - messsageEditText.setOnKeyListener(new View.OnKeyListener() { - @Override - public boolean onKey(View view, int i, KeyEvent keyEvent) { - if (i == 4 && !keyboardVisible && emojiPopup != null && emojiPopup.isShowing()) { - if (keyEvent.getAction() == 1) { - showEmojiPopup(false); - } - return true; - } else if (i == KeyEvent.KEYCODE_ENTER && sendByEnter && keyEvent.getAction() == KeyEvent.ACTION_DOWN) { - sendMessage(); - return true; - } - return false; - } - }); - - messsageEditText.setOnClickListener(new View.OnClickListener() { - @Override - public void onClick(View view) { - if (emojiPopup != null && emojiPopup.isShowing()) { - showEmojiPopup(false); - } - } - }); - - messsageEditText.setOnEditorActionListener(new TextView.OnEditorActionListener() { - @Override - public boolean onEditorAction(TextView textView, int i, KeyEvent keyEvent) { - if (i == EditorInfo.IME_ACTION_SEND) { - sendMessage(); - return true; - } else if (sendByEnter) { - if (keyEvent != null && i == EditorInfo.IME_NULL && keyEvent.getAction() == KeyEvent.ACTION_DOWN) { - sendMessage(); - return true; - } - } - return false; - } - }); - - sendButton.setOnClickListener(new View.OnClickListener() { - @Override - public void onClick(View view) { - sendMessage(); - } - }); - - audioSendButton.setOnTouchListener(new View.OnTouchListener() { - @Override - public boolean onTouch(View view, MotionEvent motionEvent) { - if (motionEvent.getAction() == MotionEvent.ACTION_DOWN) { - startedDraggingX = -1; - MediaController.getInstance().startRecording(dialog_id); - updateAudioRecordIntefrace(); - } else if (motionEvent.getAction() == MotionEvent.ACTION_UP || motionEvent.getAction() == MotionEvent.ACTION_CANCEL) { - startedDraggingX = -1; - MediaController.getInstance().stopRecording(true); - recordingAudio = false; - updateAudioRecordIntefrace(); - } else if (motionEvent.getAction() == MotionEvent.ACTION_MOVE && recordingAudio) { - float x = motionEvent.getX(); - if (x < -distCanMove) { - MediaController.getInstance().stopRecording(false); - recordingAudio = false; - updateAudioRecordIntefrace(); - } - if(android.os.Build.VERSION.SDK_INT > 13) { - x = x + audioSendButton.getX(); - FrameLayout.LayoutParams params = (FrameLayout.LayoutParams)slideText.getLayoutParams(); - if (startedDraggingX != -1) { - float dist = (x - startedDraggingX); - params.leftMargin = Utilities.dp(30) + (int)dist; - slideText.setLayoutParams(params); - float alpha = 1.0f + dist / distCanMove; - if (alpha > 1) { - alpha = 1; - } else if (alpha < 0) { - alpha = 0; - } - slideText.setAlpha(alpha); - } - if (x <= slideText.getX() + slideText.getWidth() + Utilities.dp(30)) { - if (startedDraggingX == -1) { - startedDraggingX = x; - distCanMove = (recordPanel.getMeasuredWidth() - slideText.getMeasuredWidth() - Utilities.dp(48)) / 2.0f; - if (distCanMove <= 0) { - distCanMove = Utilities.dp(80); - } else if (distCanMove > Utilities.dp(80)) { - distCanMove = Utilities.dp(80); - } - } - } - if (params.leftMargin > Utilities.dp(30)) { - params.leftMargin = Utilities.dp(30); - slideText.setLayoutParams(params); - slideText.setAlpha(1); - startedDraggingX = -1; - } - } - } - view.onTouchEvent(motionEvent); - return true; - } - }); - pagedownButton.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View view) { @@ -946,49 +785,6 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } }); - checkSendButton(); - - messsageEditText.addTextChangedListener(new TextWatcher() { - @Override - public void beforeTextChanged(CharSequence charSequence, int i, int i2, int i3) { - - } - - @Override - public void onTextChanged(CharSequence charSequence, int i, int i2, int i3) { - String message = getTrimmedString(charSequence.toString()); - sendButton.setEnabled(message.length() != 0); - checkSendButton(); - - if (message.length() != 0 && lastTypingTimeSend < System.currentTimeMillis() - 5000 && !ignoreTextChange) { - int currentTime = ConnectionsManager.getInstance().getCurrentTime(); - if (currentUser != null && currentUser.status != null && currentUser.status.expires < currentTime) { - return; - } - lastTypingTimeSend = System.currentTimeMillis(); - MessagesController.getInstance().sendTyping(dialog_id, classGuid); - } - } - - @Override - public void afterTextChanged(Editable editable) { - if (sendByEnter && editable.length() > 0 && editable.charAt(editable.length() - 1) == '\n') { - sendMessage(); - } - int i = 0; - ImageSpan[] arrayOfImageSpan = editable.getSpans(0, editable.length(), ImageSpan.class); - int j = arrayOfImageSpan.length; - while (true) { - if (i >= j) { - Emoji.replaceEmoji(editable, messsageEditText.getPaint().getFontMetricsInt(), Utilities.dp(20)); - return; - } - editable.removeSpan(arrayOfImageSpan[i]); - i++; - } - } - }); - bottomOverlayChat.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View view) { @@ -996,7 +792,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa return; } AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); - builder.setMessage(LocaleController.getString("AreYouSure", R.string.AreYouSure)); + builder.setMessage(LocaleController.getString("AreYouSureDeleteThisChat", R.string.AreYouSureDeleteThisChat)); builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), new DialogInterface.OnClickListener() { @Override @@ -1027,6 +823,8 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } else { bottomOverlayChat.setVisibility(View.GONE); } + + chatActivityEnterView.setContainerView(getParentActivity(), fragmentView); } else { ViewGroup parent = (ViewGroup)fragmentView.getParent(); if (parent != null) { @@ -1036,125 +834,6 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa return fragmentView; } - private String getTrimmedString(String src) { - String result = src.trim(); - if (result.length() == 0) { - return result; - } - while (src.startsWith("\n")) { - src = src.substring(1); - } - while (src.endsWith("\n")) { - src = src.substring(0, src.length() - 1); - } - return src; - } - - private void checkSendButton() { - String message = getTrimmedString(messsageEditText.getText().toString()); - if (message.length() > 0) { - sendButton.setVisibility(View.VISIBLE); - audioSendButton.setVisibility(View.INVISIBLE); - } else { - sendButton.setVisibility(View.INVISIBLE); - audioSendButton.setVisibility(View.VISIBLE); - } - } - - private void updateAudioRecordIntefrace() { - if (recordingAudio) { - try { - if (mWakeLock == null) { - PowerManager pm = (PowerManager) ApplicationLoader.applicationContext.getSystemService(Context.POWER_SERVICE); - mWakeLock = pm.newWakeLock(PowerManager.SCREEN_DIM_WAKE_LOCK | PowerManager.ON_AFTER_RELEASE, "audio record lock"); - mWakeLock.acquire(); - } - } catch (Exception e) { - FileLog.e("tmessages", e); - } - Utilities.lockOrientation(getParentActivity()); - - recordPanel.setVisibility(View.VISIBLE); - recordTimeText.setText("00:00"); - lastTimeString = null; - if(android.os.Build.VERSION.SDK_INT > 13) { - FrameLayout.LayoutParams params = (FrameLayout.LayoutParams)slideText.getLayoutParams(); - params.leftMargin = Utilities.dp(30); - slideText.setLayoutParams(params); - slideText.setAlpha(1); - recordPanel.setX(Utilities.displaySize.x); - recordPanel.animate().setInterpolator(new AccelerateDecelerateInterpolator()).setListener(new Animator.AnimatorListener() { - @Override - public void onAnimationStart(Animator animator) { - } - - @Override - public void onAnimationEnd(Animator animator) { - recordPanel.setX(0); - } - - @Override - public void onAnimationCancel(Animator animator) { - } - - @Override - public void onAnimationRepeat(Animator animator) { - } - }).setDuration(300).translationX(0).start(); - } - } else { - if (mWakeLock != null) { - try { - mWakeLock.release(); - mWakeLock = null; - } catch (Exception e) { - FileLog.e("tmessages", e); - } - } - Utilities.unlockOrientation(getParentActivity()); - if(android.os.Build.VERSION.SDK_INT > 13) { - recordPanel.animate().setInterpolator(new AccelerateDecelerateInterpolator()).setListener(new Animator.AnimatorListener() { - @Override - public void onAnimationStart(Animator animator) { - - } - - @Override - public void onAnimationEnd(Animator animator) { - FrameLayout.LayoutParams params = (FrameLayout.LayoutParams)slideText.getLayoutParams(); - params.leftMargin = Utilities.dp(30); - slideText.setLayoutParams(params); - slideText.setAlpha(1); - recordPanel.setVisibility(View.GONE); - } - - @Override - public void onAnimationCancel(Animator animator) { - } - - @Override - public void onAnimationRepeat(Animator animator) { - } - }).setDuration(300).translationX(Utilities.displaySize.x).start(); - } else { - recordPanel.setVisibility(View.GONE); - } - } - } - - private void sendMessage() { - if (processSendingText(messsageEditText.getText().toString())) { - messsageEditText.setText(""); - lastTypingTimeSend = 0; - chatListView.post(new Runnable() { - @Override - public void run() { - chatListView.setSelectionFromTop(messages.size() - 1, -100000 - chatListView.getPaddingTop()); - } - }); - } - } - private void scrollToLastMessage() { if (unread_end_reached || first_unread_id == 0) { chatListView.setSelectionFromTop(messages.size() - 1, -100000 - chatListView.getPaddingTop()); @@ -1235,8 +914,8 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa bottomOverlay.setVisibility(View.GONE); } if (hideKeyboard) { - hideEmojiPopup(); - Utilities.hideKeyboard(getParentActivity().getCurrentFocus()); + chatActivityEnterView.hideEmojiPopup(); + AndroidUtilities.hideKeyboard(getParentActivity().getCurrentFocus()); } checkActionBarMenu(); } @@ -1368,7 +1047,11 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa if (currentEncryptedChat == null) { if (messageObject.messageOwner.id <= 0 && messageObject.isOut()) { if (messageObject.messageOwner.send_state == MessagesController.MESSAGE_SEND_STATE_SEND_ERROR) { - return 0; + if (!(messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaEmpty)) { + return 0; + } else { + return 6; + } } else { return -1; } @@ -1393,7 +1076,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } } if (!canSave) { - File f = new File(Utilities.getCacheDir(), messageObject.getFileName()); + File f = new File(AndroidUtilities.getCacheDir(), messageObject.getFileName()); if (f.exists()) { canSave = true; } @@ -1418,7 +1101,11 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa if (messageObject.type == 7) { return -1; } else if (messageObject.messageOwner.send_state == MessagesController.MESSAGE_SEND_STATE_SEND_ERROR) { - return 0; + if (!(messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaEmpty)) { + return 0; + } else { + return 6; + } } else if (messageObject.type == 10 || messageObject.type == 11 || messageObject.messageOwner.send_state == MessagesController.MESSAGE_SEND_STATE_SENDING) { if (messageObject.messageOwner.id == 0) { return -1; @@ -1437,7 +1124,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } } if (!canSave) { - File f = new File(Utilities.getCacheDir(), messageObject.getFileName()); + File f = new File(AndroidUtilities.getCacheDir(), messageObject.getFileName()); if (f.exists()) { canSave = true; } @@ -1493,7 +1180,9 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa message = holder.message; } - if (getMessageType(message) < 2) { + int type = getMessageType(message); + + if (type < 2 || type == 6) { return; } addToSelectedMessages(message); @@ -1536,9 +1225,9 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa actionBarLayer.setSubtitle(LocaleController.getString("YouLeft", R.string.YouLeft)); } else { if (onlineCount > 0 && currentChat.participants_count != 0) { - actionBarLayer.setSubtitle(String.format("%d %s, %d %s", currentChat.participants_count, LocaleController.getString("Members", R.string.Members), onlineCount, LocaleController.getString("Online", R.string.Online))); + actionBarLayer.setSubtitle(String.format("%s, %d %s", LocaleController.formatPluralString("Members", currentChat.participants_count), onlineCount, LocaleController.getString("Online", R.string.Online))); } else { - actionBarLayer.setSubtitle(String.format("%d %s", currentChat.participants_count, LocaleController.getString("Members", R.string.Members))); + actionBarLayer.setSubtitle(LocaleController.formatPluralString("Members", currentChat.participants_count)); } } } else if (currentUser != null) { @@ -1584,57 +1273,6 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } } - @Override - public void onSizeChanged(int height) { - Rect localRect = new Rect(); - getParentActivity().getWindow().getDecorView().getWindowVisibleDisplayFrame(localRect); - - WindowManager manager = (WindowManager) ApplicationLoader.applicationContext.getSystemService(Activity.WINDOW_SERVICE); - if (manager == null || manager.getDefaultDisplay() == null) { - return; - } - int rotation = manager.getDefaultDisplay().getRotation(); - - if (height > Utilities.dp(50)) { - if (rotation == Surface.ROTATION_270 || rotation == Surface.ROTATION_90) { - keyboardHeightLand = height; - ApplicationLoader.applicationContext.getSharedPreferences("emoji", 0).edit().putInt("kbd_height_land3", keyboardHeightLand).commit(); - } else { - keyboardHeight = height; - ApplicationLoader.applicationContext.getSharedPreferences("emoji", 0).edit().putInt("kbd_height", keyboardHeight).commit(); - } - } - - if (emojiPopup != null && emojiPopup.isShowing()) { - WindowManager wm = (WindowManager) ApplicationLoader.applicationContext.getSystemService(Context.WINDOW_SERVICE); - final WindowManager.LayoutParams layoutParams = (WindowManager.LayoutParams)emojiPopup.getContentView().getLayoutParams(); - layoutParams.width = contentView.getWidth(); - if (rotation == Surface.ROTATION_270 || rotation == Surface.ROTATION_90) { - layoutParams.height = keyboardHeightLand; - } else { - layoutParams.height = keyboardHeight; - } - wm.updateViewLayout(emojiPopup.getContentView(), layoutParams); - if (!keyboardVisible) { - contentView.post(new Runnable() { - @Override - public void run() { - contentView.setPadding(0, 0, 0, layoutParams.height); - contentView.requestLayout(); - } - }); - } - } - - boolean oldValue = keyboardVisible; - keyboardVisible = height > 0; - if (keyboardVisible && contentView.getPaddingBottom() > 0) { - showEmojiPopup(false); - } else if (!keyboardVisible && keyboardVisible != oldValue && emojiPopup != null && emojiPopup.isShowing()) { - showEmojiPopup(false); - } - } - @Override public void onActivityResultFragment(int requestCode, int resultCode, Intent data) { if (resultCode == Activity.RESULT_OK) { @@ -1681,7 +1319,15 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } currentPicturePath = null; } - processSendingVideo(videoPath); + /*if(android.os.Build.VERSION.SDK_INT >= 10) { + Bundle args = new Bundle(); + args.putString("videoPath", videoPath); + VideoEditorActivity fragment = new VideoEditorActivity(args); + fragment.setDelegate(this); + presentFragment(fragment); + } else {*/ + processSendingVideo(videoPath); + //} } else if (requestCode == 21) { if (data == null || data.getData() == null) { showAttachmentError(); @@ -1702,6 +1348,11 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } } + @Override + public void didFinishedVideoConverting(String videoPath) { + processSendingVideo(videoPath); + } + private void showAttachmentError() { if (getParentActivity() == null) { return; @@ -1723,16 +1374,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } public boolean processSendingText(String text) { - text = getTrimmedString(text); - if (text.length() != 0) { - int count = (int)Math.ceil(text.length() / 2048.0f); - for (int a = 0; a < count; a++) { - String mess = text.substring(a * 2048, Math.min((a + 1) * 2048, text.length())); - MessagesController.getInstance().sendMessage(mess, dialog_id); - } - return true; - } - return false; + return chatActivityEnterView.processSendingText(text); } public void processSendingPhoto(String imageFilePath, Uri imageUri) { @@ -1802,6 +1444,10 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa sendAsDocuments.add(tempPath); sendAsDocumentsOriginal.add(originalPath); } else { + if (tempPath != null) { + File temp = new File(tempPath); + originalPath += temp.length() + "_" + temp.lastModified(); + } TLRPC.TL_photo photo = (TLRPC.TL_photo)MessagesStorage.getInstance().getSentFile(originalPath, currentEncryptedChat == null ? 0 : 3); if (photo == null && uri != null) { photo = (TLRPC.TL_photo)MessagesStorage.getInstance().getSentFile(Utilities.getPath(uri), currentEncryptedChat == null ? 0 : 3); @@ -1817,7 +1463,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa public void run() { MessagesController.getInstance().sendMessage(photoFinal, originalPathFinal, dialog_id); if (chatListView != null) { - chatListView.setSelection(messages.size() + 1); + chatListView.setSelectionFromTop(messages.size() - 1, -100000 - chatListView.getPaddingTop()); } if (paused) { scrollToTopOnResume = true; @@ -1906,7 +1552,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa public void run() { MessagesController.getInstance().sendMessage(documentFinal, originalPathFinal, dialog_id); if (chatListView != null) { - chatListView.setSelection(messages.size() + 1); + chatListView.setSelectionFromTop(messages.size() - 1, -100000 - chatListView.getPaddingTop()); } if (paused) { scrollToTopOnResume = true; @@ -1947,7 +1593,10 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa new Thread(new Runnable() { @Override public void run() { - TLRPC.TL_video video = (TLRPC.TL_video)MessagesStorage.getInstance().getSentFile(videoPath, currentEncryptedChat == null ? 2 : 5); + String originalPath = videoPath; + File temp = new File(originalPath); + originalPath += temp.length() + "_" + temp.lastModified(); + TLRPC.TL_video video = (TLRPC.TL_video)MessagesStorage.getInstance().getSentFile(originalPath, currentEncryptedChat == null ? 2 : 5); if (video == null) { Bitmap thumb = ThumbnailUtils.createVideoThumbnail(videoPath, MediaStore.Video.Thumbnails.MINI_KIND); TLRPC.PhotoSize size = FileLoader.scaleAndSaveImage(thumb, 90, 90, 55, currentEncryptedChat != null); @@ -1958,8 +1607,8 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa video = new TLRPC.TL_video(); video.thumb = size; video.caption = ""; + video.mime_type = "video/mp4"; video.id = 0; - File temp = new File(videoPath); if (temp != null && temp.exists()) { video.size = (int) temp.length(); } @@ -1978,12 +1627,13 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa video.path = videoPath; final TLRPC.TL_video videoFinal = video; + final String originalPathFinal = originalPath; Utilities.RunOnUIThread(new Runnable() { @Override public void run() { - MessagesController.getInstance().sendMessage(videoFinal, videoPath, dialog_id); + MessagesController.getInstance().sendMessage(videoFinal, originalPathFinal, dialog_id); if (chatListView != null) { - chatListView.setSelection(messages.size() + 1); + chatListView.setSelectionFromTop(messages.size() - 1, -100000 - chatListView.getPaddingTop()); } if (paused) { scrollToTopOnResume = true; @@ -2136,18 +1786,20 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa chatAdapter.notifyDataSetChanged(); if (positionToUnread && unreadMessageObject != null) { if (messages.get(messages.size() - 1) == unreadMessageObject) { - chatListView.setSelectionFromTop(0, Utilities.dp(-11)); + chatListView.setSelectionFromTop(0, AndroidUtilities.dp(-11)); } else { - chatListView.setSelectionFromTop(messages.size() - messages.indexOf(unreadMessageObject), Utilities.dp(-11)); + chatListView.setSelectionFromTop(messages.size() - messages.indexOf(unreadMessageObject), AndroidUtilities.dp(-11)); } ViewTreeObserver obs = chatListView.getViewTreeObserver(); obs.addOnPreDrawListener(new ViewTreeObserver.OnPreDrawListener() { @Override public boolean onPreDraw() { - if (messages.get(messages.size() - 1) == unreadMessageObject) { - chatListView.setSelectionFromTop(0, Utilities.dp(-11)); - } else { - chatListView.setSelectionFromTop(messages.size() - messages.indexOf(unreadMessageObject), Utilities.dp(-11)); + if (!messages.isEmpty()) { + if (messages.get(messages.size() - 1) == unreadMessageObject) { + chatListView.setSelectionFromTop(0, AndroidUtilities.dp(-11)); + } else { + chatListView.setSelectionFromTop(messages.size() - messages.indexOf(unreadMessageObject), AndroidUtilities.dp(-11)); + } } chatListView.getViewTreeObserver().removeOnPreDrawListener(this); return false; @@ -2212,9 +1864,6 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa if (chatListView != null) { chatListView.invalidateViews(); } - if (emojiView != null) { - emojiView.invalidateViews(); - } } else if (id == MessagesController.updateInterfaces) { int updateMask = (Integer)args[0]; if ((updateMask & MessagesController.UPDATE_MASK_NAME) != 0 || (updateMask & MessagesController.UPDATE_MASK_STATUS) != 0 || (updateMask & MessagesController.UPDATE_MASK_CHAT_NAME) != 0 || (updateMask & MessagesController.UPDATE_MASK_CHAT_MEMBERS) != 0) { @@ -2335,7 +1984,9 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa messages.add(0, dateObj); } if (!obj.isOut() && obj.messageOwner.unread) { - obj.messageOwner.unread = false; + if (!paused) { + obj.messageOwner.unread = false; + } markAsRead = true; } dayArray.add(0, obj); @@ -2392,9 +2043,6 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } } } else if (id == MessagesController.closeChats) { - if (messsageEditText != null && messsageEditText.isFocused()) { - Utilities.hideKeyboard(messsageEditText); - } removeSelfFromStack(); } else if (id == MessagesController.messagesReaded) { ArrayList markAsReadMessages = (ArrayList)args[0]; @@ -2491,7 +2139,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } else if (id == 997) { MessagesController.getInstance().sendMessage((Double) args[0], (Double) args[1], dialog_id); if (chatListView != null) { - chatListView.setSelection(messages.size() + 1); + chatListView.setSelectionFromTop(messages.size() - 1, -100000 - chatListView.getPaddingTop()); scrollToTopOnResume = true; } } else if (id == MessagesController.chatInfoDidLoaded) { @@ -2591,14 +2239,6 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } } } - } else if (id == MediaController.recordProgressChanged) { - Long time = (Long)args[0] / 1000; - String str = String.format("%02d:%02d", time / 60, time % 60); - if (lastTimeString == null || !lastPrintString.equals(str)) { - if (recordTimeText != null) { - recordTimeText.setText(str); - } - } } else if (id == MessagesController.removeAllMessagesFromDialog) { messages.clear(); messagesByDays.clear(); @@ -2622,16 +2262,6 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa selectedMessagesCanCopyIds.clear(); actionBarLayer.hideActionMode(); chatAdapter.notifyDataSetChanged(); - } else if (id == MediaController.recordStartError || id == MediaController.recordStopped) { - if (recordingAudio) { - recordingAudio = false; - updateAudioRecordIntefrace(); - } - } else if (id == MediaController.recordStarted) { - if (!recordingAudio) { - recordingAudio = true; - updateAudioRecordIntefrace(); - } } else if (id == MediaController.screenshotTook) { updateInformationForScreenshotDetector(); } @@ -2658,7 +2288,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa topPanel.setVisibility(View.GONE); } else { topPanel.setVisibility(View.VISIBLE); - topPanelText.setShadowLayer(1, 0, Utilities.dp(1), 0xff8797a3); + topPanelText.setShadowLayer(1, 0, AndroidUtilities.dp(1), 0xff8797a3); if (isCustomTheme) { topPlaneClose.setImageResource(R.drawable.ic_msg_btn_cross_custom); topPanel.setBackgroundResource(R.drawable.top_pane_custom); @@ -2701,7 +2331,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa return; } AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); - builder.setMessage(LocaleController.getString("AreYouSure", R.string.AreYouSure)); + builder.setMessage(LocaleController.getString("AreYouSureShareMyContactInfo", R.string.AreYouSureShareMyContactInfo)); builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), new DialogInterface.OnClickListener() { @Override @@ -2727,82 +2357,6 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } } - private void createEmojiPopup() { - if (getParentActivity() == null) { - return; - } - emojiView = new EmojiView(getParentActivity()); - emojiView.setListener(new EmojiView.Listener() { - public void onBackspace() { - messsageEditText.dispatchKeyEvent(new KeyEvent(0, 67)); - } - - public void onEmojiSelected(String paramAnonymousString) { - int i = messsageEditText.getSelectionEnd(); - CharSequence localCharSequence = Emoji.replaceEmoji(paramAnonymousString, messsageEditText.getPaint().getFontMetricsInt(), Utilities.dp(20)); - messsageEditText.setText(messsageEditText.getText().insert(i, localCharSequence)); - int j = i + localCharSequence.length(); - messsageEditText.setSelection(j, j); - } - }); - emojiPopup = new PopupWindow(emojiView); - } - - private void showEmojiPopup(boolean show) { - InputMethodManager localInputMethodManager = (InputMethodManager)ApplicationLoader.applicationContext.getSystemService(Context.INPUT_METHOD_SERVICE); - if (show) { - if (emojiPopup == null) { - createEmojiPopup(); - } - int currentHeight; - WindowManager manager = (WindowManager) ApplicationLoader.applicationContext.getSystemService(Activity.WINDOW_SERVICE); - int rotation = manager.getDefaultDisplay().getRotation(); - if (keyboardHeight <= 0) { - keyboardHeight = ApplicationLoader.applicationContext.getSharedPreferences("emoji", 0).getInt("kbd_height", Utilities.dp(200)); - } - if (keyboardHeightLand <= 0) { - keyboardHeightLand = ApplicationLoader.applicationContext.getSharedPreferences("emoji", 0).getInt("kbd_height_land3", Utilities.dp(200)); - } - if (rotation == Surface.ROTATION_270 || rotation == Surface.ROTATION_90) { - currentHeight = keyboardHeightLand; - } else { - currentHeight = keyboardHeight; - } - emojiPopup.setHeight(View.MeasureSpec.makeMeasureSpec(currentHeight, View.MeasureSpec.EXACTLY)); - emojiPopup.setWidth(View.MeasureSpec.makeMeasureSpec(contentView.getWidth(), View.MeasureSpec.EXACTLY)); - - emojiPopup.showAtLocation(getParentActivity().getWindow().getDecorView(), 83, 0, 0); - if (!keyboardVisible) { - contentView.setPadding(0, 0, 0, currentHeight); - emojiButton.setImageResource(R.drawable.ic_msg_panel_hide); - return; - } - emojiButton.setImageResource(R.drawable.ic_msg_panel_kb); - return; - } - if (emojiButton != null) { - emojiButton.setImageResource(R.drawable.ic_msg_panel_smiles); - } - if (emojiPopup != null) { - emojiPopup.dismiss(); - } - if (contentView != null) { - contentView.post(new Runnable() { - public void run() { - if (contentView != null) { - contentView.setPadding(0, 0, 0, 0); - } - } - }); - } - } - - public void hideEmojiPopup() { - if (emojiPopup != null && emojiPopup.isShowing()) { - showEmojiPopup(false); - } - } - @Override public void onResume() { super.onResume(); @@ -2811,15 +2365,15 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa if (chatAdapter != null) { chatAdapter.notifyDataSetChanged(); } - MessagesController.getInstance().openned_dialog_id = dialog_id; + NotificationsController.getInstance().setOpennedDialogId(dialog_id); if (scrollToTopOnResume) { if (scrollToTopUnReadOnResume && unreadMessageObject != null) { if (chatListView != null) { - chatListView.setSelectionFromTop(messages.size() - messages.indexOf(unreadMessageObject), -chatListView.getPaddingTop() - Utilities.dp(7)); + chatListView.setSelectionFromTop(messages.size() - messages.indexOf(unreadMessageObject), -chatListView.getPaddingTop() - AndroidUtilities.dp(7)); } } else { if (chatListView != null) { - chatListView.setSelection(messages.size() + 1); + chatListView.setSelectionFromTop(messages.size() - 1, -100000 - chatListView.getPaddingTop()); } } scrollToTopUnReadOnResume = false; @@ -2827,6 +2381,12 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } paused = false; if (readWhenResume && !messages.isEmpty()) { + for (MessageObject messageObject : messages) { + if (!messageObject.isUnread() && !messageObject.isFromMe()) { + break; + } + messageObject.messageOwner.unread = false; + } readWhenResume = false; MessagesController.getInstance().markDialogAsRead(dialog_id, messages.get(0).messageOwner.id, readWithMid, 0, readWithDate, true); } @@ -2838,21 +2398,9 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa SharedPreferences.Editor editor = preferences.edit(); editor.remove("dialog_" + dialog_id); editor.commit(); - ignoreTextChange = true; - messsageEditText.setText(lastMessageText); - messsageEditText.setSelection(messsageEditText.getText().length()); - ignoreTextChange = false; - } - if (messsageEditText != null) { - messsageEditText.postDelayed(new Runnable() { - @Override - public void run() { - if (messsageEditText != null) { - messsageEditText.requestFocus(); - } - } - }, 400); + chatActivityEnterView.setFieldText(lastMessageText); } + chatActivityEnterView.setFieldFocused(true); if (currentEncryptedChat != null) { chatEnterTime = System.currentTimeMillis(); chatLeaveTime = 0; @@ -2878,7 +2426,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa @Override public void onBeginSlide() { super.onBeginSlide(); - hideEmojiPopup(); + chatActivityEnterView.hideEmojiPopup(); } private void setTypingAnimation(boolean start) { @@ -2888,9 +2436,9 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa if (start) { try { if (currentChat != null) { - actionBarLayer.setSubTitleIcon(R.drawable.typing_dots_chat, Utilities.dp(4)); + actionBarLayer.setSubTitleIcon(R.drawable.typing_dots_chat, AndroidUtilities.dp(4)); } else { - actionBarLayer.setSubTitleIcon(R.drawable.typing_dots, Utilities.dp(4)); + actionBarLayer.setSubTitleIcon(R.drawable.typing_dots, AndroidUtilities.dp(4)); } AnimationDrawable mAnim = (AnimationDrawable)actionBarLayer.getSubTitleIcon(); mAnim.setAlpha(200); @@ -2907,21 +2455,24 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa public void onPause() { super.onPause(); actionBarLayer.hideActionMode(); - hideEmojiPopup(); + chatActivityEnterView.hideEmojiPopup(); paused = true; - MessagesController.getInstance().openned_dialog_id = 0; + NotificationsController.getInstance().setOpennedDialogId(0); - if (messsageEditText != null && messsageEditText.length() != 0) { + String text = chatActivityEnterView.getFieldText(); + if (text != null) { SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("mainconfig", Activity.MODE_PRIVATE); SharedPreferences.Editor editor = preferences.edit(); - editor.putString("dialog_" + dialog_id, messsageEditText.getText().toString()); + editor.putString("dialog_" + dialog_id, text); editor.commit(); } - if (currentEncryptedChat != null) { + chatActivityEnterView.setFieldFocused(false); + + /*if (currentEncryptedChat != null) { disabled chatLeaveTime = System.currentTimeMillis(); updateInformationForScreenshotDetector(); - } + }*/ } private void updateInformationForScreenshotDetector() { @@ -2961,9 +2512,9 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa if (getParentActivity() == null) { return true; } - int height = Utilities.dp(48); + int height = AndroidUtilities.dp(48); if (!Utilities.isTablet(getParentActivity()) && getParentActivity().getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { - height = Utilities.dp(40); + height = AndroidUtilities.dp(40); selectedMessagesCountTextView.setTextSize(16); } else { selectedMessagesCountTextView.setTextSize(18); @@ -3033,7 +2584,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa selectedMessagesCanCopyIds.clear(); selectedMessagesIds.clear(); - if (single || type < 2) { + if (single || type < 2 || type == 6) { if (type >= 0) { selectedObject = message; if (getParentActivity() == null) { @@ -3043,35 +2594,35 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa CharSequence[] items = null; - if (currentEncryptedChat == null) { - if (type == 0) { - items = new CharSequence[] {LocaleController.getString("Retry", R.string.Retry), LocaleController.getString("Delete", R.string.Delete)}; - } else if (type == 1) { - items = new CharSequence[] {LocaleController.getString("Delete", R.string.Delete)}; - } else if (type == 2) { - items = new CharSequence[] {LocaleController.getString("Forward", R.string.Forward), LocaleController.getString("Delete", R.string.Delete)}; - } else if (type == 3) { - items = new CharSequence[] {LocaleController.getString("Forward", R.string.Forward), LocaleController.getString("Copy", R.string.Copy), LocaleController.getString("Delete", R.string.Delete)}; - } else if (type == 4) { - items = new CharSequence[] {LocaleController.getString(selectedObject.messageOwner.media instanceof TLRPC.TL_messageMediaDocument ? "SaveToDownloads" : "SaveToGallery", - selectedObject.messageOwner.media instanceof TLRPC.TL_messageMediaDocument ? R.string.SaveToDownloads : R.string.SaveToGallery), LocaleController.getString("Forward", R.string.Forward), LocaleController.getString("Delete", R.string.Delete)}; - } else if (type == 5) { - items = new CharSequence[] {LocaleController.getString("ApplyLocalizationFile", R.string.ApplyLocalizationFile), LocaleController.getString("SaveToDownloads", R.string.SaveToDownloads), LocaleController.getString("Forward", R.string.Forward), LocaleController.getString("Delete", R.string.Delete)}; - } + if (type == 0) { + items = new CharSequence[] {LocaleController.getString("Retry", R.string.Retry), LocaleController.getString("Delete", R.string.Delete)}; + } else if (type == 1) { + items = new CharSequence[] {LocaleController.getString("Delete", R.string.Delete)}; + } else if (type == 6) { + items = new CharSequence[] {LocaleController.getString("Retry", R.string.Retry), LocaleController.getString("Copy", R.string.Copy), LocaleController.getString("Delete", R.string.Delete)}; } else { - if (type == 0) { - items = new CharSequence[] {LocaleController.getString("Retry", R.string.Retry), LocaleController.getString("Delete", R.string.Delete)}; - } else if (type == 1) { - items = new CharSequence[] {LocaleController.getString("Delete", R.string.Delete)}; - } else if (type == 2) { - items = new CharSequence[] {LocaleController.getString("Delete", R.string.Delete)}; - } else if (type == 3) { - items = new CharSequence[] {LocaleController.getString("Copy", R.string.Copy), LocaleController.getString("Delete", R.string.Delete)}; - } else if (type == 4) { - items = new CharSequence[] {LocaleController.getString(selectedObject.messageOwner.media instanceof TLRPC.TL_messageMediaDocument ? "SaveToDownloads" : "SaveToGallery", - selectedObject.messageOwner.media instanceof TLRPC.TL_messageMediaDocument ? R.string.SaveToDownloads : R.string.SaveToGallery), LocaleController.getString("Delete", R.string.Delete)}; - } else if (type == 5) { - items = new CharSequence[] {LocaleController.getString("ApplyLocalizationFile", R.string.ApplyLocalizationFile), LocaleController.getString("Delete", R.string.Delete)}; + if (currentEncryptedChat == null) { + if (type == 2) { + items = new CharSequence[]{LocaleController.getString("Forward", R.string.Forward), LocaleController.getString("Delete", R.string.Delete)}; + } else if (type == 3) { + items = new CharSequence[]{LocaleController.getString("Forward", R.string.Forward), LocaleController.getString("Copy", R.string.Copy), LocaleController.getString("Delete", R.string.Delete)}; + } else if (type == 4) { + items = new CharSequence[]{LocaleController.getString(selectedObject.messageOwner.media instanceof TLRPC.TL_messageMediaDocument ? "SaveToDownloads" : "SaveToGallery", + selectedObject.messageOwner.media instanceof TLRPC.TL_messageMediaDocument ? R.string.SaveToDownloads : R.string.SaveToGallery), LocaleController.getString("Forward", R.string.Forward), LocaleController.getString("Delete", R.string.Delete)}; + } else if (type == 5) { + items = new CharSequence[]{LocaleController.getString("ApplyLocalizationFile", R.string.ApplyLocalizationFile), LocaleController.getString("SaveToDownloads", R.string.SaveToDownloads), LocaleController.getString("Forward", R.string.Forward), LocaleController.getString("Delete", R.string.Delete)}; + } + } else { + if (type == 2) { + items = new CharSequence[]{LocaleController.getString("Delete", R.string.Delete)}; + } else if (type == 3) { + items = new CharSequence[]{LocaleController.getString("Copy", R.string.Copy), LocaleController.getString("Delete", R.string.Delete)}; + } else if (type == 4) { + items = new CharSequence[]{LocaleController.getString(selectedObject.messageOwner.media instanceof TLRPC.TL_messageMediaDocument ? "SaveToDownloads" : "SaveToGallery", + selectedObject.messageOwner.media instanceof TLRPC.TL_messageMediaDocument ? R.string.SaveToDownloads : R.string.SaveToGallery), LocaleController.getString("Delete", R.string.Delete)}; + } else if (type == 5) { + items = new CharSequence[]{LocaleController.getString("ApplyLocalizationFile", R.string.ApplyLocalizationFile), LocaleController.getString("Delete", R.string.Delete)}; + } } } @@ -3118,14 +2669,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } else if (type == 4) { if (currentEncryptedChat == null) { if (i == 0) { - String fileName = selectedObject.getFileName(); - if (selectedObject.type == 3) { - MediaController.saveFile(fileName, selectedObject.messageOwner.attachPath, getParentActivity(), 1, null); - } else if (selectedObject.type == 1) { - MediaController.saveFile(fileName, selectedObject.messageOwner.attachPath, getParentActivity(), 0, null); - } else if (selectedObject.type == 8 || selectedObject.type == 9) { - MediaController.saveFile(fileName, selectedObject.messageOwner.attachPath, getParentActivity(), 2, selectedObject.messageOwner.media.document.file_name); - } + processSelectedOption(4); } else if (i == 1) { processSelectedOption(2); } else if (i == 2) { @@ -3139,54 +2683,30 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } } } else if (type == 5) { - if (currentEncryptedChat == null) { - if (i == 1) { - String fileName = selectedObject.getFileName(); - if (selectedObject.type == 3) { - MediaController.saveFile(fileName, selectedObject.messageOwner.attachPath, getParentActivity(), 1, null); - } else if (selectedObject.type == 1) { - MediaController.saveFile(fileName, selectedObject.messageOwner.attachPath, getParentActivity(), 0, null); - } else if (selectedObject.type == 8 || selectedObject.type == 9) { - MediaController.saveFile(fileName, selectedObject.messageOwner.attachPath, getParentActivity(), 2, selectedObject.messageOwner.media.document.file_name); - } - } else if (i == 2) { - processSelectedOption(2); - } else if (i == 3) { - processSelectedOption(1); - } + if (i == 0) { + processSelectedOption(5); } else { - if (i == 1) { - processSelectedOption(1); + if (currentEncryptedChat == null) { + if (i == 1) { + processSelectedOption(4); + } else if (i == 2) { + processSelectedOption(2); + } else if (i == 3) { + processSelectedOption(1); + } + } else { + if (i == 1) { + processSelectedOption(1); + } } } + } else if (type == 6) { if (i == 0) { - File locFile = null; - if (selectedObject.messageOwner.attachPath != null && selectedObject.messageOwner.attachPath.length() != 0) { - File f = new File(selectedObject.messageOwner.attachPath); - if (f.exists()) { - locFile = f; - } - } - if (locFile == null) { - File f = new File(Utilities.getCacheDir(), selectedObject.getFileName()); - if (f.exists()) { - locFile = f; - } - } - if (locFile != null) { - if (LocaleController.getInstance().applyLanguageFile(locFile)) { - presentFragment(new LanguageSelectActivity()); - } else { - if (getParentActivity() == null) { - return; - } - AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); - builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); - builder.setMessage(LocaleController.getString("IncorrectLocalization", R.string.IncorrectLocalization)); - builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), null); - showAlertDialog(builder); - } - } + processSelectedOption(0); + } else if (i == 1) { + processSelectedOption(3); + } else if (i == 2) { + processSelectedOption(1); } } } @@ -3204,8 +2724,11 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } private void processSelectedOption(int option) { + if (selectedObject == null) { + return; + } if (option == 0) { - if (selectedObject != null && selectedObject.messageOwner.id < 0) { + if (selectedObject.messageOwner.id < 0) { if (selectedObject.type == 0) { if (selectedObject.messageOwner instanceof TLRPC.TL_messageForwarded) { MessagesController.getInstance().sendMessage(selectedObject, dialog_id); @@ -3249,47 +2772,75 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa random_ids.add(selectedObject.messageOwner.random_id); } MessagesController.getInstance().deleteMessages(arr, random_ids, currentEncryptedChat); - chatListView.setSelection(messages.size() + 1); + chatListView.setSelectionFromTop(messages.size() - 1, -100000 - chatListView.getPaddingTop()); } } else if (option == 1) { - if (selectedObject != null) { - ArrayList ids = new ArrayList(); - ids.add(selectedObject.messageOwner.id); - removeUnreadPlane(true); - ArrayList random_ids = null; - if (currentEncryptedChat != null && selectedObject.messageOwner.random_id != 0 && selectedObject.type != 10) { - random_ids = new ArrayList(); - random_ids.add(selectedObject.messageOwner.random_id); - } - MessagesController.getInstance().deleteMessages(ids, random_ids, currentEncryptedChat); - selectedObject = null; + ArrayList ids = new ArrayList(); + ids.add(selectedObject.messageOwner.id); + removeUnreadPlane(true); + ArrayList random_ids = null; + if (currentEncryptedChat != null && selectedObject.messageOwner.random_id != 0 && selectedObject.type != 10) { + random_ids = new ArrayList(); + random_ids.add(selectedObject.messageOwner.random_id); } + MessagesController.getInstance().deleteMessages(ids, random_ids, currentEncryptedChat); } else if (option == 2) { - if (selectedObject != null) { - forwaringMessage = selectedObject; - selectedObject = null; - - Bundle args = new Bundle(); - args.putBoolean("onlySelect", true); - args.putBoolean("serverOnly", true); - args.putString("selectAlertString", LocaleController.getString("ForwardMessagesTo", R.string.ForwardMessagesTo)); - MessagesActivity fragment = new MessagesActivity(args); - fragment.setDelegate(this); - presentFragment(fragment); - } + forwaringMessage = selectedObject; + Bundle args = new Bundle(); + args.putBoolean("onlySelect", true); + args.putBoolean("serverOnly", true); + args.putString("selectAlertString", LocaleController.getString("ForwardMessagesTo", R.string.ForwardMessagesTo)); + MessagesActivity fragment = new MessagesActivity(args); + fragment.setDelegate(this); + presentFragment(fragment); } else if (option == 3) { - if (selectedObject != null) { - if(android.os.Build.VERSION.SDK_INT < 11) { - android.text.ClipboardManager clipboard = (android.text.ClipboardManager)ApplicationLoader.applicationContext.getSystemService(Context.CLIPBOARD_SERVICE); - clipboard.setText(selectedObject.messageText); - } else { - android.content.ClipboardManager clipboard = (android.content.ClipboardManager)ApplicationLoader.applicationContext.getSystemService(Context.CLIPBOARD_SERVICE); - android.content.ClipData clip = android.content.ClipData.newPlainText("label", selectedObject.messageText); - clipboard.setPrimaryClip(clip); + if(android.os.Build.VERSION.SDK_INT < 11) { + android.text.ClipboardManager clipboard = (android.text.ClipboardManager)ApplicationLoader.applicationContext.getSystemService(Context.CLIPBOARD_SERVICE); + clipboard.setText(selectedObject.messageText); + } else { + android.content.ClipboardManager clipboard = (android.content.ClipboardManager)ApplicationLoader.applicationContext.getSystemService(Context.CLIPBOARD_SERVICE); + android.content.ClipData clip = android.content.ClipData.newPlainText("label", selectedObject.messageText); + clipboard.setPrimaryClip(clip); + } + } else if (option == 4) { + String fileName = selectedObject.getFileName(); + if (selectedObject.type == 3) { + MediaController.saveFile(fileName, selectedObject.messageOwner.attachPath, getParentActivity(), 1, null); + } else if (selectedObject.type == 1) { + MediaController.saveFile(fileName, selectedObject.messageOwner.attachPath, getParentActivity(), 0, null); + } else if (selectedObject.type == 8 || selectedObject.type == 9) { + MediaController.saveFile(fileName, selectedObject.messageOwner.attachPath, getParentActivity(), 2, selectedObject.messageOwner.media.document.file_name); + } + } else if (option == 5) { + File locFile = null; + if (selectedObject.messageOwner.attachPath != null && selectedObject.messageOwner.attachPath.length() != 0) { + File f = new File(selectedObject.messageOwner.attachPath); + if (f.exists()) { + locFile = f; + } + } + if (locFile == null) { + File f = new File(AndroidUtilities.getCacheDir(), selectedObject.getFileName()); + if (f.exists()) { + locFile = f; + } + } + if (locFile != null) { + if (LocaleController.getInstance().applyLanguageFile(locFile)) { + presentFragment(new LanguageSelectActivity()); + } else { + if (getParentActivity() == null) { + return; + } + AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); + builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); + builder.setMessage(LocaleController.getString("IncorrectLocalization", R.string.IncorrectLocalization)); + builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), null); + showAlertDialog(builder); } - selectedObject = null; } } + selectedObject = null; } @Override @@ -3309,14 +2860,75 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } } + private void processForwardFromMe(MessageObject messageObject, long did) { + if (messageObject == null) { + return; + } + if (messageObject.messageOwner.media != null && !(messageObject.messageOwner.media instanceof TLRPC.TL_messageMediaEmpty)) { + if (messageObject.messageOwner.media.photo instanceof TLRPC.TL_photo) { + MessagesController.getInstance().sendMessage((TLRPC.TL_photo) messageObject.messageOwner.media.photo, null, did); + } else if (messageObject.messageOwner.media.audio instanceof TLRPC.TL_audio) { + messageObject.messageOwner.media.audio.path = messageObject.messageOwner.attachPath; + MessagesController.getInstance().sendMessage((TLRPC.TL_audio)messageObject.messageOwner.media.audio, did); + } else if (messageObject.messageOwner.media.video instanceof TLRPC.TL_video) { + messageObject.messageOwner.media.video.path = messageObject.messageOwner.attachPath; + MessagesController.getInstance().sendMessage((TLRPC.TL_video)messageObject.messageOwner.media.video, null, did); + } else if (messageObject.messageOwner.media.document instanceof TLRPC.TL_document) { + messageObject.messageOwner.media.document.path = messageObject.messageOwner.attachPath; + MessagesController.getInstance().sendMessage((TLRPC.TL_document)messageObject.messageOwner.media.document, null, did); + } else if (messageObject.messageOwner.media.geo instanceof TLRPC.TL_geoPoint) { + MessagesController.getInstance().sendMessage(messageObject.messageOwner.media.geo.lat, messageObject.messageOwner.media.geo._long, did); + } else if (messageObject.messageOwner.media.phone_number != null) { + TLRPC.User user = new TLRPC.TL_userContact(); + user.phone = messageObject.messageOwner.media.phone_number; + user.first_name = messageObject.messageOwner.media.first_name; + user.last_name = messageObject.messageOwner.media.last_name; + user.id = messageObject.messageOwner.media.user_id; + MessagesController.getInstance().sendMessage(user, did); + } else { + MessagesController.getInstance().sendMessage(messageObject, did); + } + } else if (messageObject.messageOwner.message != null) { + MessagesController.getInstance().sendMessage(messageObject.messageOwner.message, did); + } else { + MessagesController.getInstance().sendMessage(messageObject, did); + } + } + + private void forwardSelectedMessages(long did, boolean fromMyName) { + if (forwaringMessage != null) { + if (forwaringMessage.messageOwner.id > 0) { + if (!fromMyName) { + MessagesController.getInstance().sendMessage(forwaringMessage, did); + } else { + processForwardFromMe(forwaringMessage, did); + } + } + forwaringMessage = null; + } else { + ArrayList ids = new ArrayList(selectedMessagesIds.keySet()); + Collections.sort(ids); + for (Integer id : ids) { + if (id > 0) { + if (!fromMyName) { + MessagesController.getInstance().sendMessage(selectedMessagesIds.get(id), did); + } else { + processForwardFromMe(selectedMessagesIds.get(id), did); + } + } + } + selectedMessagesCanCopyIds.clear(); + selectedMessagesIds.clear(); + } + } + @Override - public void didSelectDialog(MessagesActivity activity, long did) { + public void didSelectDialog(MessagesActivity activity, long did, boolean param) { if (dialog_id != 0 && (forwaringMessage != null || !selectedMessagesIds.isEmpty())) { + if (did != dialog_id) { int lower_part = (int)did; if (lower_part != 0) { - activity.removeSelfFromStack(); - Bundle args = new Bundle(); args.putBoolean("scrollToTopOnResume", scrollToTopOnResume); if (lower_part > 0) { @@ -3324,48 +2936,16 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } else if (lower_part < 0) { args.putInt("chat_id", -lower_part); } - presentFragment(new ChatActivity(args)); - + presentFragment(new ChatActivity(args), true); removeSelfFromStack(); - if (forwaringMessage != null) { - if (forwaringMessage.messageOwner.id > 0) { - MessagesController.getInstance().sendMessage(forwaringMessage, did); - } - forwaringMessage = null; - } else { - ArrayList ids = new ArrayList(selectedMessagesIds.keySet()); - Collections.sort(ids); - for (Integer id : ids) { - if (id > 0) { - MessagesController.getInstance().sendMessage(selectedMessagesIds.get(id), did); - } - } - selectedMessagesCanCopyIds.clear(); - selectedMessagesIds.clear(); - } + forwardSelectedMessages(did, param); } else { activity.finishFragment(); } } else { activity.finishFragment(); - if (forwaringMessage != null) { - MessagesController.getInstance().sendMessage(forwaringMessage, did); - forwaringMessage = null; - } else { - ArrayList ids = new ArrayList(selectedMessagesIds.keySet()); - Collections.sort(ids, new Comparator() { - @Override - public int compare(Integer lhs, Integer rhs) { - return lhs.compareTo(rhs); - } - }); - for (Integer id : ids) { - MessagesController.getInstance().sendMessage(selectedMessagesIds.get(id), did); - } - selectedMessagesCanCopyIds.clear(); - selectedMessagesIds.clear(); - } - chatListView.setSelection(messages.size() + 1); + forwardSelectedMessages(did, param); + chatListView.setSelectionFromTop(messages.size() - 1, -100000 - chatListView.getPaddingTop()); scrollToTopOnResume = true; } } @@ -3379,8 +2959,8 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa actionBarLayer.hideActionMode(); updateVisibleRows(); return false; - } else if (emojiPopup != null && emojiPopup.isShowing()) { - hideEmojiPopup(); + } else if (chatActivityEnterView.isEmojiPopupShowing()) { + chatActivityEnterView.hideEmojiPopup(); return false; } return true; @@ -3469,16 +3049,16 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa if (!disableSelection) { if (messageType == 12) { holder.chatBubbleView.setBackgroundResource(R.drawable.chat_outgoing_text_states); - holder.chatBubbleView.setPadding(Utilities.dp(6), Utilities.dp(6), Utilities.dp(18), 0); + holder.chatBubbleView.setPadding(AndroidUtilities.dp(6), AndroidUtilities.dp(6), AndroidUtilities.dp(18), 0); } else if (messageType == 13) { holder.chatBubbleView.setBackgroundResource(R.drawable.chat_incoming_text_states); - holder.chatBubbleView.setPadding(Utilities.dp(15), Utilities.dp(6), Utilities.dp(9), 0); + holder.chatBubbleView.setPadding(AndroidUtilities.dp(15), AndroidUtilities.dp(6), AndroidUtilities.dp(9), 0); } else if (messageType == 8) { holder.chatBubbleView.setBackgroundResource(R.drawable.chat_outgoing_text_states); - holder.chatBubbleView.setPadding(Utilities.dp(9), Utilities.dp(9), Utilities.dp(18), 0); + holder.chatBubbleView.setPadding(AndroidUtilities.dp(9), AndroidUtilities.dp(9), AndroidUtilities.dp(18), 0); } else if (messageType == 9) { holder.chatBubbleView.setBackgroundResource(R.drawable.chat_incoming_text_states); - holder.chatBubbleView.setPadding(Utilities.dp(18), Utilities.dp(9), Utilities.dp(9), 0); + holder.chatBubbleView.setPadding(AndroidUtilities.dp(18), AndroidUtilities.dp(9), AndroidUtilities.dp(9), 0); } } else { if (messageType == 12) { @@ -3487,28 +3067,28 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } else { holder.chatBubbleView.setBackgroundResource(R.drawable.msg_out); } - holder.chatBubbleView.setPadding(Utilities.dp(6), Utilities.dp(6), Utilities.dp(18), 0); + holder.chatBubbleView.setPadding(AndroidUtilities.dp(6), AndroidUtilities.dp(6), AndroidUtilities.dp(18), 0); } else if (messageType == 13) { if (selected) { holder.chatBubbleView.setBackgroundResource(R.drawable.msg_in_selected); } else { holder.chatBubbleView.setBackgroundResource(R.drawable.msg_in); } - holder.chatBubbleView.setPadding(Utilities.dp(15), Utilities.dp(6), Utilities.dp(9), 0); + holder.chatBubbleView.setPadding(AndroidUtilities.dp(15), AndroidUtilities.dp(6), AndroidUtilities.dp(9), 0); } else if (messageType == 8) { if (selected) { holder.chatBubbleView.setBackgroundResource(R.drawable.msg_out_selected); } else { holder.chatBubbleView.setBackgroundResource(R.drawable.msg_out); } - holder.chatBubbleView.setPadding(Utilities.dp(9), Utilities.dp(9), Utilities.dp(18), 0); + holder.chatBubbleView.setPadding(AndroidUtilities.dp(9), AndroidUtilities.dp(9), AndroidUtilities.dp(18), 0); } else if (messageType == 9) { if (selected) { holder.chatBubbleView.setBackgroundResource(R.drawable.msg_in_selected); } else { holder.chatBubbleView.setBackgroundResource(R.drawable.msg_in); } - holder.chatBubbleView.setPadding(Utilities.dp(18), Utilities.dp(9), Utilities.dp(9), 0); + holder.chatBubbleView.setPadding(AndroidUtilities.dp(18), AndroidUtilities.dp(9), AndroidUtilities.dp(9), 0); } } } @@ -3563,7 +3143,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa view.getLocationInWindow(coords); PhotoViewer.PlaceProviderObject object = new PhotoViewer.PlaceProviderObject(); object.viewX = coords[0]; - object.viewY = coords[1] - Utilities.statusBarHeight; + object.viewY = coords[1] - AndroidUtilities.statusBarHeight; object.parentView = chatListView; object.imageReceiver = imageReceiver; object.thumb = object.imageReceiver.getBitmap(); @@ -3738,7 +3318,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa @Override public boolean canPerformActions() { - return !actionBarLayer.isActionModeShowed(); + return actionBarLayer != null && !actionBarLayer.isActionModeShowed(); } }; if (view instanceof ChatMediaCell) { @@ -3753,6 +3333,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa return; } if (message.type == 1) { + PhotoViewer.getInstance().setParentActivity(getParentActivity()); PhotoViewer.getInstance().openPhoto(message, ChatActivity.this); } else if (message.type == 3) { try { @@ -3761,7 +3342,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa f = new File(message.messageOwner.attachPath); } if (f == null || f != null && !f.exists()) { - f = new File(Utilities.getCacheDir(), message.getFileName()); + f = new File(AndroidUtilities.getCacheDir(), message.getFileName()); } Intent intent = new Intent(Intent.ACTION_VIEW); intent.setDataAndType(Uri.fromFile(f), "video/mp4"); @@ -3890,7 +3471,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } if (type == 11 || type == 10) { - int width = Utilities.displaySize.x - Utilities.dp(30); + int width = AndroidUtilities.displaySize.x - AndroidUtilities.dp(30); messageTextView.setText(message.messageText); messageTextView.setMaxWidth(width); @@ -3898,7 +3479,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa if (message.messageOwner.action instanceof TLRPC.TL_messageActionUserUpdatedPhoto) { photoImage.setImage(message.messageOwner.action.newUserPhoto.photo_small, "50_50", Utilities.getUserAvatarForId(currentUser.id)); } else { - PhotoObject photo = PhotoObject.getClosestImageWithSize(message.photoThumbs, Utilities.dp(64), Utilities.dp(64)); + PhotoObject photo = PhotoObject.getClosestImageWithSize(message.photoThumbs, AndroidUtilities.dp(64), AndroidUtilities.dp(64)); if (photo != null) { if (photo.image != null) { photoImage.setImageBitmap(photo.image); @@ -3952,11 +3533,8 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa addContactView.setVisibility(View.GONE); } } else if (type == 7) { - if (unread_to_load == 1) { - messageTextView.setText(LocaleController.formatString("OneNewMessage", R.string.OneNewMessage, unread_to_load)); - } else { - messageTextView.setText(LocaleController.formatString("FewNewMessages", R.string.FewNewMessages, unread_to_load)); - } + messageTextView.setTextSize(16); + messageTextView.setText(LocaleController.formatPluralString("NewMessages", unread_to_load)); } else if (type == 8 || type == 9) { TLRPC.Document document = message.messageOwner.media.document; if (document instanceof TLRPC.TL_document || document instanceof TLRPC.TL_documentEncrypted) { @@ -4093,7 +3671,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } if (load && message.messageOwner.attachPath != null && message.messageOwner.attachPath.length() != 0 || !load && (message.messageOwner.attachPath == null || message.messageOwner.attachPath.length() == 0)) { File cacheFile = null; - if ((cacheFile = new File(Utilities.getCacheDir(), fileName)).exists()) { + if ((cacheFile = new File(AndroidUtilities.getCacheDir(), fileName)).exists()) { if (actionAttachButton != null) { actionAttachButton.setVisibility(View.VISIBLE); if (message.type == 8 || message.type == 9) { @@ -4141,15 +3719,15 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa int width; if (currentChat != null && type != 8) { if (actionView.getVisibility() == View.VISIBLE) { - width = Utilities.displaySize.x - Utilities.dp(290); + width = AndroidUtilities.displaySize.x - AndroidUtilities.dp(290); } else { - width = Utilities.displaySize.x - Utilities.dp(270); + width = AndroidUtilities.displaySize.x - AndroidUtilities.dp(270); } } else { if (actionView.getVisibility() == View.VISIBLE) { - width = Utilities.displaySize.x - Utilities.dp(240); + width = AndroidUtilities.displaySize.x - AndroidUtilities.dp(240); } else { - width = Utilities.displaySize.x - Utilities.dp(220); + width = AndroidUtilities.displaySize.x - AndroidUtilities.dp(220); } } nameTextView.setMaxWidth(width); @@ -4385,6 +3963,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa } if (message != null) { if (message.type == 11) { + PhotoViewer.getInstance().setParentActivity(getParentActivity()); PhotoViewer.getInstance().openPhoto(message, ChatActivity.this); } else if (message.type == 8 || message.type == 9) { File f = null; @@ -4393,7 +3972,7 @@ public class ChatActivity extends BaseFragment implements SizeNotifierRelativeLa f = new File(message.messageOwner.attachPath); } if (f == null || f != null && !f.exists()) { - f = new File(Utilities.getCacheDir(), fileName); + f = new File(AndroidUtilities.getCacheDir(), fileName); } if (f != null && f.exists()) { String realMimeType = null; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/ChatProfileActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/ChatProfileActivity.java index 21dff9963..115c41405 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/ChatProfileActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/ChatProfileActivity.java @@ -11,6 +11,7 @@ package org.telegram.ui; import android.app.AlertDialog; import android.content.Context; import android.content.DialogInterface; +import android.content.Intent; import android.graphics.Typeface; import android.os.Bundle; import android.text.Html; @@ -22,12 +23,13 @@ import android.widget.ImageButton; import android.widget.ListView; import android.widget.TextView; -import org.telegram.messenger.LocaleController; -import org.telegram.messenger.MessagesStorage; +import org.telegram.android.AndroidUtilities; +import org.telegram.android.LocaleController; +import org.telegram.android.MessagesStorage; import org.telegram.messenger.TLRPC; import org.telegram.messenger.ConnectionsManager; import org.telegram.messenger.FileLog; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.UserConfig; @@ -256,8 +258,13 @@ public class ChatProfileActivity extends BaseFragment implements NotificationCen } @Override - public void didSelectContact(TLRPC.User user) { - MessagesController.getInstance().addUserToChat(chat_id, user, info); + public void didSelectContact(TLRPC.User user, String param) { + MessagesController.getInstance().addUserToChat(chat_id, user, info, Utilities.parseInt(param)); + } + + @Override + public void onActivityResultFragment(int requestCode, int resultCode, Intent data) { + avatarUpdater.onActivityResult(requestCode, resultCode, data); } @Override @@ -293,7 +300,7 @@ public class ChatProfileActivity extends BaseFragment implements NotificationCen avatarImage.getLocationInWindow(coords); PhotoViewer.PlaceProviderObject object = new PhotoViewer.PlaceProviderObject(); object.viewX = coords[0]; - object.viewY = coords[1] - Utilities.statusBarHeight; + object.viewY = coords[1] - AndroidUtilities.statusBarHeight; object.parentView = listView; object.imageReceiver = avatarImage.imageReceiver; object.thumb = object.imageReceiver.getBitmap(); @@ -436,6 +443,7 @@ public class ChatProfileActivity extends BaseFragment implements NotificationCen if (action == 0) { TLRPC.Chat chat = MessagesController.getInstance().chats.get(chat_id); if (chat.photo != null && chat.photo.photo_big != null) { + PhotoViewer.getInstance().setParentActivity(getParentActivity()); PhotoViewer.getInstance().openPhoto(chat.photo.photo_big, this); } } else if (action == 1) { @@ -590,15 +598,15 @@ public class ChatProfileActivity extends BaseFragment implements NotificationCen avatarImage = (BackupImageView)view.findViewById(R.id.settings_avatar_image); avatarImage.processDetach = false; TextView textView = (TextView)view.findViewById(R.id.settings_name); - Typeface typeface = Utilities.getTypeface("fonts/rmedium.ttf"); + Typeface typeface = AndroidUtilities.getTypeface("fonts/rmedium.ttf"); textView.setTypeface(typeface); textView.setText(chat.title); if (chat.participants_count != 0 && onlineCount > 0) { - onlineText.setText(Html.fromHtml(String.format("%d %s, %d %s", chat.participants_count, LocaleController.getString("Members", R.string.Members), onlineCount, LocaleController.getString("Online", R.string.Online)))); + onlineText.setText(Html.fromHtml(String.format("%s, %d %s", LocaleController.formatPluralString("Members", chat.participants_count), onlineCount, LocaleController.getString("Online", R.string.Online)))); } else { - onlineText.setText(String.format("%d %s", chat.participants_count, LocaleController.getString("Members", R.string.Members))); + onlineText.setText(LocaleController.formatPluralString("Members", chat.participants_count)); } TLRPC.FileLocation photo = null; @@ -622,7 +630,7 @@ public class ChatProfileActivity extends BaseFragment implements NotificationCen textView.setText(LocaleController.getString("SHAREDMEDIA", R.string.SHAREDMEDIA)); } else if (i == membersSectionRow) { TLRPC.Chat chat = MessagesController.getInstance().chats.get(chat_id); - textView.setText(String.format("%d %s", chat.participants_count, LocaleController.getString("MEMBERS", R.string.MEMBERS))); + textView.setText(LocaleController.formatPluralString("Members", chat.participants_count).toUpperCase()); } } else if (type == 2) { if (view == null) { @@ -672,7 +680,7 @@ public class ChatProfileActivity extends BaseFragment implements NotificationCen return; } AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); - builder.setMessage(LocaleController.getString("AreYouSure", R.string.AreYouSure)); + builder.setMessage(LocaleController.getString("AreYouSureDeleteAndExit", R.string.AreYouSureDeleteAndExit)); builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), new DialogInterface.OnClickListener() { @Override diff --git a/TMessagesProj/src/main/java/org/telegram/ui/ChatProfileChangeNameActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/ChatProfileChangeNameActivity.java index 1902d8fb2..2b204a9dd 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/ChatProfileChangeNameActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/ChatProfileChangeNameActivity.java @@ -20,11 +20,11 @@ import android.widget.Button; import android.widget.EditText; import android.widget.TextView; -import org.telegram.messenger.LocaleController; +import org.telegram.android.AndroidUtilities; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLRPC; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.R; -import org.telegram.messenger.Utilities; import org.telegram.ui.Views.ActionBar.BaseFragment; public class ChatProfileChangeNameActivity extends BaseFragment { @@ -108,14 +108,14 @@ public class ChatProfileChangeNameActivity extends BaseFragment { boolean animations = preferences.getBoolean("view_animations", true); if (!animations) { firstNameField.requestFocus(); - Utilities.showKeyboard(firstNameField); + AndroidUtilities.showKeyboard(firstNameField); } } @Override public void onOpenAnimationEnd() { firstNameField.requestFocus(); - Utilities.showKeyboard(firstNameField); + AndroidUtilities.showKeyboard(firstNameField); } private void saveName() { diff --git a/TMessagesProj/src/main/java/org/telegram/ui/ContactAddActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/ContactAddActivity.java index b0ff3c5c5..3ffe51631 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/ContactAddActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/ContactAddActivity.java @@ -21,11 +21,12 @@ import android.widget.Button; import android.widget.EditText; import android.widget.TextView; +import org.telegram.android.AndroidUtilities; import org.telegram.PhoneFormat.PhoneFormat; -import org.telegram.messenger.ContactsController; -import org.telegram.messenger.LocaleController; +import org.telegram.android.ContactsController; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLRPC; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; @@ -104,7 +105,7 @@ public class ContactAddActivity extends BaseFragment implements NotificationCent avatarImage = (BackupImageView)fragmentView.findViewById(R.id.settings_avatar_image); avatarImage.processDetach = false; phoneText = (TextView)fragmentView.findViewById(R.id.settings_name); - Typeface typeface = Utilities.getTypeface("fonts/rmedium.ttf"); + Typeface typeface = AndroidUtilities.getTypeface("fonts/rmedium.ttf"); phoneText.setTypeface(typeface); firstNameField = (EditText)fragmentView.findViewById(R.id.first_name_field); @@ -183,13 +184,13 @@ public class ContactAddActivity extends BaseFragment implements NotificationCent boolean animations = preferences.getBoolean("view_animations", true); if (!animations) { firstNameField.requestFocus(); - Utilities.showKeyboard(firstNameField); + AndroidUtilities.showKeyboard(firstNameField); } } @Override public void onOpenAnimationEnd() { firstNameField.requestFocus(); - Utilities.showKeyboard(firstNameField); + AndroidUtilities.showKeyboard(firstNameField); } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/ContactsActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/ContactsActivity.java index 5d1e82f1f..9e23803d2 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/ContactsActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/ContactsActivity.java @@ -15,21 +15,26 @@ import android.content.Intent; import android.content.SharedPreferences; import android.net.Uri; import android.os.Bundle; +import android.text.InputType; +import android.view.Gravity; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; +import android.view.inputmethod.EditorInfo; import android.widget.AbsListView; import android.widget.AdapterView; import android.widget.EditText; +import android.widget.FrameLayout; import android.widget.TextView; -import org.telegram.messenger.LocaleController; +import org.telegram.android.AndroidUtilities; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLObject; import org.telegram.messenger.TLRPC; import org.telegram.messenger.ConnectionsManager; -import org.telegram.messenger.ContactsController; +import org.telegram.android.ContactsController; import org.telegram.messenger.FileLog; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.RPCRequest; @@ -70,7 +75,7 @@ public class ContactsActivity extends BaseFragment implements NotificationCenter private ContactsActivityDelegate delegate; public static interface ContactsActivityDelegate { - public abstract void didSelectContact(TLRPC.User user); + public abstract void didSelectContact(TLRPC.User user, String param); } public ContactsActivity(Bundle args) { @@ -148,9 +153,9 @@ public class ContactsActivity extends BaseFragment implements NotificationCenter listView.setAdapter(listViewAdapter); listViewAdapter.notifyDataSetChanged(); if (!LocaleController.isRTL) { - listView.setPadding(Utilities.dp(16), listView.getPaddingTop(), Utilities.dp(30), listView.getPaddingBottom()); + listView.setPadding(AndroidUtilities.dp(16), listView.getPaddingTop(), AndroidUtilities.dp(30), listView.getPaddingBottom()); } else { - listView.setPadding(Utilities.dp(30), listView.getPaddingTop(), Utilities.dp(16), listView.getPaddingBottom()); + listView.setPadding(AndroidUtilities.dp(30), listView.getPaddingTop(), AndroidUtilities.dp(16), listView.getPaddingBottom()); } if (android.os.Build.VERSION.SDK_INT >= 11) { listView.setFastScrollAlwaysVisible(true); @@ -170,7 +175,7 @@ public class ContactsActivity extends BaseFragment implements NotificationCenter if (text.length() != 0) { searchWas = true; if (listView != null) { - listView.setPadding(Utilities.dp(16), listView.getPaddingTop(), Utilities.dp(16), listView.getPaddingBottom()); + listView.setPadding(AndroidUtilities.dp(16), listView.getPaddingTop(), AndroidUtilities.dp(16), listView.getPaddingBottom()); listView.setAdapter(searchListViewAdapter); searchListViewAdapter.notifyDataSetChanged(); if(android.os.Build.VERSION.SDK_INT >= 11) { @@ -214,7 +219,7 @@ public class ContactsActivity extends BaseFragment implements NotificationCenter if (ignoreUsers != null && ignoreUsers.containsKey(user.id)) { return; } - didSelectResult(user, true); + didSelectResult(user, true, null); } else { if (createSecretChat) { creatingChat = true; @@ -272,7 +277,7 @@ public class ContactsActivity extends BaseFragment implements NotificationCenter if (ignoreUsers != null && ignoreUsers.containsKey(user.id)) { return; } - didSelectResult(user, true); + didSelectResult(user, true, null); } else { if (createSecretChat) { creatingChat = true; @@ -320,7 +325,7 @@ public class ContactsActivity extends BaseFragment implements NotificationCenter @Override public void onScrollStateChanged(AbsListView absListView, int i) { if (i == SCROLL_STATE_TOUCH_SCROLL && searching && searchWas) { - Utilities.hideKeyboard(getParentActivity().getCurrentFocus()); + AndroidUtilities.hideKeyboard(getParentActivity().getCurrentFocus()); } } @@ -337,7 +342,7 @@ public class ContactsActivity extends BaseFragment implements NotificationCenter return fragmentView; } - private void didSelectResult(final TLRPC.User user, boolean useAlert) { + private void didSelectResult(final TLRPC.User user, boolean useAlert, String param) { if (useAlert && selectAlertString != null) { if (getParentActivity() == null) { return; @@ -345,17 +350,36 @@ public class ContactsActivity extends BaseFragment implements NotificationCenter AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); builder.setMessage(LocaleController.formatStringSimple(selectAlertString, Utilities.formatName(user.first_name, user.last_name))); + final EditText editText = new EditText(getParentActivity()); + if (android.os.Build.VERSION.SDK_INT < 11) { + editText.setBackgroundResource(android.R.drawable.editbox_background_normal); + } + editText.setTextSize(18); + editText.setText("50"); + editText.setGravity(Gravity.CENTER); + editText.setInputType(InputType.TYPE_CLASS_NUMBER); + editText.setImeOptions(EditorInfo.IME_ACTION_DONE); + builder.setView(editText); builder.setPositiveButton(R.string.OK, new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialogInterface, int i) { - didSelectResult(user, false); + didSelectResult(user, false, editText.getText().toString()); } }); builder.setNegativeButton(R.string.Cancel, null); showAlertDialog(builder); + ViewGroup.MarginLayoutParams layoutParams = (ViewGroup.MarginLayoutParams)editText.getLayoutParams(); + if (layoutParams != null) { + if (layoutParams instanceof FrameLayout.LayoutParams) { + ((FrameLayout.LayoutParams)layoutParams).gravity = Gravity.CENTER_HORIZONTAL; + } + layoutParams.rightMargin = layoutParams.leftMargin = AndroidUtilities.dp(10); + editText.setLayoutParams(layoutParams); + } + editText.setSelection(editText.getText().length()); } else { if (delegate != null) { - delegate.didSelectContact(user); + delegate.didSelectContact(user, param); delegate = null; } finishFragment(); @@ -419,7 +443,7 @@ public class ContactsActivity extends BaseFragment implements NotificationCenter } } } - }, null, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors); + }, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors); } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/CountrySelectActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/CountrySelectActivity.java index 86c3d7eb4..3303a31bd 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/CountrySelectActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/CountrySelectActivity.java @@ -18,8 +18,9 @@ import android.widget.BaseAdapter; import android.widget.EditText; import android.widget.TextView; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.FileLog; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; import org.telegram.ui.Adapters.BaseFragmentAdapter; @@ -147,9 +148,9 @@ public class CountrySelectActivity extends BaseFragment { ViewGroup group = (ViewGroup) listView.getParent(); listView.setAdapter(listViewAdapter); if (!LocaleController.isRTL) { - listView.setPadding(Utilities.dp(16), listView.getPaddingTop(), Utilities.dp(30), listView.getPaddingBottom()); + listView.setPadding(AndroidUtilities.dp(16), listView.getPaddingTop(), AndroidUtilities.dp(30), listView.getPaddingBottom()); } else { - listView.setPadding(Utilities.dp(30), listView.getPaddingTop(), Utilities.dp(16), listView.getPaddingBottom()); + listView.setPadding(AndroidUtilities.dp(30), listView.getPaddingTop(), AndroidUtilities.dp(16), listView.getPaddingBottom()); } if (android.os.Build.VERSION.SDK_INT >= 11) { listView.setFastScrollAlwaysVisible(true); @@ -167,7 +168,7 @@ public class CountrySelectActivity extends BaseFragment { if (text.length() != 0) { searchWas = true; if (listView != null) { - listView.setPadding(Utilities.dp(16), listView.getPaddingTop(), Utilities.dp(16), listView.getPaddingBottom()); + listView.setPadding(AndroidUtilities.dp(16), listView.getPaddingTop(), AndroidUtilities.dp(16), listView.getPaddingBottom()); listView.setAdapter(searchListViewAdapter); if(android.os.Build.VERSION.SDK_INT >= 11) { listView.setFastScrollAlwaysVisible(false); @@ -228,7 +229,7 @@ public class CountrySelectActivity extends BaseFragment { @Override public void onScrollStateChanged(AbsListView absListView, int i) { if (i == SCROLL_STATE_TOUCH_SCROLL && searching && searchWas) { - Utilities.hideKeyboard(getParentActivity().getCurrentFocus()); + AndroidUtilities.hideKeyboard(getParentActivity().getCurrentFocus()); } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/DocumentSelectActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/DocumentSelectActivity.java index a869af45f..784963d5e 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/DocumentSelectActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/DocumentSelectActivity.java @@ -24,7 +24,7 @@ import android.widget.ListView; import android.widget.TextView; import org.telegram.messenger.FileLog; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; import org.telegram.ui.Adapters.BaseFragmentAdapter; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/GroupCreateActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/GroupCreateActivity.java index 1192082d0..6baa5a90b 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/GroupCreateActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/GroupCreateActivity.java @@ -32,13 +32,14 @@ import android.widget.EditText; import android.widget.ImageView; import android.widget.TextView; +import org.telegram.android.AndroidUtilities; import org.telegram.PhoneFormat.PhoneFormat; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLRPC; import org.telegram.messenger.ConnectionsManager; -import org.telegram.messenger.ContactsController; +import org.telegram.android.ContactsController; import org.telegram.messenger.FileLog; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.UserConfig; @@ -72,7 +73,7 @@ public class GroupCreateActivity extends BaseFragment implements NotificationCen int sz = super.getSize(paint, text, start, end, fm); - int offset = Utilities.dp(6); + int offset = AndroidUtilities.dp(6); int w = (fm.bottom - fm.top) / 2; fm.top = -w - offset; fm.bottom = w - offset; @@ -126,7 +127,7 @@ public class GroupCreateActivity extends BaseFragment implements NotificationCen actionBarLayer.setDisplayHomeAsUpEnabled(true, R.drawable.ic_ab_back); actionBarLayer.setBackOverlay(R.layout.updating_state_layout); actionBarLayer.setTitle(LocaleController.getString("NewGroup", R.string.NewGroup)); - actionBarLayer.setSubtitle(String.format("%d/200 %s", selectedContacts.size(), LocaleController.getString("Members", R.string.Members))); + actionBarLayer.setSubtitle(LocaleController.formatString("MembersCount", R.string.MembersCount, selectedContacts.size(), 200)); actionBarLayer.setActionBarMenuOnItemClick(new ActionBarLayer.ActionBarMenuOnItemClick() { @Override @@ -200,7 +201,7 @@ public class GroupCreateActivity extends BaseFragment implements NotificationCen selectedContacts.remove(sp.uid); } } - actionBarLayer.setSubtitle(String.format("%d/200 %s", selectedContacts.size(), LocaleController.getString("Members", R.string.Members))); + actionBarLayer.setSubtitle(LocaleController.formatString("MembersCount", R.string.MembersCount, selectedContacts.size(), 200)); listView.invalidateViews(); } else { search = true; @@ -266,7 +267,7 @@ public class GroupCreateActivity extends BaseFragment implements NotificationCen span.uid = user.id; ignoreChange = false; } - actionBarLayer.setSubtitle(String.format("%d/200 %s", selectedContacts.size(), LocaleController.getString("Members", R.string.Members))); + actionBarLayer.setSubtitle(LocaleController.formatString("MembersCount", R.string.MembersCount, selectedContacts.size(), 200)); if (searching || searchWas) { searching = false; searchWas = false; @@ -293,7 +294,7 @@ public class GroupCreateActivity extends BaseFragment implements NotificationCen @Override public void onScrollStateChanged(AbsListView absListView, int i) { if (i == SCROLL_STATE_TOUCH_SCROLL) { - Utilities.hideKeyboard(userSelectEditText); + AndroidUtilities.hideKeyboard(userSelectEditText); } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/GroupCreateFinalActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/GroupCreateFinalActivity.java index da86a8149..6d8e2c55a 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/GroupCreateFinalActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/GroupCreateFinalActivity.java @@ -22,11 +22,11 @@ import android.widget.ImageButton; import android.widget.TextView; import org.telegram.messenger.ConnectionsManager; -import org.telegram.messenger.LocaleController; -import org.telegram.messenger.MessagesStorage; +import org.telegram.android.LocaleController; +import org.telegram.android.MessagesStorage; import org.telegram.messenger.TLRPC; import org.telegram.messenger.FileLog; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; @@ -407,11 +407,7 @@ public class GroupCreateFinalActivity extends BaseFragment implements Notificati convertView.setBackgroundColor(0xffffffff); } TextView textView = (TextView)convertView.findViewById(R.id.settings_section_text); - if (selectedContacts.size() == 1) { - textView.setText(selectedContacts.size() + " " + LocaleController.getString("MEMBER", R.string.MEMBER)); - } else { - textView.setText(selectedContacts.size() + " " + LocaleController.getString("MEMBERS", R.string.MEMBERS)); - } + textView.setText(LocaleController.formatPluralString("Members", selectedContacts.size()).toUpperCase()); return convertView; } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/IdenticonActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/IdenticonActivity.java index f3010c792..b18e9909e 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/IdenticonActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/IdenticonActivity.java @@ -20,11 +20,11 @@ import android.view.WindowManager; import android.widget.LinearLayout; import android.widget.TextView; -import org.telegram.messenger.LocaleController; +import org.telegram.android.AndroidUtilities; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLRPC; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.R; -import org.telegram.messenger.Utilities; import org.telegram.ui.Views.ActionBar.ActionBarLayer; import org.telegram.ui.Views.ActionBar.BaseFragment; import org.telegram.ui.Views.IdenticonView; @@ -48,7 +48,7 @@ public class IdenticonActivity extends BaseFragment { actionBarLayer.setDisplayHomeAsUpEnabled(true, R.drawable.ic_ab_back); actionBarLayer.setBackOverlay(R.layout.updating_state_layout); actionBarLayer.setTitle(LocaleController.getString("EncryptionKey", R.string.EncryptionKey)); - actionBarLayer.setTitleIcon(R.drawable.ic_lock_white, Utilities.dp(4)); + actionBarLayer.setTitleIcon(R.drawable.ic_lock_white, AndroidUtilities.dp(4)); actionBarLayer.setActionBarMenuOnItemClick(new ActionBarLayer.ActionBarMenuOnItemClick() { @Override diff --git a/TMessagesProj/src/main/java/org/telegram/ui/IntroActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/IntroActivity.java index 8c7d563a3..d8141fda8 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/IntroActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/IntroActivity.java @@ -24,7 +24,7 @@ import android.view.animation.AnimationUtils; import android.widget.ImageView; import android.widget.TextView; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/LanguageSelectActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/LanguageSelectActivity.java index 559613897..dc4e56ae0 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/LanguageSelectActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/LanguageSelectActivity.java @@ -20,8 +20,9 @@ import android.widget.EditText; import android.widget.ListView; import android.widget.TextView; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.FileLog; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; import org.telegram.ui.Adapters.BaseFragmentAdapter; @@ -86,7 +87,7 @@ public class LanguageSelectActivity extends BaseFragment { if (text.length() != 0) { searchWas = true; if (listView != null) { - listView.setPadding(Utilities.dp(16), listView.getPaddingTop(), Utilities.dp(16), listView.getPaddingBottom()); + listView.setPadding(AndroidUtilities.dp(16), listView.getPaddingTop(), AndroidUtilities.dp(16), listView.getPaddingBottom()); listView.setAdapter(searchListViewAdapter); if(android.os.Build.VERSION.SDK_INT >= 11) { listView.setFastScrollAlwaysVisible(false); @@ -176,7 +177,7 @@ public class LanguageSelectActivity extends BaseFragment { @Override public void onScrollStateChanged(AbsListView absListView, int i) { if (i == SCROLL_STATE_TOUCH_SCROLL && searching && searchWas) { - Utilities.hideKeyboard(getParentActivity().getCurrentFocus()); + AndroidUtilities.hideKeyboard(getParentActivity().getCurrentFocus()); } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/LaunchActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/LaunchActivity.java index 23de06c11..0b9e21bd0 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/LaunchActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/LaunchActivity.java @@ -8,38 +8,31 @@ package org.telegram.ui; -import android.app.NotificationManager; import android.content.ContentResolver; -import android.content.Context; import android.content.Intent; import android.content.SharedPreferences; -import android.content.res.Configuration; import android.database.Cursor; import android.net.Uri; import android.os.Bundle; import android.os.Parcelable; import android.provider.ContactsContract; -import android.view.Surface; import android.view.View; -import android.view.WindowManager; -import android.widget.EditText; import android.widget.TextView; import android.widget.Toast; +import org.telegram.android.AndroidUtilities; import org.telegram.PhoneFormat.PhoneFormat; import org.telegram.messenger.ConnectionsManager; import org.telegram.messenger.FileLog; -import org.telegram.messenger.LocaleController; -import org.telegram.messenger.MessagesController; +import org.telegram.android.LocaleController; +import org.telegram.android.MessagesController; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.TLRPC; import org.telegram.messenger.UserConfig; import org.telegram.messenger.Utilities; -import org.telegram.objects.MessageObject; import org.telegram.ui.Views.ActionBar.ActionBarActivity; import org.telegram.ui.Views.ActionBar.BaseFragment; -import org.telegram.ui.Views.NotificationView; import java.io.BufferedReader; import java.io.InputStream; @@ -49,7 +42,6 @@ import java.util.Map; public class LaunchActivity extends ActionBarActivity implements NotificationCenter.NotificationCenterDelegate, MessagesActivity.MessagesActivityDelegate { private boolean finished = false; - private NotificationView notificationView; private String videoPath = null; private String sendingText = null; private ArrayList photoPathsArray = null; @@ -86,11 +78,11 @@ public class LaunchActivity extends ActionBarActivity implements NotificationCen int resourceId = getResources().getIdentifier("status_bar_height", "dimen", "android"); if (resourceId > 0) { - Utilities.statusBarHeight = getResources().getDimensionPixelSize(resourceId); + AndroidUtilities.statusBarHeight = getResources().getDimensionPixelSize(resourceId); } NotificationCenter.getInstance().postNotificationName(702, this); - currentConnectionState = ConnectionsManager.getInstance().connectionState; + currentConnectionState = ConnectionsManager.getInstance().getConnectionState(); NotificationCenter.getInstance().addObserver(this, 1234); NotificationCenter.getInstance().addObserver(this, 658); @@ -148,8 +140,6 @@ public class LaunchActivity extends ActionBarActivity implements NotificationCen } handleIntent(getIntent(), false, savedInstanceState != null); - - PhotoViewer.getInstance().setParentActivity(this); } private void handleIntent(Intent intent, boolean isNew, boolean restore) { @@ -423,7 +413,7 @@ public class LaunchActivity extends ActionBarActivity implements NotificationCen NotificationCenter.getInstance().postNotificationName(MessagesController.closeChats); Bundle args = new Bundle(); args.putBoolean("onlySelect", true); - args.putString("selectAlertString", LocaleController.getString("ForwardMessagesTo", R.string.ForwardMessagesTo)); + args.putString("selectAlertString", LocaleController.getString("SendMessagesTo", R.string.SendMessagesTo)); MessagesActivity fragment = new MessagesActivity(args); fragment.setDelegate(this); presentFragment(fragment, false, true); @@ -447,7 +437,7 @@ public class LaunchActivity extends ActionBarActivity implements NotificationCen } @Override - public void didSelectDialog(MessagesActivity messageFragment, long dialog_id) { + public void didSelectDialog(MessagesActivity messageFragment, long dialog_id, boolean param) { if (dialog_id != 0) { int lower_part = (int)dialog_id; @@ -504,18 +494,13 @@ public class LaunchActivity extends ActionBarActivity implements NotificationCen @Override protected void onPause() { super.onPause(); - ConnectionsManager.setAppPaused(true); - if (notificationView != null) { - notificationView.hide(false); - } - View focusView = getCurrentFocus(); - if (focusView instanceof EditText) { - focusView.clearFocus(); - } + ApplicationLoader.mainInterfacePaused = true; + ConnectionsManager.getInstance().setAppPaused(true, false); } @Override protected void onDestroy() { + PhotoViewer.getInstance().destroyPhotoViewer(); super.onDestroy(); onFinish(); } @@ -523,20 +508,11 @@ public class LaunchActivity extends ActionBarActivity implements NotificationCen @Override protected void onResume() { super.onResume(); - if (notificationView == null && getLayoutInflater() != null) { - notificationView = (NotificationView) getLayoutInflater().inflate(R.layout.notification_layout, null); - } Utilities.checkForCrashes(this); Utilities.checkForUpdates(this); - ConnectionsManager.setAppPaused(false); + ApplicationLoader.mainInterfacePaused = false; + ConnectionsManager.getInstance().setAppPaused(false, false); actionBar.setBackOverlayVisible(currentConnectionState != 0); - try { - NotificationManager mNotificationManager = (NotificationManager)this.getSystemService(Context.NOTIFICATION_SERVICE); - mNotificationManager.cancel(1); - MessagesController.getInstance().currentPushMessage = null; - } catch (Exception e) { - FileLog.e("tmessages", e); - } } @Override @@ -550,32 +526,12 @@ public class LaunchActivity extends ActionBarActivity implements NotificationCen NotificationCenter.getInstance().removeObserver(this, 701); NotificationCenter.getInstance().removeObserver(this, 702); NotificationCenter.getInstance().removeObserver(this, 703); - if (notificationView != null) { - notificationView.hide(false); - notificationView.destroy(); - notificationView = null; - } } @Override public void onConfigurationChanged(android.content.res.Configuration newConfig) { super.onConfigurationChanged(newConfig); - Utilities.checkDisplaySize(); - } - - @Override - public void needLayout() { - super.needLayout(); - if (notificationView != null) { - WindowManager manager = (WindowManager) getSystemService(WINDOW_SERVICE); - int rotation = manager.getDefaultDisplay().getRotation(); - - int height = Utilities.dp(48); - if (!Utilities.isTablet(this) && getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { - height = Utilities.dp(40); - } - notificationView.applyOrientationPaddings(rotation == Surface.ROTATION_270 || rotation == Surface.ROTATION_90, height); - } + AndroidUtilities.checkDisplaySize(); } @Override @@ -614,11 +570,6 @@ public class LaunchActivity extends ActionBarActivity implements NotificationCen args2.putInt("enc_id", push_enc_id); presentFragment(new ChatActivity(args2), false, true); } - } else if (id == 701) { - if (notificationView != null) { - MessageObject message = (MessageObject)args[0]; - notificationView.show(message); - } } else if (id == 702) { if (args[0] != this) { onFinish(); @@ -696,4 +647,9 @@ public class LaunchActivity extends ActionBarActivity implements NotificationCen } return super.onPreIme(); } + + @Override + public void onLowMemory() { + super.onLowMemory(); + } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/LocationActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/LocationActivity.java index ddaa34639..a31d9eff3 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/LocationActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/LocationActivity.java @@ -26,10 +26,10 @@ import com.google.android.gms.maps.model.Marker; import com.google.android.gms.maps.model.MarkerOptions; import org.telegram.messenger.FileLog; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLRPC; import org.telegram.objects.MessageObject; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; @@ -133,6 +133,9 @@ public class LocationActivity extends BaseFragment implements NotificationCenter } avatarImageView = (BackupImageView)fragmentView.findViewById(R.id.location_avatar_view); + if (avatarImageView != null) { + avatarImageView.processDetach = false; + } nameTextView = (TextView)fragmentView.findViewById(R.id.location_name_label); distanceTextView = (TextView)fragmentView.findViewById(R.id.location_distance_label); View bottomView = fragmentView.findViewById(R.id.location_bottom_view); diff --git a/TMessagesProj/src/main/java/org/telegram/ui/LoginActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/LoginActivity.java index d19df2b59..aa2495a78 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/LoginActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/LoginActivity.java @@ -22,8 +22,9 @@ import android.widget.FrameLayout; import android.widget.ScrollView; import android.widget.TextView; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.FileLog; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; import org.telegram.ui.Views.ActionBar.ActionBarLayer; @@ -265,7 +266,7 @@ public class LoginActivity extends BaseFragment implements SlideView.SlideViewDe newView.setParams(params); actionBarLayer.setTitle(newView.getHeaderName()); newView.onShow(); - newView.setX(back ? -Utilities.displaySize.x : Utilities.displaySize.x); + newView.setX(back ? -AndroidUtilities.displaySize.x : AndroidUtilities.displaySize.x); outView.animate().setInterpolator(new AccelerateDecelerateInterpolator()).setListener(new Animator.AnimatorListener() { @Override public void onAnimationStart(Animator animator) { @@ -284,7 +285,7 @@ public class LoginActivity extends BaseFragment implements SlideView.SlideViewDe @Override public void onAnimationRepeat(Animator animator) { } - }).setDuration(300).translationX(back ? Utilities.displaySize.x : -Utilities.displaySize.x).start(); + }).setDuration(300).translationX(back ? AndroidUtilities.displaySize.x : -AndroidUtilities.displaySize.x).start(); newView.animate().setInterpolator(new AccelerateDecelerateInterpolator()).setListener(new Animator.AnimatorListener() { @Override public void onAnimationStart(Animator animator) { diff --git a/TMessagesProj/src/main/java/org/telegram/ui/LoginActivityPhoneView.java b/TMessagesProj/src/main/java/org/telegram/ui/LoginActivityPhoneView.java index 6d228ad8d..4f37c7f70 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/LoginActivityPhoneView.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/LoginActivityPhoneView.java @@ -21,9 +21,10 @@ import android.widget.AdapterView; import android.widget.EditText; import android.widget.TextView; +import org.telegram.android.AndroidUtilities; import org.telegram.PhoneFormat.PhoneFormat; import org.telegram.messenger.BuildVars; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLObject; import org.telegram.messenger.TLRPC; import org.telegram.messenger.ConnectionsManager; @@ -250,10 +251,10 @@ public class LoginActivityPhoneView extends SlideView implements AdapterView.OnI } if (codeField.length() != 0) { - Utilities.showKeyboard(phoneField); + AndroidUtilities.showKeyboard(phoneField); phoneField.requestFocus(); } else { - Utilities.showKeyboard(codeField); + AndroidUtilities.showKeyboard(codeField); codeField.requestFocus(); } phoneField.setOnEditorActionListener(new TextView.OnEditorActionListener() { @@ -389,7 +390,7 @@ public class LoginActivityPhoneView extends SlideView implements AdapterView.OnI } }); } - }, null, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors | RPCRequest.RPCRequestClassWithoutLogin); + }, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors | RPCRequest.RPCRequestClassWithoutLogin | RPCRequest.RPCRequestClassTryDifferentDc | RPCRequest.RPCRequestClassEnableUnauthorized); } @Override diff --git a/TMessagesProj/src/main/java/org/telegram/ui/LoginActivityRegisterView.java b/TMessagesProj/src/main/java/org/telegram/ui/LoginActivityRegisterView.java index 7515aa74d..ec2dfd09c 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/LoginActivityRegisterView.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/LoginActivityRegisterView.java @@ -17,13 +17,13 @@ import android.view.inputmethod.EditorInfo; import android.widget.EditText; import android.widget.TextView; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLObject; import org.telegram.messenger.TLRPC; import org.telegram.messenger.ConnectionsManager; -import org.telegram.messenger.ContactsController; -import org.telegram.messenger.MessagesController; -import org.telegram.messenger.MessagesStorage; +import org.telegram.android.ContactsController; +import org.telegram.android.MessagesController; +import org.telegram.android.MessagesStorage; import org.telegram.messenger.R; import org.telegram.messenger.RPCRequest; import org.telegram.messenger.UserConfig; @@ -184,7 +184,7 @@ public class LoginActivityRegisterView extends SlideView { } }); } - }, null, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassWithoutLogin); + }, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassWithoutLogin); } @Override diff --git a/TMessagesProj/src/main/java/org/telegram/ui/LoginActivitySmsView.java b/TMessagesProj/src/main/java/org/telegram/ui/LoginActivitySmsView.java index 7c80b277b..d390540f8 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/LoginActivitySmsView.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/LoginActivitySmsView.java @@ -9,6 +9,9 @@ package org.telegram.ui; import android.content.Context; +import android.content.Intent; +import android.content.pm.PackageInfo; +import android.os.Build; import android.os.Bundle; import android.text.Html; import android.util.AttributeSet; @@ -18,15 +21,16 @@ import android.view.inputmethod.EditorInfo; import android.widget.EditText; import android.widget.TextView; +import org.telegram.android.AndroidUtilities; import org.telegram.PhoneFormat.PhoneFormat; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLObject; import org.telegram.messenger.TLRPC; import org.telegram.messenger.ConnectionsManager; -import org.telegram.messenger.ContactsController; +import org.telegram.android.ContactsController; import org.telegram.messenger.FileLog; -import org.telegram.messenger.MessagesController; -import org.telegram.messenger.MessagesStorage; +import org.telegram.android.MessagesController; +import org.telegram.android.MessagesStorage; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.RPCRequest; @@ -35,6 +39,7 @@ import org.telegram.messenger.Utilities; import org.telegram.ui.Views.SlideView; import java.util.ArrayList; +import java.util.Locale; import java.util.Timer; import java.util.TimerTask; @@ -45,6 +50,7 @@ public class LoginActivitySmsView extends SlideView implements NotificationCente private EditText codeField; private TextView confirmTextView; private TextView timeText; + private TextView problemText; private Bundle currentParams; private Timer timeTimer; @@ -53,6 +59,7 @@ public class LoginActivitySmsView extends SlideView implements NotificationCente private double lastCurrentTime; private boolean waitingForSms = false; private boolean nextPressed = false; + private String lastError = ""; public LoginActivitySmsView(Context context) { super(context); @@ -74,8 +81,11 @@ public class LoginActivitySmsView extends SlideView implements NotificationCente codeField = (EditText)findViewById(R.id.login_sms_code_field); codeField.setHint(LocaleController.getString("Code", R.string.Code)); timeText = (TextView)findViewById(R.id.login_time_text); + problemText = (TextView)findViewById(R.id.login_problem); TextView wrongNumber = (TextView) findViewById(R.id.wrong_number); wrongNumber.setText(LocaleController.getString("WrongNumber", R.string.WrongNumber)); + problemText.setText(LocaleController.getString("DidNotGetTheCode", R.string.DidNotGetTheCode)); + problemText.setVisibility(time < 1000 ? VISIBLE : GONE); wrongNumber.setOnClickListener(new OnClickListener() { @Override @@ -85,6 +95,27 @@ public class LoginActivitySmsView extends SlideView implements NotificationCente } }); + problemText.setOnClickListener(new OnClickListener() { + @Override + public void onClick(View v) { + try { + PackageInfo pInfo = ApplicationLoader.applicationContext.getPackageManager().getPackageInfo(ApplicationLoader.applicationContext.getPackageName(), 0); + String version = String.format(Locale.US, "%s (%d)", pInfo.versionName, pInfo.versionCode); + + Intent mailer = new Intent(Intent.ACTION_SEND); + mailer.setType("message/rfc822"); + mailer.putExtra(Intent.EXTRA_EMAIL, new String[]{"sms@telegram.org"}); + mailer.putExtra(Intent.EXTRA_SUBJECT, "Android registration/login issue " + version + " " + requestPhone); + mailer.putExtra(Intent.EXTRA_TEXT, "Phone: " + requestPhone + "\nApp version: " + version + "\nOS version: SDK " + Build.VERSION.SDK_INT + "\nDevice Name: " + Build.MANUFACTURER + Build.MODEL + "\nLocale: " + Locale.getDefault() + "\nError: " + lastError); + getContext().startActivity(Intent.createChooser(mailer, "Send email...")); + } catch (Exception e) { + if (delegate != null) { + delegate.needShowAlert(LocaleController.getString("NoMailInstalled", R.string.NoMailInstalled)); + } + } + } + }); + codeField.setOnEditorActionListener(new TextView.OnEditorActionListener() { @Override public boolean onEditorAction(TextView textView, int i, KeyEvent keyEvent) { @@ -110,7 +141,7 @@ public class LoginActivitySmsView extends SlideView implements NotificationCente return; } codeField.setText(""); - Utilities.setWaitingForSms(true); + AndroidUtilities.setWaitingForSms(true); NotificationCenter.getInstance().addObserver(this, 998); currentParams = params; waitingForSms = true; @@ -127,12 +158,13 @@ public class LoginActivitySmsView extends SlideView implements NotificationCente String number = PhoneFormat.getInstance().format(phone); confirmTextView.setText(Html.fromHtml(String.format(LocaleController.getString("SentSmsCode", R.string.SentSmsCode) + " %s", number))); - Utilities.showKeyboard(codeField); + AndroidUtilities.showKeyboard(codeField); codeField.requestFocus(); destroyTimer(); timeText.setText(String.format("%s 1:00", LocaleController.getString("CallText", R.string.CallText))); lastCurrentTime = System.currentTimeMillis(); + problemText.setVisibility(time < 1000 ? VISIBLE : GONE); createTimer(); } @@ -157,6 +189,7 @@ public class LoginActivitySmsView extends SlideView implements NotificationCente int seconds = time / 1000 - minutes * 60; timeText.setText(String.format("%s %d:%02d", LocaleController.getString("CallText", R.string.CallText), minutes, seconds)); } else { + problemText.setVisibility(VISIBLE); timeText.setText(LocaleController.getString("Calling", R.string.Calling)); destroyTimer(); TLRPC.TL_auth_sendCall req = new TLRPC.TL_auth_sendCall(); @@ -164,9 +197,17 @@ public class LoginActivitySmsView extends SlideView implements NotificationCente req.phone_code_hash = phoneHash; ConnectionsManager.getInstance().performRpc(req, new RPCRequest.RPCRequestDelegate() { @Override - public void run(TLObject response, TLRPC.TL_error error) { + public void run(TLObject response, final TLRPC.TL_error error) { + if (error != null && error.text != null) { + Utilities.RunOnUIThread(new Runnable() { + @Override + public void run() { + lastError = error.text; + } + }); + } } - }, null, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors | RPCRequest.RPCRequestClassWithoutLogin); + }, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors | RPCRequest.RPCRequestClassWithoutLogin); } } }); @@ -194,7 +235,7 @@ public class LoginActivitySmsView extends SlideView implements NotificationCente } nextPressed = true; waitingForSms = false; - Utilities.setWaitingForSms(false); + AndroidUtilities.setWaitingForSms(false); NotificationCenter.getInstance().removeObserver(this, 998); final TLRPC.TL_auth_signIn req = new TLRPC.TL_auth_signIn(); req.phone_number = requestPhone; @@ -231,6 +272,7 @@ public class LoginActivitySmsView extends SlideView implements NotificationCente delegate.needFinishActivity(); ConnectionsManager.getInstance().initPushConnection(); } else { + lastError = error.text; if (error.text.contains("PHONE_NUMBER_UNOCCUPIED") && registered == null) { Bundle params = new Bundle(); params.putString("phoneFormated", requestPhone); @@ -256,14 +298,14 @@ public class LoginActivitySmsView extends SlideView implements NotificationCente } }); } - }, null, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors | RPCRequest.RPCRequestClassWithoutLogin); + }, true, RPCRequest.RPCRequestClassGeneric | RPCRequest.RPCRequestClassFailOnServerErrors | RPCRequest.RPCRequestClassWithoutLogin); } @Override public void onBackPressed() { destroyTimer(); currentParams = null; - Utilities.setWaitingForSms(false); + AndroidUtilities.setWaitingForSms(false); NotificationCenter.getInstance().removeObserver(this, 998); waitingForSms = false; } @@ -271,7 +313,7 @@ public class LoginActivitySmsView extends SlideView implements NotificationCente @Override public void onDestroyActivity() { super.onDestroyActivity(); - Utilities.setWaitingForSms(false); + AndroidUtilities.setWaitingForSms(false); NotificationCenter.getInstance().removeObserver(this, 998); destroyTimer(); waitingForSms = false; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/MediaActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/MediaActivity.java index 087b7e60a..52a102412 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/MediaActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/MediaActivity.java @@ -23,11 +23,11 @@ import android.widget.AdapterView; import android.widget.GridView; import android.widget.TextView; -import org.telegram.messenger.LocaleController; +import org.telegram.android.AndroidUtilities; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLRPC; -import org.telegram.messenger.Utilities; import org.telegram.objects.MessageObject; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.objects.PhotoObject; @@ -114,6 +114,7 @@ public class MediaActivity extends BaseFragment implements NotificationCenter.No listView.setOnItemClickListener(new AdapterView.OnItemClickListener() { @Override public void onItemClick(AdapterView adapterView, View view, int i, long l) { + PhotoViewer.getInstance().setParentActivity(getParentActivity()); PhotoViewer.getInstance().openPhoto(messages, i, MediaActivity.this); } }); @@ -284,7 +285,7 @@ public class MediaActivity extends BaseFragment implements NotificationCenter.No imageView.getLocationInWindow(coords); PhotoViewer.PlaceProviderObject object = new PhotoViewer.PlaceProviderObject(); object.viewX = coords[0]; - object.viewY = coords[1] - Utilities.statusBarHeight; + object.viewY = coords[1] - AndroidUtilities.statusBarHeight; object.parentView = listView; object.imageReceiver = imageView.imageReceiver; object.thumb = object.imageReceiver.getBitmap(); @@ -327,14 +328,14 @@ public class MediaActivity extends BaseFragment implements NotificationCenter.No if (rotation == Surface.ROTATION_270 || rotation == Surface.ROTATION_90) { listView.setNumColumns(6); - itemWidth = getParentActivity().getResources().getDisplayMetrics().widthPixels / 6 - Utilities.dp(2) * 5; + itemWidth = getParentActivity().getResources().getDisplayMetrics().widthPixels / 6 - AndroidUtilities.dp(2) * 5; listView.setColumnWidth(itemWidth); } else { listView.setNumColumns(4); - itemWidth = getParentActivity().getResources().getDisplayMetrics().widthPixels / 4 - Utilities.dp(2) * 3; + itemWidth = getParentActivity().getResources().getDisplayMetrics().widthPixels / 4 - AndroidUtilities.dp(2) * 3; listView.setColumnWidth(itemWidth); } - listView.setPadding(listView.getPaddingLeft(), Utilities.dp(4), listView.getPaddingRight(), listView.getPaddingBottom()); + listView.setPadding(listView.getPaddingLeft(), AndroidUtilities.dp(4), listView.getPaddingRight(), listView.getPaddingBottom()); listAdapter.notifyDataSetChanged(); if (listView != null) { diff --git a/TMessagesProj/src/main/java/org/telegram/ui/MessagesActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/MessagesActivity.java index 0913bfc83..ecdbd2c39 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/MessagesActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/MessagesActivity.java @@ -17,17 +17,19 @@ import android.view.View; import android.view.ViewGroup; import android.widget.AbsListView; import android.widget.AdapterView; +import android.widget.CheckBox; import android.widget.EditText; import android.widget.ListView; import android.widget.TextView; -import org.telegram.messenger.LocaleController; +import org.telegram.android.AndroidUtilities; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLObject; import org.telegram.messenger.TLRPC; -import org.telegram.messenger.ContactsController; +import org.telegram.android.ContactsController; import org.telegram.messenger.FileLog; -import org.telegram.messenger.MessagesController; -import org.telegram.messenger.MessagesStorage; +import org.telegram.android.MessagesController; +import org.telegram.android.MessagesStorage; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.UserConfig; @@ -74,7 +76,7 @@ public class MessagesActivity extends BaseFragment implements NotificationCenter private final static int messages_list_menu_settings = 5; public static interface MessagesActivityDelegate { - public abstract void didSelectDialog(MessagesActivity fragment, long dialog_id); + public abstract void didSelectDialog(MessagesActivity fragment, long dialog_id, boolean param); } public MessagesActivity(Bundle args) { @@ -276,7 +278,7 @@ public class MessagesActivity extends BaseFragment implements NotificationCenter } } if (onlySelect) { - didSelectResult(dialog_id, true); + didSelectResult(dialog_id, true, false); } else { Bundle args = new Bundle(); int lower_part = (int)dialog_id; @@ -324,8 +326,18 @@ public class MessagesActivity extends BaseFragment implements NotificationCenter if (which == 0) { MessagesController.getInstance().deleteDialog(selectedDialog, 0, true); } else if (which == 1) { - MessagesController.getInstance().deleteUserFromChat((int) -selectedDialog, MessagesController.getInstance().users.get(UserConfig.getClientUserId()), null); - MessagesController.getInstance().deleteDialog(selectedDialog, 0, false); + AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); + builder.setMessage(LocaleController.getString("AreYouSureDeleteAndExit", R.string.AreYouSureDeleteAndExit)); + builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); + builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialogInterface, int i) { + MessagesController.getInstance().deleteUserFromChat((int) -selectedDialog, MessagesController.getInstance().users.get(UserConfig.getClientUserId()), null); + MessagesController.getInstance().deleteDialog(selectedDialog, 0, false); + } + }); + builder.setNegativeButton(LocaleController.getString("Cancel", R.string.Cancel), null); + showAlertDialog(builder); } } }); @@ -333,7 +345,21 @@ public class MessagesActivity extends BaseFragment implements NotificationCenter builder.setItems(new CharSequence[]{LocaleController.getString("ClearHistory", R.string.ClearHistory), LocaleController.getString("Delete", R.string.Delete)}, new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { - MessagesController.getInstance().deleteDialog(selectedDialog, 0, which == 0); + if (which == 0) { + MessagesController.getInstance().deleteDialog(selectedDialog, 0, true); + } else { + AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); + builder.setMessage(LocaleController.getString("AreYouSureDeleteThisChat", R.string.AreYouSureDeleteThisChat)); + builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); + builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialogInterface, int i) { + MessagesController.getInstance().deleteDialog(selectedDialog, 0, false); + } + }); + builder.setNegativeButton(LocaleController.getString("Cancel", R.string.Cancel), null); + showAlertDialog(builder); + } } }); } @@ -347,7 +373,7 @@ public class MessagesActivity extends BaseFragment implements NotificationCenter @Override public void onScrollStateChanged(AbsListView absListView, int i) { if (i == SCROLL_STATE_TOUCH_SCROLL && searching && searchWas) { - Utilities.hideKeyboard(getParentActivity().getCurrentFocus()); + AndroidUtilities.hideKeyboard(getParentActivity().getCurrentFocus()); } } @@ -363,11 +389,6 @@ public class MessagesActivity extends BaseFragment implements NotificationCenter } } }); - - if (MessagesController.getInstance().loadingDialogs) { - progressView.setVisibility(View.VISIBLE); - } - } else { ViewGroup parent = (ViewGroup)fragmentView.getParent(); if (parent != null) { @@ -453,7 +474,7 @@ public class MessagesActivity extends BaseFragment implements NotificationCenter this.delegate = delegate; } - private void didSelectResult(final long dialog_id, boolean useAlert) { + private void didSelectResult(final long dialog_id, boolean useAlert, final boolean param) { if (useAlert && selectAlertString != null) { if (getParentActivity() == null) { return; @@ -484,17 +505,32 @@ public class MessagesActivity extends BaseFragment implements NotificationCenter } builder.setMessage(LocaleController.formatStringSimple(selectAlertString, Utilities.formatName(user.first_name, user.last_name))); } + CheckBox checkBox = null; + /*if (delegate instanceof ChatActivity) { + checkBox = new CheckBox(getParentActivity()); + checkBox.setText(LocaleController.getString("ForwardFromMyName", R.string.ForwardFromMyName)); + checkBox.setChecked(false); + builder.setView(checkBox); + }*/ + final CheckBox checkBoxFinal = checkBox; builder.setPositiveButton(R.string.OK, new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialogInterface, int i) { - didSelectResult(dialog_id, false); + didSelectResult(dialog_id, false, checkBoxFinal != null && checkBoxFinal.isChecked()); } }); builder.setNegativeButton(R.string.Cancel, null); showAlertDialog(builder); + if (checkBox != null) { + ViewGroup.MarginLayoutParams layoutParams = (ViewGroup.MarginLayoutParams)checkBox.getLayoutParams(); + if (layoutParams != null) { + layoutParams.rightMargin = layoutParams.leftMargin = AndroidUtilities.dp(10); + checkBox.setLayoutParams(layoutParams); + } + } } else { if (delegate != null) { - delegate.didSelectDialog(MessagesActivity.this, dialog_id); + delegate.didSelectDialog(MessagesActivity.this, dialog_id, param); delegate = null; } else { finishFragment(); diff --git a/TMessagesProj/src/main/java/org/telegram/ui/PhotoCropActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/PhotoCropActivity.java index 22e8395f4..a90b2e55f 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/PhotoCropActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/PhotoCropActivity.java @@ -27,11 +27,11 @@ import android.widget.Button; import android.widget.FrameLayout; import android.widget.TextView; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.FileLoader; import org.telegram.messenger.FileLog; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.R; -import org.telegram.messenger.Utilities; import org.telegram.ui.Views.ActionBar.BaseFragment; import java.io.File; @@ -72,7 +72,7 @@ public class PhotoCropActivity extends BaseFragment { private void init() { rectPaint = new Paint(); rectPaint.setColor(0xfffafafa); - rectPaint.setStrokeWidth(Utilities.dp(2)); + rectPaint.setStrokeWidth(AndroidUtilities.dp(2)); rectPaint.setStyle(Paint.Style.STROKE); circlePaint = new Paint(); circlePaint.setColor(0x7fffffff); @@ -85,7 +85,7 @@ public class PhotoCropActivity extends BaseFragment { public boolean onTouch(View view, MotionEvent motionEvent) { float x = motionEvent.getX(); float y = motionEvent.getY(); - int cornerSide = Utilities.dp(14); + int cornerSide = AndroidUtilities.dp(14); if (motionEvent.getAction() == MotionEvent.ACTION_DOWN) { if (rectX - cornerSide < x && rectX + cornerSide > x && rectY - cornerSide < y && rectY + cornerSide > y) { draggingState = 1; @@ -270,7 +270,7 @@ public class PhotoCropActivity extends BaseFragment { canvas.drawRect(rectX, rectY, rectX + rectSize, rectY + rectSize, rectPaint); - int side = Utilities.dp(7); + int side = AndroidUtilities.dp(7); canvas.drawRect(rectX - side, rectY - side, rectX + side, rectY + side, circlePaint); canvas.drawRect(rectX + rectSize - side, rectY - side, rectX + rectSize + side, rectY + side, circlePaint); canvas.drawRect(rectX - side, rectY + rectSize - side, rectX + side, rectY + rectSize + side, circlePaint); diff --git a/TMessagesProj/src/main/java/org/telegram/ui/PhotoPickerActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/PhotoPickerActivity.java index 6e17f0edc..093555c6a 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/PhotoPickerActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/PhotoPickerActivity.java @@ -23,13 +23,13 @@ import android.widget.GridView; import android.widget.ImageView; import android.widget.TextView; -import org.telegram.messenger.LocaleController; -import org.telegram.messenger.MediaController; -import org.telegram.messenger.MessagesController; +import org.telegram.android.AndroidUtilities; +import org.telegram.android.LocaleController; +import org.telegram.android.MediaController; +import org.telegram.android.MessagesController; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.TLRPC; -import org.telegram.messenger.Utilities; import org.telegram.objects.MessageObject; import org.telegram.ui.Adapters.BaseFragmentAdapter; import org.telegram.ui.Views.ActionBar.ActionBarLayer; @@ -159,6 +159,7 @@ public class PhotoPickerActivity extends BaseFragment implements NotificationCen if (i < 0 || i >= selectedAlbum.photos.size()) { return; } + PhotoViewer.getInstance().setParentActivity(getParentActivity()); PhotoViewer.getInstance().openPhotoForSelect(selectedAlbum.photos, i, PhotoPickerActivity.this); } } @@ -252,7 +253,7 @@ public class PhotoPickerActivity extends BaseFragment implements NotificationCen imageView.getLocationInWindow(coords); PhotoViewer.PlaceProviderObject object = new PhotoViewer.PlaceProviderObject(); object.viewX = coords[0]; - object.viewY = coords[1] - Utilities.statusBarHeight; + object.viewY = coords[1] - AndroidUtilities.statusBarHeight; object.parentView = listView; object.imageReceiver = imageView.imageReceiver; object.thumb = object.imageReceiver.getBitmap(); @@ -405,7 +406,7 @@ public class PhotoPickerActivity extends BaseFragment implements NotificationCen } } listView.setNumColumns(columnsCount); - itemWidth = (getParentActivity().getResources().getDisplayMetrics().widthPixels - ((columnsCount + 1) * Utilities.dp(4))) / columnsCount; + itemWidth = (getParentActivity().getResources().getDisplayMetrics().widthPixels - ((columnsCount + 1) * AndroidUtilities.dp(4))) / columnsCount; listView.setColumnWidth(itemWidth); listAdapter.notifyDataSetChanged(); diff --git a/TMessagesProj/src/main/java/org/telegram/ui/PhotoViewer.java b/TMessagesProj/src/main/java/org/telegram/ui/PhotoViewer.java index a4168a8c8..becadcd99 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/PhotoViewer.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/PhotoViewer.java @@ -45,12 +45,13 @@ import android.widget.ProgressBar; import android.widget.Scroller; import android.widget.TextView; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.ConnectionsManager; import org.telegram.messenger.FileLoader; import org.telegram.messenger.FileLog; -import org.telegram.messenger.LocaleController; -import org.telegram.messenger.MediaController; -import org.telegram.messenger.MessagesController; +import org.telegram.android.LocaleController; +import org.telegram.android.MediaController; +import org.telegram.android.MessagesController; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.TLRPC; @@ -102,6 +103,8 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat private boolean overlayViewVisible = true; private int animationInProgress = 0; + private long transitionAnimationStartTime = 0; + private Runnable animationEndRunnable = null; private PlaceProviderObject showAfterAnimation; private PlaceProviderObject hideAfterAnimation; private boolean disableShowCheck = false; @@ -175,7 +178,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat private final static int gallery_menu_showall = 2; private final static int gallery_menu_send = 3; - private final static int PAGE_SPACING = Utilities.dp(30); + private final static int PAGE_SPACING = AndroidUtilities.dp(30); private static class OverlayView extends FrameLayout { @@ -186,7 +189,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat actionButton = new TextView(context); actionButton.setBackgroundResource(R.drawable.system_black); - actionButton.setPadding(Utilities.dp(8), Utilities.dp(2), Utilities.dp(8), Utilities.dp(2)); + actionButton.setPadding(AndroidUtilities.dp(8), AndroidUtilities.dp(2), AndroidUtilities.dp(8), AndroidUtilities.dp(2)); actionButton.setTextColor(0xffffffff); actionButton.setTextSize(26); actionButton.setGravity(Gravity.CENTER); @@ -298,7 +301,17 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat if (currentFileName != null && currentFileName.equals(location)) { Float progress = (Float)args[1]; progressBar.setVisibility(View.VISIBLE); - progressBar.setProgress((int)(progress * 100)); + if (android.os.Build.VERSION.SDK_INT >= 11) { + progressBar.setProgress((int) (progress * 100)); + AnimatorSet animatorSet = new AnimatorSet(); + animatorSet.playTogether( + ObjectAnimator.ofInt(progressBar, "progress", (int) (progress * 100)) + ); + animatorSet.setDuration(400); + animatorSet.start(); + } else { + progressBar.setProgress((int) (progress * 100)); + } } } else if (id == MessagesController.userPhotosLoaded) { int guid = (Integer)args[4]; @@ -432,6 +445,9 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat } public void setParentActivity(Activity activity) { + if (parentActivity == activity) { + return; + } parentActivity = activity; scroller = new Scroller(activity); @@ -530,7 +546,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat @Override public boolean canOpenMenu() { if (currentFileName != null) { - File f = new File(Utilities.getCacheDir(), currentFileName); + File f = new File(AndroidUtilities.getCacheDir(), currentFileName); if (f.exists()) { return true; } @@ -548,7 +564,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat containerView.addView(bottomLayout); layoutParams = (FrameLayout.LayoutParams)bottomLayout.getLayoutParams(); layoutParams.width = FrameLayout.LayoutParams.MATCH_PARENT; - layoutParams.height = Utilities.dp(48); + layoutParams.height = AndroidUtilities.dp(48); layoutParams.gravity = Gravity.BOTTOM | Gravity.LEFT; bottomLayout.setLayoutParams(layoutParams); bottomLayout.setBackgroundColor(0x7F000000); @@ -559,7 +575,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat shareButton.setBackgroundResource(R.drawable.bar_selector_white); bottomLayout.addView(shareButton); layoutParams = (FrameLayout.LayoutParams) shareButton.getLayoutParams(); - layoutParams.width = Utilities.dp(50); + layoutParams.width = AndroidUtilities.dp(50); layoutParams.height = FrameLayout.LayoutParams.MATCH_PARENT; shareButton.setLayoutParams(layoutParams); shareButton.setOnClickListener(new View.OnClickListener() { @@ -573,7 +589,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat if (fileName == null) { return; } - File f = new File(Utilities.getCacheDir(), fileName); + File f = new File(AndroidUtilities.getCacheDir(), fileName); if (f.exists()) { Intent intent = new Intent(Intent.ACTION_SEND); if (fileName.endsWith("mp4")) { @@ -596,7 +612,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat deleteButton.setBackgroundResource(R.drawable.bar_selector_white); bottomLayout.addView(deleteButton); layoutParams = (FrameLayout.LayoutParams) deleteButton.getLayoutParams(); - layoutParams.width = Utilities.dp(50); + layoutParams.width = AndroidUtilities.dp(50); layoutParams.height = FrameLayout.LayoutParams.MATCH_PARENT; layoutParams.gravity = Gravity.RIGHT; deleteButton.setLayoutParams(layoutParams); @@ -628,9 +644,9 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat layoutParams.width = FrameLayout.LayoutParams.MATCH_PARENT; layoutParams.height = FrameLayout.LayoutParams.WRAP_CONTENT; layoutParams.gravity = Gravity.TOP; - layoutParams.leftMargin = Utilities.dp(60); - layoutParams.rightMargin = Utilities.dp(60); - layoutParams.topMargin = Utilities.dp(2); + layoutParams.leftMargin = AndroidUtilities.dp(60); + layoutParams.rightMargin = AndroidUtilities.dp(60); + layoutParams.topMargin = AndroidUtilities.dp(2); nameTextView.setLayoutParams(layoutParams); dateTextView = new TextView(containerView.getContext()); @@ -645,9 +661,9 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat layoutParams.width = FrameLayout.LayoutParams.MATCH_PARENT; layoutParams.height = FrameLayout.LayoutParams.WRAP_CONTENT; layoutParams.gravity = Gravity.TOP; - layoutParams.leftMargin = Utilities.dp(60); - layoutParams.rightMargin = Utilities.dp(60); - layoutParams.topMargin = Utilities.dp(26); + layoutParams.leftMargin = AndroidUtilities.dp(60); + layoutParams.rightMargin = AndroidUtilities.dp(60); + layoutParams.topMargin = AndroidUtilities.dp(26); dateTextView.setLayoutParams(layoutParams); pickerView = parentActivity.getLayoutInflater().inflate(R.layout.photo_picker_bottom_layout, null); @@ -675,7 +691,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat layoutParams = (FrameLayout.LayoutParams)pickerView.getLayoutParams(); layoutParams.width = FrameLayout.LayoutParams.MATCH_PARENT; - layoutParams.height = Utilities.dp(48); + layoutParams.height = AndroidUtilities.dp(48); layoutParams.gravity = Gravity.BOTTOM; pickerView.setLayoutParams(layoutParams); @@ -691,11 +707,11 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat containerView.addView(progressBar); layoutParams = (FrameLayout.LayoutParams)progressBar.getLayoutParams(); layoutParams.width = FrameLayout.LayoutParams.MATCH_PARENT; - layoutParams.height = Utilities.dp(3); + layoutParams.height = AndroidUtilities.dp(3); layoutParams.gravity = Gravity.BOTTOM | Gravity.CENTER_HORIZONTAL; - layoutParams.leftMargin = Utilities.dp(6); - layoutParams.rightMargin = Utilities.dp(6); - layoutParams.bottomMargin = Utilities.dp(48); + layoutParams.leftMargin = AndroidUtilities.dp(6); + layoutParams.rightMargin = AndroidUtilities.dp(6); + layoutParams.bottomMargin = AndroidUtilities.dp(48); progressBar.setLayoutParams(layoutParams); gestureDetector = new GestureDetector(containerView.getContext(), this); @@ -715,16 +731,16 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat checkImageView.setScaleType(ImageView.ScaleType.CENTER); checkImageView.setImageResource(R.drawable.selectphoto_large); layoutParams = (FrameLayout.LayoutParams)checkImageView.getLayoutParams(); - layoutParams.width = Utilities.dp(46); - layoutParams.height = Utilities.dp(46); + layoutParams.width = AndroidUtilities.dp(46); + layoutParams.height = AndroidUtilities.dp(46); layoutParams.gravity = Gravity.RIGHT; - layoutParams.rightMargin = Utilities.dp(10); + layoutParams.rightMargin = AndroidUtilities.dp(10); WindowManager manager = (WindowManager)ApplicationLoader.applicationContext.getSystemService(Activity.WINDOW_SERVICE); int rotation = manager.getDefaultDisplay().getRotation(); if (rotation == Surface.ROTATION_270 || rotation == Surface.ROTATION_90) { - layoutParams.topMargin = Utilities.dp(48); + layoutParams.topMargin = AndroidUtilities.dp(48); } else { - layoutParams.topMargin = Utilities.dp(58); + layoutParams.topMargin = AndroidUtilities.dp(58); } checkImageView.setLayoutParams(layoutParams); checkImageView.setOnClickListener(new View.OnClickListener() { @@ -988,7 +1004,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat load = true; } } else { - File cacheFile = new File(Utilities.getCacheDir(), currentFileName); + File cacheFile = new File(AndroidUtilities.getCacheDir(), currentFileName); if (cacheFile.exists()) { currentOverlay.actionButton.setText(LocaleController.getString("ViewVideo", R.string.ViewVideo)); } else { @@ -996,10 +1012,13 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat } } if (load) { - Float progress = FileLoader.getInstance().fileProgresses.get(currentFileName); if (FileLoader.getInstance().isLoadingFile(currentFileName)) { + Float progress = FileLoader.getInstance().fileProgresses.get(currentFileName); currentOverlay.actionButton.setText(LocaleController.getString("CancelDownload", R.string.CancelDownload)); progressBar.setVisibility(View.VISIBLE); + if (progress != null) { + progressBar.setProgress((int)(progress * 100)); + } } else { currentOverlay.actionButton.setText(String.format("%s %s", LocaleController.getString("DOWNLOAD", R.string.DOWNLOAD), Utilities.formatFileSize(currentMessageObject.messageOwner.media.video.size))); progressBar.setVisibility(View.GONE); @@ -1226,7 +1245,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat } if (currentFileName != null) { - File f = new File(Utilities.getCacheDir(), currentFileName); + File f = new File(AndroidUtilities.getCacheDir(), currentFileName); if (f.exists()) { progressBar.setVisibility(View.GONE); } else { @@ -1260,7 +1279,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat if (currentThumb != null && imageReceiver == centerImage) { placeHolder = currentThumb; } - int size = (int)(800 / Utilities.density); + int size = (int)(800 / AndroidUtilities.density); imageReceiver.setImage(photoEntry.path, String.format(Locale.US, "%d_%d", size, size), placeHolder != null ? new BitmapDrawable(null, placeHolder) : null); } else { imageReceiver.setImageBitmap((Bitmap) null); @@ -1335,8 +1354,21 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat openPhoto(null, null, null, photos, index, provider); } + private boolean checkAnimation() { + if (animationInProgress != 0) { + if (Math.abs(transitionAnimationStartTime - System.currentTimeMillis()) >= 500) { + if (animationEndRunnable != null) { + animationEndRunnable.run(); + animationEndRunnable = null; + } + animationInProgress = 0; + } + } + return animationInProgress != 0; + } + public void openPhoto(final MessageObject messageObject, final TLRPC.FileLocation fileLocation, final ArrayList messages, final ArrayList photos, final int index, final PhotoViewerProvider provider) { - if (parentActivity == null || isVisible || provider == null || animationInProgress != 0 || messageObject == null && fileLocation == null && messages == null && photos == null) { + if (parentActivity == null || isVisible || provider == null || checkAnimation() || messageObject == null && fileLocation == null && messages == null && photos == null) { return; } final PlaceProviderObject object = provider.getPlaceForPhoto(messageObject, fileLocation, index); @@ -1369,7 +1401,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat overlayViewVisible = true; if(android.os.Build.VERSION.SDK_INT >= 11) { - Utilities.lockOrientation(parentActivity); + AndroidUtilities.lockOrientation(parentActivity); animatingImageView.setVisibility(View.VISIBLE); animatingImageView.setImageBitmap(object.thumb); @@ -1391,23 +1423,23 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat public boolean onPreDraw() { containerView.getViewTreeObserver().removeOnPreDrawListener(this); - float scaleX = (float) Utilities.displaySize.x / layoutParams.width; - float scaleY = (float) (Utilities.displaySize.y - Utilities.statusBarHeight) / layoutParams.height; + float scaleX = (float) AndroidUtilities.displaySize.x / layoutParams.width; + float scaleY = (float) (AndroidUtilities.displaySize.y - AndroidUtilities.statusBarHeight) / layoutParams.height; float scale = scaleX > scaleY ? scaleY : scaleX; float width = layoutParams.width * scale; float height = layoutParams.height * scale; - float xPos = (Utilities.displaySize.x - width) / 2.0f; - float yPos = (Utilities.displaySize.y - Utilities.statusBarHeight - height) / 2.0f; + float xPos = (AndroidUtilities.displaySize.x - width) / 2.0f; + float yPos = (AndroidUtilities.displaySize.y - AndroidUtilities.statusBarHeight - height) / 2.0f; int clipHorizontal = Math.abs(object.imageReceiver.drawRegion.left - object.imageReceiver.imageX); int clipVertical = Math.abs(object.imageReceiver.drawRegion.top - object.imageReceiver.imageY); int coords2[] = new int[2]; object.parentView.getLocationInWindow(coords2); - int clipTop = coords2[1] - Utilities.statusBarHeight - (object.viewY + object.imageReceiver.drawRegion.top); + int clipTop = coords2[1] - AndroidUtilities.statusBarHeight - (object.viewY + object.imageReceiver.drawRegion.top); if (clipTop < 0) { clipTop = 0; } - int clipBottom = (object.viewY + object.imageReceiver.drawRegion.top + layoutParams.height) - (coords2[1] + object.parentView.getHeight() - Utilities.statusBarHeight); + int clipBottom = (object.viewY + object.imageReceiver.drawRegion.top + layoutParams.height) - (coords2[1] + object.parentView.getHeight() - AndroidUtilities.statusBarHeight); if (clipBottom < 0) { clipBottom = 0; } @@ -1428,14 +1460,14 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat ObjectAnimator.ofFloat(currentOverlay, "alpha", 1.0f) ); - animatorSet.setDuration(250); - animatorSet.addListener(new AnimatorListenerAdapter() { + animationEndRunnable = new Runnable() { @Override - public void onAnimationEnd(Animator animation) { + public void run() { animationInProgress = 0; + transitionAnimationStartTime = 0; containerView.invalidate(); animatingImageView.setVisibility(View.GONE); - Utilities.unlockOrientation(parentActivity); + AndroidUtilities.unlockOrientation(parentActivity); if (showAfterAnimation != null) { showAfterAnimation.imageReceiver.setVisible(true, true); } @@ -1443,7 +1475,24 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat hideAfterAnimation.imageReceiver.setVisible(false, true); } } + }; + + animatorSet.setDuration(250); + animatorSet.addListener(new AnimatorListenerAdapter() { + @Override + public void onAnimationEnd(Animator animation) { + if (animationEndRunnable != null) { + animationEndRunnable.run(); + animationEndRunnable = null; + } + } + + @Override + public void onAnimationCancel(Animator animation) { + onAnimationEnd(animation); + } }); + transitionAnimationStartTime = System.currentTimeMillis(); animatorSet.start(); animatingImageView.setOnDrawListener(new ClippingImageView.onDrawListener() { @@ -1461,6 +1510,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat }); } else { animationInProgress = 0; + transitionAnimationStartTime = 0; containerView.invalidate(); AnimationSet animationSet = new AnimationSet(true); AlphaAnimation animation = new AlphaAnimation(0.0f, 1.0f); @@ -1478,7 +1528,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat } public void closePhoto(boolean animated) { - if (parentActivity == null || !isVisible || animationInProgress != 0) { + if (parentActivity == null || !isVisible || checkAnimation()) { return; } @@ -1502,7 +1552,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat final PlaceProviderObject object = placeProvider.getPlaceForPhoto(currentMessageObject, currentFileLocation, currentIndex); if(android.os.Build.VERSION.SDK_INT >= 11 && animated) { - Utilities.lockOrientation(parentActivity); + AndroidUtilities.lockOrientation(parentActivity); animationInProgress = 1; animatingImageView.setVisibility(View.VISIBLE); @@ -1522,13 +1572,13 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat } animatingImageView.setLayoutParams(layoutParams); - float scaleX = (float) Utilities.displaySize.x / layoutParams.width; - float scaleY = (float) (Utilities.displaySize.y - Utilities.statusBarHeight) / layoutParams.height; + float scaleX = (float) AndroidUtilities.displaySize.x / layoutParams.width; + float scaleY = (float) (AndroidUtilities.displaySize.y - AndroidUtilities.statusBarHeight) / layoutParams.height; float scale2 = scaleX > scaleY ? scaleY : scaleX; float width = layoutParams.width * scale * scale2; float height = layoutParams.height * scale * scale2; - float xPos = (Utilities.displaySize.x - width) / 2.0f; - float yPos = (Utilities.displaySize.y - Utilities.statusBarHeight - height) / 2.0f; + float xPos = (AndroidUtilities.displaySize.x - width) / 2.0f; + float yPos = (AndroidUtilities.displaySize.y - AndroidUtilities.statusBarHeight - height) / 2.0f; animatingImageView.setTranslationX(xPos + translationX); animatingImageView.setTranslationY(yPos + translationY); animatingImageView.setScaleX(scale * scale2); @@ -1543,11 +1593,11 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat int coords2[] = new int[2]; object.parentView.getLocationInWindow(coords2); - int clipTop = coords2[1] - Utilities.statusBarHeight - (object.viewY + object.imageReceiver.drawRegion.top); + int clipTop = coords2[1] - AndroidUtilities.statusBarHeight - (object.viewY + object.imageReceiver.drawRegion.top); if (clipTop < 0) { clipTop = 0; } - int clipBottom = (object.viewY + object.imageReceiver.drawRegion.top + (object.imageReceiver.drawRegion.bottom - object.imageReceiver.drawRegion.top)) - (coords2[1] + object.parentView.getHeight() - Utilities.statusBarHeight); + int clipBottom = (object.viewY + object.imageReceiver.drawRegion.top + (object.imageReceiver.drawRegion.bottom - object.imageReceiver.drawRegion.top)) - (coords2[1] + object.parentView.getHeight() - AndroidUtilities.statusBarHeight); if (clipBottom < 0) { clipBottom = 0; } @@ -1570,20 +1620,36 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat animatorSet.playTogether( ObjectAnimator.ofInt(backgroundDrawable, "alpha", 0), ObjectAnimator.ofFloat(animatingImageView, "alpha", 0.0f), - ObjectAnimator.ofFloat(animatingImageView, "translationY", translationY >= 0 ? Utilities.displaySize.y : -Utilities.displaySize.y), + ObjectAnimator.ofFloat(animatingImageView, "translationY", translationY >= 0 ? AndroidUtilities.displaySize.y : -AndroidUtilities.displaySize.y), ObjectAnimator.ofFloat(containerView, "alpha", 0.0f) ); } + animationEndRunnable = new Runnable() { + @Override + public void run() { + AndroidUtilities.unlockOrientation(parentActivity); + animationInProgress = 0; + onPhotoClosed(object); + } + }; + animatorSet.setDuration(250); animatorSet.addListener(new AnimatorListenerAdapter() { @Override public void onAnimationEnd(Animator animation) { - Utilities.unlockOrientation(parentActivity); - animationInProgress = 0; - onPhotoClosed(object); + if (animationEndRunnable != null) { + animationEndRunnable.run(); + animationEndRunnable = null; + } + } + + @Override + public void onAnimationCancel(Animator animation) { + onAnimationEnd(animation); } }); + transitionAnimationStartTime = System.currentTimeMillis(); animatorSet.start(); } else { AnimationSet animationSet = new AnimationSet(true); @@ -1597,6 +1663,16 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat animationSet.addAnimation(scaleAnimation); animationSet.setDuration(150); animationInProgress = 2; + animationEndRunnable = new Runnable() { + @Override + public void run() { + if (animationListener != null) { + animationInProgress = 0; + onPhotoClosed(object); + animationListener = null; + } + } + }; animationSet.setAnimationListener(animationListener = new Animation.AnimationListener() { @Override public void onAnimationStart(Animation animation) { @@ -1605,10 +1681,9 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat @Override public void onAnimationEnd(Animation animation) { - if (animationListener != null) { - animationInProgress = 0; - onPhotoClosed(object); - animationListener = null; + if (animationEndRunnable != null) { + animationEndRunnable.run(); + animationEndRunnable = null; } } @@ -1617,10 +1692,27 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat } }); + transitionAnimationStartTime = System.currentTimeMillis(); containerView.startAnimation(animationSet); } } + public void destroyPhotoViewer() { + if (parentActivity == null || windowView == null) { + return; + } + try { + WindowManager wm = (WindowManager) parentActivity.getSystemService(Context.WINDOW_SERVICE); + if (windowView.getParent() != null) { + wm.removeViewImmediate(windowView); + } + windowView = null; + } catch (Exception e) { + FileLog.e("tmessages", e); + } + Instance = null; + } + private void onPhotoClosed(PlaceProviderObject object) { disableShowCheck = true; currentMessageObject = null; @@ -1678,7 +1770,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat private boolean onTouchEvent(MotionEvent ev) { if (animationInProgress != 0 || animationStartTime != 0) { if (animationStartTime == 0) { - Utilities.unlockOrientation(parentActivity); + AndroidUtilities.unlockOrientation(parentActivity); } return false; } @@ -1713,7 +1805,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat dragY = moveStartY = ev.getY(); draggingDown = false; canDragDown = true; - Utilities.lockOrientation(parentActivity); + AndroidUtilities.lockOrientation(parentActivity); if (velocityTracker != null) { velocityTracker.clear(); } @@ -1732,7 +1824,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat } float dx = Math.abs(ev.getX() - moveStartX); float dy = Math.abs(ev.getY() - dragY); - if (canDragDown && !draggingDown && scale == 1 && dy >= Utilities.dp(30) && dy / 2 > dx) { + if (canDragDown && !draggingDown && scale == 1 && dy >= AndroidUtilities.dp(30) && dy / 2 > dx) { draggingDown = true; moving = false; dragY = ev.getY(); @@ -1747,7 +1839,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat } else if (!invalidCoords && animationStartTime == 0) { float moveDx = moveStartX - ev.getX(); float moveDy = moveStartY - ev.getY(); - if (moving || scale == 1 && Math.abs(moveDy) + Utilities.dp(12) < Math.abs(moveDx) || scale != 1) { + if (moving || scale == 1 && Math.abs(moveDy) + AndroidUtilities.dp(12) < Math.abs(moveDx) || scale != 1) { if (!moving) { moveDx = 0; moveDy = 0; @@ -1834,11 +1926,11 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat velocity = velocityTracker.getXVelocity(); } - if((translationX < minX - containerView.getWidth() / 3 || velocity < -Utilities.dp(650)) && rightImage.hasImage()){ + if((translationX < minX - containerView.getWidth() / 3 || velocity < -AndroidUtilities.dp(650)) && rightImage.hasImage()){ goToNext(); return true; } - if((translationX > maxX + containerView.getWidth() / 3 || velocity > Utilities.dp(650)) && leftImage.hasImage()){ + if((translationX > maxX + containerView.getWidth() / 3 || velocity > AndroidUtilities.dp(650)) && leftImage.hasImage()){ goToPrev(); return true; } @@ -1855,7 +1947,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat } animateTo(scale, moveToX, moveToY); } else { - Utilities.unlockOrientation(parentActivity); + AndroidUtilities.unlockOrientation(parentActivity); } } return false; @@ -1905,7 +1997,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat toggleOverlayView(true); } if (scale == newScale && translationX == newTx && translationY == newTy) { - Utilities.unlockOrientation(parentActivity); + AndroidUtilities.unlockOrientation(parentActivity); return; } zoomAnimation = isZoom; @@ -1915,7 +2007,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat animationStartTime = System.currentTimeMillis(); animationDuration = 250; containerView.postInvalidate(); - Utilities.lockOrientation(parentActivity); + AndroidUtilities.lockOrientation(parentActivity); } private void onDraw(Canvas canvas) { @@ -1962,7 +2054,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat scale = animateToScale; animationStartTime = 0; updateMinMax(scale); - Utilities.unlockOrientation(parentActivity); + AndroidUtilities.unlockOrientation(parentActivity); zoomAnimation = false; } if (!scroller.isFinished()) { @@ -2023,10 +2115,10 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat if (scale >= 1.0f) { ImageReceiver sideImage = null; float k = 1; - if (currentTranslationX > maxX + Utilities.dp(20)) { + if (currentTranslationX > maxX + AndroidUtilities.dp(20)) { k = -1; sideImage = leftImage; - } else if (currentTranslationX < minX - Utilities.dp(20)) { + } else if (currentTranslationX < minX - AndroidUtilities.dp(20)) { sideImage = rightImage; } @@ -2078,9 +2170,9 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat WindowManager manager = (WindowManager)ApplicationLoader.applicationContext.getSystemService(Activity.WINDOW_SERVICE); int rotation = manager.getDefaultDisplay().getRotation(); if (rotation == Surface.ROTATION_270 || rotation == Surface.ROTATION_90) { - layoutParams.topMargin = Utilities.dp(48); + layoutParams.topMargin = AndroidUtilities.dp(48); } else { - layoutParams.topMargin = Utilities.dp(58); + layoutParams.topMargin = AndroidUtilities.dp(58); } checkImageView.setLayoutParams(layoutParams); return false; @@ -2105,7 +2197,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat loadFile = true; } } else { - File cacheFile = new File(Utilities.getCacheDir(), currentFileName); + File cacheFile = new File(AndroidUtilities.getCacheDir(), currentFileName); if (cacheFile.exists()) { Intent intent = new Intent(Intent.ACTION_VIEW); intent.setDataAndType(Uri.fromFile(cacheFile), "video/mp4"); diff --git a/TMessagesProj/src/main/java/org/telegram/ui/PopupNotificationActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/PopupNotificationActivity.java new file mode 100644 index 000000000..c2f86eaf1 --- /dev/null +++ b/TMessagesProj/src/main/java/org/telegram/ui/PopupNotificationActivity.java @@ -0,0 +1,977 @@ +/* + * This is the source code of Telegram for Android v. 1.4.x. + * It is licensed under GNU GPL v. 2 or later. + * You should have received a copy of the license in this archive (see LICENSE). + * + * Copyright Nikolai Kudashov, 2013-2014. + */ + +package org.telegram.ui; + +import android.app.Activity; +import android.app.KeyguardManager; +import android.content.Context; +import android.content.Intent; +import android.content.SharedPreferences; +import android.content.res.Configuration; +import android.graphics.drawable.AnimationDrawable; +import android.os.Bundle; +import android.os.PowerManager; +import android.util.AttributeSet; +import android.util.TypedValue; +import android.view.Gravity; +import android.view.MotionEvent; +import android.view.VelocityTracker; +import android.view.View; +import android.view.ViewGroup; +import android.view.ViewTreeObserver; +import android.view.WindowManager; +import android.view.animation.TranslateAnimation; +import android.widget.FrameLayout; +import android.widget.RelativeLayout; +import android.widget.TextView; + +import org.telegram.android.AndroidUtilities; +import org.telegram.android.ContactsController; +import org.telegram.android.LocaleController; +import org.telegram.android.MediaController; +import org.telegram.android.MessagesController; +import org.telegram.PhoneFormat.PhoneFormat; +import org.telegram.android.NotificationsController; +import org.telegram.messenger.ConnectionsManager; +import org.telegram.messenger.FileLog; +import org.telegram.messenger.NotificationCenter; +import org.telegram.messenger.R; +import org.telegram.messenger.TLRPC; +import org.telegram.messenger.Utilities; +import org.telegram.objects.MessageObject; +import org.telegram.objects.PhotoObject; +import org.telegram.ui.Views.ActionBar.ActionBar; +import org.telegram.ui.Views.ActionBar.ActionBarLayer; +import org.telegram.ui.Views.ActionBar.ActionBarMenu; +import org.telegram.ui.Views.BackupImageView; +import org.telegram.ui.Views.ChatActivityEnterView; +import org.telegram.ui.Views.FrameLayoutFixed; +import org.telegram.ui.Views.PopupAudioView; + +import java.io.File; +import java.util.ArrayList; + +public class PopupNotificationActivity extends Activity implements NotificationCenter.NotificationCenterDelegate { + + private ActionBarLayer actionBarLayer; + private ChatActivityEnterView chatActivityEnterView; + private BackupImageView avatarImageView; + private TextView countText; + private ViewGroup messageContainer; + private ViewGroup centerView; + private ViewGroup leftView; + private ViewGroup rightView; + private ArrayList textViews = new ArrayList(); + private ArrayList imageViews = new ArrayList(); + private ArrayList audioViews = new ArrayList(); + private VelocityTracker velocityTracker = null; + + private int classGuid; + private TLRPC.User currentUser; + private TLRPC.Chat currentChat; + private boolean finished = false; + private CharSequence lastPrintString; + private MessageObject currentMessageObject = null; + private int currentMessageNum = 0; + private PowerManager.WakeLock wakeLock = null; + private int downloadAudios = 0; + private int downloadPhotos = 0; + private boolean animationInProgress = false; + private long animationStartTime = 0; + private float moveStartX = -1; + private boolean startedMoving = false; + private Runnable onAnimationEndRunnable = null; + + private class FrameLayoutTouch extends FrameLayoutFixed { + public FrameLayoutTouch(Context context) { + super(context); + } + + public FrameLayoutTouch(Context context, AttributeSet attrs) { + super(context, attrs); + } + + public FrameLayoutTouch(Context context, AttributeSet attrs, int defStyle) { + super(context, attrs, defStyle); + } + + @Override + public boolean onInterceptTouchEvent(MotionEvent ev) { + return checkTransitionAnimation() || ((PopupNotificationActivity) getContext()).onTouchEventMy(ev); + } + + @Override + public boolean onTouchEvent(MotionEvent ev) { + return checkTransitionAnimation() || ((PopupNotificationActivity) getContext()).onTouchEventMy(ev); + } + + @Override + public void requestDisallowInterceptTouchEvent(boolean disallowIntercept) { + ((PopupNotificationActivity)getContext()).onTouchEventMy(null); + super.requestDisallowInterceptTouchEvent(disallowIntercept); + } + } + + public class FrameLayoutAnimationListener extends FrameLayoutFixed { + public FrameLayoutAnimationListener(Context context) { + super(context); + } + + public FrameLayoutAnimationListener(Context context, AttributeSet attrs) { + super(context, attrs); + } + + public FrameLayoutAnimationListener(Context context, AttributeSet attrs, int defStyle) { + super(context, attrs, defStyle); + } + + @Override + protected void onAnimationEnd() { + super.onAnimationEnd(); + if (onAnimationEndRunnable != null) { + onAnimationEndRunnable.run(); + onAnimationEndRunnable = null; + } + } + } + + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + classGuid = ConnectionsManager.getInstance().generateClassGuid(); + NotificationCenter.getInstance().addObserver(this, 1234); + NotificationCenter.getInstance().addObserver(this, NotificationsController.pushMessagesUpdated); + NotificationCenter.getInstance().addObserver(this, MessagesController.updateInterfaces); + NotificationCenter.getInstance().addObserver(this, MediaController.audioProgressDidChanged); + NotificationCenter.getInstance().addObserver(this, MediaController.audioDidReset); + NotificationCenter.getInstance().addObserver(this, MessagesController.contactsDidLoaded); + NotificationCenter.getInstance().addObserver(this, 999); + + chatActivityEnterView = new ChatActivityEnterView(); + chatActivityEnterView.setDelegate(new ChatActivityEnterView.ChatActivityEnterViewDelegate() { + @Override + public void onMessageSend() { + if (currentMessageObject == null) { + return; + } + NotificationsController.getInstance().popupMessages.remove(currentMessageNum); + MessagesController.getInstance().markDialogAsRead(currentMessageObject.getDialogId(), currentMessageObject.messageOwner.id, Math.max(0, currentMessageObject.messageOwner.id), 0, currentMessageObject.messageOwner.date, true); + currentMessageObject = null; + getNewMessage(); + } + + @Override + public void needSendTyping() { + if (currentMessageObject != null) { + MessagesController.getInstance().sendTyping(currentMessageObject.getDialogId(), classGuid); + } + } + }); + + setContentView(R.layout.popup_notification_layout); + RelativeLayout popupContainer = (RelativeLayout) findViewById(R.id.popup_container); + messageContainer = new FrameLayoutTouch(this); + popupContainer.addView(messageContainer, 0); + + ActionBar actionBar = new ActionBar(this); + popupContainer.addView(actionBar); + ViewGroup.LayoutParams layoutParams = actionBar.getLayoutParams(); + layoutParams.width = ViewGroup.LayoutParams.MATCH_PARENT; + actionBar.setLayoutParams(layoutParams); + + actionBarLayer = actionBar.createLayer(); + actionBarLayer.setDisplayHomeAsUpEnabled(true, R.drawable.ic_ab_back); + actionBarLayer.setBackgroundResource(R.color.header); + actionBarLayer.setItemsBackground(R.drawable.bar_selector); + actionBar.setCurrentActionBarLayer(actionBarLayer); + + ActionBarMenu menu = actionBarLayer.createMenu(); + View view = menu.addItemResource(2, R.layout.popup_count_layout); + countText = (TextView) view.findViewById(R.id.count_text); + + view = menu.addItemResource(1, R.layout.chat_header_layout); + avatarImageView = (BackupImageView)view.findViewById(R.id.chat_avatar_image); + avatarImageView.processDetach = false; + + actionBarLayer.setActionBarMenuOnItemClick(new ActionBarLayer.ActionBarMenuOnItemClick() { + @Override + public void onItemClick(int id) { + if (id == -1) { + onFinish(); + finish(); + } else if (id == 1) { + openCurrentMessage(); + } else if (id == 2) { + switchToNextMessage(); + } + } + }); + + chatActivityEnterView.setContainerView(this, findViewById(R.id.chat_layout)); + + PowerManager pm = (PowerManager)ApplicationLoader.applicationContext.getSystemService(Context.POWER_SERVICE); + wakeLock = pm.newWakeLock(PowerManager.SCREEN_DIM_WAKE_LOCK | PowerManager.ACQUIRE_CAUSES_WAKEUP, "screen"); + wakeLock.setReferenceCounted(false); + + handleIntent(getIntent()); + } + + @Override + public void onConfigurationChanged(Configuration newConfig) { + super.onConfigurationChanged(newConfig); + AndroidUtilities.checkDisplaySize(); + fixLayout(); + } + + @Override + protected void onNewIntent(Intent intent) { + super.onNewIntent(intent); + handleIntent(intent); + } + + private void switchToNextMessage() { + if (NotificationsController.getInstance().popupMessages.size() > 1) { + if (currentMessageNum < NotificationsController.getInstance().popupMessages.size() - 1) { + currentMessageNum++; + } else { + currentMessageNum = 0; + } + currentMessageObject = NotificationsController.getInstance().popupMessages.get(currentMessageNum); + updateInterfaceForCurrentMessage(2); + countText.setText(String.format("%d/%d", currentMessageNum + 1, NotificationsController.getInstance().popupMessages.size())); + } + } + + private void switchToPreviousMessage() { + if (NotificationsController.getInstance().popupMessages.size() > 1) { + if (currentMessageNum > 0) { + currentMessageNum--; + } else { + currentMessageNum = NotificationsController.getInstance().popupMessages.size() - 1; + } + currentMessageObject = NotificationsController.getInstance().popupMessages.get(currentMessageNum); + updateInterfaceForCurrentMessage(1); + countText.setText(String.format("%d/%d", currentMessageNum + 1, NotificationsController.getInstance().popupMessages.size())); + } + } + + public boolean checkTransitionAnimation() { + if (animationInProgress && animationStartTime < System.currentTimeMillis() - 400) { + animationInProgress = false; + if (onAnimationEndRunnable != null) { + onAnimationEndRunnable.run(); + onAnimationEndRunnable = null; + } + } + return animationInProgress; + } + + public boolean onTouchEventMy(MotionEvent motionEvent) { + if (checkTransitionAnimation()) { + return false; + } + if (motionEvent != null && motionEvent.getAction() == MotionEvent.ACTION_DOWN) { + moveStartX = motionEvent.getX(); + } else if (motionEvent != null && motionEvent.getAction() == MotionEvent.ACTION_MOVE) { + float x = motionEvent.getX(); + int diff = (int)(x - moveStartX); + if (moveStartX != -1 && !startedMoving) { + if (Math.abs(diff) > AndroidUtilities.dp(10)) { + startedMoving = true; + moveStartX = x; + AndroidUtilities.lockOrientation(this); + diff = 0; + if (velocityTracker == null) { + velocityTracker = VelocityTracker.obtain(); + } else { + velocityTracker.clear(); + } + } + } + if (startedMoving) { + if (leftView == null && diff > 0) { + diff = 0; + } + if (rightView == null && diff < 0) { + diff = 0; + } + if (velocityTracker != null) { + velocityTracker.addMovement(motionEvent); + } + applyViewsLayoutParams(diff); + } + } else if (motionEvent == null || motionEvent.getAction() == MotionEvent.ACTION_UP || motionEvent.getAction() == MotionEvent.ACTION_CANCEL) { + if (motionEvent != null && startedMoving) { + FrameLayout.LayoutParams layoutParams = (FrameLayout.LayoutParams) centerView.getLayoutParams(); + int diff = (int)(motionEvent.getX() - moveStartX); + int width = AndroidUtilities.displaySize.x - AndroidUtilities.dp(24); + int moveDiff = 0; + int forceMove = 0; + View otherView = null; + if (velocityTracker != null) { + velocityTracker.computeCurrentVelocity(1000); + if (velocityTracker.getXVelocity() >= 3500) { + forceMove = 1; + } else if (velocityTracker.getXVelocity() <= -3500) { + forceMove = 2; + } + } + if ((forceMove == 1 || diff > width / 3) && leftView != null) { + moveDiff = width - layoutParams.leftMargin; + otherView = leftView; + onAnimationEndRunnable = new Runnable() { + @Override + public void run() { + animationInProgress = false; + switchToPreviousMessage(); + AndroidUtilities.unlockOrientation(PopupNotificationActivity.this); + } + }; + } else if ((forceMove == 2 || diff < -width / 3) && rightView != null) { + moveDiff = -width - layoutParams.leftMargin; + otherView = rightView; + onAnimationEndRunnable = new Runnable() { + @Override + public void run() { + animationInProgress = false; + switchToNextMessage(); + AndroidUtilities.unlockOrientation(PopupNotificationActivity.this); + } + }; + } else if (layoutParams.leftMargin != 0) { + moveDiff = -layoutParams.leftMargin; + otherView = diff > 0 ? leftView : rightView; + onAnimationEndRunnable = new Runnable() { + @Override + public void run() { + animationInProgress = false; + applyViewsLayoutParams(0); + AndroidUtilities.unlockOrientation(PopupNotificationActivity.this); + } + }; + } + if (moveDiff != 0) { + int time = (int)(Math.abs((float)moveDiff / (float)width) * 200); + TranslateAnimation animation = new TranslateAnimation(0, moveDiff, 0, 0); + animation.setDuration(time); + centerView.startAnimation(animation); + if (otherView != null) { + animation = new TranslateAnimation(0, moveDiff, 0, 0); + animation.setDuration(time); + otherView.startAnimation(animation); + } + animationInProgress = true; + animationStartTime = System.currentTimeMillis(); + } + } else { + applyViewsLayoutParams(0); + } + if (velocityTracker != null) { + velocityTracker.recycle(); + velocityTracker = null; + } + startedMoving = false; + moveStartX = -1; + } + return startedMoving; + } + + private void applyViewsLayoutParams(int xOffset) { + FrameLayout.LayoutParams layoutParams = null; + int widht = AndroidUtilities.displaySize.x - AndroidUtilities.dp(24); + if (leftView != null) { + layoutParams = (FrameLayout.LayoutParams) leftView.getLayoutParams(); + layoutParams.gravity = Gravity.TOP | Gravity.LEFT; + layoutParams.height = ViewGroup.LayoutParams.MATCH_PARENT; + layoutParams.width = widht; + layoutParams.leftMargin = -widht + xOffset; + leftView.setLayoutParams(layoutParams); + } + if (centerView != null) { + layoutParams = (FrameLayout.LayoutParams) centerView.getLayoutParams(); + layoutParams.gravity = Gravity.TOP | Gravity.LEFT; + layoutParams.height = ViewGroup.LayoutParams.MATCH_PARENT; + layoutParams.width = widht; + layoutParams.leftMargin = xOffset; + centerView.setLayoutParams(layoutParams); + } + if (rightView != null) { + layoutParams = (FrameLayout.LayoutParams) rightView.getLayoutParams(); + layoutParams.gravity = Gravity.TOP | Gravity.LEFT; + layoutParams.height = ViewGroup.LayoutParams.MATCH_PARENT; + layoutParams.width = widht; + layoutParams.leftMargin = widht + xOffset; + rightView.setLayoutParams(layoutParams); + } + messageContainer.invalidate(); + } + + private ViewGroup getViewForMessage(int num, boolean applyOffset) { + if (NotificationsController.getInstance().popupMessages.size() == 1 && (num < 0 || num >= NotificationsController.getInstance().popupMessages.size())) { + return null; + } + if (num == -1) { + num = NotificationsController.getInstance().popupMessages.size() - 1; + } else if (num == NotificationsController.getInstance().popupMessages.size()) { + num = 0; + } + ViewGroup view = null; + MessageObject messageObject = NotificationsController.getInstance().popupMessages.get(num); + if (messageObject.type == 1) { + if (imageViews.size() > 0) { + view = imageViews.get(0); + imageViews.remove(0); + } else { + view = new FrameLayoutAnimationListener(this); + view.addView(getLayoutInflater().inflate(R.layout.popup_image_layout, null)); + view.setTag(2); + + view.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + openCurrentMessage(); + } + }); + } + + TextView messageText = (TextView)view.findViewById(R.id.message_text); + BackupImageView imageView = (BackupImageView) view.findViewById(R.id.message_image); + imageView.imageReceiver.isAspectFit = true; + PhotoObject currentPhotoObject = PhotoObject.getClosestImageWithSize(messageObject.photoThumbs, 800, 800); + boolean photoSet = false; + if (currentPhotoObject != null) { + boolean photoExist = true; + String fileName = MessageObject.getAttachFileName(currentPhotoObject.photoOwner); + if (messageObject.type == 1) { + File cacheFile = new File(AndroidUtilities.getCacheDir(), fileName); + if (!cacheFile.exists()) { + photoExist = false; + } + } + if (photoExist || downloadPhotos == 0 || downloadPhotos == 2 && ConnectionsManager.isConnectedToWiFi()) { + imageView.setImage(currentPhotoObject.photoOwner.location, "100_100", messageObject.imagePreview, currentPhotoObject.photoOwner.size); + photoSet = true; + } else { + if (messageObject.imagePreview != null) { + imageView.setImageBitmap(messageObject.imagePreview); + photoSet = true; + } + } + } + if (!photoSet) { + imageView.setVisibility(View.GONE); + messageText.setVisibility(View.VISIBLE); + messageText.setTextSize(TypedValue.COMPLEX_UNIT_SP, MessagesController.getInstance().fontSize); + messageText.setText(messageObject.messageText); + } else { + imageView.setVisibility(View.VISIBLE); + messageText.setVisibility(View.GONE); + } + } else if (messageObject.type == 2) { + PopupAudioView cell = null; + if (audioViews.size() > 0) { + view = audioViews.get(0); + audioViews.remove(0); + cell = (PopupAudioView)view.findViewWithTag(300); + } else { + view = new FrameLayoutAnimationListener(this); + view.addView(getLayoutInflater().inflate(R.layout.popup_audio_layout, null)); + view.setTag(3); + + view.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + openCurrentMessage(); + } + }); + + ViewGroup audioContainer = (ViewGroup)view.findViewById(R.id.audio_container); + cell = new PopupAudioView(this); + cell.setTag(300); + audioContainer.addView(cell); + } + + cell.setMessageObject(messageObject); + if ((downloadAudios == 0 || downloadAudios == 2 && ConnectionsManager.isConnectedToWiFi())) { + cell.downloadAudioIfNeed(); + } + } else { + if (textViews.size() > 0) { + view = textViews.get(0); + textViews.remove(0); + } else { + view = new FrameLayoutAnimationListener(this); + view.addView(getLayoutInflater().inflate(R.layout.popup_text_layout, null)); + view.setTag(1); + + View textContainer = view.findViewById(R.id.text_container); + textContainer.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + openCurrentMessage(); + } + }); + } + TextView messageText = (TextView)view.findViewById(R.id.message_text); + messageText.setTextSize(TypedValue.COMPLEX_UNIT_SP, MessagesController.getInstance().fontSize); + messageText.setText(messageObject.messageText); + } + if (view.getParent() == null) { + messageContainer.addView(view); + } + view.setVisibility(View.VISIBLE); + + if (applyOffset) { + int widht = AndroidUtilities.displaySize.x - AndroidUtilities.dp(24); + FrameLayout.LayoutParams layoutParams = (FrameLayout.LayoutParams) view.getLayoutParams(); + layoutParams.gravity = Gravity.TOP | Gravity.LEFT; + layoutParams.height = ViewGroup.LayoutParams.MATCH_PARENT; + layoutParams.width = widht; + if (num == currentMessageNum) { + layoutParams.leftMargin = 0; + } else if (num == currentMessageNum - 1) { + layoutParams.leftMargin = -widht; + } else if (num == currentMessageNum + 1) { + layoutParams.leftMargin = widht; + } + view.setLayoutParams(layoutParams); + view.invalidate(); + } + + return view; + } + + private void reuseView(ViewGroup view) { + if (view == null) { + return; + } + int tag = (Integer)view.getTag(); + view.setVisibility(View.GONE); + if (tag == 1) { + textViews.add(view); + } else if (tag == 2) { + imageViews.add(view); + } else if (tag == 3) { + audioViews.add(view); + } + } + + private void prepareLayouts(int move) { + if (move == 0) { + reuseView(centerView); + reuseView(leftView); + reuseView(rightView); + for (int a = currentMessageNum - 1; a < currentMessageNum + 2; a++) { + if (a == currentMessageNum - 1) { + leftView = getViewForMessage(a, true); + } else if (a == currentMessageNum) { + centerView = getViewForMessage(a, true); + } else if (a == currentMessageNum + 1) { + rightView = getViewForMessage(a, true); + } + } + } else if (move == 1) { + reuseView(rightView); + rightView = centerView; + centerView = leftView; + leftView = getViewForMessage(currentMessageNum - 1, true); + } else if (move == 2) { + reuseView(leftView); + leftView = centerView; + centerView = rightView; + rightView = getViewForMessage(currentMessageNum + 1, true); + } else if (move == 3) { + if (rightView != null) { + int offset = ((FrameLayout.LayoutParams) rightView.getLayoutParams()).leftMargin; + reuseView(rightView); + rightView = getViewForMessage(currentMessageNum + 1, false); + int widht = AndroidUtilities.displaySize.x - AndroidUtilities.dp(24); + FrameLayout.LayoutParams layoutParams = (FrameLayout.LayoutParams) rightView.getLayoutParams(); + layoutParams.gravity = Gravity.TOP | Gravity.LEFT; + layoutParams.height = ViewGroup.LayoutParams.MATCH_PARENT; + layoutParams.width = widht; + layoutParams.leftMargin = offset; + rightView.setLayoutParams(layoutParams); + rightView.invalidate(); + } + } else if (move == 4) { + if (leftView != null) { + int offset = ((FrameLayout.LayoutParams) leftView.getLayoutParams()).leftMargin; + reuseView(leftView); + leftView = getViewForMessage(0, false); + int widht = AndroidUtilities.displaySize.x - AndroidUtilities.dp(24); + FrameLayout.LayoutParams layoutParams = (FrameLayout.LayoutParams) leftView.getLayoutParams(); + layoutParams.gravity = Gravity.TOP | Gravity.LEFT; + layoutParams.height = ViewGroup.LayoutParams.MATCH_PARENT; + layoutParams.width = widht; + layoutParams.leftMargin = offset; + leftView.setLayoutParams(layoutParams); + leftView.invalidate(); + } + } + } + + private void fixLayout() { + messageContainer.getViewTreeObserver().addOnPreDrawListener(new ViewTreeObserver.OnPreDrawListener() { + @Override + public boolean onPreDraw() { + messageContainer.getViewTreeObserver().removeOnPreDrawListener(this); + if (!checkTransitionAnimation() && !startedMoving) { + ViewGroup.MarginLayoutParams layoutParams = (ViewGroup.MarginLayoutParams)messageContainer.getLayoutParams(); + if (!Utilities.isTablet(PopupNotificationActivity.this) && PopupNotificationActivity.this.getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { + layoutParams.topMargin = AndroidUtilities.dp(40); + } else { + layoutParams.topMargin = AndroidUtilities.dp(48); + } + layoutParams.bottomMargin = AndroidUtilities.dp(48); + layoutParams.width = ViewGroup.MarginLayoutParams.MATCH_PARENT; + layoutParams.height = ViewGroup.MarginLayoutParams.MATCH_PARENT; + messageContainer.setLayoutParams(layoutParams); + applyViewsLayoutParams(0); + } + return false; + } + }); + } + + private void handleIntent(Intent intent) { + KeyguardManager km = (KeyguardManager) getSystemService(KEYGUARD_SERVICE); + if (km.inKeyguardRestrictedInputMode() || !ApplicationLoader.isScreenOn) { + getWindow().addFlags( + WindowManager.LayoutParams.FLAG_DIM_BEHIND | + WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED | + WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON | + WindowManager.LayoutParams.FLAG_FORCE_NOT_FULLSCREEN); + } else { + getWindow().addFlags( + WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED | + WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON | + WindowManager.LayoutParams.FLAG_FORCE_NOT_FULLSCREEN); + getWindow().clearFlags(WindowManager.LayoutParams.FLAG_DIM_BEHIND); + } + + if (currentMessageObject == null) { + currentMessageNum = 0; + } + getNewMessage(); + } + + private void getNewMessage() { + if (NotificationsController.getInstance().popupMessages.isEmpty()) { + onFinish(); + finish(); + return; + } + + boolean found = false; + if ((currentMessageNum != 0 || chatActivityEnterView.hasText() || startedMoving) && currentMessageObject != null) { + for (int a = 0; a < NotificationsController.getInstance().popupMessages.size(); a++) { + if (NotificationsController.getInstance().popupMessages.get(a).messageOwner.id == currentMessageObject.messageOwner.id) { + currentMessageNum = a; + found = true; + break; + } + } + } + if (!found) { + currentMessageNum = 0; + currentMessageObject = NotificationsController.getInstance().popupMessages.get(0); + updateInterfaceForCurrentMessage(0); + } else if (startedMoving) { + if (currentMessageNum == NotificationsController.getInstance().popupMessages.size() - 1) { + prepareLayouts(3); + } else if (currentMessageNum == 1) { + prepareLayouts(4); + } + } + countText.setText(String.format("%d/%d", currentMessageNum + 1, NotificationsController.getInstance().popupMessages.size())); + } + + private void openCurrentMessage() { + if (currentMessageObject == null) { + return; + } + Intent intent = new Intent(ApplicationLoader.applicationContext, LaunchActivity.class); + long dialog_id = currentMessageObject.getDialogId(); + if ((int)dialog_id != 0) { + int lower_id = (int)dialog_id; + if (lower_id < 0) { + intent.putExtra("chatId", -lower_id); + } else { + intent.putExtra("userId", lower_id); + } + } else { + intent.putExtra("encId", (int)(dialog_id >> 32)); + } + intent.setAction("com.tmessages.openchat" + Math.random() + Integer.MAX_VALUE); + intent.setFlags(0x00008000); + startActivity(intent); + onFinish(); + finish(); + } + + private void updateInterfaceForCurrentMessage(int move) { + if (actionBarLayer == null) { + return; + } + currentChat = null; + currentUser = null; + long dialog_id = currentMessageObject.getDialogId(); + chatActivityEnterView.setDialogId(dialog_id); + if ((int)dialog_id != 0) { + int lower_id = (int)dialog_id; + if (lower_id > 0) { + currentUser = MessagesController.getInstance().users.get(lower_id); + } else { + currentChat = MessagesController.getInstance().chats.get(-lower_id); + currentUser = MessagesController.getInstance().users.get(currentMessageObject.messageOwner.from_id); + } + } else { + TLRPC.EncryptedChat encryptedChat = MessagesController.getInstance().encryptedChats.get((int)(dialog_id >> 32)); + currentUser = MessagesController.getInstance().users.get(encryptedChat.user_id); + } + + if (currentChat != null && currentUser != null) { + actionBarLayer.setTitle(currentChat.title); + actionBarLayer.setSubtitle(Utilities.formatName(currentUser.first_name, currentUser.last_name)); + actionBarLayer.setTitleIcon(0, 0); + } else if (currentUser != null) { + actionBarLayer.setTitle(Utilities.formatName(currentUser.first_name, currentUser.last_name)); + if ((int)dialog_id == 0) { + actionBarLayer.setTitleIcon(R.drawable.ic_lock_white, AndroidUtilities.dp(4)); + } else { + actionBarLayer.setTitleIcon(0, 0); + } + } + + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("mainconfig", Activity.MODE_PRIVATE); + + if (currentChat != null) { + downloadPhotos = preferences.getInt("photo_download_chat2", 0); + downloadAudios = preferences.getInt("audio_download_chat2", 0); + } else { + downloadPhotos = preferences.getInt("photo_download_user2", 0); + downloadAudios = preferences.getInt("audio_download_user2", 0); + } + + prepareLayouts(move); + updateSubtitle(); + checkAndUpdateAvatar(); + applyViewsLayoutParams(0); + } + + private void updateSubtitle() { + if (actionBarLayer == null) { + return; + } + if (currentChat != null || currentUser == null) { + return; + } + if (currentUser.id / 1000 != 777 && currentUser.id / 1000 != 333 && ContactsController.getInstance().contactsDict.get(currentUser.id) == null && (ContactsController.getInstance().contactsDict.size() != 0 || !ContactsController.getInstance().isLoadingContacts())) { + if (currentUser.phone != null && currentUser.phone.length() != 0) { + actionBarLayer.setTitle(PhoneFormat.getInstance().format("+" + currentUser.phone)); + } else { + actionBarLayer.setTitle(Utilities.formatName(currentUser.first_name, currentUser.last_name)); + } + } else { + actionBarLayer.setTitle(Utilities.formatName(currentUser.first_name, currentUser.last_name)); + } + CharSequence printString = MessagesController.getInstance().printingStrings.get(currentMessageObject.getDialogId()); + if (printString == null || printString.length() == 0) { + lastPrintString = null; + setTypingAnimation(false); + TLRPC.User user = MessagesController.getInstance().users.get(currentUser.id); + if (user != null) { + currentUser = user; + } + actionBarLayer.setSubtitle(LocaleController.formatUserStatus(currentUser)); + } else { + lastPrintString = printString; + actionBarLayer.setSubtitle(printString); + setTypingAnimation(true); + } + } + + private void checkAndUpdateAvatar() { + TLRPC.FileLocation newPhoto = null; + int placeHolderId = 0; + if (currentChat != null) { + TLRPC.Chat chat = MessagesController.getInstance().chats.get(currentChat.id); + if (chat == null) { + return; + } + currentChat = chat; + if (currentChat.photo != null) { + newPhoto = currentChat.photo.photo_small; + } + placeHolderId = Utilities.getGroupAvatarForId(currentChat.id); + } else if (currentUser != null) { + TLRPC.User user = MessagesController.getInstance().users.get(currentUser.id); + if (user == null) { + return; + } + currentUser = user; + if (currentUser.photo != null) { + newPhoto = currentUser.photo.photo_small; + } + placeHolderId = Utilities.getUserAvatarForId(currentUser.id); + } + if (avatarImageView != null) { + avatarImageView.setImage(newPhoto, "50_50", placeHolderId); + } + } + + private void setTypingAnimation(boolean start) { + if (actionBarLayer == null) { + return; + } + if (start) { + try { + actionBarLayer.setSubTitleIcon(R.drawable.typing_dots, AndroidUtilities.dp(4)); + AnimationDrawable mAnim = (AnimationDrawable)actionBarLayer.getSubTitleIcon(); + mAnim.setAlpha(200); + mAnim.start(); + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } else { + actionBarLayer.setSubTitleIcon(0, 0); + } + } + + @Override + public void onBackPressed() { + if (chatActivityEnterView.isEmojiPopupShowing()) { + chatActivityEnterView.hideEmojiPopup(); + return; + } + super.onBackPressed(); + } + + @Override + protected void onResume() { + super.onResume(); + if (chatActivityEnterView != null) { + chatActivityEnterView.setFieldFocused(true); + } + ConnectionsManager.getInstance().setAppPaused(false, false); + fixLayout(); + wakeLock.acquire(7000); + } + + @Override + protected void onPause() { + super.onPause(); + overridePendingTransition(0, 0); + if (chatActivityEnterView != null) { + chatActivityEnterView.hideEmojiPopup(); + chatActivityEnterView.setFieldFocused(false); + } + ConnectionsManager.getInstance().setAppPaused(true, false); + if (wakeLock.isHeld()) { + wakeLock.release(); + } + } + + @Override + public void didReceivedNotification(int id, Object... args) { + if (id == 1234) { + onFinish(); + finish(); + } else if (id == NotificationsController.pushMessagesUpdated) { + getNewMessage(); + } else if (id == MessagesController.updateInterfaces) { + if (currentMessageObject == null) { + return; + } + int updateMask = (Integer)args[0]; + if ((updateMask & MessagesController.UPDATE_MASK_NAME) != 0 || (updateMask & MessagesController.UPDATE_MASK_STATUS) != 0 || (updateMask & MessagesController.UPDATE_MASK_CHAT_NAME) != 0 || (updateMask & MessagesController.UPDATE_MASK_CHAT_MEMBERS) != 0) { + updateSubtitle(); + } + if ((updateMask & MessagesController.UPDATE_MASK_AVATAR) != 0 || (updateMask & MessagesController.UPDATE_MASK_CHAT_AVATAR) != 0) { + checkAndUpdateAvatar(); + } + if ((updateMask & MessagesController.UPDATE_MASK_USER_PRINT) != 0) { + CharSequence printString = MessagesController.getInstance().printingStrings.get(currentMessageObject.getDialogId()); + if (lastPrintString != null && printString == null || lastPrintString == null && printString != null || lastPrintString != null && printString != null && !lastPrintString.equals(printString)) { + updateSubtitle(); + } + } + } else if (id == MediaController.audioDidReset) { + Integer mid = (Integer)args[0]; + if (messageContainer != null) { + int count = messageContainer.getChildCount(); + for (int a = 0; a < count; a++) { + View view = messageContainer.getChildAt(a); + if ((Integer)view.getTag() == 3) { + PopupAudioView cell = (PopupAudioView)view.findViewWithTag(300); + if (cell.getMessageObject() != null && cell.getMessageObject().messageOwner.id == mid) { + cell.updateButtonState(); + break; + } + } + } + } + } else if (id == MediaController.audioProgressDidChanged) { + Integer mid = (Integer)args[0]; + if (messageContainer != null) { + int count = messageContainer.getChildCount(); + for (int a = 0; a < count; a++) { + View view = messageContainer.getChildAt(a); + if ((Integer)view.getTag() == 3) { + PopupAudioView cell = (PopupAudioView)view.findViewWithTag(300); + if (cell.getMessageObject() != null && cell.getMessageObject().messageOwner.id == mid) { + cell.updateProgress(); + break; + } + } + } + } + } else if (id == 999) { + if (messageContainer != null) { + int count = messageContainer.getChildCount(); + for (int a = 0; a < count; a++) { + View view = messageContainer.getChildAt(a); + view.invalidate(); + } + } + } else if (id == MessagesController.contactsDidLoaded) { + updateSubtitle(); + } + } + + @Override + protected void onDestroy() { + super.onDestroy(); + onFinish(); + if (wakeLock.isHeld()) { + wakeLock.release(); + } + } + + protected void onFinish() { + if (finished) { + return; + } + finished = true; + NotificationCenter.getInstance().removeObserver(this, 1234); + NotificationCenter.getInstance().removeObserver(this, NotificationsController.pushMessagesUpdated); + NotificationCenter.getInstance().removeObserver(this, MessagesController.updateInterfaces); + NotificationCenter.getInstance().removeObserver(this, MediaController.audioProgressDidChanged); + NotificationCenter.getInstance().removeObserver(this, MediaController.audioDidReset); + NotificationCenter.getInstance().removeObserver(this, MessagesController.contactsDidLoaded); + NotificationCenter.getInstance().removeObserver(this, 999); + if (chatActivityEnterView != null) { + chatActivityEnterView.onDestroy(); + } + if (wakeLock.isHeld()) { + wakeLock.release(); + } + } +} diff --git a/TMessagesProj/src/main/java/org/telegram/ui/ProfileNotificationsActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/ProfileNotificationsActivity.java index 7acc1fbb3..506a8770e 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/ProfileNotificationsActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/ProfileNotificationsActivity.java @@ -26,15 +26,21 @@ import android.widget.AdapterView; import android.widget.ListView; import android.widget.TextView; +import org.telegram.android.MessagesController; +import org.telegram.messenger.ConnectionsManager; import org.telegram.messenger.FileLog; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; +import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; +import org.telegram.messenger.RPCRequest; +import org.telegram.messenger.TLObject; +import org.telegram.messenger.TLRPC; import org.telegram.ui.Adapters.BaseFragmentAdapter; import org.telegram.ui.Views.ActionBar.ActionBarLayer; import org.telegram.ui.Views.ActionBar.BaseFragment; import org.telegram.ui.Views.ColorPickerView; -public class ProfileNotificationsActivity extends BaseFragment { +public class ProfileNotificationsActivity extends BaseFragment implements NotificationCenter.NotificationCenterDelegate { private ListView listView; private long dialog_id; @@ -50,20 +56,22 @@ public class ProfileNotificationsActivity extends BaseFragment { dialog_id = args.getLong("dialog_id"); } - @Override - public void onFragmentDestroy() { - super.onFragmentDestroy(); - } - @Override public boolean onFragmentCreate() { settingsNotificationsRow = rowCount++; settingsVibrateRow = rowCount++; settingsLedRow = rowCount++; settingsSoundRow = rowCount++; + NotificationCenter.getInstance().addObserver(this, MessagesController.notificationsSettingsUpdated); return super.onFragmentCreate(); } + @Override + public void onFragmentDestroy() { + super.onFragmentDestroy(); + NotificationCenter.getInstance().removeObserver(this, MessagesController.notificationsSettingsUpdated); + } + @Override public View createView(LayoutInflater inflater, ViewGroup container) { if (fragmentView == null) { @@ -112,6 +120,9 @@ public class ProfileNotificationsActivity extends BaseFragment { if (listView != null) { listView.invalidateViews(); } + if (i == settingsNotificationsRow) { + updateServerNotificationsSettings(); + } } }); builder.setNegativeButton(LocaleController.getString("Cancel", R.string.Cancel), null); @@ -211,6 +222,45 @@ public class ProfileNotificationsActivity extends BaseFragment { return fragmentView; } + public void updateServerNotificationsSettings() { + if ((int)dialog_id == 0) { + return; + } + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Activity.MODE_PRIVATE); + TLRPC.TL_account_updateNotifySettings req = new TLRPC.TL_account_updateNotifySettings(); + req.settings = new TLRPC.TL_inputPeerNotifySettings(); + req.settings.sound = "default"; + req.settings.events_mask = 0; + req.settings.mute_until = preferences.getInt("notify2_" + dialog_id, 0) != 2 ? 0 : Integer.MAX_VALUE; + req.settings.show_previews = preferences.getBoolean("preview_" + dialog_id, true); + + req.peer = new TLRPC.TL_inputNotifyPeer(); + + if ((int)dialog_id < 0) { + ((TLRPC.TL_inputNotifyPeer)req.peer).peer = new TLRPC.TL_inputPeerChat(); + ((TLRPC.TL_inputNotifyPeer)req.peer).peer.chat_id = -(int)dialog_id; + } else { + TLRPC.User user = MessagesController.getInstance().users.get((int)dialog_id); + if (user == null) { + return; + } + if (user instanceof TLRPC.TL_userForeign || user instanceof TLRPC.TL_userRequest) { + ((TLRPC.TL_inputNotifyPeer)req.peer).peer = new TLRPC.TL_inputPeerForeign(); + ((TLRPC.TL_inputNotifyPeer)req.peer).peer.access_hash = user.access_hash; + } else { + ((TLRPC.TL_inputNotifyPeer)req.peer).peer = new TLRPC.TL_inputPeerContact(); + } + ((TLRPC.TL_inputNotifyPeer)req.peer).peer.user_id = (int)dialog_id; + } + + ConnectionsManager.getInstance().performRpc(req, new RPCRequest.RPCRequestDelegate() { + @Override + public void run(TLObject response, TLRPC.TL_error error) { + + } + }); + } + @Override public void onActivityResultFragment(int requestCode, int resultCode, Intent data) { if (resultCode == Activity.RESULT_OK) { @@ -248,6 +298,13 @@ public class ProfileNotificationsActivity extends BaseFragment { } } + @Override + public void didReceivedNotification(int id, Object... args) { + if (id == MessagesController.notificationsSettingsUpdated) { + listView.invalidateViews(); + } + } + private class ListAdapter extends BaseFragmentAdapter { private Context mContext; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/SettingsActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/SettingsActivity.java index 6568bad52..1c4d1697a 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/SettingsActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/SettingsActivity.java @@ -34,17 +34,19 @@ import android.widget.ListView; import android.widget.TextView; import android.widget.Toast; +import org.telegram.android.AndroidUtilities; +import org.telegram.android.ContactsController; import org.telegram.PhoneFormat.PhoneFormat; import org.telegram.messenger.BuildVars; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.SerializedData; import org.telegram.messenger.TLClassStore; import org.telegram.messenger.TLObject; import org.telegram.messenger.TLRPC; import org.telegram.messenger.ConnectionsManager; import org.telegram.messenger.FileLog; -import org.telegram.messenger.MessagesController; -import org.telegram.messenger.MessagesStorage; +import org.telegram.android.MessagesController; +import org.telegram.android.MessagesStorage; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.RPCRequest; @@ -167,7 +169,7 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter }); } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } }; NotificationCenter.getInstance().addObserver(this, MessagesController.updateInterfaces); @@ -245,7 +247,26 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter } AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); builder.setTitle(LocaleController.getString("TextSize", R.string.TextSize)); - builder.setItems(new CharSequence[]{String.format("%d", 12), String.format("%d", 13), String.format("%d", 14), String.format("%d", 15), String.format("%d", 16), String.format("%d", 17), String.format("%d", 18), String.format("%d", 19), String.format("%d", 20), String.format("%d", 21), String.format("%d", 22), String.format("%d", 23), String.format("%d", 24)}, new DialogInterface.OnClickListener() { + builder.setItems(new CharSequence[] { + String.format("%d", 12), + String.format("%d", 13), + String.format("%d", 14), + String.format("%d", 15), + String.format("%d", 16), + String.format("%d", 17), + String.format("%d", 18), + String.format("%d", 19), + String.format("%d", 20), + String.format("%d", 21), + String.format("%d", 22), + String.format("%d", 23), + String.format("%d", 24), + String.format("%d", 25), + String.format("%d", 26), + String.format("%d", 27), + String.format("%d", 28), + String.format("%d", 29), + String.format("%d", 30)}, new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("mainconfig", Activity.MODE_PRIVATE); @@ -272,7 +293,7 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter } else if (i == notificationRow) { presentFragment(new SettingsNotificationsActivity()); } else if (i == blockedRow) { - presentFragment(new SettingsBlockedUsers()); + presentFragment(new SettingsBlockedUsersActivity()); } else if (i == backgroundRow) { presentFragment(new SettingsWallpapersActivity()); } else if (i == askQuestionRow) { @@ -282,7 +303,7 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter final TextView message = new TextView(getParentActivity()); message.setText(Html.fromHtml(LocaleController.getString("AskAQuestionInfo", R.string.AskAQuestionInfo))); message.setTextSize(18); - message.setPadding(Utilities.dp(8), Utilities.dp(5), Utilities.dp(8), Utilities.dp(6)); + message.setPadding(AndroidUtilities.dp(8), AndroidUtilities.dp(5), AndroidUtilities.dp(8), AndroidUtilities.dp(6)); message.setMovementMethod(new LinkMovementMethodMy()); AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); @@ -313,7 +334,7 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter return; } AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); - builder.setMessage(LocaleController.getString("AreYouSure", R.string.AreYouSure)); + builder.setMessage(LocaleController.getString("AreYouSureSessions", R.string.AreYouSureSessions)); builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), new DialogInterface.OnClickListener() { @Override @@ -343,7 +364,7 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter MessagesController.getInstance().registerForPush(UserConfig.pushString); ConnectionsManager.getInstance().initPushConnection(); } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } }); builder.setNegativeButton(LocaleController.getString("Cancel", R.string.Cancel), null); @@ -460,7 +481,7 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter avatarImage.getLocationInWindow(coords); PhotoViewer.PlaceProviderObject object = new PhotoViewer.PlaceProviderObject(); object.viewX = coords[0]; - object.viewY = coords[1] - Utilities.statusBarHeight; + object.viewY = coords[1] - AndroidUtilities.statusBarHeight; object.parentView = listView; object.imageReceiver = avatarImage.imageReceiver; object.user_id = UserConfig.getClientUserId(); @@ -509,7 +530,9 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter if (datacentersBytes != null) { SerializedData data = new SerializedData(datacentersBytes); supportUser = (TLRPC.User)TLClassStore.Instance().TLdeserialize(data, data.readInt32()); - + if (supportUser != null && supportUser.id == 333000) { + supportUser = null; + } } } catch (Exception e) { FileLog.e("tmessages", e); @@ -564,7 +587,7 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter }); } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } else { MessagesController.getInstance().users.putIfAbsent(supportUser.id, supportUser); Bundle args = new Bundle(); @@ -725,6 +748,7 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter if (i == 0 && full) { TLRPC.User user = MessagesController.getInstance().users.get(UserConfig.getClientUserId()); if (user != null && user.photo != null && user.photo.photo_big != null) { + PhotoViewer.getInstance().setParentActivity(getParentActivity()); PhotoViewer.getInstance().openPhoto(user.photo.photo_big, SettingsActivity.this); } } else if (i == 0 && !full || i == 1 && full) { @@ -775,7 +799,7 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter }); } } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } } }); @@ -787,7 +811,7 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter textView.setText(LocaleController.getString("Online", R.string.Online)); textView = (TextView)view.findViewById(R.id.settings_name); - Typeface typeface = Utilities.getTypeface("fonts/rmedium.ttf"); + Typeface typeface = AndroidUtilities.getTypeface("fonts/rmedium.ttf"); textView.setTypeface(typeface); TLRPC.User user = MessagesController.getInstance().users.get(UserConfig.getClientUserId()); if (user == null) { @@ -926,17 +950,21 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter return; } AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); - builder.setMessage(LocaleController.getString("AreYouSure", R.string.AreYouSure)); + builder.setMessage(LocaleController.getString("AreYouSureLogout", R.string.AreYouSureLogout)); builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialogInterface, int i) { + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Activity.MODE_PRIVATE); + SharedPreferences.Editor editor = preferences.edit(); + editor.clear().commit(); NotificationCenter.getInstance().postNotificationName(1234); MessagesController.getInstance().unregistedPush(); MessagesController.getInstance().logOut(); UserConfig.clearConfig(); MessagesStorage.getInstance().cleanUp(); MessagesController.getInstance().cleanUp(); + ContactsController.getInstance().deleteAllAppAccounts(); } }); builder.setNegativeButton(LocaleController.getString("Cancel", R.string.Cancel), null); diff --git a/TMessagesProj/src/main/java/org/telegram/ui/SettingsBlockedUsers.java b/TMessagesProj/src/main/java/org/telegram/ui/SettingsBlockedUsersActivity.java similarity index 96% rename from TMessagesProj/src/main/java/org/telegram/ui/SettingsBlockedUsers.java rename to TMessagesProj/src/main/java/org/telegram/ui/SettingsBlockedUsersActivity.java index 0029f53c2..29afea2a8 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/SettingsBlockedUsers.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/SettingsBlockedUsersActivity.java @@ -20,11 +20,11 @@ import android.widget.ListView; import android.widget.TextView; import org.telegram.PhoneFormat.PhoneFormat; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLObject; import org.telegram.messenger.TLRPC; import org.telegram.messenger.ConnectionsManager; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.RPCRequest; @@ -38,7 +38,7 @@ import org.telegram.ui.Views.ActionBar.BaseFragment; import java.util.ArrayList; import java.util.HashMap; -public class SettingsBlockedUsers extends BaseFragment implements NotificationCenter.NotificationCenterDelegate, ContactsActivity.ContactsActivityDelegate { +public class SettingsBlockedUsersActivity extends BaseFragment implements NotificationCenter.NotificationCenterDelegate, ContactsActivity.ContactsActivityDelegate { private ListView listView; private ListAdapter listViewAdapter; private boolean loading; @@ -82,7 +82,7 @@ public class SettingsBlockedUsers extends BaseFragment implements NotificationCe args.putBoolean("usersAsSections", true); args.putBoolean("returnAsResult", true); ContactsActivity fragment = new ContactsActivity(args); - fragment.setDelegate(SettingsBlockedUsers.this); + fragment.setDelegate(SettingsBlockedUsersActivity.this); presentFragment(fragment); } } @@ -148,7 +148,7 @@ public class SettingsBlockedUsers extends BaseFragment implements NotificationCe public void run(TLObject response, TLRPC.TL_error error) { } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } } }); @@ -220,7 +220,7 @@ public class SettingsBlockedUsers extends BaseFragment implements NotificationCe } }); } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); ConnectionsManager.getInstance().bindRequestToGuid(requestId, classGuid); } @@ -256,7 +256,7 @@ public class SettingsBlockedUsers extends BaseFragment implements NotificationCe } @Override - public void didSelectContact(TLRPC.User user) { + public void didSelectContact(TLRPC.User user, String param) { if (user == null || blockedContactsDict.containsKey(user.id)) { return; } @@ -273,7 +273,7 @@ public class SettingsBlockedUsers extends BaseFragment implements NotificationCe public void run(TLObject response, TLRPC.TL_error error) { } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } private class ListAdapter extends BaseFragmentAdapter { diff --git a/TMessagesProj/src/main/java/org/telegram/ui/SettingsChangeNameActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/SettingsChangeNameActivity.java index 15b8578d0..9b1b355f6 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/SettingsChangeNameActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/SettingsChangeNameActivity.java @@ -19,16 +19,16 @@ import android.widget.Button; import android.widget.EditText; import android.widget.TextView; -import org.telegram.messenger.LocaleController; +import org.telegram.android.AndroidUtilities; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLObject; import org.telegram.messenger.TLRPC; import org.telegram.messenger.ConnectionsManager; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.RPCRequest; import org.telegram.messenger.UserConfig; -import org.telegram.messenger.Utilities; import org.telegram.ui.Views.ActionBar.BaseFragment; public class SettingsChangeNameActivity extends BaseFragment { @@ -120,7 +120,7 @@ public class SettingsChangeNameActivity extends BaseFragment { boolean animations = preferences.getBoolean("view_animations", true); if (!animations) { firstNameField.requestFocus(); - Utilities.showKeyboard(firstNameField); + AndroidUtilities.showKeyboard(firstNameField); } } @@ -143,12 +143,12 @@ public class SettingsChangeNameActivity extends BaseFragment { public void run(TLObject response, TLRPC.TL_error error) { } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } @Override public void onOpenAnimationEnd() { firstNameField.requestFocus(); - Utilities.showKeyboard(firstNameField); + AndroidUtilities.showKeyboard(firstNameField); } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/SettingsNotificationsActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/SettingsNotificationsActivity.java index c313a3d06..9b7298bb7 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/SettingsNotificationsActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/SettingsNotificationsActivity.java @@ -27,12 +27,14 @@ import android.widget.ListView; import android.widget.TextView; import android.widget.Toast; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; +import org.telegram.android.NotificationsController; +import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.TLObject; import org.telegram.messenger.TLRPC; import org.telegram.messenger.ConnectionsManager; import org.telegram.messenger.FileLog; -import org.telegram.messenger.MessagesController; +import org.telegram.android.MessagesController; import org.telegram.messenger.R; import org.telegram.messenger.RPCRequest; import org.telegram.messenger.Utilities; @@ -41,7 +43,7 @@ import org.telegram.ui.Views.ActionBar.ActionBarLayer; import org.telegram.ui.Views.ActionBar.BaseFragment; import org.telegram.ui.Views.ColorPickerView; -public class SettingsNotificationsActivity extends BaseFragment { +public class SettingsNotificationsActivity extends BaseFragment implements NotificationCenter.NotificationCenterDelegate { private ListView listView; private boolean reseting = false; @@ -52,19 +54,22 @@ public class SettingsNotificationsActivity extends BaseFragment { private int messageVibrateRow; private int messageSoundRow; private int messageLedRow; + private int messagePopupNotificationRow; private int groupSectionRow; private int groupAlertRow; private int groupPreviewRow; private int groupVibrateRow; private int groupSoundRow; private int groupLedRow; + private int groupPopupNotificationRow; private int inappSectionRow; private int inappSoundRow; private int inappVibrateRow; private int inappPreviewRow; private int eventsSectionRow; private int contactJoinedRow; - private int pebbleSectionRow; + private int otherSectionRow; + private int badgeNumberRow; private int pebbleAlertRow; private int resetSectionRow; private int resetNotificationsRow; @@ -78,12 +83,14 @@ public class SettingsNotificationsActivity extends BaseFragment { messagePreviewRow = rowCount++; messageVibrateRow = rowCount++; messageLedRow = rowCount++; + messagePopupNotificationRow = rowCount++; messageSoundRow = rowCount++; groupSectionRow = rowCount++; groupAlertRow = rowCount++; groupPreviewRow = rowCount++; groupVibrateRow = rowCount++; groupLedRow = rowCount++; + groupPopupNotificationRow = rowCount++; groupSoundRow = rowCount++; inappSectionRow = rowCount++; inappSoundRow = rowCount++; @@ -91,14 +98,23 @@ public class SettingsNotificationsActivity extends BaseFragment { inappPreviewRow = rowCount++; eventsSectionRow = rowCount++; contactJoinedRow = rowCount++; - pebbleSectionRow = rowCount++; + otherSectionRow = rowCount++; + badgeNumberRow = rowCount++; pebbleAlertRow = rowCount++; resetSectionRow = rowCount++; resetNotificationsRow = rowCount++; + NotificationCenter.getInstance().addObserver(this, MessagesController.notificationsSettingsUpdated); + return super.onFragmentCreate(); } + @Override + public void onFragmentDestroy() { + super.onFragmentDestroy(); + NotificationCenter.getInstance().removeObserver(this, MessagesController.notificationsSettingsUpdated); + } + @Override public View createView(LayoutInflater inflater, ViewGroup container) { if (fragmentView == null) { @@ -134,10 +150,10 @@ public class SettingsNotificationsActivity extends BaseFragment { } editor.commit(); listView.invalidateViews(); + updateServerNotificationsSettings(i == groupAlertRow); } else if (i == messagePreviewRow || i == groupPreviewRow) { SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Activity.MODE_PRIVATE); SharedPreferences.Editor editor = preferences.edit(); - boolean enabledAll = true; boolean enabled; if (i == messagePreviewRow) { enabled = preferences.getBoolean("EnablePreviewAll", true); @@ -148,6 +164,7 @@ public class SettingsNotificationsActivity extends BaseFragment { } editor.commit(); listView.invalidateViews(); + updateServerNotificationsSettings(i == groupPreviewRow); } else if (i == messageVibrateRow || i == groupVibrateRow) { SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Activity.MODE_PRIVATE); SharedPreferences.Editor editor = preferences.edit(); @@ -228,7 +245,7 @@ public class SettingsNotificationsActivity extends BaseFragment { } }); } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } else if (i == inappSoundRow) { SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Activity.MODE_PRIVATE); SharedPreferences.Editor editor = preferences.edit(); @@ -265,6 +282,14 @@ public class SettingsNotificationsActivity extends BaseFragment { editor.putBoolean("EnablePebbleNotifications", !enabled); editor.commit(); listView.invalidateViews(); + } else if (i == badgeNumberRow) { + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Activity.MODE_PRIVATE); + SharedPreferences.Editor editor = preferences.edit(); + boolean enabled = preferences.getBoolean("badgeNumber", true); + editor.putBoolean("badgeNumber", !enabled); + editor.commit(); + listView.invalidateViews(); + NotificationsController.getInstance().setBadgeEnabled(!enabled); } else if (i == notificationsServiceRow) { final SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Activity.MODE_PRIVATE); boolean enabled = preferences.getBoolean("pushService", true); @@ -342,6 +367,32 @@ public class SettingsNotificationsActivity extends BaseFragment { } }); showAlertDialog(builder); + } else if (i == messagePopupNotificationRow || i == groupPopupNotificationRow) { + AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); + builder.setTitle(LocaleController.getString("PopupNotification", R.string.PopupNotification)); + builder.setItems(new CharSequence[] { + LocaleController.getString("NoPopup", R.string.NoPopup), + LocaleController.getString("OnlyWhenScreenOn", R.string.OnlyWhenScreenOn), + LocaleController.getString("OnlyWhenScreenOff", R.string.OnlyWhenScreenOff), + LocaleController.getString("AlwaysShowPopup", R.string.AlwaysShowPopup) + }, new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialog, int which) { + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Activity.MODE_PRIVATE); + SharedPreferences.Editor editor = preferences.edit(); + if (i == messagePopupNotificationRow) { + editor.putInt("popupAll", which); + } else if (i == groupPopupNotificationRow) { + editor.putInt("popupGroup", which); + } + editor.commit(); + if (listView != null) { + listView.invalidateViews(); + } + } + }); + builder.setNegativeButton(LocaleController.getString("Cancel", R.string.Cancel), null); + showAlertDialog(builder); } } }); @@ -354,6 +405,29 @@ public class SettingsNotificationsActivity extends BaseFragment { return fragmentView; } + public void updateServerNotificationsSettings(boolean group) { + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("Notifications", Activity.MODE_PRIVATE); + TLRPC.TL_account_updateNotifySettings req = new TLRPC.TL_account_updateNotifySettings(); + req.settings = new TLRPC.TL_inputPeerNotifySettings(); + req.settings.sound = "default"; + req.settings.events_mask = 0; + if (!group) { + req.peer = new TLRPC.TL_inputNotifyUsers(); + req.settings.mute_until = preferences.getBoolean("EnableAll", true) ? 0 : Integer.MAX_VALUE; + req.settings.show_previews = preferences.getBoolean("EnablePreviewAll", true); + } else { + req.peer = new TLRPC.TL_inputNotifyChats(); + req.settings.mute_until = preferences.getBoolean("EnableGroup", true) ? 0 : Integer.MAX_VALUE; + req.settings.show_previews = preferences.getBoolean("EnablePreviewGroup", true); + } + ConnectionsManager.getInstance().performRpc(req, new RPCRequest.RPCRequestDelegate() { + @Override + public void run(TLObject response, TLRPC.TL_error error) { + + } + }); + } + @Override public void onActivityResultFragment(int requestCode, int resultCode, Intent data) { if (resultCode == Activity.RESULT_OK) { @@ -396,6 +470,13 @@ public class SettingsNotificationsActivity extends BaseFragment { } } + @Override + public void didReceivedNotification(int id, Object... args) { + if (id == MessagesController.notificationsSettingsUpdated) { + listView.invalidateViews(); + } + } + private class ListAdapter extends BaseFragmentAdapter { private Context mContext; @@ -410,7 +491,7 @@ public class SettingsNotificationsActivity extends BaseFragment { @Override public boolean isEnabled(int i) { - return !(i == messageSectionRow || i == groupSectionRow || i == inappSectionRow || i == eventsSectionRow || i == pebbleSectionRow || i == resetSectionRow); + return !(i == messageSectionRow || i == groupSectionRow || i == inappSectionRow || i == eventsSectionRow || i == otherSectionRow || i == resetSectionRow); } @Override @@ -450,8 +531,8 @@ public class SettingsNotificationsActivity extends BaseFragment { textView.setText(LocaleController.getString("InAppNotifications", R.string.InAppNotifications)); } else if (i == eventsSectionRow) { textView.setText(LocaleController.getString("Events", R.string.Events)); - } else if (i == pebbleSectionRow) { - textView.setText(LocaleController.getString("Pebble", R.string.Pebble)); + } else if (i == otherSectionRow) { + textView.setText(LocaleController.getString("PhoneOther", R.string.PhoneOther)); } else if (i == resetSectionRow) { textView.setText(LocaleController.getString("Reset", R.string.Reset)); } @@ -511,12 +592,16 @@ public class SettingsNotificationsActivity extends BaseFragment { divider.setVisibility(View.INVISIBLE); } else if (i == pebbleAlertRow) { enabled = preferences.getBoolean("EnablePebbleNotifications", false); - textView.setText(LocaleController.getString("Alert", R.string.Alert)); + textView.setText(LocaleController.getString("Pebble", R.string.Pebble)); divider.setVisibility(View.INVISIBLE); } else if (i == notificationsServiceRow) { enabled = preferences.getBoolean("pushService", true); textView.setText(LocaleController.getString("NotificationsService", R.string.NotificationsService)); divider.setVisibility(View.INVISIBLE); + } else if (i == badgeNumberRow) { + enabled = preferences.getBoolean("badgeNumber", true); + textView.setText(LocaleController.getString("BadgeNumber", R.string.BadgeNumber)); + divider.setVisibility(View.VISIBLE); } if (enabled) { checkButton.setImageResource(R.drawable.btn_check_on); @@ -553,6 +638,24 @@ public class SettingsNotificationsActivity extends BaseFragment { textView.setText(LocaleController.getString("ResetAllNotifications", R.string.ResetAllNotifications)); textViewDetail.setText(LocaleController.getString("UndoAllCustom", R.string.UndoAllCustom)); divider.setVisibility(View.INVISIBLE); + } else if (i == messagePopupNotificationRow || i == groupPopupNotificationRow) { + textView.setText(LocaleController.getString("PopupNotification", R.string.PopupNotification)); + int option = 0; + if (i == messagePopupNotificationRow) { + option = preferences.getInt("popupAll", 0); + } else if (i == groupPopupNotificationRow) { + option = preferences.getInt("popupGroup", 0); + } + if (option == 0) { + textViewDetail.setText(LocaleController.getString("NoPopup", R.string.NoPopup)); + } else if (option == 1) { + textViewDetail.setText(LocaleController.getString("OnlyWhenScreenOn", R.string.OnlyWhenScreenOn)); + } else if (option == 2) { + textViewDetail.setText(LocaleController.getString("OnlyWhenScreenOff", R.string.OnlyWhenScreenOff)); + } else if (option == 3) { + textViewDetail.setText(LocaleController.getString("AlwaysShowPopup", R.string.AlwaysShowPopup)); + } + divider.setVisibility(View.VISIBLE); } } else if (type == 3) { if (view == null) { @@ -576,13 +679,13 @@ public class SettingsNotificationsActivity extends BaseFragment { @Override public int getItemViewType(int i) { - if (i == messageSectionRow || i == groupSectionRow || i == inappSectionRow || i == eventsSectionRow || i == pebbleSectionRow || i == resetSectionRow) { + if (i == messageSectionRow || i == groupSectionRow || i == inappSectionRow || i == eventsSectionRow || i == otherSectionRow || i == resetSectionRow) { return 0; } else if (i == messageAlertRow || i == messagePreviewRow || i == messageVibrateRow || i == groupAlertRow || i == groupPreviewRow || i == groupVibrateRow || i == inappSoundRow || i == inappVibrateRow || i == inappPreviewRow || i == contactJoinedRow || - i == pebbleAlertRow || i == notificationsServiceRow) { + i == pebbleAlertRow || i == notificationsServiceRow || i == badgeNumberRow) { return 1; } else if (i == messageLedRow || i == groupLedRow) { return 3; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/SettingsWallpapersActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/SettingsWallpapersActivity.java index 088354b21..b6620d7e3 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/SettingsWallpapersActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/SettingsWallpapersActivity.java @@ -29,13 +29,14 @@ import android.widget.ImageView; import android.widget.ProgressBar; import android.widget.TextView; -import org.telegram.messenger.LocaleController; +import org.telegram.android.AndroidUtilities; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLObject; import org.telegram.messenger.TLRPC; import org.telegram.messenger.ConnectionsManager; import org.telegram.messenger.FileLoader; import org.telegram.messenger.FileLog; -import org.telegram.messenger.MessagesStorage; +import org.telegram.android.MessagesStorage; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.RPCRequest; @@ -111,8 +112,8 @@ public class SettingsWallpapersActivity extends BaseFragment implements Notifica boolean done; TLRPC.WallPaper wallPaper = wallpappersByIds.get(selectedBackground); if (wallPaper != null && wallPaper.id != 1000001 && wallPaper instanceof TLRPC.TL_wallPaper) { - int width = Utilities.displaySize.x; - int height = Utilities.displaySize.y; + int width = AndroidUtilities.displaySize.x; + int height = AndroidUtilities.displaySize.y; if (width > height) { int temp = width; width = height; @@ -120,7 +121,7 @@ public class SettingsWallpapersActivity extends BaseFragment implements Notifica } TLRPC.PhotoSize size = PhotoObject.getClosestPhotoSizeWithSize(wallPaper.sizes, width, height); String fileName = size.location.volume_id + "_" + size.location.local_id + ".jpg"; - File f = new File(Utilities.getCacheDir(), fileName); + File f = new File(AndroidUtilities.getCacheDir(), fileName); File toFile = new File(ApplicationLoader.applicationContext.getFilesDir(), "wallpaper.jpg"); try { done = Utilities.copyFile(f, toFile); @@ -216,7 +217,7 @@ public class SettingsWallpapersActivity extends BaseFragment implements Notifica if (requestCode == 10) { Utilities.addMediaToGallery(currentPicturePath); try { - Bitmap bitmap = FileLoader.loadBitmap(currentPicturePath, null, Utilities.dp(320), Utilities.dp(480)); + Bitmap bitmap = FileLoader.loadBitmap(currentPicturePath, null, AndroidUtilities.dp(320), AndroidUtilities.dp(480)); File toFile = new File(ApplicationLoader.applicationContext.getFilesDir(), "wallpaper-temp.jpg"); FileOutputStream stream = new FileOutputStream(toFile); bitmap.compress(Bitmap.CompressFormat.JPEG, 87, stream); @@ -232,7 +233,7 @@ public class SettingsWallpapersActivity extends BaseFragment implements Notifica return; } try { - Bitmap bitmap = FileLoader.loadBitmap(null, data.getData(), Utilities.dp(320), Utilities.dp(480)); + Bitmap bitmap = FileLoader.loadBitmap(null, data.getData(), AndroidUtilities.dp(320), AndroidUtilities.dp(480)); File toFile = new File(ApplicationLoader.applicationContext.getFilesDir(), "wallpaper-temp.jpg"); FileOutputStream stream = new FileOutputStream(toFile); bitmap.compress(Bitmap.CompressFormat.JPEG, 87, stream); @@ -261,8 +262,8 @@ public class SettingsWallpapersActivity extends BaseFragment implements Notifica private void processSelectedBackground() { TLRPC.WallPaper wallPaper = wallpappersByIds.get(selectedBackground); if (selectedBackground != -1 && selectedBackground != 1000001 && wallPaper != null && wallPaper instanceof TLRPC.TL_wallPaper) { - int width = Utilities.displaySize.x; - int height = Utilities.displaySize.y; + int width = AndroidUtilities.displaySize.x; + int height = AndroidUtilities.displaySize.y; if (width > height) { int temp = width; width = height; @@ -270,7 +271,7 @@ public class SettingsWallpapersActivity extends BaseFragment implements Notifica } TLRPC.PhotoSize size = PhotoObject.getClosestPhotoSizeWithSize(wallPaper.sizes, width, height); String fileName = size.location.volume_id + "_" + size.location.local_id + ".jpg"; - File f = new File(Utilities.getCacheDir(), fileName); + File f = new File(AndroidUtilities.getCacheDir(), fileName); if (!f.exists()) { progressBar.setProgress(0); loadingFile = fileName; @@ -413,7 +414,7 @@ public class SettingsWallpapersActivity extends BaseFragment implements Notifica } }); } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); ConnectionsManager.getInstance().bindRequestToGuid(reqId, classGuid); } @@ -528,7 +529,7 @@ public class SettingsWallpapersActivity extends BaseFragment implements Notifica BackupImageView image = (BackupImageView)view.findViewById(R.id.image); View selection = view.findViewById(R.id.selection); TLRPC.WallPaper wallPaper = wallPapers.get(i - 1); - TLRPC.PhotoSize size = PhotoObject.getClosestPhotoSizeWithSize(wallPaper.sizes, Utilities.dp(100), Utilities.dp(100)); + TLRPC.PhotoSize size = PhotoObject.getClosestPhotoSizeWithSize(wallPaper.sizes, AndroidUtilities.dp(100), AndroidUtilities.dp(100)); if (size != null && size.location != null) { image.setImage(size.location, "100_100", 0); } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/UserProfileActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/UserProfileActivity.java index f2fe59641..86659edf8 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/UserProfileActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/UserProfileActivity.java @@ -23,15 +23,16 @@ import android.widget.ImageButton; import android.widget.ListView; import android.widget.TextView; +import org.telegram.android.AndroidUtilities; import org.telegram.PhoneFormat.PhoneFormat; -import org.telegram.messenger.LocaleController; +import org.telegram.android.LocaleController; import org.telegram.messenger.TLObject; import org.telegram.messenger.TLRPC; import org.telegram.messenger.ConnectionsManager; -import org.telegram.messenger.ContactsController; +import org.telegram.android.ContactsController; import org.telegram.messenger.FileLog; -import org.telegram.messenger.MessagesController; -import org.telegram.messenger.MessagesStorage; +import org.telegram.android.MessagesController; +import org.telegram.android.MessagesStorage; import org.telegram.messenger.NotificationCenter; import org.telegram.messenger.R; import org.telegram.messenger.RPCRequest; @@ -51,7 +52,6 @@ public class UserProfileActivity extends BaseFragment implements NotificationCen private ListView listView; private ListAdapter listAdapter; private int user_id; - private String selectedPhone; private int totalMediaCount = -1; private boolean creatingChat = false; private long dialog_id; @@ -129,7 +129,7 @@ public class UserProfileActivity extends BaseFragment implements NotificationCen actionBarLayer.setBackOverlay(R.layout.updating_state_layout); if (dialog_id != 0) { actionBarLayer.setTitle(LocaleController.getString("SecretTitle", R.string.SecretTitle)); - actionBarLayer.setTitleIcon(R.drawable.ic_lock_white, Utilities.dp(4)); + actionBarLayer.setTitleIcon(R.drawable.ic_lock_white, AndroidUtilities.dp(4)); } else { actionBarLayer.setTitle(LocaleController.getString("ContactInfo", R.string.ContactInfo)); } @@ -140,7 +140,7 @@ public class UserProfileActivity extends BaseFragment implements NotificationCen finishFragment(); } else if (id == block_contact) { AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); - builder.setMessage(LocaleController.getString("AreYouSure", R.string.AreYouSure)); + builder.setMessage(LocaleController.getString("AreYouSureBlockContact", R.string.AreYouSureBlockContact)); builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), new DialogInterface.OnClickListener() { @Override @@ -159,7 +159,7 @@ public class UserProfileActivity extends BaseFragment implements NotificationCen public void run(TLObject response, TLRPC.TL_error error) { } - }, null, true, RPCRequest.RPCRequestClassGeneric); + }); } }); builder.setNegativeButton(LocaleController.getString("Cancel", R.string.Cancel), null); @@ -186,7 +186,7 @@ public class UserProfileActivity extends BaseFragment implements NotificationCen return; } AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); - builder.setMessage(LocaleController.getString("AreYouSure", R.string.AreYouSure)); + builder.setMessage(LocaleController.getString("AreYouSureDeleteContact", R.string.AreYouSureDeleteContact)); builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), new DialogInterface.OnClickListener() { @Override @@ -218,7 +218,7 @@ public class UserProfileActivity extends BaseFragment implements NotificationCen return; } AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); - builder.setMessage(LocaleController.getString("AreYouSure", R.string.AreYouSure)); + builder.setMessage(LocaleController.getString("AreYouSureSecretChat", R.string.AreYouSureSecretChat)); builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), new DialogInterface.OnClickListener() { @Override @@ -384,7 +384,7 @@ public class UserProfileActivity extends BaseFragment implements NotificationCen avatarImage.getLocationInWindow(coords); PhotoViewer.PlaceProviderObject object = new PhotoViewer.PlaceProviderObject(); object.viewX = coords[0]; - object.viewY = coords[1] - Utilities.statusBarHeight; + object.viewY = coords[1] - AndroidUtilities.statusBarHeight; object.parentView = listView; object.imageReceiver = avatarImage.imageReceiver; object.user_id = user_id; @@ -445,7 +445,7 @@ public class UserProfileActivity extends BaseFragment implements NotificationCen } @Override - public void didSelectDialog(MessagesActivity messageFragment, long dialog_id) { + public void didSelectDialog(MessagesActivity messageFragment, long dialog_id, boolean param) { if (dialog_id != 0) { Bundle args = new Bundle(); args.putBoolean("scrollToTopOnResume", true); @@ -524,6 +524,7 @@ public class UserProfileActivity extends BaseFragment implements NotificationCen public void onClick(View view) { TLRPC.User user = MessagesController.getInstance().users.get(user_id); if (user.photo != null && user.photo.photo_big != null) { + PhotoViewer.getInstance().setParentActivity(getParentActivity()); PhotoViewer.getInstance().openPhoto(user.photo.photo_big, UserProfileActivity.this); } } @@ -533,7 +534,7 @@ public class UserProfileActivity extends BaseFragment implements NotificationCen onlineText = (TextView)view.findViewById(R.id.settings_online); } TextView textView = (TextView)view.findViewById(R.id.settings_name); - Typeface typeface = Utilities.getTypeface("fonts/rmedium.ttf"); + Typeface typeface = AndroidUtilities.getTypeface("fonts/rmedium.ttf"); textView.setTypeface(typeface); textView.setText(Utilities.formatName(user.first_name, user.last_name)); @@ -572,29 +573,20 @@ public class UserProfileActivity extends BaseFragment implements NotificationCen if (user.phone == null || user.phone.length() == 0 || getParentActivity() == null) { return; } - selectedPhone = user.phone; AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); - builder.setItems(new CharSequence[] {LocaleController.getString("Copy", R.string.Copy), LocaleController.getString("Call", R.string.Call)}, new DialogInterface.OnClickListener() { + builder.setItems(new CharSequence[] {LocaleController.getString("Copy", R.string.Copy)}, new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialogInterface, int i) { - if (i == 1) { - try { - Intent intent = new Intent(Intent.ACTION_DIAL, Uri.parse("tel:+" + selectedPhone)); - intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); - getParentActivity().startActivity(intent); - } catch (Exception e) { - FileLog.e("tmessages", e); - } - } else if (i == 0) { + if (i == 0) { int sdk = android.os.Build.VERSION.SDK_INT; if(sdk < android.os.Build.VERSION_CODES.HONEYCOMB) { android.text.ClipboardManager clipboard = (android.text.ClipboardManager)ApplicationLoader.applicationContext.getSystemService(Context.CLIPBOARD_SERVICE); - clipboard.setText(selectedPhone); + clipboard.setText(user.phone); } else { android.content.ClipboardManager clipboard = (android.content.ClipboardManager)ApplicationLoader.applicationContext.getSystemService(Context.CLIPBOARD_SERVICE); - android.content.ClipData clip = android.content.ClipData.newPlainText("label", selectedPhone); + android.content.ClipData clip = android.content.ClipData.newPlainText("label", user.phone); clipboard.setPrimaryClip(clip); } } @@ -603,21 +595,37 @@ public class UserProfileActivity extends BaseFragment implements NotificationCen showAlertDialog(builder); } }); - } - ImageButton button = (ImageButton)view.findViewById(R.id.settings_edit_name); - button.setOnClickListener(new View.OnClickListener() { - @Override - public void onClick(View view) { - TLRPC.User user = MessagesController.getInstance().users.get(user_id); - if (user == null || user instanceof TLRPC.TL_userEmpty) { - return; + ImageButton button = (ImageButton)view.findViewById(R.id.settings_edit_name); + button.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + TLRPC.User user = MessagesController.getInstance().users.get(user_id); + if (user == null || user instanceof TLRPC.TL_userEmpty) { + return; + } + NotificationCenter.getInstance().postNotificationName(MessagesController.closeChats); + Bundle args = new Bundle(); + args.putInt("user_id", user_id); + presentFragment(new ChatActivity(args), true); } - NotificationCenter.getInstance().postNotificationName(MessagesController.closeChats); - Bundle args = new Bundle(); - args.putInt("user_id", user_id); - presentFragment(new ChatActivity(args), true); - } - }); + }); + button = (ImageButton)view.findViewById(R.id.settings_call_phone); + button.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + try { + Intent intent = new Intent(Intent.ACTION_DIAL, Uri.parse("tel:+" + user.phone)); + intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); + getParentActivity().startActivity(intent); + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + }); + } + ImageButton button = (ImageButton)view.findViewById(R.id.settings_call_phone); + button.setVisibility(user.phone == null || user.phone.length() == 0 ? View.GONE : View.VISIBLE); + TextView textView = (TextView)view.findViewById(R.id.settings_row_text); TextView detailTextView = (TextView)view.findViewById(R.id.settings_row_text_detail); View divider = view.findViewById(R.id.settings_row_divider); diff --git a/TMessagesProj/src/main/java/org/telegram/ui/VideoEditorActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/VideoEditorActivity.java new file mode 100644 index 000000000..2774c356b --- /dev/null +++ b/TMessagesProj/src/main/java/org/telegram/ui/VideoEditorActivity.java @@ -0,0 +1,552 @@ +/* + * This is the source code of Telegram for Android v. 1.7.x. + * It is licensed under GNU GPL v. 2 or later. + * You should have received a copy of the license in this archive (see LICENSE). + * + * Copyright Nikolai Kudashov, 2013-2014. + */ + +package org.telegram.ui; + +import android.content.res.Configuration; +import android.media.MediaPlayer; +import android.os.Bundle; +import android.view.LayoutInflater; +import android.view.SurfaceHolder; +import android.view.SurfaceView; +import android.view.View; +import android.view.ViewGroup; +import android.view.ViewTreeObserver; +import android.widget.FrameLayout; +import android.widget.ImageView; +import android.widget.TextView; + +import com.coremedia.iso.boxes.Container; +import com.googlecode.mp4parser.authoring.Movie; +import com.googlecode.mp4parser.authoring.Track; +import com.googlecode.mp4parser.authoring.builder.DefaultMp4Builder; +import com.googlecode.mp4parser.authoring.container.mp4.MovieCreator; +import com.googlecode.mp4parser.authoring.tracks.CroppedTrack; + +import org.telegram.android.AndroidUtilities; +import org.telegram.android.LocaleController; +import org.telegram.messenger.FileLog; +import org.telegram.messenger.R; +import org.telegram.messenger.UserConfig; +import org.telegram.messenger.Utilities; +import org.telegram.ui.Views.ActionBar.ActionBarLayer; +import org.telegram.ui.Views.ActionBar.ActionBarMenu; +import org.telegram.ui.Views.ActionBar.BaseFragment; +import org.telegram.ui.Views.VideoSeekBarView; +import org.telegram.ui.Views.VideoTimelineView; + +import java.io.File; +import java.io.FileOutputStream; +import java.nio.channels.FileChannel; +import java.util.Arrays; +import java.util.LinkedList; +import java.util.List; + +public class VideoEditorActivity extends BaseFragment implements SurfaceHolder.Callback { + + private MediaPlayer videoPlayer = null; + private SurfaceHolder surfaceHolder = null; + private VideoTimelineView videoTimelineView = null; + private View videoContainerView = null; + private TextView originalSizeTextView = null; + private TextView editedSizeTextView = null; + private View textContainerView = null; + private ImageView playButton = null; + private VideoSeekBarView videoSeekBarView = null; + + private boolean initied = false; + private String videoPath = null; + private int videoWidth; + private int videoHeight; + private float lastProgress = 0; + private boolean needSeek = false; + private VideoEditorActivityDelegate delegate; + + public interface VideoEditorActivityDelegate { + public abstract void didFinishedVideoConverting(String videoPath); + } + + private Runnable progressRunnable = new Runnable() { + @Override + public void run() { + while (videoPlayer.isPlaying()) { + Utilities.RunOnUIThread(new Runnable() { + @Override + public void run() { + if (videoPlayer.isPlaying()) { + float startTime = videoTimelineView.getLeftProgress() * videoPlayer.getDuration(); + float endTime = videoTimelineView.getRightProgress() * videoPlayer.getDuration(); + if (startTime == endTime) { + startTime = endTime - 0.01f; + } + float progress = (videoPlayer.getCurrentPosition() - startTime) / (endTime - startTime); + if (progress > lastProgress) { + videoSeekBarView.setProgress(progress); + lastProgress = progress; + } + if (videoPlayer.getCurrentPosition() >= endTime) { + try { + videoPlayer.pause(); + onPlayComplete(); + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + } + } + }); + try { + Thread.sleep(50); + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + } + }; + + public VideoEditorActivity(Bundle args) { + super(args); + videoPath = args.getString("videoPath"); + } + + @Override + public boolean onFragmentCreate() { + if (videoPath == null) { + return false; + } + videoPlayer = new MediaPlayer(); + videoPlayer.setOnCompletionListener(new MediaPlayer.OnCompletionListener() { + @Override + public void onCompletion(MediaPlayer mp) { + Utilities.RunOnUIThread(new Runnable() { + @Override + public void run() { + onPlayComplete(); + } + }); + } + }); + return super.onFragmentCreate(); + } + + @Override + public void onFragmentDestroy() { + if (videoTimelineView != null) { + videoTimelineView.destroy(); + } + super.onFragmentDestroy(); + } + + @Override + public View createView(LayoutInflater inflater, ViewGroup container) { + if (fragmentView == null) { + actionBarLayer.setBackgroundColor(0xff333333); + actionBarLayer.setItemsBackground(R.drawable.bar_selector_white); + actionBarLayer.setDisplayHomeAsUpEnabled(true, R.drawable.photo_back); + actionBarLayer.setTitle(LocaleController.getString("EditVideo", R.string.EditVideo)); + actionBarLayer.setActionBarMenuOnItemClick(new ActionBarLayer.ActionBarMenuOnItemClick() { + @Override + public void onItemClick(int id) { + if (id == -1) { + finishFragment(); + } else if (id == 1) { + try { + startConvert(); + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + } + }); + + ActionBarMenu menu = actionBarLayer.createMenu(); + View doneItem = menu.addItemResource(1, R.layout.group_create_done_layout); + + TextView doneTextView = (TextView)doneItem.findViewById(R.id.done_button); + doneTextView.setText(LocaleController.getString("Done", R.string.Done).toUpperCase()); + + fragmentView = inflater.inflate(R.layout.video_editor_layout, container, false); + originalSizeTextView = (TextView)fragmentView.findViewById(R.id.original_size); + editedSizeTextView = (TextView)fragmentView.findViewById(R.id.edited_size); + videoContainerView = fragmentView.findViewById(R.id.video_container); + textContainerView = fragmentView.findViewById(R.id.info_container); + + videoTimelineView = (VideoTimelineView)fragmentView.findViewById(R.id.video_timeline_view); + videoTimelineView.setVideoPath(videoPath); + videoTimelineView.setDelegate(new VideoTimelineView.VideoTimelineViewDelegate() { + @Override + public void onLeftProgressChanged(float progress) { + try { + if (videoPlayer.isPlaying()) { + videoPlayer.pause(); + playButton.setImageResource(R.drawable.video_play); + } + videoPlayer.setOnSeekCompleteListener(null); + videoPlayer.seekTo((int)(videoPlayer.getDuration() * progress)); + } catch (Exception e) { + FileLog.e("tmessages", e); + } + needSeek = true; + videoSeekBarView.setProgress(0); + updateVideoEditedInfo(); + } + + @Override + public void onRifhtProgressChanged(float progress) { + try { + if (videoPlayer.isPlaying()) { + videoPlayer.pause(); + playButton.setImageResource(R.drawable.video_play); + } + videoPlayer.setOnSeekCompleteListener(null); + videoPlayer.seekTo((int)(videoPlayer.getDuration() * progress)); + } catch (Exception e) { + FileLog.e("tmessages", e); + } + needSeek = true; + videoSeekBarView.setProgress(0); + updateVideoEditedInfo(); + } + }); + + videoSeekBarView = (VideoSeekBarView)fragmentView.findViewById(R.id.video_seekbar); + videoSeekBarView.delegate = new VideoSeekBarView.SeekBarDelegate() { + @Override + public void onSeekBarDrag(float progress) { + if (videoPlayer.isPlaying()) { + try { + float prog = videoTimelineView.getLeftProgress() + (videoTimelineView.getRightProgress() - videoTimelineView.getLeft()) * progress; + videoPlayer.seekTo((int)(videoPlayer.getDuration() * prog)); + lastProgress = progress; + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } else { + lastProgress = progress; + needSeek = true; + } + } + }; + + playButton = (ImageView)fragmentView.findViewById(R.id.play_button); + playButton.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + if (surfaceHolder.isCreating()) { + return; + } + play(); + } + }); + + SurfaceView surfaceView = (SurfaceView) fragmentView.findViewById(R.id.video_view); + surfaceHolder = surfaceView.getHolder(); + surfaceHolder.addCallback(this); + surfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS); + surfaceHolder.setFixedSize(270, 480); + + updateVideoOriginalInfo(); + updateVideoEditedInfo(); + } else { + ViewGroup parent = (ViewGroup)fragmentView.getParent(); + if (parent != null) { + parent.removeView(fragmentView); + } + } + return fragmentView; + } + + @Override + public void onResume() { + super.onResume(); + fixLayout(); + } + + @Override + public void onConfigurationChanged(Configuration newConfig) { + super.onConfigurationChanged(newConfig); + fixLayout(); + } + + @Override + public void surfaceCreated(SurfaceHolder holder) { + videoPlayer.setDisplay(holder); + try { + videoPlayer.setDataSource(videoPath); + videoPlayer.prepare(); + videoWidth = videoPlayer.getVideoWidth(); + videoHeight = videoPlayer.getVideoHeight(); + fixVideoSize(); + videoPlayer.seekTo((int) (videoTimelineView.getLeftProgress() * videoPlayer.getDuration())); + initied = true; + } catch (Exception e) { + FileLog.e("tmessages", e); + } + updateVideoOriginalInfo(); + updateVideoEditedInfo(); + } + + @Override + public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) { + + } + + @Override + public void surfaceDestroyed(SurfaceHolder holder) { + videoPlayer.setDisplay(null); + } + + private void onPlayComplete() { + playButton.setImageResource(R.drawable.video_play); + videoSeekBarView.setProgress(0); + try { + videoPlayer.seekTo((int) (videoTimelineView.getLeftProgress() * videoPlayer.getDuration())); + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + + private void updateVideoOriginalInfo() { + if (!initied || originalSizeTextView == null) { + return; + } + File file = new File(videoPath); + String videoDimension = String.format("%dx%d", videoPlayer.getVideoWidth(), videoPlayer.getVideoHeight()); + int minutes = videoPlayer.getDuration() / 1000 / 60; + int seconds = (int)Math.ceil(videoPlayer.getDuration() / 1000) - minutes * 60; + String videoTimeSize = String.format("%d:%02d, %s", minutes, seconds, Utilities.formatFileSize(file.length())); + originalSizeTextView.setText(String.format("%s: %s, %s", LocaleController.getString("OriginalVideo", R.string.OriginalVideo), videoDimension, videoTimeSize)); + } + + private void updateVideoEditedInfo() { + if (!initied || editedSizeTextView == null) { + return; + } + File file = new File(videoPath); + long size = file.length(); + float videoWidth = videoPlayer.getVideoWidth(); + float videoHeight = videoPlayer.getVideoHeight(); + if (videoWidth > 640 || videoHeight > 640) { + float scale = videoWidth > videoHeight ? 640.0f / videoWidth : 640.0f / videoHeight; + videoWidth *= scale; + videoHeight *= scale; + size *= (scale * scale); + } + String videoDimension = String.format("%dx%d", (int)videoWidth, (int)videoHeight); + int minutes = videoPlayer.getDuration() / 1000 / 60; + int seconds = (int)Math.ceil(videoPlayer.getDuration() / 1000) - minutes * 60; + String videoTimeSize = String.format("%d:%02d, ~%s", minutes, seconds, Utilities.formatFileSize(size)); + editedSizeTextView.setText(String.format("%s: %s, %s", LocaleController.getString("EditedVideo", R.string.EditedVideo), videoDimension, videoTimeSize)); + } + + private void fixVideoSize() { + if (videoWidth == 0 || videoHeight == 0 || fragmentView == null || getParentActivity() == null) { + return; + } + int viewHeight = 0; + if (!Utilities.isTablet(getParentActivity()) && getParentActivity().getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { + viewHeight = AndroidUtilities.displaySize.y - AndroidUtilities.statusBarHeight - AndroidUtilities.dp(40); + } else { + viewHeight = AndroidUtilities.displaySize.y - AndroidUtilities.statusBarHeight - AndroidUtilities.dp(48); + } + + int width = 0; + int height = 0; + if (getParentActivity().getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { + width = AndroidUtilities.displaySize.x - AndroidUtilities.displaySize.x / 2 - AndroidUtilities.dp(24); + height = viewHeight - AndroidUtilities.dp(32); + } else { + width = AndroidUtilities.displaySize.x; + height = viewHeight - AndroidUtilities.dp(176); + } + + float wr = (float)width / (float)videoWidth; + float hr = (float)height / (float)videoHeight; + float ar = (float)videoWidth / (float)videoHeight; + + if (wr > hr) { + width = (int) (height * ar); + } else { + height = (int) (width / ar); + } + + surfaceHolder.setFixedSize(width, height); + } + + private void fixLayout() { + if (originalSizeTextView == null) { + return; + } + originalSizeTextView.getViewTreeObserver().addOnPreDrawListener(new ViewTreeObserver.OnPreDrawListener() { + @Override + public boolean onPreDraw() { + originalSizeTextView.getViewTreeObserver().removeOnPreDrawListener(this); + if (getParentActivity().getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { + FrameLayout.LayoutParams layoutParams = (FrameLayout.LayoutParams)videoContainerView.getLayoutParams(); + layoutParams.topMargin = AndroidUtilities.dp(16); + layoutParams.bottomMargin = AndroidUtilities.dp(16); + layoutParams.width = AndroidUtilities.displaySize.x / 2 - AndroidUtilities.dp(24); + layoutParams.leftMargin = AndroidUtilities.dp(16); + videoContainerView.setLayoutParams(layoutParams); + + layoutParams = (FrameLayout.LayoutParams)textContainerView.getLayoutParams(); + layoutParams.height = FrameLayout.LayoutParams.MATCH_PARENT; + layoutParams.width = AndroidUtilities.displaySize.x / 2 - AndroidUtilities.dp(24); + layoutParams.leftMargin = AndroidUtilities.displaySize.x / 2 + AndroidUtilities.dp(8); + layoutParams.rightMargin = AndroidUtilities.dp(16); + layoutParams.topMargin = AndroidUtilities.dp(16); + textContainerView.setLayoutParams(layoutParams); + } else { + FrameLayout.LayoutParams layoutParams = (FrameLayout.LayoutParams)videoContainerView.getLayoutParams(); + layoutParams.topMargin = AndroidUtilities.dp(16); + layoutParams.bottomMargin = AndroidUtilities.dp(160); + layoutParams.width = FrameLayout.LayoutParams.MATCH_PARENT; + layoutParams.leftMargin = 0; + videoContainerView.setLayoutParams(layoutParams); + + layoutParams = (FrameLayout.LayoutParams)textContainerView.getLayoutParams(); + layoutParams.height = AndroidUtilities.dp(143); + layoutParams.width = FrameLayout.LayoutParams.MATCH_PARENT; + layoutParams.leftMargin = 0; + layoutParams.rightMargin = 0; + layoutParams.topMargin = 0; + textContainerView.setLayoutParams(layoutParams); + } + fixVideoSize(); + videoTimelineView.clearFrames(); + return false; + } + }); + } + + private void play() { + if (videoPlayer.isPlaying()) { + videoPlayer.pause(); + playButton.setImageResource(R.drawable.video_play); + } else { + try { + playButton.setImageDrawable(null); + lastProgress = 0; + if (needSeek) { + float prog = videoTimelineView.getLeftProgress() + (videoTimelineView.getRightProgress() - videoTimelineView.getLeft()) * videoSeekBarView.getProgress(); + videoPlayer.seekTo((int)(videoPlayer.getDuration() * prog)); + needSeek = false; + } + videoPlayer.setOnSeekCompleteListener(new MediaPlayer.OnSeekCompleteListener() { + @Override + public void onSeekComplete(MediaPlayer mp) { + float startTime = videoTimelineView.getLeftProgress() * videoPlayer.getDuration(); + float endTime = videoTimelineView.getRightProgress() * videoPlayer.getDuration(); + if (startTime == endTime) { + startTime = endTime - 0.01f; + } + lastProgress = (videoPlayer.getCurrentPosition() - startTime) / (endTime - startTime); + videoSeekBarView.setProgress(lastProgress); + } + }); + videoPlayer.start(); + new Thread(progressRunnable).start(); + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + } + + public void setDelegate(VideoEditorActivityDelegate delegate) { + this.delegate = delegate; + } + + private void startConvert() throws Exception { + Movie movie = MovieCreator.build(videoPath); + + List tracks = movie.getTracks(); + movie.setTracks(new LinkedList()); + + double startTime = videoTimelineView.getLeftProgress() * videoPlayer.getDuration() / 1000.0; + double endTime = videoTimelineView.getRightProgress() * videoPlayer.getDuration() / 1000.0; + + boolean timeCorrected = false; + for (Track track : tracks) { + if (track.getSyncSamples() != null && track.getSyncSamples().length > 0) { + if (timeCorrected) { + throw new RuntimeException("The startTime has already been corrected by another track with SyncSample. Not Supported."); + } + startTime = correctTimeToSyncSample(track, startTime, false); + endTime = correctTimeToSyncSample(track, endTime, true); + timeCorrected = true; + } + } + + for (Track track : tracks) { + long currentSample = 0; + double currentTime = 0; + double lastTime = 0; + long startSample = -1; + long endSample = -1; + + for (int i = 0; i < track.getSampleDurations().length; i++) { + long delta = track.getSampleDurations()[i]; + if (currentTime > lastTime && currentTime <= startTime) { + startSample = currentSample; + } + if (currentTime > lastTime && currentTime <= endTime) { + endSample = currentSample; + } + lastTime = currentTime; + currentTime += (double) delta / (double) track.getTrackMetaData().getTimescale(); + currentSample++; + } + movie.addTrack(new CroppedTrack(track, startSample, endSample)); + } + long start1 = System.currentTimeMillis(); + Container out = new DefaultMp4Builder().build(movie); + long start2 = System.currentTimeMillis(); + + String fileName = Integer.MIN_VALUE + "_" + UserConfig.lastLocalId + ".mp4"; + UserConfig.lastLocalId--; + File cacheFile = new File(AndroidUtilities.getCacheDir(), fileName); + UserConfig.saveConfig(false); + + FileOutputStream fos = new FileOutputStream(cacheFile); + FileChannel fc = fos.getChannel(); + out.writeContainer(fc); + + fc.close(); + fos.close(); + if (delegate != null) { + delegate.didFinishedVideoConverting(cacheFile.getAbsolutePath()); + finishFragment(); + } + } + + private static double correctTimeToSyncSample(Track track, double cutHere, boolean next) { + double[] timeOfSyncSamples = new double[track.getSyncSamples().length]; + long currentSample = 0; + double currentTime = 0; + for (int i = 0; i < track.getSampleDurations().length; i++) { + long delta = track.getSampleDurations()[i]; + if (Arrays.binarySearch(track.getSyncSamples(), currentSample + 1) >= 0) { + timeOfSyncSamples[Arrays.binarySearch(track.getSyncSamples(), currentSample + 1)] = currentTime; + } + currentTime += (double) delta / (double) track.getTrackMetaData().getTimescale(); + currentSample++; + } + double previous = 0; + for (double timeOfSyncSample : timeOfSyncSamples) { + if (timeOfSyncSample > cutHere) { + if (next) { + return timeOfSyncSample; + } else { + return previous; + } + } + previous = timeOfSyncSample; + } + return timeOfSyncSamples[timeOfSyncSamples.length - 1]; + } +} diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBar.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBar.java index 76ae5d374..faf729a6a 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBar.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBar.java @@ -19,6 +19,7 @@ import android.view.View; import android.view.ViewGroup; import android.widget.FrameLayout; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; @@ -52,7 +53,7 @@ public class ActionBar extends FrameLayout { addView(shadowView); shadowView.setVisibility(INVISIBLE); ViewGroup.LayoutParams layoutParams = shadowView.getLayoutParams(); - layoutParams.width = Utilities.dp(2); + layoutParams.width = AndroidUtilities.dp(2); layoutParams.height = LayoutParams.MATCH_PARENT; shadowView.setLayoutParams(layoutParams); shadowView.setBackgroundResource(R.drawable.shadow); @@ -116,7 +117,7 @@ public class ActionBar extends FrameLayout { layoutParams.width = LayoutParams.MATCH_PARENT; layoutParams.height = LayoutParams.MATCH_PARENT; layer.setLayoutParams(layoutParams); - shadowView.setX(-Utilities.dp(2)); + shadowView.setX(-AndroidUtilities.dp(2)); shadowView.setVisibility(VISIBLE); previousLayer.setBackOverlayVisible(isBackOverlayVisible); } @@ -143,7 +144,7 @@ public class ActionBar extends FrameLayout { return; } currentLayer.setX(dx); - shadowView.setX(dx - Utilities.dp(2)); + shadowView.setX(dx - AndroidUtilities.dp(2)); if (dx != 0) { if (previousLayer != null) { previousLayer.setAlpha(Math.min(1, (float) dx / (float) currentLayer.getMeasuredWidth())); @@ -159,11 +160,11 @@ public class ActionBar extends FrameLayout { public void setupAnimations(ArrayList animators, boolean back) { if (back) { animators.add(ObjectAnimator.ofFloat(currentLayer, "x", 0)); - animators.add(ObjectAnimator.ofFloat(shadowView, "x", -Utilities.dp(2))); + animators.add(ObjectAnimator.ofFloat(shadowView, "x", -AndroidUtilities.dp(2))); animators.add(ObjectAnimator.ofFloat(previousLayer, "alpha", 0)); } else { animators.add(ObjectAnimator.ofFloat(currentLayer, "x", getMeasuredWidth())); - animators.add(ObjectAnimator.ofFloat(shadowView, "x", getMeasuredWidth() - Utilities.dp(2))); + animators.add(ObjectAnimator.ofFloat(shadowView, "x", getMeasuredWidth() - AndroidUtilities.dp(2))); animators.add(ObjectAnimator.ofFloat(previousLayer, "alpha", 1.0f)); } } @@ -171,9 +172,9 @@ public class ActionBar extends FrameLayout { @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { if (!Utilities.isTablet(getContext()) && getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { - super.onMeasure(widthMeasureSpec, MeasureSpec.makeMeasureSpec(Utilities.dp(40), MeasureSpec.EXACTLY)); + super.onMeasure(widthMeasureSpec, MeasureSpec.makeMeasureSpec(AndroidUtilities.dp(40), MeasureSpec.EXACTLY)); } else { - super.onMeasure(widthMeasureSpec, MeasureSpec.makeMeasureSpec(Utilities.dp(48), MeasureSpec.EXACTLY)); + super.onMeasure(widthMeasureSpec, MeasureSpec.makeMeasureSpec(AndroidUtilities.dp(48), MeasureSpec.EXACTLY)); } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarActivity.java index 3cdcd8ddb..40b72321a 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarActivity.java @@ -32,6 +32,7 @@ import android.view.animation.Animation; import android.view.animation.AnimationUtils; import android.widget.FrameLayout; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.FileLog; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; @@ -139,7 +140,7 @@ public class ActionBarActivity extends Activity { contentView.addView(shadowView); shadowView.setBackgroundResource(R.drawable.shadow); ViewGroup.LayoutParams layoutParams = shadowView.getLayoutParams(); - layoutParams.width = Utilities.dp(2); + layoutParams.width = AndroidUtilities.dp(2); layoutParams.height = FrameLayout.LayoutParams.MATCH_PARENT; shadowView.setLayoutParams(layoutParams); shadowView.setVisibility(View.INVISIBLE); @@ -202,7 +203,7 @@ public class ActionBarActivity extends Activity { containerViewBack.setX(0); actionBar.stopMoving(backAnimation); shadowView.setVisibility(View.INVISIBLE); - shadowView.setX(-Utilities.dp(2)); + shadowView.setX(-AndroidUtilities.dp(2)); if (!backAnimation) { BaseFragment lastFragment = fragmentsStack.get(fragmentsStack.size() - 1); lastFragment.onPause(); @@ -229,7 +230,7 @@ public class ActionBarActivity extends Activity { } } containerViewBack.setVisibility(View.GONE); - Utilities.unlockOrientation(this); + AndroidUtilities.unlockOrientation(this); startedTracking = false; animationInProgress = false; } @@ -239,7 +240,7 @@ public class ActionBarActivity extends Activity { startedTracking = true; startedTrackingX = (int) ev.getX(); shadowView.setVisibility(View.VISIBLE); - shadowView.setX(-Utilities.dp(2)); + shadowView.setX(-AndroidUtilities.dp(2)); containerViewBack.setVisibility(View.VISIBLE); beginTrackingSent = false; @@ -260,7 +261,7 @@ public class ActionBarActivity extends Activity { } lastFragment.onResume(); - Utilities.lockOrientation(this); + AndroidUtilities.lockOrientation(this); } public boolean onTouchEvent(MotionEvent ev) { @@ -284,12 +285,12 @@ public class ActionBarActivity extends Activity { int dx = Math.max(0, (int) (ev.getX() - startedTrackingX)); int dy = Math.abs((int)ev.getY() - startedTrackingY); velocityTracker.addMovement(ev); - if (maybeStartTracking && !startedTracking && dx >= Utilities.dp(10) && Math.abs(dx) / 3 > dy) { + if (maybeStartTracking && !startedTracking && dx >= AndroidUtilities.dp(10) && Math.abs(dx) / 3 > dy) { prepareForMoving(ev); } else if (startedTracking) { if (!beginTrackingSent) { if (getCurrentFocus() != null) { - Utilities.hideKeyboard(getCurrentFocus()); + AndroidUtilities.hideKeyboard(getCurrentFocus()); } BaseFragment currentFragment = fragmentsStack.get(fragmentsStack.size() - 1); currentFragment.onBeginSlide(); @@ -297,7 +298,7 @@ public class ActionBarActivity extends Activity { } actionBar.moveActionBarByX(dx); containerView.setX(dx); - shadowView.setX(dx - Utilities.dp(2)); + shadowView.setX(dx - AndroidUtilities.dp(2)); } } else if (ev != null && ev.getPointerId(0) == startedTrackingPointerId && (ev.getAction() == MotionEvent.ACTION_CANCEL || ev.getAction() == MotionEvent.ACTION_UP || ev.getAction() == MotionEvent.ACTION_POINTER_UP)) { if (velocityTracker == null) { @@ -321,11 +322,11 @@ public class ActionBarActivity extends Activity { if (!backAnimation) { distToMove = containerView.getMeasuredWidth() - x; animators.add(ObjectAnimator.ofFloat(containerView, "x", containerView.getMeasuredWidth())); - animators.add(ObjectAnimator.ofFloat(shadowView, "x", containerView.getMeasuredWidth() - Utilities.dp(2))); + animators.add(ObjectAnimator.ofFloat(shadowView, "x", containerView.getMeasuredWidth() - AndroidUtilities.dp(2))); } else { distToMove = x; animators.add(ObjectAnimator.ofFloat(containerView, "x", 0)); - animators.add(ObjectAnimator.ofFloat(shadowView, "x", -Utilities.dp(2))); + animators.add(ObjectAnimator.ofFloat(shadowView, "x", -AndroidUtilities.dp(2))); } actionBar.setupAnimations(animators, backAnimation); @@ -439,9 +440,9 @@ public class ActionBarActivity extends Activity { int height = 0; if (actionBar.getVisibility() == View.VISIBLE) { if (!Utilities.isTablet(this) && getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { - height = Utilities.dp(40); + height = AndroidUtilities.dp(40); } else { - height = Utilities.dp(48); + height = AndroidUtilities.dp(48); } } @@ -500,7 +501,7 @@ public class ActionBarActivity extends Activity { return false; } if (getCurrentFocus() != null) { - Utilities.hideKeyboard(getCurrentFocus()); + AndroidUtilities.hideKeyboard(getCurrentFocus()); } boolean needAnimation = openAnimation != null && !forceWithoutAnimation && getSharedPreferences("mainconfig", Activity.MODE_PRIVATE).getBoolean("view_animations", true); @@ -575,7 +576,7 @@ public class ActionBarActivity extends Activity { return; } if (getCurrentFocus() != null) { - Utilities.hideKeyboard(getCurrentFocus()); + AndroidUtilities.hideKeyboard(getCurrentFocus()); } boolean needAnimation = animated && closeAnimation != null && getSharedPreferences("mainconfig", Activity.MODE_PRIVATE).getBoolean("view_animations", true); final BaseFragment currentFragment = fragmentsStack.get(fragmentsStack.size() - 1); @@ -634,6 +635,7 @@ public class ActionBarActivity extends Activity { } public void removeFragmentFromStack(BaseFragment fragment) { + fragment.onPause(); fragment.onFragmentDestroy(); fragment.setParentActivity(null); fragmentsStack.remove(fragment); diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarLayer.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarLayer.java index 5e8567a18..701624e00 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarLayer.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarLayer.java @@ -21,6 +21,7 @@ import android.widget.FrameLayout; import android.widget.ImageView; import android.widget.TextView; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; @@ -65,7 +66,7 @@ public class ActionBarLayer extends FrameLayout { layoutParams.height = LayoutParams.FILL_PARENT; layoutParams.gravity = Gravity.TOP | Gravity.LEFT; backButtonFrameLayout.setLayoutParams(layoutParams); - backButtonFrameLayout.setPadding(0, 0, Utilities.dp(4), 0); + backButtonFrameLayout.setPadding(0, 0, AndroidUtilities.dp(4), 0); backButtonFrameLayout.setOnClickListener(new OnClickListener() { @Override public void onClick(View view) { @@ -99,7 +100,7 @@ public class ActionBarLayer extends FrameLayout { layoutParams.width = LayoutParams.WRAP_CONTENT; layoutParams.height = LayoutParams.WRAP_CONTENT; layoutParams.gravity = Gravity.TOP | Gravity.LEFT; - layoutParams.setMargins(Utilities.dp(3), (height - backButtonImageView.getDrawable().getIntrinsicHeight()) / 2, 0, 0); + layoutParams.setMargins(AndroidUtilities.dp(3), (height - backButtonImageView.getDrawable().getIntrinsicHeight()) / 2, 0, 0); backButtonImageView.setLayoutParams(layoutParams); } } @@ -110,11 +111,11 @@ public class ActionBarLayer extends FrameLayout { if (!Utilities.isTablet(getContext()) && getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { layoutParams.width = (int)(logoImageView.getDrawable().getIntrinsicWidth() / 1.3f); layoutParams.height = (int)(logoImageView.getDrawable().getIntrinsicHeight() / 1.3f); - layoutParams.setMargins(Utilities.dp(12), (height - layoutParams.height) / 2, 0, 0); + layoutParams.setMargins(AndroidUtilities.dp(12), (height - layoutParams.height) / 2, 0, 0); } else { layoutParams.width = logoImageView.getDrawable().getIntrinsicWidth(); layoutParams.height = logoImageView.getDrawable().getIntrinsicHeight(); - layoutParams.setMargins(Utilities.dp(12), (height - layoutParams.width) / 2, 0, 0); + layoutParams.setMargins(AndroidUtilities.dp(12), (height - layoutParams.width) / 2, 0, 0); } layoutParams.gravity = Gravity.TOP | Gravity.LEFT; logoImageView.setLayoutParams(layoutParams); @@ -122,9 +123,9 @@ public class ActionBarLayer extends FrameLayout { } private void positionTitle(int width, int height) { - int offset = Utilities.dp(2); + int offset = AndroidUtilities.dp(2); if (!Utilities.isTablet(getContext()) && getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { - offset = Utilities.dp(1); + offset = AndroidUtilities.dp(1); } int maxTextWidth = 0; @@ -163,17 +164,17 @@ public class ActionBarLayer extends FrameLayout { int x = 0; if (logoImageView == null || logoImageView.getVisibility() == GONE) { - x = Utilities.dp(16); + x = AndroidUtilities.dp(16); } else { if (!Utilities.isTablet(getContext()) && getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { - x = Utilities.dp(22) + (int)(logoImageView.getDrawable().getIntrinsicWidth() / 1.3f); + x = AndroidUtilities.dp(22) + (int)(logoImageView.getDrawable().getIntrinsicWidth() / 1.3f); } else { - x = Utilities.dp(22) + logoImageView.getDrawable().getIntrinsicWidth(); + x = AndroidUtilities.dp(22) + logoImageView.getDrawable().getIntrinsicWidth(); } } if (menu != null) { - maxTextWidth = Math.min(maxTextWidth, width - menu.getMeasuredWidth() - Utilities.dp(16)); + maxTextWidth = Math.min(maxTextWidth, width - menu.getMeasuredWidth() - AndroidUtilities.dp(16)); } if (titleTextView != null && titleTextView.getVisibility() == VISIBLE) { @@ -196,7 +197,7 @@ public class ActionBarLayer extends FrameLayout { } ViewGroup.LayoutParams layoutParams1 = backButtonFrameLayout.getLayoutParams(); - layoutParams1.width = x + maxTextWidth + (isSearchFieldVisible ? 0 : Utilities.dp(6)); + layoutParams1.width = x + maxTextWidth + (isSearchFieldVisible ? 0 : AndroidUtilities.dp(6)); backButtonFrameLayout.setLayoutParams(layoutParams1); } @@ -206,7 +207,7 @@ public class ActionBarLayer extends FrameLayout { } FrameLayout.LayoutParams layoutParams = (FrameLayout.LayoutParams)menu.getLayoutParams(); layoutParams.width = isSearchFieldVisible ? LayoutParams.MATCH_PARENT : LayoutParams.WRAP_CONTENT; - layoutParams.leftMargin = isSearchFieldVisible ? Utilities.dp(26) + logoImageView.getDrawable().getIntrinsicWidth() : 0; + layoutParams.leftMargin = isSearchFieldVisible ? AndroidUtilities.dp(26) + logoImageView.getDrawable().getIntrinsicWidth() : 0; menu.setLayoutParams(layoutParams); menu.measure(width, height); } @@ -402,7 +403,7 @@ public class ActionBarLayer extends FrameLayout { if (subTitleTextView != null) { subTitleTextView.setVisibility(visible ? GONE : VISIBLE); } - backButtonFrameLayout.setPadding(0, 0, visible ? 0 : Utilities.dp(4), 0); + backButtonFrameLayout.setPadding(0, 0, visible ? 0 : AndroidUtilities.dp(4), 0); if (visible) { oldUseLogo = logoImageView != null && logoImageView.getVisibility() == VISIBLE; setDisplayUseLogoEnabled(true, R.drawable.ic_ab_search); @@ -495,7 +496,7 @@ public class ActionBarLayer extends FrameLayout { layoutParams.height = LayoutParams.MATCH_PARENT; actionOverlay.setLayoutParams(layoutParams); actionOverlay.measure(widthMeasureSpec, heightMeasureSpec); - layoutParams.width = Math.min(actionOverlay.getMeasuredWidth() + Utilities.dp(4), widthMeasureSpec - (menu != null ? menu.getMeasuredWidth() : 0)); + layoutParams.width = Math.min(actionOverlay.getMeasuredWidth() + AndroidUtilities.dp(4), widthMeasureSpec - (menu != null ? menu.getMeasuredWidth() : 0)); actionOverlay.setLayoutParams(layoutParams); } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarMenu.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarMenu.java index 823eb704b..b22b439e4 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarMenu.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarMenu.java @@ -16,7 +16,7 @@ import android.widget.FrameLayout; import android.widget.ImageView; import android.widget.LinearLayout; -import org.telegram.messenger.Utilities; +import org.telegram.android.AndroidUtilities; public class ActionBarMenu extends LinearLayout { @@ -68,7 +68,7 @@ public class ActionBarMenu extends LinearLayout { addView(menuItem); LinearLayout.LayoutParams layoutParams = (LinearLayout.LayoutParams)menuItem.getLayoutParams(); layoutParams.height = FrameLayout.LayoutParams.MATCH_PARENT; - layoutParams.width = Utilities.dp(56); + layoutParams.width = AndroidUtilities.dp(56); menuItem.setLayoutParams(layoutParams); menuItem.setOnClickListener(new OnClickListener() { @Override diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarMenuItem.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarMenuItem.java index a655d93d8..e3c1117df 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarMenuItem.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/ActionBar/ActionBarMenuItem.java @@ -26,6 +26,7 @@ import android.widget.ImageView; import android.widget.LinearLayout; import android.widget.TextView; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.R; import org.telegram.messenger.Utilities; @@ -151,8 +152,8 @@ public class ActionBarMenuItem extends ImageView { delimeter.setBackgroundColor(0xffdcdcdc); popupLayout.addView(delimeter); LinearLayout.LayoutParams layoutParams = (LinearLayout.LayoutParams)delimeter.getLayoutParams(); - layoutParams.width = Utilities.dp(196); - layoutParams.height = Utilities.density >= 3 ? 2 : 1; + layoutParams.width = AndroidUtilities.dp(196); + layoutParams.height = AndroidUtilities.density >= 3 ? 2 : 1; delimeter.setLayoutParams(layoutParams); delimeter.setTag(100 + id); } @@ -160,19 +161,19 @@ public class ActionBarMenuItem extends ImageView { textView.setTextColor(0xff000000); textView.setBackgroundResource(R.drawable.list_selector); textView.setGravity(Gravity.CENTER_VERTICAL); - textView.setPadding(Utilities.dp(16), 0, Utilities.dp(16), 0); + textView.setPadding(AndroidUtilities.dp(16), 0, AndroidUtilities.dp(16), 0); textView.setTextSize(18); - textView.setMinWidth(Utilities.dp(196)); + textView.setMinWidth(AndroidUtilities.dp(196)); textView.setTag(id); textView.setText(text); if (icon != 0) { - textView.setCompoundDrawablePadding(Utilities.dp(12)); + textView.setCompoundDrawablePadding(AndroidUtilities.dp(12)); textView.setCompoundDrawablesWithIntrinsicBounds(getResources().getDrawable(icon), null, null, null); } popupLayout.addView(textView); LinearLayout.LayoutParams layoutParams = (LinearLayout.LayoutParams)textView.getLayoutParams(); layoutParams.width = LinearLayout.LayoutParams.WRAP_CONTENT; - layoutParams.height = Utilities.dp(48); + layoutParams.height = AndroidUtilities.dp(48); textView.setLayoutParams(layoutParams); textView.setOnClickListener(new OnClickListener() { @Override @@ -201,7 +202,7 @@ public class ActionBarMenuItem extends ImageView { popupWindow.setClippingEnabled(true); popupWindow.setInputMethodMode(ActionBarPopupWindow.INPUT_METHOD_NOT_NEEDED); popupWindow.setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_UNSPECIFIED); - popupLayout.measure(MeasureSpec.makeMeasureSpec(Utilities.dp(1000), MeasureSpec.AT_MOST), MeasureSpec.makeMeasureSpec(Utilities.dp(1000), MeasureSpec.AT_MOST)); + popupLayout.measure(MeasureSpec.makeMeasureSpec(AndroidUtilities.dp(1000), MeasureSpec.AT_MOST), MeasureSpec.makeMeasureSpec(AndroidUtilities.dp(1000), MeasureSpec.AT_MOST)); } popupWindow.setFocusable(true); if (popupLayout.getMeasuredWidth() == 0) { @@ -219,7 +220,7 @@ public class ActionBarMenuItem extends ImageView { if (searchField.getVisibility() == VISIBLE) { searchField.setVisibility(GONE); setVisibility(VISIBLE); - Utilities.hideKeyboard(searchField); + AndroidUtilities.hideKeyboard(searchField); if (listener != null) { listener.onSearchCollapse(); } @@ -229,7 +230,7 @@ public class ActionBarMenuItem extends ImageView { setVisibility(GONE); searchField.setText(""); searchField.requestFocus(); - Utilities.showKeyboard(searchField); + AndroidUtilities.showKeyboard(searchField); if (listener != null) { listener.onSearchExpand(); } @@ -254,13 +255,13 @@ public class ActionBarMenuItem extends ImageView { searchField.setTextColor(0xffffffff); searchField.setSingleLine(true); searchField.setBackgroundResource(R.drawable.search_light_states); - searchField.setPadding(Utilities.dp(6), 0, Utilities.dp(6), 0); + searchField.setPadding(AndroidUtilities.dp(6), 0, AndroidUtilities.dp(6), 0); searchField.setInputType(EditorInfo.TYPE_TEXT_FLAG_NO_SUGGESTIONS); searchField.setOnEditorActionListener(new TextView.OnEditorActionListener() { @Override public boolean onEditorAction(TextView v, int actionId, KeyEvent event) { if (actionId == EditorInfo.IME_ACTION_SEARCH || event != null && event.getAction() == KeyEvent.ACTION_UP && event.getKeyCode() == KeyEvent.KEYCODE_SEARCH) { - Utilities.hideKeyboard(searchField); + AndroidUtilities.hideKeyboard(searchField); } return false; } @@ -308,8 +309,8 @@ public class ActionBarMenuItem extends ImageView { layoutParams.weight = 1; layoutParams.width = 0; layoutParams.gravity = Gravity.CENTER_VERTICAL; - layoutParams.height = Utilities.dp(36); - layoutParams.rightMargin = Utilities.dp(4); + layoutParams.height = AndroidUtilities.dp(36); + layoutParams.rightMargin = AndroidUtilities.dp(4); searchField.setLayoutParams(layoutParams); searchField.setVisibility(GONE); } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/AvatarUpdater.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/AvatarUpdater.java index 0deea1222..10fbf3c4b 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/AvatarUpdater.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/AvatarUpdater.java @@ -15,6 +15,7 @@ import android.net.Uri; import android.os.Bundle; import android.provider.MediaStore; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.TLRPC; import org.telegram.messenger.FileLoader; import org.telegram.messenger.FileLog; @@ -117,8 +118,8 @@ public class AvatarUpdater implements NotificationCenter.NotificationCenterDeleg if (bitmap == null) { return; } - smallPhoto = FileLoader.scaleAndSaveImage(bitmap, 100, 100, 87, false); - bigPhoto = FileLoader.scaleAndSaveImage(bitmap, 800, 800, 87, false); + smallPhoto = FileLoader.scaleAndSaveImage(bitmap, 100, 100, 80, false); + bigPhoto = FileLoader.scaleAndSaveImage(bitmap, 800, 800, 80, false); if (bigPhoto != null && smallPhoto != null) { if (returnOnly) { if (delegate != null) { @@ -126,7 +127,7 @@ public class AvatarUpdater implements NotificationCenter.NotificationCenterDeleg } } else { UserConfig.saveConfig(false); - uploadingAvatar = Utilities.getCacheDir() + "/" + bigPhoto.location.volume_id + "_" + bigPhoto.location.local_id + ".jpg"; + uploadingAvatar = AndroidUtilities.getCacheDir() + "/" + bigPhoto.location.volume_id + "_" + bigPhoto.location.local_id + ".jpg"; NotificationCenter.getInstance().addObserver(AvatarUpdater.this, FileLoader.FileDidUpload); NotificationCenter.getInstance().addObserver(AvatarUpdater.this, FileLoader.FileDidFailUpload); FileLoader.getInstance().uploadFile(uploadingAvatar, false); diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/BackupImageView.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/BackupImageView.java index 598b4e501..7afc9c1de 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/BackupImageView.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/BackupImageView.java @@ -18,8 +18,6 @@ import android.view.View; import org.telegram.messenger.TLRPC; -import java.lang.ref.WeakReference; - public class BackupImageView extends View { public ImageReceiver imageReceiver; public boolean processDetach = true; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/ChatActivityEnterView.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/ChatActivityEnterView.java new file mode 100644 index 000000000..06f7ba7df --- /dev/null +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/ChatActivityEnterView.java @@ -0,0 +1,647 @@ +/* + * This is the source code of Telegram for Android v. 1.4.x. + * It is licensed under GNU GPL v. 2 or later. + * You should have received a copy of the license in this archive (see LICENSE). + * + * Copyright Nikolai Kudashov, 2013-2014. + */ + +package org.telegram.ui.Views; + +import android.animation.Animator; +import android.app.Activity; +import android.content.Context; +import android.content.SharedPreferences; +import android.graphics.Rect; +import android.os.PowerManager; +import android.text.Editable; +import android.text.TextWatcher; +import android.text.style.ImageSpan; +import android.view.KeyEvent; +import android.view.MotionEvent; +import android.view.Surface; +import android.view.View; +import android.view.WindowManager; +import android.view.animation.AccelerateDecelerateInterpolator; +import android.view.inputmethod.EditorInfo; +import android.view.inputmethod.InputMethodManager; +import android.widget.EditText; +import android.widget.FrameLayout; +import android.widget.ImageButton; +import android.widget.ImageView; +import android.widget.PopupWindow; +import android.widget.TextView; + +import org.telegram.android.AndroidUtilities; +import org.telegram.android.Emoji; +import org.telegram.android.LocaleController; +import org.telegram.android.MediaController; +import org.telegram.android.MessagesController; +import org.telegram.messenger.ConnectionsManager; +import org.telegram.messenger.FileLog; +import org.telegram.messenger.NotificationCenter; +import org.telegram.messenger.R; +import org.telegram.messenger.TLRPC; +import org.telegram.ui.ApplicationLoader; + +public class ChatActivityEnterView implements NotificationCenter.NotificationCenterDelegate, SizeNotifierRelativeLayout.SizeNotifierRelativeLayoutDelegate { + + public static interface ChatActivityEnterViewDelegate { + public abstract void onMessageSend(); + public abstract void needSendTyping(); + } + + private EditText messsageEditText; + private ImageButton sendButton; + private PopupWindow emojiPopup; + private ImageView emojiButton; + private EmojiView emojiView; + private TextView recordTimeText; + private ImageButton audioSendButton; + private View recordPanel; + private View slideText; + private PowerManager.WakeLock mWakeLock = null; + private SizeNotifierRelativeLayout sizeNotifierRelativeLayout; + + private int keyboardHeight = 0; + private int keyboardHeightLand = 0; + private boolean keyboardVisible; + private boolean sendByEnter = false; + private long lastTypingTimeSend = 0; + private String lastTimeString = null; + private float startedDraggingX = -1; + private float distCanMove = AndroidUtilities.dp(80); + private boolean recordingAudio = false; + + private Activity parentActivity; + private long dialog_id; + private boolean ignoreTextChange = false; + private ChatActivityEnterViewDelegate delegate; + + public ChatActivityEnterView() { + NotificationCenter.getInstance().addObserver(this, MediaController.recordStarted); + NotificationCenter.getInstance().addObserver(this, MediaController.recordStartError); + NotificationCenter.getInstance().addObserver(this, MediaController.recordStopped); + NotificationCenter.getInstance().addObserver(this, MediaController.recordProgressChanged); + NotificationCenter.getInstance().addObserver(this, MessagesController.closeChats); + NotificationCenter.getInstance().addObserver(this, MediaController.audioDidSent); + NotificationCenter.getInstance().addObserver(this, 999); + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("mainconfig", Activity.MODE_PRIVATE); + sendByEnter = preferences.getBoolean("send_by_enter", false); + } + + public void onDestroy() { + NotificationCenter.getInstance().removeObserver(this, MediaController.recordStarted); + NotificationCenter.getInstance().removeObserver(this, MediaController.recordStartError); + NotificationCenter.getInstance().removeObserver(this, MediaController.recordStopped); + NotificationCenter.getInstance().removeObserver(this, MediaController.recordProgressChanged); + NotificationCenter.getInstance().removeObserver(this, MessagesController.closeChats); + NotificationCenter.getInstance().removeObserver(this, MediaController.audioDidSent); + NotificationCenter.getInstance().removeObserver(this, 999); + if (mWakeLock != null) { + try { + mWakeLock.release(); + mWakeLock = null; + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + if (sizeNotifierRelativeLayout != null) { + sizeNotifierRelativeLayout.delegate = null; + sizeNotifierRelativeLayout = null; + } + } + + public void setContainerView(Activity activity, View containerView) { + parentActivity = activity; + + sizeNotifierRelativeLayout = (SizeNotifierRelativeLayout)containerView.findViewById(R.id.chat_layout); + sizeNotifierRelativeLayout.delegate = this; + + messsageEditText = (EditText)containerView.findViewById(R.id.chat_text_edit); + messsageEditText.setHint(LocaleController.getString("TypeMessage", R.string.TypeMessage)); + + sendButton = (ImageButton)containerView.findViewById(R.id.chat_send_button); + sendButton.setEnabled(false); + sendButton.setVisibility(View.INVISIBLE); + emojiButton = (ImageView)containerView.findViewById(R.id.chat_smile_button); + audioSendButton = (ImageButton)containerView.findViewById(R.id.chat_audio_send_button); + recordPanel = containerView.findViewById(R.id.record_panel); + recordTimeText = (TextView)containerView.findViewById(R.id.recording_time_text); + slideText = containerView.findViewById(R.id.slideText); + TextView textView = (TextView)containerView.findViewById(R.id.slideToCancelTextView); + textView.setText(LocaleController.getString("SlideToCancel", R.string.SlideToCancel)); + + emojiButton.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + if (emojiPopup == null) { + showEmojiPopup(true); + } else { + showEmojiPopup(!emojiPopup.isShowing()); + } + } + }); + + messsageEditText.setOnKeyListener(new View.OnKeyListener() { + @Override + public boolean onKey(View view, int i, KeyEvent keyEvent) { + if (i == 4 && !keyboardVisible && emojiPopup != null && emojiPopup.isShowing()) { + if (keyEvent.getAction() == 1) { + showEmojiPopup(false); + } + return true; + } else if (i == KeyEvent.KEYCODE_ENTER && sendByEnter && keyEvent.getAction() == KeyEvent.ACTION_DOWN) { + sendMessage(); + return true; + } + return false; + } + }); + + messsageEditText.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + if (emojiPopup != null && emojiPopup.isShowing()) { + showEmojiPopup(false); + } + } + }); + + messsageEditText.setOnEditorActionListener(new TextView.OnEditorActionListener() { + @Override + public boolean onEditorAction(TextView textView, int i, KeyEvent keyEvent) { + if (i == EditorInfo.IME_ACTION_SEND) { + sendMessage(); + return true; + } else if (sendByEnter) { + if (keyEvent != null && i == EditorInfo.IME_NULL && keyEvent.getAction() == KeyEvent.ACTION_DOWN) { + sendMessage(); + return true; + } + } + return false; + } + }); + + sendButton.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + sendMessage(); + } + }); + + audioSendButton.setOnTouchListener(new View.OnTouchListener() { + @Override + public boolean onTouch(View view, MotionEvent motionEvent) { + if (motionEvent.getAction() == MotionEvent.ACTION_DOWN) { + startedDraggingX = -1; + MediaController.getInstance().startRecording(dialog_id); + updateAudioRecordIntefrace(); + audioSendButton.getParent().requestDisallowInterceptTouchEvent(true); + } else if (motionEvent.getAction() == MotionEvent.ACTION_UP || motionEvent.getAction() == MotionEvent.ACTION_CANCEL) { + startedDraggingX = -1; + MediaController.getInstance().stopRecording(true); + recordingAudio = false; + updateAudioRecordIntefrace(); + } else if (motionEvent.getAction() == MotionEvent.ACTION_MOVE && recordingAudio) { + float x = motionEvent.getX(); + if (x < -distCanMove) { + MediaController.getInstance().stopRecording(false); + recordingAudio = false; + updateAudioRecordIntefrace(); + } + if(android.os.Build.VERSION.SDK_INT > 13) { + x = x + audioSendButton.getX(); + FrameLayout.LayoutParams params = (FrameLayout.LayoutParams)slideText.getLayoutParams(); + if (startedDraggingX != -1) { + float dist = (x - startedDraggingX); + params.leftMargin = AndroidUtilities.dp(30) + (int)dist; + slideText.setLayoutParams(params); + float alpha = 1.0f + dist / distCanMove; + if (alpha > 1) { + alpha = 1; + } else if (alpha < 0) { + alpha = 0; + } + slideText.setAlpha(alpha); + } + if (x <= slideText.getX() + slideText.getWidth() + AndroidUtilities.dp(30)) { + if (startedDraggingX == -1) { + startedDraggingX = x; + distCanMove = (recordPanel.getMeasuredWidth() - slideText.getMeasuredWidth() - AndroidUtilities.dp(48)) / 2.0f; + if (distCanMove <= 0) { + distCanMove = AndroidUtilities.dp(80); + } else if (distCanMove > AndroidUtilities.dp(80)) { + distCanMove = AndroidUtilities.dp(80); + } + } + } + if (params.leftMargin > AndroidUtilities.dp(30)) { + params.leftMargin = AndroidUtilities.dp(30); + slideText.setLayoutParams(params); + slideText.setAlpha(1); + startedDraggingX = -1; + } + } + } + view.onTouchEvent(motionEvent); + return true; + } + }); + + messsageEditText.addTextChangedListener(new TextWatcher() { + @Override + public void beforeTextChanged(CharSequence charSequence, int i, int i2, int i3) { + + } + + @Override + public void onTextChanged(CharSequence charSequence, int i, int i2, int i3) { + String message = getTrimmedString(charSequence.toString()); + sendButton.setEnabled(message.length() != 0); + checkSendButton(); + + if (message.length() != 0 && lastTypingTimeSend < System.currentTimeMillis() - 5000 && !ignoreTextChange) { + int currentTime = ConnectionsManager.getInstance().getCurrentTime(); + TLRPC.User currentUser = null; + if ((int)dialog_id > 0) { + currentUser = MessagesController.getInstance().users.get((int)dialog_id); + } + if (currentUser != null && currentUser.status != null && currentUser.status.expires < currentTime) { + return; + } + lastTypingTimeSend = System.currentTimeMillis(); + if (delegate != null) { + delegate.needSendTyping(); + } + } + } + + @Override + public void afterTextChanged(Editable editable) { + if (sendByEnter && editable.length() > 0 && editable.charAt(editable.length() - 1) == '\n') { + sendMessage(); + } + int i = 0; + ImageSpan[] arrayOfImageSpan = editable.getSpans(0, editable.length(), ImageSpan.class); + int j = arrayOfImageSpan.length; + while (true) { + if (i >= j) { + Emoji.replaceEmoji(editable, messsageEditText.getPaint().getFontMetricsInt(), AndroidUtilities.dp(20)); + return; + } + editable.removeSpan(arrayOfImageSpan[i]); + i++; + } + } + }); + + checkSendButton(); + } + + private void sendMessage() { + if (processSendingText(messsageEditText.getText().toString())) { + messsageEditText.setText(""); + lastTypingTimeSend = 0; + if (delegate != null) { + delegate.onMessageSend(); + } + } + } + + public boolean processSendingText(String text) { + text = getTrimmedString(text); + if (text.length() != 0) { + int count = (int)Math.ceil(text.length() / 2048.0f); + for (int a = 0; a < count; a++) { + String mess = text.substring(a * 2048, Math.min((a + 1) * 2048, text.length())); + MessagesController.getInstance().sendMessage(mess, dialog_id); + } + return true; + } + return false; + } + + private String getTrimmedString(String src) { + String result = src.trim(); + if (result.length() == 0) { + return result; + } + while (src.startsWith("\n")) { + src = src.substring(1); + } + while (src.endsWith("\n")) { + src = src.substring(0, src.length() - 1); + } + return src; + } + + private void checkSendButton() { + String message = getTrimmedString(messsageEditText.getText().toString()); + if (message.length() > 0) { + sendButton.setVisibility(View.VISIBLE); + audioSendButton.setVisibility(View.INVISIBLE); + } else { + sendButton.setVisibility(View.INVISIBLE); + audioSendButton.setVisibility(View.VISIBLE); + } + } + + private void updateAudioRecordIntefrace() { + if (recordingAudio) { + try { + if (mWakeLock == null) { + PowerManager pm = (PowerManager) ApplicationLoader.applicationContext.getSystemService(Context.POWER_SERVICE); + mWakeLock = pm.newWakeLock(PowerManager.SCREEN_DIM_WAKE_LOCK | PowerManager.ON_AFTER_RELEASE, "audio record lock"); + mWakeLock.acquire(); + } + } catch (Exception e) { + FileLog.e("tmessages", e); + } + AndroidUtilities.lockOrientation(parentActivity); + + recordPanel.setVisibility(View.VISIBLE); + recordTimeText.setText("00:00"); + lastTimeString = null; + if(android.os.Build.VERSION.SDK_INT > 13) { + FrameLayout.LayoutParams params = (FrameLayout.LayoutParams)slideText.getLayoutParams(); + params.leftMargin = AndroidUtilities.dp(30); + slideText.setLayoutParams(params); + slideText.setAlpha(1); + recordPanel.setX(AndroidUtilities.displaySize.x); + recordPanel.animate().setInterpolator(new AccelerateDecelerateInterpolator()).setListener(new Animator.AnimatorListener() { + @Override + public void onAnimationStart(Animator animator) { + } + + @Override + public void onAnimationEnd(Animator animator) { + recordPanel.setX(0); + } + + @Override + public void onAnimationCancel(Animator animator) { + } + + @Override + public void onAnimationRepeat(Animator animator) { + } + }).setDuration(300).translationX(0).start(); + } + } else { + if (mWakeLock != null) { + try { + mWakeLock.release(); + mWakeLock = null; + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + AndroidUtilities.unlockOrientation(parentActivity); + if(android.os.Build.VERSION.SDK_INT > 13) { + recordPanel.animate().setInterpolator(new AccelerateDecelerateInterpolator()).setListener(new Animator.AnimatorListener() { + @Override + public void onAnimationStart(Animator animator) { + + } + + @Override + public void onAnimationEnd(Animator animator) { + FrameLayout.LayoutParams params = (FrameLayout.LayoutParams)slideText.getLayoutParams(); + params.leftMargin = AndroidUtilities.dp(30); + slideText.setLayoutParams(params); + slideText.setAlpha(1); + recordPanel.setVisibility(View.GONE); + } + + @Override + public void onAnimationCancel(Animator animator) { + } + + @Override + public void onAnimationRepeat(Animator animator) { + } + }).setDuration(300).translationX(AndroidUtilities.displaySize.x).start(); + } else { + recordPanel.setVisibility(View.GONE); + } + } + } + + private void showEmojiPopup(boolean show) { + InputMethodManager localInputMethodManager = (InputMethodManager)ApplicationLoader.applicationContext.getSystemService(Context.INPUT_METHOD_SERVICE); + if (show) { + if (emojiPopup == null) { + createEmojiPopup(); + } + int currentHeight; + WindowManager manager = (WindowManager) ApplicationLoader.applicationContext.getSystemService(Activity.WINDOW_SERVICE); + int rotation = manager.getDefaultDisplay().getRotation(); + if (keyboardHeight <= 0) { + keyboardHeight = ApplicationLoader.applicationContext.getSharedPreferences("emoji", 0).getInt("kbd_height", AndroidUtilities.dp(200)); + } + if (keyboardHeightLand <= 0) { + keyboardHeightLand = ApplicationLoader.applicationContext.getSharedPreferences("emoji", 0).getInt("kbd_height_land3", AndroidUtilities.dp(200)); + } + if (rotation == Surface.ROTATION_270 || rotation == Surface.ROTATION_90) { + currentHeight = keyboardHeightLand; + } else { + currentHeight = keyboardHeight; + } + emojiPopup.setHeight(View.MeasureSpec.makeMeasureSpec(currentHeight, View.MeasureSpec.EXACTLY)); + emojiPopup.setWidth(View.MeasureSpec.makeMeasureSpec(sizeNotifierRelativeLayout.getWidth(), View.MeasureSpec.EXACTLY)); + + emojiPopup.showAtLocation(parentActivity.getWindow().getDecorView(), 83, 0, 0); + if (!keyboardVisible) { + sizeNotifierRelativeLayout.setPadding(0, 0, 0, currentHeight); + emojiButton.setImageResource(R.drawable.ic_msg_panel_hide); + return; + } + emojiButton.setImageResource(R.drawable.ic_msg_panel_kb); + return; + } + if (emojiButton != null) { + emojiButton.setImageResource(R.drawable.ic_msg_panel_smiles); + } + if (emojiPopup != null) { + emojiPopup.dismiss(); + } + if (sizeNotifierRelativeLayout != null) { + sizeNotifierRelativeLayout.post(new Runnable() { + public void run() { + if (sizeNotifierRelativeLayout != null) { + sizeNotifierRelativeLayout.setPadding(0, 0, 0, 0); + } + } + }); + } + } + + public void hideEmojiPopup() { + if (emojiPopup != null && emojiPopup.isShowing()) { + showEmojiPopup(false); + } + } + + private void createEmojiPopup() { + if (parentActivity == null) { + return; + } + emojiView = new EmojiView(parentActivity); + emojiView.setListener(new EmojiView.Listener() { + public void onBackspace() { + messsageEditText.dispatchKeyEvent(new KeyEvent(0, 67)); + } + + public void onEmojiSelected(String paramAnonymousString) { + int i = messsageEditText.getSelectionEnd(); + CharSequence localCharSequence = Emoji.replaceEmoji(paramAnonymousString, messsageEditText.getPaint().getFontMetricsInt(), AndroidUtilities.dp(20)); + messsageEditText.setText(messsageEditText.getText().insert(i, localCharSequence)); + int j = i + localCharSequence.length(); + messsageEditText.setSelection(j, j); + } + }); + emojiPopup = new PopupWindow(emojiView); + } + + public void setDelegate(ChatActivityEnterViewDelegate delegate) { + this.delegate = delegate; + } + + public void setDialogId(long id) { + dialog_id = id; + } + + public void setFieldText(String text) { + ignoreTextChange = true; + messsageEditText.setText(text); + messsageEditText.setSelection(messsageEditText.getText().length()); + ignoreTextChange = false; + } + + public void setFieldFocused(boolean focus) { + if (messsageEditText == null) { + return; + } + if (focus) { + if (!messsageEditText.isFocused()) { + messsageEditText.postDelayed(new Runnable() { + @Override + public void run() { + if (messsageEditText != null) { + messsageEditText.requestFocus(); + } + } + }, 600); + } + } else { + if (messsageEditText.isFocused() && !keyboardVisible) { + messsageEditText.clearFocus(); + } + } + } + + public boolean hasText() { + return messsageEditText != null && messsageEditText.length() > 0; + } + + public String getFieldText() { + if (messsageEditText != null && messsageEditText.length() > 0) { + return messsageEditText.getText().toString(); + } + return null; + } + + public boolean isEmojiPopupShowing() { + return emojiPopup != null && emojiPopup.isShowing(); + } + + @Override + public void onSizeChanged(int height) { + Rect localRect = new Rect(); + parentActivity.getWindow().getDecorView().getWindowVisibleDisplayFrame(localRect); + + WindowManager manager = (WindowManager) ApplicationLoader.applicationContext.getSystemService(Activity.WINDOW_SERVICE); + if (manager == null || manager.getDefaultDisplay() == null) { + return; + } + int rotation = manager.getDefaultDisplay().getRotation(); + + if (height > AndroidUtilities.dp(50)) { + if (rotation == Surface.ROTATION_270 || rotation == Surface.ROTATION_90) { + keyboardHeightLand = height; + ApplicationLoader.applicationContext.getSharedPreferences("emoji", 0).edit().putInt("kbd_height_land3", keyboardHeightLand).commit(); + } else { + keyboardHeight = height; + ApplicationLoader.applicationContext.getSharedPreferences("emoji", 0).edit().putInt("kbd_height", keyboardHeight).commit(); + } + } + + if (emojiPopup != null && emojiPopup.isShowing()) { + WindowManager wm = (WindowManager) ApplicationLoader.applicationContext.getSystemService(Context.WINDOW_SERVICE); + final WindowManager.LayoutParams layoutParams = (WindowManager.LayoutParams)emojiPopup.getContentView().getLayoutParams(); + layoutParams.width = sizeNotifierRelativeLayout.getWidth(); + if (rotation == Surface.ROTATION_270 || rotation == Surface.ROTATION_90) { + layoutParams.height = keyboardHeightLand; + } else { + layoutParams.height = keyboardHeight; + } + wm.updateViewLayout(emojiPopup.getContentView(), layoutParams); + if (!keyboardVisible) { + sizeNotifierRelativeLayout.post(new Runnable() { + @Override + public void run() { + if (sizeNotifierRelativeLayout != null) { + sizeNotifierRelativeLayout.setPadding(0, 0, 0, layoutParams.height); + sizeNotifierRelativeLayout.requestLayout(); + } + } + }); + } + } + + boolean oldValue = keyboardVisible; + keyboardVisible = height > 0; + if (keyboardVisible && sizeNotifierRelativeLayout.getPaddingBottom() > 0) { + showEmojiPopup(false); + } else if (!keyboardVisible && keyboardVisible != oldValue && emojiPopup != null && emojiPopup.isShowing()) { + showEmojiPopup(false); + } + } + + @Override + public void didReceivedNotification(int id, Object... args) { + if (id == 999) { + if (emojiView != null) { + emojiView.invalidateViews(); + } + } else if (id == MediaController.recordProgressChanged) { + Long time = (Long)args[0] / 1000; + String str = String.format("%02d:%02d", time / 60, time % 60); + if (lastTimeString == null || !lastTimeString.equals(str)) { + if (recordTimeText != null) { + recordTimeText.setText(str); + } + } + } else if (id == MessagesController.closeChats) { + if (messsageEditText != null && messsageEditText.isFocused()) { + AndroidUtilities.hideKeyboard(messsageEditText); + } + } else if (id == MediaController.recordStartError || id == MediaController.recordStopped) { + if (recordingAudio) { + recordingAudio = false; + updateAudioRecordIntefrace(); + } + } else if (id == MediaController.recordStarted) { + if (!recordingAudio) { + recordingAudio = true; + updateAudioRecordIntefrace(); + } + } else if (id == MediaController.audioDidSent) { + if (delegate != null) { + delegate.onMessageSend(); + } + } + } +} diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/ClippingImageView.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/ClippingImageView.java index 69b04d21d..543272ba2 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/ClippingImageView.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/ClippingImageView.java @@ -15,6 +15,8 @@ import android.graphics.Paint; import android.graphics.Rect; import android.view.View; +import org.telegram.messenger.FileLog; + public class ClippingImageView extends View { private int clipBottom; private int clipLeft; @@ -64,7 +66,11 @@ public class ClippingImageView extends View { canvas.save(); canvas.clipRect(clipLeft / getScaleY(), clipTop / getScaleY(), getWidth() - clipRight / getScaleY(), getHeight() - clipBottom / getScaleY()); drawRect.set(0, 0, getWidth(), getHeight()); - canvas.drawBitmap(this.bmp, null, drawRect, this.paint); + try { + canvas.drawBitmap(this.bmp, null, drawRect, this.paint); + } catch (Exception e) { + FileLog.e("tmessages", e); + } canvas.restore(); } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/ColorPickerView.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/ColorPickerView.java index 7386dea6a..7135cbfbc 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/ColorPickerView.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/ColorPickerView.java @@ -29,7 +29,7 @@ import android.util.AttributeSet; import android.view.MotionEvent; import android.view.View; -import org.telegram.messenger.Utilities; +import org.telegram.android.AndroidUtilities; public class ColorPickerView extends View { @@ -105,15 +105,15 @@ public class ColorPickerView extends View { } private void init(AttributeSet attrs, int defStyle) { - mColorWheelThickness = Utilities.dp(8); - mColorWheelRadius = Utilities.dp(124); + mColorWheelThickness = AndroidUtilities.dp(8); + mColorWheelRadius = AndroidUtilities.dp(124); mPreferredColorWheelRadius = mColorWheelRadius; - mColorCenterRadius = Utilities.dp(54); + mColorCenterRadius = AndroidUtilities.dp(54); mPreferredColorCenterRadius = mColorCenterRadius; - mColorCenterHaloRadius = Utilities.dp(60); + mColorCenterHaloRadius = AndroidUtilities.dp(60); mPreferredColorCenterHaloRadius = mColorCenterHaloRadius; - mColorPointerRadius = Utilities.dp(14); - mColorPointerHaloRadius = Utilities.dp(18); + mColorPointerRadius = AndroidUtilities.dp(14); + mColorPointerHaloRadius = AndroidUtilities.dp(18); mAngle = (float) (-Math.PI / 2); diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/EmojiView.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/EmojiView.java index cb162010c..b8cb4817e 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/EmojiView.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/EmojiView.java @@ -24,10 +24,10 @@ import android.widget.ImageView; import android.widget.LinearLayout; import android.widget.TextView; -import org.telegram.messenger.Emoji; -import org.telegram.messenger.LocaleController; +import org.telegram.android.AndroidUtilities; +import org.telegram.android.Emoji; +import org.telegram.android.LocaleController; import org.telegram.messenger.R; -import org.telegram.messenger.Utilities; import java.util.ArrayList; @@ -104,7 +104,7 @@ public class EmojiView extends LinearLayout { setOrientation(LinearLayout.VERTICAL); for (int i = 0; i < Emoji.data.length; i++) { GridView gridView = new GridView(getContext()); - gridView.setColumnWidth(Utilities.dpf(45.0f)); + gridView.setColumnWidth(AndroidUtilities.dpf(45.0f)); gridView.setNumColumns(-1); views.add(gridView); @@ -120,8 +120,8 @@ public class EmojiView extends LinearLayout { tabs.setViewPager(pager); tabs.setShouldExpand(true); tabs.setIndicatorColor(0xff33b5e5); - tabs.setIndicatorHeight(Utilities.dpf(2.0f)); - tabs.setUnderlineHeight(Utilities.dpf(2.0f)); + tabs.setIndicatorHeight(AndroidUtilities.dpf(2.0f)); + tabs.setUnderlineHeight(AndroidUtilities.dpf(2.0f)); tabs.setUnderlineColor(1711276032); tabs.setTabBackground(0); LinearLayout localLinearLayout = new LinearLayout(getContext()); @@ -138,7 +138,7 @@ public class EmojiView extends LinearLayout { } } }); - localLinearLayout.addView(localImageView, new LinearLayout.LayoutParams(Utilities.dpf(61.0f), LayoutParams.MATCH_PARENT)); + localLinearLayout.addView(localImageView, new LinearLayout.LayoutParams(AndroidUtilities.dpf(61.0f), LayoutParams.MATCH_PARENT)); recentsWrap = new FrameLayout(getContext()); recentsWrap.addView(views.get(0)); TextView localTextView = new TextView(getContext()); @@ -148,7 +148,7 @@ public class EmojiView extends LinearLayout { localTextView.setGravity(17); recentsWrap.addView(localTextView); views.get(0).setEmptyView(localTextView); - addView(localLinearLayout, new LinearLayout.LayoutParams(-1, Utilities.dpf(48.0f))); + addView(localLinearLayout, new LinearLayout.LayoutParams(-1, AndroidUtilities.dpf(48.0f))); addView(pager); loadRecents(); if (Emoji.data[0] == null || Emoji.data[0].length == 0) { diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/ImageReceiver.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/ImageReceiver.java index 77b73196f..11cf3a9cd 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/ImageReceiver.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/ImageReceiver.java @@ -13,7 +13,6 @@ import android.graphics.Canvas; import android.graphics.Rect; import android.graphics.drawable.BitmapDrawable; import android.graphics.drawable.Drawable; -import android.os.Build; import android.view.View; import org.telegram.messenger.TLRPC; @@ -36,6 +35,7 @@ public class ImageReceiver { public Rect drawRegion = new Rect(); private boolean isVisible = true; private boolean selfSetting = false; + public boolean isAspectFit = false; public void setImage(TLRPC.FileLocation path, String filter, Drawable placeholder) { setImage(path, null, filter, placeholder, 0); @@ -61,6 +61,9 @@ public class ImageReceiver { last_size = 0; currentImage = null; FileLoader.getInstance().cancelLoadingForImageView(this); + if (parentView != null) { + parentView.invalidate(); + } return; } String key; @@ -92,16 +95,13 @@ public class ImageReceiver { if (img == null) { isPlaceholder = true; FileLoader.getInstance().loadImage(path, httpUrl, this, filter, true, size); - if (parentView != null) { - parentView.invalidate(); - } } else { selfSetting = true; setImageBitmap(img, currentPath); selfSetting = false; - if (parentView != null) { - parentView.invalidate(); - } + } + if (parentView != null) { + parentView.invalidate(); } } @@ -166,9 +166,7 @@ public class ImageReceiver { } if (canDelete) { currentImage = null; - if (Build.VERSION.SDK_INT < 11) { - bitmap.recycle(); - } + bitmap.recycle(); } } else { currentImage = null; @@ -191,28 +189,39 @@ public class ImageReceiver { float scaleW = bitmapW / (float)w; float scaleH = bitmapH / (float)h; - if (Math.abs(scaleW - scaleH) > 0.00001f) { + if (isAspectFit) { + float scale = Math.max(scaleW, scaleH); canvas.save(); - canvas.clipRect(x, y, x + w, y + h); - - if (bitmapW / scaleH > w) { - bitmapW /= scaleH; - drawRegion.set(x - (bitmapW - w) / 2, y, x + (bitmapW + w) / 2, y + h); - } else { - bitmapH /= scaleW; - drawRegion.set(x, y - (bitmapH - h) / 2, x + w, y + (bitmapH + h) / 2); - } + bitmapW /= scale; + bitmapH /= scale; + drawRegion.set(x + (w - bitmapW) / 2, y + (h - bitmapH) / 2, x + (w + bitmapW) / 2, y + (h + bitmapH) / 2); bitmapDrawable.setBounds(drawRegion); - if (isVisible) { - bitmapDrawable.draw(canvas); - } - + bitmapDrawable.draw(canvas); canvas.restore(); } else { - drawRegion.set(x, y, x + w, y + h); - bitmapDrawable.setBounds(drawRegion); - if (isVisible) { - bitmapDrawable.draw(canvas); + if (Math.abs(scaleW - scaleH) > 0.00001f) { + canvas.save(); + canvas.clipRect(x, y, x + w, y + h); + + if (bitmapW / scaleH > w) { + bitmapW /= scaleH; + drawRegion.set(x - (bitmapW - w) / 2, y, x + (bitmapW + w) / 2, y + h); + } else { + bitmapH /= scaleW; + drawRegion.set(x, y - (bitmapH - h) / 2, x + w, y + (bitmapH + h) / 2); + } + bitmapDrawable.setBounds(drawRegion); + if (isVisible) { + bitmapDrawable.draw(canvas); + } + + canvas.restore(); + } else { + drawRegion.set(x, y, x + w, y + h); + bitmapDrawable.setBounds(drawRegion); + if (isVisible) { + bitmapDrawable.draw(canvas); + } } } } else if (last_placeholder != null) { diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/MessageActionLayout.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/MessageActionLayout.java index d0e2e1367..793b45f7c 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/MessageActionLayout.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/MessageActionLayout.java @@ -10,8 +10,8 @@ package org.telegram.ui.Views; import android.widget.FrameLayout; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.R; -import org.telegram.messenger.Utilities; public class MessageActionLayout extends FrameLayout { public TightTextView messageTextView; @@ -31,7 +31,7 @@ public class MessageActionLayout extends FrameLayout { @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec); - setMeasuredDimension(messageTextView.linesMaxWidth + Utilities.dp(14), getMeasuredHeight()); + setMeasuredDimension(messageTextView.linesMaxWidth + AndroidUtilities.dp(14), getMeasuredHeight()); } @Override diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/NotificationView.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/NotificationView.java deleted file mode 100644 index 3fef3f2a0..000000000 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/NotificationView.java +++ /dev/null @@ -1,326 +0,0 @@ -/* - * This is the source code of Telegram for Android v. 1.3.2. - * It is licensed under GNU GPL v. 2 or later. - * You should have received a copy of the license in this archive (see LICENSE). - * - * Copyright Nikolai Kudashov, 2013. - */ - -package org.telegram.ui.Views; - -import android.content.Context; -import android.graphics.PixelFormat; -import android.util.AttributeSet; -import android.util.TypedValue; -import android.view.Gravity; -import android.view.View; -import android.view.ViewGroup; -import android.view.WindowManager; -import android.view.animation.Animation; -import android.view.animation.AnimationUtils; -import android.widget.FrameLayout; -import android.widget.ImageView; -import android.widget.LinearLayout; -import android.widget.TextView; - -import org.telegram.messenger.LocaleController; -import org.telegram.messenger.TLRPC; -import org.telegram.messenger.FileLog; -import org.telegram.messenger.MessagesController; -import org.telegram.messenger.NotificationCenter; -import org.telegram.messenger.R; -import org.telegram.messenger.Utilities; -import org.telegram.objects.MessageObject; -import org.telegram.ui.ApplicationLoader; - -import java.util.Timer; -import java.util.TimerTask; - -public class NotificationView extends LinearLayout { - public BackupImageView avatarImage; - public TextView nameTextView; - public TextView messageTextView; - public ImageView closeButton; - public FrameLayout textLayout; - private WindowManager.LayoutParams notificationLayoutParams; - private ViewGroup notificationParentView; - private boolean onScreen; - private Animation animShow; - private Animation animHide; - private Timer hideTimer; - private int currentChatId = 0; - private int currentUserId = 0; - private int currentEncId = 0; - private boolean isVisible; - private final Integer timerSync = 1; - - public NotificationView(Context context) { - super(context); - } - - public NotificationView(Context context, AttributeSet attrs) { - super(context, attrs); - } - - public NotificationView(Context context, AttributeSet attrs, int defStyle) { - super(context, attrs, defStyle); - } - - @Override - protected void onFinishInflate() { - super.onFinishInflate(); - avatarImage = (BackupImageView)findViewById(R.id.avatar_image); - nameTextView = (TextView)findViewById(R.id.name_text_view); - messageTextView = (TextView)findViewById(R.id.message_text_view); - closeButton = (ImageView)findViewById(R.id.close_button); - textLayout = (FrameLayout)findViewById(R.id.text_layout); - closeButton.setOnClickListener(new OnClickListener() { - @Override - public void onClick(View v) { - try { - synchronized (timerSync) { - if (hideTimer != null) { - hideTimer.cancel(); - hideTimer = null; - } - } - } catch (Exception e) { - FileLog.e("tmessages", e); - } - hide(true); - } - }); - - this.setOnClickListener(new OnClickListener() { - @Override - public void onClick(View v) { - try { - synchronized (timerSync) { - if (hideTimer != null) { - hideTimer.cancel(); - hideTimer = null; - } - } - } catch (Exception e) { - FileLog.e("tmessages", e); - } - hide(true); - - NotificationCenter.getInstance().postNotificationName(658, currentChatId, currentUserId, currentEncId); - } - }); - - notificationParentView = new FrameLayout(getContext()); - notificationParentView.addView(this); - notificationParentView.setFocusable(false); - setFocusable(false); - WindowManager wm = (WindowManager) ApplicationLoader.applicationContext.getSystemService(Context.WINDOW_SERVICE); - notificationLayoutParams = new WindowManager.LayoutParams(); - notificationLayoutParams.height = 90; - notificationLayoutParams.format = PixelFormat.TRANSLUCENT; - notificationLayoutParams.width = WindowManager.LayoutParams.FILL_PARENT; - notificationLayoutParams.gravity = Gravity.CLIP_HORIZONTAL | Gravity.TOP; - notificationLayoutParams.type = WindowManager.LayoutParams.TYPE_SYSTEM_ERROR; - notificationLayoutParams.flags = WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN | WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS | WindowManager.LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH | WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE; - isVisible = false; - wm.addView(notificationParentView, notificationLayoutParams); - notificationParentView.setVisibility(View.INVISIBLE); - - animHide = AnimationUtils.loadAnimation(ApplicationLoader.applicationContext, R.anim.slide_up); - animHide.setAnimationListener(new Animation.AnimationListener() { - public void onAnimationStart(Animation animation) { - onScreen = false; - } - - public void onAnimationRepeat(Animation animation) { - - } - - public void onAnimationEnd(Animation animation) { - setVisibility(GONE); - WindowManager wm = (WindowManager)ApplicationLoader.applicationContext.getSystemService(Context.WINDOW_SERVICE); - isVisible = false; - notificationParentView.setVisibility(View.INVISIBLE); - } - }); - - animShow = AnimationUtils.loadAnimation(ApplicationLoader.applicationContext, R.anim.slide_down); - animShow.setAnimationListener(new Animation.AnimationListener() { - public void onAnimationStart(Animation animation) { - setVisibility(VISIBLE); - onScreen = true; - } - - public void onAnimationRepeat(Animation animation) { - - } - - public void onAnimationEnd(Animation animation) { - - } - }); - } - - public void show(MessageObject object) { - TLRPC.User user = MessagesController.getInstance().users.get(object.messageOwner.from_id); - TLRPC.Chat chat = null; - long dialog_id = object.messageOwner.dialog_id; - if (object.messageOwner.to_id.chat_id != 0) { - chat = MessagesController.getInstance().chats.get(object.messageOwner.to_id.chat_id); - if (chat == null) { - return; - } - } - if (user == null) { - return; - } - if (chat != null) { - currentChatId = chat.id; - currentUserId = 0; - currentEncId = 0; - nameTextView.setText(Utilities.formatName(user.first_name, user.last_name) + " @ " + chat.title); - } else { - int lower_id = (int)dialog_id; - if (lower_id != 0 || dialog_id == 0) { - currentUserId = user.id; - currentEncId = 0; - } else { - currentUserId = 0; - currentEncId = (int)(dialog_id >> 32); - } - currentChatId = 0; - nameTextView.setText(Utilities.formatName(user.first_name, user.last_name)); - } - nameTextView.setTextColor(Utilities.getColorForId(user.id)); - messageTextView.setText(object.messageText); - TLRPC.FileLocation photo = null; - if (user.photo != null) { - photo = user.photo.photo_small; - } - avatarImage.setImage(photo, "50_50", Utilities.getUserAvatarForId(user.id)); - - try { - synchronized (timerSync) { - if (hideTimer != null) { - hideTimer.cancel(); - hideTimer = null; - } - } - hideTimer = new Timer(); - hideTimer.schedule(new TimerTask() { - @Override - public void run() { - Utilities.RunOnUIThread(new Runnable() { - @Override - public void run() { - hide(true); - } - }); - try { - synchronized (timerSync) { - if (hideTimer != null) { - hideTimer.cancel(); - hideTimer = null; - } - } - } catch (Exception e) { - FileLog.e("tmessages", e); - } - } - }, 3000); - } catch (Exception e) { - FileLog.e("tmessages", e); - } - - if (!onScreen) { - WindowManager wm = (WindowManager)ApplicationLoader.applicationContext.getSystemService(Context.WINDOW_SERVICE); - isVisible = true; - notificationParentView.setVisibility(View.VISIBLE); - startAnimation(animShow); - } - } - - public void hide(boolean animation) { - if (onScreen) { - if (animation) { - startAnimation(animHide); - } else { - try { - synchronized (timerSync) { - if (hideTimer != null) { - hideTimer.cancel(); - hideTimer = null; - } - } - } catch (Exception e) { - FileLog.e("tmessages", e); - } - onScreen = false; - setVisibility(GONE); - if (notificationParentView != null && notificationParentView.getParent() != null) { - WindowManager wm = (WindowManager)ApplicationLoader.applicationContext.getSystemService(Context.WINDOW_SERVICE); - isVisible = false; - notificationParentView.setVisibility(View.INVISIBLE); - } - } - } - } - - public void destroy() { - try { - if (notificationParentView != null) { - notificationParentView.removeView(this); - try { - if (notificationParentView.getParent() != null) { - WindowManager wm = (WindowManager)ApplicationLoader.applicationContext.getSystemService(Context.WINDOW_SERVICE); - wm.removeViewImmediate(notificationParentView); - } - } catch (Exception e) { - FileLog.e("tmessages", e); - } - } - notificationParentView = null; - notificationLayoutParams = null; - } catch (Exception e) { - FileLog.e("tmessages", e); - } - } - - public void applyOrientationPaddings(boolean isLandscape, int height) { - FrameLayout.LayoutParams params = (FrameLayout.LayoutParams)avatarImage.getLayoutParams(); - params.width = height; - params.height = height; - avatarImage.setLayoutParams(params); - FrameLayout.LayoutParams params1 = (FrameLayout.LayoutParams)textLayout.getLayoutParams(); - if (isLandscape) { - nameTextView.setTextSize(TypedValue.COMPLEX_UNIT_SP, 14); - messageTextView.setTextSize(TypedValue.COMPLEX_UNIT_SP, 14); - nameTextView.setPadding(0, Utilities.dp(2), 0, 0); - messageTextView.setPadding(0, Utilities.dp(18), 0, 0); - if (LocaleController.isRTL) { - params1.setMargins(Utilities.dp(40), 0, height + Utilities.dp(6), 0); - } else { - params1.setMargins(height + Utilities.dp(6), 0, Utilities.dp(40), 0); - } - } else { - nameTextView.setTextSize(TypedValue.COMPLEX_UNIT_SP, 15); - messageTextView.setTextSize(TypedValue.COMPLEX_UNIT_SP, 15); - nameTextView.setPadding(0, Utilities.dp(4), 0, 0); - messageTextView.setPadding(0, Utilities.dp(24), 0, 0); - if (LocaleController.isRTL) { - params1.setMargins(Utilities.dp(40), 0, height + Utilities.dp(8), 0); - } else { - params1.setMargins(height + Utilities.dp(8), 0, Utilities.dp(40), 0); - } - } - textLayout.setLayoutParams(params1); - - if (notificationParentView != null) { - notificationLayoutParams.height = height; - if (notificationParentView.getParent() != null) { - WindowManager wm = (WindowManager) ApplicationLoader.applicationContext.getSystemService(Context.WINDOW_SERVICE); - wm.updateViewLayout(notificationParentView, notificationLayoutParams); - } - } - } -} diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/PopupAudioView.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/PopupAudioView.java new file mode 100644 index 000000000..128fc36a6 --- /dev/null +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/PopupAudioView.java @@ -0,0 +1,359 @@ +/* + * This is the source code of Telegram for Android v. 1.4.x. + * It is licensed under GNU GPL v. 2 or later. + * You should have received a copy of the license in this archive (see LICENSE). + * + * Copyright Nikolai Kudashov, 2013-2014. + */ + +package org.telegram.ui.Views; + +import android.content.Context; +import android.graphics.Canvas; +import android.graphics.drawable.Drawable; +import android.text.Layout; +import android.text.StaticLayout; +import android.text.TextPaint; +import android.view.MotionEvent; +import android.view.SoundEffectConstants; + +import org.telegram.android.AndroidUtilities; +import org.telegram.android.MediaController; +import org.telegram.android.MessagesController; +import org.telegram.messenger.FileLoader; +import org.telegram.messenger.R; +import org.telegram.objects.MessageObject; +import org.telegram.ui.Cells.BaseCell; + +import java.io.File; + +public class PopupAudioView extends BaseCell implements SeekBar.SeekBarDelegate, MediaController.FileDownloadProgressListener { + + private boolean wasLayout = false; + protected MessageObject currentMessageObject; + + private static Drawable backgroundMediaDrawableIn; + + private static Drawable[][] statesDrawable = new Drawable[8][2]; + private static TextPaint timePaint; + + private SeekBar seekBar; + private ProgressView progressView; + private int seekBarX; + private int seekBarY; + + private int buttonState = 0; + private int buttonX; + private int buttonY; + private int buttonPressed = 0; + + private StaticLayout timeLayout; + private int timeX; + int timeWidth = 0; + private String lastTimeString = null; + + private int TAG; + + public PopupAudioView(Context context) { + super(context); + if (backgroundMediaDrawableIn == null) { + backgroundMediaDrawableIn = getResources().getDrawable(R.drawable.msg_in_photo); + statesDrawable[0][0] = getResources().getDrawable(R.drawable.play1); + statesDrawable[0][1] = getResources().getDrawable(R.drawable.play1_pressed); + statesDrawable[1][0] = getResources().getDrawable(R.drawable.pause1); + statesDrawable[1][1] = getResources().getDrawable(R.drawable.pause1_pressed); + statesDrawable[2][0] = getResources().getDrawable(R.drawable.audioload1); + statesDrawable[2][1] = getResources().getDrawable(R.drawable.audioload1_pressed); + statesDrawable[3][0] = getResources().getDrawable(R.drawable.audiocancel1); + statesDrawable[3][1] = getResources().getDrawable(R.drawable.audiocancel1_pressed); + + statesDrawable[4][0] = getResources().getDrawable(R.drawable.play2); + statesDrawable[4][1] = getResources().getDrawable(R.drawable.play2_pressed); + statesDrawable[5][0] = getResources().getDrawable(R.drawable.pause2); + statesDrawable[5][1] = getResources().getDrawable(R.drawable.pause2_pressed); + statesDrawable[6][0] = getResources().getDrawable(R.drawable.audioload2); + statesDrawable[6][1] = getResources().getDrawable(R.drawable.audioload2_pressed); + statesDrawable[7][0] = getResources().getDrawable(R.drawable.audiocancel2); + statesDrawable[7][1] = getResources().getDrawable(R.drawable.audiocancel2_pressed); + + timePaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG); + timePaint.setTextSize(AndroidUtilities.dp(16)); + } + + TAG = MediaController.getInstance().generateObserverTag(); + + seekBar = new SeekBar(getContext()); + seekBar.delegate = this; + progressView = new ProgressView(); + } + + public void setMessageObject(MessageObject messageObject) { + if (currentMessageObject != messageObject) { + int uid = messageObject.messageOwner.media.audio.user_id; + if (uid == 0) { + uid = messageObject.messageOwner.from_id; + } + + seekBar.type = 1; + progressView.setProgressColors(0xffd9e2eb, 0xff86c5f8); + + currentMessageObject = messageObject; + wasLayout = false; + + if (currentMessageObject.messageOwner.id < 0 && currentMessageObject.messageOwner.send_state != MessagesController.MESSAGE_SEND_STATE_SEND_ERROR && currentMessageObject.messageOwner.send_state != MessagesController.MESSAGE_SEND_STATE_SENT) { + if (MessagesController.getInstance().sendingMessages.get(currentMessageObject.messageOwner.id) == null) { + currentMessageObject.messageOwner.send_state = MessagesController.MESSAGE_SEND_STATE_SEND_ERROR; + } + } + + requestLayout(); + } + updateButtonState(); + } + + public final MessageObject getMessageObject() { + return currentMessageObject; + } + + @Override + protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { + int width = MeasureSpec.getSize(widthMeasureSpec); + setMeasuredDimension(width, AndroidUtilities.dp(56)); + } + + @Override + protected void onLayout(boolean changed, int left, int top, int right, int bottom) { + if (currentMessageObject == null) { + super.onLayout(changed, left, top, right, bottom); + return; + } + + seekBarX = AndroidUtilities.dp(40); + buttonX = AndroidUtilities.dp(10); + timeX = getMeasuredWidth() - timeWidth - AndroidUtilities.dp(16); + + seekBar.width = getMeasuredWidth() - AndroidUtilities.dp(56) - timeWidth; + seekBar.height = AndroidUtilities.dp(30); + progressView.width = getMeasuredWidth() - AndroidUtilities.dp(80) - timeWidth; + progressView.height = AndroidUtilities.dp(30); + seekBarY = AndroidUtilities.dp(13); + buttonY = AndroidUtilities.dp(10); + + updateProgress(); + + if (changed || !wasLayout) { + wasLayout = true; + } + } + + @Override + protected void onDraw(Canvas canvas) { + if (currentMessageObject == null) { + return; + } + + if (!wasLayout) { + requestLayout(); + return; + } + + setDrawableBounds(backgroundMediaDrawableIn, 0, 0, getMeasuredWidth(), getMeasuredHeight()); + backgroundMediaDrawableIn.draw(canvas); + + if (currentMessageObject == null) { + return; + } + + canvas.save(); + if (buttonState == 0 || buttonState == 1) { + canvas.translate(seekBarX, seekBarY); + seekBar.draw(canvas); + } else { + canvas.translate(seekBarX + AndroidUtilities.dp(12), seekBarY); + progressView.draw(canvas); + } + canvas.restore(); + + int state = buttonState + 4; + timePaint.setColor(0xffa1aab3); + Drawable buttonDrawable = statesDrawable[state][buttonPressed]; + int side = AndroidUtilities.dp(36); + int x = (side - buttonDrawable.getIntrinsicWidth()) / 2; + int y = (side - buttonDrawable.getIntrinsicHeight()) / 2; + setDrawableBounds(buttonDrawable, x + buttonX, y + buttonY); + buttonDrawable.draw(canvas); + + canvas.save(); + canvas.translate(timeX, AndroidUtilities.dp(18)); + timeLayout.draw(canvas); + canvas.restore(); + } + + @Override + protected void onDetachedFromWindow() { + super.onDetachedFromWindow(); + MediaController.getInstance().removeLoadingFileObserver(this); + } + + @Override + public boolean onTouchEvent(MotionEvent event) { + float x = event.getX(); + float y = event.getY(); + boolean result = seekBar.onTouch(event.getAction(), event.getX() - seekBarX, event.getY() - seekBarY); + if (result) { + if (event.getAction() == MotionEvent.ACTION_DOWN) { + getParent().requestDisallowInterceptTouchEvent(true); + } + invalidate(); + } else { + int side = AndroidUtilities.dp(36); + if (event.getAction() == MotionEvent.ACTION_DOWN) { + if (x >= buttonX && x <= buttonX + side && y >= buttonY && y <= buttonY + side) { + buttonPressed = 1; + invalidate(); + result = true; + } + } else if (buttonPressed == 1) { + if (event.getAction() == MotionEvent.ACTION_UP) { + buttonPressed = 0; + playSoundEffect(SoundEffectConstants.CLICK); + didPressedButton(); + invalidate(); + } else if (event.getAction() == MotionEvent.ACTION_CANCEL) { + buttonPressed = 0; + invalidate(); + } else if (event.getAction() == MotionEvent.ACTION_MOVE) { + if (!(x >= buttonX && x <= buttonX + side && y >= buttonY && y <= buttonY + side)) { + buttonPressed = 0; + invalidate(); + } + } + } + if (!result) { + result = super.onTouchEvent(event); + } + } + + return result; + } + + private void didPressedButton() { + if (buttonState == 0) { + boolean result = MediaController.getInstance().playAudio(currentMessageObject); + if (result) { + buttonState = 1; + invalidate(); + } + } else if (buttonState == 1) { + boolean result = MediaController.getInstance().pauseAudio(currentMessageObject); + if (result) { + buttonState = 0; + invalidate(); + } + } else if (buttonState == 2) { + FileLoader.getInstance().loadFile(null, null, null, currentMessageObject.messageOwner.media.audio); + buttonState = 3; + invalidate(); + } else if (buttonState == 3) { + FileLoader.getInstance().cancelLoadFile(null, null, null, currentMessageObject.messageOwner.media.audio); + buttonState = 2; + invalidate(); + } + } + + public void updateProgress() { + if (currentMessageObject == null) { + return; + } + + if (!seekBar.isDragging()) { + seekBar.setProgress(currentMessageObject.audioProgress); + } + + int duration = 0; + if (!MediaController.getInstance().isPlayingAudio(currentMessageObject)) { + duration = currentMessageObject.messageOwner.media.audio.duration; + } else { + duration = currentMessageObject.audioProgressSec; + } + String timeString = String.format("%02d:%02d", duration / 60, duration % 60); + if (lastTimeString == null || lastTimeString != null && !lastTimeString.equals(timeString)) { + timeWidth = (int)Math.ceil(timePaint.measureText(timeString)); + timeLayout = new StaticLayout(timeString, timePaint, timeWidth, Layout.Alignment.ALIGN_NORMAL, 1.0f, 0.0f, false); + } + invalidate(); + } + + public void downloadAudioIfNeed() { + if (buttonState == 2) { + FileLoader.getInstance().loadFile(null, null, null, currentMessageObject.messageOwner.media.audio); + buttonState = 3; + invalidate(); + } + } + + public void updateButtonState() { + String fileName = currentMessageObject.getFileName(); + File cacheFile = new File(AndroidUtilities.getCacheDir(), fileName); + if (cacheFile.exists()) { + MediaController.getInstance().removeLoadingFileObserver(this); + boolean playing = MediaController.getInstance().isPlayingAudio(currentMessageObject); + if (!playing || playing && MediaController.getInstance().isAudioPaused()) { + buttonState = 0; + } else { + buttonState = 1; + } + progressView.setProgress(0); + } else { + MediaController.getInstance().addLoadingFileObserver(fileName, this); + if (!FileLoader.getInstance().isLoadingFile(fileName)) { + buttonState = 2; + progressView.setProgress(0); + } else { + buttonState = 3; + Float progress = FileLoader.getInstance().fileProgresses.get(fileName); + if (progress != null) { + progressView.setProgress(progress); + } else { + progressView.setProgress(0); + } + } + } + updateProgress(); + } + + @Override + public void onFailedDownload(String fileName) { + updateButtonState(); + } + + @Override + public void onSuccessDownload(String fileName) { + updateButtonState(); + } + + @Override + public void onProgressDownload(String fileName, float progress) { + progressView.setProgress(progress); + invalidate(); + } + + @Override + public void onProgressUpload(String fileName, float progress, boolean isEncrypted) { + + } + + @Override + public int getObserverTag() { + return TAG; + } + + @Override + public void onSeekBarDrag(float progress) { + if (currentMessageObject == null) { + return; + } + currentMessageObject.audioProgress = progress; + MediaController.getInstance().seekToProgress(currentMessageObject, progress); + } +} diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/ProgressView.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/ProgressView.java index cc6e95013..671c858f2 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/ProgressView.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/ProgressView.java @@ -11,7 +11,7 @@ package org.telegram.ui.Views; import android.graphics.Canvas; import android.graphics.Paint; -import org.telegram.messenger.Utilities; +import org.telegram.android.AndroidUtilities; public class ProgressView { private Paint innerPaint; @@ -20,7 +20,7 @@ public class ProgressView { public float currentProgress = 0; public int width; public int height; - public float progressHeight = Utilities.dpf(2.0f); + public float progressHeight = AndroidUtilities.dpf(2.0f); public ProgressView() { innerPaint = new Paint(); diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/SeekBar.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/SeekBar.java index 268e6173d..37543fc27 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/SeekBar.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/SeekBar.java @@ -14,8 +14,8 @@ import android.graphics.Paint; import android.graphics.drawable.Drawable; import android.view.MotionEvent; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.R; -import org.telegram.messenger.Utilities; public class SeekBar { @@ -121,8 +121,8 @@ public class SeekBar { outer = outerPaint2; } int y = (height - thumbHeight) / 2; - canvas.drawRect(thumbWidth / 2, height / 2 - Utilities.dp(1), width - thumbWidth / 2, height / 2 + Utilities.dp(1), inner); - canvas.drawRect(thumbWidth / 2, height / 2 - Utilities.dp(1), thumbWidth / 2 + thumbX, height / 2 + Utilities.dp(1), outer); + canvas.drawRect(thumbWidth / 2, height / 2 - AndroidUtilities.dp(1), width - thumbWidth / 2, height / 2 + AndroidUtilities.dp(1), inner); + canvas.drawRect(thumbWidth / 2, height / 2 - AndroidUtilities.dp(1), thumbWidth / 2 + thumbX, height / 2 + AndroidUtilities.dp(1), outer); thumb.setBounds(thumbX, y, thumbX + thumbWidth, y + thumbHeight); thumb.draw(canvas); } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/SizeNotifierRelativeLayout.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/SizeNotifierRelativeLayout.java index 13b594bd9..41667658c 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/SizeNotifierRelativeLayout.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/SizeNotifierRelativeLayout.java @@ -14,7 +14,7 @@ import android.graphics.Rect; import android.graphics.drawable.Drawable; import android.widget.RelativeLayout; -import org.telegram.messenger.Utilities; +import org.telegram.android.AndroidUtilities; public class SizeNotifierRelativeLayout extends RelativeLayout { @@ -50,7 +50,7 @@ public class SizeNotifierRelativeLayout extends RelativeLayout { protected void onLayout(boolean changed, int l, int t, int r, int b) { super.onLayout(changed, l, t, r, b); if (delegate != null) { - int usableViewHeight = this.getRootView().getHeight() - Utilities.statusBarHeight; + int usableViewHeight = this.getRootView().getHeight() - AndroidUtilities.statusBarHeight; this.getWindowVisibleDisplayFrame(rect); int keyboardHeight = usableViewHeight - (rect.bottom - rect.top); delegate.onSizeChanged(keyboardHeight); @@ -60,15 +60,17 @@ public class SizeNotifierRelativeLayout extends RelativeLayout { @Override protected void onDraw(Canvas canvas) { if (backgroundDrawable != null) { - float scaleX = (float)Utilities.displaySize.x / (float)backgroundDrawable.getIntrinsicWidth(); - float scaleY = (float)Utilities.displaySize.y / (float)backgroundDrawable.getIntrinsicHeight(); + float scaleX = (float)AndroidUtilities.displaySize.x / (float)backgroundDrawable.getIntrinsicWidth(); + float scaleY = (float)AndroidUtilities.displaySize.y / (float)backgroundDrawable.getIntrinsicHeight(); float scale = scaleX < scaleY ? scaleY : scaleX; int width = (int)Math.ceil(backgroundDrawable.getIntrinsicWidth() * scale); int height = (int)Math.ceil(backgroundDrawable.getIntrinsicHeight() * scale); - int x = (Utilities.displaySize.x - width) / 2; - int y = (Utilities.displaySize.y - height) / 2; + int x = (AndroidUtilities.displaySize.x - width) / 2; + int y = (AndroidUtilities.displaySize.y - height) / 2; backgroundDrawable.setBounds(x, y, x + width, y + height); backgroundDrawable.draw(canvas); + } else { + super.onDraw(canvas); } } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/TimerButton.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/TimerButton.java index 3bf8abd07..25257a58d 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Views/TimerButton.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/TimerButton.java @@ -19,9 +19,9 @@ import android.text.TextPaint; import android.util.AttributeSet; import android.view.View; +import org.telegram.android.AndroidUtilities; import org.telegram.messenger.FileLog; import org.telegram.messenger.R; -import org.telegram.messenger.Utilities; public class TimerButton extends View { @@ -38,7 +38,7 @@ public class TimerButton extends View { emptyTimerDrawable = getResources().getDrawable(R.drawable.header_timer); timerDrawable = getResources().getDrawable(R.drawable.header_timer2); timePaint = new TextPaint(Paint.ANTI_ALIAS_FLAG); - timePaint.setTextSize(Utilities.dp(10)); + timePaint.setTextSize(AndroidUtilities.dp(10)); timePaint.setColor(0xffd7e8f7); timePaint.setTypeface(Typeface.DEFAULT_BOLD); } @@ -110,7 +110,7 @@ public class TimerButton extends View { drawable.draw(canvas); if (time != 0 && timeLayout != null) { - canvas.translate((width - timeWidth) / 2, (height - timeHeight) / 2 + Utilities.dp(1)); + canvas.translate((width - timeWidth) / 2, (height - timeHeight) / 2 + AndroidUtilities.dp(1)); timeLayout.draw(canvas); } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/VideoSeekBarView.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/VideoSeekBarView.java new file mode 100644 index 000000000..4bdab183d --- /dev/null +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/VideoSeekBarView.java @@ -0,0 +1,133 @@ +/* + * This is the source code of Telegram for Android v. 1.7.x. + * It is licensed under GNU GPL v. 2 or later. + * You should have received a copy of the license in this archive (see LICENSE). + * + * Copyright Nikolai Kudashov, 2013-2014. + */ + +package org.telegram.ui.Views; + +import android.content.Context; +import android.graphics.Canvas; +import android.graphics.Paint; +import android.graphics.drawable.Drawable; +import android.util.AttributeSet; +import android.view.MotionEvent; +import android.view.View; + +import org.telegram.android.AndroidUtilities; +import org.telegram.messenger.R; + +public class VideoSeekBarView extends View { + + private static Drawable thumbDrawable1; + private static Drawable thumbDrawablePressed1; + private static Paint innerPaint1 = new Paint(); + private static int thumbWidth; + private static int thumbHeight; + private int thumbDX = 0; + private float progress = 0; + private boolean pressed = false; + public SeekBarDelegate delegate; + + public abstract interface SeekBarDelegate { + public void onSeekBarDrag(float progress); + } + + private void init(Context context) { + if (thumbDrawable1 == null) { + thumbDrawable1 = context.getResources().getDrawable(R.drawable.playback); + thumbDrawablePressed1 = context.getResources().getDrawable(R.drawable.playback_active); + innerPaint1.setColor(0x99999999); + thumbWidth = thumbDrawable1.getIntrinsicWidth(); + thumbHeight = thumbDrawable1.getIntrinsicHeight(); + } + } + + public VideoSeekBarView(Context context) { + super(context); + init(context); + } + + public VideoSeekBarView(Context context, AttributeSet attrs) { + super(context, attrs); + init(context); + } + + public VideoSeekBarView(Context context, AttributeSet attrs, int defStyleAttr) { + super(context, attrs, defStyleAttr); + init(context); + } + + @Override + public boolean onTouchEvent(MotionEvent event) { + if (event == null) { + return false; + } + float x = event.getX(); + float y = event.getY(); + float thumbX = (int)((getMeasuredWidth() - thumbWidth) * progress); + if (event.getAction() == MotionEvent.ACTION_DOWN) { + int additionWidth = (getMeasuredHeight() - thumbWidth) / 2; + if (thumbX - additionWidth <= x && x <= thumbX + thumbWidth + additionWidth && y >= 0 && y <= getMeasuredHeight()) { + pressed = true; + thumbDX = (int)(x - thumbX); + getParent().requestDisallowInterceptTouchEvent(true); + invalidate(); + return true; + } + } else if (event.getAction() == MotionEvent.ACTION_UP || event.getAction() == MotionEvent.ACTION_CANCEL) { + if (pressed) { + if (event.getAction() == MotionEvent.ACTION_UP && delegate != null) { + delegate.onSeekBarDrag(thumbX / (float)(getMeasuredWidth() - thumbWidth)); + } + pressed = false; + invalidate(); + return true; + } + } else if (event.getAction() == MotionEvent.ACTION_MOVE) { + if (pressed) { + thumbX = (int)(x - thumbDX); + if (thumbX < 0) { + thumbX = 0; + } else if (thumbX > getMeasuredWidth() - thumbWidth) { + thumbX = getMeasuredWidth() - thumbWidth; + } + progress = thumbX / (getMeasuredWidth() - thumbWidth); + invalidate(); + return true; + } + } + return false; + } + + public void setProgress(float progress) { + if (progress < 0) { + progress = 0; + } else if (progress > 1) { + progress = 1; + } + this.progress = progress; + invalidate(); + } + + public float getProgress() { + return progress; + } + + @Override + protected void onDraw(Canvas canvas) { + Drawable thumb = null; + if (!pressed) { + thumb = thumbDrawable1; + } else { + thumb = thumbDrawablePressed1; + } + int y = (getMeasuredHeight() - thumbHeight) / 2; + int thumbX = (int)((getMeasuredWidth() - thumbWidth) * progress); + canvas.drawRect(thumbWidth / 2, getMeasuredHeight() / 2 - AndroidUtilities.dp(1), getMeasuredWidth() - thumbWidth / 2, getMeasuredHeight() / 2 + AndroidUtilities.dp(1), innerPaint1); + thumb.setBounds(thumbX, y, thumbX + thumbWidth, y + thumbHeight); + thumb.draw(canvas); + } +} diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Views/VideoTimelineView.java b/TMessagesProj/src/main/java/org/telegram/ui/Views/VideoTimelineView.java new file mode 100644 index 000000000..f8fe8e21f --- /dev/null +++ b/TMessagesProj/src/main/java/org/telegram/ui/Views/VideoTimelineView.java @@ -0,0 +1,285 @@ +/* + * This is the source code of Telegram for Android v. 1.7.x. + * It is licensed under GNU GPL v. 2 or later. + * You should have received a copy of the license in this archive (see LICENSE). + * + * Copyright Nikolai Kudashov, 2013-2014. + */ + +package org.telegram.ui.Views; + +import android.annotation.TargetApi; +import android.content.Context; +import android.graphics.Bitmap; +import android.graphics.Canvas; +import android.graphics.Paint; +import android.graphics.Rect; +import android.media.MediaMetadataRetriever; +import android.os.AsyncTask; +import android.util.AttributeSet; +import android.view.MotionEvent; +import android.view.View; + +import org.telegram.android.AndroidUtilities; +import org.telegram.messenger.FileLog; + +import java.util.ArrayList; + +@TargetApi(10) +public class VideoTimelineView extends View { + private long videoLength = 0; + private float progressLeft = 0; + private float progressRight = 1; + private Paint paint; + private Paint paint2; + private boolean pressedLeft = false; + private boolean pressedRight = false; + private float pressDx = 0; + private MediaMetadataRetriever mediaMetadataRetriever = null; + private VideoTimelineViewDelegate delegate = null; + private ArrayList frames = new ArrayList(); + private AsyncTask currentTask = null; + private static final Integer sync = 1; + private long frameTimeOffset = 0; + private int frameWidth = 0; + private int frameHeight = 0; + private int framesToLoad = 0; + + public abstract interface VideoTimelineViewDelegate { + public void onLeftProgressChanged(float progress); + public void onRifhtProgressChanged(float progress); + } + + private void init() { + paint = new Paint(); + paint.setColor(0xff66d1ee); + paint2 = new Paint(); + paint2.setColor(0x2266d1ee); + } + + public VideoTimelineView(Context context) { + super(context); + init(); + } + + public VideoTimelineView(Context context, AttributeSet attrs) { + super(context, attrs); + init(); + } + + public VideoTimelineView(Context context, AttributeSet attrs, int defStyleAttr) { + super(context, attrs, defStyleAttr); + init(); + } + + public float getLeftProgress() { + return progressLeft; + } + + public float getRightProgress() { + return progressRight; + } + + @Override + public boolean onTouchEvent(MotionEvent event) { + if (event == null) { + return false; + } + float x = event.getX(); + float y = event.getY(); + + int width = getMeasuredWidth() - AndroidUtilities.dp(12); + int startX = (int)(width * progressLeft) + AndroidUtilities.dp(3); + int endX = (int)(width * progressRight) + AndroidUtilities.dp(9); + + if (event.getAction() == MotionEvent.ACTION_DOWN) { + int additionWidth = AndroidUtilities.dp(12); + if (startX - additionWidth <= x && x <= startX + additionWidth && y >= 0 && y <= getMeasuredHeight()) { + pressedLeft = true; + pressDx = (int)(x - startX); + getParent().requestDisallowInterceptTouchEvent(true); + invalidate(); + return true; + } else if (endX - additionWidth <= x && x <= endX + additionWidth && y >= 0 && y <= getMeasuredHeight()) { + pressedRight = true; + pressDx = (int)(x - endX); + getParent().requestDisallowInterceptTouchEvent(true); + invalidate(); + return true; + } + } else if (event.getAction() == MotionEvent.ACTION_UP || event.getAction() == MotionEvent.ACTION_CANCEL) { + if (pressedLeft) { + pressedLeft = false; + return true; + } else if (pressedRight) { + pressedRight = false; + return true; + } + } else if (event.getAction() == MotionEvent.ACTION_MOVE) { + if (pressedLeft) { + startX = (int)(x - pressDx); + if (startX < AndroidUtilities.dp(3)) { + startX = AndroidUtilities.dp(3); + } else if (startX > endX - AndroidUtilities.dp(6)) { + startX = endX - AndroidUtilities.dp(6); + } + progressLeft = (float)(startX - AndroidUtilities.dp(3)) / (float)width; + if (delegate != null) { + delegate.onLeftProgressChanged(progressLeft); + } + invalidate(); + return true; + } else if (pressedRight) { + endX = (int)(x - pressDx); + if (endX < startX + AndroidUtilities.dp(6)) { + endX = startX + AndroidUtilities.dp(6); + } else if (endX > width + AndroidUtilities.dp(9)) { + endX = width + AndroidUtilities.dp(9); + } + progressRight = (float)(endX - AndroidUtilities.dp(9)) / (float)width; + if (delegate != null) { + delegate.onRifhtProgressChanged(progressRight); + } + invalidate(); + return true; + } + } + return false; + } + + public void setVideoPath(String path) { + mediaMetadataRetriever = new MediaMetadataRetriever(); + mediaMetadataRetriever.setDataSource(path); + String duration = mediaMetadataRetriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_DURATION); + videoLength = Long.parseLong(duration); + } + + public void setDelegate(VideoTimelineViewDelegate delegate) { + this.delegate = delegate; + } + + private void reloadFrames(int frameNum) { + if (mediaMetadataRetriever == null) { + return; + } + if (frameNum == 0) { + frameHeight = getMeasuredHeight() - AndroidUtilities.dp(4); + framesToLoad = getMeasuredWidth() / frameHeight; + frameWidth = (int)Math.ceil((float)getMeasuredWidth() / (float)framesToLoad); + frameTimeOffset = videoLength / framesToLoad; + } + currentTask = new AsyncTask() { + private int frameNum = 0; + + @Override + protected Bitmap doInBackground(Integer... objects) { + frameNum = objects[0]; + Bitmap bitmap = null; + if (isCancelled()) { + return null; + } + try { + bitmap = mediaMetadataRetriever.getFrameAtTime(frameTimeOffset * frameNum * 1000); + if (isCancelled()) { + return null; + } + if (bitmap != null) { + Bitmap result = Bitmap.createBitmap(frameWidth, frameHeight, bitmap.getConfig()); + Canvas canvas = new Canvas(result); + float scaleX = (float) frameWidth / (float) bitmap.getWidth(); + float scaleY = (float) frameHeight / (float) bitmap.getHeight(); + float scale = scaleX > scaleY ? scaleX : scaleY; + int w = (int) (bitmap.getWidth() * scale); + int h = (int) (bitmap.getHeight() * scale); + Rect srcRect = new Rect(0, 0, bitmap.getWidth(), bitmap.getHeight()); + Rect destRect = new Rect((frameWidth - w) / 2, (frameHeight - h) / 2, w, h); + Paint paint = new Paint(); + canvas.drawBitmap(bitmap, srcRect, destRect, null); + bitmap.recycle(); + bitmap = result; + } + } catch (Exception e) { + FileLog.e("tmessages", e); + } + return bitmap; + } + + @Override + protected void onPostExecute(Bitmap bitmap) { + if (!isCancelled()) { + frames.add(bitmap); + invalidate(); + if (frameNum < framesToLoad) { + reloadFrames(frameNum + 1); + } + } + } + }; + + if (android.os.Build.VERSION.SDK_INT >= 11) { + currentTask.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR, frameNum, null, null); + } else { + currentTask.execute(frameNum, null, null); + } + } + + public void destroy() { + synchronized (sync) { + try { + if (mediaMetadataRetriever != null) { + mediaMetadataRetriever.release(); + mediaMetadataRetriever = null; + } + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + for (Bitmap bitmap : frames) { + if (bitmap != null) { + bitmap.recycle(); + } + } + frames.clear(); + if (currentTask != null) { + currentTask.cancel(true); + currentTask = null; + } + } + + public void clearFrames() { + for (Bitmap bitmap : frames) { + if (bitmap != null) { + bitmap.recycle(); + } + } + frames.clear(); + if (currentTask != null) { + currentTask.cancel(true); + currentTask = null; + } + invalidate(); + } + + @Override + protected void onDraw(Canvas canvas) { + if (frames.isEmpty() && currentTask == null) { + reloadFrames(0); + } else { + int offset = 0; + for (Bitmap bitmap : frames) { + if (bitmap != null) { + canvas.drawBitmap(bitmap, offset * frameWidth, AndroidUtilities.dp(2), null); + } + offset++; + } + } + int width = getMeasuredWidth() - AndroidUtilities.dp(12); + int startX = (int)(width * progressLeft); + int endX = (int)(width * progressRight); + canvas.drawRect(startX, 0, startX + AndroidUtilities.dp(6), getMeasuredHeight(), paint); + canvas.drawRect(endX + AndroidUtilities.dp(6), 0, endX + AndroidUtilities.dp(12), getMeasuredHeight(), paint); + canvas.drawRect(startX + AndroidUtilities.dp(6), AndroidUtilities.dp(4), endX + AndroidUtilities.dp(6), getMeasuredHeight() - AndroidUtilities.dp(4), paint2); + canvas.drawRect(startX + AndroidUtilities.dp(6), AndroidUtilities.dp(2), endX + AndroidUtilities.dp(6), AndroidUtilities.dp(4), paint); + canvas.drawRect(startX + AndroidUtilities.dp(6), getMeasuredHeight() - AndroidUtilities.dp(4), endX + AndroidUtilities.dp(6), getMeasuredHeight() - AndroidUtilities.dp(2), paint); + } +} diff --git a/TMessagesProj/src/main/res/drawable-hdpi/playback.png b/TMessagesProj/src/main/res/drawable-hdpi/playback.png new file mode 100644 index 000000000..1ca26fcac Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-hdpi/playback.png differ diff --git a/TMessagesProj/src/main/res/drawable-hdpi/playback_active.png b/TMessagesProj/src/main/res/drawable-hdpi/playback_active.png new file mode 100644 index 000000000..11760303e Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-hdpi/playback_active.png differ diff --git a/TMessagesProj/src/main/res/drawable-hdpi/video_play.png b/TMessagesProj/src/main/res/drawable-hdpi/video_play.png new file mode 100644 index 000000000..ce78ffabe Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-hdpi/video_play.png differ diff --git a/TMessagesProj/src/main/res/drawable-ldpi/playback.png b/TMessagesProj/src/main/res/drawable-ldpi/playback.png new file mode 100644 index 000000000..d82736e01 Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-ldpi/playback.png differ diff --git a/TMessagesProj/src/main/res/drawable-ldpi/playback_active.png b/TMessagesProj/src/main/res/drawable-ldpi/playback_active.png new file mode 100644 index 000000000..66d42bc17 Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-ldpi/playback_active.png differ diff --git a/TMessagesProj/src/main/res/drawable-ldpi/video_play.png b/TMessagesProj/src/main/res/drawable-ldpi/video_play.png new file mode 100644 index 000000000..ef7a33726 Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-ldpi/video_play.png differ diff --git a/TMessagesProj/src/main/res/drawable-mdpi/playback.png b/TMessagesProj/src/main/res/drawable-mdpi/playback.png new file mode 100644 index 000000000..729c999e9 Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-mdpi/playback.png differ diff --git a/TMessagesProj/src/main/res/drawable-mdpi/playback_active.png b/TMessagesProj/src/main/res/drawable-mdpi/playback_active.png new file mode 100644 index 000000000..65c7c4750 Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-mdpi/playback_active.png differ diff --git a/TMessagesProj/src/main/res/drawable-mdpi/video_play.png b/TMessagesProj/src/main/res/drawable-mdpi/video_play.png new file mode 100644 index 000000000..9e930642f Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-mdpi/video_play.png differ diff --git a/TMessagesProj/src/main/res/drawable-xhdpi/playback.png b/TMessagesProj/src/main/res/drawable-xhdpi/playback.png new file mode 100644 index 000000000..8393b7406 Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-xhdpi/playback.png differ diff --git a/TMessagesProj/src/main/res/drawable-xhdpi/playback_active.png b/TMessagesProj/src/main/res/drawable-xhdpi/playback_active.png new file mode 100644 index 000000000..48c99fb9d Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-xhdpi/playback_active.png differ diff --git a/TMessagesProj/src/main/res/drawable-xhdpi/video_play.png b/TMessagesProj/src/main/res/drawable-xhdpi/video_play.png new file mode 100644 index 000000000..1837fef41 Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-xhdpi/video_play.png differ diff --git a/TMessagesProj/src/main/res/drawable-xxhdpi/playback.png b/TMessagesProj/src/main/res/drawable-xxhdpi/playback.png new file mode 100644 index 000000000..517920f78 Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-xxhdpi/playback.png differ diff --git a/TMessagesProj/src/main/res/drawable-xxhdpi/playback_active.png b/TMessagesProj/src/main/res/drawable-xxhdpi/playback_active.png new file mode 100644 index 000000000..4ed866438 Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-xxhdpi/playback_active.png differ diff --git a/TMessagesProj/src/main/res/drawable-xxhdpi/video_play.png b/TMessagesProj/src/main/res/drawable-xxhdpi/video_play.png new file mode 100644 index 000000000..aa05f5c53 Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-xxhdpi/video_play.png differ diff --git a/TMessagesProj/src/main/res/layout-ar/user_profile_phone_layout.xml b/TMessagesProj/src/main/res/layout-ar/user_profile_phone_layout.xml index 86fc6f1be..544b7294c 100644 --- a/TMessagesProj/src/main/res/layout-ar/user_profile_phone_layout.xml +++ b/TMessagesProj/src/main/res/layout-ar/user_profile_phone_layout.xml @@ -22,6 +22,17 @@ android:layout_gravity="left|center_vertical" android:layout_marginLeft="48dp"/> + + + android:layout_height="40dp" + android:layout_gravity="top"> + android:layout_marginTop="7dp" + android:layout_gravity="top"> diff --git a/TMessagesProj/src/main/res/layout/login_layout.xml b/TMessagesProj/src/main/res/layout/login_layout.xml index 9b249a74f..70818ccca 100644 --- a/TMessagesProj/src/main/res/layout/login_layout.xml +++ b/TMessagesProj/src/main/res/layout/login_layout.xml @@ -159,6 +159,18 @@ android:textColor="#808080" android:lineSpacingExtra="2dp"/> + + + + + + \ No newline at end of file diff --git a/TMessagesProj/src/main/res/layout/popup_count_layout.xml b/TMessagesProj/src/main/res/layout/popup_count_layout.xml new file mode 100644 index 000000000..1593006af --- /dev/null +++ b/TMessagesProj/src/main/res/layout/popup_count_layout.xml @@ -0,0 +1,16 @@ + + + + + \ No newline at end of file diff --git a/TMessagesProj/src/main/res/layout/popup_image_layout.xml b/TMessagesProj/src/main/res/layout/popup_image_layout.xml new file mode 100644 index 000000000..f9e1beb95 --- /dev/null +++ b/TMessagesProj/src/main/res/layout/popup_image_layout.xml @@ -0,0 +1,25 @@ + + + + + + + \ No newline at end of file diff --git a/TMessagesProj/src/main/res/layout/popup_notification_layout.xml b/TMessagesProj/src/main/res/layout/popup_notification_layout.xml new file mode 100644 index 000000000..32cd0f23e --- /dev/null +++ b/TMessagesProj/src/main/res/layout/popup_notification_layout.xml @@ -0,0 +1,157 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/TMessagesProj/src/main/res/layout/popup_text_layout.xml b/TMessagesProj/src/main/res/layout/popup_text_layout.xml new file mode 100644 index 000000000..8f949a756 --- /dev/null +++ b/TMessagesProj/src/main/res/layout/popup_text_layout.xml @@ -0,0 +1,28 @@ + + + + + + + + + \ No newline at end of file diff --git a/TMessagesProj/src/main/res/layout/user_profile_phone_layout.xml b/TMessagesProj/src/main/res/layout/user_profile_phone_layout.xml index ff654495d..3b8b75597 100644 --- a/TMessagesProj/src/main/res/layout/user_profile_phone_layout.xml +++ b/TMessagesProj/src/main/res/layout/user_profile_phone_layout.xml @@ -30,6 +30,17 @@ android:textAllCaps="true" android:layout_gravity="bottom"/> + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/TMessagesProj/src/main/res/values-ar/strings.xml b/TMessagesProj/src/main/res/values-ar/strings.xml index 69397359b..f3a3522e7 100644 --- a/TMessagesProj/src/main/res/values-ar/strings.xml +++ b/TMessagesProj/src/main/res/values-ar/strings.xml @@ -22,11 +22,12 @@ جاري الاتصال بك ... رمز التفعيل الرقم خاطئ؟ + هل استقبلت الرمز؟ اسمك اختر الاسم الأول واسم العائلة - + الاسم الأول اسم العائلة إلغاء التسجيل @@ -76,7 +77,6 @@ أرفق يكتب… يكتبون… - و %d آخرون كتبون هل يوجد لديك سؤال\nحول تيليجرام؟ التقط صورة صورة @@ -90,7 +90,6 @@ الرسالة المعاد توجيهها من لا توجد رسائل أحدث - أعضاء الرسالة أكتب رسالة تحميل @@ -104,8 +103,6 @@ لا تترك أثرًا في خوادمنا تمتلك عداد للتدمير الذاتي لا تسمح بتحويل الرسائل - %1$d رسالة جديدة - %1$d رسائل جديدة لقد تم إخراجك من هذه المجموعة لقد قمت بمغادرة المجموعة حذف هذه المجموعة @@ -113,7 +110,7 @@ قم بالسحب للإلغاء حفظ في الجهاز تطبيق ملف التعريب - Unsupported attachment + المرفق غير مدعوم تم طلب محادثة سرية @@ -172,10 +169,9 @@ إرسال الرسالة إلى... أدخل اسم للمجموعة - عضو اسم المجموعة - أعضاء جميع جهات الاتصال + %1$d/%2$d عضو أدخل سم للمجموعة @@ -273,7 +269,13 @@ بواسطة WiFi فقط الاسم الأول اسم العائلة - LED Color + لون إضاءة الـ LED + إشعارات منبثقة + بدون إشعارات منبثقة + فقط عندما تكون الشاشة تعمل + فقط عندما تكون الشاشة مطفأة + دائمًا أظهر الإشعارات المنبثقة + Badge Number لا توجد وسائط بعد @@ -294,8 +296,13 @@ حفظ في الجهاز %1$d من %2$d الألبوم - All Photos - No photos yet + جميع الصور + لا توجد صور حتى الآن + + + Edit Video + Original Video + Edited Video التالي @@ -355,13 +362,25 @@ اسم العائلة غير صحيح جاري التحميل ... ليس لديك أي مشغل مقاطع مرئية، يرجى تنزيل أية مشغل + يرجى التفضل بإرسال بريد الكتروني إلى sms@telegram.org وشرح مشكلتك. لا يوجد لديك تطبيق يمكنه فتح \'%1$s\'، يرجى تنزيل تطبيق مناسب للإستمرار هذا المستخدم ليس لديه تيليجرام بعد ، هل ترغب في دعوته الآن؟ هل أنت متأكد؟ هل تريد إضافة جهة اتصال؟ - إلى المجموعة؟ %1$s هل تريد إضافة + هل ترغب في إضافة %1$s للمجموعة؟\n\n\n\nعدد الرسائل الحديثة المراد إعادة تحويلها: ؟%1$s هل تريد إعادة توجيه الرسائل إلى هل تريد حذف هذه الدردشة؟ + هل ترغب في إرسال رسالة إلى %1$s؟ + هل أنت متأكد من رغبتك في تسجيل الخروج؟ + هل أنت متأكد من تسجيل الخروج من جميع الأجهزة الأخرى باستثناء هذا الجهاز؟ + هل أنت متأكد من رغبتك في مغادرة المجموعة وحذفها؟ + هل أنت متأكد من رغبتك في حذف المجموعة؟ + هل أنت متأكد من رغبتك في مشاركة جهة الاتصال الخاصة بك؟ + هل أنت متأكد من رغبتك في حظر جهة الاتصال هذه؟ + هل أنت متأكد من رغبتك في إزالة الحظر عن جهة الاتصال هذه؟ + هل أنت متأكد من رغبتك في حذف جهة الاتصال هذه؟ + هل أنت متأكد من رغبتك في بدء محادثة سرية؟ + أعد الإرسال باستخدام اسمي تيليجرام @@ -380,6 +399,38 @@ تيليجرام]]> الرسائل مشفرة بشكل قوي وتستطيع تدمير ذاتها إبدأ المراسلة + + لا يوجد أعضاء + %1$d عضو + %1$d عضوان + %1$d أعضاء + %1$d عضو + %1$d عضو + كذلك %1$d عضو آخر يقوب بالكتابة + كذلك %1$d عضو آخر يقوم بالكتابة + كذلك %1$d عضوان آخران يقومان بالكتابة + كذلك %1$d أعضاء آخرون يقومون بالكتابة + كذلك %1$d عضو آخرون يقومون بالكتابة + كذلك %1$d عضو آخرون يقومون بالكتابة + لا يوجد رسائل جديدة + %1$d رسالة جديدة + %1$d رسالتان جديدتان + %1$d رسائل جديدة + %1$d رسالة جديدة + %1$d رسالة جديدة + لا يوجد رسائل + %1$d رسالة + %1$d رسالتان + %1$d رسائل + %1$d رسالة + %1$d رسالة + ليس من جهة اتصال + من %1$d جهة اتصال + من %1$d جهتان اتصال + من %1$d جهات اتصال + من %1$d جهة اتصال + من %1$d جهة اتصال + CACHE_TAG \ No newline at end of file diff --git a/TMessagesProj/src/main/res/values-de/strings.xml b/TMessagesProj/src/main/res/values-de/strings.xml index 16e4137e4..2fa921381 100644 --- a/TMessagesProj/src/main/res/values-de/strings.xml +++ b/TMessagesProj/src/main/res/values-de/strings.xml @@ -22,6 +22,7 @@ Wir rufen dich an… Code Falsche Nummer? + Code nicht erhalten? Dein Name @@ -76,7 +77,6 @@ Anhängen schreibt... tippen… - und %d weitere Personen Du hast eine Frage\nzu Telegram? Foto aufnehmen Galerie @@ -90,7 +90,6 @@ Weitergeleitete Nachricht Von Keine aktuellen - Mitglieder Nachricht Nachricht verfassen Download @@ -104,8 +103,6 @@ Hinterlassen keine Spuren auf unseren Servern Haben einen Selbstzerstörungs-Timer Erlauben keine Weiterleitung von Nachrichten - %1$d neue Nachricht - %1$d neue Nachrichten Du wurdest aus der Gruppe entfernt Du hast die Gruppe verlassen Diese Gruppe löschen @@ -113,7 +110,7 @@ WISCHEN UM ABZUBRECHEN Im Ordner Downloads speichern Standort-Datei benutzen - Unsupported attachment + Nicht unterstützte Datei Geheimen Chat angefordert @@ -172,10 +169,9 @@ Sende Nachricht an… Gruppennamen eingeben - MITGLIED Gruppenname - MITGLIEDER ALLE KONTAKTE + %1$d/%2$d Mitglieder GRUPPENNAMEN EINGEBEN @@ -227,7 +223,7 @@ DEINE TELEFONNUMMER NACHRICHTEN Benachrichtigung - Nachrichtenvorschau + Vorschau GRUPPEN Nachrichtenton auswählen IN-APP @@ -270,10 +266,16 @@ Sofern Google Play Dienste ausreichend für deine Benachrichtigungen sind, kannst du unseren Benachrichtigungsdienst abschalten. Wir empfehlen allerdings, unseren Dienst dauerhaft aktiviert zu lassen um über neue Nachrichten in Echtzeit informiert zu werden. sortiert nach Kontakte importieren - nur über WLAN + Nur über W-LAN Vorname Nachname - LED Farbe + LED-Farbe + Popup-Benachrichtigung + Kein Popup + Nur wenn Bildschirm „an“ + Nur wenn Bildschirm „aus“ + Popups immer anzeigen + Nummer auf Symbol Noch keine geteilten Medien vorhanden @@ -294,8 +296,13 @@ In der Galerie speichern %1$d von %2$d Galerie - All Photos - No photos yet + Alle Fotos + Noch keine Fotos + + + Edit Video + Original Video + Edited Video Weiter @@ -355,13 +362,25 @@ Ungültiger Nachname Lädt… Du hast keinen Videoplayer. Bitte installiere einen um fortzufahren. + Bitte sende uns eine Email an sms@telegram.org mit einer Beschreibung des Problems. Du hast keine App, die den Dokumententyp \'%1$s\' öffnen kann. Dieser Benutzer hat noch kein Telegram. Möchtest du ihn einladen? Bist du sicher? Kontakt hinzufügen? - %1$s zur Gruppe hinzufügen? + %1$s zur Gruppe hinzufügen?\n\nAnzahl der letzten Nachrichten für die Weiterleitung: Nachrichten an %1$s weiterleiten? Diesen Chat löschen? + Nachricht an %1$s senden? + Möchtest du dich wirklich abmelden? + Sicher, dass du alle anderen Geräte abmelden möchtest? + Diese Gruppe wirklich löschen und verlassen? + Möchtest du wirklich diesen Chat löschen? + Möchtest du wirklich die eigenen Kontaktdaten teilen? + Diesen Kontakt wirklich blockieren? + Blockierung für diesen Kontakt wirklich aufheben? + Diesen Kontakt wirklich löschen? + Wirklich einen geheimen Chat starten? + mit meinem Namen weiterleiten Telegram @@ -380,6 +399,38 @@ Telegram]]>-Nachrichten sind stark verschlüsselt und können sich selbst zerstören Jetzt beginnen + + keine Mitglieder + %1$d Mitglied + %1$d Mitglieder + %1$d Mitglieder + %1$d Mitglieder + %1$d Mitglieder + und %1$d weitere Personen schreiben + und %1$d weitere Personen schreiben + und %1$d weitere Personen schreiben + und %1$d weitere Personen schreiben + und %1$d weitere Personen schreiben + und %1$d weitere Personen schreiben + keine neuen Nachrichten + %1$d neue Nachricht + %1$d neue Nachrichten + %1$d neue Nachrichten + %1$d neue Nachrichten + %1$d neue Nachrichten + keine Nachrichten + %1$d Nachricht + %1$d Nachrichten + %1$d Nachrichten + %1$d Nachrichten + %1$d Nachrichten + von keinem Kontakt + von %1$d Kontakt + von %1$d Kontakten + von %1$d Kontakten + von %1$d Kontakten + von %1$d Kontakten + CACHE_TAG \ No newline at end of file diff --git a/TMessagesProj/src/main/res/values-es/strings.xml b/TMessagesProj/src/main/res/values-es/strings.xml index 0b101766c..035676ae5 100644 --- a/TMessagesProj/src/main/res/values-es/strings.xml +++ b/TMessagesProj/src/main/res/values-es/strings.xml @@ -22,6 +22,7 @@ Llamándote... Código ¿Número incorrecto? + ¿No recibiste el código? Tu nombre @@ -76,7 +77,6 @@ Adjuntar está escribiendo... están escribiendo... - y %d personas más ¿Tienes una pregunta\nsobre Telegram? Hacer foto Galería @@ -90,7 +90,6 @@ Mensaje reenviado De No hay recientes - miembros Mensaje Escribe un mensaje Descargar @@ -104,8 +103,6 @@ No dejan rastro en nuestros servidores Tienen autodestrucción de mensajes No permiten reenvíos de mensajes - %1$d nuevo mensaje - %1$d nuevos mensajes Has sido expulsado de este grupo Has abandonado este grupo Eliminar este grupo @@ -113,7 +110,7 @@ DESLIZA PARA CANCELAR Guardar en descargas Aplicar archivo de traducción - Unsupported attachment + Adjunto no soportado Chat secreto solicitado @@ -172,10 +169,9 @@ Enviar mensaje a... El nombre del grupo - MIEMBRO Nombre del grupo - MIEMBROS TODOS LOS CONTACTOS + %1$d/%2$d miembros INGRESA EL NOMBRE DEL GRUPO @@ -270,10 +266,16 @@ Si los servicios de google play son suficientes para recibir notificaciones, puedes desactivar el \'Servicio de notificaciones\'. Sin embargo, te recomendamos activarlos para mantener la aplicación funcionando en segundo plano y recibir notificaciones de forma instantánea. Ordenar por Importar contactos - Sólo vía WiFi + Solo vía Wifi Nombre Apellido Color del LED + Notificación emergente + Sin notificación emergente + Sólo con pantalla encendida + Sólo con pantalla apagada + Siempre mostrar notificación emergente + Globo de notificación No hay fotos ni vídeos compartidos aún @@ -294,8 +296,13 @@ Guardar en galería %1$d de %2$d Galería - All Photos - No photos yet + Todas + No hay fotos aún + + + Edit Video + Original Video + Edited Video Siguiente @@ -355,13 +362,25 @@ Apellido/s inválido/s Cargando... No tienes reproductor de vídeo. Por favor, instala uno para continuar. + Por favor, envía un correo a sms@telegram.org y explica tu problema. No tienes una aplicación que pueda manejar el tipo mime \'%1$s\'. Por favor, instala una para continuar Este usuario no tiene Telegram aún. ¿Enviarle una invitación? ¿Estás seguro? ¿Añadir contacto? - ¿Añadir a %1$s al grupo? + ¿Añadir a %1$s al grupo?\n\nNúmero de los últimos mensajes para reenviar: ¿Reenviar mensajes a %1$s? ¿Eliminar este chat? + ¿Enviar mensajes a %1$s? + ¿Estás seguro/a que quieres cerrar sesión? + ¿Estás seguro/a que quieres terminar todas las otras sesiones? + ¿Estás seguro/a que quieres eliminar y dejar el grupo? + ¿Estás seguro/a que quieres eliminar este chat? + ¿Estás seguro/a que quieres compartir tu información de contacto? + ¿Estás seguro/a que quieres bloquear este contacto? + ¿Estás seguro/a que quieres desbloquear este contacto? + ¿Estás seguro/a que quieres eliminar este contacto? + ¿Estás seguro/a que quieres iniciar un chat secreto? + reenviar desde mi nombre Telegram @@ -380,6 +399,38 @@ Los mensajes de Telegram]]> están fuertemente]]>cifrados y se pueden autodestruir. Empieza a conversar + + sin miembros + %1$d miembro + %1$d miembros + %1$d miembros + %1$d miembros + %1$d miembros + y %1$d personas más están escribiendo + y %1$d personas más están escribiendo + y %1$d personas más están escribiendo + y %1$d personas más están escribiendo + y %1$d personas más están escribiendo + y %1$d personas más están escribiendo + no hay mensajes nuevos + %1$d nuevo mensaje + %1$d nuevos mensajes + %1$d nuevos mensajes + %1$d nuevos mensajes + %1$d nuevos mensajes + no hay mensajes + %1$d mensaje + %1$d mensajes + %1$d mensajes + %1$d mensajes + %1$d mensajes + unused + de %1$d contacto + de %1$d contactos + de %1$d contactos + de %1$d contactos + de %1$d contactos + CACHE_TAG \ No newline at end of file diff --git a/TMessagesProj/src/main/res/values-it/strings.xml b/TMessagesProj/src/main/res/values-it/strings.xml index fcb8cf810..e4595b3a4 100644 --- a/TMessagesProj/src/main/res/values-it/strings.xml +++ b/TMessagesProj/src/main/res/values-it/strings.xml @@ -22,6 +22,7 @@ Ti stiamo chiamando… Codice Numero errato? + Non hai ricevuto il codice? Il tuo nome @@ -76,7 +77,6 @@ Allega sta scrivendo… stanno scrivendo… - e altre %d persone Hai una domanda\nsu Telegram? Scatta una foto Galleria @@ -90,7 +90,6 @@ Messaggio inoltrato Da Nessuno recente - membri Messaggio Scrivi il messaggio Scarica @@ -104,8 +103,6 @@ Non lasciano traccia sui nostri server Hanno un contatore di autodistruzione Non permettono l’inoltro - %1$d nuovo messaggio - %1$d nuovi messaggi Sei stato espulso da questo gruppo Hai lasciato il gruppo Elimina questo gruppo @@ -113,7 +110,7 @@ TRASCINA PER ANNULLARE Salva in download Applica file di localizzazione - Unsupported attachment + Allegato non supportato Chat segreta richiesta @@ -172,10 +169,9 @@ Invia messaggio a... Immetti il nome del gruppo - MEMBRO Nome gruppo - MEMBRI TUTTI I CONTATTI + %1$d/%2$d membri INSERISCI IL NOME DEL GRUPPO @@ -273,7 +269,13 @@ Solo tramite WiFi Nome Cognome - LED Color + Colore LED + Notifica popup + Nessun popup + Solo con schermo acceso + Solo con schermo spento + Mostra sempre i popup + Badge Number Nessun media condiviso @@ -297,6 +299,11 @@ Tutte le foto Ancora nessuna foto + + Edit Video + Original Video + Edited Video + Avanti Indietro @@ -355,13 +362,25 @@ Cognome non valido Caricamento… Non hai un lettore video, per favore installane uno per continuare + Invia un’email a sms@telegram.org spiegandoci il problema. Non hai nessuna applicazione che può gestire il tipo mime \'%1$s\', installane una per continuare Questo utente non ha ancora Telegram, vuoi invitarlo? Sei sicuro? Vuoi aggiungere il contatto? - Vuoi aggiungere %1$s al gruppo? + Aggiungere %1$s al gruppo?\n\nNumero di messaggi recenti da inoltrare: Vuoi inoltrare i messaggi a %1$s? Vuoi eliminare questa chat? + Inviare i messaggi a %1$s? + Terminare la sessione? + Chiudere tutte le altre sessioni? + Eliminare il gruppo e uscire da esso? + Eliminare questa chat? + Condividere le proprie informazioni di contatto? + Bloccare questo contatto? + Sbloccare questo contatto? + Eliminare questo contatto? + Iniziare una chat segreta? + inoltra dal mio nome Telegram @@ -380,6 +399,38 @@ Telegram]]> cifra in maniera sicura i messaggi e può far sì che si autodistruggano Inizia a inviare messaggi + + nessun membro + %1$d membro + %1$d membri + %1$d membri + %1$d membri + %1$d membri + e %1$d altre persone stanno scrivendo + e %1$d altra persona stanno scrivendo + e %1$d altre persone stanno scrivendo + e %1$d altre persone stanno scrivendo + e %1$d altre persone stanno scrivendo + e %1$d altre persone stanno scrivendo + nessun nuovo messaggio + %1$d nuovo messaggio + %1$d nuovi messaggi + %1$d nuovi messaggi + %1$d nuovi messaggi + %1$d nuovi messaggi + nessun messaggio + %1$d messaggio + %1$d messaggi + %1$d messaggi + %1$d messaggi + %1$d messaggi + da nessun contatto + da %1$d contatto + da %1$d contatti + da %1$d contatti + da %1$d contatti + da %1$d contatti + CACHE_TAG \ No newline at end of file diff --git a/TMessagesProj/src/main/res/values-nl/strings.xml b/TMessagesProj/src/main/res/values-nl/strings.xml index abe731836..e92fc5a4e 100644 --- a/TMessagesProj/src/main/res/values-nl/strings.xml +++ b/TMessagesProj/src/main/res/values-nl/strings.xml @@ -22,6 +22,7 @@ We bellen je… Code Verkeerd nummer? + Geen code ontvangen? Je naam @@ -76,7 +77,6 @@ Bijvoegen is aan het typen… zijn aan het typen… - en nog %d personen Heb je een vraag\nover Telegram? Foto maken Galerij @@ -90,7 +90,6 @@ Doorgestuurd bericht Van Niets recents - deelnemers Bericht Typ een bericht... Downloaden @@ -104,8 +103,6 @@ laten geen sporen achter op onze server verlopen automatisch staan doorsturen niet toe - %1$d nieuw bericht - %1$d nieuwe berichten Je bent verwijderd uit deze groep Je hebt deze groep verlaten Deze groep verwijderen @@ -113,7 +110,7 @@ SLEEP OM TE ANNULEREN Opslaan in Downloads Vertaling toepassen - Unsupported attachment + Bijlageformaat niet ondersteund Privégesprek aangevraagd @@ -172,10 +169,9 @@ Bericht verzenden naar… Groepsnaam... - DEELNEMER Groepsnaam - DEELNEMERS ALLE CONTACTEN + %1$d/%2$d deelnemers GROEPSNAAM INSTELLEN @@ -273,7 +269,13 @@ Alleen via WiFi Voornaam Achternaam - LED Color + LED kleur + Popup melding + Geen popup + Alleen wanneer scherm \"aan\" staat + Alleen wanneer scherm \"uit\" staat + Altijd popup tonen + Badge Number Nog geen media gedeeld @@ -297,6 +299,11 @@ Alle foto\'s Nog geen foto\'s + + Edit Video + Original Video + Edited Video + Volgende Vorige @@ -355,13 +362,25 @@ Ongeldige achternaam Bezig met laden… Je hebt geen mediaspeler. Installeer een mediaspeler om door te gaan. + Stuur aub een emailbericht naar sms@telegram.org en beschrijf uw probleem Je hebt geen applicaties die het MIME-type \'%1$s\' ondersteunen. Installeer een geschikte applicatie om door te gaan. Deze gebruiker heeft nog geen Telegram. Wil je een uitnodiging sturen? Weet je het zeker? Contact toevoegen? - %1$s toevoegen aan de groep? + %1$s toevoegen aan de groep?\n\nAantal recente berichten om door te sturen: Berichten doorsturen naar %1$s? Dit gesprek verwijderen? + Berichten naar %1$s verzenden? + Weet u zeker dat u wil uitloggen? + Alle andere apparaten afmelden? + Deze groep verlaten en groep verwijderen? + Dit gesprek verwijderen? + Deze contact-informatie delen? + Deze persoon blokkeren? + Deze persoon deblokkeren? + Deze contactpersoon verwijderen? + Een privégesprek starten? + doorsturen via mijn eigen naam Telegram @@ -380,6 +399,38 @@ Telegram]]> berichten zijn sterk versleuteld en kunnen zichzelf vernietigen Begin nu met chatten + + geen deelnemers + %1$d deelnemer + %1$d deelnemers + %1$d deelnemers + %1$d deelnemers + %1$d deelnemers + en nog %1$d personen zijn aan het typen + en nog %1$d personen zijn aan het typen + en nog %1$d personen zijn aan het typen + en nog %1$d personen zijn aan het typen + en nog %1$d personen zijn aan het typen + en nog %1$d personen zijn aan het typen + geen nieuwe berichten + %1$d nieuw bericht + %1$d nieuwe berichten + %1$d nieuwe berichten + %1$d nieuwe berichten + %1$d nieuwe berichten + geen berichten + %1$d bericht + %1$d berichten + %1$d berichten + %1$d berichten + %1$d berichten + van geen enkel contactpersoon + van %1$d contactpersoon + van %1$d contactpersonen + van %1$d contactpersonen + van %1$d contactpersonen + van %1$d contactpersonen + CACHE_TAG \ No newline at end of file diff --git a/TMessagesProj/src/main/res/values-pt-rBR/strings.xml b/TMessagesProj/src/main/res/values-pt-rBR/strings.xml index 40fcdb908..dbcc8b02d 100644 --- a/TMessagesProj/src/main/res/values-pt-rBR/strings.xml +++ b/TMessagesProj/src/main/res/values-pt-rBR/strings.xml @@ -22,6 +22,7 @@ Estamos te ligando... Código Número incorreto? + Não recebeu o código? Seu nome @@ -76,7 +77,6 @@ Anexar está escrevendo... estão escrevendo... - e %d mais pessoas Tem alguma dúvida\nsobre o Telegram? Tirar foto Galeria @@ -90,7 +90,6 @@ Mensagem encaminhada De Nada recente - membros Mensagem Escrever mensagem Baixar @@ -100,12 +99,10 @@ %s convidou você para uma conversa secreta. Você convidou %s para uma conversa secreta. Conversas secretas: - Utilizam criptografia ponto a ponto - Não deixam rastro em nossos servidores + Utilizam criptografia ponta a ponta + Não deixam rasto em nossos servidores Têm temporizador para a autodestruição das mensagens Não permitem o reencaminhamento - %1$d nova mensagem - %1$d novas mensagens Você foi removido deste grupo Você saiu deste grupo Apagar este grupo @@ -113,7 +110,7 @@ DESLIZE PARA CANCELAR Salvar em downloads Aplicar arquivo de localização - Unsupported attachment + Anexo não suportado Conversa secreta solicitada @@ -172,10 +169,9 @@ Enviar mensagem para... Digite o nome do grupo - MEMBRO Nome do grupo - MEMBROS TODOS OS CONTATOS + %1$d/%2$d membros DIGITE O NOME DO GRUPO @@ -270,10 +266,16 @@ Se os serviços do Google Play forem suficientes para você receber as notificações, você pode desabilitar o \"Serviço de Notificações\". Porém, nós recomendamos deixá-lo ativo para que o aplicativo continue rodando em segundo plano e recebendo notificações instantâneas. Ordenar Por Importar Contatos - Unicamente com WiFi + Apenas por WiFi Primeiro nome Sobrenome - LED Color + Cor do LED + Notificação Popup + Sem popup + Somente com a tela ligada + Somente com a tela desligada + Sempre mostrar popup + Badge Number Ainda não há mídia compartilhada @@ -294,9 +296,14 @@ Salvar na galeria %1$d de %2$d Galeria - Todas as fotos + Todas as Fotos Ainda não há fotos + + Edit Video + Original Video + Edited Video + Próximo Voltar @@ -355,13 +362,25 @@ Sobrenome inválido Carregando... Você não possui um reprodutor de vídeo, instale um para continuar + Por favor, envie um email para sms@telegram.org e explique seu problema. Você não possui algum aplicativo que pode lidar com o tipo MIME \'%1$s\'. Por favor, instale um para continuar Este usuário ainda não possui Telegram, deseja enviar um convite? Você tem certeza? Adicionar contato? - Adicionar %1$s ao grupo? + Adicionar %1$s para o grupo?\n\nNúmero das últimas mensagens para encaminhar: Encaminhar mensagem para %1$s? Apagar esta conversa? + Enviar mensagens para %1$s? + Você tem certeza que deseja sair dessa sessão? + Você tem certeza que deseja terminar todas as outras sessões? + Você tem certeza que deseja deletar e sair do grupo? + Você tem certeza que deseja deletar esta conversa? + Você tem certeza que deseja compartilhar as informações do seu contato? + Você tem certeza que deseja bloquear este contato? + Você tem certeza que deseja desbloquear este contato? + Você tem certeza que deseja deletar este contato? + Você tem certeza que deseja iniciar uma conversa secreta? + encaminhar pelo meu nome Telegram @@ -372,14 +391,46 @@ Baseado na nuvem Privado Bem-vindo à era das mensagens rápidas e seguras - Telegram]]> envia mensagens mais rapidamente do que]]>qualquer outro aplicativo - Telegram]]> será gratuito para sempre. Sem propaganda.]]>Sem taxa de assinatura - Telegram]]> mantém suas mensagens seguras]]>contra ataques de hackers - Telegram]]> não tem limites para o tamanho de]]>suas mídias e conversas - Telegram]]> permite que você acesse suas mensagens]]>a partir de vários dispositivos - As mensagens do Telegram]]> são fortemente criptografadas]]>e podem se autodestruir + Telegram]]> envia mensagens mais rapidamente do que qualquer outro aplicativo + Telegram]]> será gratuito para sempre. Sem propaganda. Sem taxa de assinatura + Telegram]]> mantém suas mensagens seguras contra ataques de hackers + Telegram]]> não tem limites para o tamanho de suas mídias e conversas + Telegram]]> permite que você acesse suas mensagens a partir de vários dispositivos + As mensagens do Telegram]]> são fortemente criptografadas e podem se autodestruir Comece a conversar + + sem membros + %1$d membro + %1$d membros + %1$d membros + %1$d membros + %1$d membros + e mais %1$d pessoas estão escrevendo + e mais %1$d pessoa está escrevendo + e mais %1$d pessoas estão escrevendo + e mais %1$d pessoas estão escrevendo + e mais %1$d pessoas estão escrevendo + e mais %1$d pessoas estão escrevendo + sem novas mensagens + %1$d nova mensagem + %1$d novas mensagens + %1$d novas mensagens + %1$d novas mensagens + %1$d novas mensagens + sem mensagem + %1$d mensagem + %1$d mensagens + %1$d mensagens + %1$d mensagens + %1$d mensagens + de nenhum contato + de %1$d contato + de %1$d contatos + de %1$d contatos + de %1$d contatos + de %1$d contatos + CACHE_TAG \ No newline at end of file diff --git a/TMessagesProj/src/main/res/values-pt-rPT/strings.xml b/TMessagesProj/src/main/res/values-pt-rPT/strings.xml index 110e2c476..13f7a41dc 100644 --- a/TMessagesProj/src/main/res/values-pt-rPT/strings.xml +++ b/TMessagesProj/src/main/res/values-pt-rPT/strings.xml @@ -22,6 +22,7 @@ A ligar... Código Número incorreto? + Didn\'t get the code? O seu nome @@ -76,7 +77,6 @@ Anexar está a escrever... estão a escrever... - e mais %d pessoas Tem alguma pergunta\nacerca do Telegram? Tirar uma foto Galeria @@ -90,7 +90,6 @@ Mensagem reencaminhada De Não há recentes - membros Mensagem Escrever mensagem Transferir @@ -104,8 +103,6 @@ Não deixam rasto nos nossos servidores Têm temporizador para a autodestruição das mensagens Não permitem o reencaminhamento - %1$d nova mensagem - %1$d novas mensagens Foi removido do grupo Deixou este grupo Eliminar este grupo @@ -172,10 +169,9 @@ Enviar mensagem para... Introduza o nome do grupo - MEMBRO Nome do grupo - MEMBROS TODOS OS CONTACTOS + %1$d/%2$d members INTRODUZA O NOME DO GRUPO @@ -274,6 +270,12 @@ Nome Apelidos LED Color + Popup Notification + No popup + Only when screen "on" + Only when screen "off" + Always show popup + Badge Number Ainda não há multimédia partilhado @@ -297,6 +299,11 @@ Todas as fotos Ainda não há fotos + + Edit Video + Original Video + Edited Video + Seguinte Anterior @@ -355,13 +362,25 @@ Apelido inválido A carregar... Não tem nenhum reprodutor de vídeo. Para continuar, instale algum + Please send an email to sms@telegram.org and explain your problem. Não tem nenhuma aplicação que controle o tipo de MIME \'%1$s\'. Para continuar, instale alguma Este utilizador ainda não tem o Telegram. Quer enviar um convite? Tem a certeza? Adicionar contacto? - Adicionar %1$s ao grupo? + Add %1$s to the group?\n\nNumber of last messages to forward: Reencaminhar mensagens para %1$s? Eliminar este chat? + Send messages to %1$s? + Are you sure you want to logout? + Are you sure you want to terminate all other sessions? + Are you sure you want to delete and leave group? + Are you sure you want to delete this chat? + Are you sure that you want to share your contact info? + Are you sure you want to block this contact? + Are you sure you want to unblock this contact? + Are you sure you want to delete this contact? + Are you sure you want to start secret chat? + forward from my name Telegram @@ -380,6 +399,42 @@ As mensagens do Telegram]]> estão fortemente encriptadas]]>e podem ser autodestruídas Comece a conversar + + no members + %1$d member + %1$d members + %1$d members + %1$d members + %1$d members + + and %1$d more people are typing + and %1$d more people are typing + and %1$d more people are typing + and %1$d more people are typing + and %1$d more people are typing + and %1$d more people are typing + + no new messages + %1$d new message + %1$d new messages + %1$d new messages + %1$d new messages + %1$d new messages + + no messages + %1$d message + %1$d messages + %1$d messages + %1$d messages + %1$d messages + + from no contacts + from %1$d contact + from %1$d contacts + from %1$d contacts + from %1$d contacts + from %1$d contacts + CACHE_TAG \ No newline at end of file diff --git a/TMessagesProj/src/main/res/values/strings.xml b/TMessagesProj/src/main/res/values/strings.xml index 8030a4c68..b5a9c5975 100644 --- a/TMessagesProj/src/main/res/values/strings.xml +++ b/TMessagesProj/src/main/res/values/strings.xml @@ -22,6 +22,7 @@ Calling you... Code Wrong number? + Didn\'t get the code? Your name @@ -76,7 +77,6 @@ Attach is typing... are typing... - and %d more people Got a question\nabout Telegram? Take photo Gallery @@ -90,7 +90,6 @@ Forwarded message From No recent - members Message Type message Download @@ -104,8 +103,6 @@ Leave no trace on our servers Have a self-destruct timer Do not allow forwarding - %1$d new message - %1$d new messages You were removed from this group You left this group Delete this group @@ -172,10 +169,9 @@ Send message to... Enter group name - MEMBER Group name - MEMBERS ALL CONTACTS + %1$d/%2$d members ENTER GROUP NAME @@ -274,6 +270,12 @@ First name Last name LED Color + Popup Notification + No popup + Only when screen "on" + Only when screen "off" + Always show popup + Badge Number No shared media yet @@ -297,6 +299,11 @@ All Photos No photos yet + + Edit Video + Original Video + Edited Video + Next Back @@ -355,13 +362,25 @@ Invalid last name Loading... You don\'t have a video player, please install one to continue + Please send an email to sms@telegram.org and explain your problem. You don\'t have any application that can handle with mime type \'%1$s\', please install one to continue This user does not have Telegram yet, send an invitation? Are you sure? Add contact? - Add %1$s to the group? + Add %1$s to the group?\n\nNumber of last messages to forward: Forward messages to %1$s? Delete this chat? + Send messages to %1$s? + Are you sure you want to logout? + Are you sure you want to terminate all other sessions? + Are you sure you want to delete and leave group? + Are you sure you want to delete this chat? + Are you sure that you want to share your contact info? + Are you sure you want to block this contact? + Are you sure you want to unblock this contact? + Are you sure you want to delete this contact? + Are you sure you want to start secret chat? + forward from my name Telegram @@ -380,6 +399,38 @@ Telegram]]> messages are heavily encrypted]]>and can self-destruct Start Messaging + + no members + %1$d member + %1$d members + %1$d members + %1$d members + %1$d members + and %1$d more people are typing + and %1$d more people are typing + and %1$d more people are typing + and %1$d more people are typing + and %1$d more people are typing + and %1$d more people are typing + no new messages + %1$d new message + %1$d new messages + %1$d new messages + %1$d new messages + %1$d new messages + no messages + %1$d message + %1$d messages + %1$d messages + %1$d messages + %1$d messages + from no contacts + from %1$d contact + from %1$d contacts + from %1$d contacts + from %1$d contacts + from %1$d contacts + CACHE_TAG \ No newline at end of file diff --git a/TMessagesProj/src/main/res/values/styles.xml b/TMessagesProj/src/main/res/values/styles.xml index 2f71635a7..247018e30 100644 --- a/TMessagesProj/src/main/res/values/styles.xml +++ b/TMessagesProj/src/main/res/values/styles.xml @@ -7,13 +7,14 @@ @style/ActionBar.Transparent.TMessages.Start @android:color/white @android:color/white - @drawable/shadow + @null + +