Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

nu-ansi-term overhaul #53

Closed
wants to merge 62 commits into from
Closed

nu-ansi-term overhaul #53

wants to merge 62 commits into from

Conversation

bzm3r
Copy link

@bzm3r bzm3r commented Oct 12, 2023

The main thing I was trying to fix was: being able to give format_args! directly as objects that can be styled by nu-ansi-term. The reasoning behind that was to 1) not have to allocate Strings unnecessarily when writing to a buffer, while still being able to format, and 2) to ease creation of ansi-formattable strings.

I also discovered that there's a lot of unnecessary usage of write!, and in some cases, with unnecessary use of fmt::Arguments (i.e. write!(f, "{}", 39)): so I removed those too, and simply made calls to write_str (here's the difference between write_str and write!: https://godbolt.org/z/WsTG345ac). This, surprisingly, required tweaking the way the AnyWrite trait was set up. (This was a really long/painful bit, even though it is ultimately trivial to write out. I think my conclusion ultimately is that the AnyWrite trait is a mistake. It is sufficient to have an io::Write as the primary writer. There is no point in trying to generalize over fmt::Write and io::Write.)

There are other performance improvements here too: the current version of nu-ansi-term re-calculates style differences every time a string is written to a writer:

fn write_to_any<W: AnyWrite<Wstr = S> + ?Sized>(&self, w: &mut W) -> Result<(), W::Error> {

On the other hand, I cache the style updates, and only re-calculate them when there is a change/update to the strings/styles.

When trying to pass tests, I found that the Difference machinery was particularly difficult to work with (even though it is very simple) because of lots of code duplication:

if first.is_bold && !next.is_bold {

So I then worked to simplify that so that, by breaking it down into re-usable components. I used bitflags for this, because that's what I am familiar with.

Upon trying to use what I was left with from the above, I realized that I really wished there was a way to nest ANSI strings, with some simple definition of how styles interact (for now, for me, parent styles merged with child styles is sufficient). So there's some functionality that allows one to give a parent style as a context to a child string.

Part of the goal with all of this was to run criterion benchmarks; but I'd run out of energy/motivation to do so, hence introduced the work as is. So, I've spun the work off into another crate, and when I have the energy to do benchmarks, will do those, but for now I need to get working on my actual projects

way we do not call write_fmt unnecesarily, and use write_str/write_all
for plain/non-formatting input.
… no longer need to specifically implement From<T> for Content for a wide variety of different T
…osts; however, now we have lifetime errors we must be careful about.
…tances, rather than separating it out into content/oscontrol/styles.
@fdncred
Copy link

fdncred commented Oct 13, 2023

Thanks for the PR. It was good chatting with you on Discord about it.

You're right, it's large, probably too large. What I'm trying to wrap my head around is why. What exactly are you trying to fix?

Like I said in Discord, we probably won't accept the macros unless there's some great justification, which I'm not seeing yet but maybe it's hidden in all the changes. Also, breaking changes have to be justified.

I really appreciate all your effort here but I don't see how we can accept this PR as is. Maybe others on the nushell core-team will jump in and help.

…lly possible to make the style difference calculations const (using while loops, but for now I have not pursued that
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants