import math from accounts.models import IAmPrincipal from manage_events.models import Event, Venue from django.utils.timezone import now import googlemaps from django.conf import settings def haversine(lon1, lat1, lon2, lat2): """ Calculate the great circle distance in kilometers between two points on the earth (specified in decimal degrees) """ # convert decimal degrees to radians lon1, lat1, lon2, lat2 = map(math.radians, [lon1, lat1, lon2, lat2]) # haversine formula dlon = lon2 - lon1 dlat = lat2 - lat1 a = ( math.sin(dlat / 2) ** 2 + math.cos(lat1) * math.cos(lat2) * math.sin(dlon / 2) ** 2 ) c = 2 * math.asin(math.sqrt(a)) r = 6371 # Radius of earth in kilometers. Use 3956 for miles return c * r def filter_events_by_location(user_lat, user_lon, radius_km=10): venues_within_radius = [] # Check each venue to see if it's within the radius for venue in Venue.objects.filter(deleted=False, active=True): print("venue: ", venue) distance = haversine(user_lon, user_lat, venue.longitude, venue.latitude) print("distance: ", distance) if distance <= radius_km: venues_within_radius.append(venue.id) print("venues_within_radius: ", venues_within_radius) # Filter events based on the venues within the radius events = Event.objects.filter(venue__id__in=venues_within_radius) return events from math import sin, cos, radians, sqrt, atan2 def haversine_one(lon1, lat1, lon2, lat2): """ Calculates the distance between two points on a sphere using the Haversine formula. Args: lon1 (float): Longitude of the first point. lat1 (float): Latitude of the first point. lon2 (float): Longitude of the second point. lat2 (float): Latitude of the second point. Returns: float: Distance in kilometers between the two points. """ R = 6371 # Earth's radius in kilometers dlon = radians(lon2 - lon1) dlat = radians(lat2 - lat1) a = sin(dlat / 2) * sin(dlat / 2) + cos(radians(lat1)) * cos(radians(lat2)) * sin( dlon / 2 ) * sin(dlon / 2) c = 2 * atan2(sqrt(a), sqrt(1 - a)) return R * c API_KEY = settings.GOOGLE_MAPS_API_KEY gmaps = googlemaps.Client(key=API_KEY) def get_location_info(latitude, longitude): reverse_geocode_result = gmaps.reverse_geocode((latitude, longitude)) if reverse_geocode_result: location = reverse_geocode_result[0] city = None state = None country = None for component in location.get("address_components", []): types = component.get("types", []) # print("types: ", types) if "locality" in types: city = component.get("long_name") elif "administrative_area_level_1" in types: state = component.get("long_name") elif "country" in types: country = component.get("long_name") country_code = component.get("short_name") if city is None and state is not None: city = state return { "city": city, "state": state, "country": country, "country_code": country_code, } else: return {} def update_principal_location(principal, latitude, longitude): location_data = get_location_info(latitude=latitude, longitude=longitude) city = location_data.get("city") state = location_data.get("state") country = location_data.get("country") country_code = location_data.get("country_code") if hasattr(principal, "city"): principal.city = city or state if hasattr(principal, "state"): principal.state = state if hasattr(principal, "country"): principal.country = country if hasattr(principal, "address_line1"): principal.address_line1 = country_code principal.save()