Skip to content

Automated PR to merge dev to main #384

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

Merged
merged 7 commits into from
Apr 16, 2025
2 changes: 1 addition & 1 deletion src/app/[locale]/seller/sale-items/[id]/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -174,7 +174,7 @@ export default function BuyFromSellerForm({ params }: { params: { id: string } }
alt="seller logo"
fill
sizes="(max-width: 768px) 100vw, (max-width: 1200px) 50vw, 33vw"
style={{ objectFit: 'cover', maxHeight: '200px', maxWidth: '100%' }}
style={{ objectFit: 'contain', maxHeight: '200px', maxWidth: '100%' }}
/>
</div>
<div className="my-auto">
Expand Down
2 changes: 1 addition & 1 deletion src/components/shared/About/Info/Info.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ import { CloseButton } from '@/components/shared/Forms/Buttons/Buttons';
const InfoModel = (props: any) => {
const t = useTranslations();

const [version, setVersion] = useState('v1.4.0');
const [version, setVersion] = useState('v1.5.6');

return (
<>
Expand Down
64 changes: 42 additions & 22 deletions src/components/shared/map/Map.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { useTranslations } from 'next-intl';
import Image from 'next/image';
import React, { useEffect, useState, useCallback, useContext } from 'react';
import React, { useEffect, useState, useCallback, useContext, useRef } from 'react';
import { MapContainer, Marker, Popup, TileLayer, useMapEvents } from 'react-leaflet';
import L, { LatLngExpression, LatLngBounds, LatLngTuple } from 'leaflet';
import _ from 'lodash';
Expand Down Expand Up @@ -132,34 +132,54 @@ const Map = ({
logger.debug('Sellers Array:', { sellers });
}, [sellers]);

// Function to handle marker click
const handleMarkerClick = (sellerCoordinates: LatLngTuple) => {
if (!mapRef.current) return;

const map = mapRef.current;
const currentZoom = map.getZoom();

// Set the view to the seller's coordinates
map.setView(sellerCoordinates, currentZoom, { animate: true });
// Get the position of the clicked marker
const markerPoint = map.latLngToContainerPoint(sellerCoordinates);
// Get the width and height of the map container
const mapSize = map.getSize();
const mapWidth = mapSize.x;
const mapHeight = mapSize.y;
// Calculate the offsets to center the marker in the map view
const panOffset = L.point(mapWidth / 2 - markerPoint.x, mapHeight / 2 - markerPoint.y);

// Pan the map by the calculated offset
map.panBy(panOffset, { animate: false }); // Disable animation to make the movement instant
const useMarkerZoomHandler = (mapRef: React.RefObject<L.Map>) => {
const lastClickedMarker = useRef<string | null>(null);

// Function to handle marker click
const handleMarkerClick = (sellerCoordinates: LatLngTuple) => {
if (!mapRef.current) return;

const map = mapRef.current;
const currentZoom = map.getZoom();
const maxZoom = map.getMaxZoom();

const coordKey = sellerCoordinates.join(',');

// Prevent zooming again on the same marker
if (lastClickedMarker.current === coordKey) return;

// Update the last clicked marker
lastClickedMarker.current = coordKey;

// Calculate target zoom
const targetZoom = Math.min(currentZoom + 3, maxZoom);

// Convert lat/lng to pixel position
const markerPoint = map.latLngToContainerPoint(sellerCoordinates);

// Offset to move popup up and left
const OFFSET_X = -3;
const OFFSET_Y = 28;
const panOffset = L.point(OFFSET_X, OFFSET_Y);

// New center for map
const newCenter = map.containerPointToLatLng(markerPoint.subtract(panOffset));

// Zoom and pan with animation
map.setView(newCenter, targetZoom, { animate: true });
};

return handleMarkerClick;
};

useEffect(() => {
if (mapRef.current) {
fetchInitialCoordinates(); // Fetch sellers when map is ready
}
}, [mapRef.current]);

const handleMarkerClick = useMarkerZoomHandler(mapRef);

const saveMapState = () => {
try{
if (!mapRef.current) {
Expand Down
29 changes: 24 additions & 5 deletions src/components/shared/map/MapMarkerPopup.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,10 @@ const MapMarkerPopup = ({ seller }: { seller: any }) => {
? seller.image
: '/images/logo.svg';

const truncateChars = (text: string, maxChars: number): string => {
return text.length > maxChars ? text.slice(0, maxChars) + '...' : text;
};

const translateSellerCategory = (category: string): string => {
switch (category) {
case 'activeSeller':
Expand All @@ -35,24 +39,39 @@ const MapMarkerPopup = ({ seller }: { seller: any }) => {
<div style={{ position: 'relative', zIndex: 20, padding: '10px' }}>
{/* Seller name and type - Close with a small gap */}
<div style={{ textAlign: 'center', marginBottom: '5px' }}>
<h2 style={{ fontWeight: 'bold', fontSize: '18px', marginBottom: '2px' }}>
{seller.name}
<h2
style={{
fontWeight: 'bold',
fontSize: '15px',
marginBottom: '2px',
whiteSpace: 'nowrap',
overflow: 'hidden',
textOverflow: 'ellipsis',
}}
>
{truncateChars(seller.name, 12)} {/* Adjust limit as needed */}
</h2>

{seller.seller_type && (
<p style={{ fontSize: '14px', color: '#6B7280', marginTop: '0px', marginBottom: '4px' }}>
{translateSellerCategory(seller.seller_type)}
</p>

)}
</div>

{/* Seller image - Close to seller type */}
<div style={{ textAlign: 'center', marginBottom: '5px' }}>
<div style={{ width: '150px', height: '70px', overflow: 'hidden', margin: '0 auto', display: 'flex', justifyContent: 'center', alignItems: 'center' }}>
<Image
src={imageUrl}
alt="Seller Image"
width={150}
height={50}
style={{ borderRadius: '0px', objectFit: 'cover', display: 'block', margin: '0 auto' }}
height={70}
style={{
objectFit: 'contain',
width: '100%',
height: '100%',
}}
/>
</div>

Expand Down