React Native Retrieve Actual Image Sizes

后端 未结 4 1424
孤城傲影
孤城傲影 2020-12-24 04:56

I would like to be able to know the actual size of a network-loaded image that has been passed into I have tried using onLayout to

4条回答
  •  天涯浪人
    2020-12-24 05:40

    This answer is now out of date. See Bill's answer.

    Image.getSize(myUri, (width, height) => { this.setState({ width, height }) });
    

    Old Answer (valid for older builds of react native)

    Ok, I got it working. Currently this takes some modification of the React-Native installation as it's not natively supported.

    I followed the tips in this thread to enabled me to do this. https://github.com/facebook/react-native/issues/494

    Mainly, alter the RCTNetworkImageView.m file: add the following into setImageURL

    void (^loadImageEndHandler)(UIImage *image) = ^(UIImage *image) {
      NSDictionary *event = @{
        @"target": self.reactTag,
        @"size": @{
          @"height": @(image.size.height),
          @"width": @(image.size.width)
        }
      };
      [_eventDispatcher sendInputEventWithName:@"loaded" body:event];
    };
    

    Then edit the line that handles the load completion:

    [self.layer removeAnimationForKey:@"contents"];
    self.layer.contentsScale = image.scale;
    self.layer.contents = (__bridge id)image.CGImage;
    loadEndHandler();
    

    replace

    loadEndHandler();
    

    with

    loadImageEndHandler(image);
    

    Then in React-Native you have access to the size via the native events. data from the onLoaded function - note the documentation currently says the function is onLoad but this is incorrect. The correct functions are as follows for v0.8.0:

    onLoadStart
    onLoadProgress
    onLoaded
    onLoadError
    onLoadAbort
    

    These can be accessed like so:

    onImageLoaded: function(data){
        try{
            console.log("image width:"+data.nativeEvents.size.width);
            console.log("image height:"+data.nativeEvents.size.height);
        }catch(e){
            //error
        }
    },
    ...
    render: function(){
        return (
            
                
            
        );
    }
    

    Points to note:

    • I have set a large image window and set it inside a wrapping element of 1x1px this is because the image must fit inside if you are to retrieve meaningful values.

    • The resize mode must be 'contain' to enable you to get the correct sizes, otherwise the constrained size will be reported.

    • The image sizes are scaled proportionately to the scale factor of the device, e.g. a 200*200 image on an iPhone6 (not 6 plus) will be reported as 100*100. I assume that this also means it will be reported as 67*67 on an iPhone6 plus but I have not tested this.

    • I have not yet got this to work for GIF files which traverse a different path on the Obj-C side of the bridge. I will update this answer once I have done that.

    • I believe there is a PR going through for this at the moment but until it is included in the core then this change will have to be made to the react-native installation every time you update/re-install.

提交回复
热议问题