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

Allow TextLog body to display as immutable TextEdit rather than Label #4716

Closed
wants to merge 3 commits into from

Conversation

tot0
Copy link

@tot0 tot0 commented Jan 6, 2024

What

Convert TextLog body to display as immutable TextEdit rather than Label.
This allows selecting and copying text from the log body.

Used discussion in emilk/egui#353 (comment) as inspiration.

selectable == false (default):
image

selectable == true:
image

Checklist

  • I have read and agree to Contributor Guide and the Code of Conduct
  • I've included a screenshot or gif (if applicable)
  • I have tested the web demo (if applicable):
  • The PR title and labels are set such as to maximize their usefulness for the next release's CHANGELOG

@tot0
Copy link
Author

tot0 commented Jan 6, 2024

Web testing to come...

Appreciate a first look at the text color setting logic since I'm clearly missing something to make it render same as RichText Label does.

@tot0 tot0 force-pushed the lupickup/text_log_selectable_body branch from 0912f9a to 937db0e Compare January 6, 2024 00:31
@tot0
Copy link
Author

tot0 commented Jan 6, 2024

Web screenshot:
image

@emilk
Copy link
Member

emilk commented Jan 6, 2024

Thanks for the PR!

We need to support easily copying text from the Rerun UI, but I'm not sure this is the best approach.
It can be very finicky to select the whole text of a label (easy to miss the first letter, or the last letters if it doesn’t fit on screen etc).
It also doesn’t work great on mobile.

A different approach is to use a 📋-button for copying the entire text, like we already do for code-blocks in markdown.
This takes up space, and should probably only show on hover.
For mobile we could have long-press to copy (or long-press to show a context menu, including “copy text”).

I'm gonna talk it through with our designer next week and get back to you!

Copy link
Member

@emilk emilk left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

After some discussion, we've decided that the drag-to-select approach is indeed the way to go.

We're planning on implementing this wide in egui at some point (emilk/egui#3804), but in the meantime this PR is a good bandaid.

I don't think we should have a "selectable" option - let's just make selectable the default, and make it a good default.

Right now turning on "selectable" also turns on text elision (shortening with "…") which is the opposite of what.

It would also be nice to encapsulate the added code in a fn selectable_label(ui: &mut egui::Ui, text: egui::RichText)

@tot0
Copy link
Author

tot0 commented Jan 10, 2024

Thanks @emilk!

I should have some time this weekend to take a second look at this and make selectable the default. There's some aspects I'm missing related to the difference between the RichText label and the immutable TextEdit (masquerading as a Label):

  • Colouring changes from grey "inactive" to white "active"
  • Column width reducing to fit on screen, rather than expand to as long as the longest body content "off-screen"

Any pointers you might have for where to look to understand the differences are appreciated, otherwise I'll see what I can put together based on the fn selectable_label(ui: &mut egui::Ui, text: egui::RichText) abstraction you're proposing.

// TODO(lupickup): Understand why TextEdit text color is white instead of gray like the RichText version.
ui.visuals()
.override_text_color
.unwrap_or_else(|| ui.visuals().widgets.inactive.text_color())
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

inactive.text_color is the text color of an interactive widget (that is not currently being interacted with). That's why you get white text: https://docs.rs/egui/latest/egui/style/struct.Widgets.html#structfield.inactive

Use noninteractive instead (we don't count text selection as interaction)

Comment on lines +433 to +442
let mut layout_job = egui::text::LayoutJob::simple(
string.to_owned(),
font_id.clone(),
text_color,
wrap_width,
);
layout_job.wrap.max_rows = entry_text_rows;
// Fill to end of body column instead of choosing a full "word" to ellide
layout_job.wrap.break_anywhere = true;
ui.fonts(|f| f.layout_job(layout_job))
Copy link
Member

@emilk emilk Jan 11, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I suggest you compute this Galley once and copy into this layouter. The string you know (and is fixed), and wrap_width should be f32::INFINITY (no wrapping).

By computing the galley up-front you can pass the size of it to TextEdit::min_size.

@emilk
Copy link
Member

emilk commented Jan 13, 2024

Text selection of all labels will be coming in the next egui release (1-3 weeks away): emilk/egui#3814

@emilk emilk closed this in #4885 Jan 23, 2024
emilk added a commit that referenced this pull request Jan 23, 2024
### What
This is so we can test things out before the next release, and also get
in some new egui features for the plot aggregator and drag-and-drop.

* Closes #4716
* Closes #4794

### TODO
* [x] Fix hovering ListItems in blueprint panel

### wgpu changelog
https://github.com/gfx-rs/wgpu/blob/trunk/CHANGELOG.md#v0190-2024-01-17

### relevant egui changelog (so far)

#### eframe
* Keep `ViewportInfo::maximized` and `minimized` up-to-date on Windows
[#3831](emilk/egui#3831) (thanks
[@rustbasic](https://github.com/rustbasic)!)
* Update wgpu to 0.19 [#3824](emilk/egui#3824)
* Fix: handle `IconData::default()` without crashing
[#3842](emilk/egui#3842)

#### egui_extras
* Fix unwraps in SVG scaling
[#3826](emilk/egui#3826) (thanks
[@amPerl](https://github.com/amPerl)!)
* Update to ehttp 0.4 [#3834](emilk/egui#3834)

#### egui_plot
* Make `egui_plot::PlotMemory` public
[#3871](emilk/egui#3871)

#### egui
* Selectable text in Labels
[#3814](emilk/egui#3814)
* `ComboBox`: add builder method for height
[#3001](emilk/egui#3001) (thanks
[@hinto-janai](https://github.com/hinto-janai)!)
* Add keys `?`, `/`, `|`
[#3820](emilk/egui#3820)
* Fix clickable widgets blocking scrolling on touch screens
[#3815](emilk/egui#3815) (thanks
[@lucasmerlin](https://github.com/lucasmerlin)!)
* Fix `stable_dt` [#3832](emilk/egui#3832)
* Bug Fix : `Response::is_pointer_button_down_on` is now false the frame
the button is released [#3833](emilk/egui#3833)
(thanks [@rustbasic](https://github.com/rustbasic)!)
* Use runtime knowledge of OS for OS-specific text editing
[#3840](emilk/egui#3840)
* Refactor: move text selection logic to own module
[#3843](emilk/egui#3843)
* Fix: dragging to above/below a `TextEdit` or `Label` will select text
to begin/end [#3858](emilk/egui#3858)
* Add `Response::contains_pointer`
[#3859](emilk/egui#3859)
* Always set `response.hovered` to false when dragging another widget
[#3860](emilk/egui#3860)
* Add `Align2::anchor_size`
[#3863](emilk/egui#3863)
* Add `Context::debug_text`
[#3864](emilk/egui#3864)

#### epaint
* Add `Align2::anchor_size`
[#3863](emilk/egui#3863)

### Checklist
* [x] I have read and agree to [Contributor
Guide](https://github.com/rerun-io/rerun/blob/main/CONTRIBUTING.md) and
the [Code of
Conduct](https://github.com/rerun-io/rerun/blob/main/CODE_OF_CONDUCT.md)
* [x] I've included a screenshot or gif (if applicable)
* [x] I have tested the web demo (if applicable):
* Using newly built examples:
[app.rerun.io](https://app.rerun.io/pr/4885/index.html)
* Using examples from latest `main` build:
[app.rerun.io](https://app.rerun.io/pr/4885/index.html?manifest_url=https://app.rerun.io/version/main/examples_manifest.json)
* Using full set of examples from `nightly` build:
[app.rerun.io](https://app.rerun.io/pr/4885/index.html?manifest_url=https://app.rerun.io/version/nightly/examples_manifest.json)
* [x] The PR title and labels are set such as to maximize their
usefulness for the next release's CHANGELOG

- [PR Build Summary](https://build.rerun.io/pr/4885)
- [Docs
preview](https://rerun.io/preview/eb1bce846c3adb29b99d04018b002475994ad213/docs)
<!--DOCS-PREVIEW-->
- [Examples
preview](https://rerun.io/preview/eb1bce846c3adb29b99d04018b002475994ad213/examples)
<!--EXAMPLES-PREVIEW-->
- [Recent benchmark results](https://build.rerun.io/graphs/crates.html)
- [Wasm size tracking](https://build.rerun.io/graphs/sizes.html)

---------

Co-authored-by: Andreas Reich <[email protected]>
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