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

fix(iOS): Replace uses of CGColorRef with UIColor to avoid manual memory management #46847

Open
wants to merge 3 commits into
base: main
Choose a base branch
from

Conversation

Saadnajmi
Copy link
Contributor

@Saadnajmi Saadnajmi commented Oct 4, 2024

Summary:

Update React Native on iOS to do less manual memory management, by replacing uses of CGColorRef with UIColor, and only calling UIColor.CGColor when needed. This results in much less manual memory management, which is probably a good thing in 2024 :D. The downside is there is a breaking change: the signature of a method in RCTBorderDrawing changes.

This is a followup to #46797 . After that PR merged and I tested merging React Native macOS to the 0.76-stable branch cut commit again, I saw even more places I needed to manually call CGColorRetain / CGColorRelease. The reason is due to React Native macOS specifics (explained below) and I could update React Native macOS to not need these changes, but I thought I would at least throw up a PR to propose the changes, as it may be good to move away from using Core Graphics' C base API as much as possible.

Longer Explanation

With microsoft#2209 , I wrote a shim of UIGraphicsImageRenderer for macOS. The main difference is my shim calls the NSImage API imageWithSize:flipped:drawingHandler: to shim the UIGraphicsImageRenderer API imageWithData:. The difference between the two is that the macOS API copies the block, and executes it when Appkit is about to draw the image, while the iOS API executes the block right away. Because of this, I think I am hitting way more places where CGColorRef variables needed to be retained / released. Additionally, I hit more of them when I merge to the 0.76 branch cut commit (this is why I didn't catch it with #46797).

Given this constraint, I have a couple of options:

  1. Refactor my macOS shim to use the deprecated API [NSImage lockFocus]
    • I am not a fan of this because lockFocus was deprecated for imageWithSize:flipped:drawingHandler:
  2. Refactor my macOS shim to do what we used to do: Create a CGContext manually and write it to an image
    • This is probably OK. Relies on less Appkit specifics, and potentially gives more control to RN on the rendering layer, which I recall @lenaic told me is better for Fabric)
  3. Refactor React Native to avoid CGColorRef altogether, and use UIColor (which ARC will memory manage for us) as much as possible.
    • This is the approach of this PR and my preferred approach. The downside is this changes the signature of some of the methods in RCTBorderDrawing which is a breaking change. I've seen other PRs do this, so maybe its OK?

Changelog:

[IOS] [BREAKING] - Replace uses of CGColorRef with UIColor to avoid manual memory management

Test Plan:

Launching RNTester's View example (which tests a lot of the border / outline / shadow rendering) does not crash for me on both iOS and macOS.

@facebook-github-bot facebook-github-bot added CLA Signed This label is managed by the Facebook bot. Authors need to sign the CLA before a PR can be reviewed. p: Microsoft Partner: Microsoft Partner Shared with Meta Applied via automation to indicate that an Issue or Pull Request has been shared with the team. labels Oct 4, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
CLA Signed This label is managed by the Facebook bot. Authors need to sign the CLA before a PR can be reviewed. p: Microsoft Partner: Microsoft Partner Shared with Meta Applied via automation to indicate that an Issue or Pull Request has been shared with the team.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants