diff --git a/CHANGELOG.md b/CHANGELOG.md index 5ba39548..3bc7c4c0 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,25 @@ +## [v1.74.7](https://github.com/wanderer-industries/wanderer/compare/v1.74.6...v1.74.7) (2025-07-09) + + + + +## [v1.74.6](https://github.com/wanderer-industries/wanderer/compare/v1.74.5...v1.74.6) (2025-07-09) + + + + +## [v1.74.5](https://github.com/wanderer-industries/wanderer/compare/v1.74.4...v1.74.5) (2025-07-09) + + + + +### Bug Fixes: + +* Map: Add background for Pochven's systems. Changed from Region name to constellation name for pochven systems. Changed connection style for gates (display like common connection). Changed behaviour of connections. + ## [v1.74.4](https://github.com/wanderer-industries/wanderer/compare/v1.74.3...v1.74.4) (2025-07-07) diff --git a/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemKillsCounter.module.scss b/assets/js/hooks/Mapper/components/map/components/KillsCounter/KillsCounter.module.scss similarity index 100% rename from assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemKillsCounter.module.scss rename to assets/js/hooks/Mapper/components/map/components/KillsCounter/KillsCounter.module.scss diff --git a/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemKillsCounter.tsx b/assets/js/hooks/Mapper/components/map/components/KillsCounter/KillsCounter.tsx similarity index 96% rename from assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemKillsCounter.tsx rename to assets/js/hooks/Mapper/components/map/components/KillsCounter/KillsCounter.tsx index f0a019de..347a301d 100644 --- a/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemKillsCounter.tsx +++ b/assets/js/hooks/Mapper/components/map/components/KillsCounter/KillsCounter.tsx @@ -1,7 +1,7 @@ import { useMemo } from 'react'; -import { useKillsCounter } from '../../hooks/useKillsCounter'; +import { useKillsCounter } from '../../hooks/useKillsCounter.ts'; import { WdTooltipWrapper } from '@/hooks/Mapper/components/ui-kit/WdTooltipWrapper'; -import { WithChildren, WithClassName } from '@/hooks/Mapper/types/common'; +import { WithChildren, WithClassName } from '@/hooks/Mapper/types/common.ts'; import { KILLS_ROW_HEIGHT, SystemKillsList, diff --git a/assets/js/hooks/Mapper/components/map/components/KillsCounter/index.ts b/assets/js/hooks/Mapper/components/map/components/KillsCounter/index.ts new file mode 100644 index 00000000..a77e1e02 --- /dev/null +++ b/assets/js/hooks/Mapper/components/map/components/KillsCounter/index.ts @@ -0,0 +1 @@ +export * from './KillsCounter.tsx'; diff --git a/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemLocalCounter.module.scss b/assets/js/hooks/Mapper/components/map/components/LocalCounter/LocalCounter.module.scss similarity index 100% rename from assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemLocalCounter.module.scss rename to assets/js/hooks/Mapper/components/map/components/LocalCounter/LocalCounter.module.scss diff --git a/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemLocalCounter.tsx b/assets/js/hooks/Mapper/components/map/components/LocalCounter/LocalCounter.tsx similarity index 91% rename from assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemLocalCounter.tsx rename to assets/js/hooks/Mapper/components/map/components/LocalCounter/LocalCounter.tsx index 1d5a486d..486abd6a 100644 --- a/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemLocalCounter.tsx +++ b/assets/js/hooks/Mapper/components/map/components/LocalCounter/LocalCounter.tsx @@ -3,10 +3,9 @@ import clsx from 'clsx'; import { WdTooltipWrapper } from '@/hooks/Mapper/components/ui-kit/WdTooltipWrapper'; import { TooltipPosition } from '@/hooks/Mapper/components/ui-kit/WdTooltip'; import { CharItemProps, LocalCharactersList } from '../../../mapInterface/widgets/LocalCharacters/components'; -import { useLocalCharactersItemTemplate } from '../../../mapInterface/widgets/LocalCharacters/hooks/useLocalCharacters'; -import classes from './SolarSystemLocalCounter.module.scss'; import { useTheme } from '@/hooks/Mapper/hooks/useTheme.ts'; import { AvailableThemes } from '@/hooks/Mapper/mapRootProvider/types.ts'; +import classes from './LocalCounter.module.scss'; import { useMapState } from '@/hooks/Mapper/components/map/MapProvider.tsx'; interface LocalCounterProps { diff --git a/assets/js/hooks/Mapper/components/map/components/LocalCounter/index.ts b/assets/js/hooks/Mapper/components/map/components/LocalCounter/index.ts new file mode 100644 index 00000000..0a13bef6 --- /dev/null +++ b/assets/js/hooks/Mapper/components/map/components/LocalCounter/index.ts @@ -0,0 +1 @@ +export * from './LocalCounter'; diff --git a/assets/js/hooks/Mapper/components/map/components/SolarSystemEdge/SolarSystemEdge.tsx b/assets/js/hooks/Mapper/components/map/components/SolarSystemEdge/SolarSystemEdge.tsx index 431349a2..f02e40f3 100644 --- a/assets/js/hooks/Mapper/components/map/components/SolarSystemEdge/SolarSystemEdge.tsx +++ b/assets/js/hooks/Mapper/components/map/components/SolarSystemEdge/SolarSystemEdge.tsx @@ -1,7 +1,7 @@ import { useCallback, useMemo, useState } from 'react'; import classes from './SolarSystemEdge.module.scss'; -import { EdgeLabelRenderer, EdgeProps, getBezierPath, getSmoothStepPath, Position, useStore } from 'reactflow'; +import { EdgeLabelRenderer, EdgeProps, getBezierPath, Position, useStore } from 'reactflow'; import { getEdgeParams } from '@/hooks/Mapper/components/map/utils.ts'; import clsx from 'clsx'; import { ConnectionType, MassState, ShipSizeStatus, SolarSystemConnection, TimeStatus } from '@/hooks/Mapper/types'; @@ -51,11 +51,11 @@ export const SolarSystemEdge = ({ id, source, target, markerEnd, style, data }: const [hovered, setHovered] = useState(false); const [path, labelX, labelY, sx, sy, tx, ty, sourcePos, targetPos] = useMemo(() => { - const { sx, sy, tx, ty, sourcePos, targetPos } = getEdgeParams(sourceNode, targetNode); + const { sx, sy, tx, ty, sourcePos, targetPos } = getEdgeParams(sourceNode!, targetNode!); const offset = isThickConnections ? MAP_OFFSETS_TICK[targetPos] : MAP_OFFSETS[targetPos]; - const method = isWormhole ? getBezierPath : getSmoothStepPath; + const method = isWormhole ? getBezierPath : getBezierPath; const [edgePath, labelX, labelY] = method({ sourceX: sx - offset.x, diff --git a/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemNodeDefault.module.scss b/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemNodeDefault.module.scss index 98c4108a..8bf4159e 100644 --- a/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemNodeDefault.module.scss +++ b/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemNodeDefault.module.scss @@ -40,6 +40,7 @@ $neon-color-3: rgba(27, 132, 236, 0.40); z-index: 3; overflow: hidden; + &.Pochven, &.Mataria, &.Amarria, &.Gallente, @@ -95,6 +96,15 @@ $neon-color-3: rgba(27, 132, 236, 0.40); } } + &.Pochven { + &::after { + opacity: 0.8; + background-image: url('/images/pochven.webp'); + background-position-x: 0; + background-position-y: -13px; + } + } + &.selected { border-color: $pastel-pink; box-shadow: 0 0 10px #9a1af1c2; diff --git a/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemNodeDefault.tsx b/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemNodeDefault.tsx index 99f1a45b..e21768d5 100644 --- a/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemNodeDefault.tsx +++ b/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemNodeDefault.tsx @@ -12,11 +12,11 @@ import { } from '@/hooks/Mapper/components/map/constants'; import { WormholeClassComp } from '@/hooks/Mapper/components/map/components/WormholeClassComp'; import { UnsplashedSignature } from '@/hooks/Mapper/components/map/components/UnsplashedSignature'; -import { LocalCounter } from './SolarSystemLocalCounter'; -import { KillsCounter } from './SolarSystemKillsCounter'; import { TooltipSize } from '@/hooks/Mapper/components/ui-kit/WdTooltipWrapper/utils.ts'; import { TooltipPosition, WdTooltipWrapper } from '@/hooks/Mapper/components/ui-kit'; import { Tag } from 'primereact/tag'; +import { LocalCounter } from '@/hooks/Mapper/components/map/components/LocalCounter'; +import { KillsCounter } from '@/hooks/Mapper/components/map/components/KillsCounter'; // let render = 0; export const SolarSystemNodeDefault = memo((props: NodeProps) => { diff --git a/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemNodeTheme.tsx b/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemNodeTheme.tsx index b35a4d9d..696a9c8d 100644 --- a/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemNodeTheme.tsx +++ b/assets/js/hooks/Mapper/components/map/components/SolarSystemNode/SolarSystemNodeTheme.tsx @@ -12,10 +12,10 @@ import { } from '@/hooks/Mapper/components/map/constants'; import { WormholeClassComp } from '@/hooks/Mapper/components/map/components/WormholeClassComp'; import { UnsplashedSignature } from '@/hooks/Mapper/components/map/components/UnsplashedSignature'; -import { LocalCounter } from './SolarSystemLocalCounter'; -import { KillsCounter } from './SolarSystemKillsCounter'; import { TooltipPosition, WdTooltipWrapper } from '@/hooks/Mapper/components/ui-kit'; import { TooltipSize } from '@/hooks/Mapper/components/ui-kit/WdTooltipWrapper/utils.ts'; +import { LocalCounter } from '@/hooks/Mapper/components/map/components/LocalCounter'; +import { KillsCounter } from '@/hooks/Mapper/components/map/components/KillsCounter'; // let render = 0; export const SolarSystemNodeTheme = memo((props: NodeProps) => { diff --git a/assets/js/hooks/Mapper/components/map/hooks/useSolarSystemNode.ts b/assets/js/hooks/Mapper/components/map/hooks/useSolarSystemNode.ts index 3c229bac..79724aa6 100644 --- a/assets/js/hooks/Mapper/components/map/hooks/useSolarSystemNode.ts +++ b/assets/js/hooks/Mapper/components/map/hooks/useSolarSystemNode.ts @@ -5,7 +5,7 @@ import { useMapRootState } from '@/hooks/Mapper/mapRootProvider'; import { useMapGetOption } from '@/hooks/Mapper/mapRootProvider/hooks/api'; import { useMapState } from '@/hooks/Mapper/components/map/MapProvider'; import { useDoubleClick } from '@/hooks/Mapper/hooks/useDoubleClick'; -import { REGIONS_MAP, Spaces } from '@/hooks/Mapper/constants'; +import { Regions, REGIONS_MAP, Spaces } from '@/hooks/Mapper/constants'; import { isWormholeSpace } from '@/hooks/Mapper/components/map/helpers/isWormholeSpace'; import { getSystemClassStyles } from '@/hooks/Mapper/components/map/helpers'; import { sortWHClasses } from '@/hooks/Mapper/helpers'; @@ -65,6 +65,7 @@ const SpaceToClass: Record = { [Spaces.Matar]: 'Mataria', [Spaces.Amarr]: 'Amarria', [Spaces.Gallente]: 'Gallente', + [Spaces.Pochven]: 'Pochven', }; export function useLocalCounter(nodeVars: SolarSystemNodeVars) { @@ -112,6 +113,7 @@ export const useSolarSystemNode = (props: NodeProps): SolarS region_id, is_shattered, solar_system_name, + constellation_name, } = systemStaticInfo; const { isShowUnsplashedSignatures } = interfaceSettings; @@ -195,10 +197,18 @@ export const useSolarSystemNode = (props: NodeProps): SolarS const hubsAsStrings = useMemo(() => hubs.map(item => item.toString()), [hubs]); const isRally = useMemo( - () => pings.find(x => x.solar_system_id === solar_system_id && x.type === PingType.Rally), + () => !!pings.find(x => x.solar_system_id === solar_system_id && x.type === PingType.Rally), [pings, solar_system_id], ); + const regionName = useMemo(() => { + if (region_id === Regions.Pochven) { + return constellation_name; + } + + return region_name; + }, [constellation_name, region_id, region_name]); + const nodeVars: SolarSystemNodeVars = { id, selected, @@ -233,7 +243,7 @@ export const useSolarSystemNode = (props: NodeProps): SolarS isThickConnections, classTitle: class_title, temporaryName: computedTemporaryName, - regionName: region_name, + regionName, solarSystemName: solar_system_name, isRally, }; diff --git a/assets/js/hooks/Mapper/components/map/utils.ts b/assets/js/hooks/Mapper/components/map/utils.ts index 32216c83..6f7b8d2a 100644 --- a/assets/js/hooks/Mapper/components/map/utils.ts +++ b/assets/js/hooks/Mapper/components/map/utils.ts @@ -1,37 +1,48 @@ -import { Position, internalsSymbol } from 'reactflow'; +import { Position, internalsSymbol, Node } from 'reactflow'; -// returns the position (top,right,bottom or right) passed node compared to -function getParams(nodeA, nodeB) { +type Coords = [number, number]; +type CoordsWithPosition = [number, number, Position]; + +function segmentsIntersect(a1: number, a2: number, b1: number, b2: number): boolean { + const [minA, maxA] = a1 < a2 ? [a1, a2] : [a2, a1]; + const [minB, maxB] = b1 < b2 ? [b1, b2] : [b2, b1]; + + return maxA >= minB && maxB >= minA; +} + +function getParams(nodeA: Node, nodeB: Node): CoordsWithPosition { const centerA = getNodeCenter(nodeA); const centerB = getNodeCenter(nodeB); - const horizontalDiff = Math.abs(centerA.x - centerB.x); - const verticalDiff = Math.abs(centerA.y - centerB.y); - let position: Position; - // when the horizontal difference between the nodes is bigger, we use Position.Left or Position.Right for the handle - if (horizontalDiff > verticalDiff) { - position = centerA.x > centerB.x ? Position.Left : Position.Right; - } else { - // here the vertical difference between the nodes is bigger, so we use Position.Top or Position.Bottom for the handle + if ( + segmentsIntersect( + nodeA.positionAbsolute!.x - 10, + nodeA.positionAbsolute!.x - 10 + nodeA.width! + 20, + nodeB.positionAbsolute!.x, + nodeB.positionAbsolute!.x + nodeB.width!, + ) + ) { position = centerA.y > centerB.y ? Position.Top : Position.Bottom; + } else { + position = centerA.x > centerB.x ? Position.Left : Position.Right; } const [x, y] = getHandleCoordsByPosition(nodeA, position); return [x, y, position]; } -function getHandleCoordsByPosition(node, handlePosition) { - // all handles are from type source, that's why we use handleBounds.source here - const handle = node[internalsSymbol].handleBounds.source.find(h => h.position === handlePosition); +function getHandleCoordsByPosition(node: Node, handlePosition: Position): Coords { + const handle = node[internalsSymbol]!.handleBounds!.source!.find(h => h.position === handlePosition); + + if (!handle) { + throw new Error(`Handle with position ${handlePosition} not found on node ${node.id}`); + } let offsetX = handle.width / 2; let offsetY = handle.height / 2; - // this is a tiny detail to make the markerEnd of an edge visible. - // The handle position that gets calculated has the origin top-left, so depending which side we are using, we add a little offset - // when the handlePosition is Position.Right for example, we need to add an offset as big as the handle itself in order to get the correct position switch (handlePosition) { case Position.Left: offsetX = 0; @@ -47,21 +58,20 @@ function getHandleCoordsByPosition(node, handlePosition) { break; } - const x = node.positionAbsolute.x + handle.x + offsetX; - const y = node.positionAbsolute.y + handle.y + offsetY; + const x = node.positionAbsolute!.x + handle.x + offsetX; + const y = node.positionAbsolute!.y + handle.y + offsetY; return [x, y]; } -function getNodeCenter(node) { +function getNodeCenter(node: Node): { x: number; y: number } { return { - x: node.positionAbsolute.x + node.width / 2, - y: node.positionAbsolute.y + node.height / 2, + x: node.positionAbsolute!.x + node.width! / 2, + y: node.positionAbsolute!.y + node.height! / 2, }; } -// returns the parameters (sx, sy, tx, ty, sourcePos, targetPos) you need to create an edge -export function getEdgeParams(source, target) { +export function getEdgeParams(source: Node, target: Node) { const [sx, sy, sourcePos] = getParams(source, target); const [tx, ty, targetPos] = getParams(target, source); diff --git a/assets/js/hooks/Mapper/constants.ts b/assets/js/hooks/Mapper/constants.ts index 3103a0ec..ee0c398b 100644 --- a/assets/js/hooks/Mapper/constants.ts +++ b/assets/js/hooks/Mapper/constants.ts @@ -33,6 +33,7 @@ export enum Regions { Solitude = 10000044, TashMurkon = 10000020, VergeVendor = 10000068, + Pochven = 10000070, } export enum Spaces { @@ -40,6 +41,7 @@ export enum Spaces { 'Gallente' = 'Gallente', 'Matar' = 'Matar', 'Amarr' = 'Amarr', + 'Pochven' = 'Pochven', } export const REGIONS_MAP: Record = { @@ -66,6 +68,7 @@ export const REGIONS_MAP: Record = { [Regions.Solitude]: Spaces.Gallente, [Regions.TashMurkon]: Spaces.Amarr, [Regions.VergeVendor]: Spaces.Gallente, + [Regions.Pochven]: Spaces.Pochven, }; export type K162Type = { diff --git a/assets/static/images/pochven.webp b/assets/static/images/pochven.webp new file mode 100644 index 00000000..5a4112ad Binary files /dev/null and b/assets/static/images/pochven.webp differ diff --git a/lib/wanderer_app_web/live/map/components/map_characters.ex b/lib/wanderer_app_web/live/map/components/map_characters.ex index 43055567..dcfe0799 100644 --- a/lib/wanderer_app_web/live/map/components/map_characters.ex +++ b/lib/wanderer_app_web/live/map/components/map_characters.ex @@ -87,11 +87,8 @@ defmodule WandererAppWeb.MapCharacters do end @impl true - def handle_event("undo", %{"event-data" => _event_data} = _params, socket) do - # notify_to(socket.assigns.notify_to, socket.assigns.event_name, map_slug) - - {:noreply, socket} - end + def handle_event("undo", %{"event-data" => _event_data} = _params, socket), + do: {:noreply, socket} defp is_online?(character_id) do {:ok, state} = WandererApp.Character.get_character_state(character_id) diff --git a/mix.exs b/mix.exs index bfc97de6..5e4786cf 100644 --- a/mix.exs +++ b/mix.exs @@ -3,7 +3,7 @@ defmodule WandererApp.MixProject do @source_url "https://github.com/wanderer-industries/wanderer" - @version "1.74.4" + @version "1.74.7" def project do [