Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Points become little blue dots #40

Open
Denissavv opened this issue Mar 12, 2024 · 2 comments
Open

Points become little blue dots #40

Denissavv opened this issue Mar 12, 2024 · 2 comments

Comments

@Denissavv
Copy link

When I zoom-in or zoom-out, some points feels like trying to become cluster, but turn on into a little blue points.
Снимок экрана 2024-03-12 в 11 32 35

When I add key (as it shown in the example -
key={item.properties?.cluster_id ?? point-${item.properties?.id}} - blue points appear, when I remove key - the issue is fix, but I guess that clusters and points re-render every map changing position.

@JiriHoffmann
Copy link
Owner

JiriHoffmann commented Mar 25, 2024

This is most likely an issue with your rendering of map markers - unsure what else could be causing this issue without seeing the code.

@Denissavv
Copy link
Author

Sorry for my poor question, let me try to show you the whole implementation:

im using
import { YaMap } from 'react-native-yamap';

the thing is - there is no latitudeDelta and longitudeDelta after changing position of maps camera, so I calculated myself.

export const getRegionForZoom = (lat: number, lon: number, zoom: number): MapRegion => {
  const distanceDelta = Math.exp(Math.log(360) - zoom * Math.LN2);
  const { width, height } = Dimensions.get('window');
  const aspectRatio = width / height;
  return {
    latitude: lat,
    longitude: lon,
    latitudeDelta: distanceDelta * aspectRatio,
    longitudeDelta: distanceDelta,
  };
}
const [westLng, setWestLng] = useState(INITIAL_WEST_LNG);
  const [southLat, setSouthLat] = useState(INITIAL_SOUTH_LAT);
  const [eastLng, setEastLng] = useState(INITIAL_EAST_LNG);
  const [northLat, setNorthLat] = useState(INITIAL_NORTH_LAT);


  const convertedArray: IFeature[] = points
    .filter((data) => data.location.longitude !== '0' || data.location.latitude !== '0')
    .map((item) => ({
      type: 'Feature' as const,
      geometry: {
        type: 'Point' as const,
        coordinates: [+item.location.longitude, +item.location.latitude],
      },
      properties: {
        ...item,
        ...item.location,
        ...item.owner,
        id: item._id,
        data: item,
      },
    }));

  const superCluster = new Supercluster(superclusterOptions);
  superCluster.load(convertedArray);

  const clustersAndPoints = superCluster.getClusters([westLng, southLat, eastLng, northLat], zoom);

my render is looks like:

return (
  <YaMap
    ref={mapRef}
    logoPadding={{ vertical: 670, horizontal: 30 }}
    showUserPosition={false}
    initialRegion={{ lon: MoscowPoint.lon, lat: MoscowPoint.lat }}
    style={RN.StyleSheet.absoluteFillObject}
    onLayout={() => setMapIsReady(true)}
    onCameraPositionChangeEnd={(event) => {
      if (event.nativeEvent.finished) {
        setWestLng(INITIAL_WEST_LNG);
        setSouthLat(INITIAL_SOUTH_LAT);
        setEastLng(INITIAL_EAST_LNG);
        setNorthLat(INITIAL_NORTH_LAT);
        mapRef.current?.getCameraPosition((position) => {
          const { lat, lon } = position.point;
          const { zoom } = position;

          handleChangeRegion({
            ...getRegionForZoom(lat, lon, zoom),
          });
          handleChangeZoom(position.zoom);
        });
      }
    }}
  >
    <UserLocationMarker />
    <Clusterer
      data={clustersAndPoints}
      region={region}
      options={{
        radius: 20,
        extent: 600,
        minPoints: 3,
        minZoom: 0,
      }}
      mapDimensions={MAP_DIMENSIONS}
      renderItem={(item) => {
        const clusterId: number = item.properties?.cluster && item.properties?.cluster_id;
        const markerId: string = item.properties?.id;

        return (
          <ClusterAndMarkerPoint
            points={clustersAndPoints}
            clusterId={clusterId}
            markerId={markerId}
            item={item}
            onPress={
              item?.properties?.cluster &&
              item?.properties?.cluster_id !== null &&
              (() => {
                const clusterId = item?.properties?.cluster_id;
                const clusterArr: Array<number> = clustersAndPoints.map((data) => data.properties.cluster_id);
                const isClusterExist = clusterArr.includes(clusterId);
                const toCluster = {
                  lon: item?.geometry?.coordinates[0],
                  lat: item?.geometry?.coordinates[1],
                };
                if (clusterId !== undefined && isClusterExist) {
                  getClusterZoom(clusterId);
                } else {
                  if (zoom < 7) {
                    handleChangeZoom(7, toCluster, 0.6);
                  } else if (zoom < 10 && zoom > 7) {
                    handleChangeZoom(10, toCluster, 0.6);
                  } else {
                    handleChangeZoom(zoom + 3, toCluster, 0.6);
                  }
                  console.warn(`No cluster with the specified id: ${clusterId}`);
                }
              })
            }
          />
        );
      }}
    />
  </YaMap>
)

and my ClusterAndMarkerPoint:

export const ClusterAndMarkerPoint: FunctionComponent<Props> = memo(
({ item, onPress, clusterId, markerId, points }) => {
  const [logoLoaded, setLogoLoaded] = React.useState(false);

  const clusterArr: Array<number> = points.map((data) => data.properties.cluster_id);

  const handlePress = useRecoilCallback(
    ({ get, set, reset }) =>
      (id: string) => {
        if (get(openedChargePointAtom)) {
          return;
        }

        set(openedChargePointAtom, id);
        chargersScreenBottomSheetsShowablePortal.current?.show(
          `DetailedChargePoint(id=${id})`,
          DetailedStationSheet,
          {
            chargePointId: id,
            onClose: () => {
              reset(openedChargePointAtom);
              mapRef.current?.getCameraPosition((position) => {
                if (position.zoom > 10) {
                  mapRef.current?.setZoom(position.zoom - 1, 2, 1);
                } else {
                  mapRef.current?.setZoom(position.zoom, 2, 1);
                }
              });
            },
          }
        );
      },
    []
  );

  return (
    <YaMarker
      source={item?.properties?.logo_url && { uri: item?.properties?.logo_url }}
      key={clusterId || `${markerId + logoLoaded}`}
      point={{
        lat: +item.geometry.coordinates[1] || Number(item?.properties?.latitude),
        lon: +item.geometry.coordinates[0] || Number(item?.properties?.longitude),
      }}
      onPress={onPress || (() => handlePress(item?.properties?.id))}
    >
      {item?.properties?.cluster && clusterId ? (
        <ClusterComponent key={clusterId} clusterArr={clusterArr} item={item} />
      ) : (
        <>
          {item?.properties?.logo_url && (
            <PointComponent
              key={`${markerId + logoLoaded}`}
              markerId={markerId}
              logoUrl={item?.properties?.logo_url}
              logoLoaded={logoLoaded}
              setLogoLoaded={setLogoLoaded}
            />
          )}
        </>
      )}
    </YaMarker>
  );
},
(prevProps, nextProps) =>
  prevProps.item.properties?.cluster_id === nextProps.item.properties?.cluster_id &&
  prevProps.item.properties?.id === nextProps.item.properties?.id &&
  prevProps.item.properties?.point_count === nextProps.item.properties?.point_count &&
  prevProps.item.properties?.onPress === nextProps.item.properties?.onPress &&
  prevProps.item.properties?.getClusterExpansionRegion === nextProps.item.properties?.getClusterExpansionRegion &&
  prevProps.markerId === nextProps.markerId &&
  prevProps.clusterId === nextProps.clusterId
);

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants