Deprecated: Return type of I::current() should either be compatible with Iterator::current(): mixed, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /home/public/kirby/toolkit/lib/i.php on line 62

Deprecated: Return type of I::next() should either be compatible with Iterator::next(): void, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /home/public/kirby/toolkit/lib/i.php on line 91

Deprecated: Return type of I::key() should either be compatible with Iterator::key(): mixed, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /home/public/kirby/toolkit/lib/i.php on line 71

Deprecated: Return type of I::valid() should either be compatible with Iterator::valid(): bool, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /home/public/kirby/toolkit/lib/i.php on line 101

Deprecated: Return type of I::rewind() should either be compatible with Iterator::rewind(): void, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /home/public/kirby/toolkit/lib/i.php on line 53

Deprecated: Return type of Collection::count() should either be compatible with Countable::count(): int, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /home/public/kirby/toolkit/lib/collection.php on line 80

Deprecated: parse_str(): Passing null to parameter #1 ($string) of type string is deprecated in /home/public/kirby/toolkit/lib/url.php on line 135
One Tap Less | Do next with Due

Do next with Due

Hey, missed me? Sorry for posting so many links this week, but I've been kinda busy. To make it up to you, I thought we could workout a little bit with Due, Drafts and Pythonista. This time we'll create a reminder at any time without relying on natural language. Because I hate natural language on iOS.

Even if this is not of your interest, we'll learn a lot from this article. You may remember that in a previous article I taught you how to create Due reminders on saturday noon regardless of the actual weekday. Now we'll move one step forward, I'll let you customize your alarm.

This is how we'll roll: you'll create your reminder in Drafts with no limitation of lines as long as your last line is the alarm time. There's some fancy stuff here too: a time is a 4-digit string, 2 for the hour and 2 for the minute, but if you want to set an alarm to 1pm, you can just type 13. You can also skip the first 0 if you're looking for a morning alarm. If you screw up your input completely, the script will prompt you to type a valid 4-digits date.

from urllib import quote
import time
from webbrowser import open
from console import input_alert

a = sys.argv[1].split('\n')
reminder = quote('\n'.join(a[:(len(a)-1)]))
t = a[len(a)-1]

def FixTime(f):
    if len(f) == 1:
        return '0' + f + '00'
    elif len(f) == 2:
        return f + '00'
    elif len(f) == 3:
        return '0' + f
    else:
        return f

def AdjustTime(f):
    while True:
        if f.isdigit() and len(f) == 4 and int(f[:2]) <= 23 and int(f[2:]) <= 59:
            return f
        f = input_alert(f + ' is not a valid hour. Type a 4-digit hour')

g = AdjustTime(FixTime(t))

mins = int(g[:2])*60 + int(g[2:])

local = time.localtime().tm_hour*60+time.localtime().tm_min

def findTime():
    if mins > local:
        return mins - local
    else:
        return mins - local + 1440

due = 'due://x-callback-url/add?title=' + reminder + '&minslater=' + str(findTime()) + '&x-source=Drafts&x-success=drafts://'

open(due)

As you know, we use sys.argv[1].split('\n') to convert our full string imported from Drafts using \n to split the content with each paragraph holding a string within a list. This is the coolest thing because using a[len(a)-1] we grab only the last line/item, reversing the title/body template tags from Drafts regardless of the amount of lines in your text.

Afterwards, we define our functions, fixTime(f) will convert your string into a 4-digit value and AdjustTime(f) will check if the hour is valid and prompt you to fix it otherwise1.

Then we convert the outcome into minutes by multiplying the first 2 digits by 60 and adding the last 2. We do the same thing with the local time and call a third function findTime(), which will check the following: if our input time in minutes is more than our local time in minutes, meaning our event is still coming this day, return the interval in minutes. Otherwise, add 1440 minutes to the aftermath, since that hour is gone and we want to set the reminder for the next day.

Then just call Due and everything will be at its right place. If you found it too much trouble, you can keep using the natural language, just remember that you tap one extra time.

Oh, I was almost forgetting, grab the Drafts action below.

Due Next:

pythonista://DueNext?action=run&argv=[[draft]]

If you trust yourself to always type 4 digits, you can skip fixTime(f) and AdjustTime(f). If you hate tapping for the numeric keyboard, you can create a Launch Center Pro action, I just warn you that you won't manage to create the keyboard prompt before the numeric prompt (I tried and it would open the numeric keypad twice). See you next time.


  1. Thank you StackOverflow.