TIP: Append to running lists with the "Add to list" action


#4

Swipe to the right on an action to get to its “Edit” screen. Details here.

You’ll need to tap on the steps, then the script step…the lines you are looking to modify are at the top of the script and look like:

// EDIT THIS
// setup categories available
const categories = ["Movies", "TV Shows", "Blog Ideas"];

// EDIT TAG
// tag to assign to list drafts
const listTag = "lists";

If you are not familiar with scripting it can look a little intimidating, but it’s not too bad. The categories is an array, and is just a comma-separated list of quoted strings. You can have as many or as few categories as needed.


#5

Thank you, both of you :slight_smile: I reckon I could get the hang of that!


#6

Thanks for this script, It will definitely see a lot of use… one question though: is there any way to add multiple items at once? Example: if I am with a friend who says “you really need to see x, y, and z” how can I modify the script to accept data points from multiple successive lines?
Thanks in advance,


#7

Javascript’s standard Array.map can take an existing function on a single string, and apply it to a whole list of strings.

For example:

d.content = d.content + currentContent
.split('\n')
.map(x => '- [ ] ' + x)
.join('\n'),

Used in context:

Full source for an Add *All* to List variant – click to expand
(() => {
    'use strict';

    // Based on an original script by @agiletortoise

    /*
      Ask for a category, and append to a 
      tagged list for that category
    */

    // EDIT THIS
    // setup categories available
    const
        categories = ['Movies', 'TV Shows', 'Blog Ideas'],

        // EDIT TAG
        // tag to assign to list drafts
        listTag = 'lists',

        // grab text
        currentContent = draft.content.trim(),

        // A prompt for selecting an item from a list.
        p = categories.reduce(

            // Accumulator updates - a button added for 
            // each category in the list:
            (prompt, buttonName) => {
                prompt.addButton(buttonName);
                return prompt;
            },

            // Initial accumulator: a prompt with properties:
            Object.assign(
                Prompt.create(), {
                    title: 'Select list:',
                    message: 'Ask for a category, and append' +
                        ' to a tagged list for that category',
                    isCancellable: true
                }
            )
        );

    return p.show() ? (() => {
        const
            category = p.buttonPressed,

            // query for list drafts...
            drafts = Draft.query(category, 'inbox', [listTag]),

            // index of first draft that matches a condition
            iDraft = drafts.findIndex(
                draft => draft.content.startsWith('## ' + category)
            ),

            d = iDraft !== -1 ? (
                drafts[iDraft]
            ) : Object.assign(
                Draft.create(), {
                    content: '## ' + category + '\n\n'
                });

        return (
            // tag and update content
            d.addTag(listTag),

            d.content = d.content + currentContent
            .split('\n')
            .map(x => '- [ ] ' + x)
            .join('\n'),

            d.update(),
            console.log(true)
        );
    })() : (
        context.cancel(),
        console.log(false)
    );
})();

JS :: Building prompts with Array.reduce and Object.assign
#8

Is there a way to cross off [x] items e.g. from a shopping list?


#9

They are tappable task marks. Is that what you are asking?


#10

Experimenting with a version that:

  • collects the category names from the top of the list drafts
  • adds a prompt to create a new category / list draft

Not listed, so it doesn’t step on Greg’s example, but you can look at it here.


#11

Yes I have those. But to delete the ones done. I.e. in a shopping list it deletes the items you have picked up leaving the ones you need, when you next open the note.
Hope that makes sense.


#12

Great addition. Thanks.


#13

This is great, thanks!


#14

You can modify this action that I created which moves the done tasks to the bottom of the list to do what you need.


#15

Re the final lines of that action

begin = begin.slice(0,-1);
end = end.slice(0,-1);
editor.setText(begin + "\n" + end);
d.update;
editor.focus(d);
  • My understanding is that update is a method, so presumably it needs to be called with a trailing parentheses ? d.update()

(rather than just evaluating to a function value ?)


#16

Is it possible to run this script without the check boxes?


#17

You know what I’d like here? I’d like the action to turn each listed item into a tappable link to search Google or Duck Duck Go so when I later come back to the list it’s easy to look up whatever the thing is.


#18

This great thanks appreciated.


#19

Is there a way to adapt this script to prepend rather than append text to an existing draft? I keep a running list of favourite quotes with the most recent at the top. At the moment when I open the draft each time and the cursor default to the end of the text. I’ve had a look but coding isn’ t my strong point!

Thanks in advance.

Euan


#20

Yes, it’s certainly possible to alter the script to put new list items at the top. A little more complex if you want to maintain the heading, since the script would have to local the right insertion point, not just tack text on the top.

Not restoring the last cursor position is a bug in the current release which will be fixed in the next update.


#21

No heading so that’s not a problem but some idea of how to modify the script to prepend would be good.

Thanks!


#22

I updated my tweaked version of this action:

  • new Add option to append or prepend items to a list.

  • Collect list names from tagged drafts.

  • Create new lists inside the action.

Action directory: https://actions.getdrafts.com/a/1Gd


#23

Can you add in the description and code comments that to identify a list, the set tag (e.g. lists) and ## header is required?

Thanks for the fork!