Adding and subtracting times with core TiddlyWiki functionality

I am trying to accomplish a logbook functionality in TiddlyWiki where I am able to list Tiddlers and calculate various aggregated times.

So far I have been unsuccessful in accomplishing the following:
Say that we have the tiddlers

Tiddler A with fields
time 1: 10:10
time 2: 11:05

and Tiddler B with fields
time 1: 09:45
time 2: 10:05

Now I want to be able to write a filter which selects returns the time difference between time 1 and time 2 and then summed, which would return 0:55 + 0:20 = 1:15 in this example.

Is this possible with just core TiddlyWiki functionality or do I have to write my own Javascript macros and/or filter operators? I would like to avoid relying on having to store states in fields or temporary tiddlers if possible.

Welcome @emil to talk.tiddlywiki.org.

If these times are always on the same day this should be achievable, you just need to detect when hours exceed 23 or are less than 0, minutes greater than 59 and less than zero.

However you may find something to help in this large collection of great time and date tools by Eric. You may find it easier to use these tools to set ands manage the times. Otherwise date and time calculations can be done with other plugins.

I will add additional resources if I can.

Hi Emil,
here’s the link:
https://tiddlytools.com/timer.html

Thanks.

I will try to specify my question.

I have created a macro to substitute the time duration between t1 and t2:

\define tdiff(t1, t2)
\whitespace trim
<!-- Returns the duration between t1 and t2 in minutes -->
<$vars    h1={{{ [[$t1$]split[:]nth[1]multiply[60]] }}}
          h2={{{ [[$t2$]split[:]nth[1]multiply[60]] }}}
          m1={{{ [[$t1$]split[:]nth[2]] }}}
          m2={{{ [[$t2$]split[:]nth[2]] }}}>

<$text text={{{ [<h2>subtract<h1>add<m2>subtract<m1>] }}} />

\end

Now I want to be able to write a filter which returns the accumulated time difference in tiddlers specified by the filter.

Something like

{{{ [[Tiddler A] [Tiddler B] :map[tdiff[t1], [t2]] :reduce[add<accumulator>] }}}

which obviously doesn’t work.

I could wrap the filter expression in a list widget but then I don’t know how to sum the results. I could also store the time duration in minutes in a field in the respective tiddler but I want to avoid that since t1 and t2 should be enough information to do the calculations.

From what I understand https://tiddlytools.com/timer.html relies on button actions to store durations. I want to avoid that if possible as I want to be able to change t1 for example and have all calculations update automatically.

I finally found a solution which works for me. I’m sharing it here in case anyone is interested.

The key thing for me was to realise that a recursive macro was the way to go. Thanks to this example for the inspiration.

\define time-sum(filt: "[all[tiddlers]has[time 1]]", accumulator: "0", count: "0")

<$list filter="[<__count__>match[0]]">
  <$let count = {{{ $filt$ +[count[]] }}}>
  <$macrocall $name=recursive-time-add accumulator=<<accumulator>> count=<<count>> filt=<<__filt__>>/>
\end

\define recursive-time-add(filt: "[all[tiddlers]has[time 1]]", accumulator:"0", count:"1")

<$list filter="[<__count__>!match[0]]">

<!-- Determine time difference and accumulated value -->
<$let  count = {{{ [<__count__>subtract[1]] }}}
       title = {{{ $filt$ +[nth<__count__>] }}}
       hacc = {{{ [<__accumulator__>split[:]nth[1]] }}}
       macc = {{{ [<__accumulator__>split[:]nth[2]] }}}
       h1 = {{{ [<title>get[time 1]split[:]nth[1]] }}}
       h2 = {{{ [<title>get[time 2]split[:]nth[1]] }}}
       m1 = {{{ [<title>get[time 1]split[:]nth[2]] }}}
       m2 = {{{ [<title>get[time 2]split[:]nth[2]] }}}
       mdiff = {{{ [<m2>subtract<m1>add[60]remainder[60]pad[2]] }}}
       m2h = {{{ [<m2>subtract<m1>divide[60]floor[]] }}}
       hdiff = {{{ [<h2>subtract<h1>add[24]remainder[24]add<m2h>] }}}
       maccnew = {{{ [<macc>add<mdiff>add[60]remainder[60]pad[2]] }}}
       m2hacc = {{{ [<macc>add<mdiff>divide[60]floor[]] }}}
       haccnew = {{{ [<hdiff>add<hacc>] }}}     
       accumulator = {{{ [<haccnew>addsuffix[:]addsuffix<maccnew>] }}}>

<!-- Print time difference and accumulated value -->
<<hdiff>>:<<mdiff>>,
<<accumulator>>

<!-- Recursively add next item in list -->
<$macrocall $name=recursive-time-add accumulator=<<accumulator>> count=<<count>> filt=<<__filt__>>/>

<$list filter="[<__count__>match[1]]">

Total: <<accumulator>>

\end

<<time-sum "[tag[Log]]">>

I’m still figuring out how to comfortable break out functionality into multiple sub-macros. It’s hard to break the notion of treating macros as functions and avoiding macro calls in attribute assignments.