Skip to content

Latest commit

 

History

History
342 lines (250 loc) · 12.3 KB

notes.org

File metadata and controls

342 lines (250 loc) · 12.3 KB

Bufler notes

[#A] Contents

[#B] Ideas

Automatically detect current buffer’s workspace and prioritize its buffers when using bufler-switch-buffer

For the case where the user hasn’t set the current frame’s workspace, the bufler-switch-buffer command could automatically find the group the current buffer is in and sort other buffers from that group first.

Add Mike Zamansky’s video to readme

Multiple Bufler buffers

i.e. call Bufler like (bufler :groups GROUPS :buffer-name "*Matrix Bufler*"), and those variables should be set buffer-locally, and refreshing should use those values instead of the global ones. That would allow multiple, unique Bufler buffers.

Rename some things

e.g. the grouping rules should probably be rules rather than groups, to distinguish the rules from the groups of buffers that they produce.

Try to improve vc-state

Here’s a common scenario:

  1. bufler-list.
  2. Switch to a buffer showing a file in a project.
  3. Make changes, save file, switch to magit-status, commit.
  4. bufler-list. Even though the file is now up-to-date, it shows as edited because vc-state only gets updated when the buffer is saved, and the buffer hasn’t been saved since it was committed.

Unfortunately, calling vc-state-refresh every time bufler-list is updated seems far too slow.

Depend on project 0.3.0 and use project-root instead of project-roots

project is on ELPA, and the version there is newer than the one included with Emacs 26.3, and it declares project-roots obsolete.

Testing

Can probably use with-simulated-input to do some testing, which will help with refactoring.

Buffer/group sorting

The WIP branch works pretty well already.

[2021-09-22 Wed 02:49] Using taxy will make this much simpler.

Sortable columns

Should be covered with taxy-magit-section, when sorting columns is added to it.

Integrate bufler-workspace-mode with tab-bar-mode

Rather than replacing the tab-bar-tabs-function and having Bufler groups be the only tabs displayed in the tab bar, selecting a Bufler group would add a tab to the bar, prefixed with Bflr:. Selecting that tab would set the frame’s bufler-workspace-path (probably by advising tab-bar-switch-to-tab). There also needs to be an easy way to make a new tab for a Bufler group.

Selecting a tab bar tab would also cause the tab line to only display buffers in that tab’s Bufler group.

I think this would generally be more useful than the current implementation, but it means completely changing the design.

Also, I’m noticing that the tab bar redisplays from scratch every time Emacs does (i.e. on every keystroke, scroll event, etc.), so having bufler-workspace-mode active makes redisplay slow. The code will need to be very optimized, and it might need another cache of some kind.

Use tree-widget for displaying hierarchies

Jonas Bernoulli uses it in epkg-desc.el, and it looks very nice. However, I’m guessing there are reasons he made or uses magit-section instead.

Of special interest is how it uses display properties to align text in columns. That might be a good alternative to using format for alignment.

Use tab-line-tabs-buffer-group-function

e.g. see Amit’s Thoughts: Emacs: prettier tab-line.

Non-consuming grouping option

The idea to have buffers appear in multiple groups which they match was mentioned in this comment by Gerry Agbobada. Here’s a rough concept of how the alternative to bufler-group-tree could work.

(defun group-tree-non-consuming (fns sequence)
  (cl-labels ((rec (fns sequence)
                   (cl-loop for fn in fns
                            collect (pcase fn
                                      ((pred functionp)
                                       (cons fn (cl-loop for item in sequence
                                                         when (funcall fn item)
                                                         collect item)))
                                      (`(,(and (pred stringp) label) ,(and (pred functionp) fn))
                                       (cons label (cl-loop for item in sequence
                                                            when (funcall fn item)
                                                            collect item)))
                                      ((pred listp)
                                       (cons (get-label (car fn))
                                             (rec (cdr fn) (cl-remove-if-not (get-fn (car fn)) sequence)))))))
              (get-fn (fn)
                      (pcase-exhaustive fn
                        (`(,(pred stringp) ,(pred functionp))
                         (cadr fn))
                        ((pred functionp)
                         fn)))
              (get-label (fn)
                         (pcase-exhaustive fn
                           (`(,(and (pred stringp) label) ,(pred functionp))
                            label)
                           ((pred functionp)
                            fn))))
    (rec fns sequence)))

(cl-labels ((<5-p (n) (< n 5)))
  (group-tree-non-consuming (list (list (list "< 5" #'<5-p)
                                        (list "even" #'evenp)
                                        (list "non-zero" (-not #'zerop)))
                                  #'evenp)
                            '(0 1 2 3 4 5 6 7 8 9)))
;; (("< 5"
;;   ("even" 0 2 4)
;;   ("non-zero" 1 2 3 4))
;;  (evenp 0 2 4 6 8))

CANCELED Use group-tree-defmacro

Was working fine in the prototype, so it should work fine here too. But I want to release 0.2 before making any changes like this.

[2021-09-22 Wed 02:44] Will be covered by using taxy.

CANCELED Keyword arguments to groups

e.g. instead of:

(group-not "*Special*" (group ...) ...)

Something like:

(group-not :name "*Special*" (group ...) ...)

Which should also allow:

(group-not (group ...) ...)

That would provide a lot of flexibility.

[2021-09-22 Wed 02:44] Will be covered by using taxy.

CANCELED Use cl-loop instead of -any? and -all?

In these functions. I’d expect cl-loop to be faster.

(defun bufler-and (name &rest preds)
  ;; Copied from dash-functional.el.
  "Return a grouping function that groups buffers matching all of PREDS.
The resulting group is named NAME. This can also be used with a
single predicate to apply a name to a group."
  (byte-compile (lambda (x)
                  (when (-all? (-cut funcall <> x) preds)
                    name))))

(defun bufler-or (name &rest preds)
  ;; Copied from dash-functional.el.
  "Return a grouping function that groups buffers matching any of PREDS.
The resulting group is named NAME."
  (byte-compile (lambda (x)
                  (when (-any? (-cut funcall <> x) preds)
                    name))))

[2021-09-22 Wed 02:45] Will be covered by using taxy.

CANCELED bufler-defpred

From comment:

  • A macro like bufler-defpred would define a grouping predicate. It would define a function like bufler--predicate-NAME, and it would add its macrolet form to a variable like bufler-predicates.
  • A function like bufler-define-expand-groups would define a function bufler-expand-groups which would splice in the predicate macrolet forms into the cl-macrolet form.
  • Users would do something like (setf bufler-groups (bufler-expand-groups ...)).
  • New groups could be added with bufler-defpred, which would also call bufler-define-expand-groups to redefine the expansion function to include the new predicate.

[2021-09-22 Wed 02:49] Will be covered using taxy.

CANCELED Factor out GUI code

There should be a companion library to group-tree that provides the section-based view with columns.

[2021-09-22 Wed 02:52] Covered by taxy-magit-section.

Name

Bufler

Sort of like “buffer butler.” Maybe a buffalo for a mascot?

…Yep, works great!

Mr. Buffer

Sort of cute and catchy. Maybe some clip art available.

Pass ACTION argument to pop-to-buffer

As Mike Zamansky mentioned, it would be nice to be able to control how the bufler-list window opens.

[#B] Plans

0.2

Release 0.2

  • [X] Check comment TODOs (using magit-todos).
  • [X] Check issues.
  • [X] Check plans (in this file).
  • [X] Check linters.
  • [X] Check tests.
  • [X] Update version numbers in file headers.
    • [X] bufler.el
    • [X] helm-bufler.el
  • [X] Tag and sign new version (using Magit’s t r).
  • [X] Push master.
  • [X] Push tags.
  • [X] Post-release changes:
    • [X] Bump version numbers to n+1-pre:
      • [X] bufler.el
      • [X] helm-bufler.el
      • [X] README.org

Prefix to bufler-list to clear cache

Sometimes changing bufler-groups doesn’t seem to take effect because buffer-list hasn’t changed and bufler-buffers is cached.

Explain the big 4 features

I think the big 4 features now are basically:

  1. bufler-list
  2. bufler-switch-buffer
  3. bufler-workspace-mode
  4. bufler-tabs-mode

And while they all work together, they can also be used independently. bufler-list and bufler-switch-buffer don’t even require bufler-workspace-mode to be activated.

References

[#C] Checklists

TEMPLATE Release

  • [ ] Check comment TODOs (using magit-todos).
  • [ ] Check issues.
  • [ ] Check plans (in this file).
  • [ ] Check linters.
  • [ ] Check tests.
  • [ ] Update version numbers in file headers.
    • [ ] bufler.el
    • [ ] helm-bufler.el
    • [ ] README.org
  • [ ] Update changelog in README.org.
  • [ ] Tag and sign new version (using Magit’s t r).
  • [ ] Push master.
  • [ ] Push tags.
  • [ ] Post-release changes:
    • [ ] Bump version numbers to n+1-pre:
      • [ ] bufler.el
      • [ ] helm-bufler.el
      • [ ] README.org

[#C] COMMENT Config

Org settings

File-local variables