diff --git a/TMessagesProj/build.gradle b/TMessagesProj/build.gradle index 00e4e0621..0fccd29b3 100644 --- a/TMessagesProj/build.gradle +++ b/TMessagesProj/build.gradle @@ -79,7 +79,7 @@ android { defaultConfig { minSdkVersion 8 targetSdkVersion 23 - versionCode 685 - versionName "3.3.1" + versionCode 695 + versionName "3.3.2" } } diff --git a/TMessagesProj/jni/sqlite/sqlite3.c b/TMessagesProj/jni/sqlite/sqlite3.c index 73ee2685c..486eefee4 100644 --- a/TMessagesProj/jni/sqlite/sqlite3.c +++ b/TMessagesProj/jni/sqlite/sqlite3.c @@ -17,6 +17,7 @@ ** language. The code for the "sqlite3" command-line shell is also in a ** separate file. This file contains only code for the core SQLite library. */ +#define SQLITE_THREADSAFE 0 #define SQLITE_CORE 1 #define SQLITE_AMALGAMATION 1 #ifndef SQLITE_PRIVATE diff --git a/TMessagesProj/libs/armeabi-v7a/libtmessages.15.so b/TMessagesProj/libs/armeabi-v7a/libtmessages.15.so index f62e87467..db018dbe6 100755 Binary files a/TMessagesProj/libs/armeabi-v7a/libtmessages.15.so and b/TMessagesProj/libs/armeabi-v7a/libtmessages.15.so differ diff --git a/TMessagesProj/libs/armeabi/libtmessages.15.so b/TMessagesProj/libs/armeabi/libtmessages.15.so index 36b131c8e..a03c82b13 100755 Binary files a/TMessagesProj/libs/armeabi/libtmessages.15.so and b/TMessagesProj/libs/armeabi/libtmessages.15.so differ diff --git a/TMessagesProj/libs/x86/libtmessages.15.so b/TMessagesProj/libs/x86/libtmessages.15.so index f7b9edf1a..a669d14bf 100755 Binary files a/TMessagesProj/libs/x86/libtmessages.15.so and b/TMessagesProj/libs/x86/libtmessages.15.so differ diff --git a/TMessagesProj/src/main/AndroidManifest.xml b/TMessagesProj/src/main/AndroidManifest.xml index 2e1ca0ef4..74e63fcda 100644 --- a/TMessagesProj/src/main/AndroidManifest.xml +++ b/TMessagesProj/src/main/AndroidManifest.xml @@ -44,7 +44,8 @@ android:hardwareAccelerated="@bool/useHardwareAcceleration" android:icon="@drawable/ic_launcher" android:largeHeap="true" - android:theme="@style/Theme.TMessages.Start"> + android:theme="@style/Theme.TMessages.Start" + android:manageSpaceActivity="org.telegram.ui.ManageSpaceActivity"> + + @@ -168,6 +176,7 @@ + diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/AndroidUtilities.java b/TMessagesProj/src/main/java/org/telegram/messenger/AndroidUtilities.java index 7abff0967..ab507911d 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/AndroidUtilities.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/AndroidUtilities.java @@ -536,7 +536,7 @@ public class AndroidUtilities { } public static int getViewInset(View view) { - if (view == null || Build.VERSION.SDK_INT < 21) { + if (view == null || Build.VERSION.SDK_INT < 21 || view.getHeight() == AndroidUtilities.displaySize.y || view.getHeight() == AndroidUtilities.displaySize.y - statusBarHeight) { return 0; } try { diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/ApplicationLoader.java b/TMessagesProj/src/main/java/org/telegram/messenger/ApplicationLoader.java index aeb1b20a8..1e485197b 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/ApplicationLoader.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/ApplicationLoader.java @@ -234,16 +234,16 @@ public class ApplicationLoader extends Application { appVersion = "App version unknown"; systemVersion = "SDK " + Build.VERSION.SDK_INT; } - if (langCode.length() == 0) { + if (langCode.trim().length() == 0) { langCode = "en"; } - if (deviceModel.length() == 0) { + if (deviceModel.trim().length() == 0) { deviceModel = "Android unknown"; } - if (appVersion.length() == 0) { + if (appVersion.trim().length() == 0) { appVersion = "App version unknown"; } - if (systemVersion.length() == 0) { + if (systemVersion.trim().length() == 0) { systemVersion = "SDK Unknown"; } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/BuildVars.java b/TMessagesProj/src/main/java/org/telegram/messenger/BuildVars.java index 716dc48e2..303034bf9 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/BuildVars.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/BuildVars.java @@ -10,7 +10,7 @@ package org.telegram.messenger; public class BuildVars { public static boolean DEBUG_VERSION = false; - public static int BUILD_VERSION = 685; + public static int BUILD_VERSION = 695; public static int APP_ID = 0; //obtain your own APP_ID at https://core.telegram.org/api/obtaining_api_id public static String APP_HASH = ""; //obtain your own APP_HASH at https://core.telegram.org/api/obtaining_api_id public static String HOCKEY_APP_HASH = "your-hockeyapp-api-key-here"; diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/ClearCacheService.java b/TMessagesProj/src/main/java/org/telegram/messenger/ClearCacheService.java new file mode 100644 index 000000000..e0ee3635b --- /dev/null +++ b/TMessagesProj/src/main/java/org/telegram/messenger/ClearCacheService.java @@ -0,0 +1,77 @@ +/* + * This is the source code of Telegram for Android v. 3.x.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-2015. + */ + +package org.telegram.messenger; + +import android.app.Activity; +import android.app.IntentService; +import android.content.Intent; +import android.content.SharedPreferences; +import android.os.Build; +import android.system.Os; +import android.system.StructStat; + +import java.io.File; +import java.util.HashMap; + +public class ClearCacheService extends IntentService { + + public ClearCacheService() { + super("ClearCacheService"); + } + + @Override + protected void onHandleIntent(Intent intent) { + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("mainconfig", Activity.MODE_PRIVATE); + final int keepMedia = preferences.getInt("keep_media", 2); + if (keepMedia == 2) { + return; + } + Utilities.globalQueue.postRunnable(new Runnable() { + @Override + public void run() { + long currentTime = System.currentTimeMillis(); + long diff = 60 * 60 * 1000 * 24 * (keepMedia == 0 ? 7 : 30); + final HashMap paths = ImageLoader.getInstance().createMediaPaths(); + for (HashMap.Entry entry : paths.entrySet()) { + if (entry.getKey() == FileLoader.MEDIA_DIR_CACHE) { + continue; + } + try { + File[] array = entry.getValue().listFiles(); + if (array != null) { + for (int b = 0; b < array.length; b++) { + File f = array[b]; + if (f.isFile()) { + if (Build.VERSION.SDK_INT >= 21) { + try { + StructStat stat = Os.stat(f.getPath()); + if (stat.st_atime != 0) { + if (stat.st_atime + diff < currentTime) { + f.delete(); + } + } else if (stat.st_mtime + diff < currentTime) { + f.delete(); + } + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } else if (f.lastModified() + diff < currentTime) { + f.delete(); + } + } + } + } + } catch (Throwable e) { + FileLog.e("tmessages", e); + } + } + } + }); + } +} diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/FileLoadOperation.java b/TMessagesProj/src/main/java/org/telegram/messenger/FileLoadOperation.java index e23b557a3..295729f0b 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/FileLoadOperation.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/FileLoadOperation.java @@ -49,6 +49,7 @@ public class FileLoadOperation { private int currentDownloadChunkSize; private int currentMaxDownloadRequests; private int requestsCount; + private int renameRetryCount; private int nextDownloadOffset = 0; private ArrayList requestInfos; @@ -194,7 +195,7 @@ public class FileLoadOperation { String fileNameTemp; String fileNameIv = null; if (location.volume_id != 0 && location.local_id != 0) { - fileNameTemp = location.volume_id + "_" + location.local_id + "_temp." + ext; + fileNameTemp = location.volume_id + "_" + location.local_id + ".temp"; fileNameFinal = location.volume_id + "_" + location.local_id + "." + ext; if (key != null) { fileNameIv = location.volume_id + "_" + location.local_id + ".iv"; @@ -210,7 +211,7 @@ public class FileLoadOperation { return; } } else { - fileNameTemp = datacenter_id + "_" + location.id + "_temp" + ext; + fileNameTemp = datacenter_id + "_" + location.id + ".temp"; fileNameFinal = datacenter_id + "_" + location.id + ext; if (key != null) { fileNameIv = datacenter_id + "_" + location.id + ".iv"; @@ -236,7 +237,7 @@ public class FileLoadOperation { if (!cacheFileFinal.exists()) { cacheFileTemp = new File(tempPath, fileNameTemp); if (cacheFileTemp.exists()) { - downloadedBytes = (int)cacheFileTemp.length(); + downloadedBytes = (int) cacheFileTemp.length(); nextDownloadOffset = downloadedBytes = downloadedBytes / currentDownloadChunkSize * currentDownloadChunkSize; } @@ -324,6 +325,11 @@ public class FileLoadOperation { private void cleanup() { try { if (fileOutputStream != null) { + try { + fileOutputStream.getChannel().close(); + } catch (Exception e) { + FileLog.e("tmessages", e); + } fileOutputStream.close(); fileOutputStream = null; } @@ -340,7 +346,8 @@ public class FileLoadOperation { FileLog.e("tmessages", e); } if (delayedRequestInfos != null) { - for (RequestInfo requestInfo : delayedRequestInfos) { + for (int a = 0; a < delayedRequestInfos.size(); a++) { + RequestInfo requestInfo = delayedRequestInfos.get(a); if (requestInfo.response != null) { requestInfo.response.disableFree = false; requestInfo.response.freeResources(); @@ -358,11 +365,28 @@ public class FileLoadOperation { cleanup(); if (cacheIvTemp != null) { cacheIvTemp.delete(); + cacheIvTemp = null; } if (cacheFileTemp != null) { - if (!cacheFileTemp.renameTo(cacheFileFinal)) { + boolean renameResult = cacheFileTemp.renameTo(cacheFileFinal); + if (!renameResult) { if (BuildVars.DEBUG_VERSION) { - FileLog.e("tmessages", "unable to rename temp = " + cacheFileTemp + " to final = " + cacheFileFinal); + FileLog.e("tmessages", "unable to rename temp = " + cacheFileTemp + " to final = " + cacheFileFinal + " retry = " + renameRetryCount); + } + renameRetryCount++; + if (renameRetryCount < 3) { + state = stateDownloading; + Utilities.stageQueue.postRunnable(new Runnable() { + @Override + public void run() { + try { + onFinishLoadingFile(); + } catch (Exception e) { + delegate.didFailedLoadingFile(FileLoadOperation.this, 0); + } + } + }, 200); + return; } cacheFileFinal = cacheFileTemp; } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/FileLoader.java b/TMessagesProj/src/main/java/org/telegram/messenger/FileLoader.java index 5daa4f4cf..8b7f8ef16 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/FileLoader.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/FileLoader.java @@ -80,6 +80,10 @@ public class FileLoader { mediaDirs = dirs; } + public File checkDirectory(int type) { + return mediaDirs.get(type); + } + public File getDirectory(int type) { File dir = mediaDirs.get(type); if (dir == null && type != MEDIA_DIR_CACHE) { @@ -746,7 +750,7 @@ public class FileLoader { return ""; } - public void deleteFiles(final ArrayList files) { + public void deleteFiles(final ArrayList files, final int type) { if (files == null || files.isEmpty()) { return; } @@ -765,16 +769,19 @@ public class FileLoader { } } try { - File qFile = new File(file.getPath(), "q_" + file.getName()); + File qFile = new File(file.getParentFile(), "q_" + file.getName()); if (qFile.exists()) { - if (!file.delete()) { - file.deleteOnExit(); + if (!qFile.delete()) { + qFile.deleteOnExit(); } } } catch (Exception e) { FileLog.e("tmessages", e); } } + if (type == 2) { + ImageLoader.getInstance().clearMemory(); + } } }); } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/ImageLoader.java b/TMessagesProj/src/main/java/org/telegram/messenger/ImageLoader.java index 22ad1f691..453e37e51 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/ImageLoader.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/ImageLoader.java @@ -1256,7 +1256,7 @@ public class ImageLoader { try { File imagePath = new File(telegramPath, "Telegram Images"); imagePath.mkdir(); - if (imagePath.isDirectory() && canMoveFiles(cachePath, imagePath)) { + if (imagePath.isDirectory() && canMoveFiles(cachePath, imagePath, FileLoader.MEDIA_DIR_IMAGE)) { mediaDirs.put(FileLoader.MEDIA_DIR_IMAGE, imagePath); FileLog.e("tmessages", "image path = " + imagePath); } @@ -1267,7 +1267,7 @@ public class ImageLoader { try { File videoPath = new File(telegramPath, "Telegram Video"); videoPath.mkdir(); - if (videoPath.isDirectory() && canMoveFiles(cachePath, videoPath)) { + if (videoPath.isDirectory() && canMoveFiles(cachePath, videoPath, FileLoader.MEDIA_DIR_VIDEO)) { mediaDirs.put(FileLoader.MEDIA_DIR_VIDEO, videoPath); FileLog.e("tmessages", "video path = " + videoPath); } @@ -1278,7 +1278,7 @@ public class ImageLoader { try { File audioPath = new File(telegramPath, "Telegram Audio"); audioPath.mkdir(); - if (audioPath.isDirectory() && canMoveFiles(cachePath, audioPath)) { + if (audioPath.isDirectory() && canMoveFiles(cachePath, audioPath, FileLoader.MEDIA_DIR_AUDIO)) { new File(audioPath, ".nomedia").createNewFile(); mediaDirs.put(FileLoader.MEDIA_DIR_AUDIO, audioPath); FileLog.e("tmessages", "audio path = " + audioPath); @@ -1290,7 +1290,7 @@ public class ImageLoader { try { File documentPath = new File(telegramPath, "Telegram Documents"); documentPath.mkdir(); - if (documentPath.isDirectory() && canMoveFiles(cachePath, documentPath)) { + if (documentPath.isDirectory() && canMoveFiles(cachePath, documentPath, FileLoader.MEDIA_DIR_DOCUMENT)) { new File(documentPath, ".nomedia").createNewFile(); mediaDirs.put(FileLoader.MEDIA_DIR_DOCUMENT, documentPath); FileLog.e("tmessages", "documents path = " + documentPath); @@ -1310,23 +1310,35 @@ public class ImageLoader { return mediaDirs; } - private boolean canMoveFiles(File from, File to) { + private boolean canMoveFiles(File from, File to, int type) { RandomAccessFile file = null; try { - for (int a = 0; a < 2; a++) { - File srcFile = new File(from, "temp.file"); - srcFile.createNewFile(); - file = new RandomAccessFile(srcFile, "rws"); - file.write(1); - file.close(); - file = null; - File dstFile = new File(to, "temp.file"); - boolean canRename = srcFile.renameTo(dstFile); - srcFile.delete(); - dstFile.delete(); - if (canRename) { - return true; - } + File srcFile = null; + File dstFile = null; + if (type == FileLoader.MEDIA_DIR_IMAGE) { + srcFile = new File(from, "000000000_999999_temp.jpg"); + dstFile = new File(to, "000000000_999999.jpg"); + } else if (type == FileLoader.MEDIA_DIR_DOCUMENT) { + srcFile = new File(from, "000000000_999999_temp.doc"); + dstFile = new File(to, "000000000_999999.doc"); + } else if (type == FileLoader.MEDIA_DIR_AUDIO) { + srcFile = new File(from, "000000000_999999_temp.ogg"); + dstFile = new File(to, "000000000_999999.ogg"); + } else if (type == FileLoader.MEDIA_DIR_VIDEO) { + srcFile = new File(from, "000000000_999999_temp.mp4"); + dstFile = new File(to, "000000000_999999.mp4"); + } + byte[] buffer = new byte[1024]; + srcFile.createNewFile(); + file = new RandomAccessFile(srcFile, "rws"); + file.write(buffer); + file.close(); + file = null; + boolean canRename = srcFile.renameTo(dstFile); + srcFile.delete(); + dstFile.delete(); + if (canRename) { + return true; } } catch (Exception e) { FileLog.e("tmessages", e); diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/LocaleController.java b/TMessagesProj/src/main/java/org/telegram/messenger/LocaleController.java index 58ecd85a8..355427b08 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/LocaleController.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/LocaleController.java @@ -495,7 +495,7 @@ public class LocaleController { FileLog.e("tmessages", e); } } - return null; + return new HashMap<>(); } public void applyLanguage(LocaleInfo localeInfo, boolean override) { @@ -800,6 +800,7 @@ public class LocaleController { public static String formatShortNumber(int number, int[] rounded) { String K = ""; int lastDec = 0; + int KCount = 0; while (number / 1000 > 0) { K += "K"; lastDec = (number % 1000) / 100; @@ -813,7 +814,11 @@ public class LocaleController { rounded[0] = (int) value; } if (lastDec != 0 && K.length() > 0) { - return String.format(Locale.US, "%d.%d%s", number, lastDec, K); + if (K.length() == 2) { + return String.format(Locale.US, "%d.%dM", number, lastDec); + } else { + return String.format(Locale.US, "%d.%d%s", number, lastDec, K); + } } return String.format(Locale.US, "%d%s", number, K); } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/MediaController.java b/TMessagesProj/src/main/java/org/telegram/messenger/MediaController.java index 1f9d6cf15..50ec51e5a 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/MediaController.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/MediaController.java @@ -1750,6 +1750,7 @@ public class MediaController implements NotificationCenter.NotificationCenterDel } } catch (Exception e) { FileLog.e("tmessages", e); + NotificationCenter.getInstance().postNotificationName(NotificationCenter.audioPlayStateChanged, playingMessageObject != null ? playingMessageObject.getId() : 0); if (audioPlayer != null) { audioPlayer.release(); audioPlayer = null; diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/MessagesController.java b/TMessagesProj/src/main/java/org/telegram/messenger/MessagesController.java index 67ebb73ac..2a8e3a3a6 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/MessagesController.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/MessagesController.java @@ -1318,22 +1318,27 @@ public class MessagesController implements NotificationCenter.NotificationCenter } } - public void deleteDialog(final long did, final boolean onlyHistory) { + public void deleteDialog(final long did, final int onlyHistory) { deleteDialog(did, true, onlyHistory, 0); } - private void deleteDialog(final long did, final boolean first, final boolean onlyHistory, final int max_id) { + private void deleteDialog(final long did, final boolean first, final int onlyHistory, final int max_id) { int lower_part = (int) did; int high_id = (int) (did >> 32); int max_id_delete = max_id; + if (onlyHistory == 2) { + MessagesStorage.getInstance().deleteDialog(did, onlyHistory); + return; + } + if (first) { TLRPC.Dialog dialog = dialogs_dict.get(did); if (dialog != null) { if (max_id_delete == 0) { max_id_delete = Math.max(0, dialog.top_message); } - if (!onlyHistory) { + if (onlyHistory == 0) { dialogs.remove(dialog); if (dialogsServerOnly.remove(dialog)) { if (dialog instanceof TLRPC.TL_dialogChannel) { @@ -1341,6 +1346,8 @@ public class MessagesController implements NotificationCenter.NotificationCenter @Override public void run() { channelsPts.remove(-(int) did); + shortPollChannels.delete(-(int) did); + needShortPollChannels.delete(-(int) did); } }); } @@ -1399,7 +1406,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } }, ConnectionsManager.RequestFlagInvokeAfter); } else { - if (onlyHistory) { + if (onlyHistory == 1) { SecretChatHelper.getInstance().sendClearHistoryMessage(getEncryptedChat(high_id), null); } else { SecretChatHelper.getInstance().declineSecretChat(high_id); @@ -1852,6 +1859,10 @@ public class MessagesController implements NotificationCenter.NotificationCenter } public void loadMessages(final long dialog_id, final int count, final int max_id, boolean fromCache, int midDate, final int classGuid, final int load_type, final int last_message_id, final int important, final int loadIndex) { + loadMessages(dialog_id, count, max_id, fromCache, midDate, classGuid, load_type, last_message_id, important, loadIndex, 0, 0, 0, false); + } + + public void loadMessages(final long dialog_id, final int count, final int max_id, boolean fromCache, int midDate, final int classGuid, final int load_type, final int last_message_id, final int important, final int loadIndex, final int first_unread, final int unread_count, final int last_date, final boolean queryFromServer) { int lower_part = (int) dialog_id; if (fromCache || lower_part == 0) { MessagesStorage.getInstance().getMessages(dialog_id, count, max_id, midDate, classGuid, load_type, important, loadIndex); @@ -1864,6 +1875,8 @@ public class MessagesController implements NotificationCenter.NotificationCenter req.add_offset = -count / 2; } else if (load_type == 1) { req.add_offset = -count - 1; + } else if (load_type == 2 && max_id != 0) { + req.add_offset = -count + 6; } else { if (max_id != 0) { req.add_offset = -1; @@ -1880,6 +1893,8 @@ public class MessagesController implements NotificationCenter.NotificationCenter req.add_offset = -count / 2; } else if (load_type == 1) { req.add_offset = -count - 1; + } else if (load_type == 2 && max_id != 0) { + req.add_offset = -count + 6; } else { req.add_offset = 0; } @@ -1895,7 +1910,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter if (res.messages.size() > count) { res.messages.remove(0); } - processLoadedMessages(res, dialog_id, count, max_id, false, classGuid, 0, last_message_id, 0, 0, load_type, important, false, loadIndex); + processLoadedMessages(res, dialog_id, count, max_id, false, classGuid, first_unread, last_message_id, unread_count, last_date, load_type, important, false, loadIndex, queryFromServer); } } }); @@ -1904,7 +1919,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } public void processLoadedMessages(final TLRPC.messages_Messages messagesRes, final long dialog_id, final int count, final int max_id, final boolean isCache, final int classGuid, - final int first_unread, final int last_message_id, final int unread_count, final int last_date, final int load_type, final int important, final boolean isEnd, final int loadIndex) { + final int first_unread, final int last_message_id, final int unread_count, final int last_date, final int load_type, final int important, final boolean isEnd, final int loadIndex, final boolean queryFromServer) { Utilities.stageQueue.postRunnable(new Runnable() { @Override public void run() { @@ -1938,7 +1953,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter AndroidUtilities.runOnUIThread(new Runnable() { @Override public void run() { - loadMessages(dialog_id, count, max_id, false, 0, classGuid, load_type, last_message_id, important, loadIndex); + loadMessages(dialog_id, count, load_type == 2 && queryFromServer ? first_unread : max_id, false, 0, classGuid, load_type, last_message_id, important, loadIndex, first_unread, unread_count, last_date, queryFromServer); } }); return; @@ -1999,7 +2014,19 @@ public class MessagesController implements NotificationCenter.NotificationCenter public void run() { putUsers(messagesRes.users, isCache); putChats(messagesRes.chats, isCache); - NotificationCenter.getInstance().postNotificationName(NotificationCenter.messagesDidLoaded, dialog_id, count, objects, isCache, first_unread, last_message_id, unread_count, last_date, load_type, messagesRes.collapsed, isEnd, classGuid, loadIndex); + int first_unread_final = Integer.MAX_VALUE; + if (queryFromServer && load_type == 2) { + for (int a = 0; a < messagesRes.messages.size(); a++) { + TLRPC.Message message = messagesRes.messages.get(a); + if (!message.out && message.id > first_unread && message.id < first_unread_final) { + first_unread_final = message.id; + } + } + } + if (first_unread_final == Integer.MAX_VALUE) { + first_unread_final = first_unread; + } + NotificationCenter.getInstance().postNotificationName(NotificationCenter.messagesDidLoaded, dialog_id, count, objects, isCache, first_unread_final, last_message_id, unread_count, last_date, load_type, messagesRes.collapsed, isEnd, classGuid, loadIndex); if (messagesToReload != null) { reloadMessages(messagesToReload, dialog_id); } @@ -3153,7 +3180,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter if (fragment != null) { AlertsCreator.showAddUserAlert(error.text, fragment, true); } else if (error.text.equals("PEER_FLOOD")) { - NotificationCenter.getInstance().postNotificationName(NotificationCenter.spamErrorReceived, 1); + NotificationCenter.getInstance().postNotificationName(NotificationCenter.needShowAlert, 1); } } }); @@ -3360,7 +3387,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter AlertsCreator.showAddUserAlert(error.text, fragment, isChannel && !isMegagroup); } else { if (error.text.equals("PEER_FLOOD")) { - NotificationCenter.getInstance().postNotificationName(NotificationCenter.spamErrorReceived, 1); + NotificationCenter.getInstance().postNotificationName(NotificationCenter.needShowAlert, 1); } } } @@ -3370,7 +3397,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter processUpdates((TLRPC.Updates) response, false); if (isChannel) { if (inputUser instanceof TLRPC.TL_inputUserSelf) { - generateJoinMessage(chat_id); + generateJoinMessage(chat_id, true); } AndroidUtilities.runOnUIThread(new Runnable() { @Override @@ -3450,7 +3477,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter AndroidUtilities.runOnUIThread(new Runnable() { @Override public void run() { - MessagesController.getInstance().deleteDialog(-chat_id, false); + MessagesController.getInstance().deleteDialog(-chat_id, 0); } }); } @@ -3663,16 +3690,16 @@ public class MessagesController implements NotificationCenter.NotificationCenter req.app_version = "App version unknown"; } - if (req.lang_code == null || req.lang_code.length() == 0) { + if (req.lang_code == null || req.lang_code.trim().length() == 0) { req.lang_code = "en"; } - if (req.device_model == null || req.device_model.length() == 0) { + if (req.device_model == null || req.device_model.trim().length() == 0) { req.device_model = "Android unknown"; } - if (req.app_version == null || req.app_version.length() == 0) { + if (req.app_version == null || req.app_version.trim().length() == 0) { req.app_version = "App version unknown"; } - if (req.system_version == null || req.system_version.length() == 0) { + if (req.system_version == null || req.system_version.trim().length() == 0) { req.system_version = "SDK Unknown"; } @@ -3926,7 +3953,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter } else { needShortPollChannels.put(channelId, 0); if (shortPollChannels.indexOfKey(channelId) < 0) { - getChannelDifference(channelId); + getChannelDifference(channelId, 2); } } } @@ -3934,17 +3961,26 @@ public class MessagesController implements NotificationCenter.NotificationCenter } public void getChannelDifference(final int channelId) { - getChannelDifference(channelId, false); + getChannelDifference(channelId, 0); } - public void getChannelDifference(final int channelId, final boolean newDialog) { + public void getChannelDifference(final int channelId, final int newDialogType) { Boolean gettingDifferenceChannel = gettingDifferenceChannels.get(channelId); if (gettingDifferenceChannel == null) { gettingDifferenceChannel = false; } + if (gettingDifferenceChannel) { + return; + } + int limit = 100; Integer channelPts; - if (newDialog) { + if (newDialogType == 1) { + channelPts = channelsPts.get(channelId); + if (channelPts != null) { + return; + } channelPts = 1; + limit = 1; } else { channelPts = channelsPts.get(channelId); if (channelPts == null) { @@ -3952,8 +3988,12 @@ public class MessagesController implements NotificationCenter.NotificationCenter if (channelPts != 0) { channelsPts.put(channelId, channelPts); } + if (channelPts == 0 && newDialogType == 2) { + channelPts = 1; + limit = 1; + } } - if (channelPts == 0 || gettingDifferenceChannel) { + if (channelPts == 0) { return; } } @@ -3962,7 +4002,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter req.channel = getInputChannel(channelId); req.filter = new TLRPC.TL_channelMessagesFilterEmpty(); req.pts = channelPts; - req.limit = newDialog ? 1 : 100; + req.limit = limit; FileLog.e("tmessages", "start getChannelDifference with pts = " + channelPts + " channelId = " + channelId); ConnectionsManager.getInstance().sendRequest(req, new RequestDelegate() { @Override @@ -4142,7 +4182,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter res.unread_important_count = Math.max(res.unread_count, res.unread_important_count); res.top_important_message = Math.max(res.top_important_message, res.top_message); } - MessagesStorage.getInstance().overwriteChannel(channelId, (TLRPC.TL_updates_channelDifferenceTooLong) res, newDialog); + MessagesStorage.getInstance().overwriteChannel(channelId, (TLRPC.TL_updates_channelDifferenceTooLong) res, newDialogType); } gettingDifferenceChannels.remove(channelId); channelsPts.put(channelId, res.pts); @@ -4401,9 +4441,9 @@ public class MessagesController implements NotificationCenter.NotificationCenter }); } - public void generateJoinMessage(final int chat_id) { + public void generateJoinMessage(final int chat_id, boolean ignoreLeft) { TLRPC.Chat chat = getChat(chat_id); - if (chat == null || !ChatObject.isChannel(chat_id) || chat.megagroup) { + if (chat == null || !ChatObject.isChannel(chat_id) || chat.megagroup || (chat.left || chat.kicked) && !ignoreLeft) { return; } @@ -5368,6 +5408,10 @@ public class MessagesController implements NotificationCenter.NotificationCenter } else if (update instanceof TLRPC.TL_updateNotifySettings) { updatesOnMainThread.add(update); } else if (update instanceof TLRPC.TL_updateServiceNotification) { + TLRPC.TL_updateServiceNotification notification = (TLRPC.TL_updateServiceNotification) update; + if (notification.popup && notification.message != null && notification.message.length() > 0) { + NotificationCenter.getInstance().postNotificationName(NotificationCenter.needShowAlert, 2, notification.message); + } TLRPC.TL_message newMessage = new TLRPC.TL_message(); newMessage.local_id = newMessage.id = UserConfig.getNewMessageId(); UserConfig.saveConfig(false); @@ -5380,7 +5424,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter newMessage.dialog_id = 777000; newMessage.media = update.media; newMessage.flags |= TLRPC.MESSAGE_FLAG_HAS_MEDIA; - newMessage.message = ((TLRPC.TL_updateServiceNotification) update).message; + newMessage.message = notification.message; messagesArr.add(newMessage); MessageObject obj = new MessageObject(newMessage, usersDict, chatsDict, true); @@ -5435,6 +5479,12 @@ public class MessagesController implements NotificationCenter.NotificationCenter MessagesStorage.getInstance().updateChatInfo(update.chat_id, update.user_id, 2, update.is_admin ? 1 : 0, update.version); } else if (update instanceof TLRPC.TL_updateChatAdmins) { updatesOnMainThread.add(update); + } else if (update instanceof TLRPC.TL_updateStickerSets) { + updatesOnMainThread.add(update); + } else if (update instanceof TLRPC.TL_updateStickerSetsOrder) { + updatesOnMainThread.add(update); + } else if (update instanceof TLRPC.TL_updateNewStickerSet) { + updatesOnMainThread.add(update); } } if (!messages.isEmpty()) { @@ -5492,7 +5542,8 @@ public class MessagesController implements NotificationCenter.NotificationCenter ArrayList dbUsers = new ArrayList<>(); ArrayList dbUsersStatus = new ArrayList<>(); SharedPreferences.Editor editor = null; - for (TLRPC.Update update : updatesOnMainThread) { + for (int a = 0; a < updatesOnMainThread.size(); a++) { + final TLRPC.Update update = updatesOnMainThread.get(a); final TLRPC.User toDbUser = new TLRPC.User(); toDbUser.id = update.user_id; final TLRPC.User currentUser = getUser(update.user_id); @@ -5602,14 +5653,25 @@ public class MessagesController implements NotificationCenter.NotificationCenter TLRPC.Dialog dialog = dialogs_dict.get(-(long) update.channel_id); TLRPC.Chat chat = getChat(update.channel_id); if (dialog == null && chat instanceof TLRPC.TL_channel && !chat.left) { - getChannelDifference(update.channel_id, true); + Utilities.stageQueue.postRunnable(new Runnable() { + @Override + public void run() { + getChannelDifference(update.channel_id, 1); + } + }); } else if (chat.left && dialog != null) { - deleteDialog(dialog.id, false); + deleteDialog(dialog.id, 0); } updateMask |= UPDATE_MASK_CHANNEL; loadFullChat(update.channel_id, 0, true); } else if (update instanceof TLRPC.TL_updateChatAdmins) { updateMask |= UPDATE_MASK_CHAT_ADMINS; + } else if (update instanceof TLRPC.TL_updateStickerSets) { + StickersQuery.loadStickers(false, true); + } else if (update instanceof TLRPC.TL_updateStickerSetsOrder) { + StickersQuery.reorderStickers(update.order); + } else if (update instanceof TLRPC.TL_updateNewStickerSet) { + StickersQuery.addNewStickerSet(update.stickerset); } } if (editor != null) { @@ -5747,7 +5809,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter MessagesStorage.getInstance().putWebPages(webPages); } if (markAsReadMessagesInbox.size() != 0 || markAsReadMessagesOutbox.size() != 0 || !markAsReadEncrypted.isEmpty()) { - if (markAsReadMessagesInbox.size() != 0 || markAsReadMessagesOutbox.size() != 0) { + if (markAsReadMessagesInbox.size() != 0) { MessagesStorage.getInstance().updateDialogsWithReadMessages(markAsReadMessagesInbox, true); } MessagesStorage.getInstance().markMessagesAsRead(markAsReadMessagesInbox, markAsReadMessagesOutbox, markAsReadEncrypted, true); diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/MessagesStorage.java b/TMessagesProj/src/main/java/org/telegram/messenger/MessagesStorage.java index 9a2b377f5..560328f2c 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/MessagesStorage.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/MessagesStorage.java @@ -689,7 +689,7 @@ public class MessagesStorage { TLRPC.Chat chat = chats.get(a); if (chat != null && (chat.left || chat.migrated_to != null)) { long did = -chat.id; - database.executeFast("UPDATE dialogs SET unread_count = 0 WHERE did = " + did).stepThis().dispose(); + database.executeFast("UPDATE dialogs SET unread_count = 0, unread_count_i = 0 WHERE did = " + did).stepThis().dispose(); database.executeFast(String.format(Locale.US, "UPDATE messages SET read_state = 3 WHERE uid = %d AND mid > 0 AND read_state IN(0,2) AND out = 0", did)).stepThis().dispose(); chats.remove(a); a--; @@ -965,31 +965,12 @@ public class MessagesStorage { }); } - public void deleteDialog(final long did, final boolean messagesOnly) { + public void deleteDialog(final long did, final int messagesOnly) { storageQueue.postRunnable(new Runnable() { @Override public void run() { try { - if (!messagesOnly) { - database.executeFast("DELETE FROM dialogs WHERE did = " + did).stepThis().dispose(); - database.executeFast("DELETE FROM chat_settings_v2 WHERE uid = " + did).stepThis().dispose(); - database.executeFast("DELETE FROM channel_users_v2 WHERE did = " + did).stepThis().dispose(); - database.executeFast("DELETE FROM search_recent WHERE did = " + did).stepThis().dispose(); - int lower_id = (int)did; - int high_id = (int)(did >> 32); - if (lower_id != 0) { - if (high_id == 1) { - database.executeFast("DELETE FROM chats WHERE uid = " + lower_id).stepThis().dispose(); - } else if (lower_id < 0) { - //database.executeFast("DELETE FROM chats WHERE uid = " + (-lower_id)).stepThis().dispose(); - } - } else { - database.executeFast("DELETE FROM enc_chats WHERE uid = " + high_id).stepThis().dispose(); - //database.executeFast("DELETE FROM secret_holes WHERE uid = " + high_id).stepThis().dispose(); - } - } - - if ((int) did == 0) { + if ((int) did == 0 || messagesOnly == 2) { SQLiteCursor cursor = database.queryFinalized("SELECT data FROM messages WHERE uid = " + did); ArrayList filesToDelete = new ArrayList<>(); try { @@ -1038,11 +1019,77 @@ public class MessagesStorage { FileLog.e("tmessages", e); } cursor.dispose(); - FileLoader.getInstance().deleteFiles(filesToDelete); + FileLoader.getInstance().deleteFiles(filesToDelete, messagesOnly); } - database.executeFast("UPDATE dialogs SET unread_count = 0 WHERE did = " + did).stepThis().dispose(); + if (messagesOnly == 0) { + database.executeFast("DELETE FROM dialogs WHERE did = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM chat_settings_v2 WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM channel_users_v2 WHERE did = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM search_recent WHERE did = " + did).stepThis().dispose(); + int lower_id = (int)did; + int high_id = (int)(did >> 32); + if (lower_id != 0) { + if (high_id == 1) { + database.executeFast("DELETE FROM chats WHERE uid = " + lower_id).stepThis().dispose(); + } else if (lower_id < 0) { + //database.executeFast("DELETE FROM chats WHERE uid = " + (-lower_id)).stepThis().dispose(); + } + } else { + database.executeFast("DELETE FROM enc_chats WHERE uid = " + high_id).stepThis().dispose(); + //database.executeFast("DELETE FROM secret_holes WHERE uid = " + high_id).stepThis().dispose(); + } + } else if (messagesOnly == 2) { + SQLiteCursor cursor = database.queryFinalized("SELECT last_mid_i, last_mid FROM dialogs WHERE did = " + did); + ArrayList arrayList = new ArrayList<>(); + if (cursor.next()) { + long last_mid_i = cursor.longValue(0); + long last_mid = cursor.longValue(1); + SQLiteCursor cursor2 = database.queryFinalized("SELECT data FROM messages WHERE uid = " + did + " AND mid IN (" + last_mid_i + "," + last_mid + ")"); + try { + while (cursor2.next()) { + NativeByteBuffer data = new NativeByteBuffer(cursor2.byteArrayLength(0)); + if (data != null && cursor2.byteBufferValue(0, data) != 0) { + TLRPC.Message message = TLRPC.Message.TLdeserialize(data, data.readInt32(false), false); + if (message == null) { + continue; + } + arrayList.add(message); + } + data.reuse(); + } + } catch (Exception e) { + FileLog.e("tmessages", e); + } + cursor2.dispose(); + + database.executeFast("DELETE FROM messages WHERE uid = " + did + " AND mid != " + last_mid_i + " AND mid != " + last_mid).stepThis().dispose(); + database.executeFast("DELETE FROM channel_group WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM messages_holes WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM messages_imp_holes WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM bot_keyboard WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM media_counts_v2 WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM media_v2 WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM media_holes_v2 WHERE uid = " + did).stepThis().dispose(); + BotQuery.clearBotKeyboard(did, null); + + SQLitePreparedStatement state5 = database.executeFast("REPLACE INTO messages_holes VALUES(?, ?, ?)"); + SQLitePreparedStatement state6 = database.executeFast("REPLACE INTO media_holes_v2 VALUES(?, ?, ?, ?)"); + SQLitePreparedStatement state7 = database.executeFast("REPLACE INTO messages_imp_holes VALUES(?, ?, ?)"); + SQLitePreparedStatement state8 = database.executeFast("REPLACE INTO channel_group VALUES(?, ?, ?, ?)"); + createFirstHoles(did, state5, state6, state7, state8, arrayList); + state5.dispose(); + state6.dispose(); + state7.dispose(); + state8.dispose(); + } + cursor.dispose(); + return; + } + + database.executeFast("UPDATE dialogs SET unread_count = 0, unread_count_i = 0 WHERE did = " + did).stepThis().dispose(); database.executeFast("DELETE FROM messages WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM channel_group WHERE uid = " + did).stepThis().dispose(); database.executeFast("DELETE FROM bot_keyboard WHERE uid = " + did).stepThis().dispose(); database.executeFast("DELETE FROM media_counts_v2 WHERE uid = " + did).stepThis().dispose(); database.executeFast("DELETE FROM media_v2 WHERE uid = " + did).stepThis().dispose(); @@ -1249,7 +1296,6 @@ public class MessagesStorage { private void updateDialogsWithReadMessagesInternal(final ArrayList messages, final SparseArray inbox) { try { HashMap dialogsToUpdate = new HashMap<>(); - StringBuilder dialogsToReload = new StringBuilder(); if (messages != null && !messages.isEmpty()) { String ids = TextUtils.join(",", messages); @@ -1267,10 +1313,6 @@ public class MessagesStorage { Integer currentCount = dialogsToUpdate.get(uid); if (currentCount == null) { dialogsToUpdate.put(uid, 1); - if (dialogsToReload.length() != 0) { - dialogsToReload.append(","); - } - dialogsToReload.append(uid); } else { dialogsToUpdate.put(uid, currentCount + 1); } @@ -1280,35 +1322,24 @@ public class MessagesStorage { for (int b = 0; b < inbox.size(); b++) { int key = inbox.keyAt(b); long messageId = inbox.get(key); - SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT COUNT(mid) FROM messages WHERE uid = %d AND mid <= %d AND read_state IN(0,2) AND out = 0", key, messageId)); + SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT COUNT(mid) FROM messages WHERE uid = %d AND mid > %d AND read_state IN(0,2) AND out = 0", key, messageId)); if (cursor.next()) { int count = cursor.intValue(0); - if (count != 0) { - dialogsToUpdate.put((long) key, count); - if (dialogsToReload.length() != 0) { - dialogsToReload.append(","); - } - dialogsToReload.append(key); - } + dialogsToUpdate.put((long) key, count); } cursor.dispose(); + + SQLitePreparedStatement state = database.executeFast("UPDATE dialogs SET inbox_max = max((SELECT inbox_max FROM dialogs WHERE did = ?), ?) WHERE did = ?"); + state.requery(); + state.bindLong(1, key); + state.bindInteger(2, (int) messageId); + state.bindLong(3, key); + state.step(); + state.dispose(); } } - if (dialogsToReload.length() > 0) { - SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT did, unread_count FROM dialogs WHERE did IN(%s)", dialogsToReload.toString())); - while (cursor.next()) { - long did = cursor.longValue(0); - int count = cursor.intValue(1); - Integer currentCount = dialogsToUpdate.get(did); - if (currentCount != null) { - dialogsToUpdate.put(did, Math.max(0, count - currentCount)); - } else { - dialogsToUpdate.remove(did); - } - } - cursor.dispose(); - + if (!dialogsToUpdate.isEmpty()) { database.beginTransaction(); SQLitePreparedStatement state = database.executeFast("UPDATE dialogs SET unread_count = ? WHERE did = ?"); for (HashMap.Entry entry : dialogsToUpdate.entrySet()) { @@ -1721,11 +1752,18 @@ public class MessagesStorage { state.dispose(); } - state = database.executeFast("UPDATE dialogs SET unread_count = 0, inbox_max = max((SELECT inbox_max FROM dialogs WHERE did = ?), ?) WHERE did = ?"); + int currentMaxId = 0; + SQLiteCursor cursor = database.queryFinalized("SELECT inbox_max FROM dialogs WHERE did = " + dialog_id); + if (cursor.next()) { + currentMaxId = cursor.intValue(0); + } + cursor.dispose(); + currentMaxId = Math.max(currentMaxId, (int) max_id); + + state = database.executeFast("UPDATE dialogs SET unread_count = 0, unread_count_i = 0, inbox_max = ? WHERE did = ?"); state.requery(); - state.bindLong(1, dialog_id); - state.bindInteger(2, (int) max_id); - state.bindLong(3, dialog_id); + state.bindInteger(1, currentMaxId); + state.bindLong(2, dialog_id); state.step(); state.dispose(); @@ -2041,8 +2079,10 @@ public class MessagesStorage { int offset_query = 0; int min_unread_id = 0; int last_message_id = 0; + boolean queryFromServer = false; int max_unread_date = 0; long messageMaxId = max_id; + int max_id_query = max_id; int channelId = 0; if (important != 0) { channelId = -(int) dialog_id; @@ -2058,11 +2098,56 @@ public class MessagesStorage { HashMap> replyMessageOwners = new HashMap<>(); SQLiteCursor cursor; - int lower_id = (int)dialog_id; + int lower_id = (int) dialog_id; if (lower_id != 0) { String imp = important == 2 ? " AND imp = 1 " : ""; String holesTable = important == 2 ? "messages_imp_holes" : "messages_holes"; + if (load_type != 1 && load_type != 3 && minDate == 0) { + if (load_type == 2) { + cursor = database.queryFinalized("SELECT inbox_max, unread_count, date FROM dialogs WHERE did = " + dialog_id); + if (cursor.next()) { + messageMaxId = max_id_query = min_unread_id = cursor.intValue(0); + count_unread = cursor.intValue(1); + max_unread_date = cursor.intValue(2); + queryFromServer = true; + if (messageMaxId != 0 && channelId != 0) { + messageMaxId |= ((long) channelId) << 32; + } + } + cursor.dispose(); + if (!queryFromServer) { + cursor = database.queryFinalized(String.format(Locale.US, "SELECT min(mid), max(date) FROM messages WHERE uid = %d AND out = 0 AND read_state IN(0,2) AND mid > 0" + imp, dialog_id)); + if (cursor.next()) { + min_unread_id = cursor.intValue(0); + max_unread_date = cursor.intValue(1); + } + cursor.dispose(); + if (min_unread_id != 0) { + cursor = database.queryFinalized(String.format(Locale.US, "SELECT COUNT(*) FROM messages WHERE uid = %d AND mid >= %d " + imp + "AND out = 0 AND read_state IN(0,2)", dialog_id, min_unread_id)); + if (cursor.next()) { + count_unread = cursor.intValue(0); + } + cursor.dispose(); + } + } + } + + if (count_query > count_unread || count_unread < 4) { + count_query = Math.max(count_query, count_unread + 10); + if (count_unread < 4) { + count_unread = 0; + min_unread_id = 0; + messageMaxId = 0; + last_message_id = 0; + queryFromServer = false; + } + } else { + offset_query = count_unread - count_query; + count_query += 10; + } + } + cursor = database.queryFinalized(String.format(Locale.US, "SELECT start FROM " + holesTable + " WHERE uid = %d AND start IN (0, 1)", dialog_id)); if (cursor.next()) { isEnd = cursor.intValue(0) == 1; @@ -2085,24 +2170,24 @@ public class MessagesStorage { cursor.dispose(); } - if (load_type == 3) { + if (load_type == 3 || queryFromServer && load_type == 2) { cursor = database.queryFinalized(String.format(Locale.US, "SELECT max(mid) FROM messages WHERE uid = %d AND mid > 0", dialog_id)); if (cursor.next()) { last_message_id = cursor.intValue(0); } cursor.dispose(); - boolean containMessage = false; - cursor = database.queryFinalized(String.format(Locale.US, "SELECT mid FROM messages WHERE mid = %d", messageMaxId)); + boolean containMessage = true; + cursor = database.queryFinalized(String.format(Locale.US, "SELECT start FROM " + holesTable + " WHERE uid = %d AND start < %d AND end > %d", dialog_id, max_id_query, max_id_query)); if (cursor.next()) { - containMessage = true; + containMessage = false; } cursor.dispose(); if (containMessage) { long holeMessageMaxId = 0; long holeMessageMinId = 1; - cursor = database.queryFinalized(String.format(Locale.US, "SELECT start FROM " + holesTable + " WHERE uid = %d AND start >= %d ORDER BY start ASC LIMIT 1", dialog_id, max_id)); + cursor = database.queryFinalized(String.format(Locale.US, "SELECT start FROM " + holesTable + " WHERE uid = %d AND start >= %d ORDER BY start ASC LIMIT 1", dialog_id, max_id_query)); if (cursor.next()) { holeMessageMaxId = cursor.intValue(0); if (channelId != 0) { @@ -2110,7 +2195,7 @@ public class MessagesStorage { } } cursor.dispose(); - cursor = database.queryFinalized(String.format(Locale.US, "SELECT end FROM " + holesTable + " WHERE uid = %d AND end <= %d ORDER BY end DESC LIMIT 1", dialog_id, max_id)); + cursor = database.queryFinalized(String.format(Locale.US, "SELECT end FROM " + holesTable + " WHERE uid = %d AND end <= %d ORDER BY end DESC LIMIT 1", dialog_id, max_id_query)); if (cursor.next()) { holeMessageMinId = cursor.intValue(0); if (channelId != 0) { @@ -2173,39 +2258,11 @@ public class MessagesStorage { cursor = database.queryFinalized(String.format(Locale.US, "SELECT m.read_state, m.data, m.send_state, m.mid, m.date, r.random_id, m.replydata, m.media FROM messages as m LEFT JOIN randoms as r ON r.mid = m.mid WHERE m.uid = %d AND m.date <= %d " + imp + "ORDER BY m.date DESC, m.mid DESC LIMIT %d,%d", dialog_id, minDate, offset_query, count_query)); } } else { - if (load_type == 2) { - cursor = database.queryFinalized(String.format(Locale.US, "SELECT max(mid) FROM messages WHERE uid = %d AND mid > 0", dialog_id)); - if (cursor.next()) { - last_message_id = cursor.intValue(0); - } - cursor.dispose(); - - cursor = database.queryFinalized(String.format(Locale.US, "SELECT min(mid), max(date) FROM messages WHERE uid = %d AND out = 0 AND read_state IN(0,2) AND mid > 0" + imp, dialog_id)); - if (cursor.next()) { - min_unread_id = cursor.intValue(0); - max_unread_date = cursor.intValue(1); - } - cursor.dispose(); - if (min_unread_id != 0) { - cursor = database.queryFinalized(String.format(Locale.US, "SELECT COUNT(*) FROM messages WHERE uid = %d AND mid >= %d " + imp + "AND out = 0 AND read_state IN(0,2)", dialog_id, min_unread_id)); - if (cursor.next()) { - count_unread = cursor.intValue(0); - } - cursor.dispose(); - } - } - - if (count_query > count_unread || count_unread < 4) { - count_query = Math.max(count_query, count_unread + 10); - if (count_unread < 4) { - count_unread = 0; - min_unread_id = 0; - last_message_id = 0; - } - } else { - offset_query = count_unread - count_query; - count_query += 10; + cursor = database.queryFinalized(String.format(Locale.US, "SELECT max(mid) FROM messages WHERE uid = %d AND mid > 0", dialog_id)); + if (cursor.next()) { + last_message_id = cursor.intValue(0); } + cursor.dispose(); long holeMessageId = 0; cursor = database.queryFinalized(String.format(Locale.US, "SELECT max(end) FROM " + holesTable + " WHERE uid = %d", dialog_id)); @@ -2338,10 +2395,6 @@ public class MessagesStorage { cursor.dispose(); } - if (load_type == 3 && res.messages.size() == 1) { - res.messages.clear(); - } - Collections.sort(res.messages, new Comparator() { @Override public int compare(TLRPC.Message lhs, TLRPC.Message rhs) { @@ -2368,6 +2421,20 @@ public class MessagesStorage { } }); + if ((load_type == 3 || load_type == 2 && queryFromServer) && !res.messages.isEmpty()) { + int minId = res.messages.get(res.messages.size() - 1).id; + int maxId = res.messages.get(0).id; + if (!(minId <= max_id_query && maxId >= max_id_query)) { + replyMessages.clear(); + usersToLoad.clear(); + chatsToLoad.clear(); + res.messages.clear(); + } + } + if (load_type == 3 && res.messages.size() == 1) { + res.messages.clear(); + } + if (important == 2 && !res.messages.isEmpty()) { if (max_id != 0) { cursor = database.queryFinalized(String.format(Locale.US, "SELECT start, end, count FROM channel_group WHERE uid = %d AND ((start >= %d AND end <= %d) OR (start = %d))", dialog_id, res.messages.get(res.messages.size() - 1).id, res.messages.get(0).id, res.messages.get(0).id)); @@ -2421,7 +2488,7 @@ public class MessagesStorage { res.collapsed.clear(); FileLog.e("tmessages", e); } finally { - MessagesController.getInstance().processLoadedMessages(res, dialog_id, count_query, max_id, true, classGuid, min_unread_id, last_message_id, count_unread, max_unread_date, load_type, important, isEnd, loadIndex); + MessagesController.getInstance().processLoadedMessages(res, dialog_id, count_query, max_id, true, classGuid, min_unread_id, last_message_id, count_unread, max_unread_date, load_type, important, isEnd, loadIndex, queryFromServer); } } }); @@ -3174,14 +3241,14 @@ public class MessagesStorage { }); } - public void overwriteChannel(final int channel_id, final TLRPC.TL_updates_channelDifferenceTooLong difference, final boolean newDialog) { + public void overwriteChannel(final int channel_id, final TLRPC.TL_updates_channelDifferenceTooLong difference, final int newDialogType) { storageQueue.postRunnable(new Runnable() { @Override public void run() { try { boolean checkInvite = false; final long did = -channel_id; - if (newDialog) { + if (newDialogType != 0) { SQLiteCursor cursor = database.queryFinalized("SELECT pts FROM dialogs WHERE did = " + did); if (!cursor.next()) { checkInvite = true; @@ -3190,6 +3257,7 @@ public class MessagesStorage { } database.executeFast("DELETE FROM messages WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM channel_group WHERE uid = " + did).stepThis().dispose(); database.executeFast("DELETE FROM bot_keyboard WHERE uid = " + did).stepThis().dispose(); database.executeFast("DELETE FROM media_counts_v2 WHERE uid = " + did).stepThis().dispose(); database.executeFast("DELETE FROM media_v2 WHERE uid = " + did).stepThis().dispose(); @@ -3224,7 +3292,11 @@ public class MessagesStorage { } }); if (checkInvite) { - MessagesController.getInstance().checkChannelInviter(channel_id); + if (newDialogType == 1) { + MessagesController.getInstance().checkChannelInviter(channel_id); + } else { + MessagesController.getInstance().generateJoinMessage(channel_id, false); + } } } catch (Exception e) { FileLog.e("tmessages", e); @@ -3281,6 +3353,7 @@ public class MessagesStorage { StringBuilder messageMediaIds = null; HashMap mediaTypes = null; StringBuilder messageIds = new StringBuilder(); + HashMap dialogsReadMax = new HashMap<>(); HashMap messagesIdsMap = new HashMap<>(); HashMap messagesIdsMapNotImportant = new HashMap<>(); @@ -3308,15 +3381,27 @@ public class MessagesStorage { } if ((message.to_id.channel_id == 0 && MessageObject.isUnread(message) || MessageObject.isContentUnread(message)) && !MessageObject.isOut(message)) { - if (messageIds.length() > 0) { - messageIds.append(","); + Integer currentMaxId = dialogsReadMax.get(message.dialog_id); + if (currentMaxId == null) { + SQLiteCursor cursor = database.queryFinalized("SELECT inbox_max FROM dialogs WHERE did = " + message.dialog_id); + if (cursor.next()) { + currentMaxId = cursor.intValue(0); + } else { + currentMaxId = 0; + } + cursor.dispose(); + dialogsReadMax.put(message.dialog_id, currentMaxId); } - - messageIds.append(messageId); - if (message.to_id.channel_id == 0 || MessageObject.isMegagroup(message) || MessageObject.isImportant(message)) { - messagesIdsMap.put(messageId, message.dialog_id); - } else if (message.to_id.channel_id != 0) { - messagesIdsMapNotImportant.put(messageId, message.dialog_id); + if (message.id < 0 || currentMaxId < message.id) { + if (messageIds.length() > 0) { + messageIds.append(","); + } + messageIds.append(messageId); + if (message.to_id.channel_id == 0 || MessageObject.isMegagroup(message) || MessageObject.isImportant(message)) { + messagesIdsMap.put(messageId, message.dialog_id); + } else if (message.to_id.channel_id != 0) { + messagesIdsMapNotImportant.put(messageId, message.dialog_id); + } } } if (SharedMediaQuery.canAddMessageToMedia(message)) { @@ -4005,14 +4090,6 @@ public class MessagesStorage { int key = inbox.keyAt(b); long messageId = inbox.get(key); database.executeFast(String.format(Locale.US, "UPDATE messages SET read_state = read_state | 1 WHERE uid = %d AND mid > 0 AND mid <= %d AND read_state IN(0,2) AND out = 0", key, messageId)).stepThis().dispose(); - - SQLitePreparedStatement state = database.executeFast("UPDATE dialogs SET inbox_max = max((SELECT inbox_max FROM dialogs WHERE did = ?), ?) WHERE did = ?"); - state.requery(); - state.bindLong(1, key); - state.bindInteger(2, (int) messageId); - state.bindLong(3, key); - state.step(); - state.dispose(); } } if (outbox != null) { @@ -4174,7 +4251,7 @@ public class MessagesStorage { FileLog.e("tmessages", e); } cursor.dispose(); - FileLoader.getInstance().deleteFiles(filesToDelete); + FileLoader.getInstance().deleteFiles(filesToDelete, 0); if (channelId != 0 && unread_count != 0) { long did = -channelId; @@ -4217,7 +4294,7 @@ public class MessagesStorage { dialogsToUpdate.add(cursor.longValue(0)); } cursor.dispose(); - state = database.executeFast("UPDATE dialogs SET unread_count = 0, last_mid = (SELECT mid FROM messages WHERE uid = ? AND date = (SELECT MAX(date) FROM messages WHERE uid = ? AND date != 0)) WHERE did = ?"); + state = database.executeFast("UPDATE dialogs SET unread_count = 0, unread_count_i = 0, last_mid = (SELECT mid FROM messages WHERE uid = ? AND date = (SELECT MAX(date) FROM messages WHERE uid = ? AND date != 0)) WHERE did = ?"); } database.beginTransaction(); for (int a = 0; a < dialogsToUpdate.size(); a++) { @@ -4980,6 +5057,94 @@ public class MessagesStorage { }); } + public static void createFirstHoles(long did, SQLitePreparedStatement state5, SQLitePreparedStatement state6, SQLitePreparedStatement state7, SQLitePreparedStatement state8, ArrayList arrayList) throws Exception { + int impMessageId = 0; + int notImpMessageId = 0; + for (int a = 0; a < arrayList.size(); a++) { + TLRPC.Message message = arrayList.get(a); + + if (MessageObject.isImportant(message)) { + state7.requery(); + state7.bindLong(1, did); + state7.bindInteger(2, message.id == 1 ? 1 : 0); + state7.bindInteger(3, message.id); + state7.step(); + impMessageId = Math.max(message.id, impMessageId); + } else { + notImpMessageId = Math.max(message.id, notImpMessageId); + } + } + + if (impMessageId != 0 && notImpMessageId == 0) { + notImpMessageId = impMessageId; + impMessageId = 0; + } + + if (arrayList.size() == 1) { + int messageId = arrayList.get(0).id; + + state5.requery(); + state5.bindLong(1, did); + state5.bindInteger(2, messageId == 1 ? 1 : 0); + state5.bindInteger(3, messageId); + state5.step(); + + for (int b = 0; b < SharedMediaQuery.MEDIA_TYPES_COUNT; b++) { + state6.requery(); + state6.bindLong(1, did); + state6.bindInteger(2, b); + state6.bindInteger(3, messageId == 1 ? 1 : 0); + state6.bindInteger(4, messageId); + state6.step(); + } + } else if (arrayList.size() == 2) { + int firstId = arrayList.get(0).id; + int lastId = arrayList.get(1).id; + if (firstId > lastId) { + int temp = firstId; + firstId = lastId; + lastId = temp; + } + + state5.requery(); + state5.bindLong(1, did); + state5.bindInteger(2, firstId == 1 ? 1 : 0); + state5.bindInteger(3, firstId); + state5.step(); + + state5.requery(); + state5.bindLong(1, did); + state5.bindInteger(2, firstId); + state5.bindInteger(3, lastId); + state5.step(); + + for (int b = 0; b < SharedMediaQuery.MEDIA_TYPES_COUNT; b++) { + state6.requery(); + state6.bindLong(1, did); + state6.bindInteger(2, b); + state6.bindInteger(3, firstId == 1 ? 1 : 0); + state6.bindInteger(4, firstId); + state6.step(); + + state6.requery(); + state6.bindLong(1, did); + state6.bindInteger(2, b); + state6.bindInteger(3, firstId); + state6.bindInteger(4, lastId); + state6.step(); + } + + if (impMessageId != 0 && impMessageId < notImpMessageId) { + state8.requery(); + state8.bindLong(1, did); + state8.bindInteger(2, impMessageId); + state8.bindInteger(3, Integer.MAX_VALUE); + state8.bindInteger(4, notImpMessageId - impMessageId); + state8.step(); + } + } + } + private void putDialogsInternal(final TLRPC.messages_Dialogs dialogs) { try { database.beginTransaction(); @@ -5002,7 +5167,7 @@ public class MessagesStorage { SQLitePreparedStatement state5 = database.executeFast("REPLACE INTO messages_holes VALUES(?, ?, ?)"); SQLitePreparedStatement state6 = database.executeFast("REPLACE INTO media_holes_v2 VALUES(?, ?, ?, ?)"); SQLitePreparedStatement state7 = database.executeFast("REPLACE INTO messages_imp_holes VALUES(?, ?, ?)"); - SQLitePreparedStatement state8 = null; + SQLitePreparedStatement state8 = database.executeFast("REPLACE INTO channel_group VALUES(?, ?, ?, ?)"); for (int a = 0; a < dialogs.dialogs.size(); a++) { TLRPC.Dialog dialog = dialogs.dialogs.get(a); @@ -5018,8 +5183,7 @@ public class MessagesStorage { } int messageDate = 0; int messageDateI = 0; - int impMessageId = 0; - int notImpMessageId = 0; + boolean isMegagroup = false; ArrayList arrayList = new_dialogMessage.get(dialog.id); if (arrayList != null) { @@ -5062,17 +5226,6 @@ public class MessagesStorage { state.bindInteger(10, MessageObject.isImportant(message) ? 1 : 0); state.step(); - if (MessageObject.isImportant(message)) { - state7.requery(); - state7.bindLong(1, dialog.id); - state7.bindInteger(2, message.id == 1 ? 1 : 0); - state7.bindInteger(3, message.id); - state7.step(); - impMessageId = Math.max(message.id, impMessageId); - } else { - notImpMessageId = Math.max(message.id, notImpMessageId); - } - if (SharedMediaQuery.canAddMessageToMedia(message)) { state3.requery(); state3.bindLong(1, messageId); @@ -5084,77 +5237,8 @@ public class MessagesStorage { } data.reuse(); } - if (impMessageId != 0 && notImpMessageId == 0) { - notImpMessageId = impMessageId; - impMessageId = 0; - } - if (arrayList.size() == 1) { - int messageId = arrayList.get(0).id; - - state5.requery(); - state5.bindLong(1, dialog.id); - state5.bindInteger(2, messageId == 1 ? 1 : 0); - state5.bindInteger(3, messageId); - state5.step(); - - for (int b = 0; b < SharedMediaQuery.MEDIA_TYPES_COUNT; b++) { - state6.requery(); - state6.bindLong(1, dialog.id); - state6.bindInteger(2, b); - state6.bindInteger(3, messageId == 1 ? 1 : 0); - state6.bindInteger(4, messageId); - state6.step(); - } - } else if (arrayList.size() == 2) { - int firstId = arrayList.get(0).id; - int lastId = arrayList.get(1).id; - if (firstId > lastId) { - int temp = firstId; - firstId = lastId; - lastId = temp; - } - - state5.requery(); - state5.bindLong(1, dialog.id); - state5.bindInteger(2, firstId == 1 ? 1 : 0); - state5.bindInteger(3, firstId); - state5.step(); - - state5.requery(); - state5.bindLong(1, dialog.id); - state5.bindInteger(2, firstId); - state5.bindInteger(3, lastId); - state5.step(); - - for (int b = 0; b < SharedMediaQuery.MEDIA_TYPES_COUNT; b++) { - state6.requery(); - state6.bindLong(1, dialog.id); - state6.bindInteger(2, b); - state6.bindInteger(3, firstId == 1 ? 1 : 0); - state6.bindInteger(4, firstId); - state6.step(); - - state6.requery(); - state6.bindLong(1, dialog.id); - state6.bindInteger(2, b); - state6.bindInteger(3, firstId); - state6.bindInteger(4, lastId); - state6.step(); - } - - if (impMessageId != 0 && impMessageId < notImpMessageId) { - if (state8 == null) { - state8 = database.executeFast("REPLACE INTO channel_group VALUES(?, ?, ?, ?)"); - } - state8.requery(); - state8.bindLong(1, dialog.id); - state8.bindInteger(2, impMessageId); - state8.bindInteger(3, Integer.MAX_VALUE); - state8.bindInteger(4, notImpMessageId - impMessageId); - state8.step(); - } - } + createFirstHoles(dialog.id, state5, state6, state7, state8, arrayList); } long topMessage = dialog.top_message; @@ -5195,9 +5279,7 @@ public class MessagesStorage { state5.dispose(); state6.dispose(); state7.dispose(); - if (state8 != null) { - state8.dispose(); - } + state8.dispose(); } putUsersInternal(dialogs.users); diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/NotificationCenter.java b/TMessagesProj/src/main/java/org/telegram/messenger/NotificationCenter.java index c78f8fa5a..72694ab58 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/NotificationCenter.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/NotificationCenter.java @@ -63,7 +63,7 @@ public class NotificationCenter { public static final int botKeyboardDidLoaded = totalEvents++; public static final int chatSearchResultsAvailable = totalEvents++; public static final int musicDidLoaded = totalEvents++; - public static final int spamErrorReceived = totalEvents++; + public static final int needShowAlert = totalEvents++; public static final int didUpdatedMessagesViews = totalEvents++; public static final int needReloadRecentDialogsSearch = totalEvents++; diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/SecretChatHelper.java b/TMessagesProj/src/main/java/org/telegram/messenger/SecretChatHelper.java index 3ecb16d84..da18258e6 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/SecretChatHelper.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/SecretChatHelper.java @@ -1078,7 +1078,7 @@ public class SecretChatHelper { }); } }); - MessagesStorage.getInstance().deleteDialog(did, true); + MessagesStorage.getInstance().deleteDialog(did, 1); NotificationCenter.getInstance().postNotificationName(NotificationCenter.dialogsNeedReload); NotificationCenter.getInstance().postNotificationName(NotificationCenter.removeAllMessagesFromDialog, did, false); } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/SendMessagesHelper.java b/TMessagesProj/src/main/java/org/telegram/messenger/SendMessagesHelper.java index 3f8d6f541..5d541918e 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/SendMessagesHelper.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/SendMessagesHelper.java @@ -722,7 +722,7 @@ public class SendMessagesHelper implements NotificationCenter.NotificationCenter @Override public void run() { if (error.text.equals("PEER_FLOOD")) { - NotificationCenter.getInstance().postNotificationName(NotificationCenter.spamErrorReceived, 0); + NotificationCenter.getInstance().postNotificationName(NotificationCenter.needShowAlert, 0); } } }); @@ -1700,7 +1700,7 @@ public class SendMessagesHelper implements NotificationCenter.NotificationCenter @Override public void run() { if (error.text.equals("PEER_FLOOD")) { - NotificationCenter.getInstance().postNotificationName(NotificationCenter.spamErrorReceived, 0); + NotificationCenter.getInstance().postNotificationName(NotificationCenter.needShowAlert, 0); } } }); @@ -1812,7 +1812,7 @@ public class SendMessagesHelper implements NotificationCenter.NotificationCenter TLRPC.PhotoSize size2 = newMsg.media.document.thumb; TLRPC.PhotoSize size = sentMessage.media.document.thumb; - if (size2.location != null && size2.location.volume_id == Integer.MIN_VALUE && size.location != null && !(size instanceof TLRPC.TL_photoSizeEmpty) && !(size2 instanceof TLRPC.TL_photoSizeEmpty)) { + if (size2 != null && size2.location != null && size2.location.volume_id == Integer.MIN_VALUE && size != null && size.location != null && !(size instanceof TLRPC.TL_photoSizeEmpty) && !(size2 instanceof TLRPC.TL_photoSizeEmpty)) { String fileName = size2.location.volume_id + "_" + size2.location.local_id; String fileName2 = size.location.volume_id + "_" + size.location.local_id; if (!fileName.equals(fileName2)) { @@ -1822,7 +1822,7 @@ public class SendMessagesHelper implements NotificationCenter.NotificationCenter ImageLoader.getInstance().replaceImageInCache(fileName, fileName2, size.location); size2.location = size.location; } - } else if (MessageObject.isStickerMessage(sentMessage) && size2.location != null) { + } else if (MessageObject.isStickerMessage(sentMessage) && size2 != null && size2.location != null) { size.location = size2.location; } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/TgChooserTargetService.java b/TMessagesProj/src/main/java/org/telegram/messenger/TgChooserTargetService.java index 7ff78713c..fea43faaa 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/TgChooserTargetService.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/TgChooserTargetService.java @@ -100,7 +100,6 @@ public class TgChooserTargetService extends ChooserTargetService { FileLog.e("tmessages", e); } for (int a = 0; a < dialogs.size(); a++) { - float score = (a + 1) / 20.0f; Bundle extras = new Bundle(); Icon icon = null; String name = null; @@ -138,7 +137,7 @@ public class TgChooserTargetService extends ChooserTargetService { if (icon == null) { icon = Icon.createWithResource(ApplicationLoader.applicationContext, R.drawable.logo_avatar); } - targets.add(new ChooserTarget(name, icon, score, componentName, extras)); + targets.add(new ChooserTarget(name, icon, 1.0f, componentName, extras)); } } semaphore.release(); diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/query/StickersQuery.java b/TMessagesProj/src/main/java/org/telegram/messenger/query/StickersQuery.java index 54f0b592f..a0fbd5151 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/query/StickersQuery.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/query/StickersQuery.java @@ -33,11 +33,13 @@ import org.telegram.ui.ActionBar.BaseFragment; import org.telegram.ui.Components.StickersAlert; import java.util.ArrayList; +import java.util.Collections; +import java.util.Comparator; import java.util.HashMap; public class StickersQuery { - private static String loadHash; + private static int loadHash; private static int loadDate; private static ArrayList stickerSets = new ArrayList<>(); private static HashMap stickerSetsById = new HashMap<>(); @@ -49,7 +51,7 @@ public class StickersQuery { private static boolean stickersLoaded; public static void cleanup() { - loadHash = null; + loadHash = 0; loadDate = 0; allStickers.clear(); stickerSets.clear(); @@ -98,6 +100,59 @@ public class StickersQuery { return value != null ? value : ""; } + public static void reorderStickers(final ArrayList order) { + Collections.sort(stickerSets, new Comparator() { + @Override + public int compare(TLRPC.TL_messages_stickerSet lhs, TLRPC.TL_messages_stickerSet rhs) { + int index1 = order.indexOf(lhs.set.id); + int index2 = order.indexOf(rhs.set.id); + if (index1 > index2) { + return 1; + } else if (index1 < index2) { + return -1; + } + return 0; + } + }); + loadHash = calcStickersHash(stickerSets); + NotificationCenter.getInstance().postNotificationName(NotificationCenter.stickersDidLoaded); + StickersQuery.loadStickers(false, true); + } + + public static void calcNewHash() { + loadHash = calcStickersHash(stickerSets); + } + + public static void addNewStickerSet(final TLRPC.TL_messages_stickerSet set) { + if (!stickerSetsById.containsKey(set.set.id)) { + stickerSets.add(0, set); + stickerSetsById.put(set.set.id, set); + for (int a = 0; a < set.documents.size(); a++) { + TLRPC.Document document = set.documents.get(a); + stickersById.put(document.id, document); + } + for (int a = 0; a < set.packs.size(); a++) { + TLRPC.TL_stickerPack stickerPack = set.packs.get(a); + stickerPack.emoticon = stickerPack.emoticon.replace("\uFE0F", ""); + ArrayList arrayList = allStickers.get(stickerPack.emoticon); + if (arrayList == null) { + arrayList = new ArrayList<>(); + allStickers.put(stickerPack.emoticon, arrayList); + } + for (int c = 0; c < stickerPack.documents.size(); c++) { + Long id = stickerPack.documents.get(c); + if (!stickersByEmoji.containsKey(id)) { + stickersByEmoji.put(id, stickerPack.emoticon); + } + arrayList.add(stickersById.get(id)); + } + } + loadHash = calcStickersHash(stickerSets); + NotificationCenter.getInstance().postNotificationName(NotificationCenter.stickersDidLoaded); + } + StickersQuery.loadStickers(false, true); + } + public static void loadStickers(boolean cache, boolean force) { if (loadingStickers) { return; @@ -109,7 +164,7 @@ public class StickersQuery { public void run() { ArrayList newStickerArray = null; int date = 0; - String hash = null; + int hash = 0; SQLiteCursor cursor = null; try { cursor = MessagesStorage.getInstance().getDatabase().queryFinalized("SELECT data, date, hash FROM stickers_v2 WHERE 1"); @@ -124,7 +179,7 @@ public class StickersQuery { } } date = cursor.intValue(1); - hash = cursor.stringValue(2); + hash = calcStickersHash(newStickerArray); data.reuse(); } } catch (Throwable e) { @@ -138,8 +193,8 @@ public class StickersQuery { } }); } else { - TLRPC.TL_messages_getAllStickers req = new TLRPC.TL_messages_getAllStickers(); - req.hash = loadHash == null || force ? "" : loadHash; + final TLRPC.TL_messages_getAllStickers req = new TLRPC.TL_messages_getAllStickers(); + req.hash = force ? 0 : loadHash; ConnectionsManager.getInstance().sendRequest(req, new RequestDelegate() { @Override public void run(final TLObject response, final TLRPC.TL_error error) { @@ -194,7 +249,7 @@ public class StickersQuery { }); } } else { - processLoadedStickers(null, false, (int) (System.currentTimeMillis() / 1000), error == null ? "" : null); + processLoadedStickers(null, false, (int) (System.currentTimeMillis() / 1000), req.hash); } } }); @@ -203,7 +258,7 @@ public class StickersQuery { } } - private static void putStickersToCache(final ArrayList stickers, final int date, final String hash) { + private static void putStickersToCache(final ArrayList stickers, final int date, final int hash) { MessagesStorage.getInstance().getStorageQueue().postRunnable(new Runnable() { @Override public void run() { @@ -223,7 +278,7 @@ public class StickersQuery { state.bindInteger(1, 1); state.bindByteBuffer(2, data); state.bindInteger(3, date); - state.bindString(4, hash); + state.bindInteger(4, hash); state.step(); data.reuse(); state.dispose(); @@ -242,7 +297,8 @@ public class StickersQuery { } public static long getStickerSetId(TLRPC.Document document) { - for (TLRPC.DocumentAttribute attribute : document.attributes) { + for (int a = 0; a < document.attributes.size(); a++) { + TLRPC.DocumentAttribute attribute = document.attributes.get(a); if (attribute instanceof TLRPC.TL_documentAttributeSticker) { if (attribute.stickerset instanceof TLRPC.TL_inputStickerSetID) { return attribute.stickerset.id; @@ -253,7 +309,19 @@ public class StickersQuery { return -1; } - private static void processLoadedStickers(final ArrayList res, final boolean cache, final int date, final String hash) { + private static int calcStickersHash(ArrayList sets) { + long acc = 0; + for (int a = 0; a < sets.size(); a++) { + TLRPC.StickerSet set = sets.get(a).set; + if (set.disabled) { + continue; + } + acc = ((acc * 20261) + 0x80000000L + set.hash) % 0x80000000L; + } + return (int) acc; + } + + private static void processLoadedStickers(final ArrayList res, final boolean cache, final int date, final int hash) { AndroidUtilities.runOnUIThread(new Runnable() { @Override public void run() { @@ -264,11 +332,11 @@ public class StickersQuery { Utilities.stageQueue.postRunnable(new Runnable() { @Override public void run() { - if (cache && (res == null || date < (int) (System.currentTimeMillis() / 1000 - 60 * 60)) || !cache && res == null && hash == null) { + if (cache && (res == null || date < (int) (System.currentTimeMillis() / 1000 - 60 * 60)) || !cache && res == null && hash == 0) { AndroidUtilities.runOnUIThread(new Runnable() { @Override public void run() { - if (res != null && hash != null) { + if (res != null && hash != 0) { loadHash = hash; } loadStickers(false, false); @@ -350,7 +418,7 @@ public class StickersQuery { loadDate = date; } }); - putStickersToCache(null, date, null); + putStickersToCache(null, date, 0); } } }); @@ -452,6 +520,25 @@ public class StickersQuery { stickerSetID.id = stickerSet.id; if (hide != 0) { stickerSet.disabled = hide == 1; + for (int a = 0; a < stickerSets.size(); a++) { + TLRPC.TL_messages_stickerSet set = stickerSets.get(a); + if (set.set.id == stickerSet.id) { + stickerSets.remove(a); + if (hide == 2) { + stickerSets.add(0, set); + } else { + for (int b = stickerSets.size() - 1; b >= 0; b--) { + if (stickerSets.get(b).set.disabled) { + continue; + } + stickerSets.add(b + 1, set); + break; + } + } + break; + } + } + loadHash = calcStickersHash(stickerSets); NotificationCenter.getInstance().postNotificationName(NotificationCenter.stickersDidLoaded); TLRPC.TL_messages_installStickerSet req = new TLRPC.TL_messages_installStickerSet(); req.stickerset = stickerSetID; @@ -462,7 +549,7 @@ public class StickersQuery { AndroidUtilities.runOnUIThread(new Runnable() { @Override public void run() { - loadStickers(false, true); + loadStickers(false, false); } }, 1000); } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/support/util/MessageThreadUtil.java b/TMessagesProj/src/main/java/org/telegram/messenger/support/util/MessageThreadUtil.java index b0b64ed73..a9d59b1fe 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/support/util/MessageThreadUtil.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/support/util/MessageThreadUtil.java @@ -20,9 +20,6 @@ import android.os.Handler; import android.os.Looper; import android.util.Log; -import org.telegram.messenger.support.util.ThreadUtil; -import org.telegram.messenger.support.util.TileList; - import java.util.concurrent.Executor; import java.util.concurrent.Executors; diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/support/widget/helper/ItemTouchHelper.java b/TMessagesProj/src/main/java/org/telegram/messenger/support/widget/helper/ItemTouchHelper.java index 4d80b8437..3aece7ccb 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/support/widget/helper/ItemTouchHelper.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/support/widget/helper/ItemTouchHelper.java @@ -1357,7 +1357,7 @@ public class ItemTouchHelper extends RecyclerView.ItemDecoration /** * Drag scroll speed keeps accelerating until this many milliseconds before being capped. */ - private static final long DRAG_SCROLL_ACCELERATION_LIMIT_TIME_MS = 2000; + private static final long DRAG_SCROLL_ACCELERATION_LIMIT_TIME_MS = 500; private int mCachedMaxScrollSpeed = -1; diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/support/widget/helper/ItemTouchUIUtilImpl.java b/TMessagesProj/src/main/java/org/telegram/messenger/support/widget/helper/ItemTouchUIUtilImpl.java index 21c225cf4..f0d631f5d 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/support/widget/helper/ItemTouchUIUtilImpl.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/support/widget/helper/ItemTouchUIUtilImpl.java @@ -26,18 +26,18 @@ import android.view.View; * public API, which is not desired in this case. */ class ItemTouchUIUtilImpl { - final static int item_touch_helper_previous_elevation = 123; + static class Lollipop extends Honeycomb { @Override public void onDraw(Canvas c, RecyclerView recyclerView, View view, - float dX, float dY, int actionState, boolean isCurrentlyActive) { + float dX, float dY, int actionState, boolean isCurrentlyActive) { if (isCurrentlyActive) { - Object originalElevation = view.getTag(item_touch_helper_previous_elevation); + Object originalElevation = view.getTag(); if (originalElevation == null) { originalElevation = ViewCompat.getElevation(view); float newElevation = 1f + findMaxElevation(recyclerView, view); ViewCompat.setElevation(view, newElevation); - view.setTag(item_touch_helper_previous_elevation, originalElevation); + view.setTag(originalElevation); } } super.onDraw(c, recyclerView, view, dX, dY, actionState, isCurrentlyActive); @@ -61,11 +61,11 @@ class ItemTouchUIUtilImpl { @Override public void clearView(View view) { - final Object tag = view.getTag(item_touch_helper_previous_elevation); + final Object tag = view.getTag(); if (tag != null && tag instanceof Float) { ViewCompat.setElevation(view, (Float) tag); } - view.setTag(item_touch_helper_previous_elevation, null); + view.setTag(null); super.clearView(view); } } @@ -85,14 +85,14 @@ class ItemTouchUIUtilImpl { @Override public void onDraw(Canvas c, RecyclerView recyclerView, View view, - float dX, float dY, int actionState, boolean isCurrentlyActive) { + float dX, float dY, int actionState, boolean isCurrentlyActive) { ViewCompat.setTranslationX(view, dX); ViewCompat.setTranslationY(view, dY); } @Override public void onDrawOver(Canvas c, RecyclerView recyclerView, - View view, float dX, float dY, int actionState, boolean isCurrentlyActive) { + View view, float dX, float dY, int actionState, boolean isCurrentlyActive) { } } @@ -100,7 +100,7 @@ class ItemTouchUIUtilImpl { static class Gingerbread implements ItemTouchUIUtil { private void draw(Canvas c, RecyclerView parent, View view, - float dX, float dY) { + float dX, float dY) { c.save(); c.translate(dX, dY); parent.drawChild(c, view, 0); @@ -119,7 +119,7 @@ class ItemTouchUIUtilImpl { @Override public void onDraw(Canvas c, RecyclerView recyclerView, View view, - float dX, float dY, int actionState, boolean isCurrentlyActive) { + float dX, float dY, int actionState, boolean isCurrentlyActive) { if (actionState != ItemTouchHelper.ACTION_STATE_DRAG) { draw(c, recyclerView, view, dX, dY); } @@ -127,8 +127,8 @@ class ItemTouchUIUtilImpl { @Override public void onDrawOver(Canvas c, RecyclerView recyclerView, - View view, float dX, float dY, - int actionState, boolean isCurrentlyActive) { + View view, float dX, float dY, + int actionState, boolean isCurrentlyActive) { if (actionState == ItemTouchHelper.ACTION_STATE_DRAG) { draw(c, recyclerView, view, dX, dY); } diff --git a/TMessagesProj/src/main/java/org/telegram/messenger/video/Track.java b/TMessagesProj/src/main/java/org/telegram/messenger/video/Track.java index 4285fd347..421a52a55 100644 --- a/TMessagesProj/src/main/java/org/telegram/messenger/video/Track.java +++ b/TMessagesProj/src/main/java/org/telegram/messenger/video/Track.java @@ -109,8 +109,6 @@ public class Track { avcConfigurationBox.setSequenceParameterSets(spsArray); avcConfigurationBox.setPictureParameterSets(ppsArray); } - //ByteArrayInputStream byteArrayInputStream = new ByteArrayInputStream(spsBytes); - //SeqParameterSet seqParameterSet = SeqParameterSet.read(byteArrayInputStream); avcConfigurationBox.setAvcLevelIndication(13); avcConfigurationBox.setAvcProfileIndication(100); diff --git a/TMessagesProj/src/main/java/org/telegram/tgnet/TLRPC.java b/TMessagesProj/src/main/java/org/telegram/tgnet/TLRPC.java index 54a1567b6..43e27e932 100644 --- a/TMessagesProj/src/main/java/org/telegram/tgnet/TLRPC.java +++ b/TMessagesProj/src/main/java/org/telegram/tgnet/TLRPC.java @@ -54,7 +54,7 @@ public class TLRPC { public static final int MESSAGE_FLAG_HAS_VIEWS = 0x00000400; public static final int MESSAGE_FLAG_MEGAGROUP = 0x80000000; - public static final int LAYER = 42; + public static final int LAYER = 43; public static class ChatPhoto extends TLObject { public FileLocation photo_small; @@ -105,6 +105,34 @@ public class TLRPC { } } + public static class TL_help_termsOfService extends TLObject { + public static int constructor = 0xf1ee3e90; + + public String text; + + public static TL_help_termsOfService TLdeserialize(AbstractSerializedData stream, int constructor, boolean exception) { + if (TL_help_termsOfService.constructor != constructor) { + if (exception) { + throw new RuntimeException(String.format("can't parse magic %x in TL_help_termsOfService", constructor)); + } else { + return null; + } + } + TL_help_termsOfService result = new TL_help_termsOfService(); + result.readParams(stream, exception); + return result; + } + + public void readParams(AbstractSerializedData stream, boolean exception) { + text = stream.readString(exception); + } + + public void serializeToStream(AbstractSerializedData stream) { + stream.writeInt32(constructor); + stream.writeString(text); + } + } + public static class NotifyPeer extends TLObject { public Peer peer; @@ -5608,6 +5636,76 @@ public class TLRPC { } } + public static class ReportReason extends TLObject { + public String text; + + public static ReportReason TLdeserialize(AbstractSerializedData stream, int constructor, boolean exception) { + ReportReason result = null; + switch(constructor) { + case 0x58dbcab8: + result = new TL_inputReportReasonSpam(); + break; + case 0x1e22c78d: + result = new TL_inputReportReasonViolence(); + break; + case 0xe1746d0a: + result = new TL_inputReportReasonOther(); + break; + case 0x2e59d922: + result = new TL_inputReportReasonPornography(); + break; + } + if (result == null && exception) { + throw new RuntimeException(String.format("can't parse magic %x in ReportReason", constructor)); + } + if (result != null) { + result.readParams(stream, exception); + } + return result; + } + } + + public static class TL_inputReportReasonSpam extends ReportReason { + public static int constructor = 0x58dbcab8; + + + public void serializeToStream(AbstractSerializedData stream) { + stream.writeInt32(constructor); + } + } + + public static class TL_inputReportReasonViolence extends ReportReason { + public static int constructor = 0x1e22c78d; + + + public void serializeToStream(AbstractSerializedData stream) { + stream.writeInt32(constructor); + } + } + + public static class TL_inputReportReasonOther extends ReportReason { + public static int constructor = 0xe1746d0a; + + + public void readParams(AbstractSerializedData stream, boolean exception) { + text = stream.readString(exception); + } + + public void serializeToStream(AbstractSerializedData stream) { + stream.writeInt32(constructor); + stream.writeString(text); + } + } + + public static class TL_inputReportReasonPornography extends ReportReason { + public static int constructor = 0x2e59d922; + + + public void serializeToStream(AbstractSerializedData stream) { + stream.writeInt32(constructor); + } + } + public static class PeerNotifyEvents extends TLObject { public static PeerNotifyEvents TLdeserialize(AbstractSerializedData stream, int constructor, boolean exception) { @@ -7585,6 +7683,7 @@ public class TLRPC { public MessageMedia media; public boolean popup; public boolean is_admin; + public TL_messages_stickerSet stickerset; public ContactLink my_link; public ContactLink foreign_link; public TL_messageGroup group; @@ -7594,6 +7693,7 @@ public class TLRPC { public ArrayList messages = new ArrayList<>(); public String phone; public WebPage webpage; + public ArrayList order = new ArrayList<>(); public EncryptedChat chat; public int max_date; public UserProfilePhoto photo; @@ -7605,6 +7705,9 @@ public class TLRPC { case 0xea4b0e5c: result = new TL_updateChatParticipantAdd(); break; + case 0x43ae3dec: + result = new TL_updateStickerSets(); + break; case 0xbec268ef: result = new TL_updateNotifySettings(); break; @@ -7671,6 +7774,9 @@ public class TLRPC { case 0xb6901959: result = new TL_updateChatParticipantAdmin(); break; + case 0x688a30aa: + result = new TL_updateNewStickerSet(); + break; case 0x9d2e67c5: result = new TL_updateContactLink(); break; @@ -7698,6 +7804,9 @@ public class TLRPC { case 0x1f2b0afd: result = new TL_updateNewMessage(); break; + case 0xf0dfb451: + result = new TL_updateStickerSetsOrder(); + break; case 0x38fe25b7: result = new TL_updateEncryptedMessagesRead(); break; @@ -7749,6 +7858,15 @@ public class TLRPC { } } + public static class TL_updateStickerSets extends Update { + public static int constructor = 0x43ae3dec; + + + public void serializeToStream(AbstractSerializedData stream) { + stream.writeInt32(constructor); + } + } + public static class TL_updateNotifySettings extends Update { public static int constructor = 0xbec268ef; @@ -8152,6 +8270,20 @@ public class TLRPC { } } + public static class TL_updateNewStickerSet extends Update { + public static int constructor = 0x688a30aa; + + + public void readParams(AbstractSerializedData stream, boolean exception) { + stickerset = TL_messages_stickerSet.TLdeserialize(stream, stream.readInt32(exception), exception); + } + + public void serializeToStream(AbstractSerializedData stream) { + stream.writeInt32(constructor); + stickerset.serializeToStream(stream); + } + } + public static class TL_updateContactLink extends Update { public static int constructor = 0x9d2e67c5; @@ -8331,6 +8463,35 @@ public class TLRPC { } } + public static class TL_updateStickerSetsOrder extends Update { + public static int constructor = 0xf0dfb451; + + + public void readParams(AbstractSerializedData stream, boolean exception) { + int magic = stream.readInt32(exception); + if (magic != 0x1cb5c415) { + if (exception) { + throw new RuntimeException(String.format("wrong Vector magic, got %x", magic)); + } + return; + } + int count = stream.readInt32(exception); + for (int a = 0; a < count; a++) { + order.add(stream.readInt64(exception)); + } + } + + public void serializeToStream(AbstractSerializedData stream) { + stream.writeInt32(constructor); + stream.writeInt32(0x1cb5c415); + int count = order.size(); + stream.writeInt32(count); + for (int a = 0; a < count; a++) { + stream.writeInt64(order.get(a)); + } + } + } + public static class TL_updateEncryptedMessagesRead extends Update { public static int constructor = 0x38fe25b7; @@ -8679,15 +8840,9 @@ public class TLRPC { public static messages_AllStickers TLdeserialize(AbstractSerializedData stream, int constructor, boolean exception) { messages_AllStickers result = null; switch(constructor) { - case 0xd51dafdb: + case 0xedfd405f: result = new TL_messages_allStickers(); break; - case 0xdcef3102: - result = new TL_messages_allStickers_old(); - break; - case 0x5ce352ec: - result = new TL_messages_allStickers_old2(); - break; case 0xe86602c3: result = new TL_messages_allStickersNotModified(); break; @@ -8703,11 +8858,12 @@ public class TLRPC { } public static class TL_messages_allStickers extends messages_AllStickers { - public static int constructor = 0xd51dafdb; + public static int constructor = 0xedfd405f; + public int hash; public void readParams(AbstractSerializedData stream, boolean exception) { - hash = stream.readString(exception); + hash = stream.readInt32(exception); int magic = stream.readInt32(exception); if (magic != 0x1cb5c415) { if (exception) { @@ -8727,7 +8883,7 @@ public class TLRPC { public void serializeToStream(AbstractSerializedData stream) { stream.writeInt32(constructor); - stream.writeString(hash); + stream.writeInt32(hash); stream.writeInt32(0x1cb5c415); int count = sets.size(); stream.writeInt32(count); @@ -8737,139 +8893,6 @@ public class TLRPC { } } - public static class TL_messages_allStickers_old extends TL_messages_allStickers { - public static int constructor = 0xdcef3102; - - - public void readParams(AbstractSerializedData stream, boolean exception) { - hash = stream.readString(exception); - int magic = stream.readInt32(exception); - if (magic != 0x1cb5c415) { - if (exception) { - throw new RuntimeException(String.format("wrong Vector magic, got %x", magic)); - } - return; - } - int count = stream.readInt32(exception); - for (int a = 0; a < count; a++) { - TL_stickerPack object = TL_stickerPack.TLdeserialize(stream, stream.readInt32(exception), exception); - if (object == null) { - return; - } - packs.add(object); - } - magic = stream.readInt32(exception); - if (magic != 0x1cb5c415) { - if (exception) { - throw new RuntimeException(String.format("wrong Vector magic, got %x", magic)); - } - return; - } - count = stream.readInt32(exception); - for (int a = 0; a < count; a++) { - Document object = Document.TLdeserialize(stream, stream.readInt32(exception), exception); - if (object == null) { - return; - } - documents.add(object); - } - } - - public void serializeToStream(AbstractSerializedData stream) { - stream.writeInt32(constructor); - stream.writeString(hash); - stream.writeInt32(0x1cb5c415); - int count = packs.size(); - stream.writeInt32(count); - for (int a = 0; a < count; a++) { - packs.get(a).serializeToStream(stream); - } - stream.writeInt32(0x1cb5c415); - count = documents.size(); - stream.writeInt32(count); - for (int a = 0; a < count; a++) { - documents.get(a).serializeToStream(stream); - } - } - } - - public static class TL_messages_allStickers_old2 extends TL_messages_allStickers { - public static int constructor = 0x5ce352ec; - - - public void readParams(AbstractSerializedData stream, boolean exception) { - hash = stream.readString(exception); - int magic = stream.readInt32(exception); - if (magic != 0x1cb5c415) { - if (exception) { - throw new RuntimeException(String.format("wrong Vector magic, got %x", magic)); - } - return; - } - int count = stream.readInt32(exception); - for (int a = 0; a < count; a++) { - TL_stickerPack object = TL_stickerPack.TLdeserialize(stream, stream.readInt32(exception), exception); - if (object == null) { - return; - } - packs.add(object); - } - magic = stream.readInt32(exception); - if (magic != 0x1cb5c415) { - if (exception) { - throw new RuntimeException(String.format("wrong Vector magic, got %x", magic)); - } - return; - } - count = stream.readInt32(exception); - for (int a = 0; a < count; a++) { - StickerSet object = StickerSet.TLdeserialize(stream, stream.readInt32(exception), exception); - if (object == null) { - return; - } - sets.add(object); - } - magic = stream.readInt32(exception); - if (magic != 0x1cb5c415) { - if (exception) { - throw new RuntimeException(String.format("wrong Vector magic, got %x", magic)); - } - return; - } - count = stream.readInt32(exception); - for (int a = 0; a < count; a++) { - Document object = Document.TLdeserialize(stream, stream.readInt32(exception), exception); - if (object == null) { - return; - } - documents.add(object); - } - } - - public void serializeToStream(AbstractSerializedData stream) { - stream.writeInt32(constructor); - stream.writeString(hash); - stream.writeInt32(0x1cb5c415); - int count = packs.size(); - stream.writeInt32(count); - for (int a = 0; a < count; a++) { - packs.get(a).serializeToStream(stream); - } - stream.writeInt32(0x1cb5c415); - count = sets.size(); - stream.writeInt32(count); - for (int a = 0; a < count; a++) { - sets.get(a).serializeToStream(stream); - } - stream.writeInt32(0x1cb5c415); - count = documents.size(); - stream.writeInt32(count); - for (int a = 0; a < count; a++) { - documents.get(a).serializeToStream(stream); - } - } - } - public static class TL_messages_allStickersNotModified extends messages_AllStickers { public static int constructor = 0xe86602c3; @@ -10608,6 +10631,7 @@ public class TLRPC { public static class ChannelMessagesFilter extends TLObject { public int flags; public boolean important_only; + public boolean exclude_new_messages; public ArrayList ranges = new ArrayList<>(); public static ChannelMessagesFilter TLdeserialize(AbstractSerializedData stream, int constructor, boolean exception) { @@ -10649,6 +10673,7 @@ public class TLRPC { public void readParams(AbstractSerializedData stream, boolean exception) { flags = stream.readInt32(exception); important_only = (flags & 1) != 0; + exclude_new_messages = (flags & 2) != 0; int magic = stream.readInt32(exception); if (magic != 0x1cb5c415) { if (exception) { @@ -10669,6 +10694,7 @@ public class TLRPC { public void serializeToStream(AbstractSerializedData stream) { stream.writeInt32(constructor); flags = important_only ? (flags | 1) : (flags &~ 1); + flags = exclude_new_messages ? (flags | 2) : (flags &~ 2); stream.writeInt32(flags); stream.writeInt32(0x1cb5c415); int count = ranges.size(); @@ -14739,6 +14765,23 @@ public class TLRPC { } } + public static class TL_account_reportPeer extends TLObject { + public static int constructor = 0xae189d5f; + + public InputPeer peer; + public ReportReason reason; + + public TLObject deserializeResponse(AbstractSerializedData stream, int constructor, boolean exception) { + return Bool.TLdeserialize(stream, constructor, exception); + } + + public void serializeToStream(AbstractSerializedData stream) { + stream.writeInt32(constructor); + peer.serializeToStream(stream); + reason.serializeToStream(stream); + } + } + public static class TL_users_getFullUser extends TLObject { public static int constructor = 0xca30a5b1; @@ -16350,9 +16393,9 @@ public class TLRPC { } public static class TL_messages_getAllStickers extends TLObject { - public static int constructor = 0xaa3bc868; + public static int constructor = 0x1c9618b1; - public String hash; + public int hash; public TLObject deserializeResponse(AbstractSerializedData stream, int constructor, boolean exception) { return messages_AllStickers.TLdeserialize(stream, constructor, exception); @@ -16360,8 +16403,8 @@ public class TLRPC { public void serializeToStream(AbstractSerializedData stream) { stream.writeInt32(constructor); - stream.writeString(hash); - } + stream.writeInt32(hash); + } } public static class TL_account_updateDeviceLocked extends TLObject { @@ -16673,6 +16716,41 @@ public class TLRPC { } } + public static class TL_help_getTermsOfService extends TLObject { + public static int constructor = 0x37d78f83; + + public String lang_code; + + public TLObject deserializeResponse(AbstractSerializedData stream, int constructor, boolean exception) { + return TL_help_termsOfService.TLdeserialize(stream, constructor, exception); + } + + public void serializeToStream(AbstractSerializedData stream) { + stream.writeInt32(constructor); + stream.writeString(lang_code); + } + } + + public static class TL_messages_reorderStickerSets extends TLObject { + public static int constructor = 0x9fcfbc30; + + public ArrayList order = new ArrayList<>(); + + public TLObject deserializeResponse(AbstractSerializedData stream, int constructor, boolean exception) { + return Bool.TLdeserialize(stream, constructor, exception); + } + + public void serializeToStream(AbstractSerializedData stream) { + stream.writeInt32(constructor); + stream.writeInt32(0x1cb5c415); + int count = order.size(); + stream.writeInt32(count); + for (int a = 0; a < count; a++) { + stream.writeInt64(order.get(a)); + } + } + } + public static class TL_channels_getDialogs extends TLObject { public static int constructor = 0xa9d3d249; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/ActionBar/BottomSheet.java b/TMessagesProj/src/main/java/org/telegram/ui/ActionBar/BottomSheet.java index 8ecf4de38..5fdc15024 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/ActionBar/BottomSheet.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/ActionBar/BottomSheet.java @@ -138,24 +138,24 @@ public class BottomSheet extends Dialog { } } - private static class BottomSheetCell extends FrameLayout { + public static class BottomSheetCell extends FrameLayout { private TextView textView; private ImageView imageView; private boolean isGrid; - public BottomSheetCell(Context context, boolean grid) { + public BottomSheetCell(Context context, int type) { super(context); - isGrid = grid; + isGrid = type == 1; setBackgroundResource(R.drawable.list_selector); - if (!grid) { + if (type != 1) { setPadding(AndroidUtilities.dp(16), 0, AndroidUtilities.dp(16), 0); } imageView = new ImageView(context); imageView.setScaleType(ImageView.ScaleType.CENTER); - if (grid) { + if (type == 1) { addView(imageView, LayoutHelper.createFrame(48, 48, Gravity.CENTER_HORIZONTAL | Gravity.TOP, 0, 8, 0, 0)); } else { addView(imageView, LayoutHelper.createFrame(24, 24, Gravity.CENTER_VERTICAL | (LocaleController.isRTL ? Gravity.RIGHT : Gravity.LEFT))); @@ -166,14 +166,20 @@ public class BottomSheet extends Dialog { textView.setSingleLine(true); textView.setGravity(Gravity.CENTER_HORIZONTAL); textView.setEllipsize(TextUtils.TruncateAt.END); - if (grid) { + if (type == 1) { textView.setTextColor(0xff757575); textView.setTextSize(TypedValue.COMPLEX_UNIT_DIP, 12); addView(textView, LayoutHelper.createFrame(LayoutHelper.MATCH_PARENT, LayoutHelper.WRAP_CONTENT, Gravity.LEFT | Gravity.TOP, 0, 60, 0, 0)); - } else { + } else if (type == 0) { textView.setTextColor(0xff212121); textView.setTextSize(TypedValue.COMPLEX_UNIT_DIP, 16); addView(textView, LayoutHelper.createFrame(LayoutHelper.WRAP_CONTENT, LayoutHelper.WRAP_CONTENT, (LocaleController.isRTL ? Gravity.RIGHT : Gravity.LEFT) | Gravity.CENTER_VERTICAL)); + } else if (type == 2) { + textView.setGravity(Gravity.CENTER); + textView.setTextColor(0xff212121); + textView.setTextSize(TypedValue.COMPLEX_UNIT_DIP, 14); + textView.setTypeface(AndroidUtilities.getTypeface("fonts/rmedium.ttf")); + addView(textView, LayoutHelper.createFrame(LayoutHelper.MATCH_PARENT, LayoutHelper.MATCH_PARENT)); } } @@ -182,6 +188,14 @@ public class BottomSheet extends Dialog { super.onMeasure(isGrid ? MeasureSpec.makeMeasureSpec(AndroidUtilities.dp(96), MeasureSpec.EXACTLY) : widthMeasureSpec, MeasureSpec.makeMeasureSpec(AndroidUtilities.dp(isGrid ? 80 : 48), MeasureSpec.EXACTLY)); } + public void setTextColor(int color) { + textView.setTextColor(color); + } + + public void setGravity(int gravity) { + textView.setGravity(gravity); + } + public void setTextAndIcon(CharSequence text, int icon) { textView.setText(text); if (icon != 0) { @@ -253,7 +267,7 @@ public class BottomSheet extends Dialog { if (child.getVisibility() == GONE || child == containerView) { continue; } - final LayoutParams lp = (LayoutParams) child.getLayoutParams(); + final FrameLayout.LayoutParams lp = (FrameLayout.LayoutParams) child.getLayoutParams(); final int width = child.getMeasuredWidth(); final int height = child.getMeasuredHeight(); @@ -402,7 +416,7 @@ public class BottomSheet extends Dialog { FrameLayout rowLayout = null; int lastRowLayoutNum = 0; for (int a = 0; a < items.length; a++) { - BottomSheetCell cell = new BottomSheetCell(getContext(), isGrid); + BottomSheetCell cell = new BottomSheetCell(getContext(), isGrid ? 1 : 0); cell.setTextAndIcon(items[a], itemIcons != null ? itemIcons[a] : 0); if (isGrid) { int row = a / 3; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/CacheControlActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/CacheControlActivity.java new file mode 100644 index 000000000..2d31df1fc --- /dev/null +++ b/TMessagesProj/src/main/java/org/telegram/ui/CacheControlActivity.java @@ -0,0 +1,659 @@ +/* + * This is the source code of Telegram for Android v. 3.x.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-2015. + */ + +package org.telegram.ui; + +import android.app.Activity; +import android.app.AlarmManager; +import android.app.AlertDialog; +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.view.View; +import android.view.ViewGroup; +import android.widget.AdapterView; +import android.widget.FrameLayout; +import android.widget.LinearLayout; +import android.widget.ListView; + +import org.telegram.SQLite.SQLiteCursor; +import org.telegram.SQLite.SQLiteDatabase; +import org.telegram.SQLite.SQLitePreparedStatement; +import org.telegram.messenger.AndroidUtilities; +import org.telegram.messenger.ApplicationLoader; +import org.telegram.messenger.ClearCacheService; +import org.telegram.messenger.FileLoader; +import org.telegram.messenger.FileLog; +import org.telegram.messenger.ImageLoader; +import org.telegram.messenger.LocaleController; +import org.telegram.messenger.MessagesStorage; +import org.telegram.messenger.R; +import org.telegram.messenger.Utilities; +import org.telegram.messenger.query.BotQuery; +import org.telegram.tgnet.NativeByteBuffer; +import org.telegram.tgnet.TLRPC; +import org.telegram.ui.ActionBar.ActionBar; +import org.telegram.ui.ActionBar.BaseFragment; +import org.telegram.ui.ActionBar.BottomSheet; +import org.telegram.ui.Adapters.BaseFragmentAdapter; +import org.telegram.ui.Cells.CheckBoxCell; +import org.telegram.ui.Cells.TextInfoPrivacyCell; +import org.telegram.ui.Cells.TextSettingsCell; +import org.telegram.ui.Components.LayoutHelper; + +import java.io.File; +import java.util.ArrayList; + +public class CacheControlActivity extends BaseFragment { + + private ListAdapter listAdapter; + + private int databaseRow; + private int databaseInfoRow; + private int keepMediaRow; + private int keepMediaInfoRow; + private int cacheRow; + private int cacheInfoRow; + private int rowCount; + + private long databaseSize = -1; + private long cacheSize = -1; + private long documentsSize = -1; + private long audioSize = -1; + private long musicSize = -1; + private long photoSize = -1; + private long videoSize = -1; + private long totalSize = -1; + private boolean clear[] = new boolean[6]; + private boolean calculating = true; + + private volatile boolean canceled = false; + + @Override + public boolean onFragmentCreate() { + super.onFragmentCreate(); + + rowCount = 0; + keepMediaRow = rowCount++; + keepMediaInfoRow = rowCount++; + cacheRow = rowCount++; + cacheInfoRow = rowCount++; + + databaseRow = rowCount++; + databaseInfoRow = rowCount++; + + File file = new File(ApplicationLoader.getFilesDirFixed(), "cache4.db"); + databaseSize = file.length(); + + Utilities.globalQueue.postRunnable(new Runnable() { + @Override + public void run() { + cacheSize = getDirectorySize(FileLoader.getInstance().checkDirectory(FileLoader.MEDIA_DIR_CACHE), 0); + if (canceled) { + return; + } + photoSize = getDirectorySize(FileLoader.getInstance().checkDirectory(FileLoader.MEDIA_DIR_IMAGE), 0); + if (canceled) { + return; + } + videoSize = getDirectorySize(FileLoader.getInstance().checkDirectory(FileLoader.MEDIA_DIR_VIDEO), 0); + if (canceled) { + return; + } + documentsSize = getDirectorySize(FileLoader.getInstance().checkDirectory(FileLoader.MEDIA_DIR_DOCUMENT), 1); + if (canceled) { + return; + } + musicSize = getDirectorySize(FileLoader.getInstance().checkDirectory(FileLoader.MEDIA_DIR_DOCUMENT), 2); + if (canceled) { + return; + } + audioSize = getDirectorySize(FileLoader.getInstance().checkDirectory(FileLoader.MEDIA_DIR_AUDIO), 0); + totalSize = cacheSize + videoSize + audioSize + photoSize + documentsSize + musicSize; + AndroidUtilities.runOnUIThread(new Runnable() { + @Override + public void run() { + calculating = false; + if (listAdapter != null) { + listAdapter.notifyDataSetChanged(); + } + } + }); + } + }); + + return true; + } + + @Override + public void onFragmentDestroy() { + super.onFragmentDestroy(); + canceled = true; + } + + /*private long getDirectorySize2(File dir) { + long size = 0; + if (dir.isDirectory()) { + File[] array = dir.listFiles(); + if (array != null) { + for (int a = 0; a < array.length; a++) { + File file = array[a]; + if (file.isDirectory()) { + size += getDirectorySize2(file); + } else { + size += file.length(); + FileLog.e("tmessages", "" + file + " size = " + file.length()); + } + } + } + } else if (dir.isFile()) { + FileLog.e("tmessages", "" + dir + " size = " + dir.length()); + size += dir.length(); + } + return size; + }*/ + + private long getDirectorySize(File dir, int documentsMusicType) { + if (dir == null || canceled) { + return 0; + } + long size = 0; + if (dir.isDirectory()) { + try { + File[] array = dir.listFiles(); + if (array != null) { + for (int a = 0; a < array.length; a++) { + if (canceled) { + return 0; + } + File file = array[a]; + if (documentsMusicType == 1 || documentsMusicType == 2) { + String name = file.getName().toLowerCase(); + if (name.endsWith(".mp3") || name.endsWith(".m4a")) { + if (documentsMusicType == 1) { + continue; + } + } else if (documentsMusicType == 2) { + continue; + } + } + if (file.isDirectory()) { + size += getDirectorySize(file, documentsMusicType); + } else { + size += file.length(); + } + } + } + } catch (Throwable e) { + FileLog.e("tmessages", e); + } + } else if (dir.isFile()) { + size += dir.length(); + } + return size; + } + + private void cleanupFolders() { + final ProgressDialog progressDialog = new ProgressDialog(getParentActivity()); + progressDialog.setMessage(LocaleController.getString("Loading", R.string.Loading)); + progressDialog.setCanceledOnTouchOutside(false); + progressDialog.setCancelable(false); + progressDialog.show(); + Utilities.globalQueue.postRunnable(new Runnable() { + @Override + public void run() { + boolean imagesCleared = false; + for (int a = 0; a < 6; a++) { + if (!clear[a]) { + continue; + } + int type = -1; + int documentsMusicType = 0; + if (a == 0) { + type = FileLoader.MEDIA_DIR_IMAGE; + } else if (a == 1) { + type = FileLoader.MEDIA_DIR_VIDEO; + } else if (a == 2) { + type = FileLoader.MEDIA_DIR_DOCUMENT; + documentsMusicType = 1; + } else if (a == 3) { + type = FileLoader.MEDIA_DIR_DOCUMENT; + documentsMusicType = 2; + } else if (a == 4) { + type = FileLoader.MEDIA_DIR_AUDIO; + } else if (a == 5) { + type = FileLoader.MEDIA_DIR_CACHE; + } + if (type == -1) { + continue; + } + File file = FileLoader.getInstance().checkDirectory(type); + if (file != null) { + try { + File[] array = file.listFiles(); + if (array != null) { + for (int b = 0; b < array.length; b++) { + if (documentsMusicType == 1 || documentsMusicType == 2) { + String name = array[b].getName().toLowerCase(); + if (name.endsWith(".mp3") || name.endsWith(".m4a")) { + if (documentsMusicType == 1) { + continue; + } + } else if (documentsMusicType == 2) { + continue; + } + } + if (array[b].isFile()) { + array[b].delete(); + } + } + } + } catch (Throwable e) { + FileLog.e("tmessages", e); + } + } + if (type == FileLoader.MEDIA_DIR_CACHE) { + cacheSize = getDirectorySize(FileLoader.getInstance().checkDirectory(FileLoader.MEDIA_DIR_CACHE), documentsMusicType); + imagesCleared = true; + } else if (type == FileLoader.MEDIA_DIR_AUDIO) { + audioSize = getDirectorySize(FileLoader.getInstance().checkDirectory(FileLoader.MEDIA_DIR_AUDIO), documentsMusicType); + } else if (type == FileLoader.MEDIA_DIR_DOCUMENT) { + if (documentsMusicType == 1) { + documentsSize = getDirectorySize(FileLoader.getInstance().checkDirectory(FileLoader.MEDIA_DIR_DOCUMENT), documentsMusicType); + } else { + musicSize = getDirectorySize(FileLoader.getInstance().checkDirectory(FileLoader.MEDIA_DIR_DOCUMENT), documentsMusicType); + } + } else if (type == FileLoader.MEDIA_DIR_IMAGE) { + imagesCleared = true; + photoSize = getDirectorySize(FileLoader.getInstance().checkDirectory(FileLoader.MEDIA_DIR_IMAGE), documentsMusicType); + } else if (type == FileLoader.MEDIA_DIR_VIDEO) { + videoSize = getDirectorySize(FileLoader.getInstance().checkDirectory(FileLoader.MEDIA_DIR_VIDEO), documentsMusicType); + } + } + final boolean imagesClearedFinal = imagesCleared; + totalSize = cacheSize + videoSize + audioSize + photoSize + documentsSize + musicSize; + AndroidUtilities.runOnUIThread(new Runnable() { + @Override + public void run() { + if (imagesClearedFinal) { + ImageLoader.getInstance().clearMemory(); + } + if (listAdapter != null) { + listAdapter.notifyDataSetChanged(); + } + try { + progressDialog.dismiss(); + } catch (Exception e) { + FileLog.e("tmessages", e); + } + } + }); + } + }); + } + + @Override + public View createView(Context context) { + actionBar.setBackButtonImage(R.drawable.ic_ab_back); + actionBar.setAllowOverlayTitle(true); + actionBar.setTitle(LocaleController.getString("CacheSettings", R.string.CacheSettings)); + actionBar.setActionBarMenuOnItemClick(new ActionBar.ActionBarMenuOnItemClick() { + @Override + public void onItemClick(int id) { + if (id == -1) { + finishFragment(); + } + } + }); + + listAdapter = new ListAdapter(context); + + fragmentView = new FrameLayout(context); + FrameLayout frameLayout = (FrameLayout) fragmentView; + frameLayout.setBackgroundColor(0xfff0f0f0); + + ListView listView = new ListView(context); + listView.setDivider(null); + listView.setDividerHeight(0); + listView.setVerticalScrollBarEnabled(false); + listView.setDrawSelectorOnTop(true); + frameLayout.addView(listView, LayoutHelper.createFrame(LayoutHelper.MATCH_PARENT, LayoutHelper.MATCH_PARENT)); + listView.setAdapter(listAdapter); + listView.setOnItemClickListener(new AdapterView.OnItemClickListener() { + @Override + public void onItemClick(final AdapterView adapterView, View view, final int i, long l) { + if (i == keepMediaRow) { + BottomSheet.Builder builder = new BottomSheet.Builder(getParentActivity()); + builder.setItems(new CharSequence[]{LocaleController.formatPluralString("Weeks", 1), LocaleController.formatPluralString("Months", 1), LocaleController.getString("KeepMediaForever", R.string.KeepMediaForever)}, new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialog, final int which) { + SharedPreferences.Editor editor = ApplicationLoader.applicationContext.getSharedPreferences("mainconfig", Activity.MODE_PRIVATE).edit(); + editor.putInt("keep_media", which).commit(); + if (listAdapter != null) { + listAdapter.notifyDataSetChanged(); + } + PendingIntent pintent = PendingIntent.getService(ApplicationLoader.applicationContext, 0, new Intent(ApplicationLoader.applicationContext, ClearCacheService.class), 0); + AlarmManager alarmManager = (AlarmManager) ApplicationLoader.applicationContext.getSystemService(Context.ALARM_SERVICE); + if (which == 2) { + alarmManager.cancel(pintent); + } else { + alarmManager.setInexactRepeating(AlarmManager.ELAPSED_REALTIME_WAKEUP, AlarmManager.INTERVAL_DAY, AlarmManager.INTERVAL_DAY, pintent); + } + } + }); + showDialog(builder.create()); + + } else if (i == databaseRow) { + AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); + builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); + builder.setNegativeButton(LocaleController.getString("Cancel", R.string.Cancel), null); + builder.setMessage(LocaleController.getString("LocalDatabaseClear", R.string.LocalDatabaseClear)); + builder.setPositiveButton(LocaleController.getString("CacheClear", R.string.CacheClear), new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialogInterface, int i) { + final ProgressDialog progressDialog = new ProgressDialog(getParentActivity()); + progressDialog.setMessage(LocaleController.getString("Loading", R.string.Loading)); + progressDialog.setCanceledOnTouchOutside(false); + progressDialog.setCancelable(false); + progressDialog.show(); + MessagesStorage.getInstance().getStorageQueue().postRunnable(new Runnable() { + @Override + public void run() { + try { + SQLiteDatabase database = MessagesStorage.getInstance().getDatabase(); + ArrayList dialogsToCleanup = new ArrayList<>(); + SQLiteCursor cursor = database.queryFinalized("SELECT did FROM dialogs WHERE 1"); + StringBuilder ids = new StringBuilder(); + while (cursor.next()) { + long did = cursor.longValue(0); + int lower_id = (int) did; + int high_id = (int) (did >> 32); + if (lower_id != 0 && high_id != 1) { + dialogsToCleanup.add(did); + } + } + cursor.dispose(); + + SQLitePreparedStatement state5 = database.executeFast("REPLACE INTO messages_holes VALUES(?, ?, ?)"); + SQLitePreparedStatement state6 = database.executeFast("REPLACE INTO media_holes_v2 VALUES(?, ?, ?, ?)"); + SQLitePreparedStatement state7 = database.executeFast("REPLACE INTO messages_imp_holes VALUES(?, ?, ?)"); + SQLitePreparedStatement state8 = database.executeFast("REPLACE INTO channel_group VALUES(?, ?, ?, ?)"); + + database.beginTransaction(); + for (int a = 0; a < dialogsToCleanup.size(); a++) { + Long did = dialogsToCleanup.get(a); + int messagesCount = 0; + cursor = database.queryFinalized("SELECT COUNT(mid) FROM messages WHERE uid = " + did); + if (cursor.next()) { + messagesCount = cursor.intValue(0); + } + cursor.dispose(); + if (messagesCount <= 2) { + continue; + } + + cursor = database.queryFinalized("SELECT last_mid_i, last_mid FROM dialogs WHERE did = " + did); + ArrayList arrayList = new ArrayList<>(); + if (cursor.next()) { + long last_mid_i = cursor.longValue(0); + long last_mid = cursor.longValue(1); + SQLiteCursor cursor2 = database.queryFinalized("SELECT data FROM messages WHERE uid = " + did + " AND mid IN (" + last_mid_i + "," + last_mid + ")"); + try { + while (cursor2.next()) { + NativeByteBuffer data = new NativeByteBuffer(cursor2.byteArrayLength(0)); + if (data != null && cursor2.byteBufferValue(0, data) != 0) { + TLRPC.Message message = TLRPC.Message.TLdeserialize(data, data.readInt32(false), false); + if (message == null) { + continue; + } + arrayList.add(message); + } + data.reuse(); + } + } catch (Exception e) { + FileLog.e("tmessages", e); + } + cursor2.dispose(); + + database.executeFast("DELETE FROM messages WHERE uid = " + did + " AND mid != " + last_mid_i + " AND mid != " + last_mid).stepThis().dispose(); + database.executeFast("DELETE FROM channel_group WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM messages_holes WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM messages_imp_holes WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM bot_keyboard WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM media_counts_v2 WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM media_v2 WHERE uid = " + did).stepThis().dispose(); + database.executeFast("DELETE FROM media_holes_v2 WHERE uid = " + did).stepThis().dispose(); + BotQuery.clearBotKeyboard(did, null); + MessagesStorage.createFirstHoles(did, state5, state6, state7, state8, arrayList); + } + cursor.dispose(); + } + state5.dispose(); + state6.dispose(); + state7.dispose(); + state8.dispose(); + database.commitTransaction(); + database.executeFast("VACUUM").stepThis().dispose(); + } catch (Exception e) { + FileLog.e("tmessages", e); + } finally { + AndroidUtilities.runOnUIThread(new Runnable() { + @Override + public void run() { + try { + progressDialog.dismiss(); + } catch (Exception e) { + FileLog.e("tmessages", e); + } + if (listAdapter != null) { + File file = new File(ApplicationLoader.getFilesDirFixed(), "cache4.db"); + databaseSize = file.length(); + listAdapter.notifyDataSetChanged(); + } + } + }); + } + } + }); + } + }); + showDialog(builder.create()); + } else if (i == cacheRow) { + if (totalSize <= 0 || getParentActivity() == null) { + return; + } + BottomSheet.Builder builder = new BottomSheet.Builder(getParentActivity()); + builder.setApplyTopPaddings(false); + LinearLayout linearLayout = new LinearLayout(getParentActivity()); + linearLayout.setOrientation(LinearLayout.VERTICAL); + for (int a = 0; a < 6; a++) { + long size = 0; + String name = null; + if (a == 0) { + size = photoSize; + name = LocaleController.getString("LocalPhotoCache", R.string.LocalPhotoCache); + } else if (a == 1) { + size = videoSize; + name = LocaleController.getString("LocalVideoCache", R.string.LocalVideoCache); + } else if (a == 2) { + size = documentsSize; + name = LocaleController.getString("LocalDocumentCache", R.string.LocalDocumentCache); + } else if (a == 3) { + size = musicSize; + name = LocaleController.getString("LocalMusicCache", R.string.LocalMusicCache); + } else if (a == 4) { + size = audioSize; + name = LocaleController.getString("LocalAudioCache", R.string.LocalAudioCache); + } else if (a == 5) { + size = cacheSize; + name = LocaleController.getString("LocalCache", R.string.LocalCache); + } + if (size > 0) { + clear[a] = true; + CheckBoxCell checkBoxCell = new CheckBoxCell(getParentActivity()); + checkBoxCell.setTag(a); + checkBoxCell.setBackgroundResource(R.drawable.list_selector); + linearLayout.addView(checkBoxCell, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, 48)); + checkBoxCell.setText(name, AndroidUtilities.formatFileSize(size), true, true); + checkBoxCell.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + CheckBoxCell cell = (CheckBoxCell) v; + int num = (Integer) cell.getTag(); + clear[num] = !clear[num]; + cell.setChecked(clear[num], true); + } + }); + } else { + clear[a] = false; + } + } + BottomSheet.BottomSheetCell cell = new BottomSheet.BottomSheetCell(getParentActivity(), 2); + cell.setBackgroundResource(R.drawable.list_selector); + cell.setTextAndIcon(LocaleController.getString("ClearMediaCache", R.string.ClearMediaCache).toUpperCase(), 0); + cell.setTextColor(0xffcd5a5a); + cell.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + try { + if (visibleDialog != null) { + visibleDialog.dismiss(); + } + } catch (Exception e) { + FileLog.e("tmessages", e); + } + cleanupFolders(); + } + }); + linearLayout.addView(cell, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, 48)); + builder.setCustomView(linearLayout); + showDialog(builder.create()); + } + } + }); + + return fragmentView; + } + + @Override + public void onResume() { + super.onResume(); + if (listAdapter != null) { + listAdapter.notifyDataSetChanged(); + } + } + + private class ListAdapter extends BaseFragmentAdapter { + private Context mContext; + + public ListAdapter(Context context) { + mContext = context; + } + + @Override + public boolean areAllItemsEnabled() { + return false; + } + + @Override + public boolean isEnabled(int i) { + return i == databaseRow || i == cacheRow && totalSize > 0 || i == keepMediaRow; + } + + @Override + public int getCount() { + return rowCount; + } + + @Override + public Object getItem(int i) { + return null; + } + + @Override + public long getItemId(int i) { + return i; + } + + @Override + public boolean hasStableIds() { + return false; + } + + @Override + public View getView(int i, View view, ViewGroup viewGroup) { + int type = getItemViewType(i); + if (type == 0) { + if (view == null) { + view = new TextSettingsCell(mContext); + view.setBackgroundColor(0xffffffff); + } + TextSettingsCell textCell = (TextSettingsCell) view; + if (i == databaseRow) { + textCell.setTextAndValue(LocaleController.getString("LocalDatabase", R.string.LocalDatabase), AndroidUtilities.formatFileSize(databaseSize), false); + } else if (i == cacheRow) { + if (calculating) { + textCell.setTextAndValue(LocaleController.getString("ClearMediaCache", R.string.ClearMediaCache), LocaleController.getString("CalculatingSize", R.string.CalculatingSize), false); + } else { + textCell.setTextAndValue(LocaleController.getString("ClearMediaCache", R.string.ClearMediaCache), totalSize == 0 ? LocaleController.getString("CacheEmpty", R.string.CacheEmpty) : AndroidUtilities.formatFileSize(totalSize), false); + } + } else if (i == keepMediaRow) { + SharedPreferences preferences = ApplicationLoader.applicationContext.getSharedPreferences("mainconfig", Activity.MODE_PRIVATE); + int keepMedia = preferences.getInt("keep_media", 2); + String value; + if (keepMedia == 0) { + value = LocaleController.formatPluralString("Weeks", 1); + } else if (keepMedia == 1) { + value = LocaleController.formatPluralString("Months", 1); + } else { + value = LocaleController.getString("KeepMediaForever", R.string.KeepMediaForever); + } + textCell.setTextAndValue(LocaleController.getString("KeepMedia", R.string.KeepMedia), value, false); + } + } else if (type == 1) { + if (view == null) { + view = new TextInfoPrivacyCell(mContext); + } + if (i == databaseInfoRow) { + ((TextInfoPrivacyCell) view).setText(LocaleController.getString("LocalDatabaseInfo", R.string.LocalDatabaseInfo)); + view.setBackgroundResource(R.drawable.greydivider_bottom); + } else if (i == cacheInfoRow) { + ((TextInfoPrivacyCell) view).setText(""); + view.setBackgroundResource(R.drawable.greydivider); + } else if (i == keepMediaInfoRow) { + ((TextInfoPrivacyCell) view).setText(AndroidUtilities.replaceTags(LocaleController.getString("KeepMediaInfo", R.string.KeepMediaInfo))); + view.setBackgroundResource(R.drawable.greydivider); + } + } + return view; + } + + @Override + public int getItemViewType(int i) { + if (i == databaseRow || i == cacheRow || i == keepMediaRow) { + return 0; + } else if (i == databaseInfoRow || i == cacheInfoRow || i == keepMediaInfoRow) { + return 1; + } + return 0; + } + + @Override + public int getViewTypeCount() { + return 2; + } + + @Override + public boolean isEmpty() { + return false; + } + } +} diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Cells/CheckBoxCell.java b/TMessagesProj/src/main/java/org/telegram/ui/Cells/CheckBoxCell.java new file mode 100644 index 000000000..b0d15c581 --- /dev/null +++ b/TMessagesProj/src/main/java/org/telegram/ui/Cells/CheckBoxCell.java @@ -0,0 +1,103 @@ +/* + * This is the source code of Telegram for Android v. 3.x.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-2015. + */ + +package org.telegram.ui.Cells; + +import android.content.Context; +import android.graphics.Canvas; +import android.graphics.Paint; +import android.text.TextUtils; +import android.util.TypedValue; +import android.view.Gravity; +import android.widget.FrameLayout; +import android.widget.TextView; + +import org.telegram.messenger.AndroidUtilities; +import org.telegram.messenger.LocaleController; +import org.telegram.ui.Components.CheckBoxSquare; +import org.telegram.ui.Components.LayoutHelper; + +public class CheckBoxCell extends FrameLayout { + + private TextView textView; + private TextView valueTextView; + private CheckBoxSquare checkBox; + private static Paint paint; + private boolean needDivider; + + public CheckBoxCell(Context context) { + super(context); + + if (paint == null) { + paint = new Paint(); + paint.setColor(0xffd9d9d9); + paint.setStrokeWidth(1); + } + + textView = new TextView(context); + textView.setTextColor(0xff212121); + textView.setTextSize(TypedValue.COMPLEX_UNIT_DIP, 16); + textView.setLines(1); + textView.setMaxLines(1); + textView.setSingleLine(true); + textView.setEllipsize(TextUtils.TruncateAt.END); + textView.setGravity((LocaleController.isRTL ? Gravity.RIGHT : Gravity.LEFT) | Gravity.CENTER_VERTICAL); + addView(textView, LayoutHelper.createFrame(LayoutHelper.MATCH_PARENT, LayoutHelper.MATCH_PARENT, (LocaleController.isRTL ? Gravity.RIGHT : Gravity.LEFT) | Gravity.TOP, (LocaleController.isRTL ? 17 : 46), 0, (LocaleController.isRTL ? 46 : 17), 0)); + + valueTextView = new TextView(context); + valueTextView.setTextColor(0xff2f8cc9); + valueTextView.setTextSize(TypedValue.COMPLEX_UNIT_DIP, 16); + valueTextView.setLines(1); + valueTextView.setMaxLines(1); + valueTextView.setSingleLine(true); + valueTextView.setEllipsize(TextUtils.TruncateAt.END); + valueTextView.setGravity((LocaleController.isRTL ? Gravity.LEFT : Gravity.RIGHT) | Gravity.CENTER_VERTICAL); + addView(valueTextView, LayoutHelper.createFrame(LayoutHelper.WRAP_CONTENT, LayoutHelper.MATCH_PARENT, (LocaleController.isRTL ? Gravity.LEFT : Gravity.RIGHT) | Gravity.TOP, 17, 0, 17, 0)); + + checkBox = new CheckBoxSquare(context); + addView(checkBox, LayoutHelper.createFrame(18, 18, (LocaleController.isRTL ? Gravity.RIGHT : Gravity.LEFT) | Gravity.TOP, (LocaleController.isRTL ? 0 : 17), 15, (LocaleController.isRTL ? 17 : 0), 0)); + } + + @Override + protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { + setMeasuredDimension(MeasureSpec.getSize(widthMeasureSpec), AndroidUtilities.dp(48) + (needDivider ? 1 : 0)); + + int availableWidth = getMeasuredWidth() - getPaddingLeft() - getPaddingRight() - AndroidUtilities.dp(34); + + valueTextView.measure(MeasureSpec.makeMeasureSpec(availableWidth / 2, MeasureSpec.AT_MOST), MeasureSpec.makeMeasureSpec(getMeasuredHeight(), MeasureSpec.EXACTLY)); + textView.measure(MeasureSpec.makeMeasureSpec(availableWidth - valueTextView.getMeasuredWidth() - AndroidUtilities.dp(8), MeasureSpec.EXACTLY), MeasureSpec.makeMeasureSpec(getMeasuredHeight(), MeasureSpec.EXACTLY)); + checkBox.measure(MeasureSpec.makeMeasureSpec(AndroidUtilities.dp(18), MeasureSpec.AT_MOST), MeasureSpec.makeMeasureSpec(AndroidUtilities.dp(18), MeasureSpec.EXACTLY)); + } + + public void setTextColor(int color) { + textView.setTextColor(color); + } + + public void setText(String text, String value, boolean checked, boolean divider) { + textView.setText(text); + checkBox.setChecked(checked, false); + valueTextView.setText(value); + needDivider = divider; + setWillNotDraw(!divider); + } + + public void setChecked(boolean checked, boolean animated) { + checkBox.setChecked(checked, animated); + } + + public boolean isChecked() { + return checkBox.isChecked(); + } + + @Override + protected void onDraw(Canvas canvas) { + if (needDivider) { + canvas.drawLine(getPaddingLeft(), getHeight() - 1, getWidth() - getPaddingRight(), getHeight() - 1, paint); + } + } +} diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Cells/StickerSetCell.java b/TMessagesProj/src/main/java/org/telegram/ui/Cells/StickerSetCell.java index e78b46e29..83838a2db 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Cells/StickerSetCell.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Cells/StickerSetCell.java @@ -11,9 +11,12 @@ package org.telegram.ui.Cells; import android.content.Context; import android.graphics.Canvas; import android.graphics.Paint; +import android.graphics.Rect; +import android.os.Build; import android.text.TextUtils; import android.util.TypedValue; import android.view.Gravity; +import android.view.MotionEvent; import android.widget.FrameLayout; import android.widget.ImageView; import android.widget.TextView; @@ -36,6 +39,7 @@ public class StickerSetCell extends FrameLayout { private boolean needDivider; private ImageView optionsButton; private TLRPC.TL_messages_stickerSet stickersSet; + private Rect rect = new Rect(); private static Paint paint; @@ -70,7 +74,15 @@ public class StickerSetCell extends FrameLayout { imageView.setAspectFit(true); addView(imageView, LayoutHelper.createFrame(48, 48, (LocaleController.isRTL ? Gravity.RIGHT : Gravity.LEFT) | Gravity.TOP, LocaleController.isRTL ? 0 : 12, 8, LocaleController.isRTL ? 12 : 0, 0)); - optionsButton = new ImageView(context); + optionsButton = new ImageView(context) { + @Override + public boolean onTouchEvent(MotionEvent event) { + if (event.getAction() == MotionEvent.ACTION_UP) { + StickerSetCell.this.getParent().requestDisallowInterceptTouchEvent(true); + } + return super.onTouchEvent(event); + } + }; optionsButton.setBackgroundResource(R.drawable.bar_selector_grey); optionsButton.setImageResource(R.drawable.doc_actions_b); optionsButton.setScaleType(ImageView.ScaleType.CENTER); @@ -90,7 +102,7 @@ public class StickerSetCell extends FrameLayout { @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { - super.onMeasure(widthMeasureSpec, MeasureSpec.makeMeasureSpec(AndroidUtilities.dp(64) + (needDivider ? 1 : 0), MeasureSpec.EXACTLY)); + super.onMeasure(MeasureSpec.makeMeasureSpec(MeasureSpec.getSize(widthMeasureSpec), MeasureSpec.EXACTLY), MeasureSpec.makeMeasureSpec(AndroidUtilities.dp(64) + (needDivider ? 1 : 0), MeasureSpec.EXACTLY)); } public void setStickersSet(TLRPC.TL_messages_stickerSet set, boolean divider) { @@ -127,6 +139,20 @@ public class StickerSetCell extends FrameLayout { return stickersSet; } + @Override + public boolean onTouchEvent(MotionEvent event) { + if (Build.VERSION.SDK_INT >= 21 && getBackground() != null) { + optionsButton.getHitRect(rect); + if (rect.contains((int) event.getX(), (int) event.getY())) { + return true; + } + if (event.getAction() == MotionEvent.ACTION_DOWN || event.getAction() == MotionEvent.ACTION_MOVE) { + getBackground().setHotspot(event.getX(), event.getY()); + } + } + return super.onTouchEvent(event); + } + @Override protected void onDraw(Canvas canvas) { if (needDivider) { diff --git a/TMessagesProj/src/main/java/org/telegram/ui/ChatActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/ChatActivity.java index 26d6b9568..2bb16fd35 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/ChatActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/ChatActivity.java @@ -721,13 +721,17 @@ public class ChatActivity extends BaseFragment implements NotificationCenter.Not } } if (str.length() != 0) { - if (Build.VERSION.SDK_INT < 11) { - android.text.ClipboardManager clipboard = (android.text.ClipboardManager) ApplicationLoader.applicationContext.getSystemService(Context.CLIPBOARD_SERVICE); - clipboard.setText(str); - } else { - android.content.ClipboardManager clipboard = (android.content.ClipboardManager) ApplicationLoader.applicationContext.getSystemService(Context.CLIPBOARD_SERVICE); - android.content.ClipData clip = android.content.ClipData.newPlainText("label", str); - clipboard.setPrimaryClip(clip); + try { + if (Build.VERSION.SDK_INT < 11) { + android.text.ClipboardManager clipboard = (android.text.ClipboardManager) ApplicationLoader.applicationContext.getSystemService(Context.CLIPBOARD_SERVICE); + clipboard.setText(str); + } else { + android.content.ClipboardManager clipboard = (android.content.ClipboardManager) ApplicationLoader.applicationContext.getSystemService(Context.CLIPBOARD_SERVICE); + android.content.ClipData clip = android.content.ClipData.newPlainText("label", str); + clipboard.setPrimaryClip(clip); + } + } catch (Exception e) { + FileLog.e("tmessages", e); } } for (int a = 1; a >= 0; a--) { @@ -807,16 +811,16 @@ public class ChatActivity extends BaseFragment implements NotificationCenter.Not if (id != clear_history) { if (isChat) { if (ChatObject.isNotInChat(currentChat)) { - MessagesController.getInstance().deleteDialog(dialog_id, false); + MessagesController.getInstance().deleteDialog(dialog_id, 0); } else { MessagesController.getInstance().deleteUserFromChat((int) -dialog_id, MessagesController.getInstance().getUser(UserConfig.getClientUserId()), null); } } else { - MessagesController.getInstance().deleteDialog(dialog_id, false); + MessagesController.getInstance().deleteDialog(dialog_id, 0); } finishFragment(); } else { - MessagesController.getInstance().deleteDialog(dialog_id, true); + MessagesController.getInstance().deleteDialog(dialog_id, 1); } } }); @@ -1611,10 +1615,10 @@ public class ChatActivity extends BaseFragment implements NotificationCenter.Not addToContactsButton.setTypeface(AndroidUtilities.getTypeface("fonts/rmedium.ttf")); addToContactsButton.setSingleLine(true); addToContactsButton.setMaxLines(1); - addToContactsButton.setPadding(AndroidUtilities.dp(50), 0, AndroidUtilities.dp(4), 0); + addToContactsButton.setPadding(AndroidUtilities.dp(4), 0, AndroidUtilities.dp(4), 0); addToContactsButton.setGravity(Gravity.CENTER); addToContactsButton.setText(LocaleController.getString("AddContactChat", R.string.AddContactChat)); - reportSpamView.addView(addToContactsButton, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.MATCH_PARENT, 0.5f, Gravity.LEFT | Gravity.TOP)); + reportSpamView.addView(addToContactsButton, LayoutHelper.createLinear(LayoutHelper.MATCH_PARENT, LayoutHelper.MATCH_PARENT, 0.5f, Gravity.LEFT | Gravity.TOP, 0, 0, 0, AndroidUtilities.dp(1))); addToContactsButton.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { @@ -2144,7 +2148,7 @@ public class ChatActivity extends BaseFragment implements NotificationCenter.Not builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialogInterface, int i) { - MessagesController.getInstance().deleteDialog(dialog_id, false); + MessagesController.getInstance().deleteDialog(dialog_id, 0); finishFragment(); } }); @@ -2187,7 +2191,7 @@ public class ChatActivity extends BaseFragment implements NotificationCenter.Not } private void checkScrollForLoad() { - if (chatLayoutManager == null) { + if (chatLayoutManager == null || paused) { return; } int firstVisibleItem = chatLayoutManager.findFirstVisibleItemPosition(); @@ -4153,7 +4157,9 @@ public class ChatActivity extends BaseFragment implements NotificationCenter.Not if (chatListView != null) { chatListView.setEmptyView(null); } - emptyViewContainer.setVisibility(View.INVISIBLE); + if (emptyViewContainer != null) { + emptyViewContainer.setVisibility(View.INVISIBLE); + } } else { if (progressView != null) { progressView.setVisibility(View.INVISIBLE); @@ -4573,14 +4579,16 @@ public class ChatActivity extends BaseFragment implements NotificationCenter.Not messages.remove(index); messagesDict[loadIndex].remove(ids); ArrayList dayArr = messagesByDays.get(obj.dateKey); - dayArr.remove(obj); - if (dayArr.isEmpty()) { - messagesByDays.remove(obj.dateKey); - if (index >= 0 && index < messages.size()) { - messages.remove(index); + if (dayArr != null) { + dayArr.remove(obj); + if (dayArr.isEmpty()) { + messagesByDays.remove(obj.dateKey); + if (index >= 0 && index < messages.size()) { + messages.remove(index); + } } + updated = true; } - updated = true; } } } @@ -5194,7 +5202,7 @@ public class ChatActivity extends BaseFragment implements NotificationCenter.Not @Override protected void onDialogDismiss(Dialog dialog) { if (closeChatDialog != null && dialog == closeChatDialog) { - MessagesController.getInstance().deleteDialog(dialog_id, false); + MessagesController.getInstance().deleteDialog(dialog_id, 0); finishFragment(); } } @@ -5422,6 +5430,7 @@ public class ChatActivity extends BaseFragment implements NotificationCenter.Not readWhenResume = false; MessagesController.getInstance().markDialogAsRead(dialog_id, messages.get(0).getId(), readWithMid, readWithDate, true, false); } + checkScrollForLoad(); if (wasPaused) { wasPaused = false; if (chatAdapter != null) { diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Components/ChatActivityEnterView.java b/TMessagesProj/src/main/java/org/telegram/ui/Components/ChatActivityEnterView.java index 1fdfc86aa..92d550966 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Components/ChatActivityEnterView.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Components/ChatActivityEnterView.java @@ -59,6 +59,7 @@ import org.telegram.messenger.AnimationCompat.AnimatorSetProxy; import org.telegram.messenger.AnimationCompat.ObjectAnimatorProxy; import org.telegram.messenger.AnimationCompat.ViewProxy; import org.telegram.messenger.ApplicationLoader; +import org.telegram.ui.StickersActivity; import java.util.Locale; @@ -1502,6 +1503,13 @@ public class ChatActivityEnterView extends FrameLayoutFixed implements Notificat delegate.onMessageSend(null); } } + + @Override + public void onStickersSettingsClick() { + if (parentFragment != null) { + parentFragment.presentFragment(new StickersActivity()); + } + } }); sizeNotifierLayout.addView(emojiView); } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Components/CheckBoxSquare.java b/TMessagesProj/src/main/java/org/telegram/ui/Components/CheckBoxSquare.java index 6517b83ea..1148bbb79 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Components/CheckBoxSquare.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Components/CheckBoxSquare.java @@ -33,7 +33,6 @@ public class CheckBoxSquare extends View { private float progress; private ObjectAnimatorProxy checkAnimator; - private boolean isCheckAnimation = true; private boolean attachedToWindow; private boolean isChecked; @@ -92,7 +91,6 @@ public class CheckBoxSquare extends View { } private void animateToCheckedState(boolean newCheckedState) { - isCheckAnimation = newCheckedState; checkAnimator = ObjectAnimatorProxy.ofFloatProxy(this, "progress", newCheckedState ? 1 : 0); checkAnimator.setDuration(300); checkAnimator.start(); @@ -173,50 +171,13 @@ public class CheckBoxSquare extends View { } if (progress > 0.5f) { - int endX = (int) (AndroidUtilities.dp(7.5f) - AndroidUtilities.dp(5) * (1.0f - bounceProgress)); //dp 2.5f - int endY = (int) (AndroidUtilities.dpf2(13.5f) - AndroidUtilities.dp(5) * (1.0f - bounceProgress)); //dpf2 8.5f + int endX = (int) (AndroidUtilities.dp(7.5f) - AndroidUtilities.dp(5) * (1.0f - bounceProgress)); + int endY = (int) (AndroidUtilities.dpf2(13.5f) - AndroidUtilities.dp(5) * (1.0f - bounceProgress)); drawCanvas.drawLine(AndroidUtilities.dp(7.5f), (int) AndroidUtilities.dpf2(13.5f), endX, endY, checkPaint); - endX = (int) (AndroidUtilities.dpf2(6.5f) + AndroidUtilities.dp(9) * (1.0f - bounceProgress)); //dpf2 15.5f - endY = (int) (AndroidUtilities.dpf2(13.5f) - AndroidUtilities.dp(9) * (1.0f - bounceProgress)); //dpf2 4.5f + endX = (int) (AndroidUtilities.dpf2(6.5f) + AndroidUtilities.dp(9) * (1.0f - bounceProgress)); + endY = (int) (AndroidUtilities.dpf2(13.5f) - AndroidUtilities.dp(9) * (1.0f - bounceProgress)); drawCanvas.drawLine((int) AndroidUtilities.dpf2(6.5f), (int) AndroidUtilities.dpf2(13.5f), endX, endY, checkPaint); } canvas.drawBitmap(drawBitmap, 0, 0, null); - /*eraser2.setStrokeWidth(AndroidUtilities.dp(size + 6)); - - drawBitmap.eraseColor(0); - float rad = getMeasuredWidth() / 2; - - float roundProgress = progress >= 0.5f ? 1.0f : progress / 0.5f; - float checkProgress = progress < 0.5f ? 0.0f : (progress - 0.5f) / 0.5f; - - float roundProgressCheckState = isCheckAnimation ? progress : (1.0f - progress); - if (roundProgressCheckState < progressBounceDiff) { - rad -= AndroidUtilities.dp(2) * roundProgressCheckState / progressBounceDiff; - } else if (roundProgressCheckState < progressBounceDiff * 2) { - rad -= AndroidUtilities.dp(2) - AndroidUtilities.dp(2) * (roundProgressCheckState - progressBounceDiff) / progressBounceDiff; - } - if (drawBackground) { - paint.setColor(0x44000000); - canvas.drawCircle(getMeasuredWidth() / 2, getMeasuredHeight() / 2, rad - AndroidUtilities.dp(1), paint); - canvas.drawCircle(getMeasuredWidth() / 2, getMeasuredHeight() / 2, rad - AndroidUtilities.dp(1), backgroundPaint); - } - - paint.setColor(color); - - bitmapCanvas.drawCircle(getMeasuredWidth() / 2, getMeasuredHeight() / 2, rad, paint); - bitmapCanvas.drawCircle(getMeasuredWidth() / 2, getMeasuredHeight() / 2, rad * (1 - roundProgress), eraser); - canvas.drawBitmap(drawBitmap, 0, 0, null); - - checkBitmap.eraseColor(0); - int w = checkDrawable.getIntrinsicWidth(); - int h = checkDrawable.getIntrinsicHeight(); - int x = (getMeasuredWidth() - w) / 2; - int y = (getMeasuredHeight() - h) / 2; - - checkDrawable.setBounds(x, y + checkOffset, x + w, y + h + checkOffset); - checkDrawable.draw(checkCanvas); - checkCanvas.drawCircle(getMeasuredWidth() / 2 - AndroidUtilities.dp(2.5f), getMeasuredHeight() / 2 + AndroidUtilities.dp(4), ((getMeasuredWidth() + AndroidUtilities.dp(6)) / 2) * (1 - checkProgress), eraser2); - - canvas.drawBitmap(checkBitmap, 0, 0, null);*/ } } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Components/EmojiView.java b/TMessagesProj/src/main/java/org/telegram/ui/Components/EmojiView.java index 1e88b10df..4b05d9946 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Components/EmojiView.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Components/EmojiView.java @@ -64,6 +64,7 @@ public class EmojiView extends FrameLayout implements NotificationCenter.Notific boolean onBackspace(); void onEmojiSelected(String emoji); void onStickerSelected(TLRPC.Document sticker); + void onStickersSettingsClick(); } private static final Field superListenerField; @@ -477,7 +478,6 @@ public class EmojiView extends FrameLayout implements NotificationCenter.Notific private ArrayList recentEmoji = new ArrayList<>(); private HashMap stickersUseHistory = new HashMap<>(); private ArrayList recentStickers = new ArrayList<>(); - private HashMap stickerSetsUseCount = new HashMap<>(); private ArrayList stickerSets = new ArrayList<>(); private int[] icons = { @@ -696,15 +696,6 @@ public class EmojiView extends FrameLayout implements NotificationCenter.Notific } stickersUseHistory.put(document.id, ++count); - long id = StickersQuery.getStickerSetId(document); - if (id != -1) { - count = stickerSetsUseCount.get(id); - if (count == null) { - count = 0; - } - stickerSetsUseCount.put(id, ++count); - } - saveRecentStickers(); if (listener != null) { listener.onStickerSelected(document); @@ -806,6 +797,12 @@ public class EmojiView extends FrameLayout implements NotificationCenter.Notific return; } int index = page - (recentStickers.isEmpty() ? 1 : 2); + if (index == stickerSets.size()) { + if (listener != null) { + listener.onStickersSettingsClick(); + } + return; + } if (index >= stickerSets.size()) { index = stickerSets.size() - 1; } @@ -1056,32 +1053,6 @@ public class EmojiView extends FrameLayout implements NotificationCenter.Notific } editor.putString("stickers", stringBuilder.toString()); - ArrayList toRemove = null; - for (HashMap.Entry entry : stickerSetsUseCount.entrySet()) { - if (!StickersQuery.isStickerPackInstalled(entry.getKey())) { - if (toRemove == null) { - toRemove = new ArrayList<>(); - } - toRemove.add(entry.getKey()); - } - } - if (toRemove != null) { - for (int a = 0; a < toRemove.size(); a++) { - stickerSetsUseCount.remove(toRemove.get(a)); - } - } - - stringBuilder.setLength(0); - for (HashMap.Entry entry : stickerSetsUseCount.entrySet()) { - if (stringBuilder.length() != 0) { - stringBuilder.append(","); - } - stringBuilder.append(entry.getKey()); - stringBuilder.append("="); - stringBuilder.append(entry.getValue()); - } - editor.putString("sets", stringBuilder.toString()); - editor.commit(); } @@ -1171,28 +1142,10 @@ public class EmojiView extends FrameLayout implements NotificationCenter.Notific } stickerSets.add(pack); } - Collections.sort(stickerSets, new Comparator() { - @Override - public int compare(TLRPC.TL_messages_stickerSet lhs, TLRPC.TL_messages_stickerSet rhs) { - Integer count1 = stickerSetsUseCount.get(lhs.set.id); - Integer count2 = stickerSetsUseCount.get(rhs.set.id); - if (count1 == null) { - count1 = 0; - } - if (count2 == null) { - count2 = 0; - } - if (count1 > count2) { - return -1; - } else if (count1 < count2) { - return 1; - } - return 0; - } - }); for (int a = 0; a < stickerSets.size(); a++) { scrollSlidingTabStrip.addStickerTab(stickerSets.get(a).documents.get(0)); } + scrollSlidingTabStrip.addIconTab(R.drawable.ic_settings); scrollSlidingTabStrip.updateTabStyles(); } @@ -1278,16 +1231,6 @@ public class EmojiView extends FrameLayout implements NotificationCenter.Notific stickersUseHistory.put(Long.parseLong(args2[0]), Integer.parseInt(args2[1])); } } - - stickerSetsUseCount.clear(); - str = preferences.getString("sets", ""); - if (str != null && str.length() > 0) { - String[] args = str.split(","); - for (String arg : args) { - String[] args2 = arg.split("="); - stickerSetsUseCount.put(Long.parseLong(args2[0]), Integer.parseInt(args2[1])); - } - } sortStickers(); updateStickerTabs(); } catch (Exception e) { diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Components/PhotoViewerCaptionEnterView.java b/TMessagesProj/src/main/java/org/telegram/ui/Components/PhotoViewerCaptionEnterView.java index 9dc34b602..275ff641e 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Components/PhotoViewerCaptionEnterView.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Components/PhotoViewerCaptionEnterView.java @@ -326,6 +326,11 @@ public class PhotoViewerCaptionEnterView extends FrameLayoutFixed implements Not public void onStickerSelected(TLRPC.Document sticker) { } + + @Override + public void onStickersSettingsClick() { + + } }); sizeNotifierLayout.addView(emojiView); } diff --git a/TMessagesProj/src/main/java/org/telegram/ui/Components/RecyclerListView.java b/TMessagesProj/src/main/java/org/telegram/ui/Components/RecyclerListView.java index 7d29cd0cd..1895f12d9 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/Components/RecyclerListView.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/Components/RecyclerListView.java @@ -40,6 +40,7 @@ public class RecyclerListView extends RecyclerView { private boolean wasPressed; private boolean disallowInterceptTouchEvents; private boolean instantClick; + private Runnable clickRunnable; private static int[] attributes; private static boolean gotAttributes; @@ -69,9 +70,12 @@ public class RecyclerListView extends RecyclerView { view.playSoundEffect(SoundEffectConstants.CLICK); onItemClickListener.onItemClick(view, currentChildPosition); } - AndroidUtilities.runOnUIThread(new Runnable() { + AndroidUtilities.runOnUIThread(clickRunnable = new Runnable() { @Override public void run() { + if (this == clickRunnable) { + clickRunnable = null; + } if (view != null) { view.setPressed(false); if (!instantClick) { @@ -95,10 +99,12 @@ public class RecyclerListView extends RecyclerView { } @Override - public void onLongPress(MotionEvent e) { - if (currentChildView != null && onItemLongClickListener != null) { - if (onItemLongClickListener.onItemClick(currentChildView, currentChildPosition)) { - currentChildView.performHapticFeedback(HapticFeedbackConstants.LONG_PRESS); + public void onLongPress(MotionEvent event) { + if (currentChildView != null) { + if (onItemLongClickListener != null) { + if (onItemLongClickListener.onItemClick(currentChildView, currentChildPosition)) { + currentChildView.performHapticFeedback(HapticFeedbackConstants.LONG_PRESS); + } } } } @@ -106,16 +112,16 @@ public class RecyclerListView extends RecyclerView { } @Override - public boolean onInterceptTouchEvent(RecyclerView view, MotionEvent e) { - int action = e.getActionMasked(); + public boolean onInterceptTouchEvent(RecyclerView view, MotionEvent event) { + int action = event.getActionMasked(); boolean isScrollIdle = RecyclerListView.this.getScrollState() == RecyclerListView.SCROLL_STATE_IDLE; if ((action == MotionEvent.ACTION_DOWN || action == MotionEvent.ACTION_POINTER_DOWN) && currentChildView == null && isScrollIdle) { - currentChildView = view.findChildViewUnder(e.getX(), e.getY()); + currentChildView = view.findChildViewUnder(event.getX(), event.getY()); currentChildPosition = -1; if (currentChildView != null) { currentChildPosition = view.getChildPosition(currentChildView); - MotionEvent childEvent = MotionEvent.obtain(0, 0, e.getActionMasked(), e.getX() - currentChildView.getLeft(), e.getY() - currentChildView.getTop(), 0); + MotionEvent childEvent = MotionEvent.obtain(0, 0, event.getActionMasked(), event.getX() - currentChildView.getLeft(), event.getY() - currentChildView.getTop(), 0); if (currentChildView.onTouchEvent(childEvent)) { interceptedByChild = true; } @@ -125,11 +131,11 @@ public class RecyclerListView extends RecyclerView { if (currentChildView != null && !interceptedByChild) { try { - if (e != null) { - mGestureDetector.onTouchEvent(e); + if (event != null) { + mGestureDetector.onTouchEvent(event); } - } catch (Exception ev) { - FileLog.e("tmessages", ev); + } catch (Exception e) { + FileLog.e("tmessages", e); } } @@ -159,24 +165,34 @@ public class RecyclerListView extends RecyclerView { } @Override - public void onTouchEvent(RecyclerView view, MotionEvent e) { + public void onTouchEvent(RecyclerView view, MotionEvent event) { } @Override public void onRequestDisallowInterceptTouchEvent(boolean disallowIntercept) { - if (selectChildRunnable != null) { - AndroidUtilities.cancelRunOnUIThread(selectChildRunnable); - selectChildRunnable = null; - } - if (currentChildView != null) { - currentChildView.setPressed(false); - currentChildView = null; - } - interceptedByChild = false; + cancelClickRunnables(true); } } + public void cancelClickRunnables(boolean uncheck) { + if (selectChildRunnable != null) { + AndroidUtilities.cancelRunOnUIThread(selectChildRunnable); + selectChildRunnable = null; + } + if (currentChildView != null) { + if (uncheck) { + currentChildView.setPressed(false); + } + currentChildView = null; + } + if (clickRunnable != null) { + AndroidUtilities.cancelRunOnUIThread(clickRunnable); + clickRunnable = null; + } + interceptedByChild = false; + } + private AdapterDataObserver observer = new AdapterDataObserver() { @Override public void onChanged() { diff --git a/TMessagesProj/src/main/java/org/telegram/ui/DialogsActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/DialogsActivity.java index 8c59565c1..8b41a837d 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/DialogsActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/DialogsActivity.java @@ -344,7 +344,9 @@ public class DialogsActivity extends BaseFragment implements NotificationCenter. MessagesController.getInstance().putUsers(users, false); MessagesStorage.getInstance().putUsersAndChats(users, null, false, true); } - dialogsSearchAdapter.putRecentSearch(dialog_id, (TLRPC.User) obj); + if (!onlySelect) { + dialogsSearchAdapter.putRecentSearch(dialog_id, (TLRPC.User) obj); + } } else if (obj instanceof TLRPC.Chat) { if (dialogsSearchAdapter.isGlobalSearch(position)) { ArrayList chats = new ArrayList<>(); @@ -357,10 +359,14 @@ public class DialogsActivity extends BaseFragment implements NotificationCenter. } else { dialog_id = AndroidUtilities.makeBroadcastId(((TLRPC.Chat) obj).id); } - dialogsSearchAdapter.putRecentSearch(dialog_id, (TLRPC.Chat) obj); + if (!onlySelect) { + dialogsSearchAdapter.putRecentSearch(dialog_id, (TLRPC.Chat) obj); + } } else if (obj instanceof TLRPC.EncryptedChat) { dialog_id = ((long) ((TLRPC.EncryptedChat) obj).id) << 32; - dialogsSearchAdapter.putRecentSearch(dialog_id, (TLRPC.EncryptedChat) obj); + if (!onlySelect) { + dialogsSearchAdapter.putRecentSearch(dialog_id, (TLRPC.EncryptedChat) obj); + } } else if (obj instanceof MessageObject) { MessageObject messageObject = (MessageObject) obj; dialog_id = messageObject.getDialogId(); @@ -472,37 +478,51 @@ public class DialogsActivity extends BaseFragment implements NotificationCenter. final TLRPC.Chat chat = MessagesController.getInstance().getChat(-lower_id); CharSequence items[]; if (chat != null && chat.megagroup) { - items = new CharSequence[]{chat == null || !chat.creator ? LocaleController.getString("LeaveMegaMenu", R.string.LeaveMegaMenu) : LocaleController.getString("DeleteMegaMenu", R.string.DeleteMegaMenu)}; + items = new CharSequence[]{LocaleController.getString("ClearHistoryCache", R.string.ClearHistoryCache), chat == null || !chat.creator ? LocaleController.getString("LeaveMegaMenu", R.string.LeaveMegaMenu) : LocaleController.getString("DeleteMegaMenu", R.string.DeleteMegaMenu)}; } else { - items = new CharSequence[]{chat == null || !chat.creator ? LocaleController.getString("LeaveChannelMenu", R.string.LeaveChannelMenu) : LocaleController.getString("ChannelDeleteMenu", R.string.ChannelDeleteMenu)}; + items = new CharSequence[]{LocaleController.getString("ClearHistoryCache", R.string.ClearHistoryCache), chat == null || !chat.creator ? LocaleController.getString("LeaveChannelMenu", R.string.LeaveChannelMenu) : LocaleController.getString("ChannelDeleteMenu", R.string.ChannelDeleteMenu)}; } builder.setItems(items, new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, final int which) { AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); - if (chat != null && chat.megagroup) { - if (!chat.creator) { - builder.setMessage(LocaleController.getString("MegaLeaveAlert", R.string.MegaLeaveAlert)); + if (which == 0) { + if (chat != null && chat.megagroup) { + builder.setMessage(LocaleController.getString("AreYouSureClearHistorySuper", R.string.AreYouSureClearHistorySuper)); } else { - builder.setMessage(LocaleController.getString("MegaDeleteAlert", R.string.MegaDeleteAlert)); + builder.setMessage(LocaleController.getString("AreYouSureClearHistoryChannel", R.string.AreYouSureClearHistoryChannel)); } + builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialogInterface, int i) { + MessagesController.getInstance().deleteDialog(selectedDialog, 2); + } + }); } else { - if (chat == null || !chat.creator) { - builder.setMessage(LocaleController.getString("ChannelLeaveAlert", R.string.ChannelLeaveAlert)); + if (chat != null && chat.megagroup) { + if (!chat.creator) { + builder.setMessage(LocaleController.getString("MegaLeaveAlert", R.string.MegaLeaveAlert)); + } else { + builder.setMessage(LocaleController.getString("MegaDeleteAlert", R.string.MegaDeleteAlert)); + } } else { - builder.setMessage(LocaleController.getString("ChannelDeleteAlert", R.string.ChannelDeleteAlert)); - } - } - builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), new DialogInterface.OnClickListener() { - @Override - public void onClick(DialogInterface dialogInterface, int i) { - MessagesController.getInstance().deleteUserFromChat((int) -selectedDialog, UserConfig.getCurrentUser(), null); - if (AndroidUtilities.isTablet()) { - NotificationCenter.getInstance().postNotificationName(NotificationCenter.closeChats, selectedDialog); + if (chat == null || !chat.creator) { + builder.setMessage(LocaleController.getString("ChannelLeaveAlert", R.string.ChannelLeaveAlert)); + } else { + builder.setMessage(LocaleController.getString("ChannelDeleteAlert", R.string.ChannelDeleteAlert)); } } - }); + builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialogInterface, int i) { + MessagesController.getInstance().deleteUserFromChat((int) -selectedDialog, UserConfig.getCurrentUser(), null); + if (AndroidUtilities.isTablet()) { + NotificationCenter.getInstance().postNotificationName(NotificationCenter.closeChats, selectedDialog); + } + } + }); + } builder.setNegativeButton(LocaleController.getString("Cancel", R.string.Cancel), null); showDialog(builder.create()); } @@ -538,12 +558,12 @@ public class DialogsActivity extends BaseFragment implements NotificationCenter. if (isChat) { TLRPC.Chat currentChat = MessagesController.getInstance().getChat((int) -selectedDialog); if (currentChat != null && ChatObject.isNotInChat(currentChat)) { - MessagesController.getInstance().deleteDialog(selectedDialog, false); + MessagesController.getInstance().deleteDialog(selectedDialog, 0); } else { MessagesController.getInstance().deleteUserFromChat((int) -selectedDialog, MessagesController.getInstance().getUser(UserConfig.getClientUserId()), null); } } else { - MessagesController.getInstance().deleteDialog(selectedDialog, false); + MessagesController.getInstance().deleteDialog(selectedDialog, 0); } if (isBot) { MessagesController.getInstance().blockUser((int) selectedDialog); @@ -552,7 +572,7 @@ public class DialogsActivity extends BaseFragment implements NotificationCenter. NotificationCenter.getInstance().postNotificationName(NotificationCenter.closeChats, selectedDialog); } } else { - MessagesController.getInstance().deleteDialog(selectedDialog, true); + MessagesController.getInstance().deleteDialog(selectedDialog, 1); } } }); diff --git a/TMessagesProj/src/main/java/org/telegram/ui/LaunchActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/LaunchActivity.java index e1f70ceec..8a2753c8e 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/LaunchActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/LaunchActivity.java @@ -359,7 +359,7 @@ public class LaunchActivity extends Activity implements ActionBarLayout.ActionBa NotificationCenter.getInstance().addObserver(this, NotificationCenter.mainUserInfoChanged); NotificationCenter.getInstance().addObserver(this, NotificationCenter.closeOtherAppActivities); NotificationCenter.getInstance().addObserver(this, NotificationCenter.didUpdatedConnectionState); - NotificationCenter.getInstance().addObserver(this, NotificationCenter.spamErrorReceived); + NotificationCenter.getInstance().addObserver(this, NotificationCenter.needShowAlert); if (Build.VERSION.SDK_INT < 14) { NotificationCenter.getInstance().addObserver(this, NotificationCenter.screenStateChanged); } @@ -663,7 +663,7 @@ public class LaunchActivity extends Activity implements ActionBarLayout.ActionBa } } if (sendingText != null) { - if (sendingText.contains("WhatsApp")) { //who needs this sent from ...? + if (sendingText.contains("WhatsApp")) { //remove unnecessary caption 'sent from WhatsApp' from photos forwarded from WhatsApp sendingText = null; } } @@ -1115,7 +1115,11 @@ public class LaunchActivity extends Activity implements ActionBarLayout.ActionBa } else { AlertDialog.Builder builder = new AlertDialog.Builder(LaunchActivity.this); builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); - builder.setMessage(LocaleController.getString("JoinToGroupErrorNotExist", R.string.JoinToGroupErrorNotExist)); + if (error.text.startsWith("FLOOD_WAIT")) { + builder.setMessage(LocaleController.getString("FloodWait", R.string.FloodWait)); + } else { + builder.setMessage(LocaleController.getString("JoinToGroupErrorNotExist", R.string.JoinToGroupErrorNotExist)); + } builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), null); showAlertDialog(builder); } @@ -1123,7 +1127,7 @@ public class LaunchActivity extends Activity implements ActionBarLayout.ActionBa } }); } - }); + }, ConnectionsManager.RequestFlagFailOnServerErrors); } else if (state == 1) { TLRPC.TL_messages_importChatInvite req = new TLRPC.TL_messages_importChatInvite(); req.hash = group; @@ -1147,21 +1151,24 @@ public class LaunchActivity extends Activity implements ActionBarLayout.ActionBa if (actionBarLayout != null) { TLRPC.Updates updates = (TLRPC.Updates) response; if (!updates.chats.isEmpty()) { + TLRPC.Chat chat = updates.chats.get(0); + chat.left = false; + chat.kicked = false; MessagesController.getInstance().putUsers(updates.users, false); MessagesController.getInstance().putChats(updates.chats, false); Bundle args = new Bundle(); - int chat_id = updates.chats.get(0).id; - args.putInt("chat_id", chat_id); + args.putInt("chat_id", chat.id); ChatActivity fragment = new ChatActivity(args); NotificationCenter.getInstance().postNotificationName(NotificationCenter.closeChats); actionBarLayout.presentFragment(fragment, false, true, true); - MessagesController.getInstance().generateJoinMessage(chat_id); } } } else { AlertDialog.Builder builder = new AlertDialog.Builder(LaunchActivity.this); builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); - if (error.text.equals("USERS_TOO_MUCH")) { + if (error.text.startsWith("FLOOD_WAIT")) { + builder.setMessage(LocaleController.getString("FloodWait", R.string.FloodWait)); + } else if (error.text.equals("USERS_TOO_MUCH")) { builder.setMessage(LocaleController.getString("JoinToGroupErrorFull", R.string.JoinToGroupErrorFull)); } else { builder.setMessage(LocaleController.getString("JoinToGroupErrorNotExist", R.string.JoinToGroupErrorNotExist)); @@ -1173,7 +1180,7 @@ public class LaunchActivity extends Activity implements ActionBarLayout.ActionBa } }); } - }); + }, ConnectionsManager.RequestFlagFailOnServerErrors); } } else if (sticker != null) { if (!mainFragmentsStack.isEmpty()) { @@ -1351,7 +1358,7 @@ public class LaunchActivity extends Activity implements ActionBarLayout.ActionBa NotificationCenter.getInstance().removeObserver(this, NotificationCenter.mainUserInfoChanged); NotificationCenter.getInstance().removeObserver(this, NotificationCenter.closeOtherAppActivities); NotificationCenter.getInstance().removeObserver(this, NotificationCenter.didUpdatedConnectionState); - NotificationCenter.getInstance().removeObserver(this, NotificationCenter.spamErrorReceived); + NotificationCenter.getInstance().removeObserver(this, NotificationCenter.needShowAlert); if (Build.VERSION.SDK_INT < 14) { NotificationCenter.getInstance().removeObserver(this, NotificationCenter.screenStateChanged); } @@ -1658,27 +1665,31 @@ public class LaunchActivity extends Activity implements ActionBarLayout.ActionBa onPasscodeResume(); } } - } else if (id == NotificationCenter.spamErrorReceived) { + } else if (id == NotificationCenter.needShowAlert) { final Integer reason = (Integer) args[0]; AlertDialog.Builder builder = new AlertDialog.Builder(this); builder.setTitle(LocaleController.getString("AppName", R.string.AppName)); builder.setPositiveButton(LocaleController.getString("OK", R.string.OK), null); - builder.setNegativeButton(LocaleController.getString("MoreInfo", R.string.MoreInfo), new DialogInterface.OnClickListener() { - @Override - public void onClick(DialogInterface dialogInterface, int i) { - try { - Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse(LocaleController.getString("NobodyLikesSpamUrl", R.string.NobodyLikesSpamUrl))); - intent.putExtra(Browser.EXTRA_APPLICATION_ID, getPackageName()); - startActivity(intent); - } catch (Exception e) { - FileLog.e("tmessages", e); + if (reason != 2) { + builder.setNegativeButton(LocaleController.getString("MoreInfo", R.string.MoreInfo), new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialogInterface, int i) { + try { + Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse(LocaleController.getString("NobodyLikesSpamUrl", R.string.NobodyLikesSpamUrl))); + intent.putExtra(Browser.EXTRA_APPLICATION_ID, getPackageName()); + startActivity(intent); + } catch (Exception e) { + FileLog.e("tmessages", e); + } } - } - }); + }); + } if (reason == 0) { builder.setMessage(LocaleController.getString("NobodyLikesSpam1", R.string.NobodyLikesSpam1)); } else if (reason == 1) { builder.setMessage(LocaleController.getString("NobodyLikesSpam2", R.string.NobodyLikesSpam2)); + } else if (reason == 2) { + builder.setMessage((String) args[1]); } if (!mainFragmentsStack.isEmpty()) { mainFragmentsStack.get(mainFragmentsStack.size() - 1).showDialog(builder.create()); diff --git a/TMessagesProj/src/main/java/org/telegram/ui/ManageSpaceActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/ManageSpaceActivity.java new file mode 100644 index 000000000..2ab8d920d --- /dev/null +++ b/TMessagesProj/src/main/java/org/telegram/ui/ManageSpaceActivity.java @@ -0,0 +1,380 @@ +/* + * This is the source code of Telegram for Android v. 3.x.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-2015. + */ + +package org.telegram.ui; + +import android.app.Activity; +import android.content.Intent; +import android.content.res.Configuration; +import android.os.Build; +import android.os.Bundle; +import android.view.MotionEvent; +import android.view.View; +import android.view.ViewGroup; +import android.view.ViewTreeObserver; +import android.view.Window; +import android.view.WindowManager; +import android.widget.FrameLayout; +import android.widget.ImageView; +import android.widget.RelativeLayout; + +import org.telegram.messenger.AndroidUtilities; +import org.telegram.messenger.ApplicationLoader; +import org.telegram.messenger.LocaleController; +import org.telegram.messenger.NotificationCenter; +import org.telegram.messenger.R; +import org.telegram.tgnet.ConnectionsManager; +import org.telegram.ui.ActionBar.ActionBarLayout; +import org.telegram.ui.ActionBar.BaseFragment; +import org.telegram.ui.ActionBar.DrawerLayoutContainer; +import org.telegram.ui.Components.LayoutHelper; + +import java.util.ArrayList; + +public class ManageSpaceActivity extends Activity implements ActionBarLayout.ActionBarLayoutDelegate { + + private boolean finished; + private int currentConnectionState; + private static ArrayList mainFragmentsStack = new ArrayList<>(); + private static ArrayList layerFragmentsStack = new ArrayList<>(); + + private ActionBarLayout actionBarLayout; + private ActionBarLayout layersActionBarLayout; + protected DrawerLayoutContainer drawerLayoutContainer; + + @Override + protected void onCreate(Bundle savedInstanceState) { + ApplicationLoader.postInitApplication(); + + requestWindowFeature(Window.FEATURE_NO_TITLE); + setTheme(R.style.Theme_TMessages); + getWindow().setBackgroundDrawableResource(R.drawable.transparent); + + super.onCreate(savedInstanceState); + + int resourceId = getResources().getIdentifier("status_bar_height", "dimen", "android"); + if (resourceId > 0) { + AndroidUtilities.statusBarHeight = getResources().getDimensionPixelSize(resourceId); + } + + actionBarLayout = new ActionBarLayout(this); + + drawerLayoutContainer = new DrawerLayoutContainer(this); + drawerLayoutContainer.setAllowOpenDrawer(false, false); + setContentView(drawerLayoutContainer, new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT)); + + if (AndroidUtilities.isTablet()) { + getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE); + + RelativeLayout launchLayout = new RelativeLayout(this); + drawerLayoutContainer.addView(launchLayout); + FrameLayout.LayoutParams layoutParams1 = (FrameLayout.LayoutParams) launchLayout.getLayoutParams(); + layoutParams1.width = LayoutHelper.MATCH_PARENT; + layoutParams1.height = LayoutHelper.MATCH_PARENT; + launchLayout.setLayoutParams(layoutParams1); + + ImageView backgroundTablet = new ImageView(this); + backgroundTablet.setScaleType(ImageView.ScaleType.CENTER_CROP); + backgroundTablet.setImageResource(R.drawable.cats); + launchLayout.addView(backgroundTablet); + RelativeLayout.LayoutParams relativeLayoutParams = (RelativeLayout.LayoutParams) backgroundTablet.getLayoutParams(); + relativeLayoutParams.width = LayoutHelper.MATCH_PARENT; + relativeLayoutParams.height = LayoutHelper.MATCH_PARENT; + backgroundTablet.setLayoutParams(relativeLayoutParams); + + launchLayout.addView(actionBarLayout); + relativeLayoutParams = (RelativeLayout.LayoutParams) actionBarLayout.getLayoutParams(); + relativeLayoutParams.width = LayoutHelper.MATCH_PARENT; + relativeLayoutParams.height = LayoutHelper.MATCH_PARENT; + actionBarLayout.setLayoutParams(relativeLayoutParams); + + FrameLayout shadowTablet = new FrameLayout(this); + shadowTablet.setBackgroundColor(0x7F000000); + launchLayout.addView(shadowTablet); + relativeLayoutParams = (RelativeLayout.LayoutParams) shadowTablet.getLayoutParams(); + relativeLayoutParams.width = LayoutHelper.MATCH_PARENT; + relativeLayoutParams.height = LayoutHelper.MATCH_PARENT; + shadowTablet.setLayoutParams(relativeLayoutParams); + shadowTablet.setOnTouchListener(new View.OnTouchListener() { + @Override + public boolean onTouch(View v, MotionEvent event) { + if (!actionBarLayout.fragmentsStack.isEmpty() && event.getAction() == MotionEvent.ACTION_UP) { + float x = event.getX(); + float y = event.getY(); + int location[] = new int[2]; + layersActionBarLayout.getLocationOnScreen(location); + int viewX = location[0]; + int viewY = location[1]; + + if (layersActionBarLayout.checkTransitionAnimation() || x > viewX && x < viewX + layersActionBarLayout.getWidth() && y > viewY && y < viewY + layersActionBarLayout.getHeight()) { + return false; + } else { + if (!layersActionBarLayout.fragmentsStack.isEmpty()) { + for (int a = 0; a < layersActionBarLayout.fragmentsStack.size() - 1; a++) { + layersActionBarLayout.removeFragmentFromStack(layersActionBarLayout.fragmentsStack.get(0)); + a--; + } + layersActionBarLayout.closeLastFragment(true); + } + return true; + } + } + return false; + } + }); + + shadowTablet.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + + } + }); + + layersActionBarLayout = new ActionBarLayout(this); + layersActionBarLayout.setRemoveActionBarExtraHeight(true); + layersActionBarLayout.setBackgroundView(shadowTablet); + layersActionBarLayout.setUseAlphaAnimations(true); + layersActionBarLayout.setBackgroundResource(R.drawable.boxshadow); + launchLayout.addView(layersActionBarLayout); + relativeLayoutParams = (RelativeLayout.LayoutParams)layersActionBarLayout.getLayoutParams(); + relativeLayoutParams.width = AndroidUtilities.dp(530); + relativeLayoutParams.height = AndroidUtilities.dp(528); + layersActionBarLayout.setLayoutParams(relativeLayoutParams); + layersActionBarLayout.init(layerFragmentsStack); + layersActionBarLayout.setDelegate(this); + layersActionBarLayout.setDrawerLayoutContainer(drawerLayoutContainer); + } else { + drawerLayoutContainer.addView(actionBarLayout, new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT)); + } + + // drawerLayoutContainer.setDrawerLayout(listView); + + drawerLayoutContainer.setParentActionBarLayout(actionBarLayout); + actionBarLayout.setDrawerLayoutContainer(drawerLayoutContainer); + actionBarLayout.init(mainFragmentsStack); + actionBarLayout.setDelegate(this); + + NotificationCenter.getInstance().postNotificationName(NotificationCenter.closeOtherAppActivities, this); + currentConnectionState = ConnectionsManager.getInstance().getConnectionState(); + + handleIntent(getIntent(), false, savedInstanceState != null, false); + needLayout(); + } + + private boolean handleIntent(Intent intent, boolean isNew, boolean restore, boolean fromPassword) { + if (AndroidUtilities.isTablet()) { + if (layersActionBarLayout.fragmentsStack.isEmpty()) { + layersActionBarLayout.addFragmentToStack(new CacheControlActivity()); + } + } else { + if (actionBarLayout.fragmentsStack.isEmpty()) { + actionBarLayout.addFragmentToStack(new CacheControlActivity()); + } + } + actionBarLayout.showLastFragment(); + if (AndroidUtilities.isTablet()) { + layersActionBarLayout.showLastFragment(); + } + intent.setAction(null); + return false; + } + + @Override + public boolean onPreIme() { + return false; + } + + @Override + protected void onNewIntent(Intent intent) { + super.onNewIntent(intent); + handleIntent(intent, true, false, false); + } + + private void onFinish() { + if (finished) { + return; + } + finished = true; + } + + public void presentFragment(BaseFragment fragment) { + actionBarLayout.presentFragment(fragment); + } + + public boolean presentFragment(final BaseFragment fragment, final boolean removeLast, boolean forceWithoutAnimation) { + return actionBarLayout.presentFragment(fragment, removeLast, forceWithoutAnimation, true); + } + + public void needLayout() { + if (AndroidUtilities.isTablet()) { + RelativeLayout.LayoutParams relativeLayoutParams = (RelativeLayout.LayoutParams)layersActionBarLayout.getLayoutParams(); + relativeLayoutParams.leftMargin = (AndroidUtilities.displaySize.x - relativeLayoutParams.width) / 2; + int y = (Build.VERSION.SDK_INT >= 21 ? AndroidUtilities.statusBarHeight : 0); + relativeLayoutParams.topMargin = y + (AndroidUtilities.displaySize.y - relativeLayoutParams.height - y) / 2; + layersActionBarLayout.setLayoutParams(relativeLayoutParams); + + + if (!AndroidUtilities.isSmallTablet() || getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) { + int leftWidth = AndroidUtilities.displaySize.x / 100 * 35; + if (leftWidth < AndroidUtilities.dp(320)) { + leftWidth = AndroidUtilities.dp(320); + } + + relativeLayoutParams = (RelativeLayout.LayoutParams) actionBarLayout.getLayoutParams(); + relativeLayoutParams.width = leftWidth; + relativeLayoutParams.height = LayoutHelper.MATCH_PARENT; + actionBarLayout.setLayoutParams(relativeLayoutParams); + + if (AndroidUtilities.isSmallTablet() && actionBarLayout.fragmentsStack.size() == 2) { + BaseFragment chatFragment = actionBarLayout.fragmentsStack.get(1); + chatFragment.onPause(); + actionBarLayout.fragmentsStack.remove(1); + actionBarLayout.showLastFragment(); + } + } else { + relativeLayoutParams = (RelativeLayout.LayoutParams) actionBarLayout.getLayoutParams(); + relativeLayoutParams.width = LayoutHelper.MATCH_PARENT; + relativeLayoutParams.height = LayoutHelper.MATCH_PARENT; + actionBarLayout.setLayoutParams(relativeLayoutParams); + } + } + } + + public void fixLayout() { + if (!AndroidUtilities.isTablet()) { + return; + } + if (actionBarLayout == null) { + return; + } + actionBarLayout.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() { + @Override + public void onGlobalLayout() { + needLayout(); + if (actionBarLayout != null) { + if (Build.VERSION.SDK_INT < 16) { + actionBarLayout.getViewTreeObserver().removeGlobalOnLayoutListener(this); + } else { + actionBarLayout.getViewTreeObserver().removeOnGlobalLayoutListener(this); + } + } + } + }); + } + + @Override + protected void onPause() { + super.onPause(); + actionBarLayout.onPause(); + if (AndroidUtilities.isTablet()) { + layersActionBarLayout.onPause(); + } + } + + @Override + protected void onDestroy() { + super.onDestroy(); + onFinish(); + } + + @Override + protected void onResume() { + super.onResume(); + actionBarLayout.onResume(); + if (AndroidUtilities.isTablet()) { + layersActionBarLayout.onResume(); + } + } + + @Override + public void onConfigurationChanged(android.content.res.Configuration newConfig) { + AndroidUtilities.checkDisplaySize(); + super.onConfigurationChanged(newConfig); + fixLayout(); + } + + private void updateCurrentConnectionState() { + String text = null; + if (currentConnectionState == ConnectionsManager.ConnectionStateWaitingForNetwork) { + text = LocaleController.getString("WaitingForNetwork", R.string.WaitingForNetwork); + } else if (currentConnectionState == ConnectionsManager.ConnectionStateConnecting) { + text = LocaleController.getString("Connecting", R.string.Connecting); + } else if (currentConnectionState == ConnectionsManager.ConnectionStateUpdating) { + text = LocaleController.getString("Updating", R.string.Updating); + } + actionBarLayout.setTitleOverlayText(text); + } + + @Override + public void onBackPressed() { + if (PhotoViewer.getInstance().isVisible()) { + PhotoViewer.getInstance().closePhoto(true, false); + } else if (drawerLayoutContainer.isDrawerOpened()) { + drawerLayoutContainer.closeDrawer(false); + } else if (AndroidUtilities.isTablet()) { + if (layersActionBarLayout.getVisibility() == View.VISIBLE) { + layersActionBarLayout.onBackPressed(); + } else { + actionBarLayout.onBackPressed(); + } + } else { + actionBarLayout.onBackPressed(); + } + } + + @Override + public void onLowMemory() { + super.onLowMemory(); + actionBarLayout.onLowMemory(); + if (AndroidUtilities.isTablet()) { + layersActionBarLayout.onLowMemory(); + } + } + + @Override + public boolean needPresentFragment(BaseFragment fragment, boolean removeLast, boolean forceWithoutAnimation, ActionBarLayout layout) { + return true; + } + + @Override + public boolean needAddFragmentToStack(BaseFragment fragment, ActionBarLayout layout) { + return true; + } + + @Override + public boolean needCloseLastFragment(ActionBarLayout layout) { + if (AndroidUtilities.isTablet()) { + if (layout == actionBarLayout && layout.fragmentsStack.size() <= 1) { + onFinish(); + finish(); + return false; + } else if (layout == layersActionBarLayout && actionBarLayout.fragmentsStack.isEmpty() && layersActionBarLayout.fragmentsStack.size() == 1) { + onFinish(); + finish(); + return false; + } + } else { + if (layout.fragmentsStack.size() <= 1) { + onFinish(); + finish(); + return false; + } + } + return true; + } + + @Override + public void onRebuildAllFragments(ActionBarLayout layout) { + if (AndroidUtilities.isTablet()) { + if (layout == layersActionBarLayout) { + actionBarLayout.rebuildAllFragmentViews(true); + actionBarLayout.showLastFragment(); + } + } + } +} diff --git a/TMessagesProj/src/main/java/org/telegram/ui/PhotoViewer.java b/TMessagesProj/src/main/java/org/telegram/ui/PhotoViewer.java index c960c973f..b218a2f95 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/PhotoViewer.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/PhotoViewer.java @@ -739,14 +739,14 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat if (uid == currentDialogId || uid == mergeDialogId) { if (uid == currentDialogId) { totalImagesCount = (Integer) args[1]; - if ((Boolean) args[2]) { + /*if ((Boolean) args[2]) { SharedMediaQuery.getMediaCount(currentDialogId, SharedMediaQuery.MEDIA_PHOTOVIDEO, classGuid, false); - } + }*/ } else if (uid == mergeDialogId) { totalImagesCountMerge = (Integer) args[1]; - if ((Boolean) args[2]) { + /*if ((Boolean) args[2]) { SharedMediaQuery.getMediaCount(mergeDialogId, SharedMediaQuery.MEDIA_PHOTOVIDEO, classGuid, false); - } + }*/ } if (needSearchImageInArr && isFirstLoading) { isFirstLoading = false; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/ProfileActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/ProfileActivity.java index 7148ee752..15a08cf4f 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/ProfileActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/ProfileActivity.java @@ -2168,7 +2168,7 @@ public class ProfileActivity extends BaseFragment implements NotificationCenter. if (chat.creator && chat_id > 0) { item.addSubItem(set_admins, LocaleController.getString("SetAdmins", R.string.SetAdmins), 0); } - if (chat.creator || chat.admin) { + if (!chat.admins_enabled || chat.creator || chat.admin) { item.addSubItem(edit_name, LocaleController.getString("EditName", R.string.EditName), 0); } item.addSubItem(leave_group, LocaleController.getString("DeleteAndExit", R.string.DeleteAndExit), 0); diff --git a/TMessagesProj/src/main/java/org/telegram/ui/SettingsActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/SettingsActivity.java index 61f4d19a5..a341fe7c2 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/SettingsActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/SettingsActivity.java @@ -132,6 +132,7 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter private int messagesSectionRow2; private int textSizeRow; private int stickersRow; + private int cacheRow; private int sendByEnterRow; private int supportSectionRow; private int supportSectionRow2; @@ -243,6 +244,7 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter messagesSectionRow2 = rowCount++; textSizeRow = rowCount++; stickersRow = rowCount++; + cacheRow = rowCount++; sendByEnterRow = rowCount++; supportSectionRow = rowCount++; supportSectionRow2 = rowCount++; @@ -559,6 +561,8 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter presentFragment(new ChangePhoneHelpActivity()); } else if (i == stickersRow) { presentFragment(new StickersActivity()); + } else if (i == cacheRow) { + presentFragment(new CacheControlActivity()); } } }); @@ -1069,7 +1073,7 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter i == askQuestionRow || i == sendLogsRow || i == sendByEnterRow || i == privacyRow || i == wifiDownloadRow || i == mobileDownloadRow || i == clearLogsRow || i == roamingDownloadRow || i == languageRow || i == usernameRow || i == switchBackendButtonRow || i == telegramFaqRow || i == contactsSortRow || i == contactsReimportRow || i == saveToGalleryRow || - i == stickersRow; + i == stickersRow || i == cacheRow; } @Override @@ -1151,6 +1155,8 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter textCell.setText(LocaleController.getString("ImportContacts", R.string.ImportContacts), true); } else if (i == stickersRow) { textCell.setText(LocaleController.getString("Stickers", R.string.Stickers), true); + } else if (i == cacheRow) { + textCell.setText(LocaleController.getString("CacheSettings", R.string.CacheSettings), true); } } else if (type == 3) { if (view == null) { @@ -1269,7 +1275,7 @@ public class SettingsActivity extends BaseFragment implements NotificationCenter return 1; } else if (i == enableAnimationsRow || i == sendByEnterRow || i == saveToGalleryRow) { return 3; - } else if (i == notificationRow || i == backgroundRow || i == askQuestionRow || i == sendLogsRow || i == privacyRow || i == clearLogsRow || i == switchBackendButtonRow || i == telegramFaqRow || i == contactsReimportRow || i == textSizeRow || i == languageRow || i == contactsSortRow || i == stickersRow) { + } else if (i == notificationRow || i == backgroundRow || i == askQuestionRow || i == sendLogsRow || i == privacyRow || i == clearLogsRow || i == switchBackendButtonRow || i == telegramFaqRow || i == contactsReimportRow || i == textSizeRow || i == languageRow || i == contactsSortRow || i == stickersRow || i == cacheRow) { return 2; } else if (i == versionRow) { return 5; diff --git a/TMessagesProj/src/main/java/org/telegram/ui/StickersActivity.java b/TMessagesProj/src/main/java/org/telegram/ui/StickersActivity.java index 7721b5f19..5c2b3b7e2 100644 --- a/TMessagesProj/src/main/java/org/telegram/ui/StickersActivity.java +++ b/TMessagesProj/src/main/java/org/telegram/ui/StickersActivity.java @@ -12,15 +12,14 @@ import android.app.AlertDialog; import android.content.Context; import android.content.DialogInterface; import android.content.Intent; +import android.graphics.Canvas; import android.os.Build; import android.os.Message; import android.text.SpannableStringBuilder; import android.text.Spanned; import android.view.View; import android.view.ViewGroup; -import android.widget.AdapterView; import android.widget.FrameLayout; -import android.widget.ListView; import android.widget.Toast; import org.telegram.messenger.LocaleController; @@ -30,13 +29,19 @@ import org.telegram.messenger.query.StickersQuery; import org.telegram.messenger.ApplicationLoader; import org.telegram.messenger.FileLog; import org.telegram.messenger.R; +import org.telegram.messenger.support.widget.LinearLayoutManager; +import org.telegram.messenger.support.widget.RecyclerView; +import org.telegram.messenger.support.widget.helper.ItemTouchHelper; +import org.telegram.tgnet.ConnectionsManager; +import org.telegram.tgnet.RequestDelegate; +import org.telegram.tgnet.TLObject; import org.telegram.tgnet.TLRPC; import org.telegram.ui.ActionBar.ActionBar; import org.telegram.ui.ActionBar.BaseFragment; -import org.telegram.ui.Adapters.BaseFragmentAdapter; import org.telegram.ui.Cells.StickerSetCell; import org.telegram.ui.Cells.TextInfoPrivacyCell; import org.telegram.ui.Components.LayoutHelper; +import org.telegram.ui.Components.RecyclerListView; import org.telegram.ui.Components.StickersAlert; import org.telegram.ui.Components.URLSpanNoUnderline; @@ -45,13 +50,68 @@ import java.util.Locale; public class StickersActivity extends BaseFragment implements NotificationCenter.NotificationCenterDelegate { + private RecyclerListView listView; private ListAdapter listAdapter; + private boolean needReorder; + private int stickersStartRow; private int stickersEndRow; private int stickersInfoRow; private int rowCount; + public class TouchHelperCallback extends ItemTouchHelper.Callback { + + public static final float ALPHA_FULL = 1.0f; + + @Override + public boolean isLongPressDragEnabled() { + return true; + } + + @Override + public int getMovementFlags(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder) { + if (viewHolder.getItemViewType() != 0) { + return makeMovementFlags(0, 0); + } + return makeMovementFlags(ItemTouchHelper.UP | ItemTouchHelper.DOWN, 0); + } + + @Override + public boolean onMove(RecyclerView recyclerView, RecyclerView.ViewHolder source, RecyclerView.ViewHolder target) { + if (source.getItemViewType() != target.getItemViewType()) { + return false; + } + listAdapter.swapElements(source.getAdapterPosition(), target.getAdapterPosition()); + return true; + } + + @Override + public void onChildDraw(Canvas c, RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder, float dX, float dY, int actionState, boolean isCurrentlyActive) { + super.onChildDraw(c, recyclerView, viewHolder, dX, dY, actionState, isCurrentlyActive); + } + + @Override + public void onSelectedChanged(RecyclerView.ViewHolder viewHolder, int actionState) { + if (actionState != ItemTouchHelper.ACTION_STATE_IDLE) { + listView.cancelClickRunnables(false); + viewHolder.itemView.setPressed(true); + } + super.onSelectedChanged(viewHolder, actionState); + } + + @Override + public void onSwiped(RecyclerView.ViewHolder viewHolder, int direction) { + + } + + @Override + public void clearView(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder) { + super.clearView(recyclerView, viewHolder); + viewHolder.itemView.setPressed(false); + } + } + @Override public boolean onFragmentCreate() { super.onFragmentCreate(); @@ -64,7 +124,7 @@ public class StickersActivity extends BaseFragment implements NotificationCenter @Override public void onFragmentDestroy() { super.onFragmentDestroy(); - NotificationCenter.getInstance().removeObserver(this, NotificationCenter.stickersDidLoaded); + sendReorder(); } @Override @@ -87,18 +147,21 @@ public class StickersActivity extends BaseFragment implements NotificationCenter FrameLayout frameLayout = (FrameLayout) fragmentView; frameLayout.setBackgroundColor(0xfff0f0f0); - ListView listView = new ListView(context); - listView.setDivider(null); - listView.setDividerHeight(0); - listView.setVerticalScrollBarEnabled(false); - listView.setDrawSelectorOnTop(true); + listView = new RecyclerListView(context); + LinearLayoutManager layoutManager = new LinearLayoutManager(context); + layoutManager.setOrientation(LinearLayoutManager.VERTICAL); + listView.setLayoutManager(layoutManager); + ItemTouchHelper itemTouchHelper = new ItemTouchHelper(new TouchHelperCallback()); + itemTouchHelper.attachToRecyclerView(listView); + frameLayout.addView(listView, LayoutHelper.createFrame(LayoutHelper.MATCH_PARENT, LayoutHelper.MATCH_PARENT)); listView.setAdapter(listAdapter); - listView.setOnItemClickListener(new AdapterView.OnItemClickListener() { + listView.setOnItemClickListener(new RecyclerListView.OnItemClickListener() { @Override - public void onItemClick(AdapterView adapterView, View view, final int i, long l) { - if (i >= stickersStartRow && i < stickersEndRow && getParentActivity() != null) { - final TLRPC.TL_messages_stickerSet stickerSet = StickersQuery.getStickerSets().get(i); + public void onItemClick(View view, int position) { + if (position >= stickersStartRow && position < stickersEndRow && getParentActivity() != null) { + sendReorder(); + final TLRPC.TL_messages_stickerSet stickerSet = StickersQuery.getStickerSets().get(position); ArrayList stickers = stickerSet.documents; if (stickers == null || stickers.isEmpty()) { return; @@ -129,6 +192,26 @@ public class StickersActivity extends BaseFragment implements NotificationCenter } } + private void sendReorder() { + if (!needReorder) { + return; + } + StickersQuery.calcNewHash(); + needReorder = false; + TLRPC.TL_messages_reorderStickerSets req = new TLRPC.TL_messages_reorderStickerSets(); + ArrayList arrayList = StickersQuery.getStickerSets(); + for (int a = 0; a < arrayList.size(); a++) { + req.order.add(arrayList.get(a).set.id); + } + ConnectionsManager.getInstance().sendRequest(req, new RequestDelegate() { + @Override + public void run(TLObject response, TLRPC.TL_error error) { + + } + }); + NotificationCenter.getInstance().postNotificationName(NotificationCenter.stickersDidLoaded); + } + private void updateRows() { rowCount = 0; ArrayList stickerSets = StickersQuery.getStickerSets(); @@ -154,43 +237,36 @@ public class StickersActivity extends BaseFragment implements NotificationCenter } } - private class ListAdapter extends BaseFragmentAdapter { + private class ListAdapter extends RecyclerListView.Adapter { private Context mContext; + private class Holder extends RecyclerView.ViewHolder { + + public Holder(View itemView) { + super(itemView); + } + } + public ListAdapter(Context context) { mContext = context; } @Override - public boolean areAllItemsEnabled() { - return false; - } - - @Override - public boolean isEnabled(int i) { - return i >= stickersStartRow && i < stickersEndRow; - } - - @Override - public int getCount() { + public int getItemCount() { return rowCount; } - @Override - public Object getItem(int i) { - return null; - } - @Override public long getItemId(int i) { + if (i >= stickersStartRow && i < stickersEndRow) { + ArrayList arrayList = StickersQuery.getStickerSets(); + return arrayList.get(i).set.id; + } else if (i == stickersInfoRow) { + return Integer.MIN_VALUE; + } return i; } - @Override - public boolean hasStableIds() { - return false; - } - private void processSelectionOption(int which, TLRPC.TL_messages_stickerSet stickerSet) { if (which == 0) { StickersQuery.removeStickersSet(getParentActivity(), stickerSet.set, !stickerSet.set.disabled ? 1 : 2); @@ -223,15 +299,25 @@ public class StickersActivity extends BaseFragment implements NotificationCenter } @Override - public View getView(int i, View view, ViewGroup viewGroup) { - int type = getItemViewType(i); - if (type == 0) { - if (view == null) { + public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) { + if (holder.getItemViewType() == 0) { + ArrayList arrayList = StickersQuery.getStickerSets(); + ((StickerSetCell) holder.itemView).setStickersSet(arrayList.get(position), position != arrayList.size() - 1); + } + } + + @Override + public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { + View view = null; + switch (viewType) { + case 0: view = new StickerSetCell(mContext); view.setBackgroundColor(0xffffffff); + view.setBackgroundResource(R.drawable.list_selector_white); ((StickerSetCell) view).setOnOptionsClick(new View.OnClickListener() { @Override public void onClick(View v) { + sendReorder(); StickerSetCell cell = (StickerSetCell) v.getParent(); final TLRPC.TL_messages_stickerSet stickerSet = cell.getStickersSet(); AlertDialog.Builder builder = new AlertDialog.Builder(getParentActivity()); @@ -239,11 +325,9 @@ public class StickersActivity extends BaseFragment implements NotificationCenter CharSequence[] items; final int[] options; if (stickerSet.set.official) { - options = new int[]{0, 2, 3}; + options = new int[]{0}; items = new CharSequence[]{ - !stickerSet.set.disabled ? LocaleController.getString("StickersHide", R.string.StickersHide) : LocaleController.getString("StickersShow", R.string.StickersShow), - LocaleController.getString("StickersShare", R.string.StickersShare), - LocaleController.getString("StickersCopy", R.string.StickersCopy), + !stickerSet.set.disabled ? LocaleController.getString("StickersHide", R.string.StickersHide) : LocaleController.getString("StickersShow", R.string.StickersShow) }; } else { options = new int[]{0, 1, 2, 3}; @@ -263,11 +347,8 @@ public class StickersActivity extends BaseFragment implements NotificationCenter showDialog(builder.create()); } }); - } - ArrayList arrayList = StickersQuery.getStickerSets(); - ((StickerSetCell) view).setStickersSet(arrayList.get(i), i != arrayList.size() - 1); - } else if (type == 1) { - if (view == null) { + break; + case 1: view = new TextInfoPrivacyCell(mContext); String text = LocaleController.getString("StickersInfo", R.string.StickersInfo); String botName = "@stickers"; @@ -291,9 +372,9 @@ public class StickersActivity extends BaseFragment implements NotificationCenter ((TextInfoPrivacyCell) view).setText(text); } view.setBackgroundResource(R.drawable.greydivider_bottom); - } + break; } - return view; + return new Holder(view); } @Override @@ -306,14 +387,15 @@ public class StickersActivity extends BaseFragment implements NotificationCenter return 0; } - @Override - public int getViewTypeCount() { - return 2; - } - - @Override - public boolean isEmpty() { - return false; + public void swapElements(int fromIndex, int toIndex) { + if (fromIndex != toIndex) { + needReorder = true; + } + ArrayList arrayList = StickersQuery.getStickerSets(); + TLRPC.TL_messages_stickerSet from = arrayList.get(fromIndex); + arrayList.set(fromIndex, arrayList.get(toIndex)); + arrayList.set(toIndex, from); + notifyItemMoved(fromIndex, toIndex); } } } diff --git a/TMessagesProj/src/main/res/drawable-hdpi/ic_settings.png b/TMessagesProj/src/main/res/drawable-hdpi/ic_settings.png new file mode 100644 index 000000000..e999e3293 Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-hdpi/ic_settings.png differ diff --git a/TMessagesProj/src/main/res/drawable-mdpi/ic_settings.png b/TMessagesProj/src/main/res/drawable-mdpi/ic_settings.png new file mode 100644 index 000000000..1d60c823c Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-mdpi/ic_settings.png differ diff --git a/TMessagesProj/src/main/res/drawable-v21/list_selector_white.xml b/TMessagesProj/src/main/res/drawable-v21/list_selector_white.xml new file mode 100644 index 000000000..5dbf2961f --- /dev/null +++ b/TMessagesProj/src/main/res/drawable-v21/list_selector_white.xml @@ -0,0 +1,14 @@ + + + + + + + diff --git a/TMessagesProj/src/main/res/drawable-xhdpi/ic_settings.png b/TMessagesProj/src/main/res/drawable-xhdpi/ic_settings.png new file mode 100644 index 000000000..c2d1c30b0 Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-xhdpi/ic_settings.png differ diff --git a/TMessagesProj/src/main/res/drawable-xxhdpi/ic_settings.png b/TMessagesProj/src/main/res/drawable-xxhdpi/ic_settings.png new file mode 100644 index 000000000..c95355277 Binary files /dev/null and b/TMessagesProj/src/main/res/drawable-xxhdpi/ic_settings.png differ diff --git a/TMessagesProj/src/main/res/drawable/list_selector_white.xml b/TMessagesProj/src/main/res/drawable/list_selector_white.xml new file mode 100644 index 000000000..160ae131a --- /dev/null +++ b/TMessagesProj/src/main/res/drawable/list_selector_white.xml @@ -0,0 +1,19 @@ + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/TMessagesProj/src/main/res/values-ar/strings.xml b/TMessagesProj/src/main/res/values-ar/strings.xml index 370d5d863..a6d96cc94 100644 --- a/TMessagesProj/src/main/res/values-ar/strings.xml +++ b/TMessagesProj/src/main/res/values-ar/strings.xml @@ -46,6 +46,7 @@ %s قام بالدخول للمحادثة السرية. لقد قمت بالدخول للمحادثة السرية. مسح سجل المحادثات + حذف من الذاكرة المخبئية حذف وخروج حذف المحادثة حساب محذوف @@ -437,7 +438,6 @@ سجل الخروج من كافة الأجهزة الأخرى الأحداث اشترك صديق في تيليجرام - PEBBLE اللغة نرجو الأخذ بالعلم أن الدعم الفني في تيليجرام يقوم به مجموعة من المتطوعين. نحن نحاول الرد بسرعة قدر المستطاع، لكن ربما نستغرق القليل من الوقت.
]]> صفحة الأسئلة الأكثر شيوعًا]]>: يوجد بها حلول للمشاكل وإجابات لمعظم الأسئلة.
اسأل أحد المتطوعين @@ -499,6 +499,24 @@ الأوقات خلال دقائق + + إعدادات الذاكرة المخبئية + قاعدة البيانات على الجهاز + هل ترغب في مسح الرسائل المحفوظة في الذاكرة المخبئية؟ + مسح قاعدة البيانات على الجهاز سيحذف الرسائل التي تم تنزيلها على جهازك ويقوم بضغط قاعدة البيانات لتوفير مساحة على جهازك. تيليجرام يحتاج لبعض البيانات ليعمل، لذلك حجم قاعدة البيانات لن يصل إلى صفر.\n\nهذه العملية ربما تأخذ عدة دقائق لتتم. + مسح الذاكرة المخبئية + مسح + جاري الحساب... + المستندات + الصور + الرسائل الصوتية + المقاطع المرئية + الموسيقى + الملفات الأخرى + إفراغ + الإحتفاظ بالوسائط + الصور، المقاطع المرئية، وجميع الملفات المحفوظة في خوادمنا التي لم تستخدمها ]]> خلال هذه المدة سيتم حذفها لتوفير المساحة. ملفات الوسائط ستبقى في خوادم تيليجرام ويمكنك إعادة تنزيلها متى ما احتجتها مرة أخرى. + إلى الأبد الأجهزة المسجّل دخول منها الجهاز الحالي @@ -781,6 +799,8 @@ هل أنت متأكد من أنك تريد بدء محادثة سرية؟ هل أنت متأكد من رغبتك في إلغاء التسجيل؟ هل أنت متأكد من رغبتك في حذف سجل المحادثات؟ + حذف كافة المحادثات والوسائط المتعلقة بهذه القناة من الذاكرة المخبئية؟ + حذف كافة المحادثات والوسائط المتعلقة بهذه المجموعة الخارقة من الذاكرة المخبئية؟ هل أنت متأكد من رغبتك في حذف %1$s؟ هل ترغب في إرسال رسالة إلى %1$s؟ أرسل جهة الاتصال إلى %1$s؟ @@ -1010,6 +1030,7 @@ h:mm a %1$s الساعة %2$s - تم تحديث تيليجرام على الأندرويد. الجديد في النسخة رقم 3.3.0:\n\n- المجموعات الآن يمكن أن يكون بها عدة مشرفين يمكنهم تغيير اسمها وشعارها وإضافة وإزالة الأعضاء.\n- المجموعات التي وصلت إلى ٢٠٠ عضو يمكن ترقيتها لتصبح مجموعة خارقة تصل إلى ١٠٠٠ عضو.\n- إضافة زر للمشاركة السريعة من خلال القنوات بجانب الرسائل.\n\nللإستزادة عن هذا التحديث من هنا:\nhttps://telegram.org/blog/supergroups - 677 + تيليجرام نسخة الأندرويد تم تحديثه. الجديد في نسخة ٣.٢.٢:\n\n- إدارة للذاكرة المخبئية: إمكانية التحكم بالذاكرة المخبئية، حذف محتوى لمحادثة معينة.\n- حذف الذاكرة المخبئية من المجموعات الخارقة والقنوات: الضغط والتعليق عليها ثم تحذفها من الذاكرة.n\- إدارة الملصقات: إعادة ترتيب ملصقاتك بشكل يدوي. ويتزامن الترتيب مع باقي أجهزتك.n\n\للإستزادة عن هذا التحديث من هنا:n\ + https://telegram.org/blog/cache-and-stickers + 693 \ 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 93af889a8..26814bcfe 100644 --- a/TMessagesProj/src/main/res/values-de/strings.xml +++ b/TMessagesProj/src/main/res/values-de/strings.xml @@ -46,6 +46,7 @@ %s ist deinem geheimen Chat beigetreten. Du bist dem geheimen Chat beigetreten. Verlauf löschen + Cache leeren Löschen und beenden Chat löschen Gelöschtes Konto @@ -437,7 +438,6 @@ Alle anderen Geräte abmelden Ereignisse Kontakt ist Telegram beigetreten - PEBBLE Sprache Bedenke bitte, dass der Telegram Support von ehrenamtlichen Helfern betreut wird. Wir versuchen so schnell wie möglich zu antworten, dies kann jedoch manchmal ein bisschen dauern.
]]>Bitte schau auch in den Fragen und Antworten ]]> nach. Dort findest du Antworten auf die meisten Fragen und wichtige Tipps zur Problembehandlung]]>.
Eine Frage stellen @@ -499,6 +499,24 @@ Mal innerhalb von Minuten + + Cache-Einstellungen + Lokale Datenbank + Textnachrichten-Cache leeren? + Zwischengespeicherte Textnachrichten werden entfernt und die Datenbank optimiert um Speicherplatz zurückzuerhalten. Auf Null lässt sich die Größe jedoch nicht reduzieren, da die App einige Daten für den laufenden Betrieb benötigt.\n\nHinweis: Der Vorgang kann mehrere Minuten dauern. + Cache Leeren + Leeren + Berechne... + Dateien + Bilder + Sprachnachrichten + Videos + Musik + Sonstige Dateien + Leer + Medien behalten + Bilder, Videos und andere Dateien, auf die du während dieser Zeit nicht zugegriffen]]> hast, werden von diesem Gerät gelöscht, um Speicherplatz zu sparen.\n\nAlle Medien bleiben in der Telegram Cloud gespeichert und können jederzeit wieder heruntergeladen werden. + Dauerhaft Sitzungen Aktuelles Gerät @@ -781,6 +799,8 @@ Geheimen Chat starten? Bist du dir sicher, dass du die Registrierung abbrechen willst? Möchtest du wirklich den Verlauf löschen? + Cache des Kanals wirklich löschen? + Cache der Supergruppe wirklich löschen? Sicher, dass du %1$s löschen willst? Nachricht an %1$s senden? Kontakt senden an %1$s? @@ -1010,6 +1030,6 @@ h:mm a %1$s um %2$s - Telegram für Android wurde aktualisiert. Neu in Version 3.3.0:\n\n- Gruppen erlauben ab sofort Administratoren: Diese können den Gruppennamen und das Bild ändern sowie Mitglieder hinzufügen und auch wieder entfernen.\n- Gruppen, die das Limit von 200 Mitgliedern erreicht haben, können in eine Supergruppe (1000 Mitglieder) geändert werden.\n- Kanäle unterstützen schnelles Teilen über den Knopf neben jeder Nachricht.\n\nAusführliche Informationen zu den neuen Funktionen in unserem Blog:\nhttps://telegram.org/blog/supergroups - 677 + Telegram für Android wurde aktualisiert. Neu in Version 3.3.2:\n\n- Cache-Verwaltung: Prüfe wieviel Speicherplatz Telegram auf deinem Gerät benutzt und lösche den gesamten Cache oder nur bestimmte Teile.\n- Lösche den Cache von Supergruppen und Kanälen (in der Chatliste Supergruppe oder Kanal gedrückt halten und "Cache löschen").\n- Sticker-Verwaltung: Ändere die Sortierung deiner Sticker-Pakete. Die Sortierung wird auf all deinen Geräten synchronisiert.\n\nAusführliche Informationen zur neuen Version findest du hier:\nhttps://telegram.org/blog/cache-and-stickers + 693 \ 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 80187a351..0d3e7e834 100644 --- a/TMessagesProj/src/main/res/values-es/strings.xml +++ b/TMessagesProj/src/main/res/values-es/strings.xml @@ -46,6 +46,7 @@ %s se unió a tu chat secreto. Te uniste al chat secreto. Borrar historial + Eliminar de la caché Eliminar y salir Eliminar chat Cuenta eliminada @@ -71,7 +72,7 @@ Eliminar grupo Perderás todos los mensajes en este grupo. Puedes añadir administradores para que te ayuden a dirigir el canal. Mantén pulsado para eliminarlos. - ¡Espera! Al eliminar este grupo se quitarán todos los miembros y los mensajes se perderán. ¿Quieres eliminarlo? + ¡Espera! Al eliminar este grupo, todos los miembros y los mensajes se perderán. ¿Quieres eliminarlo? Grupo creado un1 te añadió a este grupo ¿Quieres dejar el grupo? @@ -82,7 +83,7 @@ Lo sentimos, hay demasiados bots en el grupo. Este grupo fue convertido en un supergrupo %1$s fue convertido en un supergrupo - Los usuarios bloqueados son expulsados del grupo y sólo pueden volver si son invitados por un administrador. Los enlaces de invitación no funcionan para ellos. + Los usuarios bloqueados son eliminados del grupo y sólo pueden volver si son invitados por un administrador. Los enlaces de invitación no funcionan para ellos. Nuevo canal Nombre del canal Comentarios @@ -123,7 +124,7 @@ Administradores Eliminar canal Eliminar canal - ¡Espera! Al eliminar este canal se quitarán todos los miembros y los mensajes se perderán. ¿Quieres eliminarlo? + ¡Espera! Al eliminar este canal, todos los miembros y los mensajes se perderán. ¿Quieres eliminarlo? ¿Quieres dejar este canal? Perderás todos los mensajes en este canal. Editar @@ -182,7 +183,7 @@ Nombre de la lista Creaste una lista de difusión Añadir destinatario - Quitar de la lista de difusión + Eliminar de la lista de difusión Por favor, añade archivos a la carpeta de música en tu dispositivo para verlos aquí. Música @@ -238,7 +239,7 @@ No dejan rastro en el servidor Tienen autodestrucción de mensajes Impiden reenviar mensajes - Te expulsaron de este grupo + Te eliminaron de este grupo Dejaste este grupo Eliminar este grupo Eliminar este chat @@ -293,8 +294,8 @@ %1$s cambió la foto del grupo %2$s %1$s invitó a %3$s al grupo %2$s %1$s volvió al grupo %2$s - %1$s expulsó a %3$s del grupo %2$s - %1$s te expulsó del grupo %2$s + %1$s eliminó a %3$s del grupo %2$s + %1$s te eliminó del grupo %2$s %1$s dejó el grupo %2$s ¡%1$s se unió a Telegram! %1$s,\nDetectamos un inicio de sesión en tu cuenta desde un nuevo dispositivo, el %2$s\n\nDispositivo: %3$s\nUbicación: %4$s\n\nSi no eras tú, puedes ir a Ajustes - Privacidad y seguridad - Sesiones activas y cerrar esa sesión.\n\nSi crees que alguien ha iniciado la sesión sin tu consentimiento, puedes activar la verificación en dos pasos, en los ajustes de privacidad y seguridad.\n\nAtentamente,\nEl equipo de Telegram @@ -322,7 +323,7 @@ últ. vez hace mucho tiempo Nuevo mensaje - Enviar mensaje a... + Invitar a... Nombre del grupo Nombre del grupo %1$d/%2$d miembros @@ -343,7 +344,7 @@ Administradores Todos son administradores Todos pueden añadir nuevos miembros, editar el nombre y la foto del grupo. - Sólo los administradores pueden añadir y quitar miembros, editar el nombre y la foto del grupo. + Sólo los administradores pueden añadir y eliminar miembros, editar el nombre y la foto del grupo. Multimedia Ajustes @@ -351,7 +352,7 @@ Nombrar administradores Eliminar y dejar el grupo Notificaciones - Expulsar del grupo + Eliminar del grupo Convertir en supergrupo Por favor, ten en cuenta que los miembros del grupo tendrán que actualizar Telegram a la última versión para ver tu supergrupo. ¿Quieres convertir el grupo? ]]>Límite de miembros alcanzado.]]>\n\nPara superar el límite y tener características adicionales, conviértelo en un supergrupo:\n\n• Permiten hasta %1$s\n• Nuevos miembros ven todo el historial\n• Un admin. borra mensajes para todos\n• Notificaciones silenciadas por defecto @@ -401,7 +402,7 @@ Mostrar Compartir Copiar enlace - Quitar + Eliminar Sin stickers aún Restablecer las notificaciones @@ -437,7 +438,6 @@ Cerrar todas las otras sesiones Eventos Un contacto se unió a Telegram - PEBBLE Idioma Por favor, considera que el soporte de Telegram está hecho por voluntarios. Respondemos lo antes posible, pero puede tomar tiempo.
]]>Por favor, mira las preguntas frecuentes de Telegram]]>: tienen respuestas para la mayoría de las preguntas y soluciones a problemas]]>.
Preguntar @@ -499,6 +499,24 @@ veces en minutos + + Ajustes de caché + Base de datos local + ¿Borrar los mensajes en la caché? + Al borrar la base de datos se eliminarán los mensajes en la caché y se comprimirá la base de datos para liberar espacio de almacenamiento. Telegram requiere algunos datos para funcionar, así que la base de datos nunca podrá llegar a cero.\n\nEsto puede tardar algunos minutos. + Borrar caché + Borrar + Calculando... + Archivos + Fotos + Mensajes de voz + Vídeos + Música + Otros archivos + Vacío + Conservar multimedia + Las fotos, los vídeos y los archivos de los chats en la nube a los que no accedas]]> durante ese periodo de tiempo se eliminarán del dispositivo para liberar espacio.\n\nToda la multimedia permanecerá en la nube de Telegram y podrás volver a descargarla si la necesitas. + Siempre Sesiones activas Sesión actual @@ -720,21 +738,21 @@ Te uniste al grupo con un enlace de invitación un1 se unió al grupo con un enlace de invitación - un1 expulsó a un2 + un1 eliminó a un2 un1 dejó el grupo un1 añadió a un2 un1 eliminó la foto del grupo un1 cambió la foto del grupo un1 cambió el nombre del grupo a un2 un1 creó el grupo - Expulsaste a un2 + Eliminaste a un2 Dejaste el grupo Añadiste a un2 - Quitaste la foto del grupo + Eliminaste la foto del grupo Cambiaste la foto del grupo Cambiaste el nombre del grupo a un2 Creaste el grupo - un1 te expulsó + un1 te eliminó un1 te añadió un1 volvió al grupo Volviste al grupo @@ -781,6 +799,8 @@ ¿Quieres iniciar un chat secreto? ¿Quieres cancelar el registro? ¿Quieres eliminar el historial? + ¿Eliminar de la caché los mensajes y multimedia de este canal? + ¿Eliminar de la caché los mensajes y multimedia de este supergrupo? ¿Quieres eliminar %1$s? ¿Enviar mensajes a %1$s? ¿Enviar contacto a %1$s? @@ -1010,6 +1030,6 @@ h:mm a %1$s a las %2$s - Telegram para Android ha sido actualizada. Novedades en la versión 3.3.0:\n\n- Ahora los grupos pueden tener múltiples administradores, con la habilidad de cambiar la foto de perfil y el nombre del grupo, además de añadir y expulsar miembros.\n- Los grupos que han alcanzado los 200 usuarios, podrán ser convertidos en supergrupos con una capacidad de 1000 miembros.\n- Los canales tienen un nuevo botón para compartir contenidos más rápido, justo al lado de los mensajes.\n\nMás sobre esta actualización:\nhttps://telegram.org/blog/supergroups - 677 + Telegram para Android ha sido actualizada. Novedades en la versión 3.3.2:\n\n- Gestión de caché: controla cuánto espacio usa Telegram en tu dispositivo y borra la caché para tipos específicos de contenido.\n- Elimina la caché de supergrupos y canales: mantén pulsado sobre ellos, en la lista de chats, y elige ‘Eliminar de la caché’.\n- Gestión de stickers: ordena manualmente tus packs de stickers. El orden de los packs ahora está sincronizado en todos tus dispositivos.\n\nMás sobre esta actualización aquí:\nhttps://telegram.org/blog/cache-and-stickers + 693 \ 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 2bffae106..efb234fc7 100644 --- a/TMessagesProj/src/main/res/values-it/strings.xml +++ b/TMessagesProj/src/main/res/values-it/strings.xml @@ -46,6 +46,7 @@ %s si è unito alla tua chat segreta. Sei entrato nella chat segreta. Cancella cronologia + Elimina dalla cache Elimina ed esci Elimina chat Account eliminato @@ -80,8 +81,8 @@ Spiacenti, questo utente ha deciso di lasciare il gruppo, quindi non puoi reinvitarlo. Spiacenti, troppi amministratori in questo gruppo. Spiacenti, troppi bot in questo gruppo. - Questo gruppo è stato convertito in un supergruppo - %1$s è stato convertito in un supergruppo. + Questo gruppo è stato aggiornato a supergruppo + %1$s è stato aggiornato a supergruppo. Gli utenti in lista nera sono rimossi dal gruppo e possono tornare solo se invitati da un amministratore. I link di invito non funzionano per loro. Nuovo canale Nome canale @@ -231,7 +232,7 @@ Messaggi Condividi il mio contatto Aggiungi ai contatti - %s ti ha mandato un invito a una chat segreta. + %s ti ha invitato ad entrare in una chat segreta. Hai invitato %s a entrare in una chat segreta. Chat segrete: Utilizzano la crittografia end-to-end @@ -259,8 +260,8 @@ AGGIUNGI CONTATTO Sei sicuro di voler segnalare questo utente come spam? Sei sicuro di voler segnalare dello spam in questo gruppo? - Spiacenti, ma al momento puoi scrivere solo a contatti in comune. - Spiacenti, ma al momento puoi aggiungere ai gruppi solo a contatti in comune. + Spiacenti, ma al momento puoi scrivere solo contatti in comune. + Spiacenti, ma al momento puoi aggiungere ai gruppi solo contatti in comune. https://telegram.org/faq/it#non-posso-inviare-messaggi-a-chi-non-far-parte-dei-miei-contatti Più info Invia a... @@ -437,7 +438,6 @@ Termina le altre sessioni Eventi Un contatto si è unito a Telegram - PEBBLE Lingua Nota che il supporto di Telegram è fornito da volontari. Proviamo a rispondere non appena possibile, ma potrebbe volerci un pò.
]]>Dai un\'occhiata alle FAQ di Telegram]]>: troverai risposte alla maggior parte delle domande e suggerimenti importanti per l\'individuazione del problema]]>
Chiedi a un volontario @@ -499,6 +499,24 @@ volte in minuti + + Impostazioni cache + Database locale + Eliminare i messaggi salvati nella cache? + Cancellando il database locale verrà eliminato il testo dei messaggi salvati nella cache, e verrà compressa la dimensione del database per risparmiare spazio in memoria. Telegram necessita di alcuni dati per funzionare, quindi il database non raggiungerà mai uno spazio occupato pari a zero.\n\nQuesta operazione può richiedere alcuni minuti. + Pulisci cache + Pulisci + Calcolando... + Documenti + Foto + Note vocali + Video + Musica + Altri file + Vuota + Mantieni media + Foto, video e altri file dalle chat nel cloud che non hai aperto]]> in questo periodo verranno eliminati dal dispositivo per preservare la spazio sul disco.\n\nTutti i media rimarranno nel cloud di Telegram e potranno essere riscaricati ogni volta che ne avrai bisogno. + Per sempre Sessioni attive Sessione corrente @@ -634,7 +652,7 @@ RIPRISTINA IL MIO ACCOUNT Perderai tutte le chat e i messaggi, insieme ai media e ai file condivisi, se procederai a ripristinare il tuo account. Attenzione - Questa azione non può essere annullata.\n\n Se ripristini il tuo account, tutti i tuoi messaggi e chat saranno eliminati. + Questa azione non può essere annullata.\n\nSe ripristini il tuo account, tutti i tuoi messaggi e chat saranno eliminati. Ripristina Password Hai attivato la verifica in due passaggi, così il tuo account è protetto con una password aggiuntiva. @@ -781,6 +799,8 @@ Iniziare una chat segreta? Sei sicuro di volere eliminare questa registrazione? Sei sicuro di volere eliminare la cronologia? + Eliminare tutti i messaggi e i media salvati nella cache per questo canale? + Eliminare tutti i messaggi e i media salvati nella cache per questo supergruppo? Sei sicuro di voler eliminare %1$s? Inviare messaggi a %1$s? Inviare contatto a %1$s? @@ -1010,6 +1030,6 @@ h:mm a %1$s alle %2$s - Telegram per Android si è aggiornato. Nuovo nella versione 3.3.0:\n\n- I gruppi ora possono avere più amministratori, con l\'abilità di modificare il nome e l\'immagine, e di aggiungere e rimuovere membri.\n- I gruppi che hanno raggiunto i 200 membri possono ora essere aggiornati a supergruppi e avere fino a 1000 membri.\n- I canali ora hanno un nuovo pulsante di Condivisione Veloce a destra dei messaggi.\n\nPiù info su questo aggiornamento:\nhttps://telegram.org/blog/supergroups - 677 + Telegram per Android si è aggiornato. Nuovo nella versione 3.3.2:\n\n- Gestione della cache: Controlla quanto spazio Telegram usa sul tuo dispositivo, elimina la cache per contenuti speicifici.\n- Elimina la cache per i supergruppi e i canali: Tieni premuto su di essi nella lista delle cache e premi \'Elimina dalla cache\'.\n- Gestione degli sticker: Riordina manualmente i tuoi pacchetti di sticker. L\'ordine dei pacchetti è ora sincronizzato tra tutti i dispositivi.\n\nPiù info su questo update:\nhttps://telegram.org/blog/cache-and-stickers + 693 \ No newline at end of file diff --git a/TMessagesProj/src/main/res/values-ko/strings.xml b/TMessagesProj/src/main/res/values-ko/strings.xml index a27b2a4de..7a3559531 100644 --- a/TMessagesProj/src/main/res/values-ko/strings.xml +++ b/TMessagesProj/src/main/res/values-ko/strings.xml @@ -46,6 +46,7 @@ %s님이 비밀대화에 참여했습니다. 비밀대화에 참여했습니다. 대화내용 지우기 + 캐시에서 삭제 채팅방 나가기 이 대화 삭제 탈퇴한 계정 @@ -82,7 +83,8 @@ 죄송합니다, 그룹방에 너무 많은 봇이 있습니다. 이 그룹방은 슈퍼그룹방으로 업그레이드 되었습니다. %1$s 그룹방은 슈퍼그룹방으로 업그레이드 되었습니다. - 그룹방에서 차단되어 퇴장당한 사용자는 관리자가 초대해야지만 그룹방에 입장이 가능합니다.\n초대링크로는 초대가 되지 않습니다. + 그룹방에서 차단되어 퇴장당한 사용자는 관리자가 초대해야지만 그룹방에 입장이 가능합니다. +초대링크로는 초대가 되지 않습니다. 새 채널 채널명 코멘트들 @@ -127,8 +129,10 @@ 채널에서 나가시겠습니까? 채널에 있는 모든 메시지가 삭제됩니다. 편집 - 채널에 대한 공개링크를 선택하신 경우, 누구나 검색을 통하여 입장 가능합니다.\n\n비공개 채널로 유지를 하시고 싶으실 경우 링크 생성을 하지 말아주세요 - 유저들이 공개 채널에 대하여 검색 및 공유가 가능하도록 링크를 선택하여 주세요.\n\n채널을 공개하시지 싫으실 경우, 비공개 채널을 추천드립니다. + 채널에 대한 공개링크를 선택하신 경우, 누구나 검색을 통하여 입장 가능합니다.\n\n +비공개 채널로 유지를 하시고 싶으실 경우 링크 생성을 하지 말아주세요 + 유저들이 공개 채널에 대하여 검색 및 공유가 가능하도록 링크를 선택하여 주세요.\n\n +채널을 공개하시지 싫으실 경우, 비공개 채널을 추천드립니다. 채널 생성됨 채널 사진 업데이트됨 채널 사진 삭제됨 @@ -437,7 +441,6 @@ 다른 모든 세션 종료 이벤트 친구의 텔레그램 가입 알림 - PEBBLE 스마트워치 지원 언어 텔레그램에 관한 질문은 자원봉사자들이 답변해 드립니다. 신속한 답변을 위해 노력하지만 답변이 다소 늦을 수 있습니다.
]]>일반적인 문제와 해결방법]]>에 대해서는 \'자주 묻는 질문]]>\'을 확인해 보세요.
질문하기 @@ -499,6 +502,24 @@ 이내 + + 캐시 설정 + 로컬 데이터베이스 + 캐시된 텍스트 메시지를 삭제하시겠습니까? + 압축된 데이터베이스 및 캐시에 저장된 메시지를 로컬 데이터베이스에서 삭제하면 내부 저장공간이 증가합니다. 데이터베이스는 Telegram이 작동하는데 어느정도 필요함으로 완전히 삭제가 되지는 않습니다.\n\n이 작업은 완료되기까지 몇분정도 소요가 될 수 있습니다. + 캐시 삭제 + 삭제 + 계산중... + 문서 + 사진 + 음성 메시지 + 동영상 + 음악 + 다른 파일 + 없음 + 미디어 저장 + 이 기간 동안 클라우드 채팅방에서 접근하지 않은]]> 사진이나 동영상, 기타 파일 등은 공간 절약을 위해 이 기기에서 삭제됩니다.\n\n모든 파일은 Telegram 클라우드에 여전히 남으며 필요하시면 언제든 다시 다운로드하실 수 있습니다. + 영원히 활성화된 세션 현재 세션 @@ -781,6 +802,8 @@ 비밀대화를 시작할까요? 정말로 가입을 취소하시겠습니까? 정말로 대화내용을 지우시겠습니까? + 채널에서 캐시된 모든 텍스트 및 미디어를 삭제하시겠습니까? + 슈커그룹에서 캐시된 모든 텍스트 및 미디어를 삭제하시겠습니까? %1$s: 정말로 삭제하시겠습니까? %1$s 그룹에 메시지를 보낼까요? %1$s에게 연락처를 보내시겠습니까? @@ -1010,6 +1033,6 @@ a h:mm %1$s %2$s - 텔레그램 안드로이드 버전이 업데이트 되었습니다. 새로운 버전은 3.3.0 입니다:\n\n- 그룹방제목, 그룹방사진, 구성원 추가 및 삭제등을 할 수 있는 복수의 그룹 관리자 설정 가능\n- 200명 제한이 걸린 그룹은 1,000명까지 활용가능한 슈퍼그룹으로 업그레이드 가능\n\n슈퍼그룹 및 업데이트 관련 내용 :\nhttps://telegram.org/blog/supergroups - 677 + 텔레그램 안드로이드 버전이 업데이트 되었습니다. 새로운 버전은 3.3.2 입니다:\n\n- 캐시 관리: 저장소에서 텔레그램이 어느정도 사용하는지 관리가능, 각 기기에서 특정 컨텐츠 삭제 가능.\n- 슈퍼그룹 및 채널 캐시 삭제: 채팅목록에서 꾹 누르고 있으면 \'캐시에서 삭제\' 메뉴 선택 가능.\n- 스티커 관리: 수동으로 스티커팩 수정가능. 팩 순서는 모든 기기와 동기화 됩니다.\n\n자세한 업데이트는 https://telegram.org/blog/cache-and-stickers에서 확인하세요. + 693 \ 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 a30e200f4..e79b0053b 100644 --- a/TMessagesProj/src/main/res/values-nl/strings.xml +++ b/TMessagesProj/src/main/res/values-nl/strings.xml @@ -4,7 +4,7 @@ Telegram - Telegram Bèta + Telegram-bèta Nederlands Dutch nl @@ -46,6 +46,7 @@ %s neemt deel aan je geheime chat. Toegevoegd aan de geheime chat. Geschiedenis wissen + Cache opschonen Verwijder en verlaat Chat verwijderen Verwijderd account @@ -80,8 +81,8 @@ Deze gebruiker heeft de groep verlaten. Je kunt hem/haar niet meer uitnodigen. Maximaal aantal beheerders bereikt. Maximaal aantal bots bereikt. - De groep is omgezet naar een supergroep - %1$s is omgezet naar een supergroep + De groep is opgewaardeerd naar een supergroep + %1$s is opgewaardeerd naar een supergroep Geblokkeerde gebruikers kunnen alleen worden uitgenodigd door beheerders, uitnodigingslinks werken niet voor hen. Nieuw kanaal Kanaalnaam @@ -352,9 +353,9 @@ Groep verwijderen en verlaten Meldingen Verwijderen uit groep - Upgraden naar supergroep - Groepsdeelnemers moeten updaten naar de meest recente Telegram om je supergroep te kunnen zien. Groep echt upgraden? - ]]>Deelnemerslimiet bereikt.]]>\n\nWil je extra functies en een hogere limiet? Upgrade naar een supergroep:\n\n• Supergroepen hebben tot %1$s\n• Nieuwe leden zien de hele geschiedenis\n• Beheerder wist berichten voor iedereen\n• Meldingen staan standaard uit + Opwaarderen naar supergroep + Groepsdeelnemers moeten updaten naar de meest recente Telegram om je supergroep te kunnen zien. Groep echt opwaarderen? + ]]>Deelnemerslimiet bereikt.]]>\n\nWil je extra functies en een hogere limiet? Waardeer op naar een supergroep:\n\n• Supergroepen hebben tot %1$s\n• Nieuwe leden zien de hele geschiedenis\n• Beheerder wist berichten voor iedereen\n• Meldingen staan standaard uit Delen Toevoegen @@ -437,7 +438,6 @@ Beëindig alle andere sessies Gebeurtenissen Contact lid van Telegram - PEBBLE Taal De ondersteuning van Telegram wordt gedaan door vrijwilligers. We doen ons best om zo snel mogelijk te antwoorden.
]]>Bekijk ook de veelgestelde vragen]]>: Hier staan de antwoorden op de meeste vragen en belangrijke tips voor het oplossen van problemen]]>.
Vraag een vrijwilliger @@ -462,7 +462,7 @@ Badgenummer Kort Lang - Standaardinstelling + Systeeminstelling Standaardinstelling Automatisch media downloaden Bij mobiele verbinding @@ -499,6 +499,24 @@ keer binnen minuten + + Cache-instellingen + Lokale database + Gecachet tekstberichten wissen? + Het opschonen van de lokale database zal de tekst van gecachet berichten verwijderen en de database comprimeren om ruimte te besparen. Telegram heeft wat ruimte nodig om te kunnen functioneren, dus de databasegrootte zal nooit nul worden.\n\nDit kan enkele minuten duren. + Cache opschonen + Opschonen + Berekenen... + Bestanden + Foto\'s + Spraakberichten + Video\'s + Muziek + Overige bestanden + Leeg + Media bewaren + Foto\'s, video\'s en andere bestanden uit cloudchats die je gedurende deze periode niet hebt geopend]]> zullen worden verwijderd van dit apparaat om ruimte te besparen.\n\nAlle media zal in de Telegram-cloud bewaard blijven en kan opnieuw worden gedownload als je het weer nodig hebt. + Voor altijd Actieve sessies Huidige sessie @@ -781,6 +799,8 @@ Weet je zeker dat je een geheime chat wilt starten? Weet je zeker dat je de registratie wilt annuleren? Geschiedenis echt wissen? + Kanaalcache opschonen? + Supergroepcache echt opschonen? %1$s echt verwijderen? Berichten naar %1$s versturen? Contact delen met %1$s? @@ -824,7 +844,7 @@ %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 persoon is 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 @@ -962,7 +982,7 @@ Bijlage: %1$d foto\'s Bijlage: %1$d foto\'s Bijlage: %1$d foto\'s - Bijlage: %1$d foto\'s + Bijlage: %1$d video\'s Bijlage: 1 video Bijlage: %1$d video\'s Bijlage: %1$d video\'s @@ -1010,6 +1030,6 @@ h:mm a %1$s om %2$s - Telegram voor Android is bijgewerkt. Nieuw in versie 3.3.0:\n\n- Meerdere beheerders in groepen, naast het wijzigen van de groepsnaam en afbeelding kunnen beheerders ook leden toevoegen en verwijderen.\n- Groepen die de limiet van 200 deelnemers hebben bereikt kunnen worden geüpgraded naar supergroepen met maximaal 1000 deelnemers.\n- Snel delen in kanalen via de knop rechts van de berichten.\n\nMeer informatie over deze update is hier te vinden:\nhttps://telegram.org/blog/supergroups - 677 + Telegram voor Android is bijgewerkt. Nieuw in versie 3.3.2:\n\n- Cache-beheer: Meer controle over het ruimtegebruik van Telegram op je apparaat, je kunt de cache nu ook per soort content opschonen.\n- Cache verwijderen van supergroepen en kanalen? Tik ze aan en hou ze vast in het chats-overzicht, daarna: \'Cache opschonen\'.\n- Stickerbeheer: je kunt nu handmatig je stickerbundels sorteren, de volgorde synchroniseren we voor je, over al je apparaten.\n\nMeer weten? Kijk op:\nhttps://telegram.org/blog/cache-and-stickers + 693
\ 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 8e973af73..ebe8ddb55 100644 --- a/TMessagesProj/src/main/res/values-pt-rBR/strings.xml +++ b/TMessagesProj/src/main/res/values-pt-rBR/strings.xml @@ -46,6 +46,7 @@ %s entrou no chat secreto Você entrou no chat secreto Limpar histórico + Apagar do cache Apagar e sair Apagar conversa Conta Excluída @@ -437,7 +438,6 @@ Terminar todas as outras sessões Eventos Contato entrou para o Telegram - PEBBLE Idioma Por favor entenda que o suporte do Telegram é feito por voluntários. Tentaremos responder o mais rápido possível, mas poderemos demorar um pouco.
]]>Por favor verifique a página de perguntas frequentes do Telegram]]>: há dicas e respostas para a maioria dos problemas]]>.
Pergunte a um voluntário @@ -499,6 +499,24 @@ vezes a cada minutos + + Configurações de Cache + Banco de Dados Local + Limpar todos os textos em cache? + Limpar o banco de dados local apagará todos os textos das mensagens em cache e compactará o banco de dados para economizar espaço. O Telegram precisa de alguns dados para trabalhar, então o tamanho do banco não vai chegar a zero.\n\nEssa operação pode demorar alguns minutos para ser concluída. + Limpar Cache + Limpar + Calculando... + Documentos + Fotos + Mensagens de voz + Vídeos + Música + Outros arquivos + Vazio + Manter Mídias + Fotos, vídeos e outros arquivos da nuvem que você não acessou]]> durante esse período serão removidos deste dispositivo para economizar espaço em disco.\n\nTodas as mídias permanecerão na nuvem do Telegram e poderão ser baixadas novamente conforme necessário. + Permanentemente Sessões Ativas Sessão atual @@ -781,6 +799,8 @@ Você tem certeza que deseja começar um chat secreto? Você tem certeza que deseja cancelar o registro? Você tem certeza que deseja limpar o histórico? + Apagar todos os textos e mídias em cache desse canal? + Apagar todos os textos e mídias em cache desse supergrupo? Você tem certeza que deseja apagar %1$s? Enviar mensagens para %1$s? Enviar contato para %1$s? @@ -1010,6 +1030,6 @@ h:mm a %1$s às %2$s - Telegram para Android foi atualizado. Novidades na versão 3.3.0:\n\n- Os grupos agora podem ter múltiplos administradores com permissão para editar o nome e a imagem do grupo, adicionar e remover membros.\n- Os grupos que alcançarem 200 usuários podem ser transformados em supergrupos, que permitem até 1000 membros.\n- Os canais contam com um botão de compartilhamento rápido ao lado das mensagens.\n\nVocê pode ver mais sobre os supergrupos e sobre os demais assuntos no nosso blog:\nhttps://telegram.org/blog/supergroups - 677 + O Telegram para Android foi atualizado. Novidades da versão 3.3.2:\n\n- Gerenciamento de cache: controle quanto espaço em disco o Telegram ocupa em teu aparelho, apague o cache para tipos específicos de conteúdo.\n- Apague o cache de supergrupos e canais: toque em um deles na lista de contas e escolha "apagar do cache".\n- Gerenciamento de stickers: reordene manualmente teus pacotes de stickers. Agora essa ordem será sincronizada em todos os teus aparelhos.\nMais sobre essa atualização: https://telegram.org/blog/cache-and-stickers + 693 \ 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 258ce0cd4..1f0394737 100644 --- a/TMessagesProj/src/main/res/values-pt-rPT/strings.xml +++ b/TMessagesProj/src/main/res/values-pt-rPT/strings.xml @@ -46,6 +46,7 @@ %s entrou no chat secreto Você entrou no chat secreto Limpar histórico + Apagar do cache Apagar e sair Apagar conversa Conta Excluída @@ -437,7 +438,6 @@ Terminar todas as outras sessões Eventos Contato entrou para o Telegram - PEBBLE Idioma Por favor entenda que o suporte do Telegram é feito por voluntários. Tentaremos responder o mais rápido possível, mas poderemos demorar um pouco.
]]>Por favor verifique a página de perguntas frequentes do Telegram]]>: há dicas e respostas para a maioria dos problemas]]>.
Pergunte a um voluntário @@ -499,6 +499,24 @@ vezes a cada minutos + + Configurações de Cache + Banco de Dados Local + Limpar todos os textos em cache? + Limpar o banco de dados local apagará todos os textos das mensagens em cache e compactará o banco de dados para economizar espaço. O Telegram precisa de alguns dados para trabalhar, então o tamanho do banco não vai chegar a zero.\n\nEssa operação pode demorar alguns minutos para ser concluída. + Limpar Cache + Limpar + Calculando... + Documentos + Fotos + Mensagens de voz + Vídeos + Música + Outros arquivos + Vazio + Manter Mídias + Fotos, vídeos e outros arquivos da nuvem que você não acessou]]> durante esse período serão removidos deste dispositivo para economizar espaço em disco.\n\nTodas as mídias permanecerão na nuvem do Telegram e poderão ser baixadas novamente conforme necessário. + Permanentemente Sessões Ativas Sessão atual @@ -781,6 +799,8 @@ Você tem certeza que deseja começar um chat secreto? Você tem certeza que deseja cancelar o registro? Você tem certeza que deseja limpar o histórico? + Apagar todos os textos e mídias em cache desse canal? + Apagar todos os textos e mídias em cache desse supergrupo? Você tem certeza que deseja apagar %1$s? Enviar mensagens para %1$s? Enviar contato para %1$s? @@ -1010,6 +1030,6 @@ h:mm a %1$s às %2$s - Telegram para Android foi atualizado. Novidades na versão 3.3.0:\n\n- Os grupos agora podem ter múltiplos administradores com permissão para editar o nome e a imagem do grupo, adicionar e remover membros.\n- Os grupos que alcançarem 200 usuários podem ser transformados em supergrupos, que permitem até 1000 membros.\n- Os canais contam com um botão de compartilhamento rápido ao lado das mensagens.\n\nVocê pode ver mais sobre os supergrupos e sobre os demais assuntos no nosso blog:\nhttps://telegram.org/blog/supergroups - 677 + O Telegram para Android foi atualizado. Novidades da versão 3.3.2:\n\n- Gerenciamento de cache: controle quanto espaço em disco o Telegram ocupa em teu aparelho, apague o cache para tipos específicos de conteúdo.\n- Apague o cache de supergrupos e canais: toque em um deles na lista de contas e escolha "apagar do cache".\n- Gerenciamento de stickers: reordene manualmente teus pacotes de stickers. Agora essa ordem será sincronizada em todos os teus aparelhos.\nMais sobre essa atualização: https://telegram.org/blog/cache-and-stickers + 693 \ 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 a18e9de37..6e90320d1 100644 --- a/TMessagesProj/src/main/res/values/strings.xml +++ b/TMessagesProj/src/main/res/values/strings.xml @@ -46,6 +46,7 @@ %s joined your secret chat. You joined the secret chat. Clear history + Delete from cache Delete and exit Delete chat Deleted Account @@ -437,7 +438,6 @@ Terminate All Other Sessions Events Contact joined Telegram - PEBBLE Language Please note that Telegram Support is done by volunteers. We try to respond as quickly as possible, but it may take a while.
]]>Please take a look at the Telegram FAQ]]>: it has answers to most questions and important tips for troubleshooting]]>.
Ask a volunteer @@ -499,6 +499,24 @@ times within minutes + + Cache Settings + Local Database + Clear cached text messages? + Clearing the local database will delete the texts of cached messages and compress the database to save internal disk space. Telegram needs some data to work, so database size will not reach zero.\n\nThis operation can take a few minutes to complete. + Clear Cache + Clear + Calculating... + Documents + Photos + Voice messages + Videos + Music + Other files + Empty + Keep Media + Photos, videos and other files from cloud chats that you have not accessed]]> during this period will be removed from this device to save disk space.\n\nAll media will stay in the Telegram cloud and can be re-downloaded if you need it again. + Forever Active Sessions Current session @@ -781,6 +799,8 @@ Are you sure you want to start a secret chat? Are you sure you want to cancel registration? Are you sure you want to clear history? + Delete all cached text and media from this channel? + Delete all cached text and media from this supergroup? Are you sure you want to delete %1$s? Send messages to %1$s? Send contact to %1$s? @@ -1010,6 +1030,6 @@ h:mm a %1$s at %2$s - Telegram for Android has been updated. New in version 3.3.0:\n\n- Groups can now have multiple administrators with the ability to edit the name and logo, and add and remove members.\n- Groups that have reached their capacity of 200 users can be upgraded to supergroups of up to 1,000 members.\n- Channels got a new Quick Share button right next to messages.\n\nMore about this update:\nhttps://telegram.org/blog/supergroups - 677 + Telegram for Android has been updated. New in version 3.3.2:\n\n- Cache management: Control how much disk space Telegram uses on your device, delete cache for specific types of content.\n- Delete cache from supergroups and channels: Tap and hold on them in the chats list and \'Delete from Cache\'.\n- Sticker management: Manually rearrange your sticker packs. Pack order is now synced across all your devices.\n\nMore about this update:\nhttps://telegram.org/blog/cache-and-stickers + 693 \ No newline at end of file