This commit is contained in:
John Preston 2015-03-02 15:35:13 +03:00
commit 7630b47c3a
64 changed files with 2699 additions and 1197 deletions

View file

@ -1,9 +1,9 @@
@echo OFF
set "AppVersion=7018"
set "AppVersionStrSmall=0.7.18"
set "AppVersionStr=0.7.18"
set "AppVersionStrFull=0.7.18.0"
set "AppVersion=7019"
set "AppVersionStrSmall=0.7.19"
set "AppVersionStr=0.7.19"
set "AppVersionStrFull=0.7.19.0"
set "DevChannel=1"
if %DevChannel% neq 0 goto preparedev

View file

@ -227,6 +227,27 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
"lng_local_storage_clear_failed" = "Clear failed :(";
"lng_settings_section_advanced" = "Advanced";
"lng_passcode_turn_on" = "Turn passcode on";
"lng_passcode_change" = "Change passcode";
"lng_passcode_create" = "Create passcode";
"lng_passcode_remove" = "Remove passcode";
"lng_passcode_turn_off" = "Turn off";
"lng_passcode_autolock_away" = "Auto-Lock if away for:";
"lng_passcode_autolock_inactive" = "Auto-Lock if inactive for:";
"lng_passcode_autolock_minutes" = "{count:_not_used_|# minute|# minutes}";
"lng_passcode_autolock_hours" = "{count:_not_used_|# hour|# hours}";
"lng_passcode_enter_old" = "Enter old passcode";
"lng_passcode_enter_new" = "Enter new passcode";
"lng_passcode_confirm_new" = "Re-enter new passcode";
"lng_passcode_about" = "When you set up a passcode, a lock icon will appear in the corner. Tap it to lock the app.\n\nNote: if you forget the passcode, you'll need to relogin in Telegram Desktop.";
"lng_passcode_differ" = "Passcodes are different";
"lng_passcode_wrong" = "Wrong passcode";
"lng_passcode_is_same" = "Passcode was not changed";
"lng_passcode_enter" = "Enter your Telegram Passcode";
"lng_passcode_submit" = "Submit";
"lng_passcode_logout" = "or you can {link_start}log out »{link_end}";
"lng_connection_type" = "Connection type:";
"lng_connection_auto_connecting" = "Default (connecting..)";
"lng_connection_auto" = "Default ({type} used)";

View file

@ -52,7 +52,7 @@ wndMinHeight: 480px;
wndDefWidth: 800px;
wndDefHeight: 600px;
wndBG: #FFF;
wndShadow: sprite(184px, 21px, 19px, 19px);
wndShadow: sprite(209px, 46px, 19px, 19px);
wndShadowShift: 1px;
layerAlpha: 0.3;
@ -116,6 +116,12 @@ sysRes: sysButton(sysUpd) {
sysCls: sysButton(sysUpd) {
img: sprite(276px, 1px, 19px, 19px);
}
sysLock: sysButton(sysUpd) {
img: sprite(184px, 22px, 19px, 19px);
}
sysUnlock: sysButton(sysUpd) {
img: sprite(207px, 22px, 19px, 19px);
}
titleBackButton: iconedButton(btnDefIconed) {
icon: sprite(133px, 197px, 13px, 20px);
iconPos: point(5px, 9px);
@ -383,7 +389,7 @@ btnIntroNext: flatButton(btnDefNext, btnDefBig) {
width: 300px;
}
boxShadow: sprite(240px, 21px, 9px, 9px);
boxShadow: sprite(230px, 46px, 9px, 9px);
introCountry: countryInput {
width: 300px;
@ -637,7 +643,7 @@ dlgFilter: flatInput(inpDefGray) {
phColor: #949494;
phFocusColor: #a4a4a4;
textMrg: margins(34px, 2px, 34px, 4px);
imgRect: sprite(208px, 28px, 24px, 24px);
imgRect: sprite(227px, 21px, 24px, 24px);
imgPos: point(6px, 5px);
width: 240px;
@ -1189,7 +1195,7 @@ participantFilter: flatInput(inpDefFlat) {
height: 52px;
font: font(16px);
textMrg: margins(39px, 11px, 10px, 10px);
imgRect: sprite(208px, 28px, 24px, 24px);
imgRect: sprite(227px, 21px, 24px, 24px);
imgPos: point(10px, 15px);
}
participantDelta: 12px;
@ -1308,7 +1314,7 @@ connectingColor: #777;
connectingPadding: margins(5px, 5px, 5px, 5px);
dropdownPadding: margins(10px, 10px, 10px, 10px);
dropdownShadow: sprite(240px, 35px, 6px, 6px);
dropdownShadow: sprite(241px, 46px, 6px, 6px);
dropdownBorder: 1px;
dropdownBorderColor: #ebebeb;
dropdownBackground: white;
@ -1694,3 +1700,17 @@ backgroundSize: size(108px, 193px);
backgroundScroll: flatScroll(newGroupScroll) {
topsh: -2px;
}
passcodeHeaderFont: font(19px);
passcodeHeaderHeight: 80px;
passcodeSkip: 40px;
passcodeInput: flatInput(inpIntroPhone) {
}
passcodeSubmit: flatButton(btnIntroNext) {
textTop: 15px;
overTextTop: 15px;
downTextTop: 16px;
width: 225px;
font: font(19px);
overFont: font(19px);
}

View file

@ -61,6 +61,7 @@ Type: files; Name: "{app}\log.txt"
Type: filesandordirs; Name: "{app}\DebugLogs"
Type: filesandordirs; Name: "{app}\tupdates"
Type: filesandordirs; Name: "{app}\tdata"
Type: filesandordirs; Name: "{app}\tcache"
Type: filesandordirs; Name: "{app}\tdumps"
Type: dirifempty; Name: "{app}"
Type: files; Name: "{userappdata}\{#MyAppName}\data"
@ -69,6 +70,7 @@ Type: files; Name: "{userappdata}\{#MyAppName}\log.txt"
Type: filesandordirs; Name: "{userappdata}\{#MyAppName}\DebugLogs"
Type: filesandordirs; Name: "{userappdata}\{#MyAppName}\tupdates"
Type: filesandordirs; Name: "{userappdata}\{#MyAppName}\tdata"
Type: filesandordirs; Name: "{userappdata}\{#MyAppName}\tcache"
Type: filesandordirs; Name: "{userappdata}\{#MyAppName}\tdumps"
Type: dirifempty; Name: "{userappdata}\{#MyAppName}"

View file

@ -18,8 +18,6 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "stdafx.h"
#include "lang.h"
#include "app.h"
#include "audio.h"
#include "application.h"
#include "fileuploader.h"
@ -111,6 +109,11 @@ namespace App {
return w ? w->settingsWidget() : 0;
}
bool passcoded() {
Window *w(wnd());
return w ? w->passcodeWidget() : 0;
}
FileUploader *uploader() {
return app() ? app()->uploader() : 0;
}
@ -122,6 +125,9 @@ namespace App {
bool loggedOut() {
Window *w(wnd());
if (cHasPasscode()) {
cSetHasPasscode(false);
}
if (w) {
w->tempDirDelete(Local::ClearManagerAll);
w->notifyClearFast();
@ -130,6 +136,8 @@ namespace App {
MainWidget *m(main());
if (m) m->destroyData();
MTP::authed(0);
Local::reset();
cSetOtherOnline(0);
histories().clear();
globalNotifyAllPtr = UnknownNotifySettings;
@ -138,6 +146,7 @@ namespace App {
App::uploader()->clear();
clearStorageImages();
if (w) {
w->getTitle()->updateBackButton();
w->updateTitleStatus();
w->getTitle()->resizeEvent(0);
}
@ -145,7 +154,12 @@ namespace App {
}
void logOut() {
MTP::logoutKeys(rpcDone(&loggedOut), rpcFail(&loggedOut));
if (MTP::started()) {
MTP::logoutKeys(rpcDone(&loggedOut), rpcFail(&loggedOut));
} else {
loggedOut();
MTP::start();
}
}
PeerId peerFromMTP(const MTPPeer &peer_id) {
@ -1477,514 +1491,6 @@ namespace App {
if (cSoundNotify() && !psSkipAudioNotify()) audioPlayNotify();
}
void writeConfig() {
QDir().mkdir(cWorkingDir() + qsl("tdata"));
QFile configFile(cWorkingDir() + qsl("tdata/config"));
if (configFile.open(QIODevice::WriteOnly)) {
DEBUG_LOG(("App Info: writing config file"));
QDataStream configStream(&configFile);
configStream.setVersion(QDataStream::Qt_5_1);
configStream << quint32(dbiVersion) << qint32(AppVersion);
configStream << quint32(dbiAutoStart) << qint32(cAutoStart());
configStream << quint32(dbiStartMinimized) << qint32(cStartMinimized());
configStream << quint32(dbiSendToMenu) << qint32(cSendToMenu());
configStream << quint32(dbiWorkMode) << qint32(cWorkMode());
configStream << quint32(dbiSeenTrayTooltip) << qint32(cSeenTrayTooltip());
configStream << quint32(dbiAutoUpdate) << qint32(cAutoUpdate());
configStream << quint32(dbiLastUpdateCheck) << qint32(cLastUpdateCheck());
configStream << quint32(dbiScale) << qint32(cConfigScale());
configStream << quint32(dbiLang) << qint32(cLang());
configStream << quint32(dbiLangFile) << cLangFile();
configStream << quint32(dbiConnectionType) << qint32(cConnectionType());
if (cConnectionType() == dbictHttpProxy || cConnectionType() == dbictTcpProxy) {
const ConnectionProxy &proxy(cConnectionProxy());
configStream << proxy.host << qint32(proxy.port) << proxy.user << proxy.password;
}
TWindowPos pos(cWindowPos());
configStream << quint32(dbiWindowPosition) << qint32(pos.x) << qint32(pos.y) << qint32(pos.w) << qint32(pos.h) << qint32(pos.moncrc) << qint32(pos.maximized);
if (configStream.status() != QDataStream::Ok) {
LOG(("App Error: could not write user config file, status: %1").arg(configStream.status()));
}
} else {
LOG(("App Error: could not open user config file for writing"));
}
}
void readConfig() {
QFile configFile(cWorkingDir() + qsl("tdata/config"));
if (configFile.open(QIODevice::ReadOnly)) {
DEBUG_LOG(("App Info: config file opened for reading"));
QDataStream configStream(&configFile);
configStream.setVersion(QDataStream::Qt_5_1);
qint32 configVersion = 0;
while (true) {
quint32 blockId;
configStream >> blockId;
if (configStream.status() == QDataStream::ReadPastEnd) {
DEBUG_LOG(("App Info: config file read end"));
break;
} else if (configStream.status() != QDataStream::Ok) {
LOG(("App Error: could not read block id, status: %1 - config file is corrupted?..").arg(configStream.status()));
break;
}
if (blockId == dbiVersion) {
configStream >> configVersion;
if (configVersion > AppVersion) break;
continue;
}
switch (blockId) {
case dbiAutoStart: {
qint32 v;
configStream >> v;
cSetAutoStart(v == 1);
} break;
case dbiStartMinimized: {
qint32 v;
configStream >> v;
cSetStartMinimized(v == 1);
} break;
case dbiSendToMenu: {
qint32 v;
configStream >> v;
cSetSendToMenu(v == 1);
} break;
case dbiSoundNotify: {
if (configVersion < 3008) {
qint32 v;
configStream >> v;
cSetSoundNotify(v == 1);
cSetNeedConfigResave(true);
}
} break;
case dbiDesktopNotify: {
if (configVersion < 3008) {
qint32 v;
configStream >> v;
cSetDesktopNotify(v == 1);
cSetNeedConfigResave(true);
}
} break;
case dbiWorkMode: {
qint32 v;
configStream >> v;
switch (v) {
case dbiwmTrayOnly: cSetWorkMode(dbiwmTrayOnly); break;
case dbiwmWindowOnly: cSetWorkMode(dbiwmWindowOnly); break;
default: cSetWorkMode(dbiwmWindowAndTray); break;
};
} break;
case dbiConnectionType: {
qint32 v;
configStream >> v;
switch (v) {
case dbictHttpProxy:
case dbictTcpProxy: {
ConnectionProxy p;
qint32 port;
configStream >> p.host >> port >> p.user >> p.password;
p.port = uint32(port);
cSetConnectionProxy(p);
}
cSetConnectionType(DBIConnectionType(v));
break;
case dbictHttpAuto:
default: cSetConnectionType(dbictAuto); break;
};
} break;
case dbiSeenTrayTooltip: {
qint32 v;
configStream >> v;
cSetSeenTrayTooltip(v == 1);
} break;
case dbiAutoUpdate: {
qint32 v;
configStream >> v;
cSetAutoUpdate(v == 1);
} break;
case dbiLastUpdateCheck: {
qint32 v;
configStream >> v;
cSetLastUpdateCheck(v);
} break;
case dbiScale: {
qint32 v;
configStream >> v;
DBIScale s = cRealScale();
switch (v) {
case dbisAuto: s = dbisAuto; break;
case dbisOne: s = dbisOne; break;
case dbisOneAndQuarter: s = dbisOneAndQuarter; break;
case dbisOneAndHalf: s = dbisOneAndHalf; break;
case dbisTwo: s = dbisTwo; break;
}
if (cRetina()) s = dbisOne;
cSetConfigScale(s);
cSetRealScale(s);
} break;
case dbiLang: {
qint32 v;
configStream >> v;
if (v == languageTest || (v >= 0 && v < languageCount)) {
cSetLang(v);
}
} break;
case dbiLangFile: {
QString v;
configStream >> v;
cSetLangFile(v);
} break;
case dbiWindowPosition: {
TWindowPos pos;
configStream >> pos.x >> pos.y >> pos.w >> pos.h >> pos.moncrc >> pos.maximized;
cSetWindowPos(pos);
} break;
}
if (configStream.status() != QDataStream::Ok) {
LOG(("App Error: could not read data, status: %1 - user config file is corrupted?..").arg(configStream.status()));
break;
}
}
}
}
void writeUserConfig() {
QFile configFile(cWorkingDir() + cDataFile() + qsl("_config"));
if (configFile.open(QIODevice::WriteOnly)) {
DEBUG_LOG(("App Info: writing user config data for encrypt"));
QByteArray toEncrypt;
toEncrypt.reserve(65536);
toEncrypt.resize(4);
{
QBuffer buffer(&toEncrypt);
buffer.open(QIODevice::Append);
QDataStream stream(&buffer);
stream.setVersion(QDataStream::Qt_5_1);
if (MTP::authedId()) {
stream << quint32(dbiUser) << qint32(MTP::authedId()) << quint32(MTP::maindc());
}
stream << quint32(dbiSendKey) << qint32(cCtrlEnter() ? dbiskCtrlEnter : dbiskEnter);
stream << quint32(dbiTileBackground) << qint32(cTileBackground() ? 1 : 0);
stream << quint32(dbiReplaceEmojis) << qint32(cReplaceEmojis() ? 1 : 0);
stream << quint32(dbiDefaultAttach) << qint32(cDefaultAttach());
stream << quint32(dbiSoundNotify) << qint32(cSoundNotify());
stream << quint32(dbiDesktopNotify) << qint32(cDesktopNotify());
stream << quint32(dbiNotifyView) << qint32(cNotifyView());
stream << quint32(dbiAskDownloadPath) << qint32(cAskDownloadPath());
stream << quint32(dbiDownloadPath) << (cAskDownloadPath() ? QString() : cDownloadPath());
stream << quint32(dbiCompressPastedImage) << qint32(cCompressPastedImage());
stream << quint32(dbiEmojiTab) << qint32(cEmojiTab());
RecentEmojiPreload v;
v.reserve(cGetRecentEmojis().size());
for (RecentEmojiPack::const_iterator i = cGetRecentEmojis().cbegin(), e = cGetRecentEmojis().cend(); i != e; ++i) {
v.push_back(qMakePair(i->first->code, i->second));
}
stream << quint32(dbiRecentEmojis) << v;
writeAllMuted(stream);
MTP::writeConfig(stream);
if (stream.status() != QDataStream::Ok) {
LOG(("App Error: could not write user config to memory buf, status: %1").arg(stream.status()));
return;
}
}
*(uint32*)(toEncrypt.data()) = toEncrypt.size();
uint32 size = toEncrypt.size(), fullSize = size;
if (fullSize & 0x0F) {
fullSize += 0x10 - (fullSize & 0x0F);
toEncrypt.resize(fullSize);
memset_rand(toEncrypt.data() + size, fullSize - size);
}
QByteArray encrypted(16 + fullSize, Qt::Uninitialized); // 128bit of sha1 - key128, sizeof(data), data
hashSha1(toEncrypt.constData(), toEncrypt.size(), encrypted.data());
aesEncryptLocal(toEncrypt.constData(), encrypted.data() + 16, fullSize, &Local::oldKey(), encrypted.constData());
DEBUG_LOG(("App Info: writing user config file"));
QDataStream configStream(&configFile);
configStream.setVersion(QDataStream::Qt_5_1);
configStream << quint32(dbiVersion) << qint32(AppVersion);
configStream << quint32(dbiEncryptedWithSalt) << cLocalSalt() << encrypted; // write all encrypted data
if (configStream.status() != QDataStream::Ok) {
LOG(("App Error: could not write user config file, status: %1").arg(configStream.status()));
}
} else {
LOG(("App Error: could not open user config file for writing"));
}
}
void readUserConfigFields(QIODevice *io) {
if (!io->isOpen()) io->open(QIODevice::ReadOnly);
QDataStream stream(io);
stream.setVersion(QDataStream::Qt_5_1);
while (true) {
quint32 blockId;
stream >> blockId;
if (stream.status() == QDataStream::ReadPastEnd) {
DEBUG_LOG(("App Info: config file read end"));
break;
} else if (stream.status() != QDataStream::Ok) {
LOG(("App Error: could not read block id, status: %1 - user config file is corrupted?..").arg(stream.status()));
break;
}
if (blockId == dbiVersion) { // should not be in encrypted part, just ignore
qint32 configVersion;
stream >> configVersion;
continue;
}
switch (blockId) {
case dbiEncryptedWithSalt: {
QByteArray salt, data, decrypted;
stream >> salt >> data;
if (salt.size() != 32) {
LOG(("App Error: bad salt in encrypted part, size: %1").arg(salt.size()));
continue;
}
cSetLocalSalt(salt);
Local::createOldKey(&salt);
if (data.size() <= 16 || (data.size() & 0x0F)) {
LOG(("App Error: bad encrypted part size: %1").arg(data.size()));
continue;
}
uint32 fullDataLen = data.size() - 16;
decrypted.resize(fullDataLen);
const char *dataKey = data.constData(), *encrypted = data.constData() + 16;
aesDecryptLocal(encrypted, decrypted.data(), fullDataLen, &Local::oldKey(), dataKey);
uchar sha1Buffer[20];
if (memcmp(hashSha1(decrypted.constData(), decrypted.size(), sha1Buffer), dataKey, 16)) {
LOG(("App Error: bad decrypt key, data from user-config not decrypted"));
continue;
}
uint32 dataLen = *(const uint32*)decrypted.constData();
if (dataLen > uint32(decrypted.size()) || dataLen <= fullDataLen - 16 || dataLen < 4) {
LOG(("App Error: bad decrypted part size: %1, fullDataLen: %2, decrypted size: %3").arg(dataLen).arg(fullDataLen).arg(decrypted.size()));
continue;
}
decrypted.resize(dataLen);
QBuffer decryptedStream(&decrypted);
decryptedStream.open(QIODevice::ReadOnly);
decryptedStream.seek(4); // skip size
readUserConfigFields(&decryptedStream);
} break;
case dbiLoggedPhoneNumber: {
QString v;
stream >> v;
if (stream.status() == QDataStream::Ok) {
cSetLoggedPhoneNumber(v);
}
} break;
case dbiMutePeer: {
readOneMuted(stream);
} break;
case dbiMutedPeers: {
readAllMuted(stream);
} break;
case dbiSendKey: {
qint32 v;
stream >> v;
cSetCtrlEnter(v == dbiskCtrlEnter);
} break;
case dbiCatsAndDogs: {
qint32 v;
stream >> v;
} break;
case dbiTileBackground: {
qint32 v;
stream >> v;
cSetTileBackground(v == 1);
} break;
case dbiReplaceEmojis: {
qint32 v;
stream >> v;
cSetReplaceEmojis(v == 1);
} break;
case dbiDefaultAttach: {
qint32 v;
stream >> v;
switch (v) {
case dbidaPhoto: cSetDefaultAttach(dbidaPhoto); break;
default: cSetDefaultAttach(dbidaDocument); break;
}
} break;
case dbiSoundNotify: {
qint32 v;
stream >> v;
cSetSoundNotify(v == 1);
} break;
case dbiDesktopNotify: {
qint32 v;
stream >> v;
cSetDesktopNotify(v == 1);
} break;
case dbiNotifyView: {
qint32 v;
stream >> v;
switch (v) {
case dbinvShowNothing: cSetNotifyView(dbinvShowNothing); break;
case dbinvShowName: cSetNotifyView(dbinvShowName); break;
default: cSetNotifyView(dbinvShowPreview); break;
}
} break;
case dbiAskDownloadPath: {
qint32 v;
stream >> v;
cSetAskDownloadPath(v == 1);
} break;
case dbiDownloadPath: {
QString v;
stream >> v;
cSetDownloadPath(v);
} break;
case dbiCompressPastedImage: {
qint32 v;
stream >> v;
cSetCompressPastedImage(v == 1);
} break;
case dbiEmojiTab: {
qint32 v;
stream >> v;
switch (v) {
case dbietRecent : cSetEmojiTab(dbietRecent); break;
case dbietPeople : cSetEmojiTab(dbietPeople); break;
case dbietNature : cSetEmojiTab(dbietNature); break;
case dbietObjects : cSetEmojiTab(dbietObjects); break;
case dbietPlaces : cSetEmojiTab(dbietPlaces); break;
case dbietSymbols : cSetEmojiTab(dbietSymbols); break;
case dbietStickers: cSetEmojiTab(dbietStickers); break;
}
} break;
case dbiRecentEmojis: {
RecentEmojiPreload v;
stream >> v;
cSetRecentEmojisPreload(v);
} break;
default:
if (!MTP::readConfigElem(blockId, stream)) {
}
break;
}
if (stream.status() != QDataStream::Ok) {
LOG(("App Error: could not read data, status: %1 - user config file is corrupted?..").arg(stream.status()));
break;
}
}
}
void readUserConfig() {
QFile configFile(cWorkingDir() + cDataFile() + qsl("_config"));
if (configFile.open(QIODevice::ReadOnly)) {
DEBUG_LOG(("App Info: user config file opened for reading"));
{
QDataStream configStream(&configFile);
configStream.setVersion(QDataStream::Qt_5_1);
quint32 blockId;
configStream >> blockId;
if (configStream.status() == QDataStream::ReadPastEnd) {
DEBUG_LOG(("App Info: config file read end"));
return;
} else if (configStream.status() != QDataStream::Ok) {
LOG(("App Error: could not read block id, status: %1 - user config file is corrupted?..").arg(configStream.status()));
return;
}
if (blockId == dbiVersion) {
qint32 configVersion;
configStream >> configVersion;
if (configVersion > AppVersion) return;
configStream >> blockId;
if (configStream.status() == QDataStream::ReadPastEnd) {
DEBUG_LOG(("App Info: config file read end"));
return;
} else if (configStream.status() != QDataStream::Ok) {
LOG(("App Error: could not read block id, status: %1 - user config file is corrupted?..").arg(configStream.status()));
return;
}
if (blockId != dbiEncryptedWithSalt) { // old version data - not encrypted
cSetNeedConfigResave(true);
}
} else {
cSetNeedConfigResave(true);
}
}
configFile.reset();
readUserConfigFields(&configFile);
}
}
void writeAllMuted(QDataStream &stream) { // deprecated
}
void readOneMuted(QDataStream &stream) { // deprecated
quint64 peerId;
stream >> peerId;
}
void readAllMuted(QDataStream &stream) {
quint32 count;
stream >> count;
for (uint32 i = 0; i < count; ++i) {
readOneMuted(stream);
}
}
void checkImageCacheSize() {
int64 nowImageCacheSize = imageCacheSize();
if (nowImageCacheSize > serviceImageCacheSize + MemoryForImageCache) {

View file

@ -39,6 +39,7 @@ namespace App {
Window *wnd();
MainWidget *main();
SettingsWidget *settings();
bool passcoded();
FileUploader *uploader();
void showSettings();
@ -151,18 +152,6 @@ namespace App {
void deinitMedia(bool completely = true);
void playSound();
void writeConfig();
void readConfig();
void writeUserConfig();
void readUserConfig();
void muteHistory(History *history);
void unmuteHistory(History *history);
void writeAllMuted(QDataStream &stream);
void readAllMuted(QDataStream &stream);
void readOneMuted(QDataStream &stream);
bool isPeerMuted(const PeerId &peer);
void checkImageCacheSize();
bool isValidPhone(QString phone);

View file

@ -152,7 +152,6 @@ Application::Application(int &argc, char **argv) : PsApplication(argc, argv),
installTranslator(_translator = new Translator());
Local::start();
style::startManager();
anim::startManager();
historyInit();
@ -174,8 +173,8 @@ Application::Application(int &argc, char **argv) : PsApplication(argc, argv),
connect(this, SIGNAL(updateFailed()), this, SLOT(onUpdateFailed()));
connect(this, SIGNAL(updateReady()), this, SLOT(onUpdateReady()));
connect(this, SIGNAL(applicationStateChanged(Qt::ApplicationState)), this, SLOT(onAppStateChanged(Qt::ApplicationState)));
connect(&writeUserConfigTimer, SIGNAL(timeout()), this, SLOT(onWriteUserConfig()));
writeUserConfigTimer.setSingleShot(true);
//connect(&writeUserConfigTimer, SIGNAL(timeout()), this, SLOT(onWriteUserConfig()));
//writeUserConfigTimer.setSingleShot(true);
connect(&killDownloadSessionsTimer, SIGNAL(timeout()), this, SLOT(killDownloadSessions()));
@ -191,7 +190,7 @@ void Application::onAppUpdate(const MTPhelp_AppUpdate &response) {
updateRequestId = 0;
cSetLastUpdateCheck(unixtime());
App::writeConfig();
Local::writeSettings();
if (response.type() == mtpc_help_noAppUpdate) {
startUpdateCheck();
} else {
@ -205,7 +204,7 @@ void Application::onAppUpdate(const MTPhelp_AppUpdate &response) {
bool Application::onAppUpdateFail() {
updateRequestId = 0;
cSetLastUpdateCheck(unixtime());
App::writeConfig();
Local::writeSettings();
startUpdateCheck();
return true;
}
@ -239,7 +238,7 @@ void Application::updateGotCurrent() {
emit updateLatest();
}
startUpdateCheck(true);
App::writeConfig();
Local::writeSettings();
}
void Application::updateFailedCurrent(QNetworkReply::NetworkError e) {
@ -259,7 +258,7 @@ void Application::onUpdateReady() {
updateCheckTimer.stop();
cSetLastUpdateCheck(unixtime());
App::writeConfig();
Local::writeSettings();
}
void Application::onUpdateFailed() {
@ -271,7 +270,7 @@ void Application::onUpdateFailed() {
}
cSetLastUpdateCheck(unixtime());
App::writeConfig();
Local::writeSettings();
}
void Application::regPhotoUpdate(const PeerId &peer, MsgId msgId) {
@ -347,11 +346,11 @@ void Application::peerClearPhoto(PeerId peer) {
}
}
void Application::writeUserConfigIn(uint64 ms) {
if (!writeUserConfigTimer.isActive()) {
writeUserConfigTimer.start(ms);
}
}
//void Application::writeUserConfigIn(uint64 ms) {
// if (!writeUserConfigTimer.isActive()) {
// writeUserConfigTimer.start(ms);
// }
//}
void Application::killDownloadSessionsStart(int32 dc) {
if (killDownloadSessionTimes.constFind(dc) == killDownloadSessionTimes.cend()) {
@ -373,9 +372,9 @@ void Application::checkLocalTime() {
if (App::main()) App::main()->checkLastUpdate(checkms());
}
void Application::onWriteUserConfig() {
App::writeUserConfig();
}
//void Application::onWriteUserConfig() {
// Local::writeUserSettings();
//}
void Application::onAppStateChanged(Qt::ApplicationState state) {
checkLocalTime();
@ -649,32 +648,44 @@ void Application::socketError(QLocalSocket::LocalSocketError e) {
startApp();
}
void Application::checkMapVersion() {
if (Local::oldMapVersion() < AppVersion) {
psRegisterCustomScheme();
if (Local::oldMapVersion()) {
QString versionFeatures;
if (DevChannel && Local::oldMapVersion() < 7019) {
versionFeatures = QString::fromUtf8("\xe2\x80\x94 Passcode lock option added");
} else if (!DevChannel && Local::oldMapVersion() < 7017) {
versionFeatures = lang(lng_new_version_minor).trimmed();
}
if (!versionFeatures.isEmpty()) {
versionFeatures = lng_new_version_wrap(lt_version, QString::fromStdWString(AppVersionStr), lt_changes, versionFeatures, lt_link, qsl("https://desktop.telegram.org/#changelog"));
window->serviceNotification(versionFeatures);
}
}
}
}
void Application::startApp() {
cChangeTimeFormat(QLocale::system().timeFormat(QLocale::ShortFormat));
DEBUG_LOG(("Application Info: starting app.."));
Local::ReadMapState state = Local::readMap(QByteArray());
if (state == Local::ReadMapPassNeeded) {
cSetHasPasscode(true);
}
DEBUG_LOG(("Application Info: local map read.."));
App::readUserConfig();
if (!Local::oldKey().created()) {
Local::createOldKey();
cSetNeedConfigResave(true);
}
if (cNeedConfigResave()) {
App::writeConfig();
App::writeUserConfig();
cSetNeedConfigResave(false);
}
DEBUG_LOG(("Application Info: user config read.."));
window->createWinId();
window->init();
DEBUG_LOG(("Application Info: window created.."));
MTP::start();
if (state != Local::ReadMapPassNeeded) {
MTP::start();
}
MTP::setStateChangedHandler(mtpStateChanged);
MTP::setSessionResetHandler(mtpSessionReset);
@ -685,12 +696,15 @@ void Application::startApp() {
App::initMedia();
DEBUG_LOG(("Application Info: showing."));
if (MTP::authedId()) {
window->setupMain(false);
if (state == Local::ReadMapPassNeeded) {
window->setupPasscode(false);
} else {
window->setupIntro(false);
if (MTP::authedId()) {
window->setupMain(false);
} else {
window->setupIntro(false);
}
}
window->firstShow();
if (cStartToSettings()) {
@ -698,20 +712,9 @@ void Application::startApp() {
}
QNetworkProxyFactory::setUseSystemConfiguration(true);
if (Local::oldMapVersion() < AppVersion) {
psRegisterCustomScheme();
if (Local::oldMapVersion()) {
QString versionFeatures;
if (DevChannel && Local::oldMapVersion() < 7018) {
versionFeatures = QString::fromUtf8("\xe2\x80\x94 Windows: crash on start fixed for some Intel cards\n\xe2\x80\x94 Linux: tray icon returned in Pantheon and Gnome");
} else if (!DevChannel && Local::oldMapVersion() < 7017) {
versionFeatures = lang(lng_new_version_minor).trimmed();
}
if (!versionFeatures.isEmpty()) {
versionFeatures = lng_new_version_wrap(lt_version, QString::fromStdWString(AppVersionStr), lt_changes, versionFeatures, lt_link, qsl("https://desktop.telegram.org/#changelog"));
window->serviceNotification(versionFeatures);
}
}
if (state != Local::ReadMapPassNeeded) {
checkMapVersion();
}
window->updateIsActive(cOnlineFocusTimeout());
@ -844,8 +847,7 @@ Application::~Application() {
cSetChatDogImage(0);
style::stopManager();
Local::stop();
delete _translator;
}

View file

@ -76,6 +76,7 @@ public:
void killDownloadSessionsStop(int32 dc);
void checkLocalTime();
void checkMapVersion();
signals:
@ -107,7 +108,7 @@ public slots:
void photoUpdated(MsgId msgId, const MTPInputFile &file);
void onEnableDebugMode();
void onWriteUserConfig();
// void onWriteUserConfig();
void killDownloadSessions();
void onAppStateChanged(Qt::ApplicationState state);

Binary file not shown.

Before

Width:  |  Height:  |  Size: 59 KiB

After

Width:  |  Height:  |  Size: 60 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 104 KiB

After

Width:  |  Height:  |  Size: 105 KiB

View file

@ -0,0 +1,152 @@
/*
This file is part of Telegram Desktop,
the official desktop version of Telegram messaging app, see https://telegram.org
Telegram Desktop is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
It is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Full license: https://github.com/telegramdesktop/tdesktop/blob/master/LICENSE
Copyright (c) 2014 John Preston, https://desktop.telegram.org
*/
#include "stdafx.h"
#include "lang.h"
#include "localstorage.h"
#include "autolockbox.h"
#include "confirmbox.h"
#include "mainwidget.h"
#include "window.h"
AutoLockBox::AutoLockBox() :
_done(this, lang(lng_about_done), st::langsCloseButton),
_hiding(false), a_opacity(0, 1) {
bool haveTestLang = (cLang() == languageTest);
int32 opts[] = { 60, 300, 3600, 18000 }, cnt = sizeof(opts) / sizeof(opts[0]);
_width = st::langsWidth;
_height = st::addContactTitleHeight + st::langsPadding.top() + st::langsPadding.bottom() + cnt * (st::langPadding.top() + st::rbDefFlat.height + st::langPadding.bottom()) + _done.height();
int32 y = st::addContactTitleHeight + st::langsPadding.top();
_options.reserve(cnt);
for (int32 i = 0; i < cnt; ++i) {
int32 v = opts[i];
_options.push_back(new FlatRadiobutton(this, qsl("autolock"), v, (v % 3600) ? lng_passcode_autolock_minutes(lt_count, v / 60) : lng_passcode_autolock_hours(lt_count, v / 3600), (cAutoLock() == v), st::langButton));
_options.back()->move(st::langsPadding.left() + st::langPadding.left(), y + st::langPadding.top());
y += st::langPadding.top() + _options.back()->height() + st::langPadding.bottom();
connect(_options.back(), SIGNAL(changed()), this, SLOT(onChange()));
}
_done.move(0, _height - _done.height());
connect(&_done, SIGNAL(clicked()), this, SLOT(onClose()));
resize(_width, _height);
showAll();
_cache = myGrab(this, rect());
hideAll();
}
void AutoLockBox::hideAll() {
_done.hide();
for (int32 i = 0, l = _options.size(); i < l; ++i) {
_options[i]->hide();
}
}
void AutoLockBox::showAll() {
_done.show();
for (int32 i = 0, l = _options.size(); i < l; ++i) {
_options[i]->show();
}
}
void AutoLockBox::keyPressEvent(QKeyEvent *e) {
if (e->key() == Qt::Key_Escape) {
onClose();
}
}
void AutoLockBox::parentResized() {
QSize s = parentWidget()->size();
setGeometry((s.width() - _width) / 2, (s.height() - _height) / 2, _width, _height);
update();
}
void AutoLockBox::paintEvent(QPaintEvent *e) {
QPainter p(this);
if (_cache.isNull()) {
if (!_hiding || a_opacity.current() > 0.01) {
// fill bg
p.fillRect(0, 0, _width, _height, st::boxBG->b);
// paint shadows
p.fillRect(0, st::addContactTitleHeight, _width, st::scrollDef.topsh, st::scrollDef.shColor->b);
// draw box title / text
p.setFont(st::addContactTitleFont->f);
p.setPen(st::black->p);
p.drawText(st::addContactTitlePos.x(), st::addContactTitlePos.y() + st::addContactTitleFont->ascent, lang(lng_languages));
}
} else {
p.setOpacity(a_opacity.current());
p.drawPixmap(0, 0, _cache);
}
}
void AutoLockBox::animStep(float64 ms) {
if (ms >= 1) {
a_opacity.finish();
_cache = QPixmap();
if (!_hiding) {
showAll();
setFocus();
}
} else {
a_opacity.update(ms, anim::linear);
}
update();
}
void AutoLockBox::onChange() {
if (isHidden()) return;
for (int32 i = 0, l = _options.size(); i < l; ++i) {
int32 v = _options[i]->val();
if (_options[i]->checked()) {
cSetAutoLock(v);
Local::writeUserSettings();
}
}
App::wnd()->checkAutoLock();
onClose();
}
void AutoLockBox::onClose() {
emit closed();
}
void AutoLockBox::startHide() {
_hiding = true;
if (_cache.isNull()) {
_cache = myGrab(this, rect());
hideAll();
}
a_opacity.start(0);
}
AutoLockBox::~AutoLockBox() {
for (int32 i = 0, l = _options.size(); i < l; ++i) {
delete _options[i];
}
}

View file

@ -0,0 +1,53 @@
/*
This file is part of Telegram Desktop,
the official desktop version of Telegram messaging app, see https://telegram.org
Telegram Desktop is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
It is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Full license: https://github.com/telegramdesktop/tdesktop/blob/master/LICENSE
Copyright (c) 2014 John Preston, https://desktop.telegram.org
*/
#pragma once
#include "layerwidget.h"
class AutoLockBox : public LayeredWidget {
Q_OBJECT
public:
AutoLockBox();
void parentResized();
void animStep(float64 ms);
void keyPressEvent(QKeyEvent *e);
void paintEvent(QPaintEvent *e);
void startHide();
~AutoLockBox();
public slots:
void onChange();
void onClose();
private:
void hideAll();
void showAll();
QVector<FlatRadiobutton*> _options;
int32 _width, _height;
BottomButton _done;
bool _hiding;
QPixmap _cache;
anim::fvalue a_opacity;
};

View file

@ -18,6 +18,8 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "stdafx.h"
#include "lang.h"
#include "localstorage.h"
#include "connectionbox.h"
#include "mainwidget.h"
#include "window.h"
@ -203,7 +205,7 @@ void ConnectionBox::onSave() {
QNetworkProxyFactory::setUseSystemConfiguration(false);
QNetworkProxyFactory::setUseSystemConfiguration(true);
}
App::writeConfig();
Local::writeSettings();
MTP::restart();
reinitImageLinkManager();
emit closed();

View file

@ -18,6 +18,8 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "stdafx.h"
#include "lang.h"
#include "localstorage.h"
#include "downloadpathbox.h"
#include "gui/filedialog.h"
@ -181,7 +183,7 @@ void DownloadPathBox::onEditPath() {
void DownloadPathBox::onSave() {
cSetDownloadPath(_defaultRadio.checked() ? QString() : (_tempRadio.checked() ? qsl("tmp") : _path));
App::writeUserConfig();
Local::writeUserSettings();
emit closed();
}

View file

@ -18,6 +18,8 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "stdafx.h"
#include "lang.h"
#include "localstorage.h"
#include "languagebox.h"
#include "confirmbox.h"
#include "mainwidget.h"
@ -183,7 +185,7 @@ void LanguageBox::onSave() {
for (int32 i = 0, l = _langs.size(); i < l; ++i) {
if (_langs[i]->checked()) {
cSetLang(_langs[i]->val());
App::writeConfig();
Local::writeSettings();
cSetRestarting(true);
cSetRestartingToSettings(true);
App::quit();

View file

@ -0,0 +1,279 @@
/*
This file is part of Telegram Desktop,
the official desktop version of Telegram messaging app, see https://telegram.org
Telegram Desktop is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
It is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Full license: https://github.com/telegramdesktop/tdesktop/blob/master/LICENSE
Copyright (c) 2014 John Preston, https://desktop.telegram.org
*/
#include "stdafx.h"
#include "lang.h"
#include "passcodebox.h"
#include "window.h"
#include "localstorage.h"
PasscodeBox::PasscodeBox(bool turningOff) : _turningOff(turningOff),
_about(st::addContactWidth - st::addContactPadding.left() - st::addContactPadding.right()),
_saveButton(this, lang(lng_settings_save), st::btnSelectDone),
_cancelButton(this, lang(lng_cancel), st::btnSelectCancel),
_oldPasscode(this, st::inpAddContact, lang(lng_passcode_enter_old)),
_newPasscode(this, st::inpAddContact, lang(lng_passcode_enter_new)),
_reenterPasscode(this, st::inpAddContact, lang(lng_passcode_confirm_new)),
a_opacity(0, 1), _hiding(false) {
_width = st::addContactWidth;
_about.setRichText(st::usernameFont, lang(lng_passcode_about));
int32 aboutHeight = _about.countHeight(_width - st::addContactPadding.left() - st::addContactPadding.right());
_oldPasscode.setEchoMode(QLineEdit::Password);
_newPasscode.setEchoMode(QLineEdit::Password);
_reenterPasscode.setEchoMode(QLineEdit::Password);
if (turningOff) {
_oldPasscode.show();
_boxTitle = lang(lng_passcode_remove);
_height = st::addContactTitleHeight + st::addContactPadding.top() + 1 * _oldPasscode.height() + st::usernameSkip + aboutHeight + st::addContactPadding.bottom() + _saveButton.height();
} else {
if (cHasPasscode()) {
_oldPasscode.show();
_boxTitle = lang(lng_passcode_change);
_height = st::addContactTitleHeight + st::addContactPadding.top() + 3 * _oldPasscode.height() + st::usernameSkip * 2 + 1 * st::addContactDelta + aboutHeight + st::addContactPadding.bottom() + _saveButton.height();
} else {
_oldPasscode.hide();
_boxTitle = lang(lng_passcode_create);
_height = st::addContactTitleHeight + st::addContactPadding.top() + 2 * _oldPasscode.height() + st::usernameSkip + 1 * st::addContactDelta + aboutHeight + st::addContactPadding.bottom() + _saveButton.height();
}
}
_oldPasscode.setGeometry(st::addContactPadding.left(), st::addContactTitleHeight + st::addContactPadding.top(), _width - st::addContactPadding.left() - st::addContactPadding.right(), _oldPasscode.height());
_newPasscode.setGeometry(st::addContactPadding.left(), _oldPasscode.y() + ((turningOff || cHasPasscode()) ? (_oldPasscode.height() + st::usernameSkip) : 0), _oldPasscode.width(), _oldPasscode.height());
_reenterPasscode.setGeometry(st::addContactPadding.left(), _newPasscode.y() + _newPasscode.height() + st::addContactDelta, _newPasscode.width(), _newPasscode.height());
int32 buttonTop = _height - _cancelButton.height();
_cancelButton.move(0, buttonTop);
_saveButton.move(_width - _saveButton.width(), buttonTop);
connect(&_saveButton, SIGNAL(clicked()), this, SLOT(onSave()));
connect(&_cancelButton, SIGNAL(clicked()), this, SLOT(onCancel()));
_badOldTimer.setSingleShot(true);
connect(&_badOldTimer, SIGNAL(timeout()), this, SLOT(onBadOldPasscode()));
connect(&_oldPasscode, SIGNAL(changed()), this, SLOT(onOldChanged()));
connect(&_newPasscode, SIGNAL(changed()), this, SLOT(onNewChanged()));
connect(&_reenterPasscode, SIGNAL(changed()), this, SLOT(onNewChanged()));
resize(_width, _height);
showAll();
_cache = myGrab(this, rect());
hideAll();
}
void PasscodeBox::hideAll() {
_oldPasscode.hide();
_newPasscode.hide();
_reenterPasscode.hide();
_saveButton.hide();
_cancelButton.hide();
}
void PasscodeBox::showAll() {
if (_turningOff) {
_oldPasscode.show();
_newPasscode.hide();
_reenterPasscode.hide();
} else {
if (cHasPasscode()) {
_oldPasscode.show();
} else {
_oldPasscode.hide();
}
_newPasscode.show();
_reenterPasscode.show();
}
_saveButton.show();
_cancelButton.show();
}
void PasscodeBox::keyPressEvent(QKeyEvent *e) {
if (e->key() == Qt::Key_Enter || e->key() == Qt::Key_Return) {
if (_oldPasscode.hasFocus()) {
if (_turningOff) {
onSave();
} else {
_newPasscode.setFocus();
}
} else if (_newPasscode.hasFocus()) {
_reenterPasscode.setFocus();
} else if (_reenterPasscode.hasFocus()) {
if (cHasPasscode() && _oldPasscode.text().isEmpty()) {
_oldPasscode.setFocus();
_oldPasscode.notaBene();
} else if (_newPasscode.text().isEmpty()) {
_newPasscode.setFocus();
_newPasscode.notaBene();
} else if (_reenterPasscode.text().isEmpty()) {
_reenterPasscode.notaBene();
} else {
onSave();
}
}
} else if (e->key() == Qt::Key_Escape) {
onCancel();
}
}
void PasscodeBox::parentResized() {
QSize s = parentWidget()->size();
setGeometry((s.width() - _width) / 2, (s.height() - _height) / 2, _width, _height);
update();
}
void PasscodeBox::paintEvent(QPaintEvent *e) {
QPainter p(this);
if (_cache.isNull()) {
if (!_hiding || a_opacity.current() > 0.01) {
// fill bg
p.fillRect(QRect(QPoint(0, 0), size()), st::boxBG->b);
// paint shadows
p.fillRect(0, st::addContactTitleHeight, _width, st::scrollDef.topsh, st::scrollDef.shColor->b);
p.fillRect(0, size().height() - st::btnSelectCancel.height - st::scrollDef.bottomsh, _width, st::scrollDef.bottomsh, st::scrollDef.shColor->b);
p.setPen(st::usernameColor->p);
_about.draw(p, st::addContactPadding.left(), (_turningOff ? _oldPasscode : _reenterPasscode).y() + _oldPasscode.height() + st::usernameSkip, _width - st::addContactPadding.left() - st::addContactPadding.right());
if (!_oldError.isEmpty()) {
p.setPen(st::setErrColor->p);
p.drawText(QRect(0, _oldPasscode.y() + _oldPasscode.height(), _width, st::usernameSkip), _oldError, style::al_center);
}
if (!_newError.isEmpty()) {
p.setPen(st::setErrColor->p);
p.drawText(QRect(0, _reenterPasscode.y() + _reenterPasscode.height(), _width, st::usernameSkip), _newError, style::al_center);
}
// paint button sep
p.fillRect(st::btnSelectCancel.width, size().height() - st::btnSelectCancel.height, st::lineWidth, st::btnSelectCancel.height, st::btnSelectSep->b);
// draw box title / text
p.setPen(st::black->p);
p.setFont(st::addContactTitleFont->f);
p.drawText(st::addContactTitlePos.x(), st::addContactTitlePos.y() + st::addContactTitleFont->ascent, _boxTitle);
}
} else {
p.setOpacity(a_opacity.current());
p.drawPixmap(0, 0, _cache);
}
}
void PasscodeBox::animStep(float64 dt) {
if (dt >= 1) {
a_opacity.finish();
_cache = QPixmap();
if (!_hiding) {
showAll();
if (_oldPasscode.isHidden()) {
_newPasscode.setFocus();
} else {
_oldPasscode.setFocus();
}
}
} else {
a_opacity.update(dt, anim::linear);
}
update();
}
void PasscodeBox::onSave() {
QString old = _oldPasscode.text(), pwd = _newPasscode.text(), conf = _reenterPasscode.text();
if (_turningOff || cHasPasscode()) {
if (Local::checkPasscode(old.toUtf8())) {
if (_turningOff) pwd = conf = QString();
} else {
_oldPasscode.setDisabled(true);
_newPasscode.setDisabled(true);
_reenterPasscode.setDisabled(true);
_saveButton.setDisabled(true);
_oldError = QString();
update();
_badOldTimer.start(WrongPasscodeTimeout);
return;
}
}
if (!_turningOff && pwd.isEmpty()) {
_newPasscode.setFocus();
_newPasscode.notaBene();
return;
}
if (pwd != conf) {
_reenterPasscode.setFocus();
_reenterPasscode.notaBene();
if (!conf.isEmpty()) {
_newError = lang(lng_passcode_differ);
update();
}
} else if (!_turningOff && cHasPasscode() && old == pwd) {
_newPasscode.setFocus();
_newPasscode.notaBene();
_newError = lang(lng_passcode_is_same);
update();
} else {
Local::setPasscode(pwd.toUtf8());
App::wnd()->checkAutoLock();
App::wnd()->getTitle()->showUpdateBtn();
emit closed();
}
}
void PasscodeBox::onBadOldPasscode() {
_oldPasscode.setDisabled(false);
_newPasscode.setDisabled(false);
_reenterPasscode.setDisabled(false);
_saveButton.setDisabled(false);
_oldPasscode.selectAll();
_oldPasscode.setFocus();
_oldPasscode.notaBene();
_oldError = lang(lng_passcode_wrong);
update();
}
void PasscodeBox::onOldChanged() {
if (!_oldError.isEmpty()) {
_oldError = QString();
update();
}
}
void PasscodeBox::onNewChanged() {
if (!_newError.isEmpty()) {
_newError = QString();
update();
}
}
void PasscodeBox::onCancel() {
emit closed();
}
void PasscodeBox::startHide() {
_hiding = true;
if (_cache.isNull()) {
_cache = myGrab(this, rect());
hideAll();
}
a_opacity.start(0);
}
PasscodeBox::~PasscodeBox() {
}

View file

@ -0,0 +1,64 @@
/*
This file is part of Telegram Desktop,
the official desktop version of Telegram messaging app, see https://telegram.org
Telegram Desktop is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
It is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Full license: https://github.com/telegramdesktop/tdesktop/blob/master/LICENSE
Copyright (c) 2014 John Preston, https://desktop.telegram.org
*/
#pragma once
#include "layerwidget.h"
class PasscodeBox : public LayeredWidget {
Q_OBJECT
public:
PasscodeBox(bool turningOff = false);
void parentResized();
void animStep(float64 dt);
void keyPressEvent(QKeyEvent *e);
void paintEvent(QPaintEvent *e);
void startHide();
~PasscodeBox();
public slots:
void onSave();
void onBadOldPasscode();
void onOldChanged();
void onNewChanged();
void onCancel();
private:
void hideAll();
void showAll();
bool _turningOff;
QString _boxTitle;
Text _about;
int32 _width, _height;
FlatButton _saveButton, _cancelButton;
FlatInput _oldPasscode, _newPasscode, _reenterPasscode;
QPixmap _cache;
anim::fvalue a_opacity;
bool _hiding;
QTimer _badOldTimer;
QString _oldError, _newError;
};

View file

@ -19,7 +19,6 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "style.h"
#include "lang.h"
#include "app.h"
#include "application.h"
#include "mainwidget.h"
#include "photocropbox.h"

View file

@ -19,7 +19,8 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "style.h"
#include "lang.h"
#include "app.h"
#include "localstorage.h"
#include "mainwidget.h"
#include "photosendbox.h"
@ -205,8 +206,10 @@ void PhotoSendBox::onSend(bool ctrlShiftEnter) {
if (App::main()) App::main()->confirmShareContact(ctrlShiftEnter, _phone, _fname, _lname);
} else {
if (!_compressed.isHidden()) {
cSetCompressPastedImage(_compressed.checked());
App::writeUserConfig();
if (_compressed.checked() != cCompressPastedImage()) {
cSetCompressPastedImage(_compressed.checked());
Local::writeUserSettings();
}
}
if (_compressed.isHidden() || _compressed.checked()) {
_img->ctrlShiftEnter = ctrlShiftEnter;

View file

@ -17,8 +17,8 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
*/
#pragma once
static const int32 AppVersion = 7018;
static const wchar_t *AppVersionStr = L"0.7.18";
static const int32 AppVersion = 7019;
static const wchar_t *AppVersionStr = L"0.7.19";
static const bool DevChannel = true;
static const wchar_t *AppNameOld = L"Telegram Win (Unofficial)";
@ -123,6 +123,8 @@ enum {
UpdateDelayConstPart = 8 * 3600, // 8 hour min time between update check requests
UpdateDelayRandPart = 8 * 3600, // 8 hour max - min time between update check requests
WrongPasscodeTimeout = 1500,
};
inline bool isServiceUser(uint64 id) {

View file

@ -1544,6 +1544,8 @@ bool DialogsWidget::addNewContact(int32 uid, bool show) {
}
void DialogsWidget::onListScroll() {
// if (!App::self()) return;
list.loadPeerPhotos(scroll.scrollTop());
if (list.state() == DialogsListWidget::SearchedState) {
if (scroll.scrollTop() > (list.searchList().size() + list.filteredList().size() + list.peopleList().size()) * st::dlgHeight - PreloadHeightsCount * scroll.height()) {

View file

@ -496,7 +496,7 @@ void EmojiPanInner::mouseReleaseEvent(QMouseEvent *e) {
}
void EmojiPanInner::onSaveConfig() {
App::writeUserConfig();
Local::writeUserSettings();
}
void EmojiPanInner::mouseMoveEvent(QMouseEvent *e) {
@ -871,7 +871,7 @@ void EmojiPan::onTabChange() {
else if (_stickers.checked()) newTab = dbietStickers;
if (newTab != cEmojiTab()) {
cSetEmojiTab(newTab);
App::writeUserConfig();
Local::writeUserSettings();
_scroll.scrollToY(0);
}
_inner.showEmojiPack(newTab);

View file

@ -18,7 +18,6 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "stdafx.h"
#include "gui/filedialog.h"
#include "app.h"
#include "application.h"
void filedialogInit() {

View file

@ -19,7 +19,6 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "text.h"
#include "lang.h"
#include "app.h"
#include <private/qharfbuzz_p.h>

View file

@ -25,6 +25,8 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "boxes/photosendbox.h"
#include "mainwidget.h"
#include "window.h"
#include "passcodewidget.h"
#include "window.h"
#include "fileuploader.h"
#include "localstorage.h"
@ -554,7 +556,7 @@ void HistoryList::dragActionFinish(const QPoint &screenPos, Qt::MouseButton butt
uint32 sel = _selected.cbegin().value();
if (sel != FullItemSel && (sel & 0xFFFF) == ((sel >> 16) & 0xFFFF)) {
_selected.clear();
App::main()->activate();
App::wnd()->setInnerFocus();
}
}
}
@ -1734,6 +1736,7 @@ void HistoryWidget::activate() {
return;
} else {
App::main()->dialogsActivate();
return;
}
}
if (_list) {
@ -1926,7 +1929,7 @@ void HistoryWidget::showPeer(const PeerId &peer, MsgId msgId, bool force, bool l
clearLoadingAround();
emit peerShown(histPeer);
return activate();
return App::wnd()->setInnerFocus();
}
updateTyping(false);
}
@ -2633,7 +2636,7 @@ bool HistoryWidget::animStep(float64 ms) {
}
onListScroll();
}
activate();
App::wnd()->setInnerFocus();
} else {
a_bgCoord.update(dt1, st::introHideFunc);
a_bgAlpha.update(dt1, st::introAlphaHideFunc);
@ -2660,7 +2663,7 @@ void HistoryWidget::onPhotoSelect() {
if (cDefaultAttach() != dbidaPhoto) {
cSetDefaultAttach(dbidaPhoto);
App::writeUserConfig();
Local::writeUserSettings();
}
QStringList photoExtensions(cPhotoExtensions());
@ -2688,7 +2691,7 @@ void HistoryWidget::onDocumentSelect() {
if (cDefaultAttach() != dbidaDocument) {
cSetDefaultAttach(dbidaDocument);
App::writeUserConfig();
Local::writeUserSettings();
}
QStringList photoExtensions(cPhotoExtensions());

View file

@ -19,7 +19,7 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "lang.h"
#include "style.h"
#include "app.h"
#include "localstorage.h"
#include "intro/intro.h"
#include "intro/introsteps.h"
@ -89,7 +89,7 @@ void IntroWidget::langChangeTo(int32 langId) {
void IntroWidget::onChangeLang() {
cSetLang(_langChangeTo);
App::writeConfig();
Local::writeSettings();
cSetRestarting(true);
cSetRestartingToSettings(false);
App::quit();
@ -332,8 +332,7 @@ void IntroWidget::mousePressEvent(QMouseEvent *e) {
}
void IntroWidget::finish(const MTPUser &user, const QImage &photo) {
wnd->setupMain(true);
wnd->startMain(user);
wnd->setupMain(true, &user);
if (!photo.isNull()) {
App::app()->uploadProfilePhoto(photo, MTP::authedId());
}

View file

@ -17,9 +17,6 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
*/
#pragma once
#include <QtWidgets/QWidget>
#include "gui/flatbutton.h"
class Window;
class IntroSteps;
class IntroPhone;
@ -39,7 +36,7 @@ public:
void resizeEvent(QResizeEvent *e);
void mousePressEvent(QMouseEvent *e);
void keyPressEvent(QKeyEvent *e);
void updateWideMode();
void animShow(const QPixmap &bgAnimCache, bool back = false);

File diff suppressed because it is too large Load diff

View file

@ -50,11 +50,18 @@ namespace _local_inner {
namespace Local {
mtpAuthKey &oldKey();
void createOldKey(QByteArray *salt = 0);
void start();
void stop();
void readSettings();
void writeSettings();
void writeUserSettings();
void writeMtpData();
void reset();
bool checkPasscode(const QByteArray &passcode);
void setPasscode(const QByteArray &passcode);
enum ClearManagerTask {
ClearManagerAll = 0xFFFF,

View file

@ -19,6 +19,8 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "application.h"
#include "pspecific.h"
#include "localstorage.h"
int main(int argc, char *argv[]) {
#ifdef _NEED_WIN_GENERATE_DUMP
_oldWndExceptionFilter = SetUnhandledExceptionFilter(_exceptionFilter);
@ -34,9 +36,10 @@ int main(int argc, char *argv[]) {
}
logsInit();
App::readConfig();
Local::readSettings();
if (cFromAutoStart() && !cAutoStart()) {
psAutoStart(false, true);
Local::stop();
return 0;
}
@ -64,6 +67,7 @@ int main(int argc, char *argv[]) {
}
}
psFinish();
Local::stop();
DEBUG_LOG(("Application Info: Telegram done, result: %1").arg(result));

View file

@ -399,6 +399,8 @@ _failDifferenceTimeout(1), _lastUpdateTime(0), _cachedX(0), _cachedY(0), _backgr
show();
setFocus();
App::initMedia();
}
mtpRequestId MainWidget::onForward(const PeerId &peer, bool forwardSelected) {
@ -462,6 +464,8 @@ void MainWidget::noHider(HistoryHider *destroyed) {
}
void MainWidget::hiderLayer(HistoryHider *h) {
if (App::passcoded()) return;
hider = h;
if (cWideMode()) {
hider->show();
@ -1249,6 +1253,7 @@ void MainWidget::onParentResize(const QSize &newSize) {
}
void MainWidget::updateOnlineDisplay() {
if (this != App::main()) return;
history.updateOnlineDisplay(history.x(), width() - history.x() - st::sysBtnDelta * 2 - st::sysCls.img.pxWidth() - st::sysRes.img.pxWidth() - st::sysMin.img.pxWidth());
if (profile) profile->updateOnlineDisplay();
if (App::wnd()->settingsWidget()) App::wnd()->settingsWidget()->updateOnlineDisplay();
@ -2091,6 +2096,7 @@ void MainWidget::onPeerShown(PeerData *peer) {
}
void MainWidget::onUpdateNotifySettings() {
if (this != App::main()) return;
while (!updateNotifySettingPeers.isEmpty()) {
PeerData *peer = *updateNotifySettingPeers.begin();
updateNotifySettingPeers.erase(updateNotifySettingPeers.begin());
@ -2260,6 +2266,7 @@ void MainWidget::updUpdated(int32 pts, int32 seq) {
}
void MainWidget::feedDifference(const MTPVector<MTPUser> &users, const MTPVector<MTPChat> &chats, const MTPVector<MTPMessage> &msgs, const MTPVector<MTPUpdate> &other) {
App::wnd()->checkAutoLock();
App::feedUsers(users);
App::feedChats(chats);
feedMessageIds(other);
@ -2283,6 +2290,8 @@ void MainWidget::getDifferenceForce() {
}
void MainWidget::getDifference() {
if (this != App::main()) return;
LOG(("Getting difference! no updates timer: %1, remains: %2").arg(noUpdatesTimer.isActive() ? 1 : 0).arg(noUpdatesTimer.remainingTime()));
if (!updInited) return;
@ -2303,9 +2312,13 @@ void MainWidget::getDifference() {
}
void MainWidget::start(const MTPUser &user) {
MTP::authed(user.c_userSelf().vid.v);
int32 uid = user.c_userSelf().vid.v;
if (MTP::authedId() != uid) {
MTP::authed(uid);
Local::writeMtpData();
}
cSetOtherOnline(0);
App::initMedia();
App::feedUsers(MTP_vector<MTPUser>(1, user));
App::app()->startUpdateCheck();
MTP::send(MTPupdates_GetState(), rpcDone(&MainWidget::gotState));
@ -2571,6 +2584,9 @@ MainWidget::~MainWidget() {
}
void MainWidget::updateOnline(bool gotOtherOffline) {
if (this != App::main()) return;
App::wnd()->checkAutoLock();
bool isOnline = App::wnd()->isActive();
int updateIn = cOnlineUpdatePeriod();
if (isOnline) {
@ -2608,6 +2624,7 @@ void MainWidget::updateOnline(bool gotOtherOffline) {
}
void MainWidget::checkIdleFinish() {
if (this != App::main()) return;
if (psIdleTime() < uint64(cOfflineIdleTimeout())) {
_idleFinishTimer.stop();
_isIdle = false;
@ -2621,6 +2638,8 @@ void MainWidget::checkIdleFinish() {
void MainWidget::updateReceived(const mtpPrime *from, const mtpPrime *end) {
if (end <= from || !MTP::authedId()) return;
App::wnd()->checkAutoLock();
if (mtpTypeId(*from) == mtpc_new_session_created) {
MTPNewSession newSession(from, end);
updSeq = 0;

View file

@ -32,7 +32,7 @@ namespace {
typedef QMap<mtpRequestId, int32> AuthExportRequests; // holds target dc for auth export request
AuthExportRequests authExportRequests;
bool started = false;
bool _started = false;
uint32 layer;
@ -161,7 +161,7 @@ namespace {
DEBUG_LOG(("MTP Info: changing request %1 dc%2 to %3").arg(requestId).arg((dc > 0) ? "" : " and main dc").arg(newdc));
if (dc < 0) {
if (MTP::authedId()) { // import auth, set dc and resend
if (MTP::authedId() && !authExportRequests.contains(requestId)) { // import auth, set dc and resend
DEBUG_LOG(("MTP Info: importing auth to dc %1").arg(newdc));
DCAuthWaiters &waiters(authWaiters[newdc]);
if (!waiters.size()) {
@ -334,7 +334,7 @@ namespace {
namespace _mtp_internal {
MTProtoSessionPtr getSession(int32 dc) {
if (!started) return MTProtoSessionPtr();
if (!_started) return MTProtoSessionPtr();
if (!dc) return mainSession;
if (!(dc % _mtp_internal::dcShift)) {
dc += mainSession->getDC();
@ -588,19 +588,13 @@ namespace MTP {
void start() {
unixtimeInit();
if (!Local::oldKey().created()) {
LOG(("App Error: trying to start MTP without local key!"));
return;
}
mtpLoadData();
MTProtoDCMap &dcs(mtpDCMap());
mainSession = MTProtoSessionPtr(new MTProtoSession());
mainSession->start(mtpMainDC());
sessions[mainSession->getDC()] = mainSession;
started = true;
_started = true;
resender = new _mtp_internal::RequestResender();
if (mtpNeedConfig()) {
@ -608,15 +602,19 @@ namespace MTP {
}
}
bool started() {
return _started;
}
void restart() {
if (!started) return;
if (!_started) return;
for (Sessions::const_iterator i = sessions.cbegin(), e = sessions.cend(); i != e; ++i) {
(*i)->restart();
}
}
void restart(int32 dcMask) {
if (!started) return;
if (!_started) return;
for (Sessions::const_iterator i = sessions.cbegin(), e = sessions.cend(); i != e; ++i) {
if ((*i)->getDC() % _mtp_internal::dcShift == dcMask % _mtp_internal::dcShift) {
@ -625,23 +623,27 @@ namespace MTP {
}
}
void setdc(int32 dc, bool fromZeroOnly) {
if (!started) return;
int32 m = mainSession->getDC();
if (!dc || m == dc || (m && fromZeroOnly)) return;
void configure(int32 dc, int32 user) {
if (_started) return;
mtpSetDC(dc);
mainSession = _mtp_internal::getSession(dc);
mtpAuthed(user);
}
void setdc(int32 dc, bool fromZeroOnly) {
if (!dc || !_started) return;
mtpSetDC(dc, fromZeroOnly);
if (dc != mainSession->getDC()) {
mainSession = _mtp_internal::getSession(dc);
}
Local::writeMtpData();
}
int32 maindc() {
if (!started) return 0;
return mainSession->getDC();
return mtpMainDC();
}
int32 dcstate(int32 dc) {
if (!started) return 0;
if (!_started) return 0;
if (!dc) return mainSession->getState();
if (!(dc % _mtp_internal::dcShift)) {
@ -655,7 +657,7 @@ namespace MTP {
}
QString dctransport(int32 dc) {
if (!started) return QString();
if (!_started) return QString();
if (!dc) return mainSession->transport();
if (!(dc % _mtp_internal::dcShift)) {
@ -669,7 +671,7 @@ namespace MTP {
}
void initdc(int32 dc) {
if (!started) return;
if (!_started) return;
_mtp_internal::getSession(dc);
}
@ -781,15 +783,15 @@ namespace MTP {
void updateDcOptions(const QVector<MTPDcOption> &options) {
mtpUpdateDcOptions(options);
App::writeUserConfig();
Local::writeSettings();
}
void writeConfig(QDataStream &stream) {
return mtpWriteConfig(stream);
mtpKeysMap getKeys() {
return mtpGetKeys();
}
bool readConfigElem(int32 blockId, QDataStream &stream) {
return mtpReadConfigElem(blockId, stream);
void setKey(int32 dc, mtpAuthKeyPtr key) {
return mtpSetKey(dc, key);
}
};

View file

@ -78,11 +78,15 @@ namespace MTP {
};
void start();
bool started();
void restart();
void restart(int32 dcMask);
void configure(int32 dc, int32 user);
void setdc(int32 dc, bool fromZeroOnly = false);
int32 maindc();
int32 dcstate(int32 dc = 0);
QString dctransport(int32 dc = 0);
void initdc(int32 dc);
@ -131,8 +135,8 @@ namespace MTP {
return result;
}
void writeConfig(QDataStream &stream);
bool readConfigElem(int32 blockId, QDataStream &stream);
mtpKeysMap getKeys();
void setKey(int32 dc, mtpAuthKeyPtr key);
};

View file

@ -91,6 +91,8 @@ public:
static const uint64 RecreateKeyId = 0xFFFFFFFFFFFFFFFFL;
friend bool operator==(const mtpAuthKey &a, const mtpAuthKey &b);
private:
char _key[256];
@ -100,7 +102,12 @@ private:
};
inline bool operator==(const mtpAuthKey &a, const mtpAuthKey &b) {
return !memcmp(a._key, b._key, 256);
}
typedef QSharedPointer<mtpAuthKey> mtpAuthKeyPtr;
typedef QVector<mtpAuthKeyPtr> mtpKeysMap;
inline void aesEncrypt(const void *src, void *dst, uint32 len, void *key, void *iv) {
uchar aes_key[32], aes_iv[32];

View file

@ -180,12 +180,6 @@ namespace {
return false;
}
BN_sub_word(&bnPrime, 1); // (p - 1) / 2
BN_div_word(&bnPrime, 2);
if (BN_is_prime_ex(&bnPrime, MTPMillerRabinIterCount, ctx, NULL) == 0) {
return false;
}
switch (g) {
case 2: {
int32 mod8 = BN_mod_word(&bnPrime, 8);
@ -226,7 +220,14 @@ namespace {
default:
LOG(("BigNum PT Error: bad g value: %1").arg(g));
return false;
break;
break;
}
BN_sub_word(&bnPrime, 1); // (p - 1) / 2
BN_div_word(&bnPrime, 2);
if (BN_is_prime_ex(&bnPrime, MTPMillerRabinIterCount, ctx, NULL) == 0) {
return false;
}
return true;
@ -1105,13 +1106,13 @@ MTProtoConnectionPrivate::MTProtoConnectionPrivate(QThread *thread, MTProtoConne
// createConn();
if (!dc) {
const mtpDcOptions &gDcOptions(mtpDCOptions());
if (!gDcOptions.size()) {
const mtpDcOptions &options(cDcOptions());
if (options.isEmpty()) {
LOG(("MTP Error: connect failed, no DCs"));
dc = 0;
return;
}
dc = gDcOptions.cbegin().value().id;
dc = options.cbegin().value().id;
DEBUG_LOG(("MTP Info: searching for any DC, %1 selected..").arg(dc));
}
@ -1699,10 +1700,10 @@ void MTProtoConnectionPrivate::socketStart(bool afterConfig) {
pingId = pingMsgId = toSendPingId = 0;
const mtpDcOption *dcOption = 0;
const mtpDcOptions &gDcOptions(mtpDCOptions());
mtpDcOptions::const_iterator dcIndex = gDcOptions.constFind(dc % _mtp_internal::dcShift);
const mtpDcOptions &options(cDcOptions());
mtpDcOptions::const_iterator dcIndex = options.constFind(dc % _mtp_internal::dcShift);
DEBUG_LOG(("MTP Info: connecting to DC %1..").arg(dc));
if (dcIndex == gDcOptions.cend()) {
if (dcIndex == options.cend()) {
if (afterConfig) {
LOG(("MTP Error: DC %1 options not found right after config load!").arg(dc));
return restart();

View file

@ -25,283 +25,13 @@ namespace {
MTProtoDCMap gDCs;
bool configLoadedOnce = false;
bool mainDCChanged = false;
int32 mainDC = 2;
int userId = 0;
mtpDcOptions gDCOptions;
int32 userId = 0;
typedef QMap<int32, mtpAuthKeyPtr> _KeysMapForWrite;
_KeysMapForWrite _keysMapForWrite;
QMutex _keysMapForWriteMutex;
int32 readAuthKeysFields(QIODevice *io) {
if (!io->isOpen()) io->open(QIODevice::ReadOnly);
QDataStream stream(io);
stream.setVersion(QDataStream::Qt_5_1);
int32 oldFound = 0;
while (true) {
quint32 blockId;
stream >> blockId;
if (stream.status() == QDataStream::ReadPastEnd) {
DEBUG_LOG(("MTP Info: keys file read end"));
break;
} else if (stream.status() != QDataStream::Ok) {
LOG(("MTP Error: could not read block id, status: %1 - keys file is corrupted?..").arg(stream.status()));
break;
}
if (blockId == dbiVersion) {
qint32 keysVersion;
stream >> keysVersion;
continue; // should not be in encrypted part, just ignore
}
if (blockId != dbiEncrypted && blockId != dbiKey) {
oldFound = 2;
}
switch (blockId) {
case dbiEncrypted: {
QByteArray data, decrypted;
stream >> data;
if (!Local::oldKey().created()) {
LOG(("MTP Error: reading encrypted keys without local key!"));
continue;
}
if (data.size() <= 16 || (data.size() & 0x0F)) {
LOG(("MTP Error: bad encrypted part size: %1").arg(data.size()));
continue;
}
uint32 fullDataLen = data.size() - 16;
decrypted.resize(fullDataLen);
const char *dataKey = data.constData(), *encrypted = data.constData() + 16;
aesDecryptLocal(encrypted, decrypted.data(), fullDataLen, &Local::oldKey(), dataKey);
uchar sha1Buffer[20];
if (memcmp(hashSha1(decrypted.constData(), decrypted.size(), sha1Buffer), dataKey, 16)) {
LOG(("MTP Error: bad decrypt key, data from user-config not decrypted"));
continue;
}
uint32 dataLen = *(const uint32*)decrypted.constData();
if (dataLen > uint32(decrypted.size()) || dataLen <= fullDataLen - 16 || dataLen < 4) {
LOG(("MTP Error: bad decrypted part size: %1, fullDataLen: %2, decrypted size: %3").arg(dataLen).arg(fullDataLen).arg(decrypted.size()));
continue;
}
decrypted.resize(dataLen);
QBuffer decryptedStream(&decrypted);
decryptedStream.open(QIODevice::ReadOnly);
decryptedStream.seek(4); // skip size
readAuthKeysFields(&decryptedStream);
} break;
case dbiKey: {
qint32 dcId;
quint32 key[64];
stream >> dcId;
stream.readRawData((char*)key, 256);
if (stream.status() == QDataStream::Ok) {
DEBUG_LOG(("MTP Info: key found, dc %1, key: %2").arg(dcId).arg(mb(key, 256).str()));
dcId = dcId % _mtp_internal::dcShift;
mtpAuthKeyPtr keyPtr(new mtpAuthKey());
keyPtr->setKey(key);
keyPtr->setDC(dcId);
MTProtoDCPtr dc(new MTProtoDC(dcId, keyPtr));
gDCs.insert(dcId, dc);
}
} break;
case dbiUser: {
quint32 dcId;
qint32 uid;
stream >> uid >> dcId;
if (stream.status() == QDataStream::Ok) {
DEBUG_LOG(("MTP Info: user found, dc %1, uid %2").arg(dcId).arg(uid));
userId = uid;
mainDC = dcId;
}
} break;
case dbiDcOption: {
quint32 dcId, port;
QString host, ip;
stream >> dcId >> host >> ip >> port;
if (stream.status() == QDataStream::Ok) {
gDCOptions.insert(dcId, mtpDcOption(dcId, host.toUtf8().constData(), ip.toUtf8().constData(), port));
}
} break;
case dbiConfig1: {
quint32 maxSize;
stream >> maxSize;
if (stream.status() == QDataStream::Ok) {
cSetMaxGroupCount(maxSize);
}
} break;
}
if (stream.status() != QDataStream::Ok) {
LOG(("MTP Error: could not read data, status: %1 - keys file is corrupted?..").arg(stream.status()));
break;
}
}
return oldFound;
}
int32 readAuthKeys(QFile &file) {
QDataStream stream(&file);
stream.setVersion(QDataStream::Qt_5_1);
int32 oldFound = 0;
quint32 blockId;
stream >> blockId;
if (stream.status() == QDataStream::ReadPastEnd) {
DEBUG_LOG(("MTP Info: keys file read end"));
return oldFound;
} else if (stream.status() != QDataStream::Ok) {
LOG(("MTP Error: could not read block id, status: %1 - keys file is corrupted?..").arg(stream.status()));
return oldFound;
}
if (blockId == dbiVersion) {
qint32 keysVersion;
stream >> keysVersion;
if (keysVersion > AppVersion) return oldFound;
stream >> blockId;
if (stream.status() == QDataStream::ReadPastEnd) {
DEBUG_LOG(("MTP Info: keys file read end"));
return oldFound;
} else if (stream.status() != QDataStream::Ok) {
LOG(("MTP Error: could not read block id, status: %1 - keys file is corrupted?..").arg(stream.status()));
return oldFound;
}
if (blockId != dbiEncrypted) {
oldFound = (blockId != dbiKey) ? 2 : 1;
}
} else {
oldFound = 2;
}
file.reset();
oldFound = qMax(oldFound, readAuthKeysFields(&file));
return oldFound;
}
void writeAuthKeys();
void readAuthKeys() {
QFile keysFile(cWorkingDir() + cDataFile());
if (keysFile.open(QIODevice::ReadOnly)) {
DEBUG_LOG(("MTP Info: keys file opened for reading"));
int32 oldFound = readAuthKeys(keysFile);
if (gDCOptions.isEmpty()) {
const BuiltInDc *bdcs = builtInDcs();
for (int i = 0, l = builtInDcsCount(); i < l; ++i) {
gDCOptions.insert(bdcs[i].id, mtpDcOption(bdcs[i].id, "", bdcs[i].ip, bdcs[i].port));
DEBUG_LOG(("MTP Info: adding built in DC %1 connect option: %2:%3").arg(bdcs[i].id).arg(bdcs[i].ip).arg(bdcs[i].port));
}
}
if (mainDC && gDCOptions.find(mainDC) == gDCOptions.cend()) { // load first dc info
userId = 0;
mainDC = (gDCOptions.constFind(2) == gDCOptions.cend()) ? gDCOptions.begin().key() : 2;
} else {
DEBUG_LOG(("MTP Info: config from local, dc option count: %1").arg(gDCOptions.size()));
}
if (oldFound > 0) {
writeAuthKeys();
if (oldFound > 1) {
App::writeUserConfig();
}
DEBUG_LOG(("MTP Info: rewritten old data / config to new data and config"));
}
} else {
DEBUG_LOG(("MTP Info: could not open keys file for reading"));
const BuiltInDc *bdcs = builtInDcs();
for (int i = 0, l = builtInDcsCount(); i < l; ++i) {
gDCOptions.insert(bdcs[i].id, mtpDcOption(bdcs[i].id, "", bdcs[i].ip, bdcs[i].port));
DEBUG_LOG(("MTP Info: adding built in DC %1 connect option: %2:%3").arg(bdcs[i].id).arg(bdcs[i].ip).arg(bdcs[i].port));
}
}
}
typedef QVector<mtpAuthKeyPtr> _KeysToWrite;
void writeAuthKeys() {
_KeysToWrite keysToWrite;
{
QMutexLocker lock(&_keysMapForWriteMutex);
for (_KeysMapForWrite::const_iterator i = _keysMapForWrite.cbegin(), e = _keysMapForWrite.cend(); i != e; ++i) {
keysToWrite.push_back(i.value());
}
}
QFile keysFile(cWorkingDir() + cDataFile());
if (keysFile.open(QIODevice::WriteOnly)) {
DEBUG_LOG(("MTP Info: writing keys data for encrypt"));
QByteArray toEncrypt;
toEncrypt.reserve(65536);
toEncrypt.resize(4);
{
QBuffer buffer(&toEncrypt);
buffer.open(QIODevice::Append);
QDataStream stream(&buffer);
stream.setVersion(QDataStream::Qt_5_1);
for (_KeysToWrite::const_iterator i = keysToWrite.cbegin(), e = keysToWrite.cend(); i != e; ++i) {
stream << quint32(dbiKey) << quint32((*i)->getDC());
(*i)->write(stream);
}
if (stream.status() != QDataStream::Ok) {
LOG(("MTP Error: could not write keys to memory buf, status: %1").arg(stream.status()));
}
}
*(uint32*)(toEncrypt.data()) = toEncrypt.size();
uint32 size = toEncrypt.size(), fullSize = size;
if (fullSize & 0x0F) {
fullSize += 0x10 - (fullSize & 0x0F);
toEncrypt.resize(fullSize);
memset_rand(toEncrypt.data() + size, fullSize - size);
}
QByteArray encrypted(16 + fullSize, Qt::Uninitialized); // 128bit of sha1 - key128, sizeof(data), data
hashSha1(toEncrypt.constData(), toEncrypt.size(), encrypted.data());
aesEncryptLocal(toEncrypt.constData(), encrypted.data() + 16, fullSize, &Local::oldKey(), encrypted.constData());
DEBUG_LOG(("MTP Info: keys file opened for writing %1 keys").arg(keysToWrite.size()));
QDataStream keysStream(&keysFile);
keysStream.setVersion(QDataStream::Qt_5_1);
keysStream << quint32(dbiVersion) << qint32(AppVersion);
keysStream << quint32(dbiEncrypted) << encrypted; // write all encrypted data
if (keysStream.status() != QDataStream::Ok) {
LOG(("MTP Error: could not write keys, status: %1").arg(keysStream.status()));
}
} else {
LOG(("MTP Error: could not open keys file for writing"));
}
}
class _KeysReader {
public:
_KeysReader() {
readAuthKeys();
}
};
}
void mtpLoadData() {
static _KeysReader keysReader;
}
int32 mtpAuthed() {
@ -309,9 +39,8 @@ int32 mtpAuthed() {
}
void mtpAuthed(int32 uid) {
if (userId != uid && mainDC) {
if (userId != uid) {
userId = uid;
App::writeUserConfig();
}
}
@ -319,10 +48,6 @@ MTProtoDCMap &mtpDCMap() {
return gDCs;
}
const mtpDcOptions &mtpDCOptions() {
return gDCOptions;
}
bool mtpNeedConfig() {
return !configLoadedOnce;
}
@ -344,12 +69,11 @@ void mtpLogoutOtherDCs() {
}
}
void mtpSetDC(int32 dc) {
void mtpSetDC(int32 dc, bool firstOnly) {
if (!dc || (firstOnly && mainDCChanged)) return;
mainDCChanged = true;
if (dc != mainDC) {
mainDC = dc;
if (userId) {
App::writeUserConfig();
}
}
}
@ -367,7 +91,7 @@ MTProtoDC::MTProtoDC(int32 id, const mtpAuthKeyPtr &key) : _id(id), _key(key), _
void MTProtoDC::authKeyWrite() {
DEBUG_LOG(("AuthKey Info: MTProtoDC::authKeyWrite() slot, dc %1").arg(_id));
if (_key) {
writeAuthKeys();
Local::writeMtpData();
}
}
@ -414,7 +138,7 @@ namespace {
cSetMaxGroupCount(data.vchat_size_max.v);
configLoadedOnce = true;
App::writeUserConfig();
Local::writeSettings();
mtpConfigLoader()->done();
}
@ -427,18 +151,22 @@ namespace {
void mtpUpdateDcOptions(const QVector<MTPDcOption> &options) {
QSet<int32> already, restart;
for (QVector<MTPDcOption>::const_iterator i = options.cbegin(), e = options.cend(); i != e; ++i) {
const MTPDdcOption &optData(i->c_dcOption());
if (already.constFind(optData.vid.v) == already.cend()) {
already.insert(optData.vid.v);
mtpDcOptions::const_iterator a = gDCOptions.constFind(optData.vid.v);
if (a != gDCOptions.cend()) {
if (a.value().ip != optData.vip_address.c_string().v || a.value().port != optData.vport.v) {
restart.insert(optData.vid.v);
{
mtpDcOptions opts(cDcOptions());
for (QVector<MTPDcOption>::const_iterator i = options.cbegin(), e = options.cend(); i != e; ++i) {
const MTPDdcOption &optData(i->c_dcOption());
if (already.constFind(optData.vid.v) == already.cend()) {
already.insert(optData.vid.v);
mtpDcOptions::const_iterator a = opts.constFind(optData.vid.v);
if (a != opts.cend()) {
if (a.value().ip != optData.vip_address.c_string().v || a.value().port != optData.vport.v) {
restart.insert(optData.vid.v);
}
}
opts.insert(optData.vid.v, mtpDcOption(optData.vid.v, optData.vhostname.c_string().v, optData.vip_address.c_string().v, optData.vport.v));
}
gDCOptions.insert(optData.vid.v, mtpDcOption(optData.vid.v, optData.vhostname.c_string().v, optData.vip_address.c_string().v, optData.vport.v));
}
cSetDcOptions(opts);
}
for (QSet<int32>::const_iterator i = restart.cbegin(), e = restart.cend(); i != e; ++i) {
MTP::restart(*i);
@ -490,9 +218,10 @@ void MTProtoConfigLoader::enumDC() {
} else {
MTP::killSession(MTP::cfg + _enumCurrent);
}
for (mtpDcOptions::const_iterator i = gDCOptions.cbegin(), e = gDCOptions.cend(); i != e; ++i) {
const mtpDcOptions &options(cDcOptions());
for (mtpDcOptions::const_iterator i = options.cbegin(), e = options.cend(); i != e; ++i) {
if (i.key() == _enumCurrent) {
_enumCurrent = (++i == e) ? gDCOptions.cbegin().key() : i.key();
_enumCurrent = (++i == e) ? options.cbegin().key() : i.key();
break;
}
}
@ -512,51 +241,16 @@ void mtpDestroyConfigLoader() {
configLoader = 0;
}
void mtpWriteConfig(QDataStream &stream) {
if (userId) {
stream << quint32(dbiUser) << qint32(userId) << quint32(mainDC);
mtpKeysMap mtpGetKeys() {
mtpKeysMap result;
QMutexLocker lock(&_keysMapForWriteMutex);
for (_KeysMapForWrite::const_iterator i = _keysMapForWrite.cbegin(), e = _keysMapForWrite.cend(); i != e; ++i) {
result.push_back(i.value());
}
for (mtpDcOptions::const_iterator i = gDCOptions.cbegin(), e = gDCOptions.cend(); i != e; ++i) {
stream << quint32(dbiDcOption) << i->id << QString(i->host.c_str()) << QString(i->ip.c_str()) << i->port;
}
stream << quint32(dbiConfig1) << qint32(cMaxGroupCount());
return result;
}
bool mtpReadConfigElem(int32 blockId, QDataStream &stream) {
switch (blockId) {
case dbiUser: {
quint32 dcId;
qint32 uid;
stream >> uid >> dcId;
if (stream.status() == QDataStream::Ok) {
DEBUG_LOG(("MTP Info: user found, dc %1, uid %2").arg(dcId).arg(uid));
userId = uid;
mainDC = dcId;
return true;
}
} break;
case dbiDcOption: {
quint32 dcId, port;
QString host, ip;
stream >> dcId >> host >> ip >> port;
if (stream.status() == QDataStream::Ok) {
gDCOptions.insert(dcId, mtpDcOption(dcId, host.toUtf8().constData(), ip.toUtf8().constData(), port));
return true;
}
} break;
case dbiConfig1: {
quint32 maxSize;
stream >> maxSize;
if (stream.status() == QDataStream::Ok) {
cSetMaxGroupCount(maxSize);
return true;
}
} break;
}
return false;
void mtpSetKey(int32 dcId, mtpAuthKeyPtr key) {
MTProtoDCPtr dc(new MTProtoDC(dcId, key));
gDCs.insert(dcId, dc);
}

View file

@ -60,17 +60,6 @@ private:
typedef QSharedPointer<MTProtoDC> MTProtoDCPtr;
typedef QMap<uint32, MTProtoDCPtr> MTProtoDCMap;
struct mtpDcOption {
mtpDcOption(int _id, const string &_host, const string &_ip, int _port) : id(_id), host(_host), ip(_ip), port(_port) {
}
int id;
string host;
string ip;
int port;
};
typedef QMap<int, mtpDcOption> mtpDcOptions;
class MTProtoConfigLoader : public QObject {
Q_OBJECT
@ -101,20 +90,17 @@ private:
MTProtoConfigLoader *mtpConfigLoader();
void mtpDestroyConfigLoader();
const mtpDcOptions &mtpDCOptions();
MTProtoDCMap &mtpDCMap();
bool mtpNeedConfig();
int32 mtpMainDC();
void mtpLogoutOtherDCs();
void mtpSetDC(int32 dc);
void mtpSetDC(int32 dc, bool firstOnly = false);
uint32 mtpMaxChatSize();
void mtpWriteAuthKeys();
void mtpLoadData();
int32 mtpAuthed();
void mtpAuthed(int32 uid);
void mtpWriteConfig(QDataStream &stream);
bool mtpReadConfigElem(int32 blockId, QDataStream &stream);
mtpKeysMap mtpGetKeys();
void mtpSetKey(int32 dc, mtpAuthKeyPtr key);
void mtpUpdateDcOptions(const QVector<MTPDcOption> &options);

View file

@ -0,0 +1,216 @@
/*
This file is part of Telegram Desktop,
the official desktop version of Telegram messaging app, see https://telegram.org
Telegram Desktop is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
It is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Full license: https://github.com/telegramdesktop/tdesktop/blob/master/LICENSE
Copyright (c) 2014 John Preston, https://desktop.telegram.org
*/
#include "stdafx.h"
#include "lang.h"
#include "style.h"
#include "localstorage.h"
#include "passcodewidget.h"
#include "window.h"
#include "application.h"
#include "gui/text.h"
class LogOutLink : public ITextLink {
public:
void onClick(Qt::MouseButton) const {
App::wnd()->onLogout();
}
};
PasscodeWidget::PasscodeWidget(QWidget *parent) : QWidget(parent),
_passcode(this, st::passcodeInput),
_submit(this, lang(lng_passcode_submit), st::passcodeSubmit),
_logout(this, lng_passcode_logout(lt_link_start, textcmdStartLink(1), lt_link_end, textcmdStopLink())) {
setGeometry(QRect(0, st::titleHeight, App::wnd()->width(), App::wnd()->height() - st::titleHeight));
connect(App::wnd(), SIGNAL(resized(const QSize &)), this, SLOT(onParentResize(const QSize &)));
_passcode.setEchoMode(QLineEdit::Password);
connect(&_submit, SIGNAL(clicked()), this, SLOT(onSubmit()));
_errorTimer.setSingleShot(true);
connect(&_errorTimer, SIGNAL(timeout()), this, SLOT(onError()));
_logout.setLink(1, TextLinkPtr(new LogOutLink()));
connect(&_passcode, SIGNAL(changed()), this, SLOT(onChanged()));
connect(&_passcode, SIGNAL(accepted()), this, SLOT(onSubmit()));
show();
_passcode.setFocus();
}
void PasscodeWidget::onParentResize(const QSize &newSize) {
resize(newSize);
}
void PasscodeWidget::onSubmit() {
if (_passcode.text().isEmpty()) {
_passcode.setFocus();
_passcode.notaBene();
return;
}
if (App::main()) {
if (Local::checkPasscode(_passcode.text().toUtf8())) {
App::wnd()->clearPasscode();
} else {
_error = QString();
_passcode.setDisabled(true);
_errorTimer.start(WrongPasscodeTimeout);
return;
}
} else {
if (Local::readMap(_passcode.text().toUtf8()) != Local::ReadMapPassNeeded) {
App::app()->checkMapVersion();
MTP::start();
if (MTP::authedId()) {
App::wnd()->setupMain(true);
} else {
App::wnd()->setupIntro(true);
}
} else {
_error = QString();
_passcode.setDisabled(true);
_errorTimer.start(WrongPasscodeTimeout);
update();
return;
}
}
}
void PasscodeWidget::onError() {
_error = lang(lng_passcode_wrong);
_passcode.setDisabled(false);
_passcode.selectAll();
_passcode.setFocus();
_passcode.notaBene();
update();
}
void PasscodeWidget::onChanged() {
if (!_error.isEmpty()) {
_error = QString();
update();
}
}
void PasscodeWidget::animShow(const QPixmap &bgAnimCache, bool back) {
_bgAnimCache = bgAnimCache;
anim::stop(this);
showAll();
_animCache = myGrab(this, rect());
a_coord = back ? anim::ivalue(-st::introSlideShift, 0) : anim::ivalue(st::introSlideShift, 0);
a_alpha = anim::fvalue(0, 1);
a_bgCoord = back ? anim::ivalue(0, st::introSlideShift) : anim::ivalue(0, -st::introSlideShift);
a_bgAlpha = anim::fvalue(1, 0);
hideAll();
anim::start(this);
show();
}
bool PasscodeWidget::animStep(float64 ms) {
float64 fullDuration = st::introSlideDelta + st::introSlideDuration, dt = ms / fullDuration;
float64 dt1 = (ms > st::introSlideDuration) ? 1 : (ms / st::introSlideDuration), dt2 = (ms > st::introSlideDelta) ? (ms - st::introSlideDelta) / (st::introSlideDuration) : 0;
bool res = true;
if (dt2 >= 1) {
res = false;
a_bgCoord.finish();
a_bgAlpha.finish();
a_coord.finish();
a_alpha.finish();
_animCache = _bgAnimCache = QPixmap();
showAll();
setInnerFocus();
} else {
a_bgCoord.update(dt1, st::introHideFunc);
a_bgAlpha.update(dt1, st::introAlphaHideFunc);
a_coord.update(dt2, st::introShowFunc);
a_alpha.update(dt2, st::introAlphaShowFunc);
}
update();
return res;
}
void PasscodeWidget::showAll() {
_passcode.show();
_submit.show();
_logout.show();
}
void PasscodeWidget::hideAll() {
_passcode.hide();
_submit.hide();
_logout.hide();
}
void PasscodeWidget::paintEvent(QPaintEvent *e) {
bool trivial = (rect() == e->rect());
setMouseTracking(true);
QPainter p(this);
if (!trivial) {
p.setClipRect(e->rect());
}
if (animating()) {
p.setOpacity(a_bgAlpha.current());
p.drawPixmap(a_bgCoord.current(), 0, _bgAnimCache);
p.setOpacity(a_alpha.current());
p.drawPixmap(a_coord.current(), 0, _animCache);
} else {
p.fillRect(rect(), st::setBG->b);
p.setFont(st::passcodeHeaderFont->f);
p.drawText(QRect(0, _passcode.y() - st::passcodeHeaderHeight, width(), st::passcodeHeaderHeight), lang(lng_passcode_enter), style::al_center);
if (!_error.isEmpty()) {
p.setFont(st::boxFont->f);
p.setPen(st::setErrColor->p);
p.drawText(QRect(0, _passcode.y() + _passcode.height(), width(), st::usernameSkip), _error, style::al_center);
}
}
}
void PasscodeWidget::resizeEvent(QResizeEvent *e) {
_passcode.move((width() - _passcode.width()) / 2, (height() / 3));
_submit.move(_passcode.x(), _passcode.y() + _passcode.height() + st::passcodeSkip);
_logout.move(_passcode.x() + (_passcode.width() - _logout.width()) / 2, _submit.y() + _submit.height() + st::linkFont->ascent);
}
void PasscodeWidget::mousePressEvent(QMouseEvent *e) {
}
void PasscodeWidget::keyPressEvent(QKeyEvent *e) {
}
void PasscodeWidget::setInnerFocus() {
_passcode.setFocus();
}
PasscodeWidget::~PasscodeWidget() {
}

View file

@ -0,0 +1,62 @@
/*
This file is part of Telegram Desktop,
the official desktop version of Telegram messaging app, see https://telegram.org
Telegram Desktop is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
It is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Full license: https://github.com/telegramdesktop/tdesktop/blob/master/LICENSE
Copyright (c) 2014 John Preston, https://desktop.telegram.org
*/
#pragma once
class PasscodeWidget : public QWidget, public Animated {
Q_OBJECT
public:
PasscodeWidget(QWidget *parent);
void paintEvent(QPaintEvent *e);
void resizeEvent(QResizeEvent *e);
void mousePressEvent(QMouseEvent *e);
void keyPressEvent(QKeyEvent *e);
void setInnerFocus();
void animShow(const QPixmap &bgAnimCache, bool back = false);
bool animStep(float64 ms);
~PasscodeWidget();
public slots:
void onParentResize(const QSize &newSize);
void onError();
void onChanged();
void onSubmit();
signals:
private:
void showAll();
void hideAll();
QPixmap _animCache, _bgAnimCache;
anim::ivalue a_coord, a_bgCoord;
anim::fvalue a_alpha, a_bgAlpha;
FlatButton _submit;
FlatInput _passcode;
FlatLabel _logout;
QString _error;
QTimer _errorTimer;
};

View file

@ -22,6 +22,8 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "application.h"
#include "mainwidget.h"
#include "localstorage.h"
#include <sys/stat.h>
#include <sys/types.h>
#include <cstdlib>
@ -703,7 +705,7 @@ void PsMainWindow::psSavePosition(Qt::WindowState state) {
if (curPos.w >= st::wndMinWidth && curPos.h >= st::wndMinHeight) {
if (curPos.x != pos.x || curPos.y != pos.y || curPos.w != pos.w || curPos.h != pos.h || curPos.moncrc != pos.moncrc || curPos.maximized != pos.maximized) {
cSetWindowPos(curPos);
App::writeConfig();
Local::writeSettings();
}
}
}
@ -1369,6 +1371,10 @@ void psUserActionDone() {
_lastUserAction = getms(true);
}
bool psIdleSupported() {
return false;
}
uint64 psIdleTime() {
return getms(true) - _lastUserAction;
}

View file

@ -167,6 +167,7 @@ private:
};
void psUserActionDone();
bool psIdleSupported();
uint64 psIdleTime();
bool psSkipAudioNotify();

View file

@ -23,6 +23,8 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "mainwidget.h"
#include "historywidget.h"
#include "localstorage.h"
namespace {
QStringList _initLogs;
@ -61,9 +63,14 @@ void MacPrivate::notifyClicked(unsigned long long peer) {
History *history = App::history(PeerId(peer));
App::wnd()->showFromTray();
App::wnd()->hideSettings();
App::main()->showPeer(history->peer->id, false, true);
App::wnd()->notifyClear(history);
if (App::passcoded()) {
App::wnd()->passcodeWidget()->setInnerFocus();
App::wnd()->notifyClear();
} else {
App::wnd()->hideSettings();
App::main()->showPeer(history->peer->id, false, true);
App::wnd()->notifyClear(history);
}
}
void MacPrivate::notifyReplied(unsigned long long peer, const char *str) {
@ -268,7 +275,7 @@ void PsMainWindow::psSavePosition(Qt::WindowState state) {
if (curPos.w >= st::wndMinWidth && curPos.h >= st::wndMinHeight) {
if (curPos.x != pos.x || curPos.y != pos.y || curPos.w != pos.w || curPos.h != pos.h || curPos.moncrc != pos.moncrc || curPos.maximized != pos.maximized) {
cSetWindowPos(curPos);
App::writeConfig();
Local::writeSettings();
}
}
}
@ -475,12 +482,12 @@ void PsMainWindow::psNotifyShown(NotifyWindow *w) {
}
void PsMainWindow::psPlatformNotify(HistoryItem *item) {
QString title = (cNotifyView() <= dbinvShowName) ? item->history()->peer->name : qsl("Telegram Desktop");
QString subtitle = (cNotifyView() <= dbinvShowName) ? item->notificationHeader() : QString();
QPixmap pix = (cNotifyView() <= dbinvShowName) ? item->history()->peer->photo->pix(st::notifyMacPhotoSize) : QPixmap();
QString msg = (cNotifyView() <= dbinvShowPreview) ? item->notificationText() : lang(lng_notification_preview);
QString title = (!App::passcoded() && cNotifyView() <= dbinvShowName) ? item->history()->peer->name : qsl("Telegram Desktop");
QString subtitle = (!App::passcoded() && cNotifyView() <= dbinvShowName) ? item->notificationHeader() : QString();
QPixmap pix = (!App::passcoded() && cNotifyView() <= dbinvShowName) ? item->history()->peer->photo->pix(st::notifyMacPhotoSize) : QPixmap();
QString msg = (!App::passcoded() && cNotifyView() <= dbinvShowPreview) ? item->notificationText() : lang(lng_notification_preview);
_private.showNotify(item->history()->peer->id, pix, title, subtitle, msg, (cNotifyView() <= dbinvShowPreview));
_private.showNotify(item->history()->peer->id, pix, title, subtitle, msg, !App::passcoded() && (cNotifyView() <= dbinvShowPreview));
}
bool PsMainWindow::eventFilter(QObject *obj, QEvent *evt) {
@ -924,6 +931,10 @@ void psUserActionDone() {
_lastUserAction = getms(true);
}
bool psIdleSupported() {
return objc_idleSupported();
}
uint64 psIdleTime() {
int64 idleTime = 0;
return objc_idleTime(idleTime) ? idleTime : (getms(true) - _lastUserAction);

View file

@ -195,6 +195,7 @@ private:
};
void psUserActionDone();
bool psIdleSupported();
uint64 psIdleTime();
bool psSkipAudioNotify();

View file

@ -57,6 +57,7 @@ void objc_activateWnd(WId winId);
void objc_debugShowAlert(const QString &str);
void objc_outputDebugString(const QString &str);
bool objc_idleSupported();
bool objc_idleTime(int64 &idleTime);
bool objc_showOpenWithMenu(int x, int y, const QString &file);

View file

@ -149,14 +149,12 @@ public:
void onNotifyClick(NSUserNotification *notification) {
NSNumber *peerObj = [[notification userInfo] objectForKey:@"peer"];
unsigned long long peerLong = peerObj ? [peerObj unsignedLongLongValue] : 0;
LOG(("Received notification click with peer %1").arg(peerLong));
wnd->notifyClicked(peerLong);
}
void onNotifyReply(NSUserNotification *notification) {
NSNumber *peerObj = [[notification userInfo] objectForKey:@"peer"];
unsigned long long peerLong = peerObj ? [peerObj unsignedLongLongValue] : 0;
LOG(("Received notification reply with peer %1").arg(peerLong));
wnd->notifyReplied(peerLong, [[[notification response] string] UTF8String]);
}
@ -328,6 +326,11 @@ PsMacWindowPrivate::~PsMacWindowPrivate() {
delete data;
}
bool objc_idleSupported() {
int64 idleTime = 0;
return objc_idleTime(idleTime);
}
bool objc_idleTime(int64 &idleTime) { // taken from https://github.com/trueinteractions/tint/issues/53
CFMutableDictionaryRef properties = 0;
CFTypeRef obj;

View file

@ -22,6 +22,8 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "application.h"
#include "mainwidget.h"
#include "localstorage.h"
#include <Shobjidl.h>
#include <dbghelp.h>
#include <shellapi.h>
@ -717,6 +719,10 @@ namespace {
}
switch (msg) {
case WM_TIMECHANGE: {
App::wnd()->checkAutoLockIn(100);
} return false;
case WM_WTSSESSION_CHANGE: {
if (wParam == WTS_SESSION_LOGOFF || wParam == WTS_SESSION_LOCK) {
sessionLoggedOff = true;
@ -1135,7 +1141,7 @@ void PsMainWindow::psSavePosition(Qt::WindowState state) {
if (curPos.w >= st::wndMinWidth && curPos.h >= st::wndMinHeight) {
if (curPos.x != pos.x || curPos.y != pos.y || curPos.w != pos.w || curPos.h != pos.h || curPos.moncrc != pos.moncrc || curPos.maximized != pos.maximized) {
cSetWindowPos(curPos);
App::writeConfig();
Local::writeSettings();
}
}
}
@ -1752,6 +1758,7 @@ namespace {
if (len && len < nameBufSize) {
if (QRegularExpression(qsl("^Telegram(\\s*\\(\\d+\\))?$")).match(QString::fromStdWString(nameBuf)).hasMatch()) {
BOOL res = ::SetForegroundWindow(hWnd);
::SetFocus(hWnd);
return FALSE;
}
}
@ -1769,6 +1776,12 @@ void psUserActionDone() {
if (sessionLoggedOff) sessionLoggedOff = false;
}
bool psIdleSupported() {
LASTINPUTINFO lii;
lii.cbSize = sizeof(LASTINPUTINFO);
return GetLastInputInfo(&lii);
}
uint64 psIdleTime() {
LASTINPUTINFO lii;
lii.cbSize = sizeof(LASTINPUTINFO);

View file

@ -168,6 +168,7 @@ private:
};
void psUserActionDone();
bool psIdleSupported();
uint64 psIdleTime();
bool psSkipAudioNotify();

View file

@ -20,6 +20,8 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "settings.h"
#include "lang.h"
mtpDcOptions gDcOptions;
bool gTestMode = false;
bool gDebug = false;
bool gManyInstance = false;
@ -76,6 +78,9 @@ bool gCompressPastedImage = true;
QString gTimeFormat = qsl("hh:mm");
int32 gAutoLock = 3600;
bool gHasPasscode = false;
DBIEmojiTab gEmojiTab = dbietRecent;
RecentEmojiPack gRecentEmojis;
RecentEmojiPreload gRecentEmojisPreload;

View file

@ -41,6 +41,18 @@ inline void cSet##Name(const Type &Name) { \
g##Name = Name; \
}
struct mtpDcOption {
mtpDcOption(int _id, const string &_host, const string &_ip, int _port) : id(_id), host(_host), ip(_ip), port(_port) {
}
int id;
string host;
string ip;
int port;
};
typedef QMap<int, mtpDcOption> mtpDcOptions;
DeclareSetting(mtpDcOptions, DcOptions);
DeclareSetting(bool, TestMode);
DeclareSetting(QString, LoggedPhoneNumber);
DeclareReadSetting(uint32, ConnectionsInSession);
@ -108,6 +120,9 @@ DeclareSetting(DBIScale, ConfigScale);
DeclareSetting(bool, CompressPastedImage);
DeclareSetting(QString, TimeFormat);
DeclareSetting(int32, AutoLock);
DeclareSetting(bool, HasPasscode);
inline void cChangeTimeFormat(const QString &newFormat) {
if (!newFormat.isEmpty()) cSetTimeFormat(newFormat);
}

View file

@ -31,6 +31,8 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "boxes/downloadpathbox.h"
#include "boxes/usernamebox.h"
#include "boxes/languagebox.h"
#include "boxes/passcodebox.h"
#include "boxes/autolockbox.h"
#include "langloaderplain.h"
#include "gui/filedialog.h"
@ -169,7 +171,14 @@ SettingsInner::SettingsInner(SettingsWidget *parent) : QWidget(parent),
_storageClearFailedWidth(st::linkFont->m.width(lang(lng_local_storage_clear_failed))),
// advanced
_passcodeEdit(this, lang(cHasPasscode() ? lng_passcode_change : lng_passcode_turn_on)),
_passcodeTurnOff(this, lang(lng_passcode_turn_off)),
_autoLock(this, (cAutoLock() % 3600) ? lng_passcode_autolock_minutes(lt_count, cAutoLock() / 60) : lng_passcode_autolock_hours(lt_count, cAutoLock() / 3600)),
_autoLockText(lang(psIdleSupported() ? lng_passcode_autolock_away : lng_passcode_autolock_inactive) + ' '),
_autoLockWidth(st::linkFont->m.width(_autoLockText)),
_connectionType(this, lng_connection_auto(lt_type, QString())),
_connectionTypeText(lang(lng_connection_type) + ' '),
_connectionTypeWidth(st::linkFont->m.width(_connectionTypeText)),
_resetSessions(this, lang(lng_settings_reset)),
_logOut(this, lang(lng_settings_logout), st::btnLogout),
_resetDone(false)
@ -264,13 +273,13 @@ SettingsInner::SettingsInner(SettingsWidget *parent) : QWidget(parent),
}
// advanced
connect(&_passcodeEdit, SIGNAL(clicked()), this, SLOT(onPasscode()));
connect(&_passcodeTurnOff, SIGNAL(clicked()), this, SLOT(onPasscodeOff()));
connect(&_autoLock, SIGNAL(clicked()), this, SLOT(onAutoLock()));
connect(&_connectionType, SIGNAL(clicked()), this, SLOT(onConnectionType()));
connect(&_resetSessions, SIGNAL(clicked()), this, SLOT(onResetSessions()));
connect(&_logOut, SIGNAL(clicked()), App::wnd(), SLOT(onLogout()));
_connectionTypeText = lang(lng_connection_type) + ' ';
_connectionTypeWidth = st::linkFont->m.width(_connectionTypeText);
if (App::main()) {
connect(App::main(), SIGNAL(peerUpdated(PeerData*)), this, SLOT(peerUpdated(PeerData*)));
}
@ -583,7 +592,15 @@ void SettingsInner::paintEvent(QPaintEvent *e) {
p.setFont(st::linkFont->f);
p.setPen(st::black->p);
p.drawText(_left + st::setHeaderLeft, _connectionType.y() + st::linkFont->ascent, _connectionTypeText);
if (self()) {
top += _passcodeEdit.height() + st::setLittleSkip;
if (cHasPasscode()) {
p.drawText(_left, top + st::linkFont->ascent, _autoLockText);
top += _autoLock.height() + st::setLittleSkip;
}
}
p.drawText(_left, _connectionType.y() + st::linkFont->ascent, _connectionTypeText);
if (self() && _resetDone) {
p.drawText(_resetSessions.x(), _resetSessions.y() + st::linkFont->ascent, lang(lng_settings_reset_done));
@ -681,7 +698,15 @@ void SettingsInner::resizeEvent(QResizeEvent *e) {
// advanced
top += st::setHeaderSkip;
_connectionType.move(_left + st::setHeaderLeft + _connectionTypeWidth, top); top += _connectionType.height() + st::setLittleSkip;
if (self()) {
_passcodeEdit.move(_left, top);
_passcodeTurnOff.move(_left + st::setWidth - _passcodeTurnOff.width(), top); top += _passcodeTurnOff.height() + st::setLittleSkip;
if (cHasPasscode()) {
_autoLock.move(_left + _autoLockWidth, top); top += _autoLock.height() + st::setLittleSkip;
}
}
_connectionType.move(_left + _connectionTypeWidth, top); top += _connectionType.height() + st::setLittleSkip;
if (self()) {
_resetSessions.move(_left, top); top += _resetSessions.height() + st::setSectionSkip;
_logOut.move(_left, top);
@ -775,6 +800,13 @@ void SettingsInner::updateConnectionType() {
}
}
void SettingsInner::passcodeChanged() {
resizeEvent(0);
_passcodeEdit.setText(lang(cHasPasscode() ? lng_passcode_change : lng_passcode_turn_on));
_autoLock.setText((cAutoLock() % 3600) ? lng_passcode_autolock_minutes(lt_count, cAutoLock() / 60) : lng_passcode_autolock_hours(lt_count, cAutoLock() / 3600));
showAll();
}
void SettingsInner::updateBackgroundRect() {
update(_left, _tileBackground.y() - st::setLittleSkip - st::setBackgroundSize, st::setBackgroundSize, st::setBackgroundSize);
}
@ -918,6 +950,14 @@ void SettingsInner::showAll() {
// advanced
if (self()) {
_passcodeEdit.show();
if (cHasPasscode()) {
_autoLock.show();
_passcodeTurnOff.show();
} else {
_autoLock.hide();
_passcodeTurnOff.hide();
}
if (_resetDone) {
_resetSessions.hide();
} else {
@ -925,6 +965,9 @@ void SettingsInner::showAll() {
}
_logOut.show();
} else {
_passcodeEdit.hide();
_autoLock.hide();
_passcodeTurnOff.hide();
_resetSessions.hide();
_logOut.hide();
}
@ -1020,7 +1063,7 @@ void SettingsInner::onChangeLanguage() {
void SettingsInner::onSaveTestLang() {
cSetLangFile(_testlang);
cSetLang(languageTest);
App::writeConfig();
Local::writeSettings();
cSetRestarting(true);
App::quit();
}
@ -1033,7 +1076,7 @@ void SettingsInner::onUpdateLocalStorage() {
void SettingsInner::onAutoUpdate() {
cSetAutoUpdate(!cAutoUpdate());
App::writeConfig();
Local::writeSettings();
resizeEvent(0);
if (cAutoUpdate()) {
App::app()->startUpdateCheck();
@ -1068,6 +1111,24 @@ void SettingsInner::onRestartNow() {
App::quit();
}
void SettingsInner::onPasscode() {
PasscodeBox *box = new PasscodeBox();
connect(box, SIGNAL(closed()), this, SLOT(passcodeChanged()));
App::wnd()->showLayer(box);
}
void SettingsInner::onPasscodeOff() {
PasscodeBox *box = new PasscodeBox(true);
connect(box, SIGNAL(closed()), this, SLOT(passcodeChanged()));
App::wnd()->showLayer(box);
}
void SettingsInner::onAutoLock() {
AutoLockBox *box = new AutoLockBox();
connect(box, SIGNAL(closed()), this, SLOT(passcodeChanged()));
App::wnd()->showLayer(box);
}
void SettingsInner::onConnectionType() {
ConnectionBox *box = new ConnectionBox();
connect(box, SIGNAL(closed()), this, SLOT(updateConnectionType()), Qt::QueuedConnection);
@ -1090,7 +1151,7 @@ void SettingsInner::onWorkmodeTray() {
}
cSetWorkMode(newMode);
App::wnd()->psUpdateWorkmode();
App::writeConfig();
Local::writeSettings();
}
void SettingsInner::onWorkmodeWindow() {
@ -1103,7 +1164,7 @@ void SettingsInner::onWorkmodeWindow() {
}
cSetWorkMode(newMode);
App::wnd()->psUpdateWorkmode();
App::writeConfig();
Local::writeSettings();
}
void SettingsInner::onAutoStart() {
@ -1114,19 +1175,19 @@ void SettingsInner::onAutoStart() {
_startMinimized.setChecked(false);
} else {
psAutoStart(_autoStart.checked());
App::writeConfig();
Local::writeSettings();
}
}
void SettingsInner::onStartMinimized() {
cSetStartMinimized(_startMinimized.checked());
App::writeConfig();
Local::writeSettings();
}
void SettingsInner::onSendToMenu() {
cSetSendToMenu(_sendToMenu.checked());
psSendToMenu(_sendToMenu.checked());
App::writeConfig();
Local::writeSettings();
}
void SettingsInner::onScaleAuto() {
@ -1164,7 +1225,7 @@ void SettingsInner::setScale(DBIScale newScale) {
if (cConfigScale() == newScale) return;
cSetConfigScale(newScale);
App::writeConfig();
Local::writeSettings();
App::wnd()->getTitle()->showUpdateBtn();
if (newScale == dbisAuto && !_dpiAutoScale.checked()) {
_dpiAutoScale.setChecked(true);
@ -1184,7 +1245,7 @@ void SettingsInner::setScale(DBIScale newScale) {
void SettingsInner::onSoundNotify() {
cSetSoundNotify(_soundNotify.checked());
App::writeUserConfig();
Local::writeUserSettings();
}
void SettingsInner::onDesktopNotify() {
@ -1193,11 +1254,11 @@ void SettingsInner::onDesktopNotify() {
App::wnd()->notifyClear();
_senderName.setDisabled(true);
_messagePreview.setDisabled(true);
App::writeUserConfig();
Local::writeUserSettings();
} else {
_senderName.setDisabled(false);
_messagePreview.setDisabled(!_senderName.checked());
App::writeUserConfig();
Local::writeUserSettings();
}
}
@ -1213,7 +1274,7 @@ void SettingsInner::onSenderName() {
} else {
cSetNotifyView(dbinvShowNothing);
}
App::writeUserConfig();
Local::writeUserSettings();
App::wnd()->notifyUpdateAll();
}
}
@ -1226,13 +1287,13 @@ void SettingsInner::onMessagePreview() {
} else {
cSetNotifyView(dbinvShowNothing);
}
App::writeUserConfig();
Local::writeUserSettings();
App::wnd()->notifyUpdateAll();
}
void SettingsInner::onReplaceEmojis() {
cSetReplaceEmojis(_replaceEmojis.checked());
App::writeUserConfig();
Local::writeUserSettings();
if (_replaceEmojis.checked()) {
_viewEmojis.show();
@ -1248,14 +1309,14 @@ void SettingsInner::onViewEmojis() {
void SettingsInner::onEnterSend() {
if (_enterSend.checked()) {
cSetCtrlEnter(false);
App::writeUserConfig();
Local::writeUserSettings();
}
}
void SettingsInner::onCtrlEnterSend() {
if (_ctrlEnterSend.checked()) {
cSetCtrlEnter(true);
App::writeUserConfig();
Local::writeUserSettings();
}
}
@ -1323,13 +1384,13 @@ void SettingsInner::onTileBackground() {
if (cTileBackground() != _tileBackground.checked()) {
cSetTileBackground(_tileBackground.checked());
if (App::main()) App::main()->clearCachedBackground();
App::writeUserConfig();
Local::writeUserSettings();
}
}
void SettingsInner::onDontAskDownloadPath() {
cSetAskDownloadPath(!_dontAskDownloadPath.checked());
App::writeUserConfig();
Local::writeUserSettings();
showAll();
resizeEvent(0);

View file

@ -86,6 +86,8 @@ public slots:
void usernameChanged();
void updateConnectionType();
void passcodeChanged();
void updateBackgroundRect();
void peerUpdated(PeerData *data);
@ -97,6 +99,10 @@ public slots:
void onCheckNow();
void onRestartNow();
void onPasscode();
void onPasscodeOff();
void onAutoLock();
void onConnectionType();
void onUsername();
@ -242,11 +248,14 @@ private:
TempDirClearState _storageClearState;
// advanced
LinkButton _connectionType, _resetSessions;
FlatButton _logOut;
LinkButton _passcodeEdit, _passcodeTurnOff, _autoLock;
QString _autoLockText;
int32 _autoLockWidth;
LinkButton _connectionType;
QString _connectionTypeText;
int32 _connectionTypeWidth;
LinkButton _resetSessions;
FlatButton _logOut;
bool _resetDone;

View file

@ -20,6 +20,7 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "lang.h"
#include "sysbuttons.h"
#include "passcodewidget.h"
#include "window.h"
#include "application.h"
@ -78,6 +79,11 @@ void SysBtn::paintEvent(QPaintEvent *e) {
}
}
void SysBtn::setSysBtnStyle(const style::sysButton &st) {
_st = st;
update();
}
HitTestType SysBtn::hitTest(const QPoint &p) const {
int x(p.x()), y(p.y()), w(width()), h(height());
if (x >= 0 && y >= 0 && x < w && y < h && isVisible()) {
@ -145,3 +151,15 @@ void UpdateBtn::onClick() {
}
App::quit();
}
LockBtn::LockBtn(QWidget *parent, Window *window) : SysBtn(parent, st::sysLock), wnd(window) {
connect(this, SIGNAL(clicked()), this, SLOT(onClick()));
}
void LockBtn::onClick() {
if (App::passcoded()) {
App::wnd()->passcodeWidget()->onSubmit();
} else {
App::wnd()->setupPasscode(true);
}
}

View file

@ -32,6 +32,7 @@ public:
void setText(const QString &text);
void paintEvent(QPaintEvent *e);
void setSysBtnStyle(const style::sysButton &st);
HitTestType hitTest(const QPoint &p) const;
@ -131,3 +132,19 @@ private:
Window *wnd;
};
class LockBtn : public SysBtn {
Q_OBJECT
public:
LockBtn(QWidget *parent, Window *window);
public slots:
void onClick();
private:
Window *wnd;
};

View file

@ -56,6 +56,7 @@ TitleWidget::TitleWidget(Window *window)
, _settings(this, lang(lng_menu_settings), st::titleTextButton)
, _contacts(this, lang(lng_menu_contacts), st::titleTextButton)
, _about(this, lang(lng_menu_about), st::titleTextButton)
, _lock(this, window)
, _update(this, window, lang(lng_menu_update))
, _minimize(this, window)
, _maximize(this, window)
@ -64,10 +65,11 @@ TitleWidget::TitleWidget(Window *window)
, lastMaximized(!(window->windowState() & Qt::WindowMaximized))
{
setGeometry(0, 0, wnd->width(), st::titleHeight);
_lock.hide();
_update.hide();
_cancel.hide();
_back.hide();
if (App::app()->updatingState() == Application::UpdatingReady) {
if (App::app()->updatingState() == Application::UpdatingReady || cHasPasscode()) {
showUpdateBtn();
}
stateChanged();
@ -155,6 +157,11 @@ void TitleWidget::resizeEvent(QResizeEvent *e) {
if (!_update.isHidden()) {
p.setX(p.x() - _update.width());
_update.move(p);
if (!_lock.isHidden()) {
p.setX(p.x() - _lock.width());
_lock.move(p);
p.setX(p.x() + _lock.width());
}
p.setX(p.x() + _update.width());
}
_cancel.move(p.x() - _cancel.width(), 0);
@ -169,15 +176,20 @@ void TitleWidget::resizeEvent(QResizeEvent *e) {
p.setX(p.x() - _minimize.width());
_minimize.move(p);
}
if (_update.isHidden() && !_lock.isHidden()) {
p.setX(p.x() - _lock.width());
_lock.move(p);
}
_settings.move(st::titleMenuOffset, 0);
_back.move(st::titleMenuOffset, 0);
_back.resize((_minimize.isHidden() ? (_update.isHidden() ? width() : _update.x()) : _minimize.x()) - st::titleMenuOffset, _back.height());
if (MTP::authedId() && _back.isHidden() && _cancel.isHidden()) {
_contacts.show();
if (MTP::authedId() && _back.isHidden() && _cancel.isHidden() && !App::passcoded()) {
if (_contacts.isHidden()) _contacts.show();
_contacts.move(_settings.x() + _settings.width(), 0);
_about.move(_contacts.x() + _contacts.width(), 0);
} else {
_contacts.hide();
if (!_contacts.isHidden()) _contacts.hide();
if (!MTP::authedId()) _about.move(_settings.x() + _settings.width(), 0);
}
@ -185,31 +197,41 @@ void TitleWidget::resizeEvent(QResizeEvent *e) {
}
void TitleWidget::updateBackButton() {
if (!cWideMode() && App::main() && App::main()->selectingPeer()) {
_cancel.show();
if (App::passcoded()) {
if (!_cancel.isHidden()) _cancel.hide();
if (!_back.isHidden()) _back.hide();
if (!_settings.isHidden()) _settings.hide();
if (!_contacts.isHidden()) _contacts.hide();
if (!_about.isHidden()) _about.hide();
_lock.setSysBtnStyle(st::sysUnlock);
} else {
if (!_cancel.isHidden()) _cancel.hide();
bool authed = (MTP::authedId() > 0);
if (cWideMode()) {
_lock.setSysBtnStyle(st::sysLock);
if (!cWideMode() && App::main() && App::main()->selectingPeer()) {
_cancel.show();
if (!_back.isHidden()) _back.hide();
if (_settings.isHidden()) _settings.show();
if (authed && _contacts.isHidden()) _contacts.show();
if (_about.isHidden()) _about.show();
if (!_settings.isHidden()) _settings.hide();
if (!_contacts.isHidden()) _contacts.hide();
if (!_about.isHidden()) _about.hide();
} else {
if (App::wnd()->needBackButton()) {
if (_back.isHidden()) _back.show();
if (!_settings.isHidden()) _settings.hide();
if (!_contacts.isHidden()) _contacts.hide();
if (!_about.isHidden()) _about.hide();
} else {
if (!_cancel.isHidden()) _cancel.hide();
bool authed = (MTP::authedId() > 0);
if (cWideMode()) {
if (!_back.isHidden()) _back.hide();
if (_settings.isHidden()) _settings.show();
if (authed && _contacts.isHidden()) _contacts.show();
if (_about.isHidden()) _about.show();
} else {
if (App::wnd()->needBackButton()) {
if (_back.isHidden()) _back.show();
if (!_settings.isHidden()) _settings.hide();
if (!_contacts.isHidden()) _contacts.hide();
if (!_about.isHidden()) _about.hide();
} else {
if (!_back.isHidden()) _back.hide();
if (_settings.isHidden()) _settings.show();
if (authed && _contacts.isHidden()) _contacts.show();
if (_about.isHidden()) _about.show();
}
}
}
}
@ -281,6 +303,7 @@ void TitleWidget::stateChanged(Qt::WindowState state) {
void TitleWidget::showUpdateBtn() {
if (!cWideMode() && App::main() && App::main()->selectingPeer()) {
_cancel.show();
_lock.hide();
_update.hide();
_minimize.hide();
_restore.hide();
@ -288,6 +311,11 @@ void TitleWidget::showUpdateBtn() {
_close.hide();
return;
}
if (cHasPasscode()) {
_lock.show();
} else {
_lock.hide();
}
bool updateReady = App::app()->updatingState() == Application::UpdatingReady;
if (updateReady || cEvalScale(cConfigScale()) != cEvalScale(cRealScale())) {
_update.setText(lang(updateReady ? lng_menu_update : lng_menu_restart));
@ -338,6 +366,7 @@ HitTestType TitleWidget::hitTest(const QPoint &p) {
if (x >= st::titleIconPos.x() && y >= st::titleIconPos.y() && x < st::titleIconPos.x() + st::titleIconImg.pxWidth() && y < st::titleIconPos.y() + st::titleIconImg.pxHeight()) {
return HitTestIcon;
} else if (false
|| (_lock.hitTest(p - _lock.geometry().topLeft()) == HitTestSysButton && _lock.isVisible())
|| (_update.hitTest(p - _update.geometry().topLeft()) == HitTestSysButton && _update.isVisible())
|| (_minimize.hitTest(p - _minimize.geometry().topLeft()) == HitTestSysButton)
|| (_maximize.hitTest(p - _maximize.geometry().topLeft()) == HitTestSysButton)

View file

@ -87,6 +87,7 @@ private:
MaskedButton _back;
FlatButton _cancel, _settings, _contacts, _about;
LockBtn _lock;
UpdateBtn _update;
MinimizeBtn _minimize;
MaximizeBtn _maximize;

View file

@ -226,7 +226,7 @@ enum DataBlockId {
dbiKey = 0,
dbiUser = 1,
dbiDcOption = 2,
dbiConfig1 = 3,
dbiMaxGroupCount = 3,
dbiMutePeer = 4,
dbiSendKey = 5,
dbiAutoStart = 6,
@ -257,6 +257,7 @@ enum DataBlockId {
dbiLang = 31,
dbiLangFile = 32,
dbiTileBackground = 33,
dbiAutoLock = 34,
dbiEncryptedWithSalt = 333,
dbiEncrypted = 444,

View file

@ -24,6 +24,7 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
#include "pspecific.h"
#include "title.h"
#include "passcodewidget.h"
#include "intro/intro.h"
#include "mainwidget.h"
#include "layerwidget.h"
@ -156,7 +157,7 @@ void NotifyWindow::updateNotifyDisplay() {
p.fillRect(st::notifyBorderWidth, h - st::notifyBorderWidth, w - st::notifyBorderWidth, st::notifyBorderWidth, st::notifyBorder->b);
p.fillRect(0, st::notifyBorderWidth, st::notifyBorderWidth, h - st::notifyBorderWidth, st::notifyBorder->b);
if (cNotifyView() <= dbinvShowName) {
if (!App::passcoded() && cNotifyView() <= dbinvShowName) {
if (history->peer->photo->loaded()) {
p.drawPixmap(st::notifyPhotoPos.x(), st::notifyPhotoPos.y(), history->peer->photo->pix(st::notifyPhotoSize));
} else {
@ -172,7 +173,7 @@ void NotifyWindow::updateNotifyDisplay() {
int32 itemWidth = w - st::notifyPhotoPos.x() - st::notifyPhotoSize - st::notifyTextLeft - st::notifyClosePos.x() - st::notifyClose.width;
QRect rectForName(st::notifyPhotoPos.x() + st::notifyPhotoSize + st::notifyTextLeft, st::notifyTextTop, itemWidth, st::msgNameFont->height);
if (cNotifyView() <= dbinvShowName) {
if (!App::passcoded() && cNotifyView() <= dbinvShowName) {
if (history->peer->chat) {
p.drawPixmap(QPoint(rectForName.left() + st::dlgChatImgLeft, rectForName.top() + st::dlgChatImgTop), App::sprite(), st::dlgChatImg);
rectForName.setLeft(rectForName.left() + st::dlgChatImgSkip);
@ -188,7 +189,7 @@ void NotifyWindow::updateNotifyDisplay() {
p.setPen(st::dlgDateColor->p);
p.drawText(rectForName.left() + rectForName.width() + st::dlgDateSkip, rectForName.top() + st::dlgHistFont->ascent, dt);
if (cNotifyView() <= dbinvShowPreview) {
if (!App::passcoded() && cNotifyView() <= dbinvShowPreview) {
const HistoryItem *textCachedFor = 0;
Text itemTextCache(itemWidth);
bool active = false;
@ -200,7 +201,7 @@ void NotifyWindow::updateNotifyDisplay() {
}
p.setPen(st::dlgNameColor->p);
if (cNotifyView() <= dbinvShowName) {
if (!App::passcoded() && cNotifyView() <= dbinvShowName) {
history->nameText.drawElided(p, rectForName.left(), rectForName.top(), rectForName.width());
} else {
p.setFont(st::msgNameFont->f);
@ -267,8 +268,13 @@ void NotifyWindow::mousePressEvent(QMouseEvent *e) {
unlinkHistoryAndNotify();
} else if (history) {
App::wnd()->showFromTray();
App::wnd()->hideSettings();
App::main()->showPeer(peer, 0, false, true);
if (App::passcoded()) {
App::wnd()->passcodeWidget()->setInnerFocus();
App::wnd()->notifyClear();
} else {
App::wnd()->hideSettings();
App::main()->showPeer(peer, 0, false, true);
}
e->ignore();
}
}
@ -330,8 +336,8 @@ NotifyWindow::~NotifyWindow() {
}
Window::Window(QWidget *parent) : PsMainWindow(parent), _serviceHistoryRequest(0), title(0),
intro(0), main(0), settings(0), layerBG(0), _isActive(false), _topWidget(0),
_connecting(0), _clearManager(0), dragging(false), _inactivePress(false), _mediaView(0) {
_passcode(0), intro(0), main(0), settings(0), layerBG(0), _isActive(false), _topWidget(0),
_connecting(0), _clearManager(0), dragging(false), _inactivePress(false), _shouldLockAt(0), _mediaView(0) {
icon16 = icon256.scaledToWidth(16, Qt::SmoothTransformation);
icon32 = icon256.scaledToWidth(32, Qt::SmoothTransformation);
@ -359,6 +365,8 @@ _connecting(0), _clearManager(0), dragging(false), _inactivePress(false), _media
_isActiveTimer.setSingleShot(true);
connect(&_isActiveTimer, SIGNAL(timeout()), this, SLOT(updateIsActive()));
connect(&_autoLockTimer, SIGNAL(timeout()), this, SLOT(checkAutoLock()));
}
void Window::inactivePress(bool inactive) {
@ -435,6 +443,11 @@ QWidget *Window::filedialogParent() {
void Window::clearWidgets() {
layerHidden();
if (_passcode) {
_passcode->hide();
_passcode->deleteLater();
_passcode = 0;
}
if (settings) {
anim::stop(settings);
settings->hide();
@ -459,11 +472,72 @@ void Window::clearWidgets() {
title->updateBackButton();
}
void Window::clearPasscode() {
if (!_passcode) return;
QPixmap bg = myGrab(this, QRect(0, st::titleHeight, width(), height() - st::titleHeight));
anim::stop(_passcode);
_passcode->hide();
_passcode->deleteLater();
_passcode = 0;
if (intro) {
intro->animShow(bg, true);
} else {
main->animShow(bg, true);
}
notifyUpdateAll();
title->updateBackButton();
}
void Window::setupPasscode(bool anim) {
QPixmap bg = myGrab(this, QRect(0, st::titleHeight, width(), height() - st::titleHeight));
if (_passcode) {
anim::stop(_passcode);
_passcode->hide();
_passcode->deleteLater();
}
_passcode = new PasscodeWidget(this);
_passcode->move(0, st::titleHeight);
if (main) main->hide();
if (settings) settings->hide();
if (intro) intro->hide();
if (anim) {
_passcode->animShow(bg);
} else {
_passcode->setInnerFocus();
}
_shouldLockAt = 0;
notifyUpdateAll();
title->updateBackButton();
}
void Window::checkAutoLockIn(int msec) {
if (_autoLockTimer.isActive()) {
int remain = _autoLockTimer.remainingTime();
if (remain > 0 && remain <= msec) return;
}
_autoLockTimer.start(msec);
}
void Window::checkAutoLock() {
if (!cHasPasscode() || App::passcoded()) return;
App::app()->checkLocalTime();
uint64 ms = getms(true), idle = psIdleTime(), should = cAutoLock() * 1000ULL;
if (idle >= should || (_shouldLockAt > 0 && ms > _shouldLockAt + 3000ULL)) {
setupPasscode(true);
} else {
_shouldLockAt = ms + (should - idle);
_autoLockTimer.start(should - idle);
}
}
void Window::setupIntro(bool anim) {
cSetContactsReceived(false);
if (intro && (intro->animating() || intro->isVisible()) && !main) return;
QPixmap bg = myGrab(this, QRect(0, st::titleHeight, width(), height() - st::titleHeight));
QPixmap bg = anim ? myGrab(this, QRect(0, st::titleHeight, width(), height() - st::titleHeight)) : QPixmap();
clearWidgets();
intro = new IntroWidget(this);
@ -515,17 +589,22 @@ void Window::sendServiceHistoryRequest() {
_serviceHistoryRequest = MTP::send(MTPmessages_GetHistory(user->input, MTP_int(0), MTP_int(0), MTP_int(1)), main->rpcDone(&MainWidget::serviceHistoryDone), main->rpcFail(&MainWidget::serviceHistoryFail));
}
void Window::setupMain(bool anim) {
QPixmap bg = myGrab(this, QRect(0, st::titleHeight, width(), height() - st::titleHeight));
void Window::setupMain(bool anim, const MTPUser *self) {
QPixmap bg = anim ? myGrab(this, QRect(0, st::titleHeight, width(), height() - st::titleHeight)) : QPixmap();
clearWidgets();
main = new MainWidget(this);
main->move(0, st::titleHeight);
if (anim) {
main->animShow(bg);
} else {
MTP::send(MTPusers_GetUsers(MTP_vector<MTPInputUser>(1, MTP_inputUserSelf())), main->rpcDone(&MainWidget::startFull));
main->activate();
}
if (self) {
main->start(*self);
} else {
MTP::send(MTPusers_GetUsers(MTP_vector<MTPInputUser>(1, MTP_inputUserSelf())), main->rpcDone(&MainWidget::startFull));
}
title->resizeEvent(0);
fixOrder();
@ -540,6 +619,8 @@ void Window::updateCounter() {
}
void Window::showSettings() {
if (_passcode) return;
if (isHidden()) showFromTray();
App::wnd()->hideLayer();
@ -563,7 +644,7 @@ void Window::showSettings() {
}
void Window::hideSettings(bool fast) {
if (!settings) return;
if (!settings || _passcode) return;
if (fast) {
anim::stop(settings);
@ -595,11 +676,6 @@ void Window::hideSettings(bool fast) {
fixOrder();
}
void Window::startMain(const MTPUser &user) {
if (main) main->start(user);
title->resizeEvent(0);
}
void Window::mtpStateChanged(int32 dc, int32 state) {
if (dc == MTP::maindc()) {
updateTitleStatus();
@ -633,6 +709,10 @@ SettingsWidget *Window::settingsWidget() {
return settings;
}
PasscodeWidget *Window::passcodeWidget() {
return _passcode;
}
void Window::showPhoto(const PhotoLink *lnk, HistoryItem *item) {
return lnk->peer() ? showPhoto(lnk->photo(), lnk->peer()) : showPhoto(lnk->photo(), item);
}
@ -740,7 +820,13 @@ void Window::layerHidden() {
}
layerBG = 0;
if (_mediaView && !_mediaView->isHidden()) _mediaView->hide();
if (settings) {
setInnerFocus();
}
void Window::setInnerFocus() {
if (_passcode) {
_passcode->setInnerFocus();
} else if (settings) {
settings->setInnerFocus();
} else if (main) {
main->setInnerFocus();
@ -872,7 +958,7 @@ bool Window::minimizeToTray() {
if (cPlatform() == dbipWindows && trayIcon && !cSeenTrayTooltip()) {
trayIcon->showMessage(QString::fromStdWString(AppName), lang(lng_tray_icon_text), QSystemTrayIcon::Information, 10000);
cSetSeenTrayTooltip(true);
App::writeConfig();
Local::writeSettings();
}
updateIsActive(cOfflineBlurTimeout());
updateTrayMenu();
@ -1526,6 +1612,7 @@ QImage Window::iconWithCounter(int size, int count, style::color bg, bool smallI
}
void Window::sendPaths() {
if (App::passcoded()) return;
if (_mediaView && !_mediaView->isHidden()) _mediaView->hide();
if (settings) {
hideSettings();

View file

@ -24,6 +24,7 @@ Copyright (c) 2014 John Preston, https://desktop.telegram.org
class MediaView;
class TitleWidget;
class PasscodeWidget;
class IntroWidget;
class MainWidget;
class SettingsWidget;
@ -143,9 +144,11 @@ public:
void updateWideMode();
bool needBackButton();
void setupPasscode(bool anim);
void clearPasscode();
void checkAutoLockIn(int msec);
void setupIntro(bool anim);
void setupMain(bool anim);
void startMain(const MTPUser &user);
void setupMain(bool anim, const MTPUser *user = 0);
void getNotifySetting(const MTPInputNotifyPeer &peer, uint32 msWait = 0);
void serviceNotification(const QString &msg, bool unread = true, const MTPMessageMedia &media = MTP_messageMediaEmpty(), bool force = false);
void sendServiceHistoryRequest();
@ -164,6 +167,7 @@ public:
IntroWidget *introWidget();
MainWidget *mainWidget();
SettingsWidget *settingsWidget();
PasscodeWidget *passcodeWidget();
void showConnecting(const QString &text, const QString &reconnect = QString());
void hideConnecting();
@ -234,10 +238,13 @@ public slots:
void checkHistoryActivation();
void updateCounter();
void checkAutoLock();
void showSettings();
void hideSettings(bool fast = false);
void layerHidden();
void setInnerFocus();
void updateTitleStatus();
void quitFromTray();
@ -279,6 +286,7 @@ private:
mtpRequestId _serviceHistoryRequest;
TitleWidget *title;
PasscodeWidget *_passcode;
IntroWidget *intro;
MainWidget *main;
SettingsWidget *settings;
@ -300,6 +308,9 @@ private:
bool _inactivePress;
QTimer _inactiveTimer;
SingleTimer _autoLockTimer;
uint64 _shouldLockAt;
typedef QMap<MsgId, uint64> NotifyWhenMap;
typedef QMap<History*, NotifyWhenMap> NotifyWhenMaps;
NotifyWhenMaps notifyWhenMaps;

View file

@ -11,7 +11,7 @@
<key>CFBundlePackageType</key>
<string>APPL</string>
<key>CFBundleShortVersionString</key>
<string>0.7.18</string>
<string>0.7.19</string>
<key>CFBundleSignature</key>
<string>????</string>
<key>CFBundleURLTypes</key>

Binary file not shown.

View file

@ -170,6 +170,10 @@
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Debug\moc_autolockbox.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Debug\moc_backgroundbox.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
@ -318,6 +322,14 @@
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Debug\moc_passcodebox.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Debug\moc_passcodewidget.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Debug\moc_phoneinput.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
@ -334,6 +346,16 @@
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Debug\moc_pspecific_linux.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Debug\moc_pspecific_mac.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Debug\moc_pspecific_wnd.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
@ -398,6 +420,10 @@
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Deploy\moc_autolockbox.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Deploy\moc_backgroundbox.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
@ -546,6 +572,14 @@
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Deploy\moc_passcodebox.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Deploy\moc_passcodewidget.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Deploy\moc_phoneinput.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
@ -562,6 +596,16 @@
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Deploy\moc_pspecific_linux.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Deploy\moc_pspecific_mac.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Deploy\moc_pspecific_wnd.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
@ -635,6 +679,10 @@
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Release\moc_autolockbox.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Release\moc_backgroundbox.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
@ -783,6 +831,14 @@
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Release\moc_passcodebox.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Release\moc_passcodewidget.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Release\moc_phoneinput.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
@ -799,6 +855,16 @@
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Release\moc_pspecific_linux.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Release\moc_pspecific_mac.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="GeneratedFiles\Release\moc_pspecific_wnd.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
@ -846,6 +912,7 @@
<ClCompile Include="SourceFiles\boxes\aboutbox.cpp" />
<ClCompile Include="SourceFiles\boxes\addcontactbox.cpp" />
<ClCompile Include="SourceFiles\boxes\addparticipantbox.cpp" />
<ClCompile Include="SourceFiles\boxes\autolockbox.cpp" />
<ClCompile Include="SourceFiles\boxes\backgroundbox.cpp" />
<ClCompile Include="SourceFiles\boxes\confirmbox.cpp" />
<ClCompile Include="SourceFiles\boxes\connectionbox.cpp" />
@ -854,6 +921,7 @@
<ClCompile Include="SourceFiles\boxes\emojibox.cpp" />
<ClCompile Include="SourceFiles\boxes\languagebox.cpp" />
<ClCompile Include="SourceFiles\boxes\newgroupbox.cpp" />
<ClCompile Include="SourceFiles\boxes\passcodebox.cpp" />
<ClCompile Include="SourceFiles\boxes\photocropbox.cpp" />
<ClCompile Include="SourceFiles\boxes\photosendbox.cpp" />
<ClCompile Include="SourceFiles\boxes\usernamebox.cpp" />
@ -905,7 +973,18 @@
<ClCompile Include="SourceFiles\mtproto\mtpScheme.cpp" />
<ClCompile Include="SourceFiles\mtproto\mtpSession.cpp" />
<ClCompile Include="SourceFiles\overviewwidget.cpp" />
<ClCompile Include="SourceFiles\passcodewidget.cpp" />
<ClCompile Include="SourceFiles\profilewidget.cpp" />
<ClCompile Include="SourceFiles\pspecific_linux.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="SourceFiles\pspecific_mac.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClCompile>
<ClCompile Include="SourceFiles\pspecific_wnd.cpp" />
<ClCompile Include="SourceFiles\settings.cpp" />
<ClCompile Include="SourceFiles\settingswidget.cpp" />
@ -1190,6 +1269,34 @@
<Outputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" -DAL_LIBTYPE_STATIC -DUNICODE -D_WITH_DEBUG -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI -DQT_NO_DEBUG -DNDEBUG "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui" "-fstdafx.h" "-f../../SourceFiles/boxes/backgroundbox.h"</Command>
</CustomBuild>
<CustomBuild Include="SourceFiles\boxes\autolockbox.h">
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">Moc%27ing autolockbox.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/boxes/autolockbox.h" -DAL_LIBTYPE_STATIC -DCUSTOM_API_ID -DUNICODE -D_WITH_DEBUG -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI -DQT_NO_DEBUG -DNDEBUG "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Moc%27ing autolockbox.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/boxes/autolockbox.h" -DAL_LIBTYPE_STATIC -DUNICODE -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">Moc%27ing autolockbox.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/boxes/autolockbox.h" -DAL_LIBTYPE_STATIC -DUNICODE -D_WITH_DEBUG -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI -DQT_NO_DEBUG -DNDEBUG "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
</CustomBuild>
<CustomBuild Include="SourceFiles\boxes\passcodebox.h">
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">Moc%27ing passcodebox.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/boxes/passcodebox.h" -DAL_LIBTYPE_STATIC -DCUSTOM_API_ID -DUNICODE -D_WITH_DEBUG -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI -DQT_NO_DEBUG -DNDEBUG "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Moc%27ing passcodebox.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/boxes/passcodebox.h" -DAL_LIBTYPE_STATIC -DUNICODE -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">Moc%27ing passcodebox.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/boxes/passcodebox.h" -DAL_LIBTYPE_STATIC -DUNICODE -D_WITH_DEBUG -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI -DQT_NO_DEBUG -DNDEBUG "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
</CustomBuild>
<ClInclude Include="SourceFiles\config.h" />
<CustomBuild Include="SourceFiles\gui\animation.h">
<Message Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Moc%27ing animation.h...</Message>
@ -1745,7 +1852,60 @@
<Outputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" -DAL_LIBTYPE_STATIC -DUNICODE -D_WITH_DEBUG -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI -DQT_NO_DEBUG -DNDEBUG "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui" "-fstdafx.h" "-f../../SourceFiles/overviewwidget.h"</Command>
</CustomBuild>
<CustomBuild Include="SourceFiles\passcodewidget.h">
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">Moc%27ing passcodewidget.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/passcodewidget.h" -DAL_LIBTYPE_STATIC -DCUSTOM_API_ID -DUNICODE -D_WITH_DEBUG -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI -DQT_NO_DEBUG -DNDEBUG "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Moc%27ing passcodewidget.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/passcodewidget.h" -DAL_LIBTYPE_STATIC -DUNICODE -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">Moc%27ing passcodewidget.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/passcodewidget.h" -DAL_LIBTYPE_STATIC -DUNICODE -D_WITH_DEBUG -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI -DQT_NO_DEBUG -DNDEBUG "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
</CustomBuild>
<ClInclude Include="SourceFiles\pspecific.h" />
<CustomBuild Include="SourceFiles\pspecific_linux.h">
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">Moc%27ing pspecific_linux.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/pspecific_linux.h" -DAL_LIBTYPE_STATIC -DCUSTOM_API_ID -DUNICODE -D_WITH_DEBUG -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI -DQT_NO_DEBUG -DNDEBUG "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Moc%27ing pspecific_linux.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/pspecific_linux.h" -DAL_LIBTYPE_STATIC -DUNICODE -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">Moc%27ing pspecific_linux.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/pspecific_linux.h" -DAL_LIBTYPE_STATIC -DUNICODE -D_WITH_DEBUG -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI -DQT_NO_DEBUG -DNDEBUG "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</CustomBuild>
<CustomBuild Include="SourceFiles\pspecific_mac.h">
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">Moc%27ing pspecific_mac.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/pspecific_mac.h" -DAL_LIBTYPE_STATIC -DCUSTOM_API_ID -DUNICODE -D_WITH_DEBUG -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI -DQT_NO_DEBUG -DNDEBUG "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Moc%27ing pspecific_mac.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/pspecific_mac.h" -DAL_LIBTYPE_STATIC -DUNICODE -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
<Message Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">Moc%27ing pspecific_mac.h...</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" "-fstdafx.h" "-f../../SourceFiles/pspecific_mac.h" -DAL_LIBTYPE_STATIC -DUNICODE -D_WITH_DEBUG -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI -DQT_NO_DEBUG -DNDEBUG "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\OpenSSL-Win32\include" "-I.\..\..\Libraries\libogg-1.3.2\include" "-I.\..\..\Libraries\opus\include" "-I.\..\..\Libraries\opusfile\include" "-I.\..\..\Libraries\openal-soft\include" "-I.\SourceFiles" "-I.\GeneratedFiles" "-I." "-I$(QTDIR)\include" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I.\..\..\Libraries\QtStatic\qtbase\include\QtCore\5.4.0\QtCore" "-I.\..\..\Libraries\QtStatic\qtbase\include\QtGui\5.4.0\QtGui"</Command>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</CustomBuild>
<ClInclude Include="SourceFiles\pspecific_mac_p.h">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</ClInclude>
<ClInclude Include="SourceFiles\settings.h" />
<ClInclude Include="SourceFiles\style.h" />
<CustomBuild Include="SourceFiles\sysbuttons.h">
@ -1808,6 +1968,11 @@
<None Include="SourceFiles\langs\lang_ko.strings" />
<None Include="SourceFiles\langs\lang_nl.strings" />
<None Include="SourceFiles\langs\lang_pt_BR.strings" />
<None Include="SourceFiles\pspecific_mac_p.mm">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Deploy|Win32'">true</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>
</None>
</ItemGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
<ImportGroup Label="ExtensionTargets">
@ -1817,4 +1982,4 @@
<UserProperties UicDir=".\GeneratedFiles" MocDir=".\GeneratedFiles\$(ConfigurationName)" MocOptions="" RccDir=".\GeneratedFiles" lupdateOnBuild="1" lupdateOptions="" lreleaseOptions="" Qt5Version_x0020_Win32="$(DefaultQtVersion)" />
</VisualStudio>
</ProjectExtensions>
</Project>
</Project>

View file

@ -786,6 +786,66 @@
<ClCompile Include="GeneratedFiles\Release\moc_backgroundbox.cpp">
<Filter>Generated Files\Release</Filter>
</ClCompile>
<ClCompile Include="SourceFiles\pspecific_linux.cpp">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Deploy\moc_pspecific_linux.cpp">
<Filter>Generated Files\Deploy</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Debug\moc_pspecific_linux.cpp">
<Filter>Generated Files\Debug</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Release\moc_pspecific_linux.cpp">
<Filter>Generated Files\Release</Filter>
</ClCompile>
<ClCompile Include="SourceFiles\pspecific_mac.cpp">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Deploy\moc_pspecific_mac.cpp">
<Filter>Generated Files\Deploy</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Debug\moc_pspecific_mac.cpp">
<Filter>Generated Files\Debug</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Release\moc_pspecific_mac.cpp">
<Filter>Generated Files\Release</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Deploy\moc_passcodewidget.cpp">
<Filter>Generated Files\Deploy</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Debug\moc_passcodewidget.cpp">
<Filter>Generated Files\Debug</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Release\moc_passcodewidget.cpp">
<Filter>Generated Files\Release</Filter>
</ClCompile>
<ClCompile Include="SourceFiles\passcodewidget.cpp">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Deploy\moc_autolockbox.cpp">
<Filter>Generated Files\Deploy</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Debug\moc_autolockbox.cpp">
<Filter>Generated Files\Debug</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Release\moc_autolockbox.cpp">
<Filter>Generated Files\Release</Filter>
</ClCompile>
<ClCompile Include="SourceFiles\boxes\autolockbox.cpp">
<Filter>boxes</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Deploy\moc_passcodebox.cpp">
<Filter>Generated Files\Deploy</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Debug\moc_passcodebox.cpp">
<Filter>Generated Files\Debug</Filter>
</ClCompile>
<ClCompile Include="GeneratedFiles\Release\moc_passcodebox.cpp">
<Filter>Generated Files\Release</Filter>
</ClCompile>
<ClCompile Include="SourceFiles\boxes\passcodebox.cpp">
<Filter>boxes</Filter>
</ClCompile>
</ItemGroup>
<ItemGroup>
<ClInclude Include="SourceFiles\stdafx.h">
@ -866,6 +926,9 @@
<ClInclude Include="SourceFiles\lang.h">
<Filter>Source Files</Filter>
</ClInclude>
<ClInclude Include="SourceFiles\pspecific_mac_p.h">
<Filter>Source Files</Filter>
</ClInclude>
</ItemGroup>
<ItemGroup>
<CustomBuild Include="SourceFiles\mtproto\mtpConnection.h">
@ -1046,6 +1109,21 @@
<CustomBuild Include="SourceFiles\boxes\backgroundbox.h">
<Filter>boxes</Filter>
</CustomBuild>
<CustomBuild Include="SourceFiles\pspecific_linux.h">
<Filter>Source Files</Filter>
</CustomBuild>
<CustomBuild Include="SourceFiles\pspecific_mac.h">
<Filter>Source Files</Filter>
</CustomBuild>
<CustomBuild Include="SourceFiles\passcodewidget.h">
<Filter>Source Files</Filter>
</CustomBuild>
<CustomBuild Include="SourceFiles\boxes\autolockbox.h">
<Filter>boxes</Filter>
</CustomBuild>
<CustomBuild Include="SourceFiles\boxes\passcodebox.h">
<Filter>boxes</Filter>
</CustomBuild>
</ItemGroup>
<ItemGroup>
<Image Include="SourceFiles\art\icon256.ico" />
@ -1072,5 +1150,8 @@
<None Include="SourceFiles\langs\lang_ko.strings">
<Filter>langs</Filter>
</None>
<None Include="SourceFiles\pspecific_mac_p.mm">
<Filter>Source Files</Filter>
</None>
</ItemGroup>
</Project>
</Project>

View file

@ -1627,7 +1627,7 @@
buildSettings = {
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
COPY_PHASE_STRIP = NO;
CURRENT_PROJECT_VERSION = 0.7.18;
CURRENT_PROJECT_VERSION = 0.7.19;
DEBUG_INFORMATION_FORMAT = dwarf;
GCC_GENERATE_DEBUGGING_SYMBOLS = YES;
GCC_OPTIMIZATION_LEVEL = 0;
@ -1645,7 +1645,7 @@
buildSettings = {
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
COPY_PHASE_STRIP = YES;
CURRENT_PROJECT_VERSION = 0.7.18;
CURRENT_PROJECT_VERSION = 0.7.19;
GCC_GENERATE_DEBUGGING_SYMBOLS = NO;
GCC_OPTIMIZATION_LEVEL = fast;
GCC_PREFIX_HEADER = ./SourceFiles/stdafx.h;
@ -1671,10 +1671,10 @@
CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
CODE_SIGN_IDENTITY = "";
COPY_PHASE_STRIP = NO;
CURRENT_PROJECT_VERSION = 0.7.18;
CURRENT_PROJECT_VERSION = 0.7.19;
DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
DYLIB_COMPATIBILITY_VERSION = 0.7;
DYLIB_CURRENT_VERSION = 0.7.18;
DYLIB_CURRENT_VERSION = 0.7.19;
ENABLE_STRICT_OBJC_MSGSEND = YES;
FRAMEWORK_SEARCH_PATHS = "";
GCC_GENERATE_DEBUGGING_SYMBOLS = YES;
@ -1812,10 +1812,10 @@
CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
CODE_SIGN_IDENTITY = "";
COPY_PHASE_STRIP = NO;
CURRENT_PROJECT_VERSION = 0.7.18;
CURRENT_PROJECT_VERSION = 0.7.19;
DEBUG_INFORMATION_FORMAT = dwarf;
DYLIB_COMPATIBILITY_VERSION = 0.7;
DYLIB_CURRENT_VERSION = 0.7.18;
DYLIB_CURRENT_VERSION = 0.7.19;
ENABLE_STRICT_OBJC_MSGSEND = YES;
FRAMEWORK_SEARCH_PATHS = "";
GCC_GENERATE_DEBUGGING_SYMBOLS = YES;

View file

@ -1,2 +1,2 @@
echo 7018 0.7.18 1
echo 7019 0.7.19 1
# AppVersion AppVersionStr DevChannel