Skip to content

Rename Context to State#4114

Merged
kattni merged 4 commits intobeeware:mainfrom
HalfWhitt:rename-context
Jan 25, 2026
Merged

Rename Context to State#4114
kattni merged 4 commits intobeeware:mainfrom
HalfWhitt:rename-context

Conversation

@HalfWhitt
Copy link
Copy Markdown
Member

Lots of changes, but pretty mechanical for the most part.

The Canvas docs, tutorial, and example are going to need an overhaul for #3994, but I think it makes sense to wait on that until most or all of the changes are available. For now, I'm only aiming to replace vocabulary and references as necessary to keep them functional and accurate through this intermediate process.

PR Checklist:

  • All new features have been tested
  • All new features have been documented
  • I have read the CONTRIBUTING.md file
  • I will abide by the code of conduct

@@ -662,26 +673,26 @@ def _draw(self, context: Any) -> None:


class FillContext(ClosedPathContext):
Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

In a vacuum, I'd also be changing these class names too, e.g. FillState. However, I've left them alone because they'll soon be going away, once their "standalone" counterparts (e.g. Fill) start doing double duty as context managers.

return f"{self.__class__.__name__}(x={self.x}, y={self.y})"

def _draw(self, context: Any) -> None:
"""Used by parent to draw all objects that are part of the context."""
Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

This lone _draw method was docstringed, unlike all the others. I removed it here, and added one to the abstract State._draw.

# A fresh state has been created as a sub-state of the canvas.
assert isinstance(closed_path, ClosedPathContext)
assert closed_path != widget.context
assert closed_path is not widget.root_state
Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

I noticed several spots in these tests was checking states with !=. This has worked in the past, but:

  • Dataclasses actually implement equality checking, so this can't be trusted anymore to be equivalent to is not.
  • is not makes the intent clearer.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Thanks for the clarification!

Comment on lines +7 to +22
1. We first define the drawing operations we want to perform in a new function:

2. Next we create a new Canvas: ```python self.canvas = toga.Canvas(flex=1) ```
```python
def draw_eyes(self):
with self.canvas.Fill(color=WHITE) as eye_whites:
eye_whites.arc(58, 92, 15)
eye_whites.arc(88, 92, 15, math.pi, 3 * math.pi)
```

Notice that we also created and used a new fill state called `eye_whites`. The `with` keyword that is used for the fill operation causes everything draw using the state to be filled with a color. In this example we filled two circular eyes with the color white.

2. Next we create a new Canvas:

```python
self.canvas = toga.Canvas(flex=1)
```
Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

I think this may have been a casualty of the Markdown changeover — I only just noticed it'd been reflowed onto one line.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Almost certainly was a casualty. There were issues with the reflow initially, and I tried to catch them all, but missed a few.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

All good! Just wanted to explain where all these new lines came from. I'm honestly impressed at how rarely I've seen artifacts like this, considering how massive a migration that was.

Copy link
Copy Markdown
Contributor

@kattni kattni left a comment

Choose a reason for hiding this comment

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

This looks pretty good to me! I have a few questions that are probably me needing a little help understanding things, and not actual problems.

Comment thread core/src/toga/widgets/canvas/state.py
Comment thread core/tests/widgets/canvas/test_canvas.py
Comment thread examples/canvas/canvas/app.py
Comment thread examples/tutorial4/tutorial/app.py
Comment thread examples/tutorial4/tutorial/app.py
Copy link
Copy Markdown
Contributor

@kattni kattni left a comment

Choose a reason for hiding this comment

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

Thanks for the clarifications! Looks good to me.

@kattni kattni merged commit bf57226 into beeware:main Jan 25, 2026
57 checks passed
@HalfWhitt HalfWhitt deleted the rename-context branch January 25, 2026 23:19
# Use the font to write on a canvas.
canvas = toga.Canvas()
canvas.context.write_text("Hello", font=my_font)
canvas.root_tate.write_text("Hello", font=my_font)
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

@HalfWhitt Just saw this typo on a quick scan; might want to piggyback a fix onto another canvas PR.

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.

Name changes in Canvas

3 participants