Skip to content

Commit 131ddb6

Browse files
committed
Implement version of toDataURL with width and height options
#855
1 parent e69d232 commit 131ddb6

6 files changed

Lines changed: 78 additions & 4 deletions

File tree

android/src/main/java/com/horcrux/svg/SvgView.java

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -306,6 +306,20 @@ String toDataURL() {
306306
return Base64.encodeToString(bitmapBytes, Base64.DEFAULT);
307307
}
308308

309+
String toDataURL(int width, int height) {
310+
Bitmap bitmap = Bitmap.createBitmap(
311+
width,
312+
height,
313+
Bitmap.Config.ARGB_8888);
314+
315+
drawChildren(new Canvas(bitmap));
316+
ByteArrayOutputStream stream = new ByteArrayOutputStream();
317+
bitmap.compress(Bitmap.CompressFormat.PNG, 100, stream);
318+
bitmap.recycle();
319+
byte[] bitmapBytes = stream.toByteArray();
320+
return Base64.encodeToString(bitmapBytes, Base64.DEFAULT);
321+
}
322+
309323
void enableTouchEvents() {
310324
if (!mResponsible) {
311325
mResponsible = true;

android/src/main/java/com/horcrux/svg/SvgViewModule.java

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
import com.facebook.react.bridge.ReactApplicationContext;
1414
import com.facebook.react.bridge.ReactContextBaseJavaModule;
1515
import com.facebook.react.bridge.ReactMethod;
16+
import com.facebook.react.bridge.ReadableMap;
1617

1718
class SvgViewModule extends ReactContextBaseJavaModule {
1819
SvgViewModule(ReactApplicationContext reactContext) {
@@ -33,4 +34,19 @@ public void toDataURL(int tag, Callback successCallback) {
3334
successCallback.invoke(svg.toDataURL());
3435
}
3536
}
37+
38+
39+
@ReactMethod
40+
public void toDataURL(int tag, ReadableMap options, Callback successCallback) {
41+
SvgView svg = SvgViewManager.getSvgViewByTag(tag);
42+
43+
if (svg != null) {
44+
successCallback.invoke(
45+
svg.toDataURL(
46+
options.getInt("width"),
47+
options.getInt("height")
48+
)
49+
);
50+
}
51+
}
3652
}

elements/Svg.js

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -49,9 +49,16 @@ export default class Svg extends Shape {
4949
this.root.setNativeProps(props);
5050
};
5151

52-
toDataURL = callback => {
53-
callback &&
54-
RNSVGSvgViewManager.toDataURL(findNodeHandle(this.root), callback);
52+
toDataURL = (callback, options) => {
53+
if (!callback) {
54+
return;
55+
}
56+
const handle = findNodeHandle(this.root);
57+
if (options) {
58+
RNSVGSvgViewManager.toDataURL(handle, options, callback);
59+
} else {
60+
RNSVGSvgViewManager.toDataURL(handle, callback);
61+
}
5562
};
5663

5764
render() {

ios/Elements/RNSVGSvgView.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,8 @@
5252

5353
- (NSString *)getDataURL;
5454

55+
- (NSString *)getDataURLwithBounds:(CGSize)bounds;
56+
5557
- (CGRect)getContextBounds;
5658

5759
- (void)drawRect:(CGRect)rect;

ios/Elements/RNSVGSvgView.m

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -247,7 +247,6 @@ - (UIView *)hitTest:(CGPoint)point withEvent:(UIEvent *)event
247247
return nil;
248248
}
249249

250-
251250
- (NSString *)getDataURL
252251
{
253252
UIGraphicsBeginImageContextWithOptions(_boundingBox.size, NO, 0);
@@ -258,6 +257,16 @@ - (NSString *)getDataURL
258257
return base64;
259258
}
260259

260+
- (NSString *)getDataURLwithBounds:(CGSize)bounds
261+
{
262+
UIGraphicsBeginImageContextWithOptions(bounds, NO, 0);
263+
[self drawRect:_boundingBox];
264+
NSData *imageData = UIImagePNGRepresentation(UIGraphicsGetImageFromCurrentImageContext());
265+
NSString *base64 = [imageData base64EncodedStringWithOptions:NSDataBase64Encoding64CharacterLineLength];
266+
UIGraphicsEndImageContext();
267+
return base64;
268+
}
269+
261270
- (void)reactSetInheritedBackgroundColor:(UIColor *)inheritedBackgroundColor
262271
{
263272
self.backgroundColor = inheritedBackgroundColor;

ios/ViewManagers/RNSVGSvgViewManager.m

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,4 +43,30 @@ - (UIView *)view
4343
}];
4444
}
4545

46+
RCT_EXPORT_METHOD(toDataURL:(nonnull NSNumber *)reactTag options:(NSDictionary *)options callback:(RCTResponseSenderBlock)callback)
47+
{
48+
[self.bridge.uiManager addUIBlock:^(RCTUIManager *uiManager, NSDictionary<NSNumber *,UIView *> *viewRegistry) {
49+
__kindof UIView *view = viewRegistry[reactTag];
50+
if ([view isKindOfClass:[RNSVGSvgView class]]) {
51+
RNSVGSvgView *svg = view;
52+
id width = [options objectForKey:@"width"];
53+
id height = [options objectForKey:@"height"];
54+
if (![width isKindOfClass:NSNumber.class] ||
55+
![height isKindOfClass:NSNumber.class]) {
56+
RCTLogError(@"Invalid width or height given to toDataURL");
57+
return;
58+
}
59+
NSNumber* w = width;
60+
NSInteger wi = (NSInteger)[w intValue];
61+
NSNumber* h = height;
62+
NSInteger hi = (NSInteger)[h intValue];
63+
64+
CGSize bounds = CGSizeMake(wi, hi);
65+
callback(@[[svg getDataURLwithBounds:bounds]]);
66+
} else {
67+
RCTLogError(@"Invalid svg returned frin registry, expecting RNSVGSvgView, got: %@", view);
68+
}
69+
}];
70+
}
71+
4672
@end

0 commit comments

Comments
 (0)