@principal-ai/file-city-react 0.5.0 → 0.5.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/components/ArchitectureMapHighlightLayers.d.ts +2 -1
- package/dist/components/ArchitectureMapHighlightLayers.d.ts.map +1 -1
- package/dist/components/ArchitectureMapHighlightLayers.js +41 -6
- package/dist/render/client/drawLayeredBuildings.d.ts.map +1 -1
- package/dist/render/client/drawLayeredBuildings.js +17 -5
- package/package.json +1 -1
- package/src/components/ArchitectureMapHighlightLayers.tsx +57 -5
- package/src/render/client/drawLayeredBuildings.ts +17 -5
- package/src/stories/AllFileTypes.stories.tsx +5 -3
- package/src/stories/ArchitectureMapGridLayout.stories.tsx +1 -1
- package/src/stories/ArchitectureMapHighlightLayers.stories.tsx +10 -3
- package/src/stories/CityViewWithReactFlow.stories.tsx +1 -1
- package/src/stories/StressTest.stories.tsx +1 -1
|
@@ -22,6 +22,7 @@ export interface ArchitectureMapHighlightLayersProps {
|
|
|
22
22
|
className?: string;
|
|
23
23
|
selectiveRender?: SelectiveRenderOptions;
|
|
24
24
|
canvasBackgroundColor?: string;
|
|
25
|
+
maxCanvasSize?: number;
|
|
25
26
|
hoverBorderColor?: string;
|
|
26
27
|
disableOpacityDimming?: boolean;
|
|
27
28
|
defaultDirectoryColor?: string;
|
|
@@ -60,7 +61,7 @@ export interface ArchitectureMapHighlightLayersProps {
|
|
|
60
61
|
buildingBorderRadius?: number;
|
|
61
62
|
districtBorderRadius?: number;
|
|
62
63
|
}
|
|
63
|
-
declare function ArchitectureMapHighlightLayersInner({ cityData, highlightLayers, onLayerToggle, focusDirectory, rootDirectoryName, onDirectorySelect, onFileClick, enableZoom, zoomToPath, onZoomComplete, zoomAnimationSpeed, allowZoomToPath, fullSize, showGrid, showFileNames, className, selectiveRender, canvasBackgroundColor, hoverBorderColor, disableOpacityDimming, defaultDirectoryColor, defaultBuildingColor, subdirectoryMode, showLayerControls, showFileTypeIcons, showDirectoryLabels, transform, // Default to no rotation
|
|
64
|
+
declare function ArchitectureMapHighlightLayersInner({ cityData, highlightLayers, onLayerToggle, focusDirectory, rootDirectoryName, onDirectorySelect, onFileClick, enableZoom, zoomToPath, onZoomComplete, zoomAnimationSpeed, allowZoomToPath, fullSize, showGrid, showFileNames, className, selectiveRender, canvasBackgroundColor, maxCanvasSize, hoverBorderColor, disableOpacityDimming, defaultDirectoryColor, defaultBuildingColor, subdirectoryMode, showLayerControls, showFileTypeIcons, showDirectoryLabels, transform, // Default to no rotation
|
|
64
65
|
onHover, buildingBorderRadius, districtBorderRadius, }: ArchitectureMapHighlightLayersProps): React.JSX.Element;
|
|
65
66
|
export declare const ArchitectureMapHighlightLayers: typeof ArchitectureMapHighlightLayersInner;
|
|
66
67
|
export {};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ArchitectureMapHighlightLayers.d.ts","sourceRoot":"","sources":["../../src/components/ArchitectureMapHighlightLayers.tsx"],"names":[],"mappings":"AAAA,OAAO,KAA4D,MAAM,OAAO,CAAC;AAQjF,OAAO,EAIL,cAAc,EAGf,MAAM,uCAAuC,CAAC;AAC/C,OAAO,EACL,QAAQ,EACR,YAAY,EACZ,YAAY,EACZ,sBAAsB,EACvB,MAAM,iCAAiC,CAAC;AAazC,MAAM,WAAW,mCAAmC;IAElD,QAAQ,CAAC,EAAE,QAAQ,CAAC;IAGpB,eAAe,CAAC,EAAE,cAAc,EAAE,CAAC;IACnC,aAAa,CAAC,EAAE,CAAC,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,KAAK,IAAI,CAAC;IAC5D,iBAAiB,CAAC,EAAE,OAAO,CAAC;IAC5B,oBAAoB,CAAC,EAAE,MAAM,CAAC;IAG9B,cAAc,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAC/B,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B,iBAAiB,CAAC,EAAE,CAAC,SAAS,EAAE,MAAM,GAAG,IAAI,KAAK,IAAI,CAAC;IACvD,WAAW,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,WAAW,KAAK,IAAI,CAAC;IACjE,UAAU,CAAC,EAAE,OAAO,CAAC;IAGrB,UAAU,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3B,cAAc,CAAC,EAAE,MAAM,IAAI,CAAC;IAC5B,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,eAAe,CAAC,EAAE,OAAO,CAAC;IAG1B,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB,SAAS,CAAC,EAAE,MAAM,CAAC;IAGnB,eAAe,CAAC,EAAE,sBAAsB,CAAC;IAGzC,qBAAqB,CAAC,EAAE,MAAM,CAAC;
|
|
1
|
+
{"version":3,"file":"ArchitectureMapHighlightLayers.d.ts","sourceRoot":"","sources":["../../src/components/ArchitectureMapHighlightLayers.tsx"],"names":[],"mappings":"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"}
|
|
@@ -179,7 +179,7 @@ class PathHierarchyLookup {
|
|
|
179
179
|
return this.abstractedPaths.has(path);
|
|
180
180
|
}
|
|
181
181
|
}
|
|
182
|
-
function ArchitectureMapHighlightLayersInner({ cityData, highlightLayers = [], onLayerToggle, focusDirectory = null, rootDirectoryName, onDirectorySelect, onFileClick, enableZoom = false, zoomToPath = null, onZoomComplete, zoomAnimationSpeed = 0.12, allowZoomToPath = true, fullSize = false, showGrid = false, showFileNames = false, className = '', selectiveRender, canvasBackgroundColor, hoverBorderColor, disableOpacityDimming = true, defaultDirectoryColor, defaultBuildingColor, subdirectoryMode, showLayerControls = false, showFileTypeIcons = true, showDirectoryLabels = true, transform = { rotation: 0 }, // Default to no rotation
|
|
182
|
+
function ArchitectureMapHighlightLayersInner({ cityData, highlightLayers = [], onLayerToggle, focusDirectory = null, rootDirectoryName, onDirectorySelect, onFileClick, enableZoom = false, zoomToPath = null, onZoomComplete, zoomAnimationSpeed = 0.12, allowZoomToPath = true, fullSize = false, showGrid = false, showFileNames = false, className = '', selectiveRender, canvasBackgroundColor, maxCanvasSize, hoverBorderColor, disableOpacityDimming = true, defaultDirectoryColor, defaultBuildingColor, subdirectoryMode, showLayerControls = false, showFileTypeIcons = true, showDirectoryLabels = true, transform = { rotation: 0 }, // Default to no rotation
|
|
183
183
|
onHover, buildingBorderRadius = 0, districtBorderRadius = 0, }) {
|
|
184
184
|
const { theme } = (0, industry_theme_1.useTheme)();
|
|
185
185
|
// Use theme colors as defaults, with prop overrides
|
|
@@ -309,7 +309,10 @@ onHover, buildingBorderRadius = 0, districtBorderRadius = 0, }) {
|
|
|
309
309
|
const calculateCanvasResolution = (fileCount, _cityBounds) => {
|
|
310
310
|
const minSize = 400;
|
|
311
311
|
const scaleFactor = Math.sqrt(fileCount / 5);
|
|
312
|
-
|
|
312
|
+
let resolution = Math.max(minSize, minSize + scaleFactor * 300);
|
|
313
|
+
if (maxCanvasSize !== undefined) {
|
|
314
|
+
resolution = Math.min(resolution, maxCanvasSize);
|
|
315
|
+
}
|
|
313
316
|
return { width: resolution, height: resolution };
|
|
314
317
|
};
|
|
315
318
|
const [canvasSize, setCanvasSize] = (0, react_1.useState)(() => calculateCanvasResolution(cityData?.buildings?.length || 10, cityData?.bounds));
|
|
@@ -1153,14 +1156,46 @@ onHover, buildingBorderRadius = 0, districtBorderRadius = 0, }) {
|
|
|
1153
1156
|
width: '100%',
|
|
1154
1157
|
height: '100%',
|
|
1155
1158
|
minHeight: '250px',
|
|
1156
|
-
backgroundColor:
|
|
1157
|
-
borderRadius: `${theme.radii[2]}px`,
|
|
1158
|
-
padding: `${theme.space[4]}px`,
|
|
1159
|
+
backgroundColor: resolvedCanvasBackgroundColor,
|
|
1160
|
+
borderRadius: fullSize ? 0 : `${theme.radii[2]}px`,
|
|
1159
1161
|
display: 'flex',
|
|
1160
1162
|
alignItems: 'center',
|
|
1161
1163
|
justifyContent: 'center',
|
|
1164
|
+
position: 'relative',
|
|
1165
|
+
overflow: 'hidden',
|
|
1162
1166
|
} },
|
|
1163
|
-
react_1.default.createElement("div", { style: {
|
|
1167
|
+
react_1.default.createElement("div", { style: {
|
|
1168
|
+
position: 'absolute',
|
|
1169
|
+
inset: 0,
|
|
1170
|
+
display: 'grid',
|
|
1171
|
+
gridTemplateColumns: 'repeat(auto-fit, minmax(80px, 1fr))',
|
|
1172
|
+
gridAutoRows: 'minmax(80px, 1fr)',
|
|
1173
|
+
gap: '20px',
|
|
1174
|
+
padding: '20px',
|
|
1175
|
+
} }, Array.from({ length: 200 }).map((_, i) => (react_1.default.createElement("div", { key: i, style: {
|
|
1176
|
+
backgroundColor: resolvedDefaultBuildingColor,
|
|
1177
|
+
borderRadius: buildingBorderRadius,
|
|
1178
|
+
opacity: 0.6 + (i % 3) * 0.2,
|
|
1179
|
+
} })))),
|
|
1180
|
+
react_1.default.createElement("div", { style: {
|
|
1181
|
+
position: 'absolute',
|
|
1182
|
+
top: '35%',
|
|
1183
|
+
left: '50%',
|
|
1184
|
+
transform: 'translate(-50%, -50%)',
|
|
1185
|
+
zIndex: 1,
|
|
1186
|
+
display: 'flex',
|
|
1187
|
+
alignItems: 'center',
|
|
1188
|
+
justifyContent: 'center',
|
|
1189
|
+
color: theme.colors.textMuted,
|
|
1190
|
+
fontFamily: theme.fonts.body,
|
|
1191
|
+
fontSize: `${theme.fontSizes[3]}px`,
|
|
1192
|
+
fontWeight: theme.fontWeights.medium,
|
|
1193
|
+
backgroundColor: resolvedCanvasBackgroundColor,
|
|
1194
|
+
borderRadius: `${theme.radii[2]}px`,
|
|
1195
|
+
padding: `${theme.space[4]}px ${theme.space[5]}px`,
|
|
1196
|
+
textAlign: 'center',
|
|
1197
|
+
minWidth: '300px',
|
|
1198
|
+
} }, "No city data available")));
|
|
1164
1199
|
}
|
|
1165
1200
|
return (react_1.default.createElement("div", { ref: containerRef, className: className, style: {
|
|
1166
1201
|
position: 'relative',
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"drawLayeredBuildings.d.ts","sourceRoot":"","sources":["../../../src/render/client/drawLayeredBuildings.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,YAAY,EACZ,YAAY,EACZ,SAAS,EACT,mBAAmB,EACnB,cAAc,EACf,MAAM,iCAAiC,CAAC;AAEzC,OAAO,EAAE,kBAAkB,EAAE,MAAM,sCAAsC,CAAC;AAI1E,YAAY,EAAE,SAAS,EAAE,mBAAmB,EAAE,cAAc,EAAE,CAAC;AAE/D;;;GAGG;AACH,qBAAa,UAAU;IAErB,OAAO,CAAC,UAAU,CAA6E;IAE/F,OAAO,CAAC,cAAc,CAAuE;IAE7F,OAAO,CAAC,WAAW,CAA6E;gBAEpF,MAAM,EAAE,cAAc,EAAE;IAIpC,OAAO,CAAC,UAAU;IA0BlB;;;;OAIG;IACH,eAAe,CACb,IAAI,EAAE,MAAM,EACZ,SAAS,GAAE,OAAO,GAAG,UAAuB,GAC3C,KAAK,CAAC;QAAE,KAAK,EAAE,cAAc,CAAC;QAAC,IAAI,EAAE,SAAS,CAAA;KAAE,CAAC;CAuCrD;AA8BD,wBAAgB,QAAQ,CACtB,GAAG,EAAE,wBAAwB,EAC7B,KAAK,EAAE,MAAM,EACb,MAAM,EAAE,MAAM,EACd,QAAQ,EAAE,MAAM,QAqBjB;AA0VD,wBAAgB,oBAAoB,CAClC,GAAG,EAAE,wBAAwB,EAC7B,SAAS,EAAE,YAAY,EAAE,EACzB,aAAa,EAAE,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,KAAK;IAAE,CAAC,EAAE,MAAM,CAAC;IAAC,CAAC,EAAE,MAAM,CAAA;CAAE,EACjE,KAAK,EAAE,MAAM,EAAE,wDAAwD;AACvE,MAAM,EAAE,cAAc,EAAE,EACxB,eAAe,CAAC,EAAE,YAAY,GAAG,IAAI,EACrC,QAAQ,CAAC,EAAE,OAAO,EAClB,qBAAqB,CAAC,EAAE,MAAM,EAC9B,YAAY,CAAC,EAAE;IACb,UAAU,EAAE,MAAM,CAAC;IACnB,aAAa,EAAE,MAAM,CAAC;IACtB,WAAW,EAAE,MAAM,CAAC;IACpB,YAAY,EAAE,MAAM,CAAC;CACtB,EACD,eAAe,CAAC,EAAE,GAAG,CAAC,MAAM,CAAC,EAAE,yDAAyD;AACxF,mBAAmB,GAAE,OAAc,EACnC,YAAY,GAAE,MAAU,EAAE,uDAAuD;AACjF,UAAU,CAAC,EAAE,UAAU,QAgQxB;AAGD,wBAAgB,oBAAoB,CAClC,GAAG,EAAE,wBAAwB,EAC7B,SAAS,EAAE,YAAY,EAAE,EACzB,aAAa,EAAE,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,KAAK;IAAE,CAAC,EAAE,MAAM,CAAC;IAAC,CAAC,EAAE,MAAM,CAAA;CAAE,EACjE,KAAK,EAAE,MAAM,EACb,MAAM,EAAE,cAAc,EAAE,EACxB,eAAe,CAAC,EAAE,YAAY,GAAG,IAAI,EACrC,oBAAoB,CAAC,EAAE,MAAM,EAC7B,aAAa,CAAC,EAAE,OAAO,EACvB,gBAAgB,CAAC,EAAE,MAAM,EACzB,qBAAqB,CAAC,EAAE,OAAO,EAC/B,iBAAiB,CAAC,EAAE,OAAO,EAC3B,YAAY,GAAE,MAAU,EAAE,2DAA2D;AACrF,UAAU,CAAC,EAAE,UAAU,EAAE,2CAA2C;AACpE,OAAO,CAAC,EAAE,GAAG,CAAC,MAAM,EAAE,kBAAkB,CAAC,
|
|
1
|
+
{"version":3,"file":"drawLayeredBuildings.d.ts","sourceRoot":"","sources":["../../../src/render/client/drawLayeredBuildings.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,YAAY,EACZ,YAAY,EACZ,SAAS,EACT,mBAAmB,EACnB,cAAc,EACf,MAAM,iCAAiC,CAAC;AAEzC,OAAO,EAAE,kBAAkB,EAAE,MAAM,sCAAsC,CAAC;AAI1E,YAAY,EAAE,SAAS,EAAE,mBAAmB,EAAE,cAAc,EAAE,CAAC;AAE/D;;;GAGG;AACH,qBAAa,UAAU;IAErB,OAAO,CAAC,UAAU,CAA6E;IAE/F,OAAO,CAAC,cAAc,CAAuE;IAE7F,OAAO,CAAC,WAAW,CAA6E;gBAEpF,MAAM,EAAE,cAAc,EAAE;IAIpC,OAAO,CAAC,UAAU;IA0BlB;;;;OAIG;IACH,eAAe,CACb,IAAI,EAAE,MAAM,EACZ,SAAS,GAAE,OAAO,GAAG,UAAuB,GAC3C,KAAK,CAAC;QAAE,KAAK,EAAE,cAAc,CAAC;QAAC,IAAI,EAAE,SAAS,CAAA;KAAE,CAAC;CAuCrD;AA8BD,wBAAgB,QAAQ,CACtB,GAAG,EAAE,wBAAwB,EAC7B,KAAK,EAAE,MAAM,EACb,MAAM,EAAE,MAAM,EACd,QAAQ,EAAE,MAAM,QAqBjB;AA0VD,wBAAgB,oBAAoB,CAClC,GAAG,EAAE,wBAAwB,EAC7B,SAAS,EAAE,YAAY,EAAE,EACzB,aAAa,EAAE,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,KAAK;IAAE,CAAC,EAAE,MAAM,CAAC;IAAC,CAAC,EAAE,MAAM,CAAA;CAAE,EACjE,KAAK,EAAE,MAAM,EAAE,wDAAwD;AACvE,MAAM,EAAE,cAAc,EAAE,EACxB,eAAe,CAAC,EAAE,YAAY,GAAG,IAAI,EACrC,QAAQ,CAAC,EAAE,OAAO,EAClB,qBAAqB,CAAC,EAAE,MAAM,EAC9B,YAAY,CAAC,EAAE;IACb,UAAU,EAAE,MAAM,CAAC;IACnB,aAAa,EAAE,MAAM,CAAC;IACtB,WAAW,EAAE,MAAM,CAAC;IACpB,YAAY,EAAE,MAAM,CAAC;CACtB,EACD,eAAe,CAAC,EAAE,GAAG,CAAC,MAAM,CAAC,EAAE,yDAAyD;AACxF,mBAAmB,GAAE,OAAc,EACnC,YAAY,GAAE,MAAU,EAAE,uDAAuD;AACjF,UAAU,CAAC,EAAE,UAAU,QAgQxB;AAGD,wBAAgB,oBAAoB,CAClC,GAAG,EAAE,wBAAwB,EAC7B,SAAS,EAAE,YAAY,EAAE,EACzB,aAAa,EAAE,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,KAAK;IAAE,CAAC,EAAE,MAAM,CAAC;IAAC,CAAC,EAAE,MAAM,CAAA;CAAE,EACjE,KAAK,EAAE,MAAM,EACb,MAAM,EAAE,cAAc,EAAE,EACxB,eAAe,CAAC,EAAE,YAAY,GAAG,IAAI,EACrC,oBAAoB,CAAC,EAAE,MAAM,EAC7B,aAAa,CAAC,EAAE,OAAO,EACvB,gBAAgB,CAAC,EAAE,MAAM,EACzB,qBAAqB,CAAC,EAAE,OAAO,EAC/B,iBAAiB,CAAC,EAAE,OAAO,EAC3B,YAAY,GAAE,MAAU,EAAE,2DAA2D;AACrF,UAAU,CAAC,EAAE,UAAU,EAAE,2CAA2C;AACpE,OAAO,CAAC,EAAE,GAAG,CAAC,MAAM,EAAE,kBAAkB,CAAC,QA0K1C"}
|
|
@@ -655,12 +655,16 @@ iconMap) {
|
|
|
655
655
|
// Draw file type icon if enabled and icon map is provided
|
|
656
656
|
// Track icon size for positioning file name below
|
|
657
657
|
let iconBottomY = pos.y;
|
|
658
|
+
let hasIcon = false;
|
|
658
659
|
if (showFileTypeIcons && iconMap) {
|
|
659
660
|
const iconConfig = (0, fileTypeIcons_1.getFileTypeIcon)(building.path, iconMap);
|
|
660
661
|
if (iconConfig) {
|
|
662
|
+
hasIcon = true;
|
|
661
663
|
// For wide buildings (wider than tall), shift icon up to make room for text below
|
|
664
|
+
// Only shift if text will actually be rendered
|
|
665
|
+
const willShowText = showFileNames && width > 100 && height > 30;
|
|
662
666
|
const isWide = width > height;
|
|
663
|
-
const iconYOffset = isWide ? -height * 0.15 : 0;
|
|
667
|
+
const iconYOffset = (willShowText && isWide) ? -height * 0.15 : 0;
|
|
664
668
|
const iconY = pos.y + iconYOffset;
|
|
665
669
|
(0, fileTypeIcons_1.drawFileTypeIcon)(ctx, iconConfig, pos.x, iconY, width, height);
|
|
666
670
|
// Calculate where the icon ends vertically
|
|
@@ -691,13 +695,21 @@ iconMap) {
|
|
|
691
695
|
const fontSize = Math.min(30, Math.max(10, Math.floor(Math.min(width, height) * 0.3)));
|
|
692
696
|
ctx.font = `${fontSize}px -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif`;
|
|
693
697
|
ctx.textAlign = 'center';
|
|
694
|
-
ctx.textBaseline = 'top'; // Changed from 'middle' to 'top'
|
|
695
698
|
const textMetrics = ctx.measureText(fileName);
|
|
696
699
|
const textWidth = textMetrics.width;
|
|
697
700
|
if (textWidth < width - 8) {
|
|
698
|
-
|
|
699
|
-
|
|
700
|
-
|
|
701
|
+
let textY;
|
|
702
|
+
if (hasIcon) {
|
|
703
|
+
// Position text below icon
|
|
704
|
+
ctx.textBaseline = 'top';
|
|
705
|
+
const spacing = 4;
|
|
706
|
+
textY = iconBottomY + spacing;
|
|
707
|
+
}
|
|
708
|
+
else {
|
|
709
|
+
// Center text vertically when no icon
|
|
710
|
+
ctx.textBaseline = 'middle';
|
|
711
|
+
textY = pos.y;
|
|
712
|
+
}
|
|
701
713
|
// Text
|
|
702
714
|
ctx.fillStyle = 'rgba(255, 255, 255, 0.95)';
|
|
703
715
|
ctx.fillText(fileName, pos.x, textY);
|
package/package.json
CHANGED
|
@@ -66,6 +66,7 @@ export interface ArchitectureMapHighlightLayersProps {
|
|
|
66
66
|
|
|
67
67
|
// Canvas appearance
|
|
68
68
|
canvasBackgroundColor?: string;
|
|
69
|
+
maxCanvasSize?: number; // Maximum canvas dimension in pixels (default: 6000, use ~2048 for mobile)
|
|
69
70
|
|
|
70
71
|
// Additional styling options
|
|
71
72
|
hoverBorderColor?: string;
|
|
@@ -305,6 +306,7 @@ function ArchitectureMapHighlightLayersInner({
|
|
|
305
306
|
className = '',
|
|
306
307
|
selectiveRender,
|
|
307
308
|
canvasBackgroundColor,
|
|
309
|
+
maxCanvasSize,
|
|
308
310
|
hoverBorderColor,
|
|
309
311
|
disableOpacityDimming = true,
|
|
310
312
|
defaultDirectoryColor,
|
|
@@ -476,7 +478,11 @@ function ArchitectureMapHighlightLayersInner({
|
|
|
476
478
|
) => {
|
|
477
479
|
const minSize = 400;
|
|
478
480
|
const scaleFactor = Math.sqrt(fileCount / 5);
|
|
479
|
-
|
|
481
|
+
let resolution = Math.max(minSize, minSize + scaleFactor * 300);
|
|
482
|
+
|
|
483
|
+
if (maxCanvasSize !== undefined) {
|
|
484
|
+
resolution = Math.min(resolution, maxCanvasSize);
|
|
485
|
+
}
|
|
480
486
|
|
|
481
487
|
return { width: resolution, height: resolution };
|
|
482
488
|
};
|
|
@@ -1624,15 +1630,61 @@ function ArchitectureMapHighlightLayersInner({
|
|
|
1624
1630
|
width: '100%',
|
|
1625
1631
|
height: '100%',
|
|
1626
1632
|
minHeight: '250px',
|
|
1627
|
-
backgroundColor:
|
|
1628
|
-
borderRadius: `${theme.radii[2]}px`,
|
|
1629
|
-
padding: `${theme.space[4]}px`,
|
|
1633
|
+
backgroundColor: resolvedCanvasBackgroundColor,
|
|
1634
|
+
borderRadius: fullSize ? 0 : `${theme.radii[2]}px`,
|
|
1630
1635
|
display: 'flex',
|
|
1631
1636
|
alignItems: 'center',
|
|
1632
1637
|
justifyContent: 'center',
|
|
1638
|
+
position: 'relative',
|
|
1639
|
+
overflow: 'hidden',
|
|
1633
1640
|
}}
|
|
1634
1641
|
>
|
|
1635
|
-
|
|
1642
|
+
{/* Decorative grid background with integrated text */}
|
|
1643
|
+
<div
|
|
1644
|
+
style={{
|
|
1645
|
+
position: 'absolute',
|
|
1646
|
+
inset: 0,
|
|
1647
|
+
display: 'grid',
|
|
1648
|
+
gridTemplateColumns: 'repeat(auto-fit, minmax(80px, 1fr))',
|
|
1649
|
+
gridAutoRows: 'minmax(80px, 1fr)',
|
|
1650
|
+
gap: '20px',
|
|
1651
|
+
padding: '20px',
|
|
1652
|
+
}}
|
|
1653
|
+
>
|
|
1654
|
+
{/* Generate grid squares to fill space */}
|
|
1655
|
+
{Array.from({ length: 200 }).map((_, i) => (
|
|
1656
|
+
<div
|
|
1657
|
+
key={i}
|
|
1658
|
+
style={{
|
|
1659
|
+
backgroundColor: resolvedDefaultBuildingColor,
|
|
1660
|
+
borderRadius: buildingBorderRadius,
|
|
1661
|
+
opacity: 0.6 + (i % 3) * 0.2,
|
|
1662
|
+
}}
|
|
1663
|
+
/>
|
|
1664
|
+
))}
|
|
1665
|
+
</div>
|
|
1666
|
+
{/* Text overlay centered */}
|
|
1667
|
+
<div
|
|
1668
|
+
style={{
|
|
1669
|
+
position: 'absolute',
|
|
1670
|
+
top: '35%',
|
|
1671
|
+
left: '50%',
|
|
1672
|
+
transform: 'translate(-50%, -50%)',
|
|
1673
|
+
zIndex: 1,
|
|
1674
|
+
display: 'flex',
|
|
1675
|
+
alignItems: 'center',
|
|
1676
|
+
justifyContent: 'center',
|
|
1677
|
+
color: theme.colors.textMuted,
|
|
1678
|
+
fontFamily: theme.fonts.body,
|
|
1679
|
+
fontSize: `${theme.fontSizes[3]}px`,
|
|
1680
|
+
fontWeight: theme.fontWeights.medium,
|
|
1681
|
+
backgroundColor: resolvedCanvasBackgroundColor,
|
|
1682
|
+
borderRadius: `${theme.radii[2]}px`,
|
|
1683
|
+
padding: `${theme.space[4]}px ${theme.space[5]}px`,
|
|
1684
|
+
textAlign: 'center',
|
|
1685
|
+
minWidth: '300px',
|
|
1686
|
+
}}
|
|
1687
|
+
>
|
|
1636
1688
|
No city data available
|
|
1637
1689
|
</div>
|
|
1638
1690
|
</div>
|
|
@@ -894,12 +894,16 @@ export function drawLayeredBuildings(
|
|
|
894
894
|
// Draw file type icon if enabled and icon map is provided
|
|
895
895
|
// Track icon size for positioning file name below
|
|
896
896
|
let iconBottomY = pos.y;
|
|
897
|
+
let hasIcon = false;
|
|
897
898
|
if (showFileTypeIcons && iconMap) {
|
|
898
899
|
const iconConfig = getFileTypeIcon(building.path, iconMap);
|
|
899
900
|
if (iconConfig) {
|
|
901
|
+
hasIcon = true;
|
|
900
902
|
// For wide buildings (wider than tall), shift icon up to make room for text below
|
|
903
|
+
// Only shift if text will actually be rendered
|
|
904
|
+
const willShowText = showFileNames && width > 100 && height > 30;
|
|
901
905
|
const isWide = width > height;
|
|
902
|
-
const iconYOffset = isWide ? -height * 0.15 : 0;
|
|
906
|
+
const iconYOffset = (willShowText && isWide) ? -height * 0.15 : 0;
|
|
903
907
|
const iconY = pos.y + iconYOffset;
|
|
904
908
|
|
|
905
909
|
drawFileTypeIcon(ctx, iconConfig, pos.x, iconY, width, height);
|
|
@@ -933,15 +937,23 @@ export function drawLayeredBuildings(
|
|
|
933
937
|
const fontSize = Math.min(30, Math.max(10, Math.floor(Math.min(width, height) * 0.3)));
|
|
934
938
|
ctx.font = `${fontSize}px -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif`;
|
|
935
939
|
ctx.textAlign = 'center';
|
|
936
|
-
ctx.textBaseline = 'top'; // Changed from 'middle' to 'top'
|
|
937
940
|
|
|
938
941
|
const textMetrics = ctx.measureText(fileName);
|
|
939
942
|
const textWidth = textMetrics.width;
|
|
940
943
|
|
|
941
944
|
if (textWidth < width - 8) {
|
|
942
|
-
|
|
943
|
-
|
|
944
|
-
|
|
945
|
+
let textY: number;
|
|
946
|
+
|
|
947
|
+
if (hasIcon) {
|
|
948
|
+
// Position text below icon
|
|
949
|
+
ctx.textBaseline = 'top';
|
|
950
|
+
const spacing = 4;
|
|
951
|
+
textY = iconBottomY + spacing;
|
|
952
|
+
} else {
|
|
953
|
+
// Center text vertically when no icon
|
|
954
|
+
ctx.textBaseline = 'middle';
|
|
955
|
+
textY = pos.y;
|
|
956
|
+
}
|
|
945
957
|
|
|
946
958
|
// Text
|
|
947
959
|
ctx.fillStyle = 'rgba(255, 255, 255, 0.95)';
|
|
@@ -11,7 +11,7 @@ const meta = {
|
|
|
11
11
|
layout: 'fullscreen',
|
|
12
12
|
},
|
|
13
13
|
decorators: [
|
|
14
|
-
Story => (
|
|
14
|
+
(Story: React.ComponentType) => (
|
|
15
15
|
<div style={{ width: '100vw', height: '100vh', backgroundColor: '#1a1a1a' }}>
|
|
16
16
|
<Story />
|
|
17
17
|
</div>
|
|
@@ -199,7 +199,7 @@ function createAllFileTypesCityData() {
|
|
|
199
199
|
};
|
|
200
200
|
});
|
|
201
201
|
|
|
202
|
-
const fileTree = buildFileSystemTreeFromFileInfoList(fileInfos);
|
|
202
|
+
const fileTree = buildFileSystemTreeFromFileInfoList(fileInfos, 'all-file-types');
|
|
203
203
|
const builder = new CodeCityBuilderWithGrid();
|
|
204
204
|
return builder.buildCityFromFileSystem(fileTree, '', {
|
|
205
205
|
paddingTop: 2,
|
|
@@ -230,6 +230,8 @@ export const AllFileTypesWithColors: Story = {
|
|
|
230
230
|
enableZoom={true}
|
|
231
231
|
buildingBorderRadius={2}
|
|
232
232
|
districtBorderRadius={4}
|
|
233
|
+
showFileTypeIcons={true}
|
|
234
|
+
showFileNames={true}
|
|
233
235
|
/>
|
|
234
236
|
<div
|
|
235
237
|
style={{
|
|
@@ -288,7 +290,7 @@ export const TestFilesWithIcons: Story = {
|
|
|
288
290
|
};
|
|
289
291
|
});
|
|
290
292
|
|
|
291
|
-
const fileTree = buildFileSystemTreeFromFileInfoList(fileInfos);
|
|
293
|
+
const fileTree = buildFileSystemTreeFromFileInfoList(fileInfos, 'test-files');
|
|
292
294
|
const builder = new CodeCityBuilderWithGrid();
|
|
293
295
|
const cityData = builder.buildCityFromFileSystem(fileTree, '', {
|
|
294
296
|
paddingTop: 2,
|
|
@@ -12,7 +12,7 @@ const meta = {
|
|
|
12
12
|
layout: 'fullscreen',
|
|
13
13
|
},
|
|
14
14
|
decorators: [
|
|
15
|
-
Story => (
|
|
15
|
+
(Story: React.ComponentType) => (
|
|
16
16
|
<div style={{ width: '100vw', height: '100vh', backgroundColor: '#1a1a1a' }}>
|
|
17
17
|
<Story />
|
|
18
18
|
</div>
|
|
@@ -200,7 +200,6 @@ export const WithAbstractionLayer: Story = {
|
|
|
200
200
|
color: '#1e40af',
|
|
201
201
|
priority: 0,
|
|
202
202
|
items: [],
|
|
203
|
-
// @ts-expect-error - abstraction layer specific properties
|
|
204
203
|
abstractionLayer: true,
|
|
205
204
|
abstractionConfig: {
|
|
206
205
|
maxZoomLevel: 2.0,
|
|
@@ -208,7 +207,7 @@ export const WithAbstractionLayer: Story = {
|
|
|
208
207
|
backgroundColor: '#1e40af',
|
|
209
208
|
allowRootAbstraction: false,
|
|
210
209
|
},
|
|
211
|
-
},
|
|
210
|
+
} as HighlightLayer,
|
|
212
211
|
],
|
|
213
212
|
fullSize: true,
|
|
214
213
|
enableZoom: true,
|
|
@@ -311,6 +310,14 @@ export const WithBorderRadius: Story = {
|
|
|
311
310
|
},
|
|
312
311
|
};
|
|
313
312
|
|
|
313
|
+
// Story showing the loading/empty state when cityData is not available
|
|
314
|
+
export const LoadingState: Story = {
|
|
315
|
+
args: {
|
|
316
|
+
cityData: undefined,
|
|
317
|
+
fullSize: true,
|
|
318
|
+
},
|
|
319
|
+
};
|
|
320
|
+
|
|
314
321
|
// Story with programmatic zoom only (no user interaction)
|
|
315
322
|
// Demonstrates allowZoomToPath={true} with enableZoom={false}
|
|
316
323
|
export const ProgrammaticZoomOnly: Story = {
|