Commit Graph

220 Commits

Author SHA1 Message Date
Emil Ernerfeldt c6bda9a38c
Make the ends of vline/hline sharper (#5676)
TL;DR: line caps are annoying in two ways:

A) we only add them for lines wider than a pixel
B) they always make the line longer (if added)
2025-02-04 15:31:51 +01:00
Emil Ernerfeldt c90b97f4ef
Fix sharp corners for rectangles with StrokeKind != Inside (#5675)
Oops!
2025-02-04 14:36:29 +01:00
Emil Ernerfeldt 23ed49334e
⚠️ Rename `Rounding` to `CornerRadius` (#5673)
Breaking change!

* `Rounding` -> `CornerRadius`
* `rounding` -> `corner_radius`

This is to:
* Clarify
* Conform to other systems (e.g. Figma)
* Avoid confusion with `GuiRounding`
2025-02-04 12:53:18 +01:00
Emil Ernerfeldt 3c07e01d08
Improve tessellation quality (#5669)
## Defining what `Rounding` is
This PR defines what `Rounding` means: it is the corner radius of
underlying `RectShape` rectangle. If you use `StrokeKind::Inside`, this
means the rounding is of the outer part of the stroke. Conversely, if
you use `StrokeKind::Outside`, the stroke is outside the rounded
rectangle, so the stroke has an inner radius or `rounding`, and an outer
radius that is larger by `stroke.width`.

This definitions is the same as Figma uses.

## Improving general shape rendering
The rendering of filled shapes (rectangles, circles, paths, bezier) has
been rewritten. Instead of first painting the fill with the stroke on
top, we now paint them as one single mesh with shared vertices at the
border. This has several benefits:

* Less work (faster and with fewer vertices produced)
* No overdraw (nicer rendering of translucent shapes)
* Correct blending of stroke and fill

The logic for rendering thin strokes has also been improved, so that the
width of a stroke of `StrokeKind::Outside` never affects the filled area
(this used to be wrong for thin strokes).

## Improving of rectangle rendering
Rectangles also has specific improvements in how thin rectangles are
painted.
The handling of "Blur width" is also a lot better, and now works for
rectangles with strokes.
There also used to be bugs with specific combinations of corner radius
and stroke width, that are now fixed.

##  But why?
With the new `egui::Scene` we end up with a lot of zoomed out shapes,
with sub-pixel strokes. These need to look good! One thing led to
another, and then I became obsessive 😅

## Tessellation Test
In order to investigate the rendering, I created a Tessellation Test in
the `egui_demo_lib`.

[Try it
here](https://egui-pr-preview.github.io/pr/5669-emilkimprove-tessellator)

![Screenshot 2025-02-04 at 08 45
50](https://github.com/user-attachments/assets/20b47a30-de6a-4ff5-885b-2e2fd6d88321)


![image](https://github.com/user-attachments/assets/e17c50eb-5ae7-48d4-bb0d-4f2165075897)
2025-02-04 11:30:12 +01:00
Emil Ernerfeldt 50294b5d9f
Be smarter when rounding rectangles to the pixel grid (#5656) 2025-01-30 21:04:36 +01:00
Emil Ernerfeldt 4b9da5f650
Remove `StrokeKind::default` (#5658)
Since there is no natural default for `RectShape`.
2025-01-30 21:02:50 +01:00
Emil Ernerfeldt 525d435a84
Require a `StrokeKind` when painting rectangles with strokes (#5648)
This is a breaking change, requiring users to think about wether the
stroke is inside/centered/outside the rect.

When in doubt, add `egui::StrokeKind::Inside` to the function call.
2025-01-29 15:52:49 +01:00
Emil Ernerfeldt 6be17136f2
`RectShape`: add control over where the stoke goes (#5647)
Adds `RectShape::stroke_kind` so you can select if the stroke goes
inside, outside, or is centered on the rectangle.

Also adds `RectShape::round_to_pixels` so you can override
`TessellationOptions::round_rects_to_pixels`.
2025-01-29 12:46:12 +01:00
Emil Ernerfeldt 164f56f554
Fix some clippy issues found by 1.84.0 (#5603) 2025-01-13 08:29:13 +01:00
Emil Ernerfeldt 4784136fee
Better rounding of rectangles with thin outlines (#5571)
Better positioning of rectangle outline when the stroke width is less
than one pixel
2025-01-02 23:50:40 +01:00
Emil Ernerfeldt ee4ab08c8a
Shrink size of `Shadow` by using `i8/u8` instead of `f32` (#5568)
* Part of https://github.com/emilk/egui/issues/4019
2025-01-02 16:22:44 +01:00
Emil Ernerfeldt d58d13781d
Store `Margin` using `i8` to reduce its size (#5567)
Adds `Marginf` to fill the previous niche.

This is all in a pursuit to shrink the sizes of often-used structs, to
improve performance (less cache misses, less memcpy:s, etc).

* On the path towards https://github.com/emilk/egui/issues/4019
2025-01-02 16:05:52 +01:00
Emil Ernerfeldt aeea70d9e7
Add `epaint::Brush` for controlling `RectShape` texturing (#5565)
Also wraps `Shape::Mesh` in an `Arc`.

No new features, but decreases size of `Shape` from 72 bytes to 64.
2025-01-02 15:34:28 +01:00
Emil Ernerfeldt cf7150c6a3
Refactor: put each shape into its own file (#5564)
Much easier to navigate the code
2025-01-02 14:55:49 +01:00
Emil Ernerfeldt 249f8bcb93
Use `u8` in `Rounding`, and introduce `Roundingf` (#5563)
* Part of https://github.com/emilk/egui/issues/4019

As part of the work on adding a custom `Border` to everything, I want to
make sure that the size of `RectShape`, `Frame` and the future `Border`
is kept small (for performance reasons).

This PR changes the storage of the corner radius of rectangles from four
`f32` (one for each corner) into four `u8`. This mean the corner radius
can only be an integer in the range 0-255 (in ui points). This should be
enough for most people.

If you want to manipulate rounding using `f32`, there is a new
`Roundingf` to fill that niche.
2025-01-02 14:29:50 +01:00
lucasmerlin 86ea3f8a5c
Fix cargo test --all-features breaking rendering due to unity vertexes (#5542)
* Closes #5297 
* [x] I have followed the instructions in the PR template

It's not great but I wasn't able to come up with a better solution.
2024-12-30 12:39:17 +01:00
Emil Ernerfeldt bf6ed3adfc
Add `Context::copy_image` (#5533)
* Closes https://github.com/emilk/egui/issues/5424

This adds support for copying images to the system clipboard on native
and on web using `Context::copy_image`.
2024-12-29 18:03:32 +01:00
Emil Ernerfeldt d20f93e9bf
Make all lines and rectangles crisp (#5518)
* Merge this first: https://github.com/emilk/egui/pull/5517

This aligns all rectangles and (horizontal or vertical) line segments to
the physical pixel grid in the `epaint::Tessellator`, making these
shapes appear crisp everywhere.

* Closes https://github.com/emilk/egui/issues/5164
* Closes https://github.com/emilk/egui/issues/3667

This undoes a lot of the explicit, egui-side aligning added in:
* https://github.com/emilk/egui/pull/4943

The new approach has several benefits over the old one:

* It is done automatically by epaint, so it is applied to everything (no
longer opt-in)
* It is applied after any layer transforms (so it always works)
* It makes line segments crisper on high-DPI screens
* All filled rectangles now has sides that end on pixel boundaries
2024-12-26 21:02:27 +01:00
Emil Ernerfeldt dfcc679d5a
Round widget coordinates to even multiple of 1/32 (#5517)
* Closes https://github.com/emilk/egui/pull/5197
* Closes https://github.com/emilk/egui/issues/5163

This should help prevent rounding errors in layout code.

@lucasmerlin you may wanna test this with `egui_flex`
2024-12-26 20:54:24 +01:00
Emil Ernerfeldt 045ed41efc
Fix zero-width strokes still affecting the feathering color of boxes (#5485) 2024-12-16 16:54:18 +01:00
Emil Ernerfeldt e8029178b6
Reduce aliasing when painting thin box outlines (#5484)
* Part of https://github.com/emilk/egui/issues/5164
2024-12-16 16:28:15 +01:00
Emil Ernerfeldt 450c6242e4 Improve error message in ColorImage::region 2024-12-16 15:14:50 +01:00
Ted de Munnik 3af907919b
Use `profiling` crate to support more profiler backends (#5150)
Hey! I am not sure if this is something that's been considered before
and decided against (I couldn't find any PR's or issues).

This change removes the internal profiling macros in library crates and
the `puffin` feature and replaces it with similar functions in the
[profiling](https://github.com/aclysma/profiling) crate. This crate
provides a layer of abstraction over various profiler instrumentation
crates and allows library users to pick their favorite (supported)
profiler.

An additional benefit for puffin users is that dependencies of egui are
included in the instrumentation output too (mainly wgpu which uses the
profiling crate), so more details might be available when profiling.

A breaking change is that instead of using the `puffin` feature on egui,
users that want to profile the crate with puffin instead have to enable
the `profile-with-puffin` feature on the profiling crate. Similarly they
could instead choose to use `profile-with-tracy` etc.

I tried to add a 'tracy' feature to egui_demo_app in order to showcase ,
however the /scripts/check.sh currently breaks on mutually exclusive
features (which this introduces), so I decided against including it for
the initial PR. I'm happy to iterate more on this if there is interest
in taking this PR though.

Screenshot showing the additional info for wgpu now available when using
puffin

![image](https://github.com/user-attachments/assets/49fc0e7e-8f88-40cb-a69e-74ca2e3f90f3)
2024-12-16 09:15:54 +01:00
Emil Ernerfeldt 53a926a428
Update MSRV to 1.80 (#5457)
Because some dependencies now require it, see:
* https://github.com/emilk/egui/pull/5456
2024-12-10 16:09:03 +01:00
Emil Ernerfeldt 328422dc62
Update MSRV to Rust 1.79 (#5421)
Mostly to fix `cargo-machete` CI
2024-12-01 18:58:35 +01:00
GiGaGon 1787952a83
Create gray -> grey doc aliases (#5362)
As someone who uses "grey" instead of "gray", it is annoying that my
autocomplete can never find any of the "gray" color related things, so
this adds doc aliases for that.

* [x] I have followed the instructions in the PR template
2024-11-11 13:21:58 +01:00
Emil Ernerfeldt fc743d63b4 Add link to helpful article in font alpha TODO 2024-11-06 13:33:43 +01:00
lucasmerlin 5d6a58b917
Fix some typos (#5339)
The spell check pipeline in #5313 suddenly failed, this fixes these
typos and some more found via my IDEs spell checker tool
2024-11-04 09:51:34 +01:00
StarStarJ 3f5cd74de7
Put font data into Arc to reduce memory consumption (#5276)
egui never accesses the `FontDefinitions`' member fields mutably, except
in `fonts_tweak_ui` where it cloned the `FontDefinitions` object anyway.

This patch reduces system memory consumption for shared font
definitions.
And also removes some overhead from copying (e.g. for the per
`pixel_per_points` font atlas)

Also it allows to keep a copy of the font definitions outside of egui.

In my App that uses international fonts:
Before:

![image](https://github.com/user-attachments/assets/f8dfb4f4-a21c-447c-8cf9-83025ad6e960)

New:

![image](https://github.com/user-attachments/assets/9f297fbd-e620-4b7e-a32a-65073ee805ed)


Note: If `Arc` is not wanted, then it could ofc be abstracted away.

I know this is quite a breaking change API wise, but would like to hear
your opinion.
2024-11-01 13:30:02 +01:00
rustbasic 288c74e332
Expand max font atlas size from 8k to 16k (#5257)
When using fonts with an average of 50,000 characters,
'epaint texture atlas overflowed!' may be printed and cause problems.
It is necessary to expand the max value related to texture.

* Closes #5256

---------

Co-authored-by: Emil Ernerfeldt <emil.ernerfeldt@gmail.com>
2024-10-29 10:42:28 +01:00
frederik-uni 04ab5e7574
`Context::add_font` (#5228)
make it easier to add fonts. 

For example if I want to add a custom FontFamily or if the user wants to
add a Chinese fallback
* [x] I have followed the instructions in the PR template

---------

Co-authored-by: Emil Ernerfeldt <emil.ernerfeldt@gmail.com>
2024-10-23 14:29:44 +02:00
Emil Ernerfeldt 24cd711f5b Fix typos 2024-10-01 10:41:59 +02:00
Emil Ernerfeldt 92adfa57dc Improve comment in text layout code 2024-09-26 09:43:27 +02:00
Emil Ernerfeldt f97f85089d
Prevent text shrinking in tooltips; round wrap-width to integer (#5161)
* Closes https://github.com/emilk/egui/pull/5106
* Closes https://github.com/emilk/egui/issues/5084


Protect against rounding errors in egui layout code.

Say the user asks to wrap at width 200.0.
The text layout wraps, and reports that the final width was 196.0
points.
This than trickles up the `Ui` chain and gets stored as the width for a
tooltip (say).
On the next frame, this is then set as the max width for the tooltip,
and we end up calling the text layout code again, this time with a wrap
width of 196.0.
Except, somewhere in the `Ui` chain with added margins etc, a rounding
error was introduced,
so that we actually set a wrap-width of 195.9997 instead.
Now the text that fit perfectly at 196.0 needs to wrap one word earlier,
and so the text re-wraps and reports a new width of 185.0 points.
And then the cycle continues.

So this PR limits the text wrap-width to be an integer.

Related issues:
* https://github.com/emilk/egui/issues/4927
* https://github.com/emilk/egui/issues/4928
* https://github.com/emilk/egui/issues/5163

--- 

Pleas test this @rustbasic
2024-09-25 11:31:41 +02:00
Christofer Nolander 6f7b9b9b87
Add support for mipmap textures. (#5146)
<!--
Please read the "Making a PR" section of
[`CONTRIBUTING.md`](https://github.com/emilk/egui/blob/master/CONTRIBUTING.md)
before opening a Pull Request!

* Keep your PR:s small and focused.
* The PR title is what ends up in the changelog, so make it descriptive!
* If applicable, add a screenshot or gif.
* If it is a non-trivial addition, consider adding a demo for it to
`egui_demo_lib`, or a new example.
* Do NOT open PR:s from your `master` branch, as that makes it hard for
maintainers to test and add commits to your PR.
* Remember to run `cargo fmt` and `cargo clippy`.
* Open the PR as a draft until you have self-reviewed it and run
`./scripts/check.sh`.
* When you have addressed a PR comment, mark it as resolved.

Please be patient! I will review your PR, but my time is limited!
-->

* [x] I have followed the instructions in the PR template

Adds support for mipmaps in the `glow` backend.

Should be possible to implement for `wgpu` in the future as well, but
requires a custom compute kernel.
2024-09-22 19:16:16 +02:00
rustbasic 7c7190f98d
Clamp font size to between 0.1 and 2048 (#5139)
Fix: Font size limit to prevent panic
2024-09-22 19:14:03 +02:00
Emil Ernerfeldt 2a40d16e5a
Center-align all text vertically (#5117)
* Closes https://github.com/emilk/egui/issues/4929
* Builds on top of https://github.com/emilk/egui/pull/2724 by @lictex
(ptal!)
* Implement `Center` and `Max` vertical text alignment properly
* Change default vertical alignment of text to centering

The end result is that text centers better in buttons and other places,
especially when mixing in emojis.
Before, mixing text of different heights (e.g. emojis and latin text) in
a label or button would cause the text to jump vertically.

## Before
This is `master`, with custom `FontTweak` to move fonts up and down:
<img width="1714" alt="image"
src="https://github.com/user-attachments/assets/a10e2927-e824-4580-baea-124c0b38a527">
<img width="102" alt="image"
src="https://github.com/user-attachments/assets/cd41f415-197b-42cd-9558-d46d63c21dcb">


## After
This PR, with the default (zero) `FontTweak`

<img width="102" alt="image"
src="https://github.com/user-attachments/assets/15e7d896-66b1-4996-ab58-dd1850b19a63">

<img width="1714" alt="image"
src="https://github.com/user-attachments/assets/54ec708c-7698-4754-b1fc-fea0fd240ec9">
2024-09-19 11:44:29 +02:00
Emil Ernerfeldt f4ed394a85
Add UI to modify `FontTweak` live (#5125)
This will make it easier to get nice sizing and vertical alignments of
fonts
2024-09-18 13:43:33 +02:00
Emil Ernerfeldt 4dd89e2052 Fix some minor clippy lints from the future 2024-09-18 09:44:23 +02:00
Nicolas 1488ffa35a
Use `log` crate instead of `eprintln` & remove some unwraps (#5010)
<!--
Please read the "Making a PR" section of
[`CONTRIBUTING.md`](https://github.com/emilk/egui/blob/master/CONTRIBUTING.md)
before opening a Pull Request!

* Keep your PR:s small and focused.
* The PR title is what ends up in the changelog, so make it descriptive!
* If applicable, add a screenshot or gif.
* If it is a non-trivial addition, consider adding a demo for it to
`egui_demo_lib`, or a new example.
* Do NOT open PR:s from your `master` branch, as that makes it hard for
maintainers to test and add commits to your PR.
* Remember to run `cargo fmt` and `cargo clippy`.
* Open the PR as a draft until you have self-reviewed it and run
`./scripts/check.sh`.
* When you have addressed a PR comment, mark it as resolved.

Please be patient! I will review your PR, but my time is limited!
-->

- I fixed the TODO to use the `log` crate instead of `eprintln`
- Set the rust-version in the `scripts/check.sh` to the same as egui is
on
- I made xtask use anyhow to remove some unwraps 

* [x] I have followed the instructions in the PR template
2024-09-13 14:23:13 +02:00
Emil Ernerfeldt 66076101e1
Add `Context::request_discard` (#5059)
* Closes https://github.com/emilk/egui/issues/4976
* Part of #4378 
* Implements parts of #843

### Background
Some widgets (like `Grid` and `Table`) needs to know the width of future
elements in order to properly size themselves. For instance, the width
of the first column of a grid may not be known until all rows of the
grid has been added, at which point it is too late. Therefore these
widgets store sizes from the previous frame. This leads to "first-frame
jitter", were the content is placed in the wrong place for one frame,
before being accurately laid out in subsequent frames.

### What
This PR adds the function `ctx.request_discard` which discards the
visual output and does another _pass_, i.e. calls the whole app UI code
once again (in eframe this means calling `App::update` again). This will
thus discard the shapes produced by the wrongly placed widgets, and
replace it with new shapes. Note that only the visual output is
discarded - all other output events are accumulated.

Calling `ctx.request_discard` should only be done in very rare
circumstances, e.g. when a `Grid` is first shown. Calling it every frame
will mean the UI code will become unnecessarily slow.

Two safe-guards are in place:

* `Options::max_passes` is by default 2, meaning egui will never do more
than 2 passes even if `request_discard` is called on every pass
* If multiple passes is done for multiple frames in a row, a warning
will be printed on the screen in debug builds:


![image](https://github.com/user-attachments/assets/c2c1e4a4-b7c9-4d7a-b3ad-abdd74bf449f)

### Breaking changes
A bunch of things that had "frame" in the name now has "pass" in them
instead:

* Functions called `begin_frame` and `end_frame` are now called
`begin_pass` and `end_pass`
* `FrameState` is now `PassState`
* etc


### TODO
* [x] Figure out good names for everything (`ctx.request_discard`)
* [x] Add API to query if we're gonna repeat this frame (to early-out
from expensive rendering)
* [x] Clear up naming confusion (pass vs frame) e.g. for `FrameState`
* [x] Figure out when to call this
* [x] Show warning on screen when there are several frames in a row with
multiple passes
* [x] Document
* [x] Default on or off?
* [x] Change `Context::frame_nr` name/docs
* [x] Rename `Context::begin_frame/end_frame` and deprecate the old ones
* [x] Test with Rerun
* [x] Document breaking changes
2024-09-13 14:20:51 +02:00
Emil Ernerfeldt 6b7f431237
Fix text sometime line-breaking or truncating too early (#5077) 2024-09-06 13:24:11 +02:00
Emil Ernerfeldt b2dcb7d8db
Fix bug in size calculation of truncated text (#5076)
The width of the elision character (`…`) was never included in the size
calculation
2024-09-06 11:30:32 +02:00
Emil Ernerfeldt 7db8797850 Fix typo 2024-09-01 10:23:40 +02:00
Juan Campa f2815b423e
Fix blurry lines (#4943)
<!--
Please read the "Making a PR" section of
[`CONTRIBUTING.md`](https://github.com/emilk/egui/blob/master/CONTRIBUTING.md)
before opening a Pull Request!

* Keep your PR:s small and focused.
* The PR title is what ends up in the changelog, so make it descriptive!
* If applicable, add a screenshot or gif.
* If it is a non-trivial addition, consider adding a demo for it to
`egui_demo_lib`, or a new example.
* Do NOT open PR:s from your `master` branch, as that makes it hard for
maintainers to test and add commits to your PR.
* Remember to run `cargo fmt` and `cargo clippy`.
* Open the PR as a draft until you have self-reviewed it and run
`./scripts/check.sh`.
* When you have addressed a PR comment, mark it as resolved.

Please be patient! I will review your PR, but my time is limited!
-->


* Closes <https://github.com/emilk/egui/issues/4776>
* [x] I have followed the instructions in the PR template



I've been meaning to look into this for a while but finally bit the
bullet this week. Contrary to what I initially thought, the problem of
blurry lines is unrelated to feathering because it also happens with
feathering disabled.

The root cause is that lines tend to land on pixel boundaries, and
because of that, frequently used strokes (e.g. 1pt), end up partially
covering pixels. This is especially noticeable on 1ppp displays.

There were a couple of things to fix, namely: individual lines like
separators and indents but also shape strokes (e.g. Frame).

Lines were easy, I just made sure we round them to the nearest pixel
_center_, instead of the nearest pixel boundary.

Strokes were a little more complicated. To illustrate why, here’s an
example: if we're rendering a 5x5 rect (black fill, red stroke), we
would expect to see something like this:

![Screenshot 2024-08-11 at 15 01
41](https://github.com/user-attachments/assets/5a5d4434-0814-451b-8179-2864dc73c6a6)

The fill and the stroke to cover entire pixels. Instead, egui was
painting the stroke partially inside and partially outside, centered
around the shape’s path (blue line):

![Screenshot 2024-08-11 at 15 00
57](https://github.com/user-attachments/assets/4284dc91-5b6e-4422-994a-17d527a6f13b)

Both methods are valid for different use-cases but the first one is what
we’d typically want for UIs to feel crisp and pixel perfect. It's also
how CSS borders work (related to #4019 and #3284).

Luckily, we can use the normal computed for each `PathPoint` to adjust
the location of the stroke to be outside, inside, or in the middle.
These also are the 3 types of strokes available in tools like Photoshop.

This PR introduces an enum `StrokeKind` which determines if a
`PathStroke` should be tessellated outside, inside, or _on_ the path
itself. Where "outside" is defined by the directions normals point to.

Tessellator will now use `StrokeKind::Outside` for closed shapes like
rect, ellipse, etc. And `StrokeKind::Middle` for the rest since there's
no meaningful "outside" concept for open paths. This PR doesn't expose
`StrokeKind` to user-land, but we can implement that later so that users
can render shapes and decide where to place the stroke.

### Strokes test
(blue lines represent the size of the rect being rendered)

`Stroke::Middle` (current behavior, 1px and 3px are blurry)
![Screenshot 2024-08-09 at 23 55
48](https://github.com/user-attachments/assets/dabeaa9e-2010-4eb6-bd7e-b9cb3660542e)


`Stroke::Outside` (proposed default behavior for closed paths)
![Screenshot 2024-08-09 at 23 51
55](https://github.com/user-attachments/assets/509c261f-0ae1-46a0-b9b8-08de31c3bd85)



`Stroke::Inside` (for completeness but unused at the moment)
![Screenshot 2024-08-09 at 23 54
49](https://github.com/user-attachments/assets/c011b1c1-60ab-4577-baa9-14c36267438a)



### Demo App
The best way to review this PR is to run the demo on a 1ppp display,
especially to test hover effects. Everything should look crisper. Also
run it in a higher dpi screen to test that nothing broke 🙏.

Before:

![egui_old](https://github.com/user-attachments/assets/cd6e9032-d44f-4cb0-bb41-f9eb4c3ae810)


After (notice the sharper lines):

![egui_new](https://github.com/user-attachments/assets/3365fc96-6eb2-4e7d-a2f5-b4712625a702)
2024-08-30 09:57:32 +02:00
Nicolas 343c3d16c3
Remove wildcard imports (#5018)
<!--
Please read the "Making a PR" section of
[`CONTRIBUTING.md`](https://github.com/emilk/egui/blob/master/CONTRIBUTING.md)
before opening a Pull Request!

* Keep your PR:s small and focused.
* The PR title is what ends up in the changelog, so make it descriptive!
* If applicable, add a screenshot or gif.
* If it is a non-trivial addition, consider adding a demo for it to
`egui_demo_lib`, or a new example.
* Do NOT open PR:s from your `master` branch, as that makes it hard for
maintainers to test and add commits to your PR.
* Remember to run `cargo fmt` and `cargo clippy`.
* Open the PR as a draft until you have self-reviewed it and run
`./scripts/check.sh`.
* When you have addressed a PR comment, mark it as resolved.

Please be patient! I will review your PR, but my time is limited!
-->

I removed (I hope so) all wildcard imports I found.

For me on my pc this improved the build time:
- for egui -5s
- for eframe -12s

* [x] I have followed the instructions in the PR template
2024-08-28 12:18:42 +02:00
Emil Ernerfeldt a59f9ed279
Nicer looking text selection, especially in light mode (#5017)
* Closes https://github.com/emilk/egui/issues/4727

This changes the text selection painting from being painted on top of
the text, to being painted behind the text, but in front of any text
background. The result is much nicer looking text selection, especially
in light mode:

### The new selections
<img width="198" alt="Screenshot 2024-08-27 at 18 58 35"
src="https://github.com/user-attachments/assets/bd342946-299c-44ab-bc2d-2aa8ddbca8eb">
<img width="187" alt="Screenshot 2024-08-27 at 18 59 26"
src="https://github.com/user-attachments/assets/352bed32-5150-49b9-a9f9-c7679a0d30b2">


### What selections used to look like
<img width="143" alt="Screenshot 2024-08-27 at 19 03 08"
src="https://github.com/user-attachments/assets/f3cbd798-cfed-4ad4-aa3a-d7480efcfa3c">
<img width="143" alt="Screenshot 2024-08-27 at 19 03 23"
src="https://github.com/user-attachments/assets/9925d18d-da82-4a44-8a98-ea6857ecc14f">


### New selection of some text with a background
<img width="134" alt="Screenshot 2024-08-27 at 18 59 12"
src="https://github.com/user-attachments/assets/1d291d7f-efbd-4efd-b6d2-cd63c9fc4fa4">
2024-08-27 19:09:44 +02:00
Oscar Gustafsson cc3a09187d
Deprecate `ahash` re-exports (#4979)
<!--
Please read the "Making a PR" section of
[`CONTRIBUTING.md`](https://github.com/emilk/egui/blob/master/CONTRIBUTING.md)
before opening a Pull Request!

* Keep your PR:s small and focused.
* The PR title is what ends up in the changelog, so make it descriptive!
* If applicable, add a screenshot or gif.
* If it is a non-trivial addition, consider adding a demo for it to
`egui_demo_lib`, or a new example.
* Do NOT open PR:s from your `master` branch, as that makes it hard for
maintainers to test and add commits to your PR.
* Remember to run `cargo fmt` and `cargo clippy`.
* Open the PR as a draft until you have self-reviewed it and run
`./scripts/check.sh`.
* When you have addressed a PR comment, mark it as resolved.

Please be patient! I will review your PR, but my time is limited!
-->
* Closes <https://github.com/emilk/egui/issues/3482>
* [x] I have followed the instructions in the PR template

Regarding the statement in #3482,
https://docs.rs/egui/latest/egui/layers/struct.GraphicLayers.html#method.drain
accepts a HashMap, but not sure if that is enough to keep the re-export.
2024-08-26 10:41:16 +02:00
Alex Pinkus ae7672e336
Move default fonts to new crate `epaint_default_fonts` (#4853)
This allows license checking tools to omit the OFL and UFL licenses when
`default_fonts` are turned off.

There was some discussion of versioning on the original issue; I have
chosen to label this version as `0.28.1` to match the other crates.
Happy to adjust the version as needed.

<!--
Please read the "Making a PR" section of
[`CONTRIBUTING.md`](https://github.com/emilk/egui/blob/master/CONTRIBUTING.md)
before opening a Pull Request!

* Keep your PR:s small and focused.
* The PR title is what ends up in the changelog, so make it descriptive!
* If applicable, add a screenshot or gif.
* If it is a non-trivial addition, consider adding a demo for it to
`egui_demo_lib`, or a new example.
* Do NOT open PR:s from your `master` branch, as that makes it hard for
maintainers to test and add commits to your PR.
* Remember to run `cargo fmt` and `cargo clippy`.
* Open the PR as a draft until you have self-reviewed it and run
`./scripts/check.sh`.
* When you have addressed a PR comment, mark it as resolved.

Please be patient! I will review your PR, but my time is limited!
-->

* Closes <https://github.com/emilk/egui/issues/2321>
* [X] I have followed the instructions in the PR template

---------

Co-authored-by: Alex Pinkus <pinkus@amazon.com>
2024-07-31 09:50:02 +02:00
Wojciech Muła 7f899c1d07
epaint: add some missing inline docs (#4815)
Document a few `Mesh` methods.
2024-07-11 11:52:27 +02:00
Emil Ernerfeldt 143119943d
Show the innermost debug rectangle when pressing all modifier keys (#4782)
This is usually what the user is interested in.
2024-07-05 08:36:56 +02:00
Emil Ernerfeldt 3add56f81b Fix wrong comment 2024-06-30 14:35:46 +02:00
Emil Ernerfeldt 89968e6f96
Bug fix: ui opacity and gray-out not affecting strokes (#4581)
Bug introduced in https://github.com/emilk/egui/pull/4353
2024-05-29 22:37:55 +02:00
Emil Ernerfeldt cc3b3629b8
Round text galley sizes to nearest ui point size (#4578)
Previously, many labels had non-integer widths. This lead to rounding
errors.

This was most notable for the new `Area` sizing code:

We would run the initial sizing pass, to measure the size of e.g. a
tooltip.
Say the tooltip contains text that was 100.123 ui points wide. With a
16pt border, that becomes 116.123, which is stored in the `Area` state
as the width. The next frame, we use that stored size as the wrapping
width. With perfect precision, we would then tell the label to wrap to
100.123 pts, which the text would _just_ fit in. However, due to
rounding errors we might end up asking it to wrap to 100.12**2** pts,
meaning the last word would now wrap and end up on the next line.

By rounding label sizes to perfect integers, we avoid such rounding
errors, and most ui elements will now end up on perfect integer point
coordinates (and `f32` can precisely express and do arithmetic on all
integers < 2^24).

Visually this has very little impact. Some labels move by a pixel here
and there, mostly for the better.
2024-05-29 18:23:11 +02:00
Antoine Beyeler bcd91f27a1
Add support for text truncation to `egui::Style` (#4556)
* Closes #4473

This PR introduce `Style::wrap_mode`, which adds support for text
truncation in addition to text wrapping. This PR also update some width
calculation of the ComboBox.

#### Core

- Add `egui::TextWrapMode` (pure enum with `Extend`, `Wrap`, `Truncate`)
- Add `Style::wrap_mode: Option<tTextWrapMode>`
- **DEPRECATED**: `Style::wrap`, use `Style::wrap_mode` instead.
- Add `Ui::wrap_mode()` to return the wrap mode to use in the current
ui. If specified in `Style`, return it. Otherwise, return
`TextWrapMode::Wrap` for vertical layout and wrapping horizontal layout,
and `TextWrapMode::Extend` otherwise.
- **DEPRECATED**: `Ui::wrap_text()`, use `Ui::wrap_mode` instead.

#### Widget

- Update the width calculation of the `ComboBox` button (_not_ its popup
menu).
- Now, `ComboBox::width()` (defaulting to `Spacing::combo_width`) is
always considered a minimum width and will extend the `Ui`, regardless
of the selected text width and wrap mode.
- Introduce `ComboBox::wrap_mode`, which overrides `Ui::wrap_mode` for
the selected text layout.
- Note: since `ComboBox` uses `ui.horizontal` internally, the default
wrap mode is always `TextWrapMode::Extend`, regardless of the caller's
`Ui`'s layout.
- The `ComboBox` button no longer extend to `ui.available_width()` with
wrapping is enabled.
- **BREAKING**: `ComboBox::wrap()` no longer has a `bool` argument and
is now a short-hand for `ComboBox::wrap_mode(TextWrapMode::Wrap)`.
- Added `ComboBox::truncate()` as short-hand for
`ComboBox::wrap_mode(TextWrapMode::Truncate)`.
- Update `Label`
  - Add `Label::wrap_mode()` to specify the text wrap mode.
- **BREAKING**: `Label::wrap()` no longer has a `bool` argument and is
now a short-hand for `Label::wrap_mode(TextWrapMode::Wrap)`.
- **BREAKING**: `Label::truncate()` no longer has a `bool` argument and
is now a short-hand for `Label::wrap_mode(TextWrapMode::Truncate)`.
- Update `Button`
  - Add `Button::wrap_mode()` to specify the text wrap mode.
- **BREAKING**: `Button::wrap()` no longer has a `bool` argument and is
now a short-hand for `Button::wrap_mode(TextWrapMode::Wrap)`.
- Added `Button::truncate()` as short-hand for
`Button::wrap_mode(TextWrapMode::Truncate)`.

#### Low-level

- **BREAKING**: `WidgetText::into_galley()` now takes an
`Option<TextWrapMode>` instead of a `Option<bool>` argument.
- **BREAKING**: `WidgetText::into_galley_impl(()` now takes a
`TextWrapping` argument instead of `wrap: bool` and `availalbe_width:
f32` arguments.

---------

Co-authored-by: Emil Ernerfeldt <emil.ernerfeldt@gmail.com>
2024-05-28 13:10:41 +02:00
Ryan Bluth f0cbb18943
Don't panic when replacement glyph is not found (#4542)
I wanted to implement a font picker that loads all system fonts but ran
into panics due to missing glyphs. Falling back to an empty glyph when
none of the fallback glyphs are available avoids the panic.
2024-05-27 11:53:06 +02:00
crumblingstatue acfe9f6f3b
Make `epaint::mutex::RwLock` allow `?Sized` types (#4485)
`parking_lot`'s `RwLock` allows this, so probably `epaint`'s `RwLock`
should too.
Although I'm not sure how much it's intended for users, rather than just
internal use by `egui`.
2024-05-13 12:49:31 +02:00
Emil Ernerfeldt c3f386aa30
Remove work-around for `unsafe` in puffin macro (#4484)
…since it is no longer in the puffin macro
2024-05-11 20:17:19 +02:00
Emil Ernerfeldt f19f99180e
Remove `extra_asserts` and `extra_debug_asserts` feature flags (#4478)
Removes `egui_assert` etc and replaces it with normal `debug_assert`
calls.

Previously you could opt-in to more runtime checks using feature flags.
Now these extra runtime checks are always enabled for debug builds.

You are most likely to encounter them if you use negative sizes or NaNs
or other similar bugs.
These usually indicate bugs in user space.
2024-05-10 19:39:08 +02:00
Emil Ernerfeldt ded8dbd45b
Fix some clippy warning from Rust 1.78.0 (#4444) 2024-05-02 17:04:25 +02:00
hardlydearly 3bb33980a9
chore: remove repetitive words (#4400)
<!--
Please read the "Making a PR" section of
[`CONTRIBUTING.md`](https://github.com/emilk/egui/blob/master/CONTRIBUTING.md)
before opening a Pull Request!

* Keep your PR:s small and focused.
* The PR title is what ends up in the changelog, so make it descriptive!
* If applicable, add a screenshot or gif.
* If it is a non-trivial addition, consider adding a demo for it to
`egui_demo_lib`, or a new example.
* Do NOT open PR:s from your `master` branch, as that makes it hard for
maintainers to add commits to your PR.
* Remember to run `cargo fmt` and `cargo cranky`.
* Open the PR as a draft until you have self-reviewed it and run
`./scripts/check.sh`.
* When you have addressed a PR comment, mark it as resolved.

Please be patient! I will review your PR, but my time is limited!
-->

remove repetitive words

Signed-off-by: hardlydearly <799511800@qq.com>
2024-04-29 10:33:29 +02:00
Emil Ernerfeldt cee790681d
Update to Rust 1.76 (#4411)
Motivation: I want to replace `cargo-cranky` with workspace lints, first
available in Rust 1.74.
However, `cargo doc` would hange on `wgpu` and `wgpu-core` on 1.74 and
1.75… so now we're on 1.76.
I think this is fine - when 1.78 is released next week we're still two
versions behind the bleeding edge.

…and the branch name is just wrong 🤦
2024-04-25 15:51:01 +02:00
Joe Sorensen 2ce82cce21
Added ability to define colors at UV coordinates along a path (#4353)
<!--
Please read the "Making a PR" section of
[`CONTRIBUTING.md`](https://github.com/emilk/egui/blob/master/CONTRIBUTING.md)
before opening a Pull Request!

* Keep your PR:s small and focused.
* The PR title is what ends up in the changelog, so make it descriptive!
* If applicable, add a screenshot or gif.
* If it is a non-trivial addition, consider adding a demo for it to
`egui_demo_lib`, or a new example.
* Do NOT open PR:s from your `master` branch, as that makes it hard for
maintainers to add commits to your PR.
* Remember to run `cargo fmt` and `cargo cranky`.
* Open the PR as a draft until you have self-reviewed it and run
`./scripts/check.sh`.
* When you have addressed a PR comment, mark it as resolved.

Please be patient! I will review your PR, but my time is limited!
-->

I had to make a couple types not Copy because closures, but it should'nt
be a massive deal.

I tried my best to make the API change as non breaking as possible.
Anywhere a PathStroke is used, you can just use a normal Stroke instead.
As mentioned above, the bezier paths couldn't be copy anymore, but IMO
that's a minor caveat.

---------

Co-authored-by: Emil Ernerfeldt <emil.ernerfeldt@gmail.com>
2024-04-22 18:35:09 +02:00
Emil Ernerfeldt 87b294534e
Add `emath::OrderedFloat` (moved from `epaint::util::OrderedFloat`) (#4389)
It makes much more sense in `emath`
2024-04-21 20:36:32 +02:00
Juan Campa c630a8de89
Fix incorrect line breaks (#4377)
<!--
Please read the "Making a PR" section of
[`CONTRIBUTING.md`](https://github.com/emilk/egui/blob/master/CONTRIBUTING.md)
before opening a Pull Request!

* Keep your PR:s small and focused.
* The PR title is what ends up in the changelog, so make it descriptive!
* If applicable, add a screenshot or gif.
* If it is a non-trivial addition, consider adding a demo for it to
`egui_demo_lib`, or a new example.
* Do NOT open PR:s from your `master` branch, as that makes it hard for
maintainers to add commits to your PR.
* Remember to run `cargo fmt` and `cargo cranky`.
* Open the PR as a draft until you have self-reviewed it and run
`./scripts/check.sh`.
* When you have addressed a PR comment, mark it as resolved.

Please be patient! I will review your PR, but my time is limited!
-->

While breaking a paragraph, it was possible to lose line break
candidates that could've been used on the next line, causing egui to
unnecessarily overrun `wrap.max_width`.

This PR fixes it so that we don't forget about those candidates.


Before:
Note that the window can't resize to the requested width because the
text is not wrapping.


https://github.com/emilk/egui/assets/1410520/6430a334-2995-4b40-bc34-8f01923f9f95

After:


https://github.com/emilk/egui/assets/1410520/225fa4cd-cbbb-4a7e-9580-7f1814c05ee7

---------

Co-authored-by: Emil Ernerfeldt <emil.ernerfeldt@gmail.com>
2024-04-21 10:58:40 +02:00
Emil Ernerfeldt a9a756e8f3
Overload operators for `Rect + Margin`, `Rect - Margin` etc (#4277)
It's more ergonomic
2024-03-30 14:03:41 +01:00
Emil Ernerfeldt a541e021aa
Add `RectShape::blur_width` to implement shadows (#4267)
This is mostly a refactor, but has some performance benefits:
* We (re)use the same tessellator as for everything else, leading to
less allocations
* We cull shapes before rendering them

Adding `RectShape::blur_width` means it can also be used for other
effects, such as glow.
2024-03-29 20:29:42 +01:00
Emil Ernerfeldt a15e6c2122
Prevent visual glitch when shadow blur width is very high (#4245)
* Closes https://github.com/emilk/egui/issues/4238

The comment in the code explains it well, but the short of it is this:
we can't handle a shadow blur width larger than the shadow rectangle, so
we need to clamp the blur. This means smaller things will cast shadows
with a smaller blur width, but that's better than having visual
glitches.
2024-03-27 11:22:38 +01:00
Emil Ernerfeldt 947b5813d7
Fix visual glitch on the right side of highly rounded rectangles (#4244)
* Part of https://github.com/emilk/egui/issues/4238

When one side of a rectangle is all rounding we need to take care not to
produce duplicated vertices in the rectangle path generator.

The old code only handled three sides, but forgot the last side (the
right side).
The new code handles the right side, and also handles the other sides
more robustly (with a floating point eps) and efficiently (in a single
pass).

The glitch was most notable in shadows with a high blur width.

Examples of the glitch:

<img width="203" alt="Screenshot 2024-03-26 at 20 15 38"
src="https://github.com/emilk/egui/assets/1148717/dc1c0a06-35f0-4fda-a011-0e37d18454a0">

<img width="220" alt="Screenshot 2024-03-27 at 09 48 48"
src="https://github.com/emilk/egui/assets/1148717/c278b28e-c3f9-4c82-ba20-0480621efd2f">

<img width="33" alt="Screenshot 2024-03-27 at 09 49 21"
src="https://github.com/emilk/egui/assets/1148717/379ddf77-6590-4444-9c2e-67ab1e071f0f">
2024-03-27 10:13:49 +01:00
Emil Ernerfeldt f8d7d0ebaa
Enforce writing username in TODO comments (#4235) 2024-03-26 11:48:24 +01:00
Emil Ernerfeldt c530504a04
CSS-like shadows with offset, spread, and blur (#4232)
This makes `epaint::Shadow` more like CSS's box-shadow, adding `offset`
and replacing `extrusion` with `blur` and `spread`.

* Closes https://github.com/emilk/egui/pull/3047

The offsets make for nice drop-shadow effects.

Old shadows:
<img width="1447" alt="old-shadows"
src="https://github.com/emilk/egui/assets/1148717/8a30f7b9-fb9d-49ea-9a2f-9367a60c448a">

New shadows:
<img width="1447" alt="new-shadows-full"
src="https://github.com/emilk/egui/assets/1148717/28cc9c1e-b0de-4c5b-a705-22e52c556584">
2024-03-26 10:37:12 +01:00
Emil Ernerfeldt 1634554032
Add `Margin` to `epaint` (#4231)
Moved from `egui`
2024-03-26 09:05:29 +01:00
Eris bce257adb3
`epaint`: Add `EllipseShape` (#4122)
Adds an Ellipse shape draw-able with the Painter, brings egui closer to
the SVG Specification.

I've done some optimization towards using less vertices and doing less
calculations.

~~Currently the vertices are evenly distributed.
It's possible this could be optimized further taking into account the
gradient and increasing the concentration of vertices where the change
in gradient is larger.~~


![EllipseTall](https://github.com/emilk/egui/assets/50041841/b105230c-ce68-49c1-b162-d1f066bf9d6a)

![EllipseWide](https://github.com/emilk/egui/assets/50041841/6f9106d2-75cb-4f2a-b0c2-039b3aadec86)
2024-03-20 13:23:21 +01:00
CrazyCraftix 4a330de53d
Fix scaling of rounded corners for rect shape (#4152) (#4161)
When scaling an `egui::Shape` of variant `Rect` using the new
`transform` function, corner rounding isn't taken into account.

The fix is to multiply the rounding by the scaling factor.

* Closes <https://github.com/emilk/egui/issues/4152>
2024-03-12 11:14:24 +01:00
Varphone Wong a93c6cd5d2
`egui`: Fixed the incorrect display of the Window frame with a wide border or large rounding (#4032)
Currently, the Window frame is displayed incorrectly when using a wide
border or large rounding.

* Closes #3806
* Closes #4024 
* Closes #4025 

* Screencast of egui demo app (emilk:master)


[window-frame-bug.webm](https://github.com/emilk/egui/assets/1274171/391f67fa-ae6f-445a-8c64-1bb575770127)

* Screencast of egui demo app (varphone:hotfix/window-custom-frame)


[window-frame-fixed.webm](https://github.com/emilk/egui/assets/1274171/1953124e-9f7a-4c2d-9024-5d2eece6b87c)
2024-03-08 10:32:23 +01:00
Varphone Wong 4d776fd84e
`epaint`: Added `Shape::{scale,translate}` wrappers (#4090)
The `Shape::translate` method has been replaced with `Shape::transform`,
which introduces breaking changes that could negatively impact existing
users.

This patch adds a `Shape::translate` wrapper to prevent these breaking
changes.
2024-03-08 10:07:31 +01:00
0Qwel 23e8312fc0
Convenience const fn for Margin, Rounding and Shadow (#4080)
I often write constants at the top of my widget files, as a "config". I
kept writing stuff like that :
```rust
const DEFAULT_INNER_MARGIN: Margin = Margin { left: 17., right: 17., top: 7., bottom: 7. };
```
So I prefixed constructors for `Margin`, `Rounding` and `Shadow` const.
No code was changed.

I also added a `Shadow::new()` for similar reasons.
2024-02-21 16:20:26 +01:00
wangxiaochuTHU ca8eeb8621
Add `ColorImage::from_gray_iter` (#3536)
Add an alternative method for creating a [`ColorImage`] that accepts
`Iterator` as the argument. It can be useful when `&[u8]` is not
available but the iterator is.

<!--
Please read the "Making a PR" section of
[`CONTRIBUTING.md`](https://github.com/emilk/egui/blob/master/CONTRIBUTING.md)
before opening a Pull Request!

* Keep your PR:s small and focused.
* If applicable, add a screenshot or gif.
* If it is a non-trivial addition, consider adding a demo for it to
`egui_demo_lib`, or a new example.
* Do NOT open PR:s from your `master` branch, as that makes it hard for
maintainers to add commits to your PR.
* Remember to run `cargo fmt` and `cargo cranky`.
* Open the PR as a draft until you have self-reviewed it and run
`./scripts/check.sh`.
* When you have addressed a PR comment, mark it as resolved.

Please be patient! I will review you PR, but my time is limited!
-->

---------

Co-authored-by: Emil Ernerfeldt <emil.ernerfeldt@gmail.com>
2024-02-20 15:29:23 +01:00
Francis Chua 069d7a634d
Add layer transforms, interaction in layer (#3906)
⚠️ Removes `Context::translate_layer`, replacing it with a sticky
`set_transform_layer`

Adds the capability to scale layers.
Allows interaction with scaled and transformed widgets inside
transformed layers.

I've also added a demo of how to have zooming and panning in a window
(see the video below).

This probably closes #1811. Having a panning and zooming container would
just be creating a new
`Area` with a new id, and applying zooming and panning with
`ctx.transform_layer`.

I've run the github workflow scripts in my repository, so hopefully the
formatting and `cargo cranky` is satisfied.

I'm not sure if all call sites where transforms would be relevant have
been handled. This might also be missing are transforming clipping
rects, but I'm not sure where / how to accomplish that. In the demo, the
clipping rect is transformed to match, which seems to work.


https://github.com/emilk/egui/assets/70821802/77e7e743-cdfe-402f-86e3-7744b3ee7b0f

---------

Co-authored-by: tweoss <fchua@puffer5.stanford.edu>
Co-authored-by: Emil Ernerfeldt <emil.ernerfeldt@gmail.com>
2024-02-17 11:02:56 +01:00
Dan Lock a5973e5cac
Add `TextureOptions::wrap_mode` (#3954)
Exposes support in both glow and wgpu for texture wrap modes

This would be breaking for manual creations of TextureOptions but would
work with the current TextureOptions::NEAREST and LINEAR without change,
keeping those clamp to edge

I wasn't sure how best to expose the options to the user and added
consts for LINEAR_REPEAT LINEAR_MIRRORED_REPEAT NEAREST_REPEAT
NEAREST_MIRRORED_REPEAT

This does not include wrap mode clamp to border as it worked fine with
glow but with wgpu it panics due to Features
Features(ADDRESS_MODE_CLAMP_TO_BORDER) are required but not enabled on
the device, and I thought it was probably best not to try to enable that
feature, but happy to include that functionality also if that is okay to
be toggled


![image](https://github.com/emilk/egui/assets/5075747/bba71f61-a105-4e5b-b8ce-1083621eb3de)

---------

Co-authored-by: Emil Ernerfeldt <emil.ernerfeldt@gmail.com>
2024-02-05 09:37:05 +01:00
Emil Ernerfeldt c5352cf6c1 Remove profile scope from `tessellate_shape` 2024-02-02 15:53:01 +01:00
Emil Ernerfeldt 1db291721f
Parallell tessellation (#3934)
* Part of https://github.com/emilk/egui/issues/1485

This adds a `rayon` feature to `epaint` and `egui` to parallelize
tessellation of large shapes, such as high-resolution plot lines.
2024-02-01 16:27:59 +01:00
StratusFearMe21 945a69d2f2
Add opacity factor to `TextShape` (#3916)
<!--
Please read the "Making a PR" section of
[`CONTRIBUTING.md`](https://github.com/emilk/egui/blob/master/CONTRIBUTING.md)
before opening a Pull Request!

* Keep your PR:s small and focused.
* If applicable, add a screenshot or gif.
* If it is a non-trivial addition, consider adding a demo for it to
`egui_demo_lib`, or a new example.
* Do NOT open PR:s from your `master` branch, as that makes it hard for
maintainers to add commits to your PR.
* Remember to run `cargo fmt` and `cargo cranky`.
* Open the PR as a draft until you have self-reviewed it and run
`./scripts/check.sh`.
* When you have addressed a PR comment, mark it as resolved.

Please be patient! I will review your PR, but my time is limited!
-->

This PR simply allows you to override the opacity of a Galley when you
draw it on screen. Last year I opened #3548 and some changes were
requested to the PR, but unfortunately school got really busy and I
wasn't able to apply them. This PR supersedes #3548 and applys the
changes requested in that PR

Closes #3548
2024-01-30 15:55:18 +01:00
Emil Ernerfeldt 5e7fa46451 Fix text selection crashes
Closes https://github.com/emilk/egui/issues/3881
2024-01-24 15:47:44 +01:00
Emil Ernerfeldt 41aad74552
Cross-widget text select (#3870)
* Closes https://github.com/emilk/egui/issues/3816


![cross-widget-text-selection](https://github.com/emilk/egui/assets/1148717/5582b9d2-8b04-47b7-9637-f48e44064a70)

Turn off with `style.interaction.multi_widget_text_select`.

There is an API for this in `LabelSelectionState`, but it's pretty
bare-bones.

This became really hairy implementation-wise, but it works decently
well.

# Limitations
* Drag-select to scroll doesn't work
* A selection disappears if you scroll past one of its end-points
* Only the text of labels and links are selectable
 
## TODO
* [x] An option to turn it off
* [x] An API for querying about the selected text, and to deselect it.
* [x] Scrolling past selection behaves weird
* [x] Shift-click to select a range
2024-01-24 15:45:22 +01:00
Emil Ernerfeldt 31cc31a67b
Add `Align2::anchor_size` (#3863) 2024-01-22 16:47:50 +01:00
Emil Ernerfeldt ff39fd6195
Fix: dragging to above/below a `TextEdit` or `Label` will select text to begin/end (#3858)
This also adds a `Galley::begin` method to match `Galley::end` (both
returning cursor positions).

* Part of https://github.com/emilk/egui/issues/3816
2024-01-22 10:49:42 +01:00
Emil Ernerfeldt 5d2e192927
Selectable text in Labels (#3814)
* Closes https://github.com/emilk/egui/issues/3804

Add ability to select the text in labels with mouse-drag, double-click,
and keyboard (once clicked).
Hit Cmd+C to copy the text. If everything of a label with elided text is
selected, the copy command will copy the full non-elided text. IME and
accesskit _should_ work, but is untested.

You can control wether or not text in labels is selected globally in
`style.interaction.selectable_labels` or on a per-label basis in
`Label::selectable`. The default is ON.

This also cleans up the `TextEdit` code somewhat, fixing a couple
smaller bugs along the way.

This does _not_ implement selecting text across multiple widgets. Text
selection is only supported within a single `Label`, `TextEdit`, `Link`
or `Hyperlink`.


![label-text-selection](https://github.com/emilk/egui/assets/1148717/c161e819-50da-4b97-9686-042e6abf3564)


## TODO
* [x] Test
2024-01-14 15:17:55 +01:00
Emil Ernerfeldt 401de05630
Use `Self` everywhere (#3787)
This turns on the clippy lint
[`clippy::use_self`](https://rust-lang.github.io/rust-clippy/v0.0.212/index.html#use_self)
and fixes it everywhere.
2024-01-08 17:41:21 +01:00
StarStarJ 7b105cfa0f
Invalidate font atlas on any change to `pixels_per_point`, not matter how small (#3698)
Apparently the font implementation uses a distance check to decide if
the font(or whatever) need recalculations, after dpi changed:

8d4de866d4/crates/epaint/src/text/fonts.rs (L381-L382)

This leads to warnings when the pixel_per_point diff is very low and
spams the log. (<- this happens for me if i resize my window on kwin,
e.g. maximize it)

(I don't want to debate if the float difference generally makes sense,
so if you want to rework that instead just close this pr)
2024-01-08 09:13:34 +01:00
Emil Ernerfeldt 8c30e8c5f7
Highlight submenu buttons when hovered and open (#3780)
Submenu buttons in menues now properly highlight when hovered and when
opened.

…plus a bunch of other cleanup
2024-01-07 22:08:32 +01:00
Varphone Wong 932fdae9e6
Fix: allow using the full Private Use Area for custom fonts (#3509)
The ignored characters are used in some custom fonts.

for example: the \u{F0FF} is used as `cleaning_services` in
MaterialIcons-Regular.ttf

<!--
Please read the "Making a PR" section of
[`CONTRIBUTING.md`](https://github.com/emilk/egui/blob/master/CONTRIBUTING.md)
before opening a Pull Request!

* Keep your PR:s small and focused.
* If applicable, add a screenshot or gif.
* If it is a non-trivial addition, consider adding a demo for it to
`egui_demo_lib`, or a new example.
* Do NOT open PR:s from your `master` branch, as that makes it hard for
maintainers to add commits to your PR.
* Remember to run `cargo fmt` and `cargo cranky`.
* Open the PR as a draft until you have self-reviewed it and run
`./scripts/check.sh`.
* When you have addressed a PR comment, mark it as resolved.

Please be patient! I will review you PR, but my time is limited!
-->

Closes <https://github.com/emilk/egui/issues/THE_RELEVANT_ISSUE>.

---------

Co-authored-by: Emil Ernerfeldt <emil.ernerfeldt@gmail.com>
2024-01-06 22:33:08 +01:00
Emil Ernerfeldt e44f54f81f
Fix text color of disabled widgets (#3744)
* Introduced recently in https://github.com/emilk/egui/pull/3727
* Closes https://github.com/emilk/egui/issues/3732
2023-12-28 11:16:39 +01:00
Emil Ernerfeldt 0a6ea15f6c
impl `Clone` for `Fonts` (#3737)
Closes https://github.com/emilk/egui/issues/3731
2023-12-25 19:00:54 +01:00
Oscar Gustafsson fc18d6f8f4
Add support for dashed lines with offset (#3720)
<!--
Please read the "Making a PR" section of
[`CONTRIBUTING.md`](https://github.com/emilk/egui/blob/master/CONTRIBUTING.md)
before opening a Pull Request!

* Keep your PR:s small and focused.
* If applicable, add a screenshot or gif.
* If it is a non-trivial addition, consider adding a demo for it to
`egui_demo_lib`, or a new example.
* Do NOT open PR:s from your `master` branch, as that makes it hard for
maintainers to add commits to your PR.
* Remember to run `cargo fmt` and `cargo cranky`.
* Open the PR as a draft until you have self-reviewed it and run
`./scripts/check.sh`.
* When you have addressed a PR comment, mark it as resolved.

Please be patient! I will review your PR, but my time is limited!
-->

Closes <https://github.com/emilk/egui/issues/3677>.

This can naturally be obtained by starting the drawing a bit "later",
but providing support for this directly will simplify interleaved
drawing of dashed lines.

An even more general approach would be to allow passing an even-length
vector of lengths and gaps, in addition to offset. Primarily thinking if
it is better to go even further if a new dashed-line-method is
introduced. The second commit introduce this (I can naturally squash
these!).
2023-12-23 16:17:04 +01:00
Emil Ernerfeldt 0561fcaba9
Replace a special `Color32::PLACEHOLDER` with widget fallback color (#3727)
This introduces a special `Color32::PLACEHOLDER` which, during text
painting, will be replaced with `TextShape::fallback_color`.

The fallback color is mandatory to set in all text painting. Usually
this comes from the current visual style.

This lets users color only parts of a `WidgetText` (using e.g. a
`LayoutJob` or a `Galley`), where the uncolored parts (using
`Color32::PLACEHOLDER`) will be replaced by a default widget color (e.g.
blue for a hyperlink).

For instance, you can color the `⚠️`-emoji red in a piece of text red
and leave the rest of the text uncolored. The color of the rest of the
text will then depend on wether or not you put that text in a label, a
button, or a hyperlink.

Overall this simplifies a lot of complexity in the code but comes with a
few breaking changes:

* `TextShape::new`, `Shape::galley`, and `Painter::galley` now take a
fallback color by argument
* `Shape::galley_with_color` has been deprecated (use `Shape::galley`
instead)
* `Painter::galley_with_color` has been deprecated (use
`Painter::galley` instead)
* `WidgetTextGalley` is gone (use `Arc<Galley>` instead)
* `WidgetTextJob` is gone (use `LayoutJob` instead)
* `RichText::into_text_job` has been replaced with
`RichText::into_layout_job`
* `WidgetText::into_text_job` has been replaced with
`WidgetText::into_layout_job`
2023-12-22 15:09:10 +01:00
Emil Ernerfeldt 8d4de866d4
Remove deprecated functions (#3692) 2023-12-08 11:02:57 +01:00
Emil Ernerfeldt bd9bc252aa
Fix buggy text withviewports on monitors with different scales (#3666)
* Closes https://github.com/emilk/egui/issues/3664

Bonus: optimize color conversions and font atlas upload, especially in
debug builds.
2023-11-30 15:56:05 +01:00
Emil Ernerfeldt 61a7b90d5b
Improve multi-viewports across monitors with different scales (#3663)
It required some ugly code in `egui-winit` in order to fix this without
breaking sem-ver (I want this to land in a 0.24.1 patch release). I'll
clean up in time for 0.25.

There is still a font rendering bug when using immediate viewports
across multiple viewports, but that's harder to fix.
2023-11-30 12:08:53 +01:00
Andreas Reich f9f5db9885
PaintCallbackInfo::viewport_in_pixels now guarantees to stay in bounds (#3604)
* Fixes https://github.com/rerun-io/rerun/issues/4297
* tested against a very hasty and incomplete port of egui/trunk, found
[here](https://github.com/rerun-io/rerun/tree/andreas/experimental-egui-trunk)


In rare cases in can happen that the viewport returned by
`PaintCallbackInfo` is outside the bounds of the screen.
for at least [wgpu/webgpu in
particular](https://www.w3.org/TR/webgpu/#dom-gpurenderpassencoder-setviewport)
this is invalid usage, other backends might be affected as well.
Since this happened due to a float rounding error (in one repro case I
had I got (width==1126.5625) + (offset=715.4376) = 1842.0001 for a
resolution of 1842) I decided to do away with fractional values on the
viewport alltogether. They _technically_ make sense since a viewport is
only specifying the NDC to pixel coordinate conversion, but practically
this may lead to surprising sub-sampling issues.

---------

Co-authored-by: Emil Ernerfeldt <emil.ernerfeldt@gmail.com>
2023-11-22 21:01:38 +01:00