@mgonza02/goal-image-gallery 1.1.0 → 1.2.0
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/CHANGELOG.md +37 -0
- package/README.md +6 -6
- package/lib/GoalImageGallery.js +1 -5
- package/lib/components/ImageGalleryEmptyState.js +7 -3
- package/lib/components/ImageGalleryGrid.js +6 -7
- package/lib/components/ImageGalleryItem.js +7 -4
- package/lib/components/ImageGalleryModal.js +12 -8
- package/lib/examples.js +23 -9
- package/lib/styles/styled-components.js +108 -139
- package/package.json +86 -87
package/CHANGELOG.md
CHANGED
|
@@ -5,6 +5,43 @@ All notable changes to the GoalImageGallery project will be documented in this f
|
|
|
5
5
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|
6
6
|
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
7
|
|
|
8
|
+
## [1.2.0] - 2026-04-29
|
|
9
|
+
|
|
10
|
+
### ⬆️ Dependency Upgrades
|
|
11
|
+
- **MUI v9**: Upgraded `@mui/material` and `@mui/icons-material` from `^5.18` to `^9.0.0`
|
|
12
|
+
- **Emotion**: Updated `@emotion/react` and `@emotion/styled` to `^11.14.0`
|
|
13
|
+
- **Node engine**: Minimum Node.js version raised to `>=18.0.0`
|
|
14
|
+
|
|
15
|
+
### 🔧 Migration — MUI v9 Breaking Changes
|
|
16
|
+
- **System props removed**: Migrated deprecated shorthand props (`color`, `alignItems`, `textAlign`, `display`) on Typography and Stack to the `sx` prop using the official `@mui/codemod v9.0.0/system-props` codemod
|
|
17
|
+
- **Stack alignItems**: Restored `alignItems` as a direct prop on `Stack` components where the codemod incorrectly moved it into `sx`, fixing a React DOM prop warning (`React does not recognize the alignItems prop on a DOM element`)
|
|
18
|
+
- **Grid v2**: Confirmed Grid already uses the v2 `size` prop API required by MUI v9
|
|
19
|
+
|
|
20
|
+
### 📦 Package Manager — Migrated to pnpm
|
|
21
|
+
- **pnpm@10.33.2**: Replaced npm with pnpm as the official package manager
|
|
22
|
+
- Added `"packageManager": "pnpm@10.33.2"` to `package.json`
|
|
23
|
+
- Added `.npmrc` with `engine-strict=true`, `auto-install-peers=true`, `shamefully-hoist=false`
|
|
24
|
+
- All `npm run X` script calls replaced with `pnpm X`
|
|
25
|
+
- `package-lock.json` replaced by `pnpm-lock.yaml`
|
|
26
|
+
- Updated `.gitignore` and `.npmignore` with pnpm log/lockfile entries
|
|
27
|
+
|
|
28
|
+
### 🐳 Docker
|
|
29
|
+
- **Dockerfile**: Replaced `npm install` with `corepack enable && corepack prepare pnpm@10.33.2 --activate` + `pnpm install --frozen-lockfile`; `CMD` updated to `pnpm start`
|
|
30
|
+
- **docker-compose.yml**: Updated `command` from `node start.js` to `pnpm build`
|
|
31
|
+
|
|
32
|
+
### 📐 Architecture
|
|
33
|
+
- Added `SOLID_PRINCIPLES.md`: documents how SRP, OCP, LSP, ISP, and DIP are applied and enforced in this codebase, including allowed import direction graph and PR checklist
|
|
34
|
+
|
|
35
|
+
|
|
36
|
+
## [1.1.1] - 2025-07-14
|
|
37
|
+
### 🐛 Bug Fixes
|
|
38
|
+
- **Fixed Image Gallery Modal**: Resolved issues with the image gallery modal not displaying correctly
|
|
39
|
+
- **Improved Image Handling**: Enhanced image error handling and loading states
|
|
40
|
+
- **Modal Responsiveness**: Ensured the modal is fully responsive and adapts to different screen sizes
|
|
41
|
+
- **Accessibility Improvements**: Enhanced keyboard navigation and ARIA attributes for better accessibility
|
|
42
|
+
- **Code Cleanup**: Removed unused imports and optimized component structure
|
|
43
|
+
- **Remove styled-components**: Replaced styled-components with MUI's Box component for better consistency
|
|
44
|
+
|
|
8
45
|
## [1.1.0] - 2025-07-14
|
|
9
46
|
|
|
10
47
|
### 🐛 Bug Fixes
|
package/README.md
CHANGED
|
@@ -53,10 +53,10 @@ import { GoalImageGallery } from '@mgonza02/goal-image-gallery';
|
|
|
53
53
|
|
|
54
54
|
## Installation & Setup
|
|
55
55
|
|
|
56
|
-
###
|
|
56
|
+
### Installation
|
|
57
57
|
|
|
58
58
|
```bash
|
|
59
|
-
|
|
59
|
+
pnpm add @mgonza02/goal-image-gallery
|
|
60
60
|
```
|
|
61
61
|
|
|
62
62
|
### Peer Dependencies
|
|
@@ -64,7 +64,7 @@ npm install @mgonza02/goal-image-gallery
|
|
|
64
64
|
Make sure you have the required peer dependencies installed:
|
|
65
65
|
|
|
66
66
|
```bash
|
|
67
|
-
|
|
67
|
+
pnpm add @mui/material @mui/icons-material @emotion/react @emotion/styled react react-dom
|
|
68
68
|
```
|
|
69
69
|
|
|
70
70
|
### Import
|
|
@@ -1106,13 +1106,13 @@ When contributing to this component:
|
|
|
1106
1106
|
For detailed information about changes, new features, and updates across versions, see [CHANGELOG.md](CHANGELOG.md).
|
|
1107
1107
|
|
|
1108
1108
|
### Recent Updates
|
|
1109
|
+
- **v1.2.0**: Upgraded to MUI v9, migrated to pnpm, Docker build pipeline, SOLID principles documentation
|
|
1110
|
+
- **v1.1.1**: Modal responsiveness, accessibility improvements, styled-components replaced with MUI Box
|
|
1111
|
+
- **v1.1.0**: Fixed handleAfterUpload array structure for bulk uploads
|
|
1109
1112
|
- **v1.0.6**: Major package cleanup and optimization
|
|
1110
1113
|
- **v1.0.5**: Initial package review and dependency analysis
|
|
1111
1114
|
- **v1.0.4**: Comprehensive documentation overhaul
|
|
1112
1115
|
- **v1.0.3**: NPM publication and scoped package setup
|
|
1113
|
-
- **v1.0.2**: Slot system implementation and UI enhancements
|
|
1114
|
-
- **v1.0.1**: Bug fixes and stability improvements
|
|
1115
|
-
- **v1.0.0**: Initial release with core features
|
|
1116
1116
|
|
|
1117
1117
|
## License
|
|
1118
1118
|
|
package/lib/GoalImageGallery.js
CHANGED
|
@@ -14,7 +14,7 @@ import { downloadImage } from "./utils/image-utils";
|
|
|
14
14
|
* Provides advanced upload capabilities, responsive design, accessibility features, and extensive customization options.
|
|
15
15
|
*
|
|
16
16
|
* @component
|
|
17
|
-
* @version 1.0
|
|
17
|
+
* @version 1.2.0
|
|
18
18
|
* @author Goal Team
|
|
19
19
|
* @since 2023
|
|
20
20
|
*
|
|
@@ -236,7 +236,6 @@ const GoalImageGallery = _ref => {
|
|
|
236
236
|
slotProps = {}
|
|
237
237
|
} = _ref;
|
|
238
238
|
const theme = useTheme();
|
|
239
|
-
const isMobile = useMediaQuery(theme.breakpoints.down("md"));
|
|
240
239
|
const [updatable, setUpdatable] = useState(false);
|
|
241
240
|
const {
|
|
242
241
|
selector: ImageSelector
|
|
@@ -257,7 +256,6 @@ const GoalImageGallery = _ref => {
|
|
|
257
256
|
selectedImageIndex,
|
|
258
257
|
selectingImage,
|
|
259
258
|
imageList,
|
|
260
|
-
selectedImage,
|
|
261
259
|
zoomLevel,
|
|
262
260
|
loading,
|
|
263
261
|
removable,
|
|
@@ -282,8 +280,6 @@ const GoalImageGallery = _ref => {
|
|
|
282
280
|
|
|
283
281
|
// Zoom and navigation handlers
|
|
284
282
|
const {
|
|
285
|
-
handleZoomIn,
|
|
286
|
-
handleZoomOut,
|
|
287
283
|
handlePreviousImage,
|
|
288
284
|
handleNextImage
|
|
289
285
|
} = useImageZoom(getImageUrl, imageList);
|
|
@@ -26,7 +26,9 @@ const ImageGalleryEmptyState = _ref => {
|
|
|
26
26
|
}
|
|
27
27
|
}), /*#__PURE__*/_jsx(Typography, {
|
|
28
28
|
variant: "h6",
|
|
29
|
-
|
|
29
|
+
sx: {
|
|
30
|
+
color: 'text.secondary'
|
|
31
|
+
},
|
|
30
32
|
children: emptyMessage
|
|
31
33
|
}), updatable && /*#__PURE__*/_jsxs(_Fragment, {
|
|
32
34
|
children: [/*#__PURE__*/_jsx(Button, {
|
|
@@ -65,8 +67,10 @@ const ImageGalleryEmptyState = _ref => {
|
|
|
65
67
|
})]
|
|
66
68
|
}), /*#__PURE__*/_jsx(Typography, {
|
|
67
69
|
variant: "caption",
|
|
68
|
-
|
|
69
|
-
|
|
70
|
+
sx: {
|
|
71
|
+
color: 'text.secondary',
|
|
72
|
+
textAlign: 'center'
|
|
73
|
+
},
|
|
70
74
|
children: "Soporta m\xFAltiples m\xE9todos de carga: archivos, portapapeles y URLs"
|
|
71
75
|
})]
|
|
72
76
|
})]
|
|
@@ -1,11 +1,9 @@
|
|
|
1
|
-
import React from 'react';
|
|
2
1
|
import PropTypes from 'prop-types';
|
|
3
|
-
import { Grid, Card, CardContent
|
|
2
|
+
import { Grid, Card, CardContent } from '@mui/material';
|
|
4
3
|
import { useTheme } from '@mui/material/styles';
|
|
5
4
|
import ImageGalleryItem from './ImageGalleryItem';
|
|
6
5
|
import ImageGalleryEmptyState from './ImageGalleryEmptyState';
|
|
7
6
|
import { StyledImageGridContainer } from '../styles/styled-components';
|
|
8
|
-
import { getGridColumns } from '../utils/image-utils';
|
|
9
7
|
|
|
10
8
|
/**
|
|
11
9
|
* Image grid component for displaying gallery images
|
|
@@ -30,8 +28,6 @@ const ImageGalleryGrid = _ref => {
|
|
|
30
28
|
onDownloadImage
|
|
31
29
|
} = _ref;
|
|
32
30
|
const theme = useTheme();
|
|
33
|
-
const isMobile = useMediaQuery(theme.breakpoints.down('md'));
|
|
34
|
-
const isTablet = useMediaQuery(theme.breakpoints.down('lg'));
|
|
35
31
|
if (imageList.length === 0) {
|
|
36
32
|
return /*#__PURE__*/_jsx(Card, {
|
|
37
33
|
elevation: 2,
|
|
@@ -53,8 +49,11 @@ const ImageGalleryGrid = _ref => {
|
|
|
53
49
|
container: true,
|
|
54
50
|
spacing: 2,
|
|
55
51
|
children: imageList.map((image, index) => /*#__PURE__*/_jsx(Grid, {
|
|
56
|
-
|
|
57
|
-
|
|
52
|
+
size: {
|
|
53
|
+
xs: 6,
|
|
54
|
+
sm: multiple ? 4 : 6,
|
|
55
|
+
md: multiple ? 3 : 4
|
|
56
|
+
},
|
|
58
57
|
sx: {
|
|
59
58
|
position: 'relative'
|
|
60
59
|
},
|
|
@@ -3,7 +3,7 @@ import PropTypes from 'prop-types';
|
|
|
3
3
|
import { Box, IconButton, Skeleton, Tooltip, Typography, Button } from '@mui/material';
|
|
4
4
|
import { alpha, useTheme } from '@mui/material/styles';
|
|
5
5
|
import { ChangeCircle as ChangeIcon, Download as DownloadIcon, Visibility as ViewIcon, Add as AddIcon, Delete as DeleteIcon } from '@mui/icons-material';
|
|
6
|
-
import {
|
|
6
|
+
import { getImageContainerStyles, getImageOverlayStyles } from '../styles/styled-components';
|
|
7
7
|
import { handleImageError } from '../utils/image-utils';
|
|
8
8
|
|
|
9
9
|
/**
|
|
@@ -30,8 +30,9 @@ const ImageGalleryItem = _ref => {
|
|
|
30
30
|
|
|
31
31
|
// Handle add button (+) image
|
|
32
32
|
if (image.image_code === '+') {
|
|
33
|
-
return /*#__PURE__*/_jsx(
|
|
33
|
+
return /*#__PURE__*/_jsx(Box, {
|
|
34
34
|
sx: {
|
|
35
|
+
...getImageContainerStyles(theme),
|
|
35
36
|
height: 200,
|
|
36
37
|
display: 'flex',
|
|
37
38
|
alignItems: 'center',
|
|
@@ -62,7 +63,8 @@ const ImageGalleryItem = _ref => {
|
|
|
62
63
|
})
|
|
63
64
|
});
|
|
64
65
|
}
|
|
65
|
-
return /*#__PURE__*/_jsxs(
|
|
66
|
+
return /*#__PURE__*/_jsxs(Box, {
|
|
67
|
+
sx: getImageContainerStyles(theme),
|
|
66
68
|
children: [loading && /*#__PURE__*/_jsx(Skeleton, {
|
|
67
69
|
variant: "rectangular",
|
|
68
70
|
width: "100%",
|
|
@@ -84,8 +86,9 @@ const ImageGalleryItem = _ref => {
|
|
|
84
86
|
objectFit: 'cover',
|
|
85
87
|
display: loading ? 'none' : 'block'
|
|
86
88
|
}
|
|
87
|
-
}, image.image_code), /*#__PURE__*/_jsxs(
|
|
89
|
+
}, image.image_code), /*#__PURE__*/_jsxs(Box, {
|
|
88
90
|
className: "image-overlay",
|
|
91
|
+
sx: getImageOverlayStyles(theme),
|
|
89
92
|
children: [/*#__PURE__*/_jsx(Tooltip, {
|
|
90
93
|
title: "Ver imagen",
|
|
91
94
|
children: /*#__PURE__*/_jsx(IconButton, {
|
|
@@ -1,8 +1,7 @@
|
|
|
1
|
-
import React from 'react';
|
|
2
1
|
import PropTypes from 'prop-types';
|
|
3
2
|
import { Modal, Zoom, Backdrop, Typography, IconButton, Stack, Chip, Tooltip, Box, useMediaQuery, useTheme } from '@mui/material';
|
|
4
3
|
import { Close as CloseIcon, ZoomIn as ZoomInIcon, ZoomOut as ZoomOutIcon, ChevronLeft as ChevronLeftIcon, ChevronRight as ChevronRightIcon } from '@mui/icons-material';
|
|
5
|
-
import {
|
|
4
|
+
import { getModalContainerStyles, getModalHeaderStyles, getModalBodyStyles, getModalFooterStyles } from '../styles/styled-components';
|
|
6
5
|
import { handleImageError } from '../utils/image-utils';
|
|
7
6
|
|
|
8
7
|
/**
|
|
@@ -42,9 +41,10 @@ const ImageGalleryModal = _ref => {
|
|
|
42
41
|
},
|
|
43
42
|
children: /*#__PURE__*/_jsx(Zoom, {
|
|
44
43
|
in: open,
|
|
45
|
-
children: /*#__PURE__*/_jsxs(
|
|
46
|
-
|
|
47
|
-
children: [/*#__PURE__*/_jsxs(
|
|
44
|
+
children: /*#__PURE__*/_jsxs(Box, {
|
|
45
|
+
sx: getModalContainerStyles(theme, isMobile),
|
|
46
|
+
children: [/*#__PURE__*/_jsxs(Box, {
|
|
47
|
+
sx: getModalHeaderStyles(theme),
|
|
48
48
|
children: [/*#__PURE__*/_jsxs(Typography, {
|
|
49
49
|
variant: "h6",
|
|
50
50
|
children: ["Imagen ", selectedImageIndex + 1, " de ", imageList.length]
|
|
@@ -77,7 +77,8 @@ const ImageGalleryModal = _ref => {
|
|
|
77
77
|
})
|
|
78
78
|
})]
|
|
79
79
|
})]
|
|
80
|
-
}), /*#__PURE__*/_jsx(
|
|
80
|
+
}), /*#__PURE__*/_jsx(Box, {
|
|
81
|
+
sx: getModalBodyStyles(theme),
|
|
81
82
|
children: /*#__PURE__*/_jsx(Box, {
|
|
82
83
|
sx: {
|
|
83
84
|
width: '100%',
|
|
@@ -105,7 +106,8 @@ const ImageGalleryModal = _ref => {
|
|
|
105
106
|
onError: e => handleImageError(e, noImageUrl)
|
|
106
107
|
})
|
|
107
108
|
})
|
|
108
|
-
}), imageList.length > 1 && /*#__PURE__*/_jsxs(
|
|
109
|
+
}), imageList.length > 1 && /*#__PURE__*/_jsxs(Box, {
|
|
110
|
+
sx: getModalFooterStyles(theme),
|
|
109
111
|
children: [/*#__PURE__*/_jsx(Tooltip, {
|
|
110
112
|
title: "Imagen anterior",
|
|
111
113
|
children: /*#__PURE__*/_jsx(IconButton, {
|
|
@@ -115,7 +117,9 @@ const ImageGalleryModal = _ref => {
|
|
|
115
117
|
})
|
|
116
118
|
}), /*#__PURE__*/_jsx(Typography, {
|
|
117
119
|
variant: "body2",
|
|
118
|
-
|
|
120
|
+
sx: {
|
|
121
|
+
color: 'text.secondary'
|
|
122
|
+
},
|
|
119
123
|
children: "Use las flechas del teclado para navegar"
|
|
120
124
|
}), /*#__PURE__*/_jsx(Tooltip, {
|
|
121
125
|
title: "Imagen siguiente",
|
package/lib/examples.js
CHANGED
|
@@ -285,8 +285,10 @@ export const AdvancedUploadExample = () => {
|
|
|
285
285
|
children: "Advanced Upload Methods Demo"
|
|
286
286
|
}), /*#__PURE__*/_jsx(Typography, {
|
|
287
287
|
variant: "body2",
|
|
288
|
-
color: "text.secondary",
|
|
289
288
|
paragraph: true,
|
|
289
|
+
sx: {
|
|
290
|
+
color: 'text.secondary'
|
|
291
|
+
},
|
|
290
292
|
children: "This gallery supports multiple upload methods:"
|
|
291
293
|
}), /*#__PURE__*/_jsxs("ul", {
|
|
292
294
|
children: [/*#__PURE__*/_jsx("li", {
|
|
@@ -358,8 +360,10 @@ export const MobileGalleryExample = () => {
|
|
|
358
360
|
children: "Mobile-Optimized Gallery"
|
|
359
361
|
}), /*#__PURE__*/_jsx(Typography, {
|
|
360
362
|
variant: "body2",
|
|
361
|
-
color: "text.secondary",
|
|
362
363
|
paragraph: true,
|
|
364
|
+
sx: {
|
|
365
|
+
color: 'text.secondary'
|
|
366
|
+
},
|
|
363
367
|
children: "Optimized for mobile devices with touch-friendly interface"
|
|
364
368
|
}), /*#__PURE__*/_jsx(GoalImageGallery, {
|
|
365
369
|
imageCodes: mobileImages,
|
|
@@ -542,14 +546,16 @@ export const CustomSelectorExample = () => {
|
|
|
542
546
|
children: title
|
|
543
547
|
}), /*#__PURE__*/_jsx(Typography, {
|
|
544
548
|
variant: "body1",
|
|
545
|
-
color: "text.secondary",
|
|
546
549
|
paragraph: true,
|
|
550
|
+
sx: {
|
|
551
|
+
color: 'text.secondary'
|
|
552
|
+
},
|
|
547
553
|
children: uploadMessage
|
|
548
554
|
}), /*#__PURE__*/_jsxs(Typography, {
|
|
549
555
|
variant: "caption",
|
|
550
|
-
display: "block",
|
|
551
|
-
color: "text.secondary",
|
|
552
556
|
sx: {
|
|
557
|
+
display: 'block',
|
|
558
|
+
color: 'text.secondary',
|
|
553
559
|
mb: 2
|
|
554
560
|
},
|
|
555
561
|
children: ["Maximum file size: ", maxFileSize / 1024 / 1024, "MB | Theme: ", theme]
|
|
@@ -612,8 +618,10 @@ export const CustomSelectorExample = () => {
|
|
|
612
618
|
children: "Custom Image Selector with Slots"
|
|
613
619
|
}), /*#__PURE__*/_jsx(Typography, {
|
|
614
620
|
variant: "body2",
|
|
615
|
-
color: "text.secondary",
|
|
616
621
|
paragraph: true,
|
|
622
|
+
sx: {
|
|
623
|
+
color: 'text.secondary'
|
|
624
|
+
},
|
|
617
625
|
children: "This example demonstrates how to use the slot system to provide a custom image selector with enhanced UI and functionality."
|
|
618
626
|
}), /*#__PURE__*/_jsx(GoalImageGallery, {
|
|
619
627
|
imageCodes: images,
|
|
@@ -768,12 +776,16 @@ export const BulkUploadExample = () => {
|
|
|
768
776
|
children: "Bulk Upload Images"
|
|
769
777
|
}), /*#__PURE__*/_jsx(Typography, {
|
|
770
778
|
variant: "body2",
|
|
771
|
-
color: "text.secondary",
|
|
772
779
|
paragraph: true,
|
|
780
|
+
sx: {
|
|
781
|
+
color: 'text.secondary'
|
|
782
|
+
},
|
|
773
783
|
children: "Drop multiple images here or click to select"
|
|
774
784
|
}), selectedFiles.length > 0 && /*#__PURE__*/_jsxs(Typography, {
|
|
775
785
|
variant: "body2",
|
|
776
|
-
|
|
786
|
+
sx: {
|
|
787
|
+
color: 'success.main'
|
|
788
|
+
},
|
|
777
789
|
children: [selectedFiles.length, " file", selectedFiles.length !== 1 ? 's' : '', " selected"]
|
|
778
790
|
}), /*#__PURE__*/_jsx(Button, {
|
|
779
791
|
variant: "contained",
|
|
@@ -800,8 +812,10 @@ export const BulkUploadExample = () => {
|
|
|
800
812
|
children: "Bulk Upload Gallery"
|
|
801
813
|
}), /*#__PURE__*/_jsx(Typography, {
|
|
802
814
|
variant: "body2",
|
|
803
|
-
color: "text.secondary",
|
|
804
815
|
paragraph: true,
|
|
816
|
+
sx: {
|
|
817
|
+
color: 'text.secondary'
|
|
818
|
+
},
|
|
805
819
|
children: "This example demonstrates bulk upload functionality where multiple images can be uploaded at once. The handleAfterUpload method now accepts arrays of image objects."
|
|
806
820
|
}), /*#__PURE__*/_jsx(GoalImageGallery, {
|
|
807
821
|
imageCodes: galleryImages,
|
|
@@ -1,173 +1,142 @@
|
|
|
1
1
|
import { Box } from '@mui/material';
|
|
2
|
-
import { alpha
|
|
2
|
+
import { alpha } from '@mui/material/styles';
|
|
3
3
|
|
|
4
4
|
/**
|
|
5
|
-
*
|
|
5
|
+
* Styles for image containers with enhanced hover effects
|
|
6
6
|
*/
|
|
7
|
-
export const
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
'
|
|
22
|
-
|
|
23
|
-
boxShadow: theme.shadows[4],
|
|
24
|
-
transform: 'translateY(-2px)',
|
|
25
|
-
'& .image-overlay': {
|
|
26
|
-
opacity: 1
|
|
27
|
-
}
|
|
7
|
+
export const getImageContainerStyles = theme => ({
|
|
8
|
+
position: 'relative',
|
|
9
|
+
borderRadius: theme.spacing(1.5),
|
|
10
|
+
overflow: 'hidden',
|
|
11
|
+
backgroundColor: theme.palette.background.paper,
|
|
12
|
+
border: `1px solid ${theme.palette.divider}`,
|
|
13
|
+
cursor: 'pointer',
|
|
14
|
+
transition: theme.transitions.create(['border-color', 'box-shadow', 'transform'], {
|
|
15
|
+
duration: theme.transitions.duration.short
|
|
16
|
+
}),
|
|
17
|
+
'&:hover': {
|
|
18
|
+
borderColor: theme.palette.primary.main,
|
|
19
|
+
boxShadow: theme.shadows[4],
|
|
20
|
+
transform: 'translateY(-2px)',
|
|
21
|
+
'& .image-overlay': {
|
|
22
|
+
opacity: 1
|
|
28
23
|
}
|
|
29
|
-
}
|
|
24
|
+
}
|
|
30
25
|
});
|
|
31
26
|
|
|
32
27
|
/**
|
|
33
|
-
*
|
|
28
|
+
* Styles for image overlay with action buttons
|
|
34
29
|
*/
|
|
35
|
-
export const
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
'
|
|
54
|
-
|
|
55
|
-
backgroundColor: alpha(theme.palette.common.black, 0.7),
|
|
56
|
-
margin: theme.spacing(0.5),
|
|
57
|
-
'&:hover': {
|
|
58
|
-
backgroundColor: alpha(theme.palette.common.black, 0.9)
|
|
59
|
-
}
|
|
30
|
+
export const getImageOverlayStyles = theme => ({
|
|
31
|
+
position: 'absolute',
|
|
32
|
+
top: 0,
|
|
33
|
+
left: 0,
|
|
34
|
+
right: 0,
|
|
35
|
+
bottom: 0,
|
|
36
|
+
background: alpha(theme.palette.common.black, 0.5),
|
|
37
|
+
display: 'flex',
|
|
38
|
+
alignItems: 'center',
|
|
39
|
+
justifyContent: 'center',
|
|
40
|
+
opacity: 0,
|
|
41
|
+
transition: theme.transitions.create('opacity', {
|
|
42
|
+
duration: theme.transitions.duration.short
|
|
43
|
+
}),
|
|
44
|
+
'& .MuiIconButton-root': {
|
|
45
|
+
color: theme.palette.common.white,
|
|
46
|
+
backgroundColor: alpha(theme.palette.common.black, 0.7),
|
|
47
|
+
margin: theme.spacing(0.5),
|
|
48
|
+
'&:hover': {
|
|
49
|
+
backgroundColor: alpha(theme.palette.common.black, 0.9)
|
|
60
50
|
}
|
|
61
|
-
}
|
|
51
|
+
}
|
|
62
52
|
});
|
|
63
53
|
|
|
64
54
|
/**
|
|
65
|
-
*
|
|
55
|
+
* Styles for modal container
|
|
66
56
|
*/
|
|
67
|
-
export const
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
borderRadius: theme.spacing(2),
|
|
82
|
-
overflow: 'hidden',
|
|
83
|
-
display: 'flex',
|
|
84
|
-
flexDirection: 'column',
|
|
85
|
-
boxShadow: 24
|
|
86
|
-
};
|
|
57
|
+
export const getModalContainerStyles = (theme, isMobile) => ({
|
|
58
|
+
top: '50%',
|
|
59
|
+
left: '50%',
|
|
60
|
+
transform: 'translate(-50%, -50%) !important',
|
|
61
|
+
position: 'absolute',
|
|
62
|
+
width: isMobile ? '95vw' : '90vw',
|
|
63
|
+
maxWidth: 1200,
|
|
64
|
+
height: isMobile ? '95vh' : '90vh',
|
|
65
|
+
backgroundColor: theme.palette.background.paper,
|
|
66
|
+
borderRadius: theme.spacing(2),
|
|
67
|
+
overflow: 'hidden',
|
|
68
|
+
display: 'flex',
|
|
69
|
+
flexDirection: 'column',
|
|
70
|
+
boxShadow: 24
|
|
87
71
|
});
|
|
88
72
|
|
|
89
73
|
/**
|
|
90
|
-
*
|
|
74
|
+
* Styles for modal header
|
|
91
75
|
*/
|
|
92
|
-
export const
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
alignItems: 'center',
|
|
100
|
-
padding: theme.spacing(2),
|
|
101
|
-
borderBottom: `1px solid ${theme.palette.divider}`,
|
|
102
|
-
backgroundColor: alpha(theme.palette.background.paper, 0.95)
|
|
103
|
-
};
|
|
76
|
+
export const getModalHeaderStyles = theme => ({
|
|
77
|
+
display: 'flex',
|
|
78
|
+
justifyContent: 'space-between',
|
|
79
|
+
alignItems: 'center',
|
|
80
|
+
padding: theme.spacing(2),
|
|
81
|
+
borderBottom: `1px solid ${theme.palette.divider}`,
|
|
82
|
+
backgroundColor: alpha(theme.palette.background.paper, 0.95)
|
|
104
83
|
});
|
|
105
84
|
|
|
106
85
|
/**
|
|
107
|
-
*
|
|
86
|
+
* Styles for modal body
|
|
108
87
|
*/
|
|
109
|
-
export const
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
justifyContent: 'center',
|
|
118
|
-
overflow: 'hidden',
|
|
119
|
-
position: 'relative',
|
|
120
|
-
backgroundColor: theme.palette.grey[50]
|
|
121
|
-
};
|
|
88
|
+
export const getModalBodyStyles = theme => ({
|
|
89
|
+
flex: 1,
|
|
90
|
+
display: 'flex',
|
|
91
|
+
alignItems: 'center',
|
|
92
|
+
justifyContent: 'center',
|
|
93
|
+
overflow: 'hidden',
|
|
94
|
+
position: 'relative',
|
|
95
|
+
backgroundColor: theme.palette.grey[50]
|
|
122
96
|
});
|
|
123
97
|
|
|
124
98
|
/**
|
|
125
|
-
*
|
|
99
|
+
* Styles for modal footer
|
|
126
100
|
*/
|
|
127
|
-
export const
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
alignItems: 'center',
|
|
135
|
-
padding: theme.spacing(2),
|
|
136
|
-
borderTop: `1px solid ${theme.palette.divider}`,
|
|
137
|
-
backgroundColor: alpha(theme.palette.background.paper, 0.95)
|
|
138
|
-
};
|
|
101
|
+
export const getModalFooterStyles = theme => ({
|
|
102
|
+
display: 'flex',
|
|
103
|
+
justifyContent: 'space-between',
|
|
104
|
+
alignItems: 'center',
|
|
105
|
+
padding: theme.spacing(2),
|
|
106
|
+
borderTop: `1px solid ${theme.palette.divider}`,
|
|
107
|
+
backgroundColor: alpha(theme.palette.background.paper, 0.95)
|
|
139
108
|
});
|
|
140
109
|
|
|
141
110
|
/**
|
|
142
|
-
*
|
|
111
|
+
* Styles for empty state container
|
|
143
112
|
*/
|
|
144
|
-
export const
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
justifyContent: 'center',
|
|
152
|
-
alignItems: 'center',
|
|
153
|
-
padding: theme.spacing(2),
|
|
154
|
-
minHeight: 300
|
|
155
|
-
};
|
|
113
|
+
export const getEmptyStateContainerStyles = theme => ({
|
|
114
|
+
display: 'flex',
|
|
115
|
+
flexDirection: 'column',
|
|
116
|
+
justifyContent: 'center',
|
|
117
|
+
alignItems: 'center',
|
|
118
|
+
padding: theme.spacing(2),
|
|
119
|
+
minHeight: 300
|
|
156
120
|
});
|
|
157
121
|
|
|
158
122
|
/**
|
|
159
|
-
*
|
|
123
|
+
* Styles for image grid container
|
|
160
124
|
*/
|
|
161
|
-
export const
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
125
|
+
export const getImageGridContainerStyles = theme => ({
|
|
126
|
+
display: 'flex',
|
|
127
|
+
flexDirection: 'column',
|
|
128
|
+
justifyContent: 'center',
|
|
129
|
+
alignItems: 'center',
|
|
130
|
+
padding: theme.spacing(2),
|
|
131
|
+
minHeight: 200
|
|
132
|
+
});
|
|
133
|
+
|
|
134
|
+
// Legacy styled components exports for backward compatibility
|
|
135
|
+
export const StyledImageContainer = Box;
|
|
136
|
+
export const ImageOverlay = Box;
|
|
137
|
+
export const StyledModalContainer = Box;
|
|
138
|
+
export const StyledModalHeader = Box;
|
|
139
|
+
export const StyledModalBody = Box;
|
|
140
|
+
export const StyledModalFooter = Box;
|
|
141
|
+
export const StyledEmptyStateContainer = Box;
|
|
142
|
+
export const StyledImageGridContainer = Box;
|
package/package.json
CHANGED
|
@@ -1,90 +1,89 @@
|
|
|
1
1
|
{
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
2
|
+
"name": "@mgonza02/goal-image-gallery",
|
|
3
|
+
"version": "1.2.0",
|
|
4
|
+
"description": "Advanced, accessible, and highly customizable React image gallery component with multi-method upload, responsive design, and extensive TypeScript support",
|
|
5
|
+
"main": "lib/index.js",
|
|
6
|
+
"module": "lib/index.js",
|
|
7
|
+
"types": "lib/index.d.ts",
|
|
8
|
+
"keywords": [
|
|
9
|
+
"react",
|
|
10
|
+
"image-gallery",
|
|
11
|
+
"material-ui",
|
|
12
|
+
"component",
|
|
13
|
+
"upload",
|
|
14
|
+
"drag-drop",
|
|
15
|
+
"clipboard",
|
|
16
|
+
"modal",
|
|
17
|
+
"zoom",
|
|
18
|
+
"responsive"
|
|
19
|
+
],
|
|
20
|
+
"author": "Goal Team",
|
|
21
|
+
"license": "MIT",
|
|
22
|
+
"repository": {
|
|
23
|
+
"type": "git",
|
|
24
|
+
"url": "git+https://github.com/mgonza02/goal-image-gallery.git"
|
|
25
|
+
},
|
|
26
|
+
"homepage": "https://github.com/mgonza02/goal-image-gallery#readme",
|
|
27
|
+
"bugs": {
|
|
28
|
+
"url": "https://github.com/mgonza02/goal-image-gallery/issues"
|
|
29
|
+
},
|
|
30
|
+
"publishConfig": {
|
|
31
|
+
"access": "public"
|
|
32
|
+
},
|
|
33
|
+
"files": [
|
|
34
|
+
"lib/",
|
|
35
|
+
"README.md",
|
|
36
|
+
"CHANGELOG.md",
|
|
37
|
+
"QUICK_REFERENCE.md",
|
|
38
|
+
"MIGRATION.md",
|
|
39
|
+
"IMPLEMENTATION_GUIDE.md",
|
|
40
|
+
"IMPLEMENTATION_SUMMARY.md",
|
|
41
|
+
"DOCUMENTATION_UPDATE_SUMMARY.md",
|
|
42
|
+
"PACKAGE_CLEANUP_SUMMARY.md",
|
|
43
|
+
"LICENSE"
|
|
44
|
+
],
|
|
45
|
+
"peerDependencies": {
|
|
46
|
+
"@emotion/react": "^11.14.0",
|
|
47
|
+
"@emotion/styled": "^11.14.0",
|
|
48
|
+
"@mui/icons-material": "^9.0.0",
|
|
49
|
+
"@mui/material": "^9.0.0",
|
|
50
|
+
"react": "^18.0.0",
|
|
51
|
+
"react-dom": "^18.0.0"
|
|
52
|
+
},
|
|
53
|
+
"dependencies": {
|
|
54
|
+
"prop-types": "^15.8.0"
|
|
55
|
+
},
|
|
56
|
+
"devDependencies": {
|
|
57
|
+
"@babel/cli": "^7.20.0",
|
|
58
|
+
"@babel/core": "^7.20.0",
|
|
59
|
+
"@babel/preset-env": "^7.20.0",
|
|
60
|
+
"@babel/preset-react": "^7.18.0",
|
|
61
|
+
"prettier": "^3.4.2"
|
|
62
|
+
},
|
|
63
|
+
"browserslist": {
|
|
64
|
+
"production": [
|
|
65
|
+
">0.2%",
|
|
66
|
+
"not dead",
|
|
67
|
+
"not op_mini all"
|
|
19
68
|
],
|
|
20
|
-
"
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
"
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
"
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
"IMPLEMENTATION_SUMMARY.md",
|
|
41
|
-
"DOCUMENTATION_UPDATE_SUMMARY.md",
|
|
42
|
-
"PACKAGE_CLEANUP_SUMMARY.md",
|
|
43
|
-
"LICENSE"
|
|
44
|
-
],
|
|
45
|
-
"peerDependencies": {
|
|
46
|
-
"@emotion/react": "^11.0.0",
|
|
47
|
-
"@emotion/styled": "^11.0.0",
|
|
48
|
-
"@mui/icons-material": "^5.18.0",
|
|
49
|
-
"@mui/material": "^5.18.0",
|
|
50
|
-
"react": "^18.0.0",
|
|
51
|
-
"react-dom": "^18.0.0"
|
|
52
|
-
},
|
|
53
|
-
"dependencies": {
|
|
54
|
-
"prop-types": "^15.8.0"
|
|
55
|
-
},
|
|
56
|
-
"scripts": {
|
|
57
|
-
"build": "npm run clean && npm run build:js && npm run build:types",
|
|
58
|
-
"build:js": "babel src --out-dir lib --copy-files --ignore '**/*.test.js'",
|
|
59
|
-
"build:types": "cp src/index.d.ts lib/index.d.ts",
|
|
60
|
-
"prepublishOnly": "npm run build",
|
|
61
|
-
"format": "prettier --write src/**/*.js",
|
|
62
|
-
"format:check": "prettier --check src/**/*.js",
|
|
63
|
-
"clean": "rm -rf lib",
|
|
64
|
-
"validate": "npm run format:check",
|
|
65
|
-
"dev": "npm run build -- --watch",
|
|
66
|
-
"prepack": "npm run validate && npm run build"
|
|
67
|
-
},
|
|
68
|
-
"devDependencies": {
|
|
69
|
-
"@babel/cli": "^7.20.0",
|
|
70
|
-
"@babel/core": "^7.20.0",
|
|
71
|
-
"@babel/preset-env": "^7.20.0",
|
|
72
|
-
"@babel/preset-react": "^7.18.0",
|
|
73
|
-
"prettier": "^3.4.2"
|
|
74
|
-
},
|
|
75
|
-
"browserslist": {
|
|
76
|
-
"production": [
|
|
77
|
-
">0.2%",
|
|
78
|
-
"not dead",
|
|
79
|
-
"not op_mini all"
|
|
80
|
-
],
|
|
81
|
-
"development": [
|
|
82
|
-
"last 1 chrome version",
|
|
83
|
-
"last 1 firefox version",
|
|
84
|
-
"last 1 safari version"
|
|
85
|
-
]
|
|
86
|
-
},
|
|
87
|
-
"engines": {
|
|
88
|
-
"node": ">=16.0.0"
|
|
89
|
-
}
|
|
69
|
+
"development": [
|
|
70
|
+
"last 1 chrome version",
|
|
71
|
+
"last 1 firefox version",
|
|
72
|
+
"last 1 safari version"
|
|
73
|
+
]
|
|
74
|
+
},
|
|
75
|
+
"engines": {
|
|
76
|
+
"node": ">=18.0.0",
|
|
77
|
+
"pnpm": ">=9.0.0"
|
|
78
|
+
},
|
|
79
|
+
"scripts": {
|
|
80
|
+
"build": "pnpm clean && pnpm build:js && pnpm build:types",
|
|
81
|
+
"build:js": "babel src --out-dir lib --copy-files --ignore '**/*.test.js'",
|
|
82
|
+
"build:types": "cp src/index.d.ts lib/index.d.ts",
|
|
83
|
+
"format": "prettier --write src/**/*.js",
|
|
84
|
+
"format:check": "prettier --check src/**/*.js",
|
|
85
|
+
"clean": "rm -rf lib",
|
|
86
|
+
"validate": "pnpm format:check",
|
|
87
|
+
"dev": "pnpm build -- --watch"
|
|
88
|
+
}
|
|
90
89
|
}
|