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

[OpenFL 8.9.1] Performance issues in HTML5 targets with TextField.appendText(...) #2229

Closed
TamarCurry opened this issue Aug 2, 2019 · 19 comments
Assignees

Comments

@TamarCurry
Copy link

In HTML5 targets, using the appendText(...) function in a TextField instance causes a significant pause if a lot of text is on display.

I made a test case app that can be viewed here: http://tamarcurry.com/openFLTextPerformance.

From what I can tell, this is due to the getLayoutGroups() function in openfl._internal.text.TextEngine.hx making numerous calls to __context.measureText(...), iterating through several loops, and many internal functions.

We feel finding a solution would benefit the entire OpenFL community and have created a bug bounty for this issue. The details of it can be found here: https://github.com/streiffus/OpenFLTextPerformance.

@larsiusprime
Copy link
Contributor

Tagging @MSGhero and @jgranick :)

@MSGhero
Copy link
Contributor

MSGhero commented Aug 3, 2019

It's like 1 ms for each function call on Flash and doesn't increase, so I guess it's not recalculating the entire field every time. Idk how to get around measureText() since I know nothing about JS, but we can probably make it 7 ms each append for this test case.

Pretty big scope actually, so it's on my list but not gonna resolve it right away. An issue with your solution is that the kerning can vary between characters based on the font, so caching two letter widths and measuring the width of two letters can be different. Arabic and Farsi are the extreme cases where letters actually combine.

@MSGhero MSGhero self-assigned this Aug 3, 2019
@larsiusprime
Copy link
Contributor

Let it be known that I'll match @streiffus bug bounty of $50, bringing the total up to $100, as I can foresee needing this myself in a future project.

@MSGhero
Copy link
Contributor

MSGhero commented Aug 3, 2019

Well, if anyone wants to give it a try, my solution would be for getLayoutGroups to take textIndex as an argument instead of always starting at 0. This would let you “resume” the layout at the point where appending starts.

Gotta make sure that the previous text already on that first line you append gets its baseline and max line height set properly. Maybe Flash recalculates the entire last line, or maybe it can resume the layout function cleanly. You can tell by turning wordWrap off in the append example above, deleting any newlines in the text, and seeing if the time is constant or increases on Flash (would increase if recalculating the entire line, which is getting longer and longer now).

Kind of a minor concern is if the first appended character is supposed to combine with the last character of the original string. I don’t fully understand how it works yet, but that could force you to recalculate the line as opposed to cleanly resuming.

@MSGhero
Copy link
Contributor

MSGhero commented Aug 3, 2019

I would also add using the above example, but alternating with replaceSelectedText, to see how long Flash text layout takes in relative terms. For instance, I don't think modifying one paragraph has any impact on any other paragraph in the text, aside from a new y offset, so that could be an optimization. Stuff like that.

@MSGhero
Copy link
Contributor

MSGhero commented Oct 8, 2020

So I figured I would be the one to tackle this, and the notes I left are very helpful actually. Thanks past me

Also thanks @streiffus for the test case, that will be very helpful

@MSGhero
Copy link
Contributor

MSGhero commented Oct 8, 2020

Flash's append time is actually a constant 0–1 ms no matter the paragraph size. Prepending text (replaceText(0, 0, lorem)) slowly increases the time, 5 ms after 40 presses or so.

@MSGhero
Copy link
Contributor

MSGhero commented Dec 10, 2020

@streiffus if you're still in this loop, I have a solution in #2437, although I wouldn't call it the solution. I've been using your code for all performance related changes, super helpful 😄

@TamarCurry
Copy link
Author

Cool, I will test out your code this weekend :)

@TamarCurry
Copy link
Author

TamarCurry commented Dec 14, 2020

@MSGhero unfortunately it seems I can't run the latest code from OpenFL dev for some reason. Previous release versions of the code work, just not dev for me. Weird. So for the moment I can't tell if your changes work since they seem to be tied to the latest code.

@Dimensionscape
Copy link
Member

What problem are you having? Dev branch should work.

@TamarCurry
Copy link
Author

@Dimensionscape I downloaded and installed from the ZIP files for OpenFL since I don't have Github setup on this laptop yet. I was getting build errors saying it couldn't find openfl.Lib and none of the OpenFL classes were showing up in my project. Downgraded to 9.0.2 and that seemed to fix it. So it's definitely something wrong with the setup with using dev on my end, but I'm not sure at the moment and it's getting pretty late.

@Dimensionscape
Copy link
Member

Hmm sorry, I just checked, dev running fine :( But hey, the changes he made arent in dev yet. You can find them here: https://github.com/MSGhero/openfl/tree/text/placement-index

@MSGhero
Copy link
Contributor

MSGhero commented Dec 14, 2020

Yeah sorry, you'll have to manually put them in (or pull my branch) since they haven't been merged into dev yet: https://github.com/openfl/openfl/pull/2437/files

@TamarCurry
Copy link
Author

I got Github installed and pulled from the branch, but now I'm getting a bunch of errors with being unable to find various classes in lime. I don't want to turn this into a tech support thread since that just bloats the comment section and my build issues are insignificant compared to this potential fix. I'll keep trying, though!

@Dimensionscape
Copy link
Member

@streiffus I'm working on a solution to solve all of the text performance regardless of insertion point. You can test it here https://openfl-fast-vs-slow-text.surge.sh/ . I will finish it up after the holidays 😄

@Dimensionscape
Copy link
Member

Dimensionscape commented Dec 25, 2020

#2449 this should fix performance for insertions anywhere. Enjoy! Happy holidays. https://github.com/Dimensionscape/openfl/tree/textfield-performance-fix

https://openfl-fast-vs-slow-text-any-insertion.surge.sh/
Live example: (note multiple characters without a break still create some significant framerate loss but I believe this is slightly unrelated. I am looking into this as well)

@Dimensionscape
Copy link
Member

Dimensionscape commented Mar 11, 2021

I'm really proud of what was accomplished in 9.1.0's TextField in terms of performance and stability. It's not perfect, but it is immensely improved and we will continue to look at ways that we can make it stabler and faster on all targets. 😄

#2466

@TamarCurry
Copy link
Author

@Dimensionscape @MSGhero nice! Can you guys message me at tamar ((dot)) curry ((at)) gmail so we can arrange for you to claim the bug bounty?

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

No branches or pull requests

4 participants