beeware / beeware/toga

Native menu items on WinForms are never deleted

Open
#4,580 3 comments 0 reactions 0 assignees View on GitHub
bug gtk qt windows
Dominant language
Python
Stars
5.4k
Forks
827
Avg merge
9h 45m
Merged PRs (30d)
58

Description

### Describe the bug

Each time `Window._impl.create_menus()` is called on the WinForms backend it creates new copies of every native menu item. However the old objects are never removed from the `Window._impl.native` list.

### How to reproduce the bug

1. Run the minimal example.
2. The expectation would be to see ``Native instances of `cmd`: 1`` printed each time.

### Minimum example code

```shell
import toga

class MinimalApp(toga.App):
def __init__(self):
super().__init__(
formal_name="MinimalApp", app_id="com.example.minimal.app"
)

def startup(self):
self.main_window = toga.MainWindow(title=self.formal_name)
self.main_window.show()

def on_running(app=self):

all_commands = [cmd for cmd in app.commands._commands.values()]
cmd = all_commands[0]
group = cmd.group

for i in range(10):
new_cmd = toga.Command(text = f"Item {i}", group=group, action=None)
app.commands.add(new_cmd)

print(f"Native instances of `cmd`: {len(cmd._impl.native)}")

self.on_running = on_running

def main():
return MinimalApp()

if __name__ == "__main__":
app = main()
app.main_loop()
```

### Screenshots

_No response_

### Environment details

- Operating system and version: Windows 11
- Python version: 3.13
- Software versions:
- Toga: 0.5.5

### Logs

```

```

### Additional context

The issue is not present on the macOS backend since the `toga_cocoa.command.Command` class has a `remove_menu_item` method which is called. One solution could be to use such a method on the WinForms backend. Another could be to replace the `toga_winforms.command.Command.native` list with a `dict` of the form `{id(MainWindow): Command}`.

In either case, the native menu items should also be deleted whenever the MainWindow instance is deleted.

I think the issue is also present on toolbar items, and I haven't looked at other backends.

Contributor guide

Open the contributing guide

Research direction

Start in the WinForms implementation at Window._impl.create_menus() and toga_winforms.command.Command, then compare the macOS Command.remove_menu_item behavior described in the issue. Confirm that repeated menu creation and MainWindow deletion release old native items; also check whether the same lifecycle issue affects toolbar items.

Written by the indexing model from the issue text.

Assessment

Tech stack
python
Domain
desktop
Issue type
Bug
Difficulty
3/5
Estimated time
1-2 days
Activity status
Quiet
Clarity
Mostly clear
Newbie friendliness
55/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.