1
0
Fork 0
mirror of https://github.com/deltachat/deltachat-core.git synced 2025-10-06 12:00:11 +02:00

Merge pull request #659 from deltachat/locations-enabled

add dc_chat_is_sending_locations()
This commit is contained in:
björn petersen 2019-04-19 01:54:11 +02:00 committed by GitHub
commit c1206b7c39
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
8 changed files with 102 additions and 10 deletions

View file

@ -11,6 +11,10 @@ your library */
#include "../src/dc_sqlite3.h"
#define UTF8_LOCK "\xF0\x9F\x94\x92"
#define UTF8_BLACK_STAR "\xE2\x98\x85"
#define UTF8_ROUND_PUSHPIN "\xF0\x9F\x93\x8D"
/*
* Reset database tables. This function is called from Core cmdline.
@ -263,11 +267,11 @@ static void log_msg(dc_context_t* context, const char* prefix, dc_msg_t* msg)
dc_log_info(context, 0, "%s#%i%s: %s (Contact#%i): %s %s%s%s%s [%s]",
prefix,
(int)dc_msg_get_id(msg),
dc_msg_get_showpadlock(msg)? "\xF0\x9F\x94\x92" : "",
dc_msg_get_showpadlock(msg)? UTF8_LOCK : "",
contact_name,
contact_id,
msgtext,
dc_msg_is_starred(msg)? " \xE2\x98\x85" : "",
dc_msg_is_starred(msg)? " " UTF8_BLACK_STAR : "",
dc_msg_get_from_id(msg)==1? "" : (dc_msg_get_state(msg)==DC_STATE_IN_SEEN? "[SEEN]" : (dc_msg_get_state(msg)==DC_STATE_IN_NOTICED? "[NOTICED]":"[FRESH]")),
dc_msg_is_info(msg)? "[INFO]" : "",
statestr,
@ -710,11 +714,12 @@ char* dc_cmdline(dc_context_t* context, const char* cmdline)
char* timestr = dc_timestamp_to_str(dc_lot_get_timestamp(lot));
char* text1 = dc_lot_get_text1(lot);
char* text2 = dc_lot_get_text2(lot);
dc_log_info(context, 0, "%s%s%s%s [%s]",
dc_log_info(context, 0, "%s%s%s%s [%s]%s",
text1? text1 : "",
text1? ": " : "",
text2? text2 : "",
statestr, timestr
statestr, timestr,
dc_chat_is_sending_locations(chat)? UTF8_ROUND_PUSHPIN : ""
);
free(text1);
free(text2);
@ -754,7 +759,10 @@ char* dc_cmdline(dc_context_t* context, const char* cmdline)
dc_array_t* msglist = dc_get_chat_msgs(context, dc_chat_get_id(sel_chat), DC_GCM_ADDDAYMARKER, 0);
char* temp2 = dc_chat_get_subtitle(sel_chat);
char* temp_name = dc_chat_get_name(sel_chat);
dc_log_info(context, 0, "%s#%i: %s [%s]", chat_prefix(sel_chat), dc_chat_get_id(sel_chat), temp_name, temp2);
dc_log_info(context, 0, "%s#%i: %s [%s]%s",
chat_prefix(sel_chat), dc_chat_get_id(sel_chat),
temp_name, temp2,
dc_chat_is_sending_locations(sel_chat)? UTF8_ROUND_PUSHPIN : "");
free(temp_name);
free(temp2);
if (msglist) {

View file

@ -388,6 +388,25 @@ int dc_chat_is_self_talk(const dc_chat_t* chat)
}
/**
* Check if locations are sent to the chat
* at the time the object was created using dc_get_chat().
* To check if locations are sent to _any_ chat,
* use dc_is_sending_locations_to_chat().
*
* @memberof dc_chat_t
* @param chat The chat object.
* @return 1=locations are sent to chat, 0=no locations are sent to chat
*/
int dc_chat_is_sending_locations(const dc_chat_t* chat)
{
if (chat==NULL || chat->magic!=DC_CHAT_MAGIC) {
return 0;
}
return chat->is_sending_locations;
}
int dc_chat_update_param(dc_chat_t* chat)
{
int success = 0;
@ -411,7 +430,7 @@ static int set_from_stmt(dc_chat_t* chat, sqlite3_stmt* row)
dc_chat_empty(chat);
#define CHAT_FIELDS " c.id,c.type,c.name, c.grpid,c.param,c.archived, c.blocked, c.gossiped_timestamp "
#define CHAT_FIELDS " c.id,c.type,c.name, c.grpid,c.param,c.archived, c.blocked, c.gossiped_timestamp, c.locations_send_until "
chat->id = sqlite3_column_int (row, row_offset++); /* the columns are defined in CHAT_FIELDS */
chat->type = sqlite3_column_int (row, row_offset++);
chat->name = dc_strdup((char*)sqlite3_column_text (row, row_offset++));
@ -420,6 +439,7 @@ static int set_from_stmt(dc_chat_t* chat, sqlite3_stmt* row)
chat->archived = sqlite3_column_int (row, row_offset++);
chat->blocked = sqlite3_column_int (row, row_offset++);
chat->gossiped_timestamp = sqlite3_column_int64(row, row_offset++);
chat->is_sending_locations = (sqlite3_column_int64(row, row_offset++)>time(NULL));
/* correct the title of some special groups */
if (chat->id==DC_CHAT_ID_DEADDROP) {

View file

@ -25,6 +25,7 @@ struct _dc_chat
int blocked; /**< One of DC_CHAT_*_BLOCKED */
dc_param_t* param; /**< Additional parameters for a chat. Should not be used directly. */
time_t gossiped_timestamp;
int is_sending_locations;
};
int dc_chat_load_from_db (dc_chat_t*, uint32_t id);

View file

@ -152,6 +152,7 @@ uint32_t dc_save_locations (dc_context_t*, uint32_t chat_id, uint
dc_kml_t* dc_kml_parse (dc_context_t*, const char* content, size_t content_bytes);
void dc_kml_unref (dc_kml_t*);
void dc_job_do_DC_JOB_MAYBE_SEND_LOCATIONS (dc_context_t*, dc_job_t*);
void dc_job_do_DC_JOB_MAYBE_SEND_LOC_ENDED (dc_context_t*, dc_job_t*);
// backups

View file

@ -702,6 +702,7 @@ static void dc_job_perform(dc_context_t* context, int thread, int probe_network)
case DC_JOB_CONFIGURE_IMAP: dc_job_do_DC_JOB_CONFIGURE_IMAP (context, &job); break;
case DC_JOB_IMEX_IMAP: dc_job_do_DC_JOB_IMEX_IMAP (context, &job); break;
case DC_JOB_MAYBE_SEND_LOCATIONS: dc_job_do_DC_JOB_MAYBE_SEND_LOCATIONS (context, &job); break;
case DC_JOB_MAYBE_SEND_LOC_ENDED: dc_job_do_DC_JOB_MAYBE_SEND_LOC_ENDED (context, &job); break;
case DC_JOB_HOUSEKEEPING: dc_housekeeping (context); break;
}

View file

@ -22,6 +22,7 @@ extern "C" {
// jobs in the SMTP-thread, range from DC_SMTP_THREAD..DC_SMTP_THREAD+999
#define DC_JOB_MAYBE_SEND_LOCATIONS 5005 // low priority ...
#define DC_JOB_MAYBE_SEND_LOC_ENDED 5007
#define DC_JOB_SEND_MDN_OLD 5010
#define DC_JOB_SEND_MDN 5011
#define DC_JOB_SEND_MSG_TO_SMTP_OLD 5900

View file

@ -473,6 +473,60 @@ void dc_job_do_DC_JOB_MAYBE_SEND_LOCATIONS(dc_context_t* context, dc_job_t* job)
}
void dc_job_do_DC_JOB_MAYBE_SEND_LOC_ENDED(dc_context_t* context, dc_job_t* job)
{
// this function is called when location-streaming _might_ have ended for a chat.
// the function checks, if location-streaming is really ended;
// if so, a device-message is added if not yet done.
uint32_t chat_id = job->foreign_id;
time_t locations_send_begin = 0;
time_t locations_send_until = 0;
sqlite3_stmt* stmt = NULL;
char* stock_str = NULL;
stmt = dc_sqlite3_prepare(context->sql,
"SELECT locations_send_begin, locations_send_until "
" FROM chats "
" WHERE id=?");
sqlite3_bind_int (stmt, 1, chat_id);
if (sqlite3_step(stmt)!=SQLITE_ROW) {
goto cleanup;
}
locations_send_begin = sqlite3_column_int64(stmt, 0);
locations_send_until = sqlite3_column_int64(stmt, 1);
sqlite3_finalize(stmt);
stmt = NULL;
if (locations_send_begin!=0 && time(NULL)<=locations_send_until) {
// still streaming -
// may happen as several calls to dc_send_locations_to_chat()
// do not un-schedule pending DC_MAYBE_SEND_LOC_ENDED jobs
goto cleanup;
}
if (locations_send_begin==0 && locations_send_until==0) {
// not streaming, device-message already sent
goto cleanup;
}
// inform the ui that location-streaming has ended
stmt = dc_sqlite3_prepare(context->sql,
"UPDATE chats "
" SET locations_send_begin=0, locations_send_until=0 "
" WHERE id=?");
sqlite3_bind_int (stmt, 1, chat_id);
sqlite3_step(stmt);
stock_str = dc_stock_system_msg(context, DC_STR_MSGLOCATIONDISABLED, NULL, NULL, 0);
dc_add_device_msg(context, chat_id, stock_str);
context->cb(context, DC_EVENT_CHAT_MODIFIED, chat_id, 0);
cleanup:
sqlite3_finalize(stmt);
free(stock_str);
}
/*******************************************************************************
* high-level ui-functions
******************************************************************************/
@ -516,8 +570,8 @@ void dc_send_locations_to_chat(dc_context_t* context, uint32_t chat_id,
" SET locations_send_begin=?, "
" locations_send_until=? "
" WHERE id=?");
sqlite3_bind_int64(stmt, 1, now);
sqlite3_bind_int64(stmt, 2, now+seconds);
sqlite3_bind_int64(stmt, 1, seconds? now : 0);
sqlite3_bind_int64(stmt, 2, seconds? now+seconds : 0);
sqlite3_bind_int (stmt, 3, chat_id);
sqlite3_step(stmt);
@ -527,16 +581,19 @@ void dc_send_locations_to_chat(dc_context_t* context, uint32_t chat_id,
msg = dc_msg_new(context, DC_MSG_TEXT);
msg->text = dc_stock_system_msg(context, DC_STR_MSGLOCATIONENABLED, NULL, NULL, 0);
dc_param_set_int(msg->param, DC_PARAM_CMD, DC_CMD_LOCATION_STREAMING_ENABLED);
msg->id = dc_send_msg(context, chat_id, msg);
context->cb(context, DC_EVENT_MSGS_CHANGED, chat_id, msg->id);
dc_send_msg(context, chat_id, msg);
}
else if(!seconds && is_sending_locations_before) {
stock_str = dc_stock_system_msg(context, DC_STR_MSGLOCATIONDISABLED, NULL, NULL, 0);
dc_add_device_msg(context, chat_id, stock_str);
}
// update eg. the "location-sending"-icon
context->cb(context, DC_EVENT_CHAT_MODIFIED, chat_id, 0);
if (seconds) {
schedule_MAYBE_SEND_LOCATIONS(context, 0);
dc_job_add(context, DC_JOB_MAYBE_SEND_LOC_ENDED, chat_id, NULL, seconds+1);
}
cleanup:
@ -549,6 +606,8 @@ cleanup:
/**
* Check if location streaming is enabled.
* Location stream can be enabled or disabled using dc_send_locations_to_chat().
* If you have already a dc_chat_t object,
* dc_chat_is_sending_locations() may be more handy.
*
* @memberof dc_context_t
* @param context The context object.

View file

@ -484,6 +484,7 @@ int dc_chat_get_archived (const dc_chat_t*);
int dc_chat_is_unpromoted (const dc_chat_t*);
int dc_chat_is_self_talk (const dc_chat_t*);
int dc_chat_is_verified (const dc_chat_t*);
int dc_chat_is_sending_locations (const dc_chat_t*);
/**