diff --git a/android/.idea/misc.xml b/android/.idea/misc.xml index 25a8820..71f6ab6 100644 --- a/android/.idea/misc.xml +++ b/android/.idea/misc.xml @@ -1,15 +1,15 @@ - @@ -19,7 +19,7 @@ - + diff --git a/android/src/main/java/org/andresoviedo/app/model3D/view/ModelRenderer.java b/android/src/main/java/org/andresoviedo/app/model3D/view/ModelRenderer.java index 36b4091..d570c86 100755 --- a/android/src/main/java/org/andresoviedo/app/model3D/view/ModelRenderer.java +++ b/android/src/main/java/org/andresoviedo/app/model3D/view/ModelRenderer.java @@ -81,11 +81,13 @@ public float getFar() { public void onSurfaceCreated(GL10 unused, EGLConfig config) { // Set the background frame color float[] backgroundColor = main.getModelActivity().getBackgroundColor(); - GLES20.glClearColor(backgroundColor[0], backgroundColor[1], backgroundColor[2], backgroundColor[3]); + //add aplha channel to background to render as a overlay on camera + GLES20.glClearColor(0f, 0f, 0f, 0f); + GLES20.glClear(GLES20.GL_DEPTH_BUFFER_BIT|GLES20.GL_COLOR_BUFFER_BIT); // Use culling to remove back faces. // Don't remove back faces so we can see them - // GLES20.glEnable(GLES20.GL_CULL_FACE); + //GLES20.glEnable(GLES20.GL_CULL_FACE); // Enable depth testing for hidden-surface elimination. GLES20.glEnable(GLES20.GL_DEPTH_TEST); diff --git a/android/src/main/java/org/andresoviedo/app/model3D/view/ModelSurfaceView.java b/android/src/main/java/org/andresoviedo/app/model3D/view/ModelSurfaceView.java index 440fadc..6d91455 100755 --- a/android/src/main/java/org/andresoviedo/app/model3D/view/ModelSurfaceView.java +++ b/android/src/main/java/org/andresoviedo/app/model3D/view/ModelSurfaceView.java @@ -7,6 +7,7 @@ import org.andresoviedo.app.model3D.services.SceneLoader; import org.andresoviedo.app.util.Utils; import org.andresoviedo.app.util.content.ContentUtils; +import android.graphics.PixelFormat; import android.os.Handler; import android.opengl.GLSurfaceView; @@ -37,6 +38,10 @@ public class ModelSurfaceView extends GLSurfaceView { public ModelSurfaceView(Context context, RN3DView parent, String modelSrc, String textureSrc, float[] backgroundColor) { super(context); + //for aplha channel + this.setZOrderOnTop(true); + this.setEGLConfigChooser(8, 8, 8, 8, 16, 0); + this.getHolder().setFormat(PixelFormat.RGBA_8888); this.parent = parent; this.modelSrc = modelSrc; diff --git a/android/src/main/java/se/bonniernews/rn3d/RN3DViewManager.java b/android/src/main/java/se/bonniernews/rn3d/RN3DViewManager.java index 2e85188..bd1c96d 100755 --- a/android/src/main/java/se/bonniernews/rn3d/RN3DViewManager.java +++ b/android/src/main/java/se/bonniernews/rn3d/RN3DViewManager.java @@ -5,8 +5,8 @@ package se.bonniernews.rn3d; import android.content.Context; -import android.support.annotation.Nullable; -import android.support.annotation.NonNull; +import androidx.annotation.Nullable; +import androidx.annotation.NonNull; import android.view.ViewGroup; import com.facebook.infer.annotation.Assertions; diff --git a/android/src/main/res/values/styles.xml b/android/src/main/res/values/styles.xml new file mode 100644 index 0000000..5102275 --- /dev/null +++ b/android/src/main/res/values/styles.xml @@ -0,0 +1,11 @@ + + + + \ No newline at end of file diff --git a/index.js b/index.js index 79a07f2..f3ac3a7 100755 --- a/index.js +++ b/index.js @@ -1,11 +1,7 @@ import ModelView from './lib/ModelView' -import ARModelView from './lib/ARModelView' import Manager from './lib/Manager' -import ARManager from './lib/ARManager' export { ModelView, - ARModelView, Manager, - ARManager } diff --git a/ios/ARKitInteraction/Utilities/Utilities.swift b/ios/ARKitInteraction/Utilities/Utilities.swift index ff8a846..ba60143 100644 --- a/ios/ARKitInteraction/Utilities/Utilities.swift +++ b/ios/ARKitInteraction/Utilities/Utilities.swift @@ -26,7 +26,8 @@ extension float4x4 { extension CGPoint { /// Extracts the screen space point from a vector returned by SCNView.projectPoint(_:). init(_ vector: SCNVector3) { - x = CGFloat(vector.x) + self.init() + x = CGFloat(vector.x) y = CGFloat(vector.y) } diff --git a/ios/RCT3DARModelView.h b/ios/RCT3DARModelView.h deleted file mode 100755 index 689d5d0..0000000 --- a/ios/RCT3DARModelView.h +++ /dev/null @@ -1,28 +0,0 @@ -#import "RCT3DModelIO.h" -#import "RCT3DModelView.h" -#import -#import -#import -#import -#import "RCT3DModel-Swift.h" - -@interface RCT3DARModelView : RCT3DModelView - -@property (nonatomic) bool miniature; -@property (nonatomic) float miniatureScale; -@property (nonatomic) float placeOpacity; - -@property (nonatomic, copy) RCTBubblingEventBlock onStart; -@property (nonatomic, copy) RCTBubblingEventBlock onSurfaceFound; -@property (nonatomic, copy) RCTBubblingEventBlock onSurfaceLost; -@property (nonatomic, copy) RCTBubblingEventBlock onSessionInterupted; -@property (nonatomic, copy) RCTBubblingEventBlock onSessionInteruptedEnded; -@property (nonatomic, copy) RCTBubblingEventBlock onPlaceObjectSuccess; -@property (nonatomic, copy) RCTBubblingEventBlock onTrackingQualityInfo; -@property (nonatomic, copy) RCTBubblingEventBlock onTapView; -@property (nonatomic, copy) RCTBubblingEventBlock onTapObject; - -- (void)restart; -- (void)takeSnapshot:(bool)saveToLibrary completion:(void (^)(BOOL success, NSURL* url))completion; - -@end diff --git a/ios/RCT3DARModelView.m b/ios/RCT3DARModelView.m deleted file mode 100755 index 241391f..0000000 --- a/ios/RCT3DARModelView.m +++ /dev/null @@ -1,177 +0,0 @@ -#import "RCT3DARModelView.h" - -@interface RCT3DARModelView () -@end - -@implementation RCT3DARModelView -{ - ARView *_arView; -} -- (instancetype)initWithFrame:(CGRect)frame { - if ((self = [super initWithFrame:frame])) { - if (@available(iOS 11.0, *)) { - _arView = [[ARView alloc] initWithFrame:frame]; - _arView.delegate = self; - [self addSubview:_arView]; - } - } - return self; -} - --(void) layoutSubviews { - [super layoutSubviews]; - if (@available(iOS 11.0, *)) { - _arView.frame = self.bounds; - } -} - --(void)loadModel { - [super loadModel]; - if (_arView != nil) { - [_arView start]; - } -} - --(void) addModelNode:(SCNNode *)node { - [super addModelNode:node]; - [self addScaleToModelNode]; - dispatch_async(dispatch_get_main_queue(), ^{ - [self setupAnimations]; - if (self.autoPlayAnimations) { - [self startAnimation]; - } else { - [self stopAnimation]; - } - self.modelNode = [_arView addVirtualObject:self.modelNode]; - }); -} - --(void) removeNode:(SCNNode *)node { - [super removeNode:node]; - [node removeFromParentNode]; -} - --(void) setScale:(float)scale { - [super setScale:scale]; - [self addScaleToModelNode]; -} - --(void) setMiniature:(bool)miniature { - if (_arView != nil) { - [_arView setMiniature:miniature]; - } -} - --(void) setMiniatureScale:(float)miniatureScale { - if (_arView != nil) { - [_arView setMinScale:miniatureScale]; - } -} - --(void) setPlaceOpacity:(float)placeOpacity { - if (_arView != nil) { - [_arView setPlaceOpac:placeOpacity]; - } -} - --(void) addScaleToModelNode { - if (self.scale && self.modelNode) { - SCNVector3 scaleV = SCNVector3Make(self.scale, self.scale, self.scale); - for(SCNNode *child in self.modelNode.childNodes) { - [child setScale:scaleV]; - } - } -} - --(void) restart { - [self stopAnimation]; - [_arView restartExperience]; -} - --(void) takeSnapshot:(bool)saveToLibrary completion:(void (^)(BOOL success, NSURL *))completion { - [_arView snapshotWithSaveToPhotoLibrary:saveToLibrary completion:completion]; -} - --(void) startAnimation { - [_arView startAnimation]; - if (self.onAnimationStart) { - self.onAnimationStart(@{}); - } -} - --(void) stopAnimation { - [_arView stopAnimation]; - if (self.onAnimationStop) { - self.onAnimationStop(@{}); - } -} - --(void) setProgress:(float)progress { - if (_arView != nil) { - [_arView setProgressWithValue:progress animationDuration:self.animationDuration]; - } -} - -// MARK: - ARViewDelegate --(void) start { - if (self.onStart) { - self.onStart(@{}); - } -} - --(void) surfaceFound { - if (self.onSurfaceFound) { - self.onSurfaceFound(@{}); - } -} - --(void) surfaceLost { - if (self.onSurfaceLost) { - self.onSurfaceLost(@{}); - } -} - --(void) sessionInterupted { - if (self.onSessionInterupted) { - self.onSessionInterupted(@{}); - } -} - --(void) sessionInteruptedEnded { - if (self.onSessionInteruptedEnded) { - self.onSessionInteruptedEnded(@{}); - } -} - --(void) trackingQualityInfoWithId:(NSInteger)id presentation:(NSString*)presentation recommendation:(NSString*)recommendation { - if (self.onTrackingQualityInfo) { - self.onTrackingQualityInfo(@{@"id": [NSNumber numberWithInteger:id], @"presentation": presentation, @"recommendation": recommendation}); - } -} - --(void) placeObjectSuccess { - if (self.onPlaceObjectSuccess) { - self.onPlaceObjectSuccess(@{}); - } -} - --(void) animationUpdateWithTime:(double)time { - if (self.onAnimationUpdate) { - NSNumber *progress = [NSNumber numberWithFloat:fmod(time, self.animationDuration) / self.animationDuration]; - self.onAnimationUpdate(@{@"progress":progress}); - } -} - --(void) tapView { - if (self.onTapView) { - self.onTapView(@{}); - } -} - --(void) tapObject { - if (self.onTapObject) { - self.onTapObject(@{}); - } -} - -@end diff --git a/ios/RCT3DARModelViewManager.h b/ios/RCT3DARModelViewManager.h deleted file mode 100755 index 096896e..0000000 --- a/ios/RCT3DARModelViewManager.h +++ /dev/null @@ -1,8 +0,0 @@ -#import -#import -#import -#import "RCT3DARModelView.h" - -@interface RCT3DARModelViewManager : RCTViewManager - -@end diff --git a/ios/RCT3DARModelViewManager.m b/ios/RCT3DARModelViewManager.m deleted file mode 100755 index 924883d..0000000 --- a/ios/RCT3DARModelViewManager.m +++ /dev/null @@ -1,130 +0,0 @@ -#import "RCT3DARModelViewManager.h" - -@implementation RCT3DARModelViewManager - -RCT_EXPORT_MODULE() - -@synthesize bridge = _bridge; - -- (UIView *)view { - if (@available(iOS 11.0, *)) { - if ([ARConfiguration isSupported]) { - return [[RCT3DARModelView alloc] init]; - } - } - return nil; -} - -- (dispatch_queue_t)methodQueue { - return _bridge.uiManager.methodQueue; -} - -RCT_EXPORT_VIEW_PROPERTY(modelSrc, NSString) -RCT_EXPORT_VIEW_PROPERTY(textureSrc, NSString) -RCT_EXPORT_VIEW_PROPERTY(scale, float) -RCT_EXPORT_VIEW_PROPERTY(autoPlayAnimations, BOOL) - -RCT_EXPORT_VIEW_PROPERTY(onLoadModelSuccess, RCTBubblingEventBlock) -RCT_EXPORT_VIEW_PROPERTY(onLoadModelError, RCTBubblingEventBlock) -RCT_EXPORT_VIEW_PROPERTY(onAnimationStart, RCTBubblingEventBlock) -RCT_EXPORT_VIEW_PROPERTY(onAnimationStop, RCTBubblingEventBlock) -RCT_EXPORT_VIEW_PROPERTY(onAnimationUpdate, RCTBubblingEventBlock) - -// MARK: - ARView specifics -RCT_EXPORT_VIEW_PROPERTY(miniature, BOOL) -RCT_EXPORT_VIEW_PROPERTY(miniatureScale, float) -RCT_EXPORT_VIEW_PROPERTY(placeOpacity, float) - -RCT_EXPORT_VIEW_PROPERTY(onStart, RCTBubblingEventBlock) -RCT_EXPORT_VIEW_PROPERTY(onSurfaceFound, RCTBubblingEventBlock) -RCT_EXPORT_VIEW_PROPERTY(onSurfaceLost, RCTBubblingEventBlock) -RCT_EXPORT_VIEW_PROPERTY(onSessionInterupted, RCTBubblingEventBlock) -RCT_EXPORT_VIEW_PROPERTY(onSessionInteruptedEnded, RCTBubblingEventBlock) -RCT_EXPORT_VIEW_PROPERTY(onPlaceObjectSuccess, RCTBubblingEventBlock) -RCT_EXPORT_VIEW_PROPERTY(onTrackingQualityInfo, RCTBubblingEventBlock) -RCT_EXPORT_VIEW_PROPERTY(onTapView, RCTBubblingEventBlock) -RCT_EXPORT_VIEW_PROPERTY(onTapObject, RCTBubblingEventBlock) - -RCT_EXPORT_METHOD(startAnimation:(nonnull NSNumber *)reactTag) -{ - [self.bridge.uiManager addUIBlock:^(__unused RCTUIManager *uiManager, NSDictionary *viewRegistry) { - RCT3DARModelView *modelView = (RCT3DARModelView*)viewRegistry[reactTag]; - if ([modelView isKindOfClass:[RCT3DARModelView class]]) { - [modelView startAnimation]; - } else { - RCTLogError(@"Cannot startAnimation: %@ (tag #%@) is not RCT3DARModelView", modelView, reactTag); - } - }]; -} - -RCT_EXPORT_METHOD(stopAnimation:(nonnull NSNumber *)reactTag) -{ - [self.bridge.uiManager addUIBlock:^(__unused RCTUIManager *uiManager, NSDictionary *viewRegistry) { - RCT3DARModelView *modelView = (RCT3DARModelView*)viewRegistry[reactTag]; - if ([modelView isKindOfClass:[RCT3DARModelView class]]) { - [modelView stopAnimation]; - } else { - RCTLogError(@"Cannot stopAnimation: %@ (tag #%@) is not RCT3DARModelView", modelView, reactTag); - } - }]; -} - -RCT_EXPORT_METHOD(setProgress:(nonnull NSNumber *)reactTag progress:(float)progress) -{ - [self.bridge.uiManager addUIBlock:^(__unused RCTUIManager *uiManager, NSDictionary *viewRegistry) { - RCT3DARModelView *modelView = (RCT3DARModelView*)viewRegistry[reactTag]; - if ([modelView isKindOfClass:[RCT3DARModelView class]]) { - [modelView setProgress:progress]; - } else { - RCTLogError(@"Cannot setProgress: %@ (tag #%@) is not RCT3DARModelView", modelView, reactTag); - } - }]; -} - -RCT_EXPORT_METHOD(checkIfARSupported:(RCTResponseSenderBlock)callback) -{ - BOOL isSupported = NO; - if (@available(iOS 11.0, *)) { - isSupported = [ARConfiguration isSupported]; - } - callback(@[@(isSupported)]); -} - -RCT_EXPORT_METHOD(restart:(nonnull NSNumber *)reactTag) -{ - [self.bridge.uiManager addUIBlock:^(__unused RCTUIManager *uiManager, NSDictionary *viewRegistry) { - RCT3DARModelView *modelView = (RCT3DARModelView*)viewRegistry[reactTag]; - if ([modelView isKindOfClass:[RCT3DARModelView class]]) { - [modelView restart]; - } else { - RCTLogError(@"Cannot restart: %@ (tag #%@) is not RCT3DARModelView", modelView, reactTag); - } - }]; -} - -RCT_EXPORT_METHOD(getSnapshot:(nonnull NSNumber *)reactTag saveToLibrary:(BOOL)saveToLibrary - findEventsWithResolver:(RCTPromiseResolveBlock)resolve - rejecter:(RCTPromiseRejectBlock)reject) -{ - [self.bridge.uiManager addUIBlock:^(__unused RCTUIManager *uiManager, NSDictionary *viewRegistry) { - RCT3DARModelView *modelView = (RCT3DARModelView*)viewRegistry[reactTag]; - if ([modelView isKindOfClass:[RCT3DARModelView class]]) { - [modelView takeSnapshot:saveToLibrary completion:^(BOOL success, NSURL *url) { - if (success) { - if (saveToLibrary) { - resolve(@{@"success":@YES}); - } else { - resolve(@{@"success":@YES, @"url": [url path]}); - } - } else { - reject(RCTErrorUnspecified, nil, RCTErrorWithMessage(@"RCT3DModelView: Could not save image")); - } - }]; - } else { - RCTLogError(@"Cannot getSnapshot: %@ (tag #%@) is not RCT3DARModelView", modelView, reactTag); - reject(RCTErrorUnspecified, nil, RCTErrorWithMessage(@"RCT3DModelView: View is not RCT3DARModelView")); - } - }]; -} - -@end diff --git a/lib/BaseModelView.js b/lib/BaseModelView.js index 787c386..a4e7930 100644 --- a/lib/BaseModelView.js +++ b/lib/BaseModelView.js @@ -1,150 +1,161 @@ -import React from 'react' -import { Platform } from 'react-native' -import RNFetchBlob from 'rn-fetch-blob' -import RNFS, { DocumentDirectoryPath } from 'react-native-fs' -import { unzip } from 'react-native-zip-archive' -import { DefaultPropTypes } from './PropTypes' -import resolveAssetSource from 'react-native/Libraries/Image/resolveAssetSource' +import React from "react"; +import { Platform } from "react-native"; +import RNFetchBlob from "rn-fetch-blob"; +import RNFS, { DocumentDirectoryPath } from "react-native-fs"; +import { unzip } from "react-native-zip-archive"; +import { DefaultPropTypes } from "./PropTypes"; +import resolveAssetSource from "react-native/Libraries/Image/resolveAssetSource"; -export const DOCUMENTS_FOLDER = `${DocumentDirectoryPath}/rct-3d-model-view` +export const DOCUMENTS_FOLDER = `${DocumentDirectoryPath}/rct-3d-model-view`; -const ACCEPTED_MODEL_TYPES = Platform.OS === 'ios' ? ['.dae', '.obj', '.scn'] : ['.dae', '.obj'] -const ACCEPTED_TEXTURE_TYPES = ['.png', '.jpg'] +const ACCEPTED_MODEL_TYPES = + Platform.OS === "ios" ? [".dae", ".obj", ".scn"] : [".dae", ".obj"]; +const ACCEPTED_TEXTURE_TYPES = [".png", ".jpg"]; class BaseModelView extends React.Component { state = { modelSrc: null, - textureSrc: null - } + textureSrc: null, + }; - componentDidMount () { - this.loadModel(this.props) + componentDidMount() { + this.loadModel(this.props); } componentWillReceiveProps(newProps) { - if (newProps.source.zip !== this.props.source.zip || + if ( + newProps.source.zip !== this.props.source.zip || newProps.source.model !== this.props.source.model || - newProps.source.texture !== this.props.source.texture) { - this.loadModel(newProps) + newProps.source.texture !== this.props.source.texture + ) { + this.loadModel(newProps); } } loadModel = (props) => { - const {source, onLoadModelStart} = props - onLoadModelStart && onLoadModelStart() + const { source, onLoadModelStart } = props; + onLoadModelStart && onLoadModelStart(); if (source.zip) { - let zipSource - if (typeof source.zip === 'string' && source.zip.startsWith('http')) { - zipSource = source.zip + let zipSource; + if (typeof source.zip === "string" && source.zip.startsWith("http")) { + zipSource = source.zip; } else { - zipSource = resolveAssetSource(source.zip).uri + zipSource = resolveAssetSource(source.zip).uri; } if (zipSource) { this.fetch(zipSource) - .then(path => { - this.unzip(path) - .then(src => { - this.getFirstFileTypeInFolder(src, ACCEPTED_MODEL_TYPES) - .then(modelSrc => { this.setState({modelSrc}) }) - .catch(this.onLoadModelError) - this.getFirstFileTypeInFolder(src, ACCEPTED_TEXTURE_TYPES) - .then(textureSrc => { this.setState({textureSrc}) }) - .catch(this.onLoadModelError) + .then((path) => { + this.unzip(path) + .then((src) => { + this.getFirstFileTypeInFolder(src, ACCEPTED_MODEL_TYPES) + .then((modelSrc) => { + this.setState({ modelSrc }); + }) + .catch(this.onLoadModelError); + this.getFirstFileTypeInFolder(src, ACCEPTED_TEXTURE_TYPES) + .then((textureSrc) => { + this.setState({ textureSrc }); + }) + .catch(this.onLoadModelError); + }) + .catch(this.onLoadModelError); }) - .catch(this.onLoadModelError) - }) - .catch(this.onLoadModelError) + .catch(this.onLoadModelError); } } else { if (source.model) { - let modelSource - if (typeof source.model === 'string' && source.model.startsWith('http')) { - modelSource = source.model + let modelSource; + if ( + typeof source.model === "string" && + source.model.startsWith("http") + ) { + modelSource = source.model; } else { - modelSource = resolveAssetSource(source.model).uri + modelSource = resolveAssetSource(source.model).uri; } if (modelSource) { this.fetch(modelSource) - .then(modelSrc => { - this.setState({modelSrc}) - }) - .catch(this.onLoadModelError) + .then((modelSrc) => { + this.setState({ modelSrc }); + }) + .catch(this.onLoadModelError); } } if (source.texture) { - let textureSource - if (typeof source.texture === 'string' && source.texture.startsWith('http')) { - textureSource = source.texture + let textureSource; + if ( + typeof source.texture === "string" && + source.texture.startsWith("http") + ) { + textureSource = source.texture; } else { - textureSource = resolveAssetSource(source.texture).uri + textureSource = resolveAssetSource(source.texture).uri; } if (textureSource) { this.fetch(textureSource) - .then(textureSrc => { - this.setState({textureSrc}) - }) - .catch(this.onLoadModelError) + .then((textureSrc) => { + this.setState({ textureSrc }); + }) + .catch(this.onLoadModelError); } } } - } + }; - fetch (uri) { - return RNFS.mkdir(DOCUMENTS_FOLDER) - .then(() => { - const name = this.getName(uri) - const targetPath = `${DOCUMENTS_FOLDER}/${name}` - return RNFS.exists(targetPath) - .then(exists => { - if (exists) { - return targetPath + fetch(uri) { + return RNFS.mkdir(DOCUMENTS_FOLDER).then(() => { + const name = this.getName(uri); + const targetPath = `${DOCUMENTS_FOLDER}/${name}`; + return RNFS.exists(targetPath).then((exists) => { + if (false) { + //remove fetching cached file as it is leadeing to mixup of files with same name + return targetPath; } else { - return RNFetchBlob - .config({ - fileCache: true, - path: targetPath + return RNFetchBlob.config({ + fileCache: false, //don't cache files + path: targetPath, }) - .fetch('GET', uri, {}) - .then(res => res.path()) + .fetch("GET", uri, { cache: "no-cache" }) + .then((res) => { + return res.path(); + }); } - }) - }) + }); + }); } - unzip (path) { - return unzip(path, DOCUMENTS_FOLDER) - .then(unzippedPath => { - let name + unzip(path) { + return unzip(path, DOCUMENTS_FOLDER).then((unzippedPath) => { + let name; if (this.props.source.unzippedFolderName) { - name = this.props.source.unzippedFolderName + name = this.props.source.unzippedFolderName; } else { - name = this.getName(path) - name = name.includes('.zip') ? name.replace('.zip', '') : name + name = this.getName(path); + name = name.includes(".zip") ? name.replace(".zip", "") : name; } - return `${unzippedPath}/${name}` - }) + return `${unzippedPath}/${name}`; + }); } getName = (source) => { - let name = source.split('/').pop() - name = name.includes('?') ? name.substring(0, name.indexOf('?')) : name - return name - } + let name = source.split("/").pop(); + name = name.includes("?") ? name.substring(0, name.indexOf("?")) : name; + return name; + }; getFirstFileTypeInFolder = (folder, acceptedFileTypes) => { - return RNFS.readDir(folder) - .then((result) => { - const file = result.find(element => { + return RNFS.readDir(folder).then((result) => { + const file = result.find((element) => { for (let i = 0; i < acceptedFileTypes.length; i++) { if (element.path.endsWith(acceptedFileTypes[i])) { - return true + return true; } } - return false - }) - return file ? file.path : null - }) - } + return false; + }); + return file ? file.path : null; + }); + }; } -export default BaseModelView +export default BaseModelView;