Streams: exploring ideas for new features

Thank you @joshuafontany. Out of curiosity, are you familiar with those particular keyboard shortcuts from elsewhere? https://defkey.com/ was not much help in figuring out if there is an existing UX pattern that we can adopt for such behaviour.

Other ideas under consideration include small sub-plugins that:

Preview of a very early take on searching in a Stream:
streams-search

4 Likes

I have been working with Adobe products a lot recently (book layout & photo retouching), & these were just off the top of my head. I know Ctrl+Shift+S is “Save As…”, not sure where I’ve seen the 4 button one - but it seems complicated to me atm.

I think there would be a better option, but I’d need to refamiliarize myself with the current TW keycodes.

2 Likes

The dynamic Stream search demo is very nifty @saqimtiaz! I think I will be using this!

I think I have customized just about every list (e.g. Recent, backlinks) to show only the root tiddler’s title. The filter operators that come with Streams make that very easy to do.

1 Like

I am quite pleased with how that is turning out. It is only about 30 lines of code and adds zero extra complexity or performance drawbacks to the main Streams plugin. We just hide the nodes that don’t match using CSS.

I am now contemplating UI related decisions, namely whether to introduce an area at the top of a stream for stream wide interface elements like the search and buttons to expand and collapse all the nodes, which can also be used by sub-plugins like Streams-Fusion or the above mentioned Search-in-Streams.

I agree, however it seems a lot of users find these customizations intimidating.

The filter operators are indeed useful. One of the recent user questions I have had was how to find the nearest common ancestor of two nodes:

[<tiddlerA>get-stream-root:includeall[]] :intersection[<tiddlerB>get-stream-root:includeall[]] :and[last[1]]

2 Likes

I am getting close to beta testing for a new release of Streams.

A UX design question that needs answering is where to place global affordances for features that relate to the entire stream and not just to individual nodes, such as expand/collapse all or searching in the stream.

One idea is an area above the stream where such controls can be added via an extensible mechanism. The concern is that this might be visually discordant, especially when the root tiddler has body text.
stream-above-nodes

An alternative is to extend the context menu with a section for global commands, where for example the search option when triggered displays a search bar above the stream, which can be closed after the search. Currently all context menu commands are specific to the node on which the context menu is triggered, so this would be a change in that regard.
Mockup:

image

Alternative layout and visual design ideas are welcome.

5 Likes

If I had to choose one method, I would choose the context menu so that I can long press to access it on my phone.

Looking forward to the beta!

I have found that what would be useful is a way to toggle the display of the body and or the stream - with the stream indicating if it has any content when closed. Sometimes I summarise what I plan to do in the stream within the text field, but once underway I just want to hide the body and view the stream and vici versa. Its a bit like a selective fold feature.

  • Mention it now because perhaps this too could be toggled - just show it at the top and provide a toggle to move it to the context menu?
  • A custom stream button on the view toolbar with a dropdown could even be used to start a stream on the current tiddler, toggle the streams display and provide the features you are exposing.
  • Me personally I would prefer them on the top, and to the left, and the opportunity to indicate it is a stream, but thats just me.

Those features look exciting :nerd_face:

Hi @Tiddlybob, can I ask why you feel the context menu option would be more usable on phones than the controls above the stream? Thank you.

@saqimtiaz When I first read your comment this morning, for some reason I thought that all of the controls on the parent header only showed up on hover, in which case a context menu would be more accessible for mobile. Now that I look back and see the persistent buttons, I think the first method would be a bit easier on mobile.

That being said… I agree that the first option might be visually discordant. What do you think about including an ellipsis that triggers the context menu for the parent header? That might help keep the UI uncluttered, while also providing a visual cue to the extended options.

Sorry to be late to this conversation; have been away from TW, mainly for want of exactly this: an agile outliner that integrates reasonably well with TiddlyWiki (absent that, my go-to notetaking app remains DynaList).

What it would take to make this work for me is two simple enhancements to existing functionalities -essentially:

  1. When i click the Fuse button that collapses a set of outline nodes into a single TiddlerName_fused tiddler, then all those separate node-tiddlers should be deleted -either automatically, or else by giving me a one-click option to do so.
  2. Given a view of all those cryptically-named node-tiddlers, i’d like to be able to shift-select any combination, or select all, and delete with a single click.

For all the sense this makes from my own UX experience, i guess from Developer perspective it’s more complicated, seeing as how it involves 2 plugins (Streams and Streams Fusion, AFAIK) for 1st point above, and maybe core UI element(s) for the 2nd… And may even run counter to the TW philosophy of “everything’s a tiddler,” which may imply having a tiddler for everything. I get that, in principle, but still…

Much as i appreciate the experience of agile-outlining in TW via Streams, then organising & saving the work to one or more well-named tiddlers as appropriate via Streams Fusion, all that joy evaporates when i contemplate the mess of tiddlers in my Recent list, whose names mean nothing to me, yet i must then click each one and pull down to delete each one individually.

Perhaps there’s a better workflow within the product as it stands that i am failing to see?
If so, perhaps it could be made more obviously accessible with some contextual help affordance.

Anyway: kudos to you both, @saqimtiaz & @fastfreddy , on this dynamite plugin combo; am happy to see that development continues -especially regarding that sub-plugins idea Saq presented above, which might be away to address my little wish-list above (?).

/walt

I like both! Not helpful to you in deciding, but an affirmation nonetheless.

1 Like

Hi Walt,

First off, no need to change what works for you if you are happy!

That sounds easily doable in Fusion. If Fuse creates a new tiddler, you can go back to the original tiddler and delete it, it will ask you if you also want to delete its children.

Is this instead of the above or in addition to? What is the use case?

The issue is that Streams started life as a technology demo and due to user demand became a plugin. What it really needs is a custom made edition around it, that is a customised TiddlyWiki.

Some users try to clean up the timeline by removing the child nodes by configuring their titles to start with $:/. This is suboptimal is it also excludes them from search. What makes sense is to customize search and the timeline to show the stream-root tiddler for each node that might otherwise be shown in the results. You don’t care or want to know which node tiddler changed, you want to see the name of the root tiddler that it belongs to. This is easy to do with the filters that come with stream, but requires customizing core tiddlers and therefore is not something that comes with the plugin.

1 Like

Hi Walt, not sure I follow this point:

  1. When i click the Fuse button that collapses a set of outline nodes into a single TiddlerName_fused tiddler, then all those separate node-tiddlers should be deleted -either automatically, or else by giving me a one-click option to do so.

Streams-fusion lets you fuse and overwrite, is that not what you need?

image

For this other point:

  1. Given a view of all those cryptically-named node-tiddlers, i’d like to be able to shift-select any combination, or select all, and delete with a single click.

I use <$macrocall $name="unusedtitle" baseName=<<parent>> separator="/" /> as template to name Streams node. It is then relatively easy to find (and delete) matching nodes using Tiddler Commander, which lets you filter and select, before deleting.

1 Like

Ah… that does indeed solve part of the problem: when i want to append the entire fused stream at bottom of current tiddler (not overwrite: because i never wanted to do that, and aksi because of the pop-up warning on selection of this option, i never really tried this function). Thanks @fastfreddy for the useful pointer!

Interesting! So: if i want to delete all Streams nodes at the end of a session (during which i should have fused all Streams content to some tiddler or other), what would be a search string that would reveal all those now-superfluous nodes in a Tiddler Commander list view, for easy select-all & delete?

Yes… That is certainly easier than trying to find and delete the parent + allChildren, given the non-intuitive naming algorithm, tho it still involves can involve too many clicks, depending how many top-level nodes+children you have to delete.

UseCase: Typically, i will start my day with a Journal tiddler, and then quickly bang-out an outline of Appointments i must keep, Projects i intend to work on, an “Inbox” of whatever random things may materialise & need to be integrated… Perhaps related to some Project or Appointment or some Reference node, which may take more thinking than i can afford at the moment. This can quickly (depending how caffeinated i may be :coffee: ) develop into quite a bushy tree, which warrants quite a lot of pruning and/or transplanting of scions from original rootstock (sorry for the run-on ag metaphor, but that’s what i do IRL :tractor: ).

SO, in answer to your Q @saqimtiaz: i think this item #2 on my list is in addition to item #1. Because i don’t like leaving my workspace in a mess from one day to the next, i need an easy way to simply disappear all those nodes that haven’t found their proper home in body text of some tiddler or other. This could perhaps be accomplished via some smart filtering in Tiddler Commander, per @fastfreddy suggestion… .Or perhaps in a more elegant fashion (not requiring use of some additional plugin) building on this feature you talk about developing…

Yes! If the search function could show me just stream-root tiddlers, screening out all those algorithmically-named child nodes (tho it would be great if it could show me a count of them beside the parent), that could really help.

Hm: a customised edition… Makes sense, now that think of it. Like Soren’s Zettelkasten, this hybrid amalgam of wiki+outlining functionalities is powerful & complex enough, it really warrants that sort of treatment. I’ve got a lot more to learn, before i could contribute any substantial help to such an effort, but- while struggling my way up the learning curve -i am happy to be engaged in this conversation!

The filter to find all of a Stream’s nodes is relatively easy: something like
[[prefix[basename]] should work. By basename, I use the root tiddler’s name.

For example, a root tiddler named demo, this will work:

It is relatively easy to modify a few tiddlers to improve search results handling of Streams. Here are my recipes:

  1. to improve general and advanced search compatibility with Streams (updated to avoid leveraging deprecated tiddlers from Deprecated — do not use (August 24th, 2021))
  • clone $:/core/ui/DefaultSearchResultList into $:/plugins/sq/streams-search/StreamSearchResults
  • change the new tiddlers’ caption to “Streams”
  • edit the fields first-search-filter and second-search-filter to insert get-stream-root[] after sort[]
  • edit $:/config/SearchResults/Default to $:/plugins/sq/streams-search/StreamSearchResults
  1. to improve recent view and tag view compatibility with Streams (and only show root tiddler names):
  • add a subfilter in $:/core/ui/SideBar/Recentand in $:/core/ui/MoreSideBar/Recent to <$macrocall $name="timeline" format={{$:/language/RecentChanges/DateFormat}} subfilter="get-stream-root[]"/>
  • modify $:/core/ui/TagTemplateto include the get-stream-root[] subfilter
<$macrocall $name="list-tagged-draggable" subfilter="get-stream-root[]" tag=<<currentTiddler>>/>
1 Like

Thanks @fastfreddy for the tip:

Works like a champ!

Dunno about the rest- i steer well clear of anything starting with ‘$:/core’ ,as a rule -but you guys have given me plenty to work with here, so i’m happy today :smiley:

/walt

Hi @saqimtiaz, I’ve been trying to hack together a poor-person’s version of the Stream search/filter feature showcased above, until the new features are ready/released.

It works wells of far, but my success is limited to first level text match. How do you handle the matching of text in subordinate nodes? You probably have already thought through that.

Am I right in suspecting you need to show the full hierarchy of subordinate notes that match the search string?

What about folded nodes?

Thanks in advance!

I should be able to get a beta release published for testing in about two weeks time.

Could you elaborate what the problem is? Search all nodes of the root tiddler for the text, for each matching node also display all ancestors but only highlight the nodes with results.

For all nodes that have matching text, force the display of all ancestors.