# Draggable marker

*Category:* Components
*Section:* Map
*Source:* https://uikit.developers.rio.cloud/#/components/mapDraggableMarker
*Captured:* 2026-04-27T14:58:51.354Z

## Draggable marker

### Example: Example 1

Terms of use © 1987–2026 HERE

10 km

Choose view
Map view
Satellite

Traffic conditions
Show traffic incidents

Marker position {"lat":48.16,"lng":11.38}

#### React (tsx)

```tsx
// See https://www.here.com/docs/bundle/draggable-marker/page/README.html

import { useState, useRef } from 'react';

import Map from '@rio-cloud/rio-uikit/Map';
import EventUtils from '@rio-cloud/rio-uikit/EventUtils';
import Marker from '@rio-cloud/rio-uikit/Marker';
import SingleMapMarker from '@rio-cloud/rio-uikit/SingleMapMarker';

import { UIKIT_DEMO_CREDENTIALS_ARE_NOT_ALLOWED_IN_PROD_ENVIRONMENT } from '../uikit_demo_credentials';
import type { MapApi, MapEvent, Position } from '@rio-cloud/rio-uikit/mapTypes';

const initialMapPosition = { lat: 48.03, lng: 11.7 };

const MarkerExample = () => {
    const mapApiRef = useRef<MapApi>();

    const [markerPosition, setMarkerPosition] = useState<Position>({ lat: 48.16, lng: 11.38 });

    const mapEventListenerMap = {
        [EventUtils.TAP]: (event: MapEvent) => {
            const pointer = event.currentPointer;
            setMarkerPosition(mapApiRef.current?.map.screenToGeo(pointer.viewportX, pointer.viewportY));
        },
    };

    const markerEventListenerMap = {
        [EventUtils.DRAG_START]: (event: MapEvent) => {
            // disable the default draggability of the underlying map
            // and calculate the offset between mouse and target's position
            // when starting to drag a marker object:
            const target = event.target;
            const pointer = event.currentPointer;

            if (target.draggable) {
                const targetPosition = mapApiRef.current?.map.geoToScreen(target.getGeometry());
                target.offset = new H.math.Point(
                    pointer.viewportX - targetPosition.x,
                    pointer.viewportY - targetPosition.y
                );
                mapApiRef.current?.behavior.disable();
            }
        },
        [EventUtils.DRAG_END]: (event: MapEvent) => {
            // re-enable the default draggability of the underlying map
            // when dragging has completed
            const target = event.target;
            if (target.draggable) {
                mapApiRef.current?.behavior.enable();
            }

            // Update final map marker position
            const pointer = event.currentPointer;
            setMarkerPosition(
                mapApiRef.current?.map.screenToGeo(
                    pointer.viewportX - target.offset.x,
                    pointer.viewportY - target.offset.y
                )
            );
        },
        [EventUtils.DRAG]: (event: MapEvent) => {
            // Listen to the drag event and move the position of the marker
            // as necessary
            const target = event.target;
            const pointer = event.currentPointer;
            if (target.draggable) {
                target.setGeometry(
                    mapApiRef.current?.map.screenToGeo(
                        pointer.viewportX - target.offset.x,
                        pointer.viewportY - target.offset.y
                    )
                );
            }
        },
    };

    return (
        <>
            <Map
                credentials={UIKIT_DEMO_CREDENTIALS_ARE_NOT_ALLOWED_IN_PROD_ENVIRONMENT}
                center={initialMapPosition}
                zoom={10}
                height={550}
                eventListenerMap={mapEventListenerMap}
            >
                {(api: MapApi) => {
                    mapApiRef.current = api;

                    return (
                        <Marker
                            position={markerPosition}
                            icon={<SingleMapMarker iconNames={['pushpin']} markerColor='bg-map-marker-poi' />}
                            eventListenerMap={markerEventListenerMap}
                            draggable
                        />
                    );
                }}
            </Map>
            <div className='margin-top-15'>
                <label>Marker position</label>
                <div>{JSON.stringify(markerPosition)}</div>
            </div>
        </>
    );
};

export default MarkerExample;
```