Updated database structure, updated sqlite (don't use this source code, it may be changed)
This commit is contained in:
parent
43674c486f
commit
c6b1a3430b
File diff suppressed because it is too large
Load Diff
@ -107,9 +107,9 @@ extern "C" {
|
|||||||
** [sqlite3_libversion_number()], [sqlite3_sourceid()],
|
** [sqlite3_libversion_number()], [sqlite3_sourceid()],
|
||||||
** [sqlite_version()] and [sqlite_source_id()].
|
** [sqlite_version()] and [sqlite_source_id()].
|
||||||
*/
|
*/
|
||||||
#define SQLITE_VERSION "3.8.4.1"
|
#define SQLITE_VERSION "3.8.6"
|
||||||
#define SQLITE_VERSION_NUMBER 3008004
|
#define SQLITE_VERSION_NUMBER 3008006
|
||||||
#define SQLITE_SOURCE_ID "2014-03-11 15:27:36 018d317b1257ce68a92908b05c9c7cf1494050d0"
|
#define SQLITE_SOURCE_ID "2014-08-15 11:46:33 9491ba7d738528f168657adb43a198238abde19e"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
** CAPI3REF: Run-Time Library Version Numbers
|
** CAPI3REF: Run-Time Library Version Numbers
|
||||||
@ -269,7 +269,7 @@ typedef sqlite_uint64 sqlite3_uint64;
|
|||||||
**
|
**
|
||||||
** ^The sqlite3_close() and sqlite3_close_v2() routines are destructors
|
** ^The sqlite3_close() and sqlite3_close_v2() routines are destructors
|
||||||
** for the [sqlite3] object.
|
** for the [sqlite3] object.
|
||||||
** ^Calls to sqlite3_close() and sqlite3_close_v2() return SQLITE_OK if
|
** ^Calls to sqlite3_close() and sqlite3_close_v2() return [SQLITE_OK] if
|
||||||
** the [sqlite3] object is successfully destroyed and all associated
|
** the [sqlite3] object is successfully destroyed and all associated
|
||||||
** resources are deallocated.
|
** resources are deallocated.
|
||||||
**
|
**
|
||||||
@ -277,7 +277,7 @@ typedef sqlite_uint64 sqlite3_uint64;
|
|||||||
** statements or unfinished sqlite3_backup objects then sqlite3_close()
|
** statements or unfinished sqlite3_backup objects then sqlite3_close()
|
||||||
** will leave the database connection open and return [SQLITE_BUSY].
|
** will leave the database connection open and return [SQLITE_BUSY].
|
||||||
** ^If sqlite3_close_v2() is called with unfinalized prepared statements
|
** ^If sqlite3_close_v2() is called with unfinalized prepared statements
|
||||||
** and unfinished sqlite3_backups, then the database connection becomes
|
** and/or unfinished sqlite3_backups, then the database connection becomes
|
||||||
** an unusable "zombie" which will automatically be deallocated when the
|
** an unusable "zombie" which will automatically be deallocated when the
|
||||||
** last prepared statement is finalized or the last sqlite3_backup is
|
** last prepared statement is finalized or the last sqlite3_backup is
|
||||||
** finished. The sqlite3_close_v2() interface is intended for use with
|
** finished. The sqlite3_close_v2() interface is intended for use with
|
||||||
@ -290,7 +290,7 @@ typedef sqlite_uint64 sqlite3_uint64;
|
|||||||
** with the [sqlite3] object prior to attempting to close the object. ^If
|
** with the [sqlite3] object prior to attempting to close the object. ^If
|
||||||
** sqlite3_close_v2() is called on a [database connection] that still has
|
** sqlite3_close_v2() is called on a [database connection] that still has
|
||||||
** outstanding [prepared statements], [BLOB handles], and/or
|
** outstanding [prepared statements], [BLOB handles], and/or
|
||||||
** [sqlite3_backup] objects then it returns SQLITE_OK but the deallocation
|
** [sqlite3_backup] objects then it returns [SQLITE_OK] and the deallocation
|
||||||
** of resources is deferred until all [prepared statements], [BLOB handles],
|
** of resources is deferred until all [prepared statements], [BLOB handles],
|
||||||
** and [sqlite3_backup] objects are also destroyed.
|
** and [sqlite3_backup] objects are also destroyed.
|
||||||
**
|
**
|
||||||
@ -386,16 +386,14 @@ SQLITE_API int sqlite3_exec(
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
** CAPI3REF: Result Codes
|
** CAPI3REF: Result Codes
|
||||||
** KEYWORDS: SQLITE_OK {error code} {error codes}
|
** KEYWORDS: {result code definitions}
|
||||||
** KEYWORDS: {result code} {result codes}
|
|
||||||
**
|
**
|
||||||
** Many SQLite functions return an integer result code from the set shown
|
** Many SQLite functions return an integer result code from the set shown
|
||||||
** here in order to indicate success or failure.
|
** here in order to indicate success or failure.
|
||||||
**
|
**
|
||||||
** New error codes may be added in future versions of SQLite.
|
** New error codes may be added in future versions of SQLite.
|
||||||
**
|
**
|
||||||
** See also: [SQLITE_IOERR_READ | extended result codes],
|
** See also: [extended result code definitions]
|
||||||
** [sqlite3_vtab_on_conflict()] [SQLITE_ROLLBACK | result codes].
|
|
||||||
*/
|
*/
|
||||||
#define SQLITE_OK 0 /* Successful result */
|
#define SQLITE_OK 0 /* Successful result */
|
||||||
/* beginning-of-error-codes */
|
/* beginning-of-error-codes */
|
||||||
@ -433,26 +431,19 @@ SQLITE_API int sqlite3_exec(
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
** CAPI3REF: Extended Result Codes
|
** CAPI3REF: Extended Result Codes
|
||||||
** KEYWORDS: {extended error code} {extended error codes}
|
** KEYWORDS: {extended result code definitions}
|
||||||
** KEYWORDS: {extended result code} {extended result codes}
|
|
||||||
**
|
**
|
||||||
** In its default configuration, SQLite API routines return one of 26 integer
|
** In its default configuration, SQLite API routines return one of 30 integer
|
||||||
** [SQLITE_OK | result codes]. However, experience has shown that many of
|
** [result codes]. However, experience has shown that many of
|
||||||
** these result codes are too coarse-grained. They do not provide as
|
** these result codes are too coarse-grained. They do not provide as
|
||||||
** much information about problems as programmers might like. In an effort to
|
** much information about problems as programmers might like. In an effort to
|
||||||
** address this, newer versions of SQLite (version 3.3.8 and later) include
|
** address this, newer versions of SQLite (version 3.3.8 and later) include
|
||||||
** support for additional result codes that provide more detailed information
|
** support for additional result codes that provide more detailed information
|
||||||
** about errors. The extended result codes are enabled or disabled
|
** about errors. These [extended result codes] are enabled or disabled
|
||||||
** on a per database connection basis using the
|
** on a per database connection basis using the
|
||||||
** [sqlite3_extended_result_codes()] API.
|
** [sqlite3_extended_result_codes()] API. Or, the extended code for
|
||||||
**
|
** the most recent error can be obtained using
|
||||||
** Some of the available extended result codes are listed here.
|
** [sqlite3_extended_errcode()].
|
||||||
** One may expect the number of extended result codes will increase
|
|
||||||
** over time. Software that uses extended result codes should expect
|
|
||||||
** to see new result codes in future releases of SQLite.
|
|
||||||
**
|
|
||||||
** The SQLITE_OK result code will never be extended. It will always
|
|
||||||
** be exactly zero.
|
|
||||||
*/
|
*/
|
||||||
#define SQLITE_IOERR_READ (SQLITE_IOERR | (1<<8))
|
#define SQLITE_IOERR_READ (SQLITE_IOERR | (1<<8))
|
||||||
#define SQLITE_IOERR_SHORT_READ (SQLITE_IOERR | (2<<8))
|
#define SQLITE_IOERR_SHORT_READ (SQLITE_IOERR | (2<<8))
|
||||||
@ -560,7 +551,10 @@ SQLITE_API int sqlite3_exec(
|
|||||||
** file that were written at the application level might have changed
|
** file that were written at the application level might have changed
|
||||||
** and that adjacent bytes, even bytes within the same sector are
|
** and that adjacent bytes, even bytes within the same sector are
|
||||||
** guaranteed to be unchanged. The SQLITE_IOCAP_UNDELETABLE_WHEN_OPEN
|
** guaranteed to be unchanged. The SQLITE_IOCAP_UNDELETABLE_WHEN_OPEN
|
||||||
** flag indicate that a file cannot be deleted when open.
|
** flag indicate that a file cannot be deleted when open. The
|
||||||
|
** SQLITE_IOCAP_IMMUTABLE flag indicates that the file is on
|
||||||
|
** read-only media and cannot be changed even by processes with
|
||||||
|
** elevated privileges.
|
||||||
*/
|
*/
|
||||||
#define SQLITE_IOCAP_ATOMIC 0x00000001
|
#define SQLITE_IOCAP_ATOMIC 0x00000001
|
||||||
#define SQLITE_IOCAP_ATOMIC512 0x00000002
|
#define SQLITE_IOCAP_ATOMIC512 0x00000002
|
||||||
@ -575,6 +569,7 @@ SQLITE_API int sqlite3_exec(
|
|||||||
#define SQLITE_IOCAP_SEQUENTIAL 0x00000400
|
#define SQLITE_IOCAP_SEQUENTIAL 0x00000400
|
||||||
#define SQLITE_IOCAP_UNDELETABLE_WHEN_OPEN 0x00000800
|
#define SQLITE_IOCAP_UNDELETABLE_WHEN_OPEN 0x00000800
|
||||||
#define SQLITE_IOCAP_POWERSAFE_OVERWRITE 0x00001000
|
#define SQLITE_IOCAP_POWERSAFE_OVERWRITE 0x00001000
|
||||||
|
#define SQLITE_IOCAP_IMMUTABLE 0x00002000
|
||||||
|
|
||||||
/*
|
/*
|
||||||
** CAPI3REF: File Locking Levels
|
** CAPI3REF: File Locking Levels
|
||||||
@ -681,7 +676,7 @@ struct sqlite3_file {
|
|||||||
** locking strategy (for example to use dot-file locks), to inquire
|
** locking strategy (for example to use dot-file locks), to inquire
|
||||||
** about the status of a lock, or to break stale locks. The SQLite
|
** about the status of a lock, or to break stale locks. The SQLite
|
||||||
** core reserves all opcodes less than 100 for its own use.
|
** core reserves all opcodes less than 100 for its own use.
|
||||||
** A [SQLITE_FCNTL_LOCKSTATE | list of opcodes] less than 100 is available.
|
** A [file control opcodes | list of opcodes] less than 100 is available.
|
||||||
** Applications that define a custom xFileControl method should use opcodes
|
** Applications that define a custom xFileControl method should use opcodes
|
||||||
** greater than 100 to avoid conflicts. VFS implementations should
|
** greater than 100 to avoid conflicts. VFS implementations should
|
||||||
** return [SQLITE_NOTFOUND] for file control opcodes that they do not
|
** return [SQLITE_NOTFOUND] for file control opcodes that they do not
|
||||||
@ -754,6 +749,7 @@ struct sqlite3_io_methods {
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
** CAPI3REF: Standard File Control Opcodes
|
** CAPI3REF: Standard File Control Opcodes
|
||||||
|
** KEYWORDS: {file control opcodes} {file control opcode}
|
||||||
**
|
**
|
||||||
** These integer constants are opcodes for the xFileControl method
|
** These integer constants are opcodes for the xFileControl method
|
||||||
** of the [sqlite3_io_methods] object and for the [sqlite3_file_control()]
|
** of the [sqlite3_io_methods] object and for the [sqlite3_file_control()]
|
||||||
@ -943,6 +939,12 @@ struct sqlite3_io_methods {
|
|||||||
** on whether or not the file has been renamed, moved, or deleted since it
|
** on whether or not the file has been renamed, moved, or deleted since it
|
||||||
** was first opened.
|
** was first opened.
|
||||||
**
|
**
|
||||||
|
** <li>[[SQLITE_FCNTL_WIN32_SET_HANDLE]]
|
||||||
|
** The [SQLITE_FCNTL_WIN32_SET_HANDLE] opcode is used for debugging. This
|
||||||
|
** opcode causes the xFileControl method to swap the file handle with the one
|
||||||
|
** pointed to by the pArg argument. This capability is used during testing
|
||||||
|
** and only needs to be supported when SQLITE_TEST is defined.
|
||||||
|
**
|
||||||
** </ul>
|
** </ul>
|
||||||
*/
|
*/
|
||||||
#define SQLITE_FCNTL_LOCKSTATE 1
|
#define SQLITE_FCNTL_LOCKSTATE 1
|
||||||
@ -966,6 +968,7 @@ struct sqlite3_io_methods {
|
|||||||
#define SQLITE_FCNTL_HAS_MOVED 20
|
#define SQLITE_FCNTL_HAS_MOVED 20
|
||||||
#define SQLITE_FCNTL_SYNC 21
|
#define SQLITE_FCNTL_SYNC 21
|
||||||
#define SQLITE_FCNTL_COMMIT_PHASETWO 22
|
#define SQLITE_FCNTL_COMMIT_PHASETWO 22
|
||||||
|
#define SQLITE_FCNTL_WIN32_SET_HANDLE 23
|
||||||
|
|
||||||
/*
|
/*
|
||||||
** CAPI3REF: Mutex Handle
|
** CAPI3REF: Mutex Handle
|
||||||
@ -2026,27 +2029,33 @@ SQLITE_API int sqlite3_complete16(const void *sql);
|
|||||||
/*
|
/*
|
||||||
** CAPI3REF: Register A Callback To Handle SQLITE_BUSY Errors
|
** CAPI3REF: Register A Callback To Handle SQLITE_BUSY Errors
|
||||||
**
|
**
|
||||||
** ^This routine sets a callback function that might be invoked whenever
|
** ^The sqlite3_busy_handler(D,X,P) routine sets a callback function X
|
||||||
** an attempt is made to open a database table that another thread
|
** that might be invoked with argument P whenever
|
||||||
** or process has locked.
|
** an attempt is made to access a database table associated with
|
||||||
|
** [database connection] D when another thread
|
||||||
|
** or process has the table locked.
|
||||||
|
** The sqlite3_busy_handler() interface is used to implement
|
||||||
|
** [sqlite3_busy_timeout()] and [PRAGMA busy_timeout].
|
||||||
**
|
**
|
||||||
** ^If the busy callback is NULL, then [SQLITE_BUSY] or [SQLITE_IOERR_BLOCKED]
|
** ^If the busy callback is NULL, then [SQLITE_BUSY]
|
||||||
** is returned immediately upon encountering the lock. ^If the busy callback
|
** is returned immediately upon encountering the lock. ^If the busy callback
|
||||||
** is not NULL, then the callback might be invoked with two arguments.
|
** is not NULL, then the callback might be invoked with two arguments.
|
||||||
**
|
**
|
||||||
** ^The first argument to the busy handler is a copy of the void* pointer which
|
** ^The first argument to the busy handler is a copy of the void* pointer which
|
||||||
** is the third argument to sqlite3_busy_handler(). ^The second argument to
|
** is the third argument to sqlite3_busy_handler(). ^The second argument to
|
||||||
** the busy handler callback is the number of times that the busy handler has
|
** the busy handler callback is the number of times that the busy handler has
|
||||||
** been invoked for this locking event. ^If the
|
** been invoked for the same locking event. ^If the
|
||||||
** busy callback returns 0, then no additional attempts are made to
|
** busy callback returns 0, then no additional attempts are made to
|
||||||
** access the database and [SQLITE_BUSY] or [SQLITE_IOERR_BLOCKED] is returned.
|
** access the database and [SQLITE_BUSY] is returned
|
||||||
|
** to the application.
|
||||||
** ^If the callback returns non-zero, then another attempt
|
** ^If the callback returns non-zero, then another attempt
|
||||||
** is made to open the database for reading and the cycle repeats.
|
** is made to access the database and the cycle repeats.
|
||||||
**
|
**
|
||||||
** The presence of a busy handler does not guarantee that it will be invoked
|
** The presence of a busy handler does not guarantee that it will be invoked
|
||||||
** when there is lock contention. ^If SQLite determines that invoking the busy
|
** when there is lock contention. ^If SQLite determines that invoking the busy
|
||||||
** handler could result in a deadlock, it will go ahead and return [SQLITE_BUSY]
|
** handler could result in a deadlock, it will go ahead and return [SQLITE_BUSY]
|
||||||
** or [SQLITE_IOERR_BLOCKED] instead of invoking the busy handler.
|
** to the application instead of invoking the
|
||||||
|
** busy handler.
|
||||||
** Consider a scenario where one process is holding a read lock that
|
** Consider a scenario where one process is holding a read lock that
|
||||||
** it is trying to promote to a reserved lock and
|
** it is trying to promote to a reserved lock and
|
||||||
** a second process is holding a reserved lock that it is trying
|
** a second process is holding a reserved lock that it is trying
|
||||||
@ -2060,28 +2069,15 @@ SQLITE_API int sqlite3_complete16(const void *sql);
|
|||||||
**
|
**
|
||||||
** ^The default busy callback is NULL.
|
** ^The default busy callback is NULL.
|
||||||
**
|
**
|
||||||
** ^The [SQLITE_BUSY] error is converted to [SQLITE_IOERR_BLOCKED]
|
|
||||||
** when SQLite is in the middle of a large transaction where all the
|
|
||||||
** changes will not fit into the in-memory cache. SQLite will
|
|
||||||
** already hold a RESERVED lock on the database file, but it needs
|
|
||||||
** to promote this lock to EXCLUSIVE so that it can spill cache
|
|
||||||
** pages into the database file without harm to concurrent
|
|
||||||
** readers. ^If it is unable to promote the lock, then the in-memory
|
|
||||||
** cache will be left in an inconsistent state and so the error
|
|
||||||
** code is promoted from the relatively benign [SQLITE_BUSY] to
|
|
||||||
** the more severe [SQLITE_IOERR_BLOCKED]. ^This error code promotion
|
|
||||||
** forces an automatic rollback of the changes. See the
|
|
||||||
** <a href="/cvstrac/wiki?p=CorruptionFollowingBusyError">
|
|
||||||
** CorruptionFollowingBusyError</a> wiki page for a discussion of why
|
|
||||||
** this is important.
|
|
||||||
**
|
|
||||||
** ^(There can only be a single busy handler defined for each
|
** ^(There can only be a single busy handler defined for each
|
||||||
** [database connection]. Setting a new busy handler clears any
|
** [database connection]. Setting a new busy handler clears any
|
||||||
** previously set handler.)^ ^Note that calling [sqlite3_busy_timeout()]
|
** previously set handler.)^ ^Note that calling [sqlite3_busy_timeout()]
|
||||||
** will also set or clear the busy handler.
|
** or evaluating [PRAGMA busy_timeout=N] will change the
|
||||||
|
** busy handler and thus clear any previously set busy handler.
|
||||||
**
|
**
|
||||||
** The busy callback should not take any actions which modify the
|
** The busy callback should not take any actions which modify the
|
||||||
** database connection that invoked the busy handler. Any such actions
|
** database connection that invoked the busy handler. In other words,
|
||||||
|
** the busy handler is not reentrant. Any such actions
|
||||||
** result in undefined behavior.
|
** result in undefined behavior.
|
||||||
**
|
**
|
||||||
** A busy handler must not close the database connection
|
** A busy handler must not close the database connection
|
||||||
@ -2097,7 +2093,7 @@ SQLITE_API int sqlite3_busy_handler(sqlite3*, int(*)(void*,int), void*);
|
|||||||
** will sleep multiple times until at least "ms" milliseconds of sleeping
|
** will sleep multiple times until at least "ms" milliseconds of sleeping
|
||||||
** have accumulated. ^After at least "ms" milliseconds of sleeping,
|
** have accumulated. ^After at least "ms" milliseconds of sleeping,
|
||||||
** the handler returns 0 which causes [sqlite3_step()] to return
|
** the handler returns 0 which causes [sqlite3_step()] to return
|
||||||
** [SQLITE_BUSY] or [SQLITE_IOERR_BLOCKED].
|
** [SQLITE_BUSY].
|
||||||
**
|
**
|
||||||
** ^Calling this routine with an argument less than or equal to zero
|
** ^Calling this routine with an argument less than or equal to zero
|
||||||
** turns off all busy handlers.
|
** turns off all busy handlers.
|
||||||
@ -2106,6 +2102,8 @@ SQLITE_API int sqlite3_busy_handler(sqlite3*, int(*)(void*,int), void*);
|
|||||||
** [database connection] any any given moment. If another busy handler
|
** [database connection] any any given moment. If another busy handler
|
||||||
** was defined (using [sqlite3_busy_handler()]) prior to calling
|
** was defined (using [sqlite3_busy_handler()]) prior to calling
|
||||||
** this routine, that other busy handler is cleared.)^
|
** this routine, that other busy handler is cleared.)^
|
||||||
|
**
|
||||||
|
** See also: [PRAGMA busy_timeout]
|
||||||
*/
|
*/
|
||||||
SQLITE_API int sqlite3_busy_timeout(sqlite3*, int ms);
|
SQLITE_API int sqlite3_busy_timeout(sqlite3*, int ms);
|
||||||
|
|
||||||
@ -2507,8 +2505,8 @@ SQLITE_API int sqlite3_set_authorizer(
|
|||||||
** [sqlite3_set_authorizer | authorizer documentation] for additional
|
** [sqlite3_set_authorizer | authorizer documentation] for additional
|
||||||
** information.
|
** information.
|
||||||
**
|
**
|
||||||
** Note that SQLITE_IGNORE is also used as a [SQLITE_ROLLBACK | return code]
|
** Note that SQLITE_IGNORE is also used as a [conflict resolution mode]
|
||||||
** from the [sqlite3_vtab_on_conflict()] interface.
|
** returned from the [sqlite3_vtab_on_conflict()] interface.
|
||||||
*/
|
*/
|
||||||
#define SQLITE_DENY 1 /* Abort the SQL statement with an error */
|
#define SQLITE_DENY 1 /* Abort the SQL statement with an error */
|
||||||
#define SQLITE_IGNORE 2 /* Don't allow access, but don't generate an error */
|
#define SQLITE_IGNORE 2 /* Don't allow access, but don't generate an error */
|
||||||
@ -2779,6 +2777,30 @@ SQLITE_API void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*);
|
|||||||
** ^If sqlite3_open_v2() is used and the "cache" parameter is present in
|
** ^If sqlite3_open_v2() is used and the "cache" parameter is present in
|
||||||
** a URI filename, its value overrides any behavior requested by setting
|
** a URI filename, its value overrides any behavior requested by setting
|
||||||
** SQLITE_OPEN_PRIVATECACHE or SQLITE_OPEN_SHAREDCACHE flag.
|
** SQLITE_OPEN_PRIVATECACHE or SQLITE_OPEN_SHAREDCACHE flag.
|
||||||
|
**
|
||||||
|
** <li> <b>psow</b>: ^The psow parameter may be "true" (or "on" or "yes" or
|
||||||
|
** "1") or "false" (or "off" or "no" or "0") to indicate that the
|
||||||
|
** [powersafe overwrite] property does or does not apply to the
|
||||||
|
** storage media on which the database file resides. ^The psow query
|
||||||
|
** parameter only works for the built-in unix and Windows VFSes.
|
||||||
|
**
|
||||||
|
** <li> <b>nolock</b>: ^The nolock parameter is a boolean query parameter
|
||||||
|
** which if set disables file locking in rollback journal modes. This
|
||||||
|
** is useful for accessing a database on a filesystem that does not
|
||||||
|
** support locking. Caution: Database corruption might result if two
|
||||||
|
** or more processes write to the same database and any one of those
|
||||||
|
** processes uses nolock=1.
|
||||||
|
**
|
||||||
|
** <li> <b>immutable</b>: ^The immutable parameter is a boolean query
|
||||||
|
** parameter that indicates that the database file is stored on
|
||||||
|
** read-only media. ^When immutable is set, SQLite assumes that the
|
||||||
|
** database file cannot be changed, even by a process with higher
|
||||||
|
** privilege, and so the database is opened read-only and all locking
|
||||||
|
** and change detection is disabled. Caution: Setting the immutable
|
||||||
|
** property on a database file that does in fact change can result
|
||||||
|
** in incorrect query results and/or [SQLITE_CORRUPT] errors.
|
||||||
|
** See also: [SQLITE_IOCAP_IMMUTABLE].
|
||||||
|
**
|
||||||
** </ul>
|
** </ul>
|
||||||
**
|
**
|
||||||
** ^Specifying an unknown parameter in the query component of a URI is not an
|
** ^Specifying an unknown parameter in the query component of a URI is not an
|
||||||
@ -2808,8 +2830,9 @@ SQLITE_API void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*);
|
|||||||
** Open file "data.db" in the current directory for read-only access.
|
** Open file "data.db" in the current directory for read-only access.
|
||||||
** Regardless of whether or not shared-cache mode is enabled by
|
** Regardless of whether or not shared-cache mode is enabled by
|
||||||
** default, use a private cache.
|
** default, use a private cache.
|
||||||
** <tr><td> file:/home/fred/data.db?vfs=unix-nolock <td>
|
** <tr><td> file:/home/fred/data.db?vfs=unix-dotfile <td>
|
||||||
** Open file "/home/fred/data.db". Use the special VFS "unix-nolock".
|
** Open file "/home/fred/data.db". Use the special VFS "unix-dotfile"
|
||||||
|
** that uses dot-files in place of posix advisory locking.
|
||||||
** <tr><td> file:data.db?mode=readonly <td>
|
** <tr><td> file:data.db?mode=readonly <td>
|
||||||
** An error. "readonly" is not a valid option for the "mode" parameter.
|
** An error. "readonly" is not a valid option for the "mode" parameter.
|
||||||
** </table>
|
** </table>
|
||||||
@ -4670,6 +4693,13 @@ SQLITE_API int sqlite3_sleep(int);
|
|||||||
** is a NULL pointer, then SQLite performs a search for an appropriate
|
** is a NULL pointer, then SQLite performs a search for an appropriate
|
||||||
** temporary file directory.
|
** temporary file directory.
|
||||||
**
|
**
|
||||||
|
** Applications are strongly discouraged from using this global variable.
|
||||||
|
** It is required to set a temporary folder on Windows Runtime (WinRT).
|
||||||
|
** But for all other platforms, it is highly recommended that applications
|
||||||
|
** neither read nor write this variable. This global variable is a relic
|
||||||
|
** that exists for backwards compatibility of legacy applications and should
|
||||||
|
** be avoided in new projects.
|
||||||
|
**
|
||||||
** It is not safe to read or modify this variable in more than one
|
** It is not safe to read or modify this variable in more than one
|
||||||
** thread at a time. It is not safe to read or modify this variable
|
** thread at a time. It is not safe to read or modify this variable
|
||||||
** if a [database connection] is being used at the same time in a separate
|
** if a [database connection] is being used at the same time in a separate
|
||||||
@ -4688,6 +4718,11 @@ SQLITE_API int sqlite3_sleep(int);
|
|||||||
** Hence, if this variable is modified directly, either it should be
|
** Hence, if this variable is modified directly, either it should be
|
||||||
** made NULL or made to point to memory obtained from [sqlite3_malloc]
|
** made NULL or made to point to memory obtained from [sqlite3_malloc]
|
||||||
** or else the use of the [temp_store_directory pragma] should be avoided.
|
** or else the use of the [temp_store_directory pragma] should be avoided.
|
||||||
|
** Except when requested by the [temp_store_directory pragma], SQLite
|
||||||
|
** does not free the memory that sqlite3_temp_directory points to. If
|
||||||
|
** the application wants that memory to be freed, it must do
|
||||||
|
** so itself, taking care to only do so after all [database connection]
|
||||||
|
** objects have been destroyed.
|
||||||
**
|
**
|
||||||
** <b>Note to Windows Runtime users:</b> The temporary directory must be set
|
** <b>Note to Windows Runtime users:</b> The temporary directory must be set
|
||||||
** prior to calling [sqlite3_open] or [sqlite3_open_v2]. Otherwise, various
|
** prior to calling [sqlite3_open] or [sqlite3_open_v2]. Otherwise, various
|
||||||
@ -5822,10 +5857,12 @@ SQLITE_API int sqlite3_vfs_unregister(sqlite3_vfs*);
|
|||||||
** <li> SQLITE_MUTEX_RECURSIVE
|
** <li> SQLITE_MUTEX_RECURSIVE
|
||||||
** <li> SQLITE_MUTEX_STATIC_MASTER
|
** <li> SQLITE_MUTEX_STATIC_MASTER
|
||||||
** <li> SQLITE_MUTEX_STATIC_MEM
|
** <li> SQLITE_MUTEX_STATIC_MEM
|
||||||
** <li> SQLITE_MUTEX_STATIC_MEM2
|
** <li> SQLITE_MUTEX_STATIC_OPEN
|
||||||
** <li> SQLITE_MUTEX_STATIC_PRNG
|
** <li> SQLITE_MUTEX_STATIC_PRNG
|
||||||
** <li> SQLITE_MUTEX_STATIC_LRU
|
** <li> SQLITE_MUTEX_STATIC_LRU
|
||||||
** <li> SQLITE_MUTEX_STATIC_LRU2
|
** <li> SQLITE_MUTEX_STATIC_PMEM
|
||||||
|
** <li> SQLITE_MUTEX_STATIC_APP1
|
||||||
|
** <li> SQLITE_MUTEX_STATIC_APP2
|
||||||
** </ul>)^
|
** </ul>)^
|
||||||
**
|
**
|
||||||
** ^The first two constants (SQLITE_MUTEX_FAST and SQLITE_MUTEX_RECURSIVE)
|
** ^The first two constants (SQLITE_MUTEX_FAST and SQLITE_MUTEX_RECURSIVE)
|
||||||
@ -6029,6 +6066,9 @@ SQLITE_API int sqlite3_mutex_notheld(sqlite3_mutex*);
|
|||||||
#define SQLITE_MUTEX_STATIC_LRU 6 /* lru page list */
|
#define SQLITE_MUTEX_STATIC_LRU 6 /* lru page list */
|
||||||
#define SQLITE_MUTEX_STATIC_LRU2 7 /* NOT USED */
|
#define SQLITE_MUTEX_STATIC_LRU2 7 /* NOT USED */
|
||||||
#define SQLITE_MUTEX_STATIC_PMEM 7 /* sqlite3PageMalloc() */
|
#define SQLITE_MUTEX_STATIC_PMEM 7 /* sqlite3PageMalloc() */
|
||||||
|
#define SQLITE_MUTEX_STATIC_APP1 8 /* For use by application */
|
||||||
|
#define SQLITE_MUTEX_STATIC_APP2 9 /* For use by application */
|
||||||
|
#define SQLITE_MUTEX_STATIC_APP3 10 /* For use by application */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
** CAPI3REF: Retrieve the mutex for a database connection
|
** CAPI3REF: Retrieve the mutex for a database connection
|
||||||
@ -6123,7 +6163,9 @@ SQLITE_API int sqlite3_test_control(int op, ...);
|
|||||||
#define SQLITE_TESTCTRL_EXPLAIN_STMT 19
|
#define SQLITE_TESTCTRL_EXPLAIN_STMT 19
|
||||||
#define SQLITE_TESTCTRL_NEVER_CORRUPT 20
|
#define SQLITE_TESTCTRL_NEVER_CORRUPT 20
|
||||||
#define SQLITE_TESTCTRL_VDBE_COVERAGE 21
|
#define SQLITE_TESTCTRL_VDBE_COVERAGE 21
|
||||||
#define SQLITE_TESTCTRL_LAST 21
|
#define SQLITE_TESTCTRL_BYTEORDER 22
|
||||||
|
#define SQLITE_TESTCTRL_ISINIT 23
|
||||||
|
#define SQLITE_TESTCTRL_LAST 23
|
||||||
|
|
||||||
/*
|
/*
|
||||||
** CAPI3REF: SQLite Runtime Status
|
** CAPI3REF: SQLite Runtime Status
|
||||||
@ -7107,6 +7149,9 @@ SQLITE_API void *sqlite3_wal_hook(
|
|||||||
** ^The [wal_autocheckpoint pragma] can be used to invoke this interface
|
** ^The [wal_autocheckpoint pragma] can be used to invoke this interface
|
||||||
** from SQL.
|
** from SQL.
|
||||||
**
|
**
|
||||||
|
** ^Checkpoints initiated by this mechanism are
|
||||||
|
** [sqlite3_wal_checkpoint_v2|PASSIVE].
|
||||||
|
**
|
||||||
** ^Every new [database connection] defaults to having the auto-checkpoint
|
** ^Every new [database connection] defaults to having the auto-checkpoint
|
||||||
** enabled with a threshold of 1000 or [SQLITE_DEFAULT_WAL_AUTOCHECKPOINT]
|
** enabled with a threshold of 1000 or [SQLITE_DEFAULT_WAL_AUTOCHECKPOINT]
|
||||||
** pages. The use of this interface
|
** pages. The use of this interface
|
||||||
@ -7123,6 +7168,10 @@ SQLITE_API int sqlite3_wal_autocheckpoint(sqlite3 *db, int N);
|
|||||||
** empty string, then a checkpoint is run on all databases of
|
** empty string, then a checkpoint is run on all databases of
|
||||||
** connection D. ^If the database connection D is not in
|
** connection D. ^If the database connection D is not in
|
||||||
** [WAL | write-ahead log mode] then this interface is a harmless no-op.
|
** [WAL | write-ahead log mode] then this interface is a harmless no-op.
|
||||||
|
** ^The [sqlite3_wal_checkpoint(D,X)] interface initiates a
|
||||||
|
** [sqlite3_wal_checkpoint_v2|PASSIVE] checkpoint.
|
||||||
|
** Use the [sqlite3_wal_checkpoint_v2()] interface to get a FULL
|
||||||
|
** or RESET checkpoint.
|
||||||
**
|
**
|
||||||
** ^The [wal_checkpoint pragma] can be used to invoke this interface
|
** ^The [wal_checkpoint pragma] can be used to invoke this interface
|
||||||
** from SQL. ^The [sqlite3_wal_autocheckpoint()] interface and the
|
** from SQL. ^The [sqlite3_wal_autocheckpoint()] interface and the
|
||||||
@ -7145,10 +7194,12 @@ SQLITE_API int sqlite3_wal_checkpoint(sqlite3 *db, const char *zDb);
|
|||||||
** Checkpoint as many frames as possible without waiting for any database
|
** Checkpoint as many frames as possible without waiting for any database
|
||||||
** readers or writers to finish. Sync the db file if all frames in the log
|
** readers or writers to finish. Sync the db file if all frames in the log
|
||||||
** are checkpointed. This mode is the same as calling
|
** are checkpointed. This mode is the same as calling
|
||||||
** sqlite3_wal_checkpoint(). The busy-handler callback is never invoked.
|
** sqlite3_wal_checkpoint(). The [sqlite3_busy_handler|busy-handler callback]
|
||||||
|
** is never invoked.
|
||||||
**
|
**
|
||||||
** <dt>SQLITE_CHECKPOINT_FULL<dd>
|
** <dt>SQLITE_CHECKPOINT_FULL<dd>
|
||||||
** This mode blocks (calls the busy-handler callback) until there is no
|
** This mode blocks (it invokes the
|
||||||
|
** [sqlite3_busy_handler|busy-handler callback]) until there is no
|
||||||
** database writer and all readers are reading from the most recent database
|
** database writer and all readers are reading from the most recent database
|
||||||
** snapshot. It then checkpoints all frames in the log file and syncs the
|
** snapshot. It then checkpoints all frames in the log file and syncs the
|
||||||
** database file. This call blocks database writers while it is running,
|
** database file. This call blocks database writers while it is running,
|
||||||
@ -7156,7 +7207,8 @@ SQLITE_API int sqlite3_wal_checkpoint(sqlite3 *db, const char *zDb);
|
|||||||
**
|
**
|
||||||
** <dt>SQLITE_CHECKPOINT_RESTART<dd>
|
** <dt>SQLITE_CHECKPOINT_RESTART<dd>
|
||||||
** This mode works the same way as SQLITE_CHECKPOINT_FULL, except after
|
** This mode works the same way as SQLITE_CHECKPOINT_FULL, except after
|
||||||
** checkpointing the log file it blocks (calls the busy-handler callback)
|
** checkpointing the log file it blocks (calls the
|
||||||
|
** [sqlite3_busy_handler|busy-handler callback])
|
||||||
** until all readers are reading from the database file only. This ensures
|
** until all readers are reading from the database file only. This ensures
|
||||||
** that the next client to write to the database file restarts the log file
|
** that the next client to write to the database file restarts the log file
|
||||||
** from the beginning. This call blocks database writers while it is running,
|
** from the beginning. This call blocks database writers while it is running,
|
||||||
@ -7294,6 +7346,7 @@ SQLITE_API int sqlite3_vtab_on_conflict(sqlite3 *);
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
** CAPI3REF: Conflict resolution modes
|
** CAPI3REF: Conflict resolution modes
|
||||||
|
** KEYWORDS: {conflict resolution mode}
|
||||||
**
|
**
|
||||||
** These constants are returned by [sqlite3_vtab_on_conflict()] to
|
** These constants are returned by [sqlite3_vtab_on_conflict()] to
|
||||||
** inform a [virtual table] implementation what the [ON CONFLICT] mode
|
** inform a [virtual table] implementation what the [ON CONFLICT] mode
|
||||||
@ -7346,6 +7399,16 @@ extern "C" {
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
typedef struct sqlite3_rtree_geometry sqlite3_rtree_geometry;
|
typedef struct sqlite3_rtree_geometry sqlite3_rtree_geometry;
|
||||||
|
typedef struct sqlite3_rtree_query_info sqlite3_rtree_query_info;
|
||||||
|
|
||||||
|
/* The double-precision datatype used by RTree depends on the
|
||||||
|
** SQLITE_RTREE_INT_ONLY compile-time option.
|
||||||
|
*/
|
||||||
|
#ifdef SQLITE_RTREE_INT_ONLY
|
||||||
|
typedef sqlite3_int64 sqlite3_rtree_dbl;
|
||||||
|
#else
|
||||||
|
typedef double sqlite3_rtree_dbl;
|
||||||
|
#endif
|
||||||
|
|
||||||
/*
|
/*
|
||||||
** Register a geometry callback named zGeom that can be used as part of an
|
** Register a geometry callback named zGeom that can be used as part of an
|
||||||
@ -7356,11 +7419,7 @@ typedef struct sqlite3_rtree_geometry sqlite3_rtree_geometry;
|
|||||||
SQLITE_API int sqlite3_rtree_geometry_callback(
|
SQLITE_API int sqlite3_rtree_geometry_callback(
|
||||||
sqlite3 *db,
|
sqlite3 *db,
|
||||||
const char *zGeom,
|
const char *zGeom,
|
||||||
#ifdef SQLITE_RTREE_INT_ONLY
|
int (*xGeom)(sqlite3_rtree_geometry*, int, sqlite3_rtree_dbl*,int*),
|
||||||
int (*xGeom)(sqlite3_rtree_geometry*, int n, sqlite3_int64 *a, int *pRes),
|
|
||||||
#else
|
|
||||||
int (*xGeom)(sqlite3_rtree_geometry*, int n, double *a, int *pRes),
|
|
||||||
#endif
|
|
||||||
void *pContext
|
void *pContext
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -7372,11 +7431,60 @@ SQLITE_API int sqlite3_rtree_geometry_callback(
|
|||||||
struct sqlite3_rtree_geometry {
|
struct sqlite3_rtree_geometry {
|
||||||
void *pContext; /* Copy of pContext passed to s_r_g_c() */
|
void *pContext; /* Copy of pContext passed to s_r_g_c() */
|
||||||
int nParam; /* Size of array aParam[] */
|
int nParam; /* Size of array aParam[] */
|
||||||
double *aParam; /* Parameters passed to SQL geom function */
|
sqlite3_rtree_dbl *aParam; /* Parameters passed to SQL geom function */
|
||||||
void *pUser; /* Callback implementation user data */
|
void *pUser; /* Callback implementation user data */
|
||||||
void (*xDelUser)(void *); /* Called by SQLite to clean up pUser */
|
void (*xDelUser)(void *); /* Called by SQLite to clean up pUser */
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
** Register a 2nd-generation geometry callback named zScore that can be
|
||||||
|
** used as part of an R-Tree geometry query as follows:
|
||||||
|
**
|
||||||
|
** SELECT ... FROM <rtree> WHERE <rtree col> MATCH $zQueryFunc(... params ...)
|
||||||
|
*/
|
||||||
|
SQLITE_API int sqlite3_rtree_query_callback(
|
||||||
|
sqlite3 *db,
|
||||||
|
const char *zQueryFunc,
|
||||||
|
int (*xQueryFunc)(sqlite3_rtree_query_info*),
|
||||||
|
void *pContext,
|
||||||
|
void (*xDestructor)(void*)
|
||||||
|
);
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
** A pointer to a structure of the following type is passed as the
|
||||||
|
** argument to scored geometry callback registered using
|
||||||
|
** sqlite3_rtree_query_callback().
|
||||||
|
**
|
||||||
|
** Note that the first 5 fields of this structure are identical to
|
||||||
|
** sqlite3_rtree_geometry. This structure is a subclass of
|
||||||
|
** sqlite3_rtree_geometry.
|
||||||
|
*/
|
||||||
|
struct sqlite3_rtree_query_info {
|
||||||
|
void *pContext; /* pContext from when function registered */
|
||||||
|
int nParam; /* Number of function parameters */
|
||||||
|
sqlite3_rtree_dbl *aParam; /* value of function parameters */
|
||||||
|
void *pUser; /* callback can use this, if desired */
|
||||||
|
void (*xDelUser)(void*); /* function to free pUser */
|
||||||
|
sqlite3_rtree_dbl *aCoord; /* Coordinates of node or entry to check */
|
||||||
|
unsigned int *anQueue; /* Number of pending entries in the queue */
|
||||||
|
int nCoord; /* Number of coordinates */
|
||||||
|
int iLevel; /* Level of current node or entry */
|
||||||
|
int mxLevel; /* The largest iLevel value in the tree */
|
||||||
|
sqlite3_int64 iRowid; /* Rowid for current entry */
|
||||||
|
sqlite3_rtree_dbl rParentScore; /* Score of parent node */
|
||||||
|
int eParentWithin; /* Visibility of parent node */
|
||||||
|
int eWithin; /* OUT: Visiblity */
|
||||||
|
sqlite3_rtree_dbl rScore; /* OUT: Write the score here */
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
** Allowed values for sqlite3_rtree_query.eWithin and .eParentWithin.
|
||||||
|
*/
|
||||||
|
#define NOT_WITHIN 0 /* Object completely outside of query region */
|
||||||
|
#define PARTLY_WITHIN 1 /* Object partially overlaps query region */
|
||||||
|
#define FULLY_WITHIN 2 /* Object fully contained within query region */
|
||||||
|
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
} /* end of the 'extern "C"' block */
|
} /* end of the 'extern "C"' block */
|
||||||
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -236,7 +236,7 @@ public class ContactsController {
|
|||||||
ContentResolver cr = ApplicationLoader.applicationContext.getContentResolver();
|
ContentResolver cr = ApplicationLoader.applicationContext.getContentResolver();
|
||||||
|
|
||||||
HashMap<String, Contact> shortContacts = new HashMap<String, Contact>();
|
HashMap<String, Contact> shortContacts = new HashMap<String, Contact>();
|
||||||
String ids = "";
|
StringBuilder ids = new StringBuilder();
|
||||||
Cursor pCur = cr.query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, projectionPhones, null, null, null);
|
Cursor pCur = cr.query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, projectionPhones, null, null, null);
|
||||||
if (pCur != null) {
|
if (pCur != null) {
|
||||||
if (pCur.getCount() > 0) {
|
if (pCur.getCount() > 0) {
|
||||||
@ -262,9 +262,9 @@ public class ContactsController {
|
|||||||
|
|
||||||
Integer id = pCur.getInt(0);
|
Integer id = pCur.getInt(0);
|
||||||
if (ids.length() != 0) {
|
if (ids.length() != 0) {
|
||||||
ids += ",";
|
ids.append(",");
|
||||||
}
|
}
|
||||||
ids += id;
|
ids.append(id);
|
||||||
|
|
||||||
int type = pCur.getInt(2);
|
int type = pCur.getInt(2);
|
||||||
Contact contact = contactsMap.get(id);
|
Contact contact = contactsMap.get(id);
|
||||||
@ -299,7 +299,7 @@ public class ContactsController {
|
|||||||
pCur.close();
|
pCur.close();
|
||||||
}
|
}
|
||||||
|
|
||||||
pCur = cr.query(ContactsContract.Data.CONTENT_URI, projectionNames, ContactsContract.CommonDataKinds.StructuredName.CONTACT_ID + " IN (" + ids + ") AND " + ContactsContract.Data.MIMETYPE + " = '" + ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE + "'", null, null);
|
pCur = cr.query(ContactsContract.Data.CONTENT_URI, projectionNames, ContactsContract.CommonDataKinds.StructuredName.CONTACT_ID + " IN (" + ids.toString() + ") AND " + ContactsContract.Data.MIMETYPE + " = '" + ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE + "'", null, null);
|
||||||
if (pCur != null && pCur.getCount() > 0) {
|
if (pCur != null && pCur.getCount() > 0) {
|
||||||
while (pCur.moveToNext()) {
|
while (pCur.moveToNext()) {
|
||||||
int id = pCur.getInt(0);
|
int id = pCur.getInt(0);
|
||||||
@ -844,14 +844,14 @@ public class ContactsController {
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
String ids = "";
|
StringBuilder ids = new StringBuilder();
|
||||||
for (TLRPC.TL_contact aContactsArr : contactsArr) {
|
for (TLRPC.TL_contact aContactsArr : contactsArr) {
|
||||||
if (ids.length() != 0) {
|
if (ids.length() != 0) {
|
||||||
ids += ",";
|
ids.append(",");
|
||||||
}
|
}
|
||||||
ids += aContactsArr.user_id;
|
ids.append(aContactsArr.user_id);
|
||||||
}
|
}
|
||||||
UserConfig.contactsHash = Utilities.MD5(ids);
|
UserConfig.contactsHash = Utilities.MD5(ids.toString());
|
||||||
UserConfig.saveConfig(false);
|
UserConfig.saveConfig(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1084,7 +1084,7 @@ public class ContactsController {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
String ids = "";
|
StringBuilder ids = new StringBuilder();
|
||||||
final HashMap<String, ArrayList<TLRPC.TL_contact>> sectionsDict = new HashMap<String, ArrayList<TLRPC.TL_contact>>();
|
final HashMap<String, ArrayList<TLRPC.TL_contact>> sectionsDict = new HashMap<String, ArrayList<TLRPC.TL_contact>>();
|
||||||
final ArrayList<String> sortedSectionsArray = new ArrayList<String>();
|
final ArrayList<String> sortedSectionsArray = new ArrayList<String>();
|
||||||
|
|
||||||
@ -1114,11 +1114,11 @@ public class ContactsController {
|
|||||||
}
|
}
|
||||||
arr.add(value);
|
arr.add(value);
|
||||||
if (ids.length() != 0) {
|
if (ids.length() != 0) {
|
||||||
ids += ",";
|
ids.append(",");
|
||||||
}
|
}
|
||||||
ids += value.user_id;
|
ids.append(value.user_id);
|
||||||
}
|
}
|
||||||
UserConfig.contactsHash = Utilities.MD5(ids);
|
UserConfig.contactsHash = Utilities.MD5(ids.toString());
|
||||||
UserConfig.saveConfig(false);
|
UserConfig.saveConfig(false);
|
||||||
|
|
||||||
Collections.sort(sortedSectionsArray, new Comparator<String>() {
|
Collections.sort(sortedSectionsArray, new Comparator<String>() {
|
||||||
@ -1189,8 +1189,8 @@ public class ContactsController {
|
|||||||
}
|
}
|
||||||
FileLog.e("tmessages", "process update - contacts add = " + newC.size() + " delete = " + contactsTD.size());
|
FileLog.e("tmessages", "process update - contacts add = " + newC.size() + " delete = " + contactsTD.size());
|
||||||
|
|
||||||
String toAdd = "";
|
StringBuilder toAdd = new StringBuilder();
|
||||||
String toDelete = "";
|
StringBuilder toDelete = new StringBuilder();
|
||||||
boolean reloadContacts = false;
|
boolean reloadContacts = false;
|
||||||
|
|
||||||
for (TLRPC.TL_contact newContact : newC) {
|
for (TLRPC.TL_contact newContact : newC) {
|
||||||
@ -1216,9 +1216,9 @@ public class ContactsController {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (toAdd.length() != 0) {
|
if (toAdd.length() != 0) {
|
||||||
toAdd += ",";
|
toAdd.append(",");
|
||||||
}
|
}
|
||||||
toAdd += user.phone;
|
toAdd.append(user.phone);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (final Integer uid : contactsTD) {
|
for (final Integer uid : contactsTD) {
|
||||||
@ -1252,14 +1252,14 @@ public class ContactsController {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (toDelete.length() != 0) {
|
if (toDelete.length() != 0) {
|
||||||
toDelete += ",";
|
toDelete.append(",");
|
||||||
}
|
}
|
||||||
toDelete += user.phone;
|
toDelete.append(user.phone);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (toAdd.length() != 0 || toDelete.length() != 0) {
|
if (toAdd.length() != 0 || toDelete.length() != 0) {
|
||||||
MessagesStorage.getInstance().applyPhoneBookUpdates(toAdd, toDelete);
|
MessagesStorage.getInstance().applyPhoneBookUpdates(toAdd.toString(), toDelete.toString());
|
||||||
}
|
}
|
||||||
|
|
||||||
if (reloadContacts) {
|
if (reloadContacts) {
|
||||||
|
@ -69,7 +69,6 @@ public class MessagesController implements NotificationCenter.NotificationCenter
|
|||||||
|
|
||||||
private boolean gettingNewDeleteTask = false;
|
private boolean gettingNewDeleteTask = false;
|
||||||
private int currentDeletingTaskTime = 0;
|
private int currentDeletingTaskTime = 0;
|
||||||
private Long currentDeletingTask = null;
|
|
||||||
private ArrayList<Integer> currentDeletingTaskMids = null;
|
private ArrayList<Integer> currentDeletingTaskMids = null;
|
||||||
|
|
||||||
public int totalDialogsCount = 0;
|
public int totalDialogsCount = 0;
|
||||||
@ -322,7 +321,6 @@ public class MessagesController implements NotificationCenter.NotificationCenter
|
|||||||
currentDeletingTaskTime = 0;
|
currentDeletingTaskTime = 0;
|
||||||
currentDeletingTaskMids = null;
|
currentDeletingTaskMids = null;
|
||||||
gettingNewDeleteTask = false;
|
gettingNewDeleteTask = false;
|
||||||
currentDeletingTask = null;
|
|
||||||
loadingDialogs = false;
|
loadingDialogs = false;
|
||||||
dialogsEndReached = false;
|
dialogsEndReached = false;
|
||||||
gettingDifference = false;
|
gettingDifference = false;
|
||||||
@ -508,14 +506,14 @@ public class MessagesController implements NotificationCenter.NotificationCenter
|
|||||||
Utilities.stageQueue.postRunnable(new Runnable() {
|
Utilities.stageQueue.postRunnable(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
if (currentDeletingTask == null && !gettingNewDeleteTask || currentDeletingTaskTime != 0 && minDate < currentDeletingTaskTime) {
|
if (currentDeletingTaskMids == null && !gettingNewDeleteTask || currentDeletingTaskTime != 0 && minDate < currentDeletingTaskTime) {
|
||||||
getNewDeleteTask(null);
|
getNewDeleteTask(null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
public void getNewDeleteTask(final Long oldTask) {
|
public void getNewDeleteTask(final ArrayList<Integer> oldTask) {
|
||||||
Utilities.stageQueue.postRunnable(new Runnable() {
|
Utilities.stageQueue.postRunnable(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
@ -528,7 +526,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter
|
|||||||
private void checkDeletingTask() {
|
private void checkDeletingTask() {
|
||||||
int currentServerTime = ConnectionsManager.getInstance().getCurrentTime();
|
int currentServerTime = ConnectionsManager.getInstance().getCurrentTime();
|
||||||
|
|
||||||
if (currentDeletingTask != null && currentDeletingTaskTime != 0 && currentDeletingTaskTime <= currentServerTime) {
|
if (currentDeletingTaskMids != null && currentDeletingTaskTime != 0 && currentDeletingTaskTime <= currentServerTime) {
|
||||||
currentDeletingTaskTime = 0;
|
currentDeletingTaskTime = 0;
|
||||||
AndroidUtilities.RunOnUIThread(new Runnable() {
|
AndroidUtilities.RunOnUIThread(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
@ -538,9 +536,9 @@ public class MessagesController implements NotificationCenter.NotificationCenter
|
|||||||
Utilities.stageQueue.postRunnable(new Runnable() {
|
Utilities.stageQueue.postRunnable(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
getNewDeleteTask(currentDeletingTask);
|
getNewDeleteTask(currentDeletingTaskMids);
|
||||||
currentDeletingTaskTime = 0;
|
currentDeletingTaskTime = 0;
|
||||||
currentDeletingTask = null;
|
currentDeletingTaskMids = null;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@ -548,20 +546,18 @@ public class MessagesController implements NotificationCenter.NotificationCenter
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void processLoadedDeleteTask(final Long taskId, final int taskTime, final ArrayList<Integer> messages) {
|
public void processLoadedDeleteTask(final int taskTime, final ArrayList<Integer> messages) {
|
||||||
Utilities.stageQueue.postRunnable(new Runnable() {
|
Utilities.stageQueue.postRunnable(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
gettingNewDeleteTask = false;
|
gettingNewDeleteTask = false;
|
||||||
if (taskId != null) {
|
if (messages != null) {
|
||||||
currentDeletingTaskTime = taskTime;
|
currentDeletingTaskTime = taskTime;
|
||||||
currentDeletingTask = taskId;
|
|
||||||
currentDeletingTaskMids = messages;
|
currentDeletingTaskMids = messages;
|
||||||
|
|
||||||
checkDeletingTask();
|
checkDeletingTask();
|
||||||
} else {
|
} else {
|
||||||
currentDeletingTaskTime = 0;
|
currentDeletingTaskTime = 0;
|
||||||
currentDeletingTask = null;
|
|
||||||
currentDeletingTaskMids = null;
|
currentDeletingTaskMids = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1275,10 +1271,10 @@ public class MessagesController implements NotificationCenter.NotificationCenter
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void loadMessages(final long dialog_id, final int count, final int max_id, boolean fromCache, int midDate, final int classGuid, boolean from_unread, boolean forward) {
|
public void loadMessages(final long dialog_id, final int count, final int max_id, boolean fromCache, int midDate, final int classGuid, boolean from_unread, boolean forward, final Semaphore semaphore) {
|
||||||
int lower_part = (int)dialog_id;
|
int lower_part = (int)dialog_id;
|
||||||
if (fromCache || lower_part == 0) {
|
if (fromCache || lower_part == 0) {
|
||||||
MessagesStorage.getInstance().getMessages(dialog_id, count, max_id, midDate, classGuid, from_unread, forward);
|
MessagesStorage.getInstance().getMessages(dialog_id, count, max_id, midDate, classGuid, from_unread, forward, semaphore);
|
||||||
} else {
|
} else {
|
||||||
TLRPC.TL_messages_getHistory req = new TLRPC.TL_messages_getHistory();
|
TLRPC.TL_messages_getHistory req = new TLRPC.TL_messages_getHistory();
|
||||||
if (lower_part < 0) {
|
if (lower_part < 0) {
|
||||||
@ -1303,7 +1299,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter
|
|||||||
public void run(TLObject response, TLRPC.TL_error error) {
|
public void run(TLObject response, TLRPC.TL_error error) {
|
||||||
if (error == null) {
|
if (error == null) {
|
||||||
final TLRPC.messages_Messages res = (TLRPC.messages_Messages) response;
|
final TLRPC.messages_Messages res = (TLRPC.messages_Messages) response;
|
||||||
processLoadedMessages(res, dialog_id, count, max_id, false, classGuid, 0, 0, 0, 0, false);
|
processLoadedMessages(res, dialog_id, count, max_id, false, classGuid, 0, 0, 0, 0, false, semaphore);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@ -1311,7 +1307,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void processLoadedMessages(final TLRPC.messages_Messages messagesRes, final long dialog_id, final int count, final int max_id, final boolean isCache, final int classGuid, final int first_unread, final int last_unread, final int unread_count, final int last_date, final boolean isForward) {
|
public void processLoadedMessages(final TLRPC.messages_Messages messagesRes, final long dialog_id, final int count, final int max_id, final boolean isCache, final int classGuid, final int first_unread, final int last_unread, final int unread_count, final int last_date, final boolean isForward, final Semaphore semaphore) {
|
||||||
Utilities.stageQueue.postRunnable(new Runnable() {
|
Utilities.stageQueue.postRunnable(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
@ -1320,10 +1316,13 @@ public class MessagesController implements NotificationCenter.NotificationCenter
|
|||||||
MessagesStorage.getInstance().putMessages(messagesRes, dialog_id);
|
MessagesStorage.getInstance().putMessages(messagesRes, dialog_id);
|
||||||
}
|
}
|
||||||
if (lower_id != 0 && isCache && messagesRes.messages.size() == 0 && !isForward) {
|
if (lower_id != 0 && isCache && messagesRes.messages.size() == 0 && !isForward) {
|
||||||
|
if (semaphore != null) {
|
||||||
|
semaphore.release();
|
||||||
|
}
|
||||||
AndroidUtilities.RunOnUIThread(new Runnable() {
|
AndroidUtilities.RunOnUIThread(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
loadMessages(dialog_id, count, max_id, false, 0, classGuid, false, false);
|
loadMessages(dialog_id, count, max_id, false, 0, classGuid, false, false, null);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
return;
|
return;
|
||||||
@ -1337,6 +1336,12 @@ public class MessagesController implements NotificationCenter.NotificationCenter
|
|||||||
message.dialog_id = dialog_id;
|
message.dialog_id = dialog_id;
|
||||||
objects.add(new MessageObject(message, usersLocal, 2));
|
objects.add(new MessageObject(message, usersLocal, 2));
|
||||||
}
|
}
|
||||||
|
if (semaphore != null) {
|
||||||
|
putUsers(messagesRes.users, isCache);
|
||||||
|
putChats(messagesRes.chats, isCache);
|
||||||
|
NotificationCenter.getInstance().postNotificationName(NotificationCenter.messagesDidLoaded, dialog_id, count, objects, isCache, first_unread, last_unread, unread_count, last_date, isForward);
|
||||||
|
semaphore.release();
|
||||||
|
} else {
|
||||||
AndroidUtilities.RunOnUIThread(new Runnable() {
|
AndroidUtilities.RunOnUIThread(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
@ -1346,6 +1351,7 @@ public class MessagesController implements NotificationCenter.NotificationCenter
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -11,6 +11,7 @@ package org.telegram.android;
|
|||||||
import android.content.Context;
|
import android.content.Context;
|
||||||
import android.content.SharedPreferences;
|
import android.content.SharedPreferences;
|
||||||
import android.text.Html;
|
import android.text.Html;
|
||||||
|
import android.text.TextUtils;
|
||||||
import android.util.SparseArray;
|
import android.util.SparseArray;
|
||||||
|
|
||||||
import org.telegram.PhoneFormat.PhoneFormat;
|
import org.telegram.PhoneFormat.PhoneFormat;
|
||||||
@ -90,7 +91,7 @@ public class MessagesStorage {
|
|||||||
database.executeFast("PRAGMA temp_store = 1").stepThis().dispose();
|
database.executeFast("PRAGMA temp_store = 1").stepThis().dispose();
|
||||||
if (createTable) {
|
if (createTable) {
|
||||||
database.executeFast("CREATE TABLE users(uid INTEGER PRIMARY KEY, name TEXT, status INTEGER, data BLOB)").stepThis().dispose();
|
database.executeFast("CREATE TABLE users(uid INTEGER PRIMARY KEY, name TEXT, status INTEGER, data BLOB)").stepThis().dispose();
|
||||||
database.executeFast("CREATE TABLE messages(mid INTEGER PRIMARY KEY, uid INTEGER, read_state INTEGER, send_state INTEGER, date INTEGER, data BLOB, out INTEGER, ttl INTEGER)").stepThis().dispose();
|
database.executeFast("CREATE TABLE messages(mid INTEGER PRIMARY KEY, uid INTEGER, read_state INTEGER, send_state INTEGER, date INTEGER, data BLOB, out INTEGER, ttl INTEGER, media INTEGER)").stepThis().dispose();
|
||||||
database.executeFast("CREATE TABLE chats(uid INTEGER PRIMARY KEY, name TEXT, data BLOB)").stepThis().dispose();
|
database.executeFast("CREATE TABLE chats(uid INTEGER PRIMARY KEY, name TEXT, data BLOB)").stepThis().dispose();
|
||||||
database.executeFast("CREATE TABLE enc_chats(uid INTEGER PRIMARY KEY, user INTEGER, name TEXT, data BLOB, g BLOB, authkey BLOB, ttl INTEGER)").stepThis().dispose();
|
database.executeFast("CREATE TABLE enc_chats(uid INTEGER PRIMARY KEY, user INTEGER, name TEXT, data BLOB, g BLOB, authkey BLOB, ttl INTEGER)").stepThis().dispose();
|
||||||
database.executeFast("CREATE TABLE dialogs(did INTEGER PRIMARY KEY, date INTEGER, unread_count INTEGER, last_mid INTEGER)").stepThis().dispose();
|
database.executeFast("CREATE TABLE dialogs(did INTEGER PRIMARY KEY, date INTEGER, unread_count INTEGER, last_mid INTEGER)").stepThis().dispose();
|
||||||
@ -101,7 +102,7 @@ public class MessagesStorage {
|
|||||||
database.executeFast("CREATE TABLE media_counts(uid INTEGER PRIMARY KEY, count INTEGER)").stepThis().dispose();
|
database.executeFast("CREATE TABLE media_counts(uid INTEGER PRIMARY KEY, count INTEGER)").stepThis().dispose();
|
||||||
database.executeFast("CREATE TABLE wallpapers(uid INTEGER PRIMARY KEY, data BLOB)").stepThis().dispose();
|
database.executeFast("CREATE TABLE wallpapers(uid INTEGER PRIMARY KEY, data BLOB)").stepThis().dispose();
|
||||||
database.executeFast("CREATE TABLE randoms(random_id INTEGER PRIMARY KEY, mid INTEGER)").stepThis().dispose();
|
database.executeFast("CREATE TABLE randoms(random_id INTEGER PRIMARY KEY, mid INTEGER)").stepThis().dispose();
|
||||||
database.executeFast("CREATE TABLE enc_tasks(date INTEGER, data BLOB)").stepThis().dispose();
|
database.executeFast("CREATE TABLE enc_tasks_v2(mid INTEGER PRIMARY KEY, date INTEGER)").stepThis().dispose();
|
||||||
database.executeFast("CREATE TABLE params(id INTEGER PRIMARY KEY, seq INTEGER, pts INTEGER, date INTEGER, qts INTEGER, lsv INTEGER, sg INTEGER, pbytes BLOB)").stepThis().dispose();
|
database.executeFast("CREATE TABLE params(id INTEGER PRIMARY KEY, seq INTEGER, pts INTEGER, date INTEGER, qts INTEGER, lsv INTEGER, sg INTEGER, pbytes BLOB)").stepThis().dispose();
|
||||||
database.executeFast("INSERT INTO params VALUES(1, 0, 0, 0, 0, 0, 0, NULL)").stepThis().dispose();
|
database.executeFast("INSERT INTO params VALUES(1, 0, 0, 0, 0, 0, 0, NULL)").stepThis().dispose();
|
||||||
database.executeFast("CREATE TABLE user_photos(uid INTEGER, id INTEGER, data BLOB, PRIMARY KEY (uid, id))").stepThis().dispose();
|
database.executeFast("CREATE TABLE user_photos(uid INTEGER, id INTEGER, data BLOB, PRIMARY KEY (uid, id))").stepThis().dispose();
|
||||||
@ -122,7 +123,7 @@ public class MessagesStorage {
|
|||||||
database.executeFast("CREATE INDEX IF NOT EXISTS sphone_deleted_idx_user_phones ON user_phones_v6(sphone, deleted);").stepThis().dispose();
|
database.executeFast("CREATE INDEX IF NOT EXISTS sphone_deleted_idx_user_phones ON user_phones_v6(sphone, deleted);").stepThis().dispose();
|
||||||
|
|
||||||
database.executeFast("CREATE INDEX IF NOT EXISTS date_idx_dialogs ON dialogs(date);").stepThis().dispose();
|
database.executeFast("CREATE INDEX IF NOT EXISTS date_idx_dialogs ON dialogs(date);").stepThis().dispose();
|
||||||
database.executeFast("CREATE INDEX IF NOT EXISTS date_idx_enc_tasks ON enc_tasks(date);").stepThis().dispose();
|
database.executeFast("CREATE INDEX IF NOT EXISTS date_idx_enc_tasks_v2 ON enc_tasks_v2(date);").stepThis().dispose();
|
||||||
database.executeFast("CREATE INDEX IF NOT EXISTS last_mid_idx_dialogs ON dialogs(last_mid);").stepThis().dispose();
|
database.executeFast("CREATE INDEX IF NOT EXISTS last_mid_idx_dialogs ON dialogs(last_mid);").stepThis().dispose();
|
||||||
database.executeFast("CREATE INDEX IF NOT EXISTS unread_count_idx_dialogs ON dialogs(unread_count);").stepThis().dispose();
|
database.executeFast("CREATE INDEX IF NOT EXISTS unread_count_idx_dialogs ON dialogs(unread_count);").stepThis().dispose();
|
||||||
|
|
||||||
@ -135,7 +136,7 @@ public class MessagesStorage {
|
|||||||
database.executeFast("CREATE INDEX IF NOT EXISTS mid_out_idx_messages ON messages(mid, out);").stepThis().dispose();
|
database.executeFast("CREATE INDEX IF NOT EXISTS mid_out_idx_messages ON messages(mid, out);").stepThis().dispose();
|
||||||
database.executeFast("CREATE INDEX IF NOT EXISTS task_idx_messages ON messages(uid, out, read_state, ttl, date, send_state);").stepThis().dispose();
|
database.executeFast("CREATE INDEX IF NOT EXISTS task_idx_messages ON messages(uid, out, read_state, ttl, date, send_state);").stepThis().dispose();
|
||||||
database.executeFast("CREATE INDEX IF NOT EXISTS send_state_idx_messages ON messages(mid, send_state, date) WHERE mid < 0 AND send_state = 1;").stepThis().dispose();
|
database.executeFast("CREATE INDEX IF NOT EXISTS send_state_idx_messages ON messages(mid, send_state, date) WHERE mid < 0 AND send_state = 1;").stepThis().dispose();
|
||||||
database.executeFast("PRAGMA user_version = 4").stepThis().dispose();
|
database.executeFast("PRAGMA user_version = 6").stepThis().dispose();
|
||||||
} else {
|
} else {
|
||||||
try {
|
try {
|
||||||
SQLiteCursor cursor = database.queryFinalized("SELECT seq, pts, date, qts, lsv, sg, pbytes FROM params WHERE id = 1");
|
SQLiteCursor cursor = database.queryFinalized("SELECT seq, pts, date, qts, lsv, sg, pbytes FROM params WHERE id = 1");
|
||||||
@ -167,8 +168,8 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
|
|
||||||
int version = database.executeInt("PRAGMA user_version");
|
int version = database.executeInt("PRAGMA user_version");
|
||||||
if (version < 4) {
|
if (version < 6) {
|
||||||
updateDbToVersion4();
|
updateDbToLastVersion(version);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
@ -177,11 +178,12 @@ public class MessagesStorage {
|
|||||||
loadUnreadMessages();
|
loadUnreadMessages();
|
||||||
}
|
}
|
||||||
|
|
||||||
public void updateDbToVersion4() {
|
public void updateDbToLastVersion(final int currentVersion) {
|
||||||
storageQueue.postRunnable(new Runnable() {
|
storageQueue.postRunnable(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
try {
|
try {
|
||||||
|
if (currentVersion < 4) {
|
||||||
database.executeFast("CREATE TABLE IF NOT EXISTS user_photos(uid INTEGER, id INTEGER, data BLOB, PRIMARY KEY (uid, id))").stepThis().dispose();
|
database.executeFast("CREATE TABLE IF NOT EXISTS user_photos(uid INTEGER, id INTEGER, data BLOB, PRIMARY KEY (uid, id))").stepThis().dispose();
|
||||||
|
|
||||||
database.executeFast("CREATE INDEX IF NOT EXISTS mid_idx_media ON media(mid);").stepThis().dispose();
|
database.executeFast("CREATE INDEX IF NOT EXISTS mid_idx_media ON media(mid);").stepThis().dispose();
|
||||||
@ -216,7 +218,6 @@ public class MessagesStorage {
|
|||||||
|
|
||||||
database.executeFast("UPDATE messages SET send_state = 2 WHERE mid < 0 AND send_state = 1").stepThis().dispose();
|
database.executeFast("UPDATE messages SET send_state = 2 WHERE mid < 0 AND send_state = 1").stepThis().dispose();
|
||||||
|
|
||||||
database.executeFast("PRAGMA user_version = 4").stepThis().dispose();
|
|
||||||
storageQueue.postRunnable(new Runnable() {
|
storageQueue.postRunnable(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
@ -253,6 +254,37 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
}
|
||||||
|
if (currentVersion < 6) {
|
||||||
|
database.executeFast("CREATE TABLE IF NOT EXISTS enc_tasks_v2(mid INTEGER PRIMARY KEY, date INTEGER)").stepThis().dispose();
|
||||||
|
database.executeFast("CREATE INDEX IF NOT EXISTS date_idx_enc_tasks_v2 ON enc_tasks_v2(date);").stepThis().dispose();
|
||||||
|
database.beginTransaction();
|
||||||
|
SQLiteCursor cursor = database.queryFinalized("SELECT date, data FROM enc_tasks WHERE 1");
|
||||||
|
SQLitePreparedStatement state = database.executeFast("REPLACE INTO enc_tasks_v2 VALUES(?, ?)");
|
||||||
|
if (cursor.next()) {
|
||||||
|
int date = cursor.intValue(0);
|
||||||
|
int length = 0;
|
||||||
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(1));
|
||||||
|
if ((length = cursor.byteBufferValue(1, data.buffer)) != 0) {
|
||||||
|
for (int a = 0; a < length / 4; a++) {
|
||||||
|
state.requery();
|
||||||
|
state.bindInteger(1, data.readInt32());
|
||||||
|
state.bindInteger(2, date);
|
||||||
|
state.step();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
buffersStorage.reuseFreeBuffer(data);
|
||||||
|
}
|
||||||
|
state.dispose();
|
||||||
|
cursor.dispose();
|
||||||
|
database.commitTransaction();
|
||||||
|
|
||||||
|
database.executeFast("DROP INDEX IF EXISTS date_idx_enc_tasks;").stepThis().dispose();
|
||||||
|
database.executeFast("DROP TABLE IF EXISTS enc_tasks;").stepThis().dispose();
|
||||||
|
|
||||||
|
database.executeFast("ALTER TABLE messages ADD COLUMN media INTEGER").stepThis().dispose();
|
||||||
|
database.executeFast("PRAGMA user_version = 6").stepThis().dispose();
|
||||||
|
}
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
FileLog.e("tmessages", e);
|
FileLog.e("tmessages", e);
|
||||||
}
|
}
|
||||||
@ -368,16 +400,16 @@ public class MessagesStorage {
|
|||||||
try {
|
try {
|
||||||
final HashMap<Long, Integer> pushDialogs = new HashMap<Long, Integer>();
|
final HashMap<Long, Integer> pushDialogs = new HashMap<Long, Integer>();
|
||||||
SQLiteCursor cursor = database.queryFinalized("SELECT d.did, d.unread_count, s.flags FROM dialogs as d LEFT JOIN dialog_settings as s ON d.did = s.did WHERE d.unread_count != 0");
|
SQLiteCursor cursor = database.queryFinalized("SELECT d.did, d.unread_count, s.flags FROM dialogs as d LEFT JOIN dialog_settings as s ON d.did = s.did WHERE d.unread_count != 0");
|
||||||
String ids = "";
|
StringBuilder ids = new StringBuilder();
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
if (cursor.isNull(2) || cursor.intValue(2) != 1) {
|
if (cursor.isNull(2) || cursor.intValue(2) != 1) {
|
||||||
long did = cursor.longValue(0);
|
long did = cursor.longValue(0);
|
||||||
int count = cursor.intValue(1);
|
int count = cursor.intValue(1);
|
||||||
pushDialogs.put(did, count);
|
pushDialogs.put(did, count);
|
||||||
if (ids.length() != 0) {
|
if (ids.length() != 0) {
|
||||||
ids += ",";
|
ids.append(",");
|
||||||
}
|
}
|
||||||
ids += did;
|
ids.append(did);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
cursor.dispose();
|
cursor.dispose();
|
||||||
@ -391,7 +423,7 @@ public class MessagesStorage {
|
|||||||
ArrayList<Integer> chatIds = new ArrayList<Integer>();
|
ArrayList<Integer> chatIds = new ArrayList<Integer>();
|
||||||
ArrayList<Integer> encryptedChatIds = new ArrayList<Integer>();
|
ArrayList<Integer> encryptedChatIds = new ArrayList<Integer>();
|
||||||
|
|
||||||
cursor = database.queryFinalized("SELECT read_state, data, send_state, mid, date, uid FROM messages WHERE uid IN (" + ids + ") AND out = 0 AND read_state = 0 ORDER BY date DESC LIMIT 50");
|
cursor = database.queryFinalized("SELECT read_state, data, send_state, mid, date, uid FROM messages WHERE uid IN (" + ids.toString() + ") AND out = 0 AND read_state = 0 ORDER BY date DESC LIMIT 50");
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(1));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(1));
|
||||||
if (data != null && cursor.byteBufferValue(1, data.buffer) != 0) {
|
if (data != null && cursor.byteBufferValue(1, data.buffer) != 0) {
|
||||||
@ -449,14 +481,8 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
cursor.dispose();
|
cursor.dispose();
|
||||||
|
|
||||||
String stringToLoad = "";
|
|
||||||
if (!encryptedChatIds.isEmpty()) {
|
if (!encryptedChatIds.isEmpty()) {
|
||||||
for (int uid : encryptedChatIds) {
|
String stringToLoad = TextUtils.join(",", encryptedChatIds);
|
||||||
if (stringToLoad.length() != 0) {
|
|
||||||
stringToLoad += ",";
|
|
||||||
}
|
|
||||||
stringToLoad += uid;
|
|
||||||
}
|
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, user, g, authkey, ttl FROM enc_chats WHERE uid IN(%s)", stringToLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, user, g, authkey, ttl FROM enc_chats WHERE uid IN(%s)", stringToLoad));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
@ -477,13 +503,7 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!userIds.isEmpty()) {
|
if (!userIds.isEmpty()) {
|
||||||
stringToLoad = "";
|
String stringToLoad = TextUtils.join(",", userIds);
|
||||||
for (Integer uid : userIds) {
|
|
||||||
if (stringToLoad.length() != 0) {
|
|
||||||
stringToLoad += ",";
|
|
||||||
}
|
|
||||||
stringToLoad += uid;
|
|
||||||
}
|
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", stringToLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", stringToLoad));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
@ -500,13 +520,7 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!chatIds.isEmpty()) {
|
if (!chatIds.isEmpty()) {
|
||||||
stringToLoad = "";
|
String stringToLoad = TextUtils.join(",", chatIds);
|
||||||
for (Integer cid : chatIds) {
|
|
||||||
if (stringToLoad.length() != 0) {
|
|
||||||
stringToLoad += ",";
|
|
||||||
}
|
|
||||||
stringToLoad += cid;
|
|
||||||
}
|
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data FROM chats WHERE uid IN(%s)", stringToLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data FROM chats WHERE uid IN(%s)", stringToLoad));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
@ -593,19 +607,19 @@ public class MessagesStorage {
|
|||||||
ArrayList<Integer> ids = new ArrayList<Integer>();
|
ArrayList<Integer> ids = new ArrayList<Integer>();
|
||||||
ArrayList<TLRPC.User> users = new ArrayList<TLRPC.User>();
|
ArrayList<TLRPC.User> users = new ArrayList<TLRPC.User>();
|
||||||
SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT * FROM blocked_users WHERE 1"));
|
SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT * FROM blocked_users WHERE 1"));
|
||||||
String usersToLoad = "";
|
StringBuilder usersToLoad = new StringBuilder();
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
int user_id = cursor.intValue(0);
|
int user_id = cursor.intValue(0);
|
||||||
ids.add(user_id);
|
ids.add(user_id);
|
||||||
if (usersToLoad.length() != 0) {
|
if (usersToLoad.length() != 0) {
|
||||||
usersToLoad += ",";
|
usersToLoad.append(",");
|
||||||
}
|
}
|
||||||
usersToLoad += user_id;
|
usersToLoad.append(user_id);
|
||||||
}
|
}
|
||||||
cursor.dispose();
|
cursor.dispose();
|
||||||
|
|
||||||
if (usersToLoad.length() != 0) {
|
if (usersToLoad.length() != 0) {
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", usersToLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", usersToLoad.toString()));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) {
|
if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) {
|
||||||
@ -793,34 +807,28 @@ public class MessagesStorage {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
public void getNewTask(final Long oldTask) {
|
public void getNewTask(final ArrayList<Integer> oldTask) {
|
||||||
storageQueue.postRunnable(new Runnable() {
|
storageQueue.postRunnable(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
try {
|
try {
|
||||||
if (oldTask != null) {
|
if (oldTask != null) {
|
||||||
database.executeFast("DELETE FROM enc_tasks WHERE rowid = " + oldTask).stepThis().dispose();
|
String ids = TextUtils.join(",", oldTask);
|
||||||
|
database.executeFast(String.format(Locale.US, "DELETE FROM enc_tasks_v2 WHERE mid IN(%s)", ids)).stepThis().dispose();
|
||||||
}
|
}
|
||||||
Long taskId = null;
|
|
||||||
int date = 0;
|
int date = 0;
|
||||||
ArrayList<Integer> arr = null;
|
ArrayList<Integer> arr = null;
|
||||||
SQLiteCursor cursor = database.queryFinalized("SELECT rowid, date, data FROM enc_tasks ORDER BY date ASC LIMIT 1");
|
SQLiteCursor cursor = database.queryFinalized("SELECT mid, date FROM enc_tasks_v2 WHERE date = (SELECT min(date) FROM enc_tasks_v2)");
|
||||||
if (cursor.next()) {
|
while (cursor.next()) {
|
||||||
taskId = cursor.longValue(0);
|
Integer mid = cursor.intValue(0);
|
||||||
date = cursor.intValue(1);
|
date = cursor.intValue(1);
|
||||||
|
if (arr == null) {
|
||||||
int length = 0;
|
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(2));
|
|
||||||
if ((length = cursor.byteBufferValue(2, data.buffer)) != 0) {
|
|
||||||
arr = new ArrayList<Integer>();
|
arr = new ArrayList<Integer>();
|
||||||
for (int a = 0; a < length / 4; a++) {
|
|
||||||
arr.add(data.readInt32());
|
|
||||||
}
|
}
|
||||||
}
|
arr.add(mid);
|
||||||
buffersStorage.reuseFreeBuffer(data);
|
|
||||||
}
|
}
|
||||||
cursor.dispose();
|
cursor.dispose();
|
||||||
MessagesController.getInstance().processLoadedDeleteTask(taskId, date, arr);
|
MessagesController.getInstance().processLoadedDeleteTask(date, arr);
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
FileLog.e("tmessages", e);
|
FileLog.e("tmessages", e);
|
||||||
}
|
}
|
||||||
@ -835,13 +843,11 @@ public class MessagesStorage {
|
|||||||
try {
|
try {
|
||||||
int minDate = Integer.MAX_VALUE;
|
int minDate = Integer.MAX_VALUE;
|
||||||
SparseArray<ArrayList<Integer>> messages = new SparseArray<ArrayList<Integer>>();
|
SparseArray<ArrayList<Integer>> messages = new SparseArray<ArrayList<Integer>>();
|
||||||
String mids = "";
|
StringBuilder mids = new StringBuilder();
|
||||||
SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT mid, ttl, read_state FROM messages WHERE uid = %d AND out = %d AND ttl > 0 AND date <= %d AND send_state = 0", ((long)chat_id) << 32, isOut, time));
|
SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT mid, ttl FROM messages WHERE uid = %d AND out = %d AND read_state = 1 AND ttl > 0 AND date <= %d AND send_state = 0 AND media != 1", ((long)chat_id) << 32, isOut, time));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
int mid = cursor.intValue(0);
|
int mid = cursor.intValue(0);
|
||||||
int ttl = cursor.intValue(1);
|
int date = readTime + cursor.intValue(1);
|
||||||
int read_state = cursor.intValue(2);
|
|
||||||
int date = readTime + ttl;
|
|
||||||
minDate = Math.min(minDate, date);
|
minDate = Math.min(minDate, date);
|
||||||
ArrayList<Integer> arr = messages.get(date);
|
ArrayList<Integer> arr = messages.get(date);
|
||||||
if (arr == null) {
|
if (arr == null) {
|
||||||
@ -849,38 +855,28 @@ public class MessagesStorage {
|
|||||||
messages.put(date, arr);
|
messages.put(date, arr);
|
||||||
}
|
}
|
||||||
if (mids.length() != 0) {
|
if (mids.length() != 0) {
|
||||||
mids += ",";
|
mids.append(",");
|
||||||
}
|
}
|
||||||
mids += "" + mid;
|
mids.append(mid);
|
||||||
arr.add(mid);
|
arr.add(mid);
|
||||||
}
|
}
|
||||||
cursor.dispose();
|
cursor.dispose();
|
||||||
if (messages.size() != 0) {
|
if (messages.size() != 0) {
|
||||||
database.beginTransaction();
|
database.beginTransaction();
|
||||||
SQLitePreparedStatement state = database.executeFast("INSERT INTO enc_tasks VALUES(?, ?)");
|
SQLitePreparedStatement state = database.executeFast("REPLACE INTO enc_tasks_v2 VALUES(?, ?)");
|
||||||
for (int a = 0; a < messages.size(); a++) {
|
for (int a = 0; a < messages.size(); a++) {
|
||||||
int key = messages.keyAt(a);
|
int key = messages.keyAt(a);
|
||||||
ArrayList<Integer> arr = messages.get(key);
|
ArrayList<Integer> arr = messages.get(key);
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(404);
|
for (Integer mid : arr) {
|
||||||
int count = 0;
|
|
||||||
for (int b = 0; b < arr.size(); b++) {
|
|
||||||
int mid = arr.get(b);
|
|
||||||
data.writeInt32(mid);
|
|
||||||
count++;
|
|
||||||
if (b == arr.size() - 1 || b != 0 && b % 100 == 0) {
|
|
||||||
state.requery();
|
state.requery();
|
||||||
data.limit(count * 4);
|
state.bindInteger(1, mid);
|
||||||
state.bindInteger(1, key);
|
state.bindInteger(2, key);
|
||||||
state.bindByteBuffer(2, data.buffer);
|
|
||||||
state.step();
|
state.step();
|
||||||
count = 0;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
buffersStorage.reuseFreeBuffer(data);
|
|
||||||
}
|
|
||||||
state.dispose();
|
state.dispose();
|
||||||
database.commitTransaction();
|
database.commitTransaction();
|
||||||
database.executeFast(String.format(Locale.US, "UPDATE messages SET ttl = 0 WHERE mid IN(%s)", mids)).stepThis().dispose();
|
database.executeFast(String.format(Locale.US, "UPDATE messages SET ttl = 0 WHERE mid IN(%s)", mids.toString())).stepThis().dispose();
|
||||||
MessagesController.getInstance().didAddedNewTask(minDate);
|
MessagesController.getInstance().didAddedNewTask(minDate);
|
||||||
}
|
}
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
@ -896,15 +892,9 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
HashMap<Long, Integer> dialogsToUpdate = new HashMap<Long, Integer>();
|
HashMap<Long, Integer> dialogsToUpdate = new HashMap<Long, Integer>();
|
||||||
String dialogsToReload = "";
|
|
||||||
if (messages != null && !messages.isEmpty()) {
|
if (messages != null && !messages.isEmpty()) {
|
||||||
String ids = "";
|
StringBuilder dialogsToReload = new StringBuilder();
|
||||||
for (int uid : messages) {
|
String ids = TextUtils.join(",", messages);
|
||||||
if (ids.length() != 0) {
|
|
||||||
ids += ",";
|
|
||||||
}
|
|
||||||
ids += uid;
|
|
||||||
}
|
|
||||||
int totalCount = 0;
|
int totalCount = 0;
|
||||||
SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT uid, read_state, out FROM messages WHERE mid IN(%s)", ids));
|
SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT uid, read_state, out FROM messages WHERE mid IN(%s)", ids));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
@ -922,20 +912,16 @@ public class MessagesStorage {
|
|||||||
if (currentCount == null) {
|
if (currentCount == null) {
|
||||||
dialogsToUpdate.put(uid, 1);
|
dialogsToUpdate.put(uid, 1);
|
||||||
if (dialogsToReload.length() != 0) {
|
if (dialogsToReload.length() != 0) {
|
||||||
dialogsToReload += ",";
|
dialogsToReload.append(",");
|
||||||
}
|
}
|
||||||
dialogsToReload += uid;
|
dialogsToReload.append(uid);
|
||||||
} else {
|
} else {
|
||||||
dialogsToUpdate.put(uid, currentCount + 1);
|
dialogsToUpdate.put(uid, currentCount + 1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
cursor.dispose();
|
cursor.dispose();
|
||||||
|
|
||||||
if (totalCount != messages.size()) {
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT did, unread_count FROM dialogs WHERE did IN(%s)", dialogsToReload.toString()));
|
||||||
FileLog.e("tmessages", "messages read mismatch!");
|
|
||||||
}
|
|
||||||
|
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT did, unread_count FROM dialogs WHERE did IN(%s)", dialogsToReload));
|
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
long did = cursor.longValue(0);
|
long did = cursor.longValue(0);
|
||||||
int count = cursor.intValue(1);
|
int count = cursor.intValue(1);
|
||||||
@ -1098,7 +1084,7 @@ public class MessagesStorage {
|
|||||||
if (info != null) {
|
if (info != null) {
|
||||||
boolean modified = false;
|
boolean modified = false;
|
||||||
ArrayList<Integer> usersArr = new ArrayList<Integer>();
|
ArrayList<Integer> usersArr = new ArrayList<Integer>();
|
||||||
String usersToLoad = "";
|
StringBuilder usersToLoad = new StringBuilder();
|
||||||
for (int a = 0; a < info.participants.size(); a++) {
|
for (int a = 0; a < info.participants.size(); a++) {
|
||||||
TLRPC.TL_chatParticipant c = info.participants.get(a);
|
TLRPC.TL_chatParticipant c = info.participants.get(a);
|
||||||
if (usersArr.contains(c.user_id)) {
|
if (usersArr.contains(c.user_id)) {
|
||||||
@ -1107,14 +1093,14 @@ public class MessagesStorage {
|
|||||||
a--;
|
a--;
|
||||||
} else {
|
} else {
|
||||||
if (usersToLoad.length() != 0) {
|
if (usersToLoad.length() != 0) {
|
||||||
usersToLoad += ",";
|
usersToLoad.append(",");
|
||||||
}
|
}
|
||||||
usersArr.add(c.user_id);
|
usersArr.add(c.user_id);
|
||||||
usersToLoad += c.user_id;
|
usersToLoad.append(c.user_id);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (usersToLoad.length() != 0) {
|
if (usersToLoad.length() != 0) {
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", usersToLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", usersToLoad.toString()));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) {
|
if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) {
|
||||||
@ -1322,13 +1308,7 @@ public class MessagesStorage {
|
|||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
try {
|
try {
|
||||||
String ids = "";
|
String ids = TextUtils.join(",", uids);
|
||||||
for (Integer uid : uids) {
|
|
||||||
if (ids.length() != 0) {
|
|
||||||
ids += ",";
|
|
||||||
}
|
|
||||||
ids += "" + uid;
|
|
||||||
}
|
|
||||||
database.executeFast("DELETE FROM contacts WHERE uid IN(" + ids + ")").stepThis().dispose();
|
database.executeFast("DELETE FROM contacts WHERE uid IN(" + ids + ")").stepThis().dispose();
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
FileLog.e("tmessages", e);
|
FileLog.e("tmessages", e);
|
||||||
@ -1446,7 +1426,7 @@ public class MessagesStorage {
|
|||||||
ArrayList<TLRPC.User> users = new ArrayList<TLRPC.User>();
|
ArrayList<TLRPC.User> users = new ArrayList<TLRPC.User>();
|
||||||
try {
|
try {
|
||||||
SQLiteCursor cursor = database.queryFinalized("SELECT * FROM contacts WHERE 1");
|
SQLiteCursor cursor = database.queryFinalized("SELECT * FROM contacts WHERE 1");
|
||||||
String uids = "";
|
StringBuilder uids = new StringBuilder();
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
int user_id = cursor.intValue(0);
|
int user_id = cursor.intValue(0);
|
||||||
if (user_id == UserConfig.getClientUserId()) {
|
if (user_id == UserConfig.getClientUserId()) {
|
||||||
@ -1456,15 +1436,15 @@ public class MessagesStorage {
|
|||||||
contact.user_id = user_id;
|
contact.user_id = user_id;
|
||||||
contact.mutual = cursor.intValue(1) == 1;
|
contact.mutual = cursor.intValue(1) == 1;
|
||||||
if (uids.length() != 0) {
|
if (uids.length() != 0) {
|
||||||
uids += ",";
|
uids.append(",");
|
||||||
}
|
}
|
||||||
contacts.add(contact);
|
contacts.add(contact);
|
||||||
uids += contact.user_id;
|
uids.append(contact.user_id);
|
||||||
}
|
}
|
||||||
cursor.dispose();
|
cursor.dispose();
|
||||||
|
|
||||||
if (uids.length() != 0) {
|
if (uids.length() != 0) {
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", uids));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", uids.toString()));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) {
|
if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) {
|
||||||
@ -1574,18 +1554,18 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
cursor.dispose();
|
cursor.dispose();
|
||||||
|
|
||||||
String usersToLoad = "";
|
StringBuilder usersToLoad = new StringBuilder();
|
||||||
for (int uid : fromUser) {
|
for (int uid : fromUser) {
|
||||||
if (!loadedUsers.contains(uid)) {
|
if (!loadedUsers.contains(uid)) {
|
||||||
if (usersToLoad.length() != 0) {
|
if (usersToLoad.length() != 0) {
|
||||||
usersToLoad += ",";
|
usersToLoad.append(",");
|
||||||
}
|
}
|
||||||
usersToLoad += uid;
|
usersToLoad.append(uid);
|
||||||
loadedUsers.add(uid);
|
loadedUsers.add(uid);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (usersToLoad.length() != 0) {
|
if (usersToLoad.length() != 0) {
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", usersToLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", usersToLoad.toString()));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) {
|
if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) {
|
||||||
@ -1722,14 +1702,9 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
cursor.dispose();
|
cursor.dispose();
|
||||||
|
|
||||||
String stringToLoad = "";
|
|
||||||
if (!encryptedChatIds.isEmpty()) {
|
if (!encryptedChatIds.isEmpty()) {
|
||||||
for (int uid : encryptedChatIds) {
|
String stringToLoad = TextUtils.join(",", encryptedChatIds);
|
||||||
if (stringToLoad.length() != 0) {
|
|
||||||
stringToLoad += ",";
|
|
||||||
}
|
|
||||||
stringToLoad += uid;
|
|
||||||
}
|
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, user, g, authkey, ttl FROM enc_chats WHERE uid IN(%s)", stringToLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, user, g, authkey, ttl FROM enc_chats WHERE uid IN(%s)", stringToLoad));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
@ -1751,13 +1726,7 @@ public class MessagesStorage {
|
|||||||
|
|
||||||
|
|
||||||
if (!userIds.isEmpty()) {
|
if (!userIds.isEmpty()) {
|
||||||
stringToLoad = "";
|
String stringToLoad = TextUtils.join(",", userIds);
|
||||||
for (Integer uid : userIds) {
|
|
||||||
if (stringToLoad.length() != 0) {
|
|
||||||
stringToLoad += ",";
|
|
||||||
}
|
|
||||||
stringToLoad += uid;
|
|
||||||
}
|
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", stringToLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", stringToLoad));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
@ -1774,20 +1743,20 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!chatIds.isEmpty() || !broadcastIds.isEmpty()) {
|
if (!chatIds.isEmpty() || !broadcastIds.isEmpty()) {
|
||||||
stringToLoad = "";
|
StringBuilder stringToLoad = new StringBuilder();
|
||||||
for (Integer cid : chatIds) {
|
for (Integer cid : chatIds) {
|
||||||
if (stringToLoad.length() != 0) {
|
if (stringToLoad.length() != 0) {
|
||||||
stringToLoad += ",";
|
stringToLoad.append(",");
|
||||||
}
|
}
|
||||||
stringToLoad += cid;
|
stringToLoad.append(cid);
|
||||||
}
|
}
|
||||||
for (Integer cid : broadcastIds) {
|
for (Integer cid : broadcastIds) {
|
||||||
if (stringToLoad.length() != 0) {
|
if (stringToLoad.length() != 0) {
|
||||||
stringToLoad += ",";
|
stringToLoad.append(",");
|
||||||
}
|
}
|
||||||
stringToLoad += (-cid);
|
stringToLoad.append(-cid);
|
||||||
}
|
}
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data FROM chats WHERE uid IN(%s)", stringToLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data FROM chats WHERE uid IN(%s)", stringToLoad.toString()));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) {
|
if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) {
|
||||||
@ -1807,7 +1776,7 @@ public class MessagesStorage {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
public void getMessages(final long dialog_id, final int count, final int max_id, final int minDate, final int classGuid, final boolean from_unread, final boolean forward) {
|
public void getMessages(final long dialog_id, final int count, final int max_id, final int minDate, final int classGuid, final boolean from_unread, final boolean forward, final Semaphore semaphore) {
|
||||||
storageQueue.postRunnable(new Runnable() {
|
storageQueue.postRunnable(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
@ -1991,18 +1960,18 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
cursor.dispose();
|
cursor.dispose();
|
||||||
|
|
||||||
String usersToLoad = "";
|
StringBuilder usersToLoad = new StringBuilder();
|
||||||
for (int uid : fromUser) {
|
for (int uid : fromUser) {
|
||||||
if (!loadedUsers.contains(uid)) {
|
if (!loadedUsers.contains(uid)) {
|
||||||
if (usersToLoad.length() != 0) {
|
if (usersToLoad.length() != 0) {
|
||||||
usersToLoad += ",";
|
usersToLoad.append(",");
|
||||||
}
|
}
|
||||||
usersToLoad += uid;
|
usersToLoad.append(uid);
|
||||||
loadedUsers.add(uid);
|
loadedUsers.add(uid);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (usersToLoad.length() != 0) {
|
if (usersToLoad.length() != 0) {
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", usersToLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", usersToLoad.toString()));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) {
|
if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) {
|
||||||
@ -2023,7 +1992,7 @@ public class MessagesStorage {
|
|||||||
res.users.clear();
|
res.users.clear();
|
||||||
FileLog.e("tmessages", e);
|
FileLog.e("tmessages", e);
|
||||||
} finally {
|
} finally {
|
||||||
MessagesController.getInstance().processLoadedMessages(res, dialog_id, count_query, max_id, true, classGuid, min_unread_id, max_unread_id, count_unread, max_unread_date, forward);
|
MessagesController.getInstance().processLoadedMessages(res, dialog_id, count_query, max_id, true, classGuid, min_unread_id, max_unread_id, count_unread, max_unread_date, forward, semaphore);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@ -2448,6 +2417,18 @@ public class MessagesStorage {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private int getMessageMediaType(TLRPC.Message message) {
|
||||||
|
if (message.media == null) {
|
||||||
|
return 0;
|
||||||
|
} else if (message.media instanceof TLRPC.TL_messageMediaPhoto) {
|
||||||
|
return 1;
|
||||||
|
} else if (message.media instanceof TLRPC.TL_messageMediaVideo) {
|
||||||
|
return 2;
|
||||||
|
} else {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private void putMessagesInternal(final ArrayList<TLRPC.Message> messages, final boolean withTransaction, final boolean isBroadcast, final int downloadMask) {
|
private void putMessagesInternal(final ArrayList<TLRPC.Message> messages, final boolean withTransaction, final boolean isBroadcast, final int downloadMask) {
|
||||||
try {
|
try {
|
||||||
if (withTransaction) {
|
if (withTransaction) {
|
||||||
@ -2458,9 +2439,9 @@ public class MessagesStorage {
|
|||||||
HashMap<Long, Integer> mediaCounts = new HashMap<Long, Integer>();
|
HashMap<Long, Integer> mediaCounts = new HashMap<Long, Integer>();
|
||||||
HashMap<Integer, Long> messagesIdsMap = new HashMap<Integer, Long>();
|
HashMap<Integer, Long> messagesIdsMap = new HashMap<Integer, Long>();
|
||||||
HashMap<Integer, Long> messagesMediaIdsMap = new HashMap<Integer, Long>();
|
HashMap<Integer, Long> messagesMediaIdsMap = new HashMap<Integer, Long>();
|
||||||
String messageIds = "";
|
StringBuilder messageIds = new StringBuilder();
|
||||||
String messageMediaIds = "";
|
StringBuilder messageMediaIds = new StringBuilder();
|
||||||
SQLitePreparedStatement state = database.executeFast("REPLACE INTO messages VALUES(?, ?, ?, ?, ?, ?, ?, ?)");
|
SQLitePreparedStatement state = database.executeFast("REPLACE INTO messages VALUES(?, ?, ?, ?, ?, ?, ?, ?, ?)");
|
||||||
SQLitePreparedStatement state2 = database.executeFast("REPLACE INTO media VALUES(?, ?, ?, ?)");
|
SQLitePreparedStatement state2 = database.executeFast("REPLACE INTO media VALUES(?, ?, ?, ?)");
|
||||||
SQLitePreparedStatement state3 = database.executeFast("REPLACE INTO randoms VALUES(?, ?)");
|
SQLitePreparedStatement state3 = database.executeFast("REPLACE INTO randoms VALUES(?, ?)");
|
||||||
SQLitePreparedStatement state4 = database.executeFast("REPLACE INTO download_queue VALUES(?, ?, ?, ?)");
|
SQLitePreparedStatement state4 = database.executeFast("REPLACE INTO download_queue VALUES(?, ?, ?, ?)");
|
||||||
@ -2477,23 +2458,23 @@ public class MessagesStorage {
|
|||||||
|
|
||||||
if (message.unread && !message.out) {
|
if (message.unread && !message.out) {
|
||||||
if (messageIds.length() > 0) {
|
if (messageIds.length() > 0) {
|
||||||
messageIds += ",";
|
messageIds.append(",");
|
||||||
}
|
}
|
||||||
messageIds += message.id;
|
messageIds.append(message.id);
|
||||||
messagesIdsMap.put(message.id, dialog_id);
|
messagesIdsMap.put(message.id, dialog_id);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (message.media instanceof TLRPC.TL_messageMediaVideo || message.media instanceof TLRPC.TL_messageMediaPhoto) {
|
if (message.ttl == 0 && (message.media instanceof TLRPC.TL_messageMediaVideo || message.media instanceof TLRPC.TL_messageMediaPhoto)) {
|
||||||
if (messageMediaIds.length() > 0) {
|
if (messageMediaIds.length() > 0) {
|
||||||
messageMediaIds += ",";
|
messageMediaIds.append(",");
|
||||||
}
|
}
|
||||||
messageMediaIds += message.id;
|
messageMediaIds.append(message.id);
|
||||||
messagesMediaIdsMap.put(message.id, dialog_id);
|
messagesMediaIdsMap.put(message.id, dialog_id);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (messageIds.length() > 0) {
|
if (messageIds.length() > 0) {
|
||||||
SQLiteCursor cursor = database.queryFinalized("SELECT mid FROM messages WHERE mid IN(" + messageIds + ")");
|
SQLiteCursor cursor = database.queryFinalized("SELECT mid FROM messages WHERE mid IN(" + messageIds.toString() + ")");
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
int mid = cursor.intValue(0);
|
int mid = cursor.intValue(0);
|
||||||
messagesIdsMap.remove(mid);
|
messagesIdsMap.remove(mid);
|
||||||
@ -2510,7 +2491,7 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (messageMediaIds.length() > 0) {
|
if (messageMediaIds.length() > 0) {
|
||||||
SQLiteCursor cursor = database.queryFinalized("SELECT mid FROM media WHERE mid IN(" + messageMediaIds + ")");
|
SQLiteCursor cursor = database.queryFinalized("SELECT mid FROM media WHERE mid IN(" + messageMediaIds.toString() + ")");
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
int mid = cursor.intValue(0);
|
int mid = cursor.intValue(0);
|
||||||
messagesMediaIdsMap.remove(mid);
|
messagesMediaIdsMap.remove(mid);
|
||||||
@ -2557,6 +2538,7 @@ public class MessagesStorage {
|
|||||||
state.bindByteBuffer(6, data.buffer);
|
state.bindByteBuffer(6, data.buffer);
|
||||||
state.bindInteger(7, (message.out ? 1 : 0));
|
state.bindInteger(7, (message.out ? 1 : 0));
|
||||||
state.bindInteger(8, message.ttl);
|
state.bindInteger(8, message.ttl);
|
||||||
|
state.bindInteger(9, getMessageMediaType(message));
|
||||||
state.step();
|
state.step();
|
||||||
|
|
||||||
if (message.random_id != 0) {
|
if (message.random_id != 0) {
|
||||||
@ -2566,7 +2548,7 @@ public class MessagesStorage {
|
|||||||
state3.step();
|
state3.step();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (message.media instanceof TLRPC.TL_messageMediaVideo || message.media instanceof TLRPC.TL_messageMediaPhoto) {
|
if (message.ttl == 0 && (message.media instanceof TLRPC.TL_messageMediaVideo || message.media instanceof TLRPC.TL_messageMediaPhoto)) {
|
||||||
state2.requery();
|
state2.requery();
|
||||||
state2.bindInteger(1, messageId);
|
state2.bindInteger(1, messageId);
|
||||||
state2.bindLong(2, dialog_id);
|
state2.bindLong(2, dialog_id);
|
||||||
@ -2862,17 +2844,17 @@ public class MessagesStorage {
|
|||||||
database.commitTransaction();
|
database.commitTransaction();
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
String ids = "";
|
StringBuilder ids = new StringBuilder();
|
||||||
HashMap<Integer, TLRPC.User> usersDict = new HashMap<Integer, TLRPC.User>();
|
HashMap<Integer, TLRPC.User> usersDict = new HashMap<Integer, TLRPC.User>();
|
||||||
for (TLRPC.User user : users) {
|
for (TLRPC.User user : users) {
|
||||||
if (ids.length() != 0) {
|
if (ids.length() != 0) {
|
||||||
ids += ",";
|
ids.append(",");
|
||||||
}
|
}
|
||||||
ids += user.id;
|
ids.append(user.id);
|
||||||
usersDict.put(user.id, user);
|
usersDict.put(user.id, user);
|
||||||
}
|
}
|
||||||
ArrayList<TLRPC.User> loadedUsers = new ArrayList<TLRPC.User>();
|
ArrayList<TLRPC.User> loadedUsers = new ArrayList<TLRPC.User>();
|
||||||
SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", ids));
|
SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", ids.toString()));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) {
|
if (data != null && cursor.byteBufferValue(0, data.buffer) != 0) {
|
||||||
@ -2950,13 +2932,7 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
if (messages != null && !messages.isEmpty()) {
|
if (messages != null && !messages.isEmpty()) {
|
||||||
String ids = "";
|
String ids = TextUtils.join(",", messages);
|
||||||
for (int uid : messages) {
|
|
||||||
if (ids.length() != 0) {
|
|
||||||
ids += ",";
|
|
||||||
}
|
|
||||||
ids += uid;
|
|
||||||
}
|
|
||||||
database.executeFast(String.format(Locale.US, "UPDATE messages SET read_state = 1 WHERE mid IN(%s)", ids)).stepThis().dispose();
|
database.executeFast(String.format(Locale.US, "UPDATE messages SET read_state = 1 WHERE mid IN(%s)", ids)).stepThis().dispose();
|
||||||
}
|
}
|
||||||
if (encryptedMessages != null && !encryptedMessages.isEmpty()) {
|
if (encryptedMessages != null && !encryptedMessages.isEmpty()) {
|
||||||
@ -2997,13 +2973,7 @@ public class MessagesStorage {
|
|||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
try {
|
try {
|
||||||
String ids = "";
|
String ids = TextUtils.join(",", messages);
|
||||||
for (long uid : messages) {
|
|
||||||
if (ids.length() != 0) {
|
|
||||||
ids += ",";
|
|
||||||
}
|
|
||||||
ids += uid;
|
|
||||||
}
|
|
||||||
SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT mid FROM randoms WHERE random_id IN(%s)", ids));
|
SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT mid FROM randoms WHERE random_id IN(%s)", ids));
|
||||||
final ArrayList<Integer> mids = new ArrayList<Integer>();
|
final ArrayList<Integer> mids = new ArrayList<Integer>();
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
@ -3038,13 +3008,7 @@ public class MessagesStorage {
|
|||||||
throw new RuntimeException("wrong db thread");
|
throw new RuntimeException("wrong db thread");
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
String ids = "";
|
String ids = TextUtils.join(",", messages);
|
||||||
for (int uid : messages) {
|
|
||||||
if (ids.length() != 0) {
|
|
||||||
ids += ",";
|
|
||||||
}
|
|
||||||
ids += uid;
|
|
||||||
}
|
|
||||||
database.executeFast(String.format(Locale.US, "DELETE FROM messages WHERE mid IN(%s)", ids)).stepThis().dispose();
|
database.executeFast(String.format(Locale.US, "DELETE FROM messages WHERE mid IN(%s)", ids)).stepThis().dispose();
|
||||||
database.executeFast(String.format(Locale.US, "DELETE FROM media WHERE mid IN(%s)", ids)).stepThis().dispose();
|
database.executeFast(String.format(Locale.US, "DELETE FROM media WHERE mid IN(%s)", ids)).stepThis().dispose();
|
||||||
database.executeFast("DELETE FROM media_counts WHERE 1").stepThis().dispose();
|
database.executeFast("DELETE FROM media_counts WHERE 1").stepThis().dispose();
|
||||||
@ -3059,13 +3023,7 @@ public class MessagesStorage {
|
|||||||
throw new RuntimeException("wrong db thread");
|
throw new RuntimeException("wrong db thread");
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
String ids = "";
|
String ids = TextUtils.join(",", messages);
|
||||||
for (int uid : messages) {
|
|
||||||
if (ids.length() != 0) {
|
|
||||||
ids += ",";
|
|
||||||
}
|
|
||||||
ids += uid;
|
|
||||||
}
|
|
||||||
SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT did FROM dialogs WHERE last_mid IN(%s)", ids));
|
SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT did FROM dialogs WHERE last_mid IN(%s)", ids));
|
||||||
ArrayList<Long> dialogsToUpdate = new ArrayList<Long>();
|
ArrayList<Long> dialogsToUpdate = new ArrayList<Long>();
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
@ -3084,13 +3042,7 @@ public class MessagesStorage {
|
|||||||
state.dispose();
|
state.dispose();
|
||||||
database.commitTransaction();
|
database.commitTransaction();
|
||||||
|
|
||||||
ids = "";
|
ids = TextUtils.join(",", dialogsToUpdate);
|
||||||
for (long uid : dialogsToUpdate) {
|
|
||||||
if (ids.length() != 0) {
|
|
||||||
ids += ",";
|
|
||||||
}
|
|
||||||
ids += uid;
|
|
||||||
}
|
|
||||||
|
|
||||||
TLRPC.messages_Dialogs dialogs = new TLRPC.messages_Dialogs();
|
TLRPC.messages_Dialogs dialogs = new TLRPC.messages_Dialogs();
|
||||||
ArrayList<TLRPC.EncryptedChat> encryptedChats = new ArrayList<TLRPC.EncryptedChat>();
|
ArrayList<TLRPC.EncryptedChat> encryptedChats = new ArrayList<TLRPC.EncryptedChat>();
|
||||||
@ -3157,13 +3109,7 @@ public class MessagesStorage {
|
|||||||
cursor.dispose();
|
cursor.dispose();
|
||||||
|
|
||||||
if (!encryptedToLoad.isEmpty()) {
|
if (!encryptedToLoad.isEmpty()) {
|
||||||
String toLoad = "";
|
String toLoad = TextUtils.join(",", encryptedToLoad);
|
||||||
for (int uid : encryptedToLoad) {
|
|
||||||
if (toLoad.length() != 0) {
|
|
||||||
toLoad += ",";
|
|
||||||
}
|
|
||||||
toLoad += uid;
|
|
||||||
}
|
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, user, g, authkey, ttl FROM enc_chats WHERE uid IN(%s)", toLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, user, g, authkey, ttl FROM enc_chats WHERE uid IN(%s)", toLoad));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
@ -3184,13 +3130,7 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!chatsToLoad.isEmpty()) {
|
if (!chatsToLoad.isEmpty()) {
|
||||||
String toLoad = "";
|
String toLoad = TextUtils.join(",", chatsToLoad);
|
||||||
for (int uid : chatsToLoad) {
|
|
||||||
if (toLoad.length() != 0) {
|
|
||||||
toLoad += ",";
|
|
||||||
}
|
|
||||||
toLoad += uid;
|
|
||||||
}
|
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data FROM chats WHERE uid IN(%s)", toLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data FROM chats WHERE uid IN(%s)", toLoad));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
@ -3204,13 +3144,7 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!usersToLoad.isEmpty()) {
|
if (!usersToLoad.isEmpty()) {
|
||||||
String toLoad = "";
|
String toLoad = TextUtils.join(",", usersToLoad);
|
||||||
for (int uid : usersToLoad) {
|
|
||||||
if (toLoad.length() != 0) {
|
|
||||||
toLoad += ",";
|
|
||||||
}
|
|
||||||
toLoad += uid;
|
|
||||||
}
|
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", toLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", toLoad));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
ByteBufferDesc data = buffersStorage.getFreeBuffer(cursor.byteArrayLength(0));
|
||||||
@ -3276,7 +3210,7 @@ public class MessagesStorage {
|
|||||||
try {
|
try {
|
||||||
database.beginTransaction();
|
database.beginTransaction();
|
||||||
if (!messages.messages.isEmpty()) {
|
if (!messages.messages.isEmpty()) {
|
||||||
SQLitePreparedStatement state = database.executeFast("REPLACE INTO messages VALUES(?, ?, ?, ?, ?, ?, ?, ?)");
|
SQLitePreparedStatement state = database.executeFast("REPLACE INTO messages VALUES(?, ?, ?, ?, ?, ?, ?, ?, ?)");
|
||||||
SQLitePreparedStatement state2 = database.executeFast("REPLACE INTO media VALUES(?, ?, ?, ?)");
|
SQLitePreparedStatement state2 = database.executeFast("REPLACE INTO media VALUES(?, ?, ?, ?)");
|
||||||
for (TLRPC.Message message : messages.messages) {
|
for (TLRPC.Message message : messages.messages) {
|
||||||
state.requery();
|
state.requery();
|
||||||
@ -3290,6 +3224,7 @@ public class MessagesStorage {
|
|||||||
state.bindByteBuffer(6, data.buffer);
|
state.bindByteBuffer(6, data.buffer);
|
||||||
state.bindInteger(7, (message.out ? 1 : 0));
|
state.bindInteger(7, (message.out ? 1 : 0));
|
||||||
state.bindInteger(8, 0);
|
state.bindInteger(8, 0);
|
||||||
|
state.bindInteger(9, getMessageMediaType(message));
|
||||||
state.step();
|
state.step();
|
||||||
|
|
||||||
if (message.media instanceof TLRPC.TL_messageMediaVideo || message.media instanceof TLRPC.TL_messageMediaPhoto) {
|
if (message.media instanceof TLRPC.TL_messageMediaVideo || message.media instanceof TLRPC.TL_messageMediaPhoto) {
|
||||||
@ -3430,13 +3365,7 @@ public class MessagesStorage {
|
|||||||
cursor.dispose();
|
cursor.dispose();
|
||||||
|
|
||||||
if (!encryptedToLoad.isEmpty()) {
|
if (!encryptedToLoad.isEmpty()) {
|
||||||
String toLoad = "";
|
String toLoad = TextUtils.join(",", encryptedToLoad);
|
||||||
for (int uid : encryptedToLoad) {
|
|
||||||
if (toLoad.length() != 0) {
|
|
||||||
toLoad += ",";
|
|
||||||
}
|
|
||||||
toLoad += uid;
|
|
||||||
}
|
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, user, g, authkey, ttl FROM enc_chats WHERE uid IN(%s)", toLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, user, g, authkey, ttl FROM enc_chats WHERE uid IN(%s)", toLoad));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
try {
|
try {
|
||||||
@ -3463,13 +3392,7 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!chatsToLoad.isEmpty()) {
|
if (!chatsToLoad.isEmpty()) {
|
||||||
String toLoad = "";
|
String toLoad = TextUtils.join(",", chatsToLoad);
|
||||||
for (int uid : chatsToLoad) {
|
|
||||||
if (toLoad.length() != 0) {
|
|
||||||
toLoad += ",";
|
|
||||||
}
|
|
||||||
toLoad += uid;
|
|
||||||
}
|
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data FROM chats WHERE uid IN(%s)", toLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data FROM chats WHERE uid IN(%s)", toLoad));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
try {
|
try {
|
||||||
@ -3489,13 +3412,7 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!usersToLoad.isEmpty()) {
|
if (!usersToLoad.isEmpty()) {
|
||||||
String toLoad = "";
|
String toLoad = TextUtils.join(",", usersToLoad);
|
||||||
for (int uid : usersToLoad) {
|
|
||||||
if (toLoad.length() != 0) {
|
|
||||||
toLoad += ",";
|
|
||||||
}
|
|
||||||
toLoad += uid;
|
|
||||||
}
|
|
||||||
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", toLoad));
|
cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN(%s)", toLoad));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
try {
|
try {
|
||||||
@ -3549,7 +3466,7 @@ public class MessagesStorage {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!dialogs.dialogs.isEmpty()) {
|
if (!dialogs.dialogs.isEmpty()) {
|
||||||
SQLitePreparedStatement state = database.executeFast("REPLACE INTO messages VALUES(?, ?, ?, ?, ?, ?, ?, ?)");
|
SQLitePreparedStatement state = database.executeFast("REPLACE INTO messages VALUES(?, ?, ?, ?, ?, ?, ?, ?, ?)");
|
||||||
SQLitePreparedStatement state2 = database.executeFast("REPLACE INTO dialogs(did, date, unread_count, last_mid) VALUES(?, ?, ?, ?)");
|
SQLitePreparedStatement state2 = database.executeFast("REPLACE INTO dialogs(did, date, unread_count, last_mid) VALUES(?, ?, ?, ?)");
|
||||||
SQLitePreparedStatement state3 = database.executeFast("REPLACE INTO media VALUES(?, ?, ?, ?)");
|
SQLitePreparedStatement state3 = database.executeFast("REPLACE INTO media VALUES(?, ?, ?, ?)");
|
||||||
SQLitePreparedStatement state4 = database.executeFast("REPLACE INTO dialog_settings VALUES(?, ?)");
|
SQLitePreparedStatement state4 = database.executeFast("REPLACE INTO dialog_settings VALUES(?, ?)");
|
||||||
@ -3574,6 +3491,7 @@ public class MessagesStorage {
|
|||||||
state.bindByteBuffer(6, data.buffer);
|
state.bindByteBuffer(6, data.buffer);
|
||||||
state.bindInteger(7, (message.out ? 1 : 0));
|
state.bindInteger(7, (message.out ? 1 : 0));
|
||||||
state.bindInteger(8, 0);
|
state.bindInteger(8, 0);
|
||||||
|
state.bindInteger(9, getMessageMediaType(message));
|
||||||
state.step();
|
state.step();
|
||||||
|
|
||||||
state2.bindLong(1, uid);
|
state2.bindLong(1, uid);
|
||||||
@ -3683,14 +3601,7 @@ public class MessagesStorage {
|
|||||||
public ArrayList<TLRPC.User> getUsers(final ArrayList<Integer> uids, final boolean[] error) {
|
public ArrayList<TLRPC.User> getUsers(final ArrayList<Integer> uids, final boolean[] error) {
|
||||||
ArrayList<TLRPC.User> users = new ArrayList<TLRPC.User>();
|
ArrayList<TLRPC.User> users = new ArrayList<TLRPC.User>();
|
||||||
try {
|
try {
|
||||||
String uidsStr = "";
|
String uidsStr = TextUtils.join(",", uids);
|
||||||
|
|
||||||
for (Integer uid : uids) {
|
|
||||||
if (uidsStr.length() != 0) {
|
|
||||||
uidsStr += ",";
|
|
||||||
}
|
|
||||||
uidsStr += uid;
|
|
||||||
}
|
|
||||||
|
|
||||||
SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN (%s)", uidsStr));
|
SQLiteCursor cursor = database.queryFinalized(String.format(Locale.US, "SELECT data, status FROM users WHERE uid IN (%s)", uidsStr));
|
||||||
while (cursor.next()) {
|
while (cursor.next()) {
|
||||||
|
@ -24,9 +24,9 @@ import java.util.zip.ZipFile;
|
|||||||
public class NativeLoader {
|
public class NativeLoader {
|
||||||
|
|
||||||
private static final long sizes[] = new long[] {
|
private static final long sizes[] = new long[] {
|
||||||
946908, //armeabi
|
951052, //armeabi
|
||||||
1028848, //armeabi-v7a
|
1032992, //armeabi-v7a
|
||||||
1603780, //x86
|
1612020, //x86
|
||||||
0, //mips
|
0, //mips
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -9000,6 +9000,41 @@ public class TLRPC {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static class TL_message_secret extends TL_message {
|
||||||
|
public static int constructor = 0x555555F8;
|
||||||
|
|
||||||
|
public void readParams(AbsSerializedData stream) {
|
||||||
|
id = stream.readInt32();
|
||||||
|
from_id = stream.readInt32();
|
||||||
|
to_id = (Peer)TLClassStore.Instance().TLdeserialize(stream, stream.readInt32());
|
||||||
|
out = stream.readBool();
|
||||||
|
unread = stream.readBool();
|
||||||
|
date = stream.readInt32();
|
||||||
|
message = stream.readString();
|
||||||
|
media = (MessageMedia)TLClassStore.Instance().TLdeserialize(stream, stream.readInt32());
|
||||||
|
if (id < 0 || (media != null && !(media instanceof TL_messageMediaEmpty) && message != null && message.length() != 0 && message.startsWith("-1"))) {
|
||||||
|
attachPath = stream.readString();
|
||||||
|
}
|
||||||
|
if (id < 0 && message.length() > 6 && media instanceof TL_messageMediaVideo) {
|
||||||
|
videoEditedInfo = new VideoEditedInfo();
|
||||||
|
videoEditedInfo.parseString(message);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void serializeToStream(AbsSerializedData stream) {
|
||||||
|
stream.writeInt32(constructor);
|
||||||
|
stream.writeInt32(id);
|
||||||
|
stream.writeInt32(from_id);
|
||||||
|
to_id.serializeToStream(stream);
|
||||||
|
stream.writeBool(out);
|
||||||
|
stream.writeBool(unread);
|
||||||
|
stream.writeInt32(date);
|
||||||
|
stream.writeString(message);
|
||||||
|
media.serializeToStream(stream);
|
||||||
|
stream.writeString(attachPath);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public static class TL_messages_deleteMessages extends TLObject {
|
public static class TL_messages_deleteMessages extends TLObject {
|
||||||
public static int constructor = 0x14f2dd0a;
|
public static int constructor = 0x14f2dd0a;
|
||||||
|
|
||||||
|
@ -117,6 +117,7 @@ public class ChatActivity extends BaseFragment implements NotificationCenter.Not
|
|||||||
private TypingDotsDrawable typingDotsDrawable;
|
private TypingDotsDrawable typingDotsDrawable;
|
||||||
private View emptyViewContainer;
|
private View emptyViewContainer;
|
||||||
private ArrayList<View> actionModeViews = new ArrayList<View>();
|
private ArrayList<View> actionModeViews = new ArrayList<View>();
|
||||||
|
private Semaphore testSemaphore = new Semaphore(0);
|
||||||
|
|
||||||
private TextView bottomOverlayText;
|
private TextView bottomOverlayText;
|
||||||
|
|
||||||
@ -352,7 +353,14 @@ public class ChatActivity extends BaseFragment implements NotificationCenter.Not
|
|||||||
super.onFragmentCreate();
|
super.onFragmentCreate();
|
||||||
|
|
||||||
loading = true;
|
loading = true;
|
||||||
MessagesController.getInstance().loadMessages(dialog_id, 30, 0, true, 0, classGuid, true, false);
|
|
||||||
|
MessagesController.getInstance().loadMessages(dialog_id, AndroidUtilities.isTablet() ? 30 : 20, 0, true, 0, classGuid, true, false, testSemaphore);
|
||||||
|
try {
|
||||||
|
testSemaphore.acquire();
|
||||||
|
} catch (Exception e) {
|
||||||
|
FileLog.e("tmessages", e);
|
||||||
|
}
|
||||||
|
|
||||||
if (currentUser != null) {
|
if (currentUser != null) {
|
||||||
userBlocked = MessagesController.getInstance().blockedUsers.contains(currentUser.id);
|
userBlocked = MessagesController.getInstance().blockedUsers.contains(currentUser.id);
|
||||||
}
|
}
|
||||||
@ -766,16 +774,16 @@ public class ChatActivity extends BaseFragment implements NotificationCenter.Not
|
|||||||
if (firstVisibleItem <= 4) {
|
if (firstVisibleItem <= 4) {
|
||||||
if (!endReached && !loading) {
|
if (!endReached && !loading) {
|
||||||
if (messagesByDays.size() != 0) {
|
if (messagesByDays.size() != 0) {
|
||||||
MessagesController.getInstance().loadMessages(dialog_id, 20, maxMessageId, !cacheEndReaced, minDate, classGuid, false, false);
|
MessagesController.getInstance().loadMessages(dialog_id, 20, maxMessageId, !cacheEndReaced, minDate, classGuid, false, false, null);
|
||||||
} else {
|
} else {
|
||||||
MessagesController.getInstance().loadMessages(dialog_id, 20, 0, !cacheEndReaced, minDate, classGuid, false, false);
|
MessagesController.getInstance().loadMessages(dialog_id, 20, 0, !cacheEndReaced, minDate, classGuid, false, false, null);
|
||||||
}
|
}
|
||||||
loading = true;
|
loading = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (firstVisibleItem + visibleItemCount >= totalItemCount - 6) {
|
if (firstVisibleItem + visibleItemCount >= totalItemCount - 6) {
|
||||||
if (!unread_end_reached && !loadingForward) {
|
if (!unread_end_reached && !loadingForward) {
|
||||||
MessagesController.getInstance().loadMessages(dialog_id, 20, minMessageId, true, maxDate, classGuid, false, true);
|
MessagesController.getInstance().loadMessages(dialog_id, 20, minMessageId, true, maxDate, classGuid, false, true, null);
|
||||||
loadingForward = true;
|
loadingForward = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -896,7 +904,7 @@ public class ChatActivity extends BaseFragment implements NotificationCenter.Not
|
|||||||
unread_end_reached = true;
|
unread_end_reached = true;
|
||||||
loading = true;
|
loading = true;
|
||||||
chatAdapter.notifyDataSetChanged();
|
chatAdapter.notifyDataSetChanged();
|
||||||
MessagesController.getInstance().loadMessages(dialog_id, 30, 0, true, 0, classGuid, true, false);
|
MessagesController.getInstance().loadMessages(dialog_id, 30, 0, true, 0, classGuid, true, false, null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2249,7 +2257,7 @@ public class ChatActivity extends BaseFragment implements NotificationCenter.Not
|
|||||||
}
|
}
|
||||||
maxDate = Integer.MIN_VALUE;
|
maxDate = Integer.MIN_VALUE;
|
||||||
minDate = 0;
|
minDate = 0;
|
||||||
MessagesController.getInstance().loadMessages(dialog_id, 30, 0, !cacheEndReaced, minDate, classGuid, false, false);
|
MessagesController.getInstance().loadMessages(dialog_id, 30, 0, !cacheEndReaced, minDate, classGuid, false, false, null);
|
||||||
loading = true;
|
loading = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -2138,7 +2138,7 @@ public class PhotoViewer implements NotificationCenter.NotificationCenterDelegat
|
|||||||
float ai = -1;
|
float ai = -1;
|
||||||
if (System.currentTimeMillis() - animationStartTime < animationDuration) {
|
if (System.currentTimeMillis() - animationStartTime < animationDuration) {
|
||||||
ai = interpolator.getInterpolation((float)(System.currentTimeMillis() - animationStartTime) / animationDuration);
|
ai = interpolator.getInterpolation((float)(System.currentTimeMillis() - animationStartTime) / animationDuration);
|
||||||
if (ai >= 0.95) {
|
if (ai >= 0.999f) {
|
||||||
ai = -1;
|
ai = -1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
3
TMessagesProj/src/main/res/anim/decelerate_cubic.xml
Normal file
3
TMessagesProj/src/main/res/anim/decelerate_cubic.xml
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<decelerateInterpolator xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
|
android:factor="1.5" />
|
@ -1,15 +1,31 @@
|
|||||||
<?xml version="1.0" encoding="utf-8"?>
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
<set xmlns:android="http://schemas.android.com/apk/res/android">
|
<set xmlns:android="http://schemas.android.com/apk/res/android">
|
||||||
<scale android:fromXScale="0.9"
|
<!--<scale-->
|
||||||
android:fromYScale="0.9"
|
<!--android:fromXScale="0.9"-->
|
||||||
android:toXScale="1.0"
|
<!--android:fromYScale="0.9"-->
|
||||||
android:toYScale="1.0"
|
<!--android:toXScale="1.0"-->
|
||||||
android:pivotX="50%"
|
<!--android:toYScale="1.0"-->
|
||||||
android:pivotY="50%"
|
<!--android:pivotX="50%"-->
|
||||||
android:duration="150"/>
|
<!--android:pivotY="50%"-->
|
||||||
|
<!--android:interpolator="@android:anim/decelerate_interpolator"-->
|
||||||
|
<!--android:duration="220"/>-->
|
||||||
|
|
||||||
|
<!--<alpha android:fromAlpha="0.0"-->
|
||||||
|
<!--android:toAlpha="1.0"-->
|
||||||
|
<!--android:interpolator="@android:anim/decelerate_interpolator"-->
|
||||||
|
<!--android:duration="@android:integer/config_mediumAnimTime" />-->
|
||||||
|
|
||||||
|
|
||||||
<alpha android:fromAlpha="0.0"
|
<alpha
|
||||||
|
android:fromAlpha="0.0"
|
||||||
android:toAlpha="1.0"
|
android:toAlpha="1.0"
|
||||||
android:duration="150" />
|
android:interpolator="@anim/decelerate_cubic"
|
||||||
|
android:duration="220"/>
|
||||||
|
|
||||||
|
<scale
|
||||||
|
android:fromXScale=".8" android:toXScale="1.0"
|
||||||
|
android:fromYScale=".8" android:toYScale="1.0"
|
||||||
|
android:pivotX="50%p" android:pivotY="50%p"
|
||||||
|
android:interpolator="@anim/decelerate_cubic"
|
||||||
|
android:duration="220"/>
|
||||||
</set>
|
</set>
|
@ -1,16 +1,34 @@
|
|||||||
<?xml version="1.0" encoding="utf-8"?>
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
<set xmlns:android="http://schemas.android.com/apk/res/android">
|
<set xmlns:android="http://schemas.android.com/apk/res/android">
|
||||||
<scale android:fromXScale="1.0"
|
<!--<scale-->
|
||||||
android:fromYScale="1.0"
|
<!--android:fromXScale="1.0"-->
|
||||||
android:toXScale="0.9"
|
<!--android:fromYScale="1.0"-->
|
||||||
android:toYScale="0.9"
|
<!--android:toXScale="0.9"-->
|
||||||
android:pivotX="50%"
|
<!--android:toYScale="0.9"-->
|
||||||
android:pivotY="50%"
|
<!--android:pivotX="50%"-->
|
||||||
android:interpolator="@android:anim/accelerate_decelerate_interpolator"
|
<!--android:pivotY="50%"-->
|
||||||
android:duration="150"/>
|
<!--android:interpolator="@android:anim/decelerate_interpolator"-->
|
||||||
|
<!--android:duration="220"/>-->
|
||||||
|
|
||||||
<alpha android:fromAlpha="1.0"
|
<!--<alpha-->
|
||||||
|
<!--android:fromAlpha="1.0"-->
|
||||||
|
<!--android:toAlpha="0.0"-->
|
||||||
|
<!--android:interpolator="@android:anim/decelerate_interpolator"-->
|
||||||
|
<!--android:duration="220" />-->
|
||||||
|
|
||||||
|
<alpha
|
||||||
|
android:fromAlpha="1.0"
|
||||||
android:toAlpha="0.0"
|
android:toAlpha="0.0"
|
||||||
android:interpolator="@android:anim/accelerate_decelerate_interpolator"
|
android:interpolator="@anim/decelerate_cubic"
|
||||||
android:duration="150" />
|
android:duration="220"/>
|
||||||
|
|
||||||
|
<scale
|
||||||
|
android:fromXScale="1.0"
|
||||||
|
android:toXScale=".8"
|
||||||
|
android:fromYScale="1.0"
|
||||||
|
android:toYScale=".8"
|
||||||
|
android:pivotX="50%p"
|
||||||
|
android:pivotY="50%p"
|
||||||
|
android:interpolator="@anim/decelerate_cubic"
|
||||||
|
android:duration="220"/>
|
||||||
</set>
|
</set>
|
BIN
TMessagesProj/src/main/res/drawable-hdpi/burn.png
Executable file
BIN
TMessagesProj/src/main/res/drawable-hdpi/burn.png
Executable file
Binary file not shown.
After Width: | Height: | Size: 2.8 KiB |
BIN
TMessagesProj/src/main/res/drawable-ldpi/burn.png
Executable file
BIN
TMessagesProj/src/main/res/drawable-ldpi/burn.png
Executable file
Binary file not shown.
After Width: | Height: | Size: 1.8 KiB |
BIN
TMessagesProj/src/main/res/drawable-mdpi/burn.png
Executable file
BIN
TMessagesProj/src/main/res/drawable-mdpi/burn.png
Executable file
Binary file not shown.
After Width: | Height: | Size: 2.1 KiB |
BIN
TMessagesProj/src/main/res/drawable-xhdpi/burn.png
Executable file
BIN
TMessagesProj/src/main/res/drawable-xhdpi/burn.png
Executable file
Binary file not shown.
After Width: | Height: | Size: 3.6 KiB |
BIN
TMessagesProj/src/main/res/drawable-xxhdpi/burn.png
Executable file
BIN
TMessagesProj/src/main/res/drawable-xxhdpi/burn.png
Executable file
Binary file not shown.
After Width: | Height: | Size: 5.1 KiB |
Loading…
Reference in New Issue
Block a user