Mobile 개발/RN Project - Map Chat

RN (React Native) - 네이버지도, 클릭 위치 marker 표시

히핑소 2020. 9. 12. 22:39
반응형

지난 번 React Native 네이버지도 연동에 이어

 

React Native 네이버지도 연동

리액트 네이티브 네이버지도 연동 방법 입니다. 개발환경 : Android, react-native cli (expo 아님) 구글링을 열심히 해본 결과 크게 2군데 react-naver map 브릿지를 제공하고 있었습니다. - zeakd.github.io/rea..

yannichoongs.tistory.com

오늘은 지도화면 클릭 시 marker 표시를 해보겠습니다.

변경 된 코드 적용 시 대략 이런 동작을 하게 됩니다.

MapViewScreen function component 를 아래와 같이 변경합니다. 총 4곳 수정.

- 동적 marker 이동을위해 useState 로 location 위도,경도 정의.
초기 위치는 제가 좋아하는 한강 밤섬.

- locationhandler : 클릭 시 alert 을 띄우고 OK 시 해당 위치에 marker 표시.
console warning 은 필요에 따라 사용.

    const [currentLocation, setCurrentLocation] = useState({latitude: 37.53815725, longitude: 126.9307627});
    const locationHandler = (e) => {
        // setCurrentLocation(e.latitude, e.longitude);
        Alert.alert(
            "",
            "Marker?",
            [
                { text: 'Cancel'},
                { text: 'OK', onPress: () => {
                    setCurrentLocation(e);
                    console.warn('onMapClick', JSON.stringify(e));
                }}
            ],
            { cancelable: false }
        );
    };

 

 

- mapclick 시 locationHandler component 로 event 전달

    onMapClick={e => locationHandler(e)}

- marker coordinate 값으로 currentLocation set.
    <Marker coordinate={currentLocation}/>

const MapViewScreen = ({navigation}) => {
    useEffect(() => {
        requestLocationPermission();
    }, []);

    const [currentLocation, setCurrentLocation] = useState({latitude: 37.53815725, longitude: 126.9307627});
    const locationHandler = (e) => {
        Alert.alert(
            "",
            "Marker?",
            [
                { text: 'Cancel'},
                { text: 'OK', onPress: () => {
                    setCurrentLocation(e);
                    console.warn('onMapClick', JSON.stringify(e));
                }}
            ],
            { cancelable: false }
        );
    };

    return <>
        <NaverMapView style={{width: '100%', height: '100%'}}
                      showsMyLocationButton={true}
                      center={{...currentLocation, zoom: 16}}
                      onTouch={e => console.warn('onTouch', JSON.stringify(e.nativeEvent))}
                      onCameraChange={e => console.warn('onCameraChange', JSON.stringify(e))}
                    //   onMapClick={e => console.warn('onMapClick', JSON.stringify(e))}
                    // onMapClick={e => locationHandler(e)}
                    onMapClick={e => locationHandler(e)}
                    useTextureView>
            <Marker coordinate={currentLocation}/>
        </NaverMapView>
        <TouchableOpacity style={{position: 'absolute', bottom: '10%', right: 8}} onPress={() => navigation.navigate('Away')}>
            <View style={{backgroundColor: 'gray', padding: 4}}>
                <Text style={{color: 'white'}}>Chat</Text>
            </View>
        </TouchableOpacity>
    </>
};

 

<marker /> 만 정의하면 기본 green marker 가 표시되고,

color 나 image, align 등등 필요에 따라 customizing 하시면 되겠습니다.

<Marker coordinate={P0} onClick={() => console.warn('onClick! p0')} caption={{text: "test caption", align: Align.Left}}/>
<Marker coordinate={P1} pinColor="blue" onClick={() => console.warn('onClick! p1')}/>
<Marker coordinate={P2} pinColor="red" onClick={() => console.warn('onClick! p2')}/>
<Marker coordinate={P4} onClick={() => console.warn('onClick! p4')} image={require("./marker.png")} width={48} height={48}/>

Marker class 가 MarkerProps 를, props 는 MapOverlay를 상속하고 있는 구조이므로

MarkerProps 에 있는 variable 을 필요에 맞게 사용하면 될 것 같습니다.

export interface Coord {
    latitude: number;
    longitude: number;
}
export interface MapOverlay {
    coordinate: Coord;
    onClick?: () => void;
}
export interface MarkerProps extends MapOverlay {
    anchor?: {
        x: number;
        y: number;
    };
    pinColor?: string;
    rotation?: number;
    flat?: boolean;
    image?: ImageSourcePropType;
    width?: number;
    height?: number;
    alpha?: number;
    animated?: boolean;
    caption?: {
        text?: string;
        align?: Align;
        textSize?: number;
        color?: string;
        haloColor?: string;
    };
    subCaption?: {
        text?: string;
        textSize?: number;
        color?: number;
        haloColor?: number;
    };
}
export declare class Marker extends Component<MarkerProps> {
    render(): JSX.Element;
}

 

반응형