Update to 3.3.2

This commit is contained in:
DrKLO 2015-12-09 21:27:52 +03:00
parent 62068e188c
commit 512e404db7
59 changed files with 2700 additions and 801 deletions

View File

@ -79,7 +79,7 @@ android {
defaultConfig {
minSdkVersion 8
targetSdkVersion 23
versionCode 685
versionName "3.3.1"
versionCode 695
versionName "3.3.2"
}
}

View File

@ -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

View File

@ -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">
<activity
android:name="org.telegram.ui.LaunchActivity"
@ -107,6 +108,13 @@
</intent-filter>
<meta-data android:name="android.service.chooser.chooser_target_service" android:value=".TgChooserTargetService" />
</activity>
<activity
android:name="org.telegram.ui.ManageSpaceActivity"
android:configChanges="keyboard|keyboardHidden|orientation|screenSize"
android:hardwareAccelerated="@bool/useHardwareAcceleration"
android:launchMode="singleTask"
android:windowSoftInputMode="adjustPan">
</activity>
<activity
android:name="org.telegram.ui.IntroActivity"
android:configChanges="keyboard|keyboardHidden|orientation|screenSize">
@ -168,6 +176,7 @@
<service android:name=".NotificationsService" android:enabled="true"/>
<service android:name=".NotificationRepeat" android:exported="false"/>
<service android:name=".ClearCacheService" android:exported="false"/>
<service android:name=".VideoEncodingService" android:enabled="true"/>
<service android:name=".MusicPlayerService" android:exported="true" android:enabled="true"/>

View File

@ -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 {

View File

@ -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";
}

View File

@ -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";

View File

@ -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<Integer, File> paths = ImageLoader.getInstance().createMediaPaths();
for (HashMap.Entry<Integer, File> 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);
}
}
}
});
}
}

View File

@ -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<RequestInfo> 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;
}

View File

@ -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<File> files) {
public void deleteFiles(final ArrayList<File> 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();
}
}
});
}

View File

@ -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);

View File

@ -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);
}

View File

@ -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;

View File

@ -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<TLRPC.User> dbUsers = new ArrayList<>();
ArrayList<TLRPC.User> 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);

View File

@ -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<File> 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<TLRPC.Message> 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<Integer> messages, final SparseArray<Long> inbox) {
try {
HashMap<Long, Integer> 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<Long, Integer> 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<Integer, ArrayList<TLRPC.Message>> 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<TLRPC.Message>() {
@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<Long, Integer> mediaTypes = null;
StringBuilder messageIds = new StringBuilder();
HashMap<Long, Integer> dialogsReadMax = new HashMap<>();
HashMap<Long, Long> messagesIdsMap = new HashMap<>();
HashMap<Long, Long> 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<TLRPC.Message> 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<TLRPC.Message> 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);

View File

@ -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++;

View File

@ -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);
}

View File

@ -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;
}

View File

@ -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();

View File

@ -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<TLRPC.TL_messages_stickerSet> stickerSets = new ArrayList<>();
private static HashMap<Long, TLRPC.TL_messages_stickerSet> 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<Long> order) {
Collections.sort(stickerSets, new Comparator<TLRPC.TL_messages_stickerSet>() {
@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<TLRPC.Document> 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<TLRPC.TL_messages_stickerSet> 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<TLRPC.TL_messages_stickerSet> stickers, final int date, final String hash) {
private static void putStickersToCache(final ArrayList<TLRPC.TL_messages_stickerSet> 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<TLRPC.TL_messages_stickerSet> res, final boolean cache, final int date, final String hash) {
private static int calcStickersHash(ArrayList<TLRPC.TL_messages_stickerSet> 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<TLRPC.TL_messages_stickerSet> 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);
}

View File

@ -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;

View File

@ -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;

View File

@ -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);
}

View File

@ -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);

View File

@ -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<Integer> messages = new ArrayList<>();
public String phone;
public WebPage webpage;
public ArrayList<Long> 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<TL_messageRange> 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<Long> 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;

View File

@ -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;

View File

@ -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<Long> 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<TLRPC.Message> 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;
}
}
}

View File

@ -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);
}
}
}

View File

@ -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) {

View File

@ -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<MessageObject> 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) {

View File

@ -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);
}

View File

@ -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);*/
}
}

View File

@ -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<String> recentEmoji = new ArrayList<>();
private HashMap<Long, Integer> stickersUseHistory = new HashMap<>();
private ArrayList<TLRPC.Document> recentStickers = new ArrayList<>();
private HashMap<Long, Integer> stickerSetsUseCount = new HashMap<>();
private ArrayList<TLRPC.TL_messages_stickerSet> 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<Long> toRemove = null;
for (HashMap.Entry<Long, Integer> 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<Long, Integer> 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<TLRPC.TL_messages_stickerSet>() {
@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) {

View File

@ -326,6 +326,11 @@ public class PhotoViewerCaptionEnterView extends FrameLayoutFixed implements Not
public void onStickerSelected(TLRPC.Document sticker) {
}
@Override
public void onStickersSettingsClick() {
}
});
sizeNotifierLayout.addView(emojiView);
}

View File

@ -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() {

View File

@ -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<TLRPC.Chat> 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);
}
}
});

View File

@ -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());

View File

@ -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<BaseFragment> mainFragmentsStack = new ArrayList<>();
private static ArrayList<BaseFragment> 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();
}
}
}
}

View File

@ -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;

View File

@ -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);

View File

@ -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;

View File

@ -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<TLRPC.Document> 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<TLRPC.TL_messages_stickerSet> 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<TLRPC.TL_messages_stickerSet> 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<TLRPC.TL_messages_stickerSet> 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<TLRPC.TL_messages_stickerSet> 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<TLRPC.TL_messages_stickerSet> 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<TLRPC.TL_messages_stickerSet> arrayList = StickersQuery.getStickerSets();
TLRPC.TL_messages_stickerSet from = arrayList.get(fromIndex);
arrayList.set(fromIndex, arrayList.get(toIndex));
arrayList.set(toIndex, from);
notifyItemMoved(fromIndex, toIndex);
}
}
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.3 KiB

View File

@ -0,0 +1,14 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ 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.
-->
<ripple xmlns:android="http://schemas.android.com/apk/res/android"
android:color="#2f000000">
<item android:id="@android:id/mask" android:drawable="@android:color/white"/>
<item android:id="@android:id/background" android:drawable="@android:color/white"/>
</ripple>

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

View File

@ -0,0 +1,19 @@
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_pressed="true">
<shape android:shape="rectangle">
<solid android:color="#fff0f0f0" />
</shape>
</item>
<item android:state_focused="true">
<shape android:shape="rectangle">
<solid android:color="#fff0f0f0" />
</shape>
</item>
<item android:state_selected="true">
<shape android:shape="rectangle">
<solid android:color="#fff0f0f0" />
</shape>
</item>
<item android:drawable="@android:color/white" />
</selector>

View File

@ -46,6 +46,7 @@
<string name="EncryptedChatStartedOutgoing">%s قام بالدخول للمحادثة السرية.</string>
<string name="EncryptedChatStartedIncoming">لقد قمت بالدخول للمحادثة السرية.</string>
<string name="ClearHistory">مسح سجل المحادثات</string>
<string name="ClearHistoryCache">حذف من الذاكرة المخبئية</string>
<string name="DeleteChat">حذف وخروج</string>
<string name="DeleteChatUser">حذف المحادثة</string>
<string name="HiddenName">حساب محذوف</string>
@ -437,7 +438,6 @@
<string name="TerminateAllSessions">سجل الخروج من كافة الأجهزة الأخرى</string>
<string name="Events">الأحداث</string>
<string name="ContactJoined">اشترك صديق في تيليجرام</string>
<string name="Pebble">PEBBLE</string>
<string name="Language">اللغة</string>
<string name="AskAQuestionInfo">نرجو الأخذ بالعلم أن الدعم الفني في تيليجرام يقوم به مجموعة من المتطوعين. نحن نحاول الرد بسرعة قدر المستطاع، لكن ربما نستغرق القليل من الوقت.<![CDATA[<br><br>]]> <![CDATA[<a href=\"https://telegram.org/faq/ar\">صفحة الأسئلة الأكثر شيوعًا</a>]]>: يوجد بها حلول للمشاكل وإجابات لمعظم الأسئلة.</string>
<string name="AskButton">اسأل أحد المتطوعين</string>
@ -499,6 +499,24 @@
<string name="SmartNotificationsTimes">الأوقات</string>
<string name="SmartNotificationsWithin">خلال</string>
<string name="SmartNotificationsMinutes">دقائق</string>
<!--cache view-->
<string name="CacheSettings">إعدادات الذاكرة المخبئية</string>
<string name="LocalDatabase">قاعدة البيانات على الجهاز</string>
<string name="LocalDatabaseClear">هل ترغب في مسح الرسائل المحفوظة في الذاكرة المخبئية؟</string>
<string name="LocalDatabaseInfo">مسح قاعدة البيانات على الجهاز سيحذف الرسائل التي تم تنزيلها على جهازك ويقوم بضغط قاعدة البيانات لتوفير مساحة على جهازك. تيليجرام يحتاج لبعض البيانات ليعمل، لذلك حجم قاعدة البيانات لن يصل إلى صفر.\n\nهذه العملية ربما تأخذ عدة دقائق لتتم.</string>
<string name="ClearMediaCache">مسح الذاكرة المخبئية</string>
<string name="CacheClear">مسح</string>
<string name="CalculatingSize">جاري الحساب...</string>
<string name="LocalDocumentCache">المستندات</string>
<string name="LocalPhotoCache">الصور</string>
<string name="LocalAudioCache">الرسائل الصوتية</string>
<string name="LocalVideoCache">المقاطع المرئية</string>
<string name="LocalMusicCache">الموسيقى</string>
<string name="LocalCache">الملفات الأخرى</string>
<string name="CacheEmpty">إفراغ</string>
<string name="KeepMedia">الإحتفاظ بالوسائط</string>
<string name="KeepMediaInfo">الصور، المقاطع المرئية، وجميع الملفات المحفوظة في خوادمنا التي لم <![CDATA[<b> تستخدمها </b>]]> خلال هذه المدة سيتم حذفها لتوفير المساحة. ملفات الوسائط ستبقى في خوادم تيليجرام ويمكنك إعادة تنزيلها متى ما احتجتها مرة أخرى.</string>
<string name="KeepMediaForever">إلى الأبد</string>
<!--sessions view-->
<string name="SessionsTitle">الأجهزة المسجّل دخول منها</string>
<string name="CurrentSession">الجهاز الحالي</string>
@ -781,6 +799,8 @@
<string name="AreYouSureSecretChat">هل أنت متأكد من أنك تريد بدء محادثة سرية؟</string>
<string name="AreYouSureRegistration">هل أنت متأكد من رغبتك في إلغاء التسجيل؟</string>
<string name="AreYouSureClearHistory">هل أنت متأكد من رغبتك في حذف سجل المحادثات؟</string>
<string name="AreYouSureClearHistoryChannel">حذف كافة المحادثات والوسائط المتعلقة بهذه القناة من الذاكرة المخبئية؟</string>
<string name="AreYouSureClearHistorySuper">حذف كافة المحادثات والوسائط المتعلقة بهذه المجموعة الخارقة من الذاكرة المخبئية؟</string>
<string name="AreYouSureDeleteMessages">هل أنت متأكد من رغبتك في حذف %1$s؟</string>
<string name="SendMessagesToGroup">هل ترغب في إرسال رسالة إلى %1$s؟</string>
<string name="SendContactToGroup">أرسل جهة الاتصال إلى %1$s؟</string>
@ -1010,6 +1030,7 @@
<string name="formatterDay12H">h:mm a</string>
<string name="formatDateAtTime">%1$s الساعة %2$s</string>
<!--update text-->
<string name="updateText">تم تحديث تيليجرام على الأندرويد. الجديد في النسخة رقم 3.3.0:\n\n- المجموعات الآن يمكن أن يكون بها عدة مشرفين يمكنهم تغيير اسمها وشعارها وإضافة وإزالة الأعضاء.\n- المجموعات التي وصلت إلى ٢٠٠ عضو يمكن ترقيتها لتصبح مجموعة خارقة تصل إلى ١٠٠٠ عضو.\n- إضافة زر للمشاركة السريعة من خلال القنوات بجانب الرسائل.\n\nللإستزادة عن هذا التحديث من هنا:\nhttps://telegram.org/blog/supergroups</string>
<string name="updateBuild">677</string>
<string name="updateText">تيليجرام نسخة الأندرويد تم تحديثه. الجديد في نسخة ٣.٢.٢:\n\n- إدارة للذاكرة المخبئية: إمكانية التحكم بالذاكرة المخبئية، حذف محتوى لمحادثة معينة.\n- حذف الذاكرة المخبئية من المجموعات الخارقة والقنوات: الضغط والتعليق عليها ثم تحذفها من الذاكرة.n\- إدارة الملصقات: إعادة ترتيب ملصقاتك بشكل يدوي. ويتزامن الترتيب مع باقي أجهزتك.n\n\للإستزادة عن هذا التحديث من هنا:n\
https://telegram.org/blog/cache-and-stickers</string>
<string name="updateBuild">693</string>
</resources>

View File

@ -46,6 +46,7 @@
<string name="EncryptedChatStartedOutgoing">%s ist deinem geheimen Chat beigetreten.</string>
<string name="EncryptedChatStartedIncoming">Du bist dem geheimen Chat beigetreten.</string>
<string name="ClearHistory">Verlauf löschen</string>
<string name="ClearHistoryCache">Cache leeren</string>
<string name="DeleteChat">Löschen und beenden</string>
<string name="DeleteChatUser">Chat löschen</string>
<string name="HiddenName">Gelöschtes Konto</string>
@ -437,7 +438,6 @@
<string name="TerminateAllSessions">Alle anderen Geräte abmelden</string>
<string name="Events">Ereignisse</string>
<string name="ContactJoined">Kontakt ist Telegram beigetreten</string>
<string name="Pebble">PEBBLE</string>
<string name="Language">Sprache</string>
<string name="AskAQuestionInfo">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.<![CDATA[<br><br>]]>Bitte schau auch in den <![CDATA[<a href=\"https://telegram.org/faq/de\">Fragen und Antworten </a>]]> nach. Dort findest du Antworten auf die meisten Fragen und wichtige Tipps zur <![CDATA[<a href=\"https://telegram.org/faq/de#problembehandlung\">Problembehandlung</a>]]>.</string>
<string name="AskButton">Eine Frage stellen</string>
@ -499,6 +499,24 @@
<string name="SmartNotificationsTimes">Mal</string>
<string name="SmartNotificationsWithin">innerhalb von</string>
<string name="SmartNotificationsMinutes">Minuten</string>
<!--cache view-->
<string name="CacheSettings">Cache-Einstellungen</string>
<string name="LocalDatabase">Lokale Datenbank</string>
<string name="LocalDatabaseClear">Textnachrichten-Cache leeren?</string>
<string name="LocalDatabaseInfo">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.</string>
<string name="ClearMediaCache">Cache Leeren</string>
<string name="CacheClear">Leeren</string>
<string name="CalculatingSize">Berechne...</string>
<string name="LocalDocumentCache">Dateien</string>
<string name="LocalPhotoCache">Bilder</string>
<string name="LocalAudioCache">Sprachnachrichten</string>
<string name="LocalVideoCache">Videos</string>
<string name="LocalMusicCache">Musik</string>
<string name="LocalCache">Sonstige Dateien</string>
<string name="CacheEmpty">Leer</string>
<string name="KeepMedia">Medien behalten</string>
<string name="KeepMediaInfo">Bilder, Videos und andere Dateien, auf die du während dieser Zeit <![CDATA[<b>nicht zugegriffen</b>]]> 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.</string>
<string name="KeepMediaForever">Dauerhaft</string>
<!--sessions view-->
<string name="SessionsTitle">Sitzungen</string>
<string name="CurrentSession">Aktuelles Gerät</string>
@ -781,6 +799,8 @@
<string name="AreYouSureSecretChat">Geheimen Chat starten?</string>
<string name="AreYouSureRegistration">Bist du dir sicher, dass du die Registrierung abbrechen willst?</string>
<string name="AreYouSureClearHistory">Möchtest du wirklich den Verlauf löschen?</string>
<string name="AreYouSureClearHistoryChannel">Cache des Kanals wirklich löschen?</string>
<string name="AreYouSureClearHistorySuper">Cache der Supergruppe wirklich löschen?</string>
<string name="AreYouSureDeleteMessages">Sicher, dass du %1$s löschen willst?</string>
<string name="SendMessagesToGroup">Nachricht an %1$s senden?</string>
<string name="SendContactToGroup">Kontakt senden an %1$s?</string>
@ -1010,6 +1030,6 @@
<string name="formatterDay12H">h:mm a</string>
<string name="formatDateAtTime">%1$s um %2$s</string>
<!--update text-->
<string name="updateText">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</string>
<string name="updateBuild">677</string>
<string name="updateText">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</string>
<string name="updateBuild">693</string>
</resources>

View File

@ -46,6 +46,7 @@
<string name="EncryptedChatStartedOutgoing">%s se unió a tu chat secreto.</string>
<string name="EncryptedChatStartedIncoming">Te uniste al chat secreto.</string>
<string name="ClearHistory">Borrar historial</string>
<string name="ClearHistoryCache">Eliminar de la caché</string>
<string name="DeleteChat">Eliminar y salir</string>
<string name="DeleteChatUser">Eliminar chat</string>
<string name="HiddenName">Cuenta eliminada</string>
@ -71,7 +72,7 @@
<string name="DeleteMegaMenu">Eliminar grupo</string>
<string name="MegaDeleteInfo">Perderás todos los mensajes en este grupo.</string>
<string name="MegaAdminsInfo">Puedes añadir administradores para que te ayuden a dirigir el canal. Mantén pulsado para eliminarlos.</string>
<string name="MegaDeleteAlert">¡Espera! Al eliminar este grupo se quitarán todos los miembros y los mensajes se perderán. ¿Quieres eliminarlo?</string>
<string name="MegaDeleteAlert">¡Espera! Al eliminar este grupo, todos los miembros y los mensajes se perderán. ¿Quieres eliminarlo?</string>
<string name="ActionCreateMega">Grupo creado</string>
<string name="MegaAddedBy">un1 te añadió a este grupo</string>
<string name="MegaLeaveAlert">¿Quieres dejar el grupo?</string>
@ -82,7 +83,7 @@
<string name="GroupUserCantBot">Lo sentimos, hay demasiados bots en el grupo.</string>
<string name="ActionMigrateFromGroup">Este grupo fue convertido en un supergrupo</string>
<string name="ActionMigrateFromGroupNotify">%1$s fue convertido en un supergrupo</string>
<string name="NoBlockedGroup">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.</string>
<string name="NoBlockedGroup">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.</string>
<string name="NewChannel">Nuevo canal</string>
<string name="EnterChannelName">Nombre del canal</string>
<string name="Comments">Comentarios</string>
@ -123,7 +124,7 @@
<string name="ChannelAdministrators">Administradores</string>
<string name="ChannelDelete">Eliminar canal</string>
<string name="ChannelDeleteMenu">Eliminar canal</string>
<string name="ChannelDeleteAlert">¡Espera! Al eliminar este canal se quitarán todos los miembros y los mensajes se perderán. ¿Quieres eliminarlo?</string>
<string name="ChannelDeleteAlert">¡Espera! Al eliminar este canal, todos los miembros y los mensajes se perderán. ¿Quieres eliminarlo?</string>
<string name="ChannelLeaveAlert">¿Quieres dejar este canal?</string>
<string name="ChannelDeleteInfo">Perderás todos los mensajes en este canal.</string>
<string name="ChannelEdit">Editar</string>
@ -182,7 +183,7 @@
<string name="EnterListName">Nombre de la lista</string>
<string name="YouCreatedBroadcastList">Creaste una lista de difusión</string>
<string name="AddRecipient">Añadir destinatario</string>
<string name="KickFromBroadcast">Quitar de la lista de difusión</string>
<string name="KickFromBroadcast">Eliminar de la lista de difusión</string>
<!--audio view-->
<string name="NoAudio">Por favor, añade archivos a la carpeta de música en tu dispositivo para verlos aquí.</string>
<string name="AttachMusic">Música</string>
@ -238,7 +239,7 @@
<string name="EncryptedDescription2">No dejan rastro en el servidor</string>
<string name="EncryptedDescription3">Tienen autodestrucción de mensajes</string>
<string name="EncryptedDescription4">Impiden reenviar mensajes</string>
<string name="YouWereKicked">Te expulsaron de este grupo</string>
<string name="YouWereKicked">Te eliminaron de este grupo</string>
<string name="YouLeft">Dejaste este grupo</string>
<string name="DeleteThisGroup">Eliminar este grupo</string>
<string name="DeleteThisChat">Eliminar este chat</string>
@ -293,8 +294,8 @@
<string name="NotificationEditedGroupPhoto">%1$s cambió la foto del grupo %2$s</string>
<string name="NotificationGroupAddMember">%1$s invitó a %3$s al grupo %2$s</string>
<string name="NotificationGroupAddSelf">%1$s volvió al grupo %2$s</string>
<string name="NotificationGroupKickMember">%1$s expulsó a %3$s del grupo %2$s</string>
<string name="NotificationGroupKickYou">%1$s te expulsó del grupo %2$s</string>
<string name="NotificationGroupKickMember">%1$s eliminó a %3$s del grupo %2$s</string>
<string name="NotificationGroupKickYou">%1$s te eliminó del grupo %2$s</string>
<string name="NotificationGroupLeftMember">%1$s dejó el grupo %2$s</string>
<string name="NotificationContactJoined">¡%1$s se unió a Telegram!</string>
<string name="NotificationUnrecognizedDevice">%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</string>
@ -322,7 +323,7 @@
<string name="ALongTimeAgo">últ. vez hace mucho tiempo</string>
<string name="NewMessageTitle">Nuevo mensaje</string>
<!--group create view-->
<string name="SendMessageTo">Enviar mensaje a...</string>
<string name="SendMessageTo">Invitar a...</string>
<string name="EnterGroupNamePlaceholder">Nombre del grupo</string>
<string name="GroupName">Nombre del grupo</string>
<string name="MembersCount">%1$d/%2$d miembros</string>
@ -343,7 +344,7 @@
<string name="SetAdminsTitle">Administradores</string>
<string name="SetAdminsAll">Todos son administradores</string>
<string name="SetAdminsAllInfo">Todos pueden añadir nuevos miembros, editar el nombre y la foto del grupo.</string>
<string name="SetAdminsNotAllInfo">Sólo los administradores pueden añadir y quitar miembros, editar el nombre y la foto del grupo.</string>
<string name="SetAdminsNotAllInfo">Sólo los administradores pueden añadir y eliminar miembros, editar el nombre y la foto del grupo.</string>
<!--group info view-->
<string name="SharedMedia">Multimedia</string>
<string name="SETTINGS">Ajustes</string>
@ -351,7 +352,7 @@
<string name="SetAdmins">Nombrar administradores</string>
<string name="DeleteAndExit">Eliminar y dejar el grupo</string>
<string name="Notifications">Notificaciones</string>
<string name="KickFromGroup">Expulsar del grupo</string>
<string name="KickFromGroup">Eliminar del grupo</string>
<string name="ConvertGroup">Convertir en supergrupo</string>
<string name="ConvertGroupAlert">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?</string>
<string name="ConvertGroupInfo"><![CDATA[<b>]]>Límite de miembros alcanzado.<![CDATA[</b>]]>\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</string>
@ -401,7 +402,7 @@
<string name="StickersShow">Mostrar</string>
<string name="StickersShare">Compartir</string>
<string name="StickersCopy">Copiar enlace</string>
<string name="StickersRemove">Quitar</string>
<string name="StickersRemove">Eliminar</string>
<string name="NoStickers">Sin stickers aún</string>
<!--settings view-->
<string name="ResetNotificationsText">Restablecer las notificaciones</string>
@ -437,7 +438,6 @@
<string name="TerminateAllSessions">Cerrar todas las otras sesiones</string>
<string name="Events">Eventos</string>
<string name="ContactJoined">Un contacto se unió a Telegram</string>
<string name="Pebble">PEBBLE</string>
<string name="Language">Idioma</string>
<string name="AskAQuestionInfo">Por favor, considera que el soporte de Telegram está hecho por voluntarios. Respondemos lo antes posible, pero puede tomar tiempo.<![CDATA[<br><br>]]>Por favor, mira las <![CDATA[<a href=\"https://telegram.org/faq/es\">preguntas frecuentes de Telegram</a>]]>: tienen respuestas para la mayoría de las preguntas y <![CDATA[<a href=\"https://telegram.org/faq/es#solucin-de-problemas\">soluciones a problemas</a>]]>.</string>
<string name="AskButton">Preguntar</string>
@ -499,6 +499,24 @@
<string name="SmartNotificationsTimes">veces</string>
<string name="SmartNotificationsWithin">en</string>
<string name="SmartNotificationsMinutes">minutos</string>
<!--cache view-->
<string name="CacheSettings">Ajustes de caché</string>
<string name="LocalDatabase">Base de datos local</string>
<string name="LocalDatabaseClear">¿Borrar los mensajes en la caché?</string>
<string name="LocalDatabaseInfo">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.</string>
<string name="ClearMediaCache">Borrar caché</string>
<string name="CacheClear">Borrar</string>
<string name="CalculatingSize">Calculando...</string>
<string name="LocalDocumentCache">Archivos</string>
<string name="LocalPhotoCache">Fotos</string>
<string name="LocalAudioCache">Mensajes de voz</string>
<string name="LocalVideoCache">Vídeos</string>
<string name="LocalMusicCache">Música</string>
<string name="LocalCache">Otros archivos</string>
<string name="CacheEmpty">Vacío</string>
<string name="KeepMedia">Conservar multimedia</string>
<string name="KeepMediaInfo">Las fotos, los vídeos y los archivos de los chats en la nube a los que <![CDATA[<b>no accedas</b>]]> 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.</string>
<string name="KeepMediaForever">Siempre</string>
<!--sessions view-->
<string name="SessionsTitle">Sesiones activas</string>
<string name="CurrentSession">Sesión actual</string>
@ -720,21 +738,21 @@
<!--messages-->
<string name="ActionInviteYou">Te uniste al grupo con un enlace de invitación</string>
<string name="ActionInviteUser">un1 se unió al grupo con un enlace de invitación</string>
<string name="ActionKickUser">un1 expulsó a un2</string>
<string name="ActionKickUser">un1 eliminó a un2</string>
<string name="ActionLeftUser">un1 dejó el grupo</string>
<string name="ActionAddUser">un1 añadió a un2</string>
<string name="ActionRemovedPhoto">un1 eliminó la foto del grupo</string>
<string name="ActionChangedPhoto">un1 cambió la foto del grupo</string>
<string name="ActionChangedTitle">un1 cambió el nombre del grupo a un2</string>
<string name="ActionCreateGroup">un1 creó el grupo</string>
<string name="ActionYouKickUser">Expulsaste a un2</string>
<string name="ActionYouKickUser">Eliminaste a un2</string>
<string name="ActionYouLeftUser">Dejaste el grupo</string>
<string name="ActionYouAddUser">Añadiste a un2</string>
<string name="ActionYouRemovedPhoto">Quitaste la foto del grupo</string>
<string name="ActionYouRemovedPhoto">Eliminaste la foto del grupo</string>
<string name="ActionYouChangedPhoto">Cambiaste la foto del grupo</string>
<string name="ActionYouChangedTitle">Cambiaste el nombre del grupo a un2</string>
<string name="ActionYouCreateGroup">Creaste el grupo</string>
<string name="ActionKickUserYou">un1 te expulsó</string>
<string name="ActionKickUserYou">un1 te eliminó</string>
<string name="ActionAddUserYou">un1 te añadió</string>
<string name="ActionAddUserSelf">un1 volvió al grupo</string>
<string name="ActionAddUserSelfYou">Volviste al grupo</string>
@ -781,6 +799,8 @@
<string name="AreYouSureSecretChat">¿Quieres iniciar un chat secreto?</string>
<string name="AreYouSureRegistration">¿Quieres cancelar el registro?</string>
<string name="AreYouSureClearHistory">¿Quieres eliminar el historial?</string>
<string name="AreYouSureClearHistoryChannel">¿Eliminar de la caché los mensajes y multimedia de este canal?</string>
<string name="AreYouSureClearHistorySuper">¿Eliminar de la caché los mensajes y multimedia de este supergrupo?</string>
<string name="AreYouSureDeleteMessages">¿Quieres eliminar %1$s?</string>
<string name="SendMessagesToGroup">¿Enviar mensajes a %1$s?</string>
<string name="SendContactToGroup">¿Enviar contacto a %1$s?</string>
@ -1010,6 +1030,6 @@
<string name="formatterDay12H">h:mm a</string>
<string name="formatDateAtTime">%1$s a las %2$s</string>
<!--update text-->
<string name="updateText">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</string>
<string name="updateBuild">677</string>
<string name="updateText">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</string>
<string name="updateBuild">693</string>
</resources>

View File

@ -46,6 +46,7 @@
<string name="EncryptedChatStartedOutgoing">%s si è unito alla tua chat segreta.</string>
<string name="EncryptedChatStartedIncoming">Sei entrato nella chat segreta.</string>
<string name="ClearHistory">Cancella cronologia</string>
<string name="ClearHistoryCache">Elimina dalla cache</string>
<string name="DeleteChat">Elimina ed esci</string>
<string name="DeleteChatUser">Elimina chat</string>
<string name="HiddenName">Account eliminato</string>
@ -80,8 +81,8 @@
<string name="GroupUserLeftError">Spiacenti, questo utente ha deciso di lasciare il gruppo, quindi non puoi reinvitarlo.</string>
<string name="GroupUserCantAdmin">Spiacenti, troppi amministratori in questo gruppo.</string>
<string name="GroupUserCantBot">Spiacenti, troppi bot in questo gruppo.</string>
<string name="ActionMigrateFromGroup">Questo gruppo è stato convertito in un supergruppo</string>
<string name="ActionMigrateFromGroupNotify">%1$s è stato convertito in un supergruppo.</string>
<string name="ActionMigrateFromGroup">Questo gruppo è stato aggiornato a supergruppo</string>
<string name="ActionMigrateFromGroupNotify">%1$s è stato aggiornato a supergruppo.</string>
<string name="NoBlockedGroup">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.</string>
<string name="NewChannel">Nuovo canale</string>
<string name="EnterChannelName">Nome canale</string>
@ -231,7 +232,7 @@
<string name="TypeMessage">Messaggi</string>
<string name="ShareMyContactInfo">Condividi il mio contatto</string>
<string name="AddToContacts">Aggiungi ai contatti</string>
<string name="EncryptedPlaceholderTitleIncoming">%s ti ha mandato un invito a una chat segreta.</string>
<string name="EncryptedPlaceholderTitleIncoming">%s ti ha invitato ad entrare in una chat segreta.</string>
<string name="EncryptedPlaceholderTitleOutgoing">Hai invitato %s a entrare in una chat segreta.</string>
<string name="EncryptedDescriptionTitle">Chat segrete:</string>
<string name="EncryptedDescription1">Utilizzano la crittografia end-to-end</string>
@ -259,8 +260,8 @@
<string name="AddContactChat">AGGIUNGI CONTATTO</string>
<string name="ReportSpamAlert">Sei sicuro di voler segnalare questo utente come spam?</string>
<string name="ReportSpamAlertGroup">Sei sicuro di voler segnalare dello spam in questo gruppo?</string>
<string name="NobodyLikesSpam1">Spiacenti, ma al momento puoi scrivere solo a contatti in comune.</string>
<string name="NobodyLikesSpam2">Spiacenti, ma al momento puoi aggiungere ai gruppi solo a contatti in comune.</string>
<string name="NobodyLikesSpam1">Spiacenti, ma al momento puoi scrivere solo contatti in comune.</string>
<string name="NobodyLikesSpam2">Spiacenti, ma al momento puoi aggiungere ai gruppi solo contatti in comune.</string>
<string name="NobodyLikesSpamUrl">https://telegram.org/faq/it#non-posso-inviare-messaggi-a-chi-non-far-parte-dei-miei-contatti</string>
<string name="MoreInfo">Più info</string>
<string name="ShareSendTo">Invia a...</string>
@ -437,7 +438,6 @@
<string name="TerminateAllSessions">Termina le altre sessioni</string>
<string name="Events">Eventi</string>
<string name="ContactJoined">Un contatto si è unito a Telegram</string>
<string name="Pebble">PEBBLE</string>
<string name="Language">Lingua</string>
<string name="AskAQuestionInfo">Nota che il supporto di Telegram è fornito da volontari. Proviamo a rispondere non appena possibile, ma potrebbe volerci un pò.<![CDATA[<br><br>]]>Dai un\'occhiata alle <![CDATA[<a href=\"https://telegram.org/faq/it#domande-generali\">FAQ di Telegram</a>]]>: troverai risposte alla maggior parte delle domande e suggerimenti importanti per <![CDATA[<a href=\"https://telegram.org/faq/it#risoluzione-dei-problemi\">l\'individuazione del problema</a>]]></string>
<string name="AskButton">Chiedi a un volontario</string>
@ -499,6 +499,24 @@
<string name="SmartNotificationsTimes">volte</string>
<string name="SmartNotificationsWithin">in</string>
<string name="SmartNotificationsMinutes">minuti</string>
<!--cache view-->
<string name="CacheSettings">Impostazioni cache</string>
<string name="LocalDatabase">Database locale</string>
<string name="LocalDatabaseClear">Eliminare i messaggi salvati nella cache?</string>
<string name="LocalDatabaseInfo">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.</string>
<string name="ClearMediaCache">Pulisci cache</string>
<string name="CacheClear">Pulisci</string>
<string name="CalculatingSize">Calcolando...</string>
<string name="LocalDocumentCache">Documenti</string>
<string name="LocalPhotoCache">Foto</string>
<string name="LocalAudioCache">Note vocali</string>
<string name="LocalVideoCache">Video</string>
<string name="LocalMusicCache">Musica</string>
<string name="LocalCache">Altri file</string>
<string name="CacheEmpty">Vuota</string>
<string name="KeepMedia">Mantieni media</string>
<string name="KeepMediaInfo">Foto, video e altri file dalle chat nel cloud che non hai <![CDATA[<b>aperto</b>]]> 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.</string>
<string name="KeepMediaForever">Per sempre</string>
<!--sessions view-->
<string name="SessionsTitle">Sessioni attive</string>
<string name="CurrentSession">Sessione corrente</string>
@ -634,7 +652,7 @@
<string name="ResetMyAccount">RIPRISTINA IL MIO ACCOUNT</string>
<string name="ResetMyAccountText">Perderai tutte le chat e i messaggi, insieme ai media e ai file condivisi, se procederai a ripristinare il tuo account.</string>
<string name="ResetMyAccountWarning">Attenzione</string>
<string name="ResetMyAccountWarningText">Questa azione non può essere annullata.\n\n Se ripristini il tuo account, tutti i tuoi messaggi e chat saranno eliminati.</string>
<string name="ResetMyAccountWarningText">Questa azione non può essere annullata.\n\nSe ripristini il tuo account, tutti i tuoi messaggi e chat saranno eliminati.</string>
<string name="ResetMyAccountWarningReset">Ripristina</string>
<string name="LoginPassword">Password</string>
<string name="LoginPasswordText">Hai attivato la verifica in due passaggi, così il tuo account è protetto con una password aggiuntiva.</string>
@ -781,6 +799,8 @@
<string name="AreYouSureSecretChat">Iniziare una chat segreta?</string>
<string name="AreYouSureRegistration">Sei sicuro di volere eliminare questa registrazione?</string>
<string name="AreYouSureClearHistory">Sei sicuro di volere eliminare la cronologia?</string>
<string name="AreYouSureClearHistoryChannel">Eliminare tutti i messaggi e i media salvati nella cache per questo canale?</string>
<string name="AreYouSureClearHistorySuper">Eliminare tutti i messaggi e i media salvati nella cache per questo supergruppo?</string>
<string name="AreYouSureDeleteMessages">Sei sicuro di voler eliminare %1$s?</string>
<string name="SendMessagesToGroup">Inviare messaggi a %1$s?</string>
<string name="SendContactToGroup">Inviare contatto a %1$s?</string>
@ -1010,6 +1030,6 @@
<string name="formatterDay12H">h:mm a</string>
<string name="formatDateAtTime">%1$s alle %2$s</string>
<!--update text-->
<string name="updateText">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</string>
<string name="updateBuild">677</string>
<string name="updateText">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</string>
<string name="updateBuild">693</string>
</resources>

View File

@ -46,6 +46,7 @@
<string name="EncryptedChatStartedOutgoing">%s님이 비밀대화에 참여했습니다.</string>
<string name="EncryptedChatStartedIncoming">비밀대화에 참여했습니다.</string>
<string name="ClearHistory">대화내용 지우기</string>
<string name="ClearHistoryCache">캐시에서 삭제</string>
<string name="DeleteChat">채팅방 나가기</string>
<string name="DeleteChatUser">이 대화 삭제</string>
<string name="HiddenName">탈퇴한 계정</string>
@ -82,7 +83,8 @@
<string name="GroupUserCantBot">죄송합니다, 그룹방에 너무 많은 봇이 있습니다.</string>
<string name="ActionMigrateFromGroup">이 그룹방은 슈퍼그룹방으로 업그레이드 되었습니다.</string>
<string name="ActionMigrateFromGroupNotify">%1$s 그룹방은 슈퍼그룹방으로 업그레이드 되었습니다.</string>
<string name="NoBlockedGroup">그룹방에서 차단되어 퇴장당한 사용자는 관리자가 초대해야지만 그룹방에 입장이 가능합니다.\n초대링크로는 초대가 되지 않습니다.</string>
<string name="NoBlockedGroup">그룹방에서 차단되어 퇴장당한 사용자는 관리자가 초대해야지만 그룹방에 입장이 가능합니다.
초대링크로는 초대가 되지 않습니다.</string>
<string name="NewChannel">새 채널</string>
<string name="EnterChannelName">채널명</string>
<string name="Comments">코멘트들</string>
@ -127,8 +129,10 @@
<string name="ChannelLeaveAlert">채널에서 나가시겠습니까?</string>
<string name="ChannelDeleteInfo">채널에 있는 모든 메시지가 삭제됩니다.</string>
<string name="ChannelEdit">편집</string>
<string name="ChannelWasPrivateAlert">채널에 대한 공개링크를 선택하신 경우, 누구나 검색을 통하여 입장 가능합니다.\n\n비공개 채널로 유지를 하시고 싶으실 경우 링크 생성을 하지 말아주세요</string>
<string name="ChannelPublicEmptyUsername">유저들이 공개 채널에 대하여 검색 및 공유가 가능하도록 링크를 선택하여 주세요.\n\n채널을 공개하시지 싫으실 경우, 비공개 채널을 추천드립니다.</string>
<string name="ChannelWasPrivateAlert">채널에 대한 공개링크를 선택하신 경우, 누구나 검색을 통하여 입장 가능합니다.\n\n
비공개 채널로 유지를 하시고 싶으실 경우 링크 생성을 하지 말아주세요</string>
<string name="ChannelPublicEmptyUsername">유저들이 공개 채널에 대하여 검색 및 공유가 가능하도록 링크를 선택하여 주세요.\n\n
채널을 공개하시지 싫으실 경우, 비공개 채널을 추천드립니다.</string>
<string name="ActionCreateChannel">채널 생성됨</string>
<string name="ActionChannelChangedPhoto">채널 사진 업데이트됨</string>
<string name="ActionChannelRemovedPhoto">채널 사진 삭제됨</string>
@ -437,7 +441,6 @@
<string name="TerminateAllSessions">다른 모든 세션 종료</string>
<string name="Events">이벤트</string>
<string name="ContactJoined">친구의 텔레그램 가입 알림</string>
<string name="Pebble">PEBBLE 스마트워치 지원</string>
<string name="Language">언어</string>
<string name="AskAQuestionInfo">텔레그램에 관한 질문은 자원봉사자들이 답변해 드립니다. 신속한 답변을 위해 노력하지만 답변이 다소 늦을 수 있습니다.<![CDATA[<br><br>]]>일반적인 문제와 <![CDATA[<a href=\"https://telegram.org/faq/ko#g\">해결방법</a>]]>에 대해서는 \'<![CDATA[<a href=\"https://telegram.org/faq/ko#a\">자주 묻는 질문</a>]]>\'을 확인해 보세요.</string>
<string name="AskButton">질문하기</string>
@ -499,6 +502,24 @@
<string name="SmartNotificationsTimes"></string>
<string name="SmartNotificationsWithin">이내</string>
<string name="SmartNotificationsMinutes"></string>
<!--cache view-->
<string name="CacheSettings">캐시 설정</string>
<string name="LocalDatabase">로컬 데이터베이스</string>
<string name="LocalDatabaseClear">캐시된 텍스트 메시지를 삭제하시겠습니까?</string>
<string name="LocalDatabaseInfo">압축된 데이터베이스 및 캐시에 저장된 메시지를 로컬 데이터베이스에서 삭제하면 내부 저장공간이 증가합니다. 데이터베이스는 Telegram이 작동하는데 어느정도 필요함으로 완전히 삭제가 되지는 않습니다.\n\n이 작업은 완료되기까지 몇분정도 소요가 될 수 있습니다.</string>
<string name="ClearMediaCache">캐시 삭제</string>
<string name="CacheClear">삭제</string>
<string name="CalculatingSize">계산중...</string>
<string name="LocalDocumentCache">문서</string>
<string name="LocalPhotoCache">사진</string>
<string name="LocalAudioCache">음성 메시지</string>
<string name="LocalVideoCache">동영상</string>
<string name="LocalMusicCache">음악</string>
<string name="LocalCache">다른 파일</string>
<string name="CacheEmpty">없음</string>
<string name="KeepMedia">미디어 저장</string>
<string name="KeepMediaInfo">이 기간 동안 클라우드 채팅방에서 <![CDATA[<b>접근하지 않은</b>]]> 사진이나 동영상, 기타 파일 등은 공간 절약을 위해 이 기기에서 삭제됩니다.\n\n모든 파일은 Telegram 클라우드에 여전히 남으며 필요하시면 언제든 다시 다운로드하실 수 있습니다.</string>
<string name="KeepMediaForever">영원히</string>
<!--sessions view-->
<string name="SessionsTitle">활성화된 세션</string>
<string name="CurrentSession">현재 세션</string>
@ -781,6 +802,8 @@
<string name="AreYouSureSecretChat">비밀대화를 시작할까요?</string>
<string name="AreYouSureRegistration">정말로 가입을 취소하시겠습니까?</string>
<string name="AreYouSureClearHistory">정말로 대화내용을 지우시겠습니까?</string>
<string name="AreYouSureClearHistoryChannel">채널에서 캐시된 모든 텍스트 및 미디어를 삭제하시겠습니까?</string>
<string name="AreYouSureClearHistorySuper">슈커그룹에서 캐시된 모든 텍스트 및 미디어를 삭제하시겠습니까?</string>
<string name="AreYouSureDeleteMessages">%1$s: 정말로 삭제하시겠습니까?</string>
<string name="SendMessagesToGroup">%1$s 그룹에 메시지를 보낼까요?</string>
<string name="SendContactToGroup">%1$s에게 연락처를 보내시겠습니까?</string>
@ -1010,6 +1033,6 @@
<string name="formatterDay12H">a h:mm</string>
<string name="formatDateAtTime">%1$s %2$s</string>
<!--update text-->
<string name="updateText">텔레그램 안드로이드 버전이 업데이트 되었습니다. 새로운 버전은 3.3.0 입니다:\n\n- 그룹방제목, 그룹방사진, 구성원 추가 및 삭제등을 할 수 있는 복수의 그룹 관리자 설정 가능\n- 200명 제한이 걸린 그룹은 1,000명까지 활용가능한 슈퍼그룹으로 업그레이드 가능\n\n슈퍼그룹 및 업데이트 관련 내용 :\nhttps://telegram.org/blog/supergroups</string>
<string name="updateBuild">677</string>
<string name="updateText">텔레그램 안드로이드 버전이 업데이트 되었습니다. 새로운 버전은 3.3.2 입니다:\n\n- 캐시 관리: 저장소에서 텔레그램이 어느정도 사용하는지 관리가능, 각 기기에서 특정 컨텐츠 삭제 가능.\n- 슈퍼그룹 및 채널 캐시 삭제: 채팅목록에서 꾹 누르고 있으면 \'캐시에서 삭제\' 메뉴 선택 가능.\n- 스티커 관리: 수동으로 스티커팩 수정가능. 팩 순서는 모든 기기와 동기화 됩니다.\n\n자세한 업데이트는 https://telegram.org/blog/cache-and-stickers에서 확인하세요.</string>
<string name="updateBuild">693</string>
</resources>

View File

@ -4,7 +4,7 @@
<resources>
<string name="AppName">Telegram</string>
<string name="AppNameBeta">Telegram Bèta</string>
<string name="AppNameBeta">Telegram-bèta</string>
<string name="LanguageName">Nederlands</string>
<string name="LanguageNameInEnglish">Dutch</string>
<string name="LanguageCode">nl</string>
@ -46,6 +46,7 @@
<string name="EncryptedChatStartedOutgoing">%s neemt deel aan je geheime chat.</string>
<string name="EncryptedChatStartedIncoming">Toegevoegd aan de geheime chat.</string>
<string name="ClearHistory">Geschiedenis wissen</string>
<string name="ClearHistoryCache">Cache opschonen</string>
<string name="DeleteChat">Verwijder en verlaat</string>
<string name="DeleteChatUser">Chat verwijderen</string>
<string name="HiddenName">Verwijderd account</string>
@ -80,8 +81,8 @@
<string name="GroupUserLeftError">Deze gebruiker heeft de groep verlaten. Je kunt hem/haar niet meer uitnodigen.</string>
<string name="GroupUserCantAdmin">Maximaal aantal beheerders bereikt.</string>
<string name="GroupUserCantBot">Maximaal aantal bots bereikt.</string>
<string name="ActionMigrateFromGroup">De groep is omgezet naar een supergroep</string>
<string name="ActionMigrateFromGroupNotify">%1$s is omgezet naar een supergroep</string>
<string name="ActionMigrateFromGroup">De groep is opgewaardeerd naar een supergroep</string>
<string name="ActionMigrateFromGroupNotify">%1$s is opgewaardeerd naar een supergroep</string>
<string name="NoBlockedGroup">Geblokkeerde gebruikers kunnen alleen worden uitgenodigd door beheerders, uitnodigingslinks werken niet voor hen.</string>
<string name="NewChannel">Nieuw kanaal</string>
<string name="EnterChannelName">Kanaalnaam</string>
@ -352,9 +353,9 @@
<string name="DeleteAndExit">Groep verwijderen en verlaten</string>
<string name="Notifications">Meldingen</string>
<string name="KickFromGroup">Verwijderen uit groep</string>
<string name="ConvertGroup">Upgraden naar supergroep</string>
<string name="ConvertGroupAlert">Groepsdeelnemers moeten updaten naar de meest recente Telegram om je supergroep te kunnen zien. Groep echt upgraden?</string>
<string name="ConvertGroupInfo"><![CDATA[<b>]]>Deelnemerslimiet bereikt.<![CDATA[</b>]]>\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</string>
<string name="ConvertGroup">Opwaarderen naar supergroep</string>
<string name="ConvertGroupAlert">Groepsdeelnemers moeten updaten naar de meest recente Telegram om je supergroep te kunnen zien. Groep echt opwaarderen?</string>
<string name="ConvertGroupInfo"><![CDATA[<b>]]>Deelnemerslimiet bereikt.<![CDATA[</b>]]>\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</string>
<!--contact info view-->
<string name="ShareContact">Delen</string>
<string name="AddContact">Toevoegen</string>
@ -437,7 +438,6 @@
<string name="TerminateAllSessions">Beëindig alle andere sessies</string>
<string name="Events">Gebeurtenissen</string>
<string name="ContactJoined">Contact lid van Telegram</string>
<string name="Pebble">PEBBLE</string>
<string name="Language">Taal</string>
<string name="AskAQuestionInfo">De ondersteuning van Telegram wordt gedaan door vrijwilligers. We doen ons best om zo snel mogelijk te antwoorden.<![CDATA[<br><br>]]>Bekijk ook de <![CDATA[<a href=\"https://telegram.org/faq#general\">veelgestelde vragen</a>]]>: Hier staan de antwoorden op de meeste vragen en belangrijke tips voor <![CDATA[<a href=\"https://telegram.org/faq#troubleshooting\">het oplossen van problemen</a>]]>.</string>
<string name="AskButton">Vraag een vrijwilliger</string>
@ -462,7 +462,7 @@
<string name="BadgeNumber">Badgenummer</string>
<string name="Short">Kort</string>
<string name="Long">Lang</string>
<string name="SystemDefault">Standaardinstelling</string>
<string name="SystemDefault">Systeeminstelling</string>
<string name="SettingsDefault">Standaardinstelling</string>
<string name="AutomaticMediaDownload">Automatisch media downloaden</string>
<string name="WhenUsingMobileData">Bij mobiele verbinding</string>
@ -499,6 +499,24 @@
<string name="SmartNotificationsTimes">keer</string>
<string name="SmartNotificationsWithin">binnen</string>
<string name="SmartNotificationsMinutes">minuten</string>
<!--cache view-->
<string name="CacheSettings">Cache-instellingen</string>
<string name="LocalDatabase">Lokale database</string>
<string name="LocalDatabaseClear">Gecachet tekstberichten wissen?</string>
<string name="LocalDatabaseInfo">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.</string>
<string name="ClearMediaCache">Cache opschonen</string>
<string name="CacheClear">Opschonen</string>
<string name="CalculatingSize">Berekenen...</string>
<string name="LocalDocumentCache">Bestanden</string>
<string name="LocalPhotoCache">Foto\'s</string>
<string name="LocalAudioCache">Spraakberichten</string>
<string name="LocalVideoCache">Video\'s</string>
<string name="LocalMusicCache">Muziek</string>
<string name="LocalCache">Overige bestanden</string>
<string name="CacheEmpty">Leeg</string>
<string name="KeepMedia">Media bewaren</string>
<string name="KeepMediaInfo">Foto\'s, video\'s en andere bestanden uit cloudchats die je gedurende deze periode niet hebt <![CDATA[<b>geopend</b>]]> 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.</string>
<string name="KeepMediaForever">Voor altijd</string>
<!--sessions view-->
<string name="SessionsTitle">Actieve sessies</string>
<string name="CurrentSession">Huidige sessie</string>
@ -781,6 +799,8 @@
<string name="AreYouSureSecretChat">Weet je zeker dat je een geheime chat wilt starten?</string>
<string name="AreYouSureRegistration">Weet je zeker dat je de registratie wilt annuleren?</string>
<string name="AreYouSureClearHistory">Geschiedenis echt wissen? </string>
<string name="AreYouSureClearHistoryChannel">Kanaalcache opschonen?</string>
<string name="AreYouSureClearHistorySuper">Supergroepcache echt opschonen?</string>
<string name="AreYouSureDeleteMessages">%1$s echt verwijderen?</string>
<string name="SendMessagesToGroup">Berichten naar %1$s versturen?</string>
<string name="SendContactToGroup">Contact delen met %1$s?</string>
@ -824,7 +844,7 @@
<string name="Members_many">%1$d deelnemers</string>
<string name="Members_other">%1$d deelnemers</string>
<string name="AndMoreTyping_zero">en nog %1$d personen zijn aan het typen</string>
<string name="AndMoreTyping_one">en nog %1$d personen zijn aan het typen</string>
<string name="AndMoreTyping_one">en nog %1$d persoon is aan het typen</string>
<string name="AndMoreTyping_two">en nog %1$d personen zijn aan het typen</string>
<string name="AndMoreTyping_few">en nog %1$d personen zijn aan het typen</string>
<string name="AndMoreTyping_many">en nog %1$d personen zijn aan het typen</string>
@ -962,7 +982,7 @@
<string name="ForwardedPhoto_few">Bijlage: %1$d foto\'s</string>
<string name="ForwardedPhoto_many">Bijlage: %1$d foto\'s</string>
<string name="ForwardedPhoto_other">Bijlage: %1$d foto\'s</string>
<string name="ForwardedVideo_zero">Bijlage: %1$d foto\'s</string>
<string name="ForwardedVideo_zero">Bijlage: %1$d video\'s</string>
<string name="ForwardedVideo_one">Bijlage: 1 video</string>
<string name="ForwardedVideo_two">Bijlage: %1$d video\'s</string>
<string name="ForwardedVideo_few">Bijlage: %1$d video\'s</string>
@ -1010,6 +1030,6 @@
<string name="formatterDay12H">h:mm a</string>
<string name="formatDateAtTime">%1$s om %2$s</string>
<!--update text-->
<string name="updateText">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</string>
<string name="updateBuild">677</string>
<string name="updateText">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</string>
<string name="updateBuild">693</string>
</resources>

View File

@ -46,6 +46,7 @@
<string name="EncryptedChatStartedOutgoing">%s entrou no chat secreto</string>
<string name="EncryptedChatStartedIncoming">Você entrou no chat secreto</string>
<string name="ClearHistory">Limpar histórico</string>
<string name="ClearHistoryCache">Apagar do cache</string>
<string name="DeleteChat">Apagar e sair</string>
<string name="DeleteChatUser">Apagar conversa</string>
<string name="HiddenName">Conta Excluída</string>
@ -437,7 +438,6 @@
<string name="TerminateAllSessions">Terminar todas as outras sessões</string>
<string name="Events">Eventos</string>
<string name="ContactJoined">Contato entrou para o Telegram</string>
<string name="Pebble">PEBBLE</string>
<string name="Language">Idioma</string>
<string name="AskAQuestionInfo">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.<![CDATA[<br><br>]]>Por favor verifique a <![CDATA[<a href=\"https://telegram.org/faq#general\">página de perguntas frequentes do Telegram</a>]]>: há dicas e respostas para a maioria dos <![CDATA[<a href=\"https://telegram.org/faq#troubleshooting\">problemas</a>]]>.</string>
<string name="AskButton">Pergunte a um voluntário</string>
@ -499,6 +499,24 @@
<string name="SmartNotificationsTimes">vezes</string>
<string name="SmartNotificationsWithin">a cada</string>
<string name="SmartNotificationsMinutes">minutos</string>
<!--cache view-->
<string name="CacheSettings">Configurações de Cache</string>
<string name="LocalDatabase">Banco de Dados Local</string>
<string name="LocalDatabaseClear">Limpar todos os textos em cache?</string>
<string name="LocalDatabaseInfo">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.</string>
<string name="ClearMediaCache">Limpar Cache</string>
<string name="CacheClear">Limpar</string>
<string name="CalculatingSize">Calculando...</string>
<string name="LocalDocumentCache">Documentos</string>
<string name="LocalPhotoCache">Fotos</string>
<string name="LocalAudioCache">Mensagens de voz</string>
<string name="LocalVideoCache">Vídeos</string>
<string name="LocalMusicCache">Música</string>
<string name="LocalCache">Outros arquivos</string>
<string name="CacheEmpty">Vazio</string>
<string name="KeepMedia">Manter Mídias</string>
<string name="KeepMediaInfo">Fotos, vídeos e outros arquivos da nuvem que você <![CDATA[<b>não acessou</b>]]> 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.</string>
<string name="KeepMediaForever">Permanentemente</string>
<!--sessions view-->
<string name="SessionsTitle">Sessões Ativas</string>
<string name="CurrentSession">Sessão atual</string>
@ -781,6 +799,8 @@
<string name="AreYouSureSecretChat">Você tem certeza que deseja começar um chat secreto?</string>
<string name="AreYouSureRegistration">Você tem certeza que deseja cancelar o registro?</string>
<string name="AreYouSureClearHistory">Você tem certeza que deseja limpar o histórico?</string>
<string name="AreYouSureClearHistoryChannel">Apagar todos os textos e mídias em cache desse canal?</string>
<string name="AreYouSureClearHistorySuper">Apagar todos os textos e mídias em cache desse supergrupo?</string>
<string name="AreYouSureDeleteMessages">Você tem certeza que deseja apagar %1$s?</string>
<string name="SendMessagesToGroup">Enviar mensagens para %1$s?</string>
<string name="SendContactToGroup">Enviar contato para %1$s?</string>
@ -1010,6 +1030,6 @@
<string name="formatterDay12H">h:mm a</string>
<string name="formatDateAtTime">%1$s às %2$s</string>
<!--update text-->
<string name="updateText">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</string>
<string name="updateBuild">677</string>
<string name="updateText">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</string>
<string name="updateBuild">693</string>
</resources>

View File

@ -46,6 +46,7 @@
<string name="EncryptedChatStartedOutgoing">%s entrou no chat secreto</string>
<string name="EncryptedChatStartedIncoming">Você entrou no chat secreto</string>
<string name="ClearHistory">Limpar histórico</string>
<string name="ClearHistoryCache">Apagar do cache</string>
<string name="DeleteChat">Apagar e sair</string>
<string name="DeleteChatUser">Apagar conversa</string>
<string name="HiddenName">Conta Excluída</string>
@ -437,7 +438,6 @@
<string name="TerminateAllSessions">Terminar todas as outras sessões</string>
<string name="Events">Eventos</string>
<string name="ContactJoined">Contato entrou para o Telegram</string>
<string name="Pebble">PEBBLE</string>
<string name="Language">Idioma</string>
<string name="AskAQuestionInfo">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.<![CDATA[<br><br>]]>Por favor verifique a <![CDATA[<a href=\"https://telegram.org/faq#general\">página de perguntas frequentes do Telegram</a>]]>: há dicas e respostas para a maioria dos <![CDATA[<a href=\"https://telegram.org/faq#troubleshooting\">problemas</a>]]>.</string>
<string name="AskButton">Pergunte a um voluntário</string>
@ -499,6 +499,24 @@
<string name="SmartNotificationsTimes">vezes</string>
<string name="SmartNotificationsWithin">a cada</string>
<string name="SmartNotificationsMinutes">minutos</string>
<!--cache view-->
<string name="CacheSettings">Configurações de Cache</string>
<string name="LocalDatabase">Banco de Dados Local</string>
<string name="LocalDatabaseClear">Limpar todos os textos em cache?</string>
<string name="LocalDatabaseInfo">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.</string>
<string name="ClearMediaCache">Limpar Cache</string>
<string name="CacheClear">Limpar</string>
<string name="CalculatingSize">Calculando...</string>
<string name="LocalDocumentCache">Documentos</string>
<string name="LocalPhotoCache">Fotos</string>
<string name="LocalAudioCache">Mensagens de voz</string>
<string name="LocalVideoCache">Vídeos</string>
<string name="LocalMusicCache">Música</string>
<string name="LocalCache">Outros arquivos</string>
<string name="CacheEmpty">Vazio</string>
<string name="KeepMedia">Manter Mídias</string>
<string name="KeepMediaInfo">Fotos, vídeos e outros arquivos da nuvem que você <![CDATA[<b>não acessou</b>]]> 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.</string>
<string name="KeepMediaForever">Permanentemente</string>
<!--sessions view-->
<string name="SessionsTitle">Sessões Ativas</string>
<string name="CurrentSession">Sessão atual</string>
@ -781,6 +799,8 @@
<string name="AreYouSureSecretChat">Você tem certeza que deseja começar um chat secreto?</string>
<string name="AreYouSureRegistration">Você tem certeza que deseja cancelar o registro?</string>
<string name="AreYouSureClearHistory">Você tem certeza que deseja limpar o histórico?</string>
<string name="AreYouSureClearHistoryChannel">Apagar todos os textos e mídias em cache desse canal?</string>
<string name="AreYouSureClearHistorySuper">Apagar todos os textos e mídias em cache desse supergrupo?</string>
<string name="AreYouSureDeleteMessages">Você tem certeza que deseja apagar %1$s?</string>
<string name="SendMessagesToGroup">Enviar mensagens para %1$s?</string>
<string name="SendContactToGroup">Enviar contato para %1$s?</string>
@ -1010,6 +1030,6 @@
<string name="formatterDay12H">h:mm a</string>
<string name="formatDateAtTime">%1$s às %2$s</string>
<!--update text-->
<string name="updateText">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</string>
<string name="updateBuild">677</string>
<string name="updateText">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</string>
<string name="updateBuild">693</string>
</resources>

View File

@ -46,6 +46,7 @@
<string name="EncryptedChatStartedOutgoing">%s joined your secret chat.</string>
<string name="EncryptedChatStartedIncoming">You joined the secret chat.</string>
<string name="ClearHistory">Clear history</string>
<string name="ClearHistoryCache">Delete from cache</string>
<string name="DeleteChat">Delete and exit</string>
<string name="DeleteChatUser">Delete chat</string>
<string name="HiddenName">Deleted Account</string>
@ -437,7 +438,6 @@
<string name="TerminateAllSessions">Terminate All Other Sessions</string>
<string name="Events">Events</string>
<string name="ContactJoined">Contact joined Telegram</string>
<string name="Pebble">PEBBLE</string>
<string name="Language">Language</string>
<string name="AskAQuestionInfo">Please note that Telegram Support is done by volunteers. We try to respond as quickly as possible, but it may take a while.<![CDATA[<br><br>]]>Please take a look at the <![CDATA[<a href=\"https://telegram.org/faq#general\">Telegram FAQ</a>]]>: it has answers to most questions and important tips for <![CDATA[<a href=\"https://telegram.org/faq#troubleshooting\">troubleshooting</a>]]>.</string>
<string name="AskButton">Ask a volunteer</string>
@ -499,6 +499,24 @@
<string name="SmartNotificationsTimes">times</string>
<string name="SmartNotificationsWithin">within</string>
<string name="SmartNotificationsMinutes">minutes</string>
<!--cache view-->
<string name="CacheSettings">Cache Settings</string>
<string name="LocalDatabase">Local Database</string>
<string name="LocalDatabaseClear">Clear cached text messages?</string>
<string name="LocalDatabaseInfo">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.</string>
<string name="ClearMediaCache">Clear Cache</string>
<string name="CacheClear">Clear</string>
<string name="CalculatingSize">Calculating...</string>
<string name="LocalDocumentCache">Documents</string>
<string name="LocalPhotoCache">Photos</string>
<string name="LocalAudioCache">Voice messages</string>
<string name="LocalVideoCache">Videos</string>
<string name="LocalMusicCache">Music</string>
<string name="LocalCache">Other files</string>
<string name="CacheEmpty">Empty</string>
<string name="KeepMedia">Keep Media</string>
<string name="KeepMediaInfo">Photos, videos and other files from cloud chats that you have <![CDATA[<b>not accessed</b>]]> 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.</string>
<string name="KeepMediaForever">Forever</string>
<!--sessions view-->
<string name="SessionsTitle">Active Sessions</string>
<string name="CurrentSession">Current session</string>
@ -781,6 +799,8 @@
<string name="AreYouSureSecretChat">Are you sure you want to start a secret chat?</string>
<string name="AreYouSureRegistration">Are you sure you want to cancel registration?</string>
<string name="AreYouSureClearHistory">Are you sure you want to clear history?</string>
<string name="AreYouSureClearHistoryChannel">Delete all cached text and media from this channel?</string>
<string name="AreYouSureClearHistorySuper">Delete all cached text and media from this supergroup?</string>
<string name="AreYouSureDeleteMessages">Are you sure you want to delete %1$s?</string>
<string name="SendMessagesToGroup">Send messages to %1$s?</string>
<string name="SendContactToGroup">Send contact to %1$s?</string>
@ -1010,6 +1030,6 @@
<string name="formatterDay12H">h:mm a</string>
<string name="formatDateAtTime">%1$s at %2$s</string>
<!--update text-->
<string name="updateText">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</string>
<string name="updateBuild">677</string>
<string name="updateText">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</string>
<string name="updateBuild">693</string>
</resources>