Android SVG.toDataURL Rendering results in indexOutOfBoundsException
See original GitHub issueGreetings,
When I attempt to render a hidden SVG using toDataURL I fairly consistently end up with an java.lang.IndexOutOfBoundsException. However, I do not encounter it at the same index consistently.
I have narrowed the exception down to being involved in GlyphContext.popContext
every time. However, I’m uncertain how the ArrayList
s that are involved are getting out of sync with the mTop
variable.
I have collected a few stack traces for when it has occurred:
Here are my relevant versions:
react-native-cli: 2.0.1
react-native: 0.58.4
react-native-svg: 9.2.4
The Device I am running this on is a Pixel 3 XL Running Android Pie (Android 9) Build Number PQ1A.190105.004
The SVG Element I am rendering has the following structure after I perform an auto-text sizing pass on it. I am attempting to invoke the toDataURL
method after a callback from onLayout
being passed to the Svg
element (not shown).
Here is the following structure.
<Svg width={1000} height={720} fill="#ffff" style={{ width: 1000, height: 720 }}>
<Group width={1000} height={720} scale={scale}>
<Group x={46} y={46} width={908} height={628}>
<Group x={0} y={0} width={908} height={380}>
<G x={0} y={0} width={908} height={380}>
<Rect
width={908}
height={380}
fill="#fff0"
/>
<Text
lengthAdjust="spacingAndGlyphs"
fill="#000"
fontFamily="sans-serif"
textAnchor="middle"
alignmentBaseline="central"
fontWeight="800"
>
{[{
ax: 908 * 0.5,
ay: 180 * 0.5
text: "given",
fontSize: 140
}].map((line, index) => {
return (
<TSpan
key={index}
x={line.ax}
y={line.ay}
fontSize={line.fontSize}
>
{line.text}
</TSpan>
);
})}
</Text>
</G>
<G x={0} y={180} width={908} height={140}>
<Rect
width={908}
height={140}
fill="#fff0"
/>
<Text
lengthAdjust="spacingAndGlyphs"
fill="#000"
fontFamily="sans-serif"
textAnchor="middle"
alignmentBaseline="central"
fontWeight="600"
>
{[{
ax: 908 * 0.5,
ay: 140 * 0.5
text: "family",
fontSize: 90
}].map((line, index) => {
return (
<TSpan
key={index}
x={line.ax}
y={line.ay}
fontSize={line.fontSize}
>
{line.text}
</TSpan>
);
})}
</Text>
</G>
<G x={0} y={320} width={908} height={60}>
<Rect
width={908}
height={60}
fill="#fff0"
/>
<Text
lengthAdjust="spacingAndGlyphs"
fill="#000"
fontFamily="sans-serif"
textAnchor="middle"
alignmentBaseline="central"
fontWeight="300"
>
{[{
ax: 908 * 0.5,
ay: 60 * 0.5
text: "company",
fontSize: 60
}].map((line, index) => {
return (
<TSpan
key={index}
x={line.ax}
y={line.ay}
fontSize={line.fontSize}
>
{line.text}
</TSpan>
);
})}
</Text>
</G>
</Group>
<Group x={0} y={380} width={908} height={248}>
<Group y={0} width={908} height={208}>
{badgeImageData && <Image width={908} height={188} href={{ uri: badgeImageData }} />}
</Group>
<G x={0} y={320} width={908} height={40}>
<Rect
width={908}
height={40}
fill="#fff0"
/>
<Text
lengthAdjust="spacingAndGlyphs"
fill="#000"
fontFamily="sans-serif"
textAnchor="middle"
alignmentBaseline="central"
fontWeight="300"
>
{[{
ax: 908 * 0.5,
ay: 40 * 0.5
text: "tag",
fontSize: 40
}].map((line, index) => {
return (
<TSpan
key={index}
x={line.ax}
y={line.ay}
fontSize={line.fontSize}
>
{line.text}
</TSpan>
);
})}
</Text>
</G>
</Group>
</Group>
</Group>
</Svg>
Here are some of the stack traces I have collected:
D/AndroidRuntime: Shutting down VM
E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.app.my, PID: 20441
java.lang.IndexOutOfBoundsException: Index: 2, Size: 2
at java.util.ArrayList.remove(ArrayList.java:503)
at com.horcrux.svg.GlyphContext.popContext(GlyphContext.java:264)
at com.horcrux.svg.GroupView.popGlyphContext(GroupView.java:74)
at com.horcrux.svg.TSpanView.getPath(TSpanView.java:104)
at com.horcrux.svg.GroupView.getPath(GroupView.java:148)
at com.horcrux.svg.TextView.getGroupPath(TextView.java:199)
at com.horcrux.svg.TextView.draw(TextView.java:136)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:102)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:102)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:102)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:102)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:102)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.SvgView.drawChildren(SvgView.java:281)
at com.horcrux.svg.SvgView.drawOutput(SvgView.java:233)
at com.horcrux.svg.SvgView.onDraw(SvgView.java:102)
at android.view.View.draw(View.java:20207)
at android.view.View.updateDisplayListIfDirty(View.java:19082)
at android.view.View.draw(View.java:19935)
at android.view.ViewGroup.drawChild(ViewGroup.java:4333)
at android.view.ViewGroup.dispatchDraw(ViewGroup.java:4112)
at com.facebook.react.views.view.ReactViewGroup.dispatchDraw(ReactViewGroup.java:672)
at android.view.View.updateDisplayListIfDirty(View.java:19073)
at android.view.View.draw(View.java:19935)
at android.view.ViewGroup.drawChild(ViewGroup.java:4333)
at android.view.ViewGroup.dispatchDraw(ViewGroup.java:4112)
at com.facebook.react.ReactRootView.dispatchDraw(ReactRootView.java:225)
at android.view.View.updateDisplayListIfDirty(View.java:19073)
at android.view.View.draw(View.java:19935)
at android.view.ViewGroup.drawChild(ViewGroup.java:4333)
at android.view.ViewGroup.dispatchDraw(ViewGroup.java:4112)
at android.view.View.updateDisplayListIfDirty(View.java:19073)
at android.view.View.draw(View.java:19935)
at android.view.ViewGroup.drawChild(ViewGroup.java:4333)
at android.view.ViewGroup.dispatchDraw(ViewGroup.java:4112)
at android.view.View.updateDisplayListIfDirty(View.java:19073)
at android.view.View.draw(View.java:19935)
at android.view.ViewGroup.drawChild(ViewGroup.java:4333)
at android.view.ViewGroup.dispatchDraw(ViewGroup.java:4112)
at android.view.View.draw(View.java:20210)
at com.android.internal.policy.DecorView.draw(DecorView.java:780)
at android.view.View.updateDisplayListIfDirty(View.java:19082)
at android.view.ThreadedRenderer.updateViewTreeDisplayList(ThreadedRenderer.java:686)
at android.view.ThreadedRenderer.updateRootDisplayList(ThreadedRenderer.java:692)
at android.view.ThreadedRenderer.draw(ThreadedRenderer.java:801)
at android.view.ViewRootImpl.draw(ViewRootImpl.java:3311)
at android.view.ViewRootImpl.performDraw(ViewRootImpl.java:3115)
at android.view.ViewRootImpl.performTraversals(ViewRootImpl.java:2484)
at android.view.ViewRootImpl.doTraversal(ViewRootImpl.java:1460)
at android.view.ViewRootImpl$TraversalRunnable.run(ViewRootImpl.java:7183)
at android.view.Choreographer$CallbackRecord.run(Choreographer.java:949)
at android.view.Choreographer.doCallbacks(Choreographer.java:761)
at android.view.Choreographer.doFrame(Choreographer.java:696)
E/AndroidRuntime: at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:935)
at android.os.Handler.handleCallback(Handler.java:873)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:193)
at android.app.ActivityThread.main(ActivityThread.java:6718)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:493)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:858)
E/unknown:ReactNative: Exception in native call
java.lang.ArrayIndexOutOfBoundsException: length=10; index=-1
at java.util.ArrayList.get(ArrayList.java:439)
at com.horcrux.svg.GlyphContext.popContext(GlyphContext.java:279)
at com.horcrux.svg.GroupView.popGlyphContext(GroupView.java:74)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:126)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:102)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:102)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:102)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:102)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.SvgView.drawChildren(SvgView.java:281)
at com.horcrux.svg.SvgView.toDataURL(SvgView.java:315)
at com.horcrux.svg.SvgViewModule.toDataURL(SvgViewModule.java:44)
at java.lang.reflect.Method.invoke(Native Method)
at com.facebook.react.bridge.JavaMethodWrapper.invoke(JavaMethodWrapper.java:372)
at com.facebook.react.bridge.JavaModuleWrapper.invoke(JavaModuleWrapper.java:158)
at com.facebook.react.bridge.queue.NativeRunnable.run(Native Method)
at android.os.Handler.handleCallback(Handler.java:873)
at android.os.Handler.dispatchMessage(Handler.java:99)
at com.facebook.react.bridge.queue.MessageQueueThreadHandler.dispatchMessage(MessageQueueThreadHandler.java:29)
at android.os.Looper.loop(Looper.java:193)
at com.facebook.react.bridge.queue.MessageQueueThreadImpl$3.run(MessageQueueThreadImpl.java:192)
at java.lang.Thread.run(Thread.java:764)
E/unknown:ReactNative: Exception in native call
java.lang.IndexOutOfBoundsException: Index: 1, Size: 1
at java.util.ArrayList.get(ArrayList.java:437)
at com.horcrux.svg.GlyphContext.popContext(GlyphContext.java:282)
at com.horcrux.svg.GroupView.popGlyphContext(GroupView.java:74)
at com.horcrux.svg.TextView.getGroupPath(TextView.java:200)
at com.horcrux.svg.TextView.draw(TextView.java:136)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:102)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:102)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:102)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:102)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.GroupView.drawGroup(GroupView.java:102)
at com.horcrux.svg.GroupView.draw(GroupView.java:81)
at com.horcrux.svg.RenderableView.render(RenderableView.java:311)
at com.horcrux.svg.SvgView.drawChildren(SvgView.java:281)
at com.horcrux.svg.SvgView.toDataURL(SvgView.java:315)
at com.horcrux.svg.SvgViewModule.toDataURL(SvgViewModule.java:44)
at java.lang.reflect.Method.invoke(Native Method)
at com.facebook.react.bridge.JavaMethodWrapper.invoke(JavaMethodWrapper.java:372)
at com.facebook.react.bridge.JavaModuleWrapper.invoke(JavaModuleWrapper.java:158)
at com.facebook.react.bridge.queue.NativeRunnable.run(Native Method)
at android.os.Handler.handleCallback(Handler.java:873)
at android.os.Handler.dispatchMessage(Handler.java:99)
at com.facebook.react.bridge.queue.MessageQueueThreadHandler.dispatchMessage(MessageQueueThreadHandler.java:29)
at android.os.Looper.loop(Looper.java:193)
at com.facebook.react.bridge.queue.MessageQueueThreadImpl$3.run(MessageQueueThreadImpl.java:192)
at java.lang.Thread.run(Thread.java:764)
I apologize for the long post, but I wanted to provide enough information to potentially identify where the issue may be. As I stated before, it seems odd that the structures would become out-of-sync with the mTop
variable, but that’s what it seems like is occurring to me.
As a last note, this is the correct version of the plugin, but I did merge the fork to allow for the toDataURL
calls to allow for a specified height
and width
, in order to rasterize a smaller image size. However, it doesn’t seem like it should affect anything.
Please let me know if you have any questions,
Thanks,
~ Ayiga
Issue Analytics
- State:
- Created 5 years ago
- Comments:13
Top GitHub Comments
Can you try with v9.2.5 ? This seems to work fine at least:
Thank you 😃 … I tried with v 9.2.3 as well, and it works perfectly like before