@squiz/resource-browser 1.65.0 → 1.66.1
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 +18 -0
- package/lib/PreviewPanel/details/MatrixResource.d.ts +2 -1
- package/lib/PreviewPanel/details/MatrixResource.js +7 -3
- package/lib/ResourceBreadcrumb/ResourceBreadcrumb.d.ts +2 -1
- package/lib/ResourceList/ResourceList.d.ts +2 -1
- package/lib/ResourcePicker/ResourcePicker.d.ts +1 -1
- package/lib/ResourcePicker/States/Error.d.ts +2 -1
- package/lib/ResourcePicker/States/Loading.d.ts +2 -1
- package/lib/ResourcePicker/States/Selected.d.ts +2 -1
- package/lib/ResourcePickerContainer/ResourcePickerContainer.d.ts +2 -1
- package/lib/SourceDropdown/SourceDropdown.d.ts +2 -1
- package/lib/SourceList/SourceList.d.ts +2 -1
- package/lib/StatusIndicator/StatusIndicator.d.ts +2 -1
- package/lib/index.css +20 -0
- package/lib/index.d.ts +2 -1
- package/package.json +8 -4
- package/src/Hooks/useResourcePath.spec.ts +14 -18
- package/src/PreviewPanel/PreviewPanel.spec.tsx +43 -0
- package/src/PreviewPanel/PreviewPanel.stories.tsx +23 -0
- package/src/PreviewPanel/details/MatrixResource.tsx +15 -3
- package/src/PreviewPanel/details/matrix-resource.scss +16 -0
- package/src/ResourceList/sample-resources.json +30 -1
- package/src/ResourcePicker/mock-image-resource.json +2 -2
- package/src/index.scss +9 -0
package/CHANGELOG.md
CHANGED
@@ -1,5 +1,23 @@
|
|
1
1
|
# @squiz/resource-browser
|
2
2
|
|
3
|
+
## 1.66.1
|
4
|
+
|
5
|
+
### Patch Changes
|
6
|
+
|
7
|
+
- 81c7cba: Image asset previews will now display the image if there is a URL in the returned resource data
|
8
|
+
Also fixes a bug around the selected resource name not having break-word applied so the filename was not wrapping as expected
|
9
|
+
|
10
|
+
## 1.66.0
|
11
|
+
|
12
|
+
### Minor Changes
|
13
|
+
|
14
|
+
- 5032c38: Added content page asset icon.
|
15
|
+
|
16
|
+
### Patch Changes
|
17
|
+
|
18
|
+
- Updated dependencies [5032c38]
|
19
|
+
- @squiz/generic-browser-lib@1.65.0
|
20
|
+
|
3
21
|
## 1.65.0
|
4
22
|
|
5
23
|
### Minor Changes
|
@@ -1,6 +1,7 @@
|
|
1
|
+
import React from 'react';
|
1
2
|
import { Resource } from '../../types';
|
2
3
|
type MatrixResourceProps = {
|
3
4
|
resource: Resource;
|
4
5
|
};
|
5
|
-
declare const MatrixResource: ({ resource: { id, type, name, status } }: MatrixResourceProps) => JSX.Element;
|
6
|
+
declare const MatrixResource: ({ resource: { id, type, name, status, url } }: MatrixResourceProps) => React.JSX.Element;
|
6
7
|
export default MatrixResource;
|
@@ -6,11 +6,15 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
6
|
const react_1 = __importDefault(require("react"));
|
7
7
|
const generic_browser_lib_1 = require("@squiz/generic-browser-lib");
|
8
8
|
const StatusIndicator_1 = __importDefault(require("../../StatusIndicator/StatusIndicator"));
|
9
|
-
const
|
9
|
+
const ImageThumb = ({ url, name }) => {
|
10
|
+
return (react_1.default.createElement("div", { className: "checkered-bg w-full h-[164px] overflow-hidden flex justify-center items-center" },
|
11
|
+
react_1.default.createElement("img", { src: url, className: "max-w-full max-h-full", alt: name })));
|
12
|
+
};
|
13
|
+
const MatrixResource = ({ resource: { id, type, name, status, url } }) => {
|
10
14
|
return (react_1.default.createElement("div", null,
|
11
15
|
react_1.default.createElement("div", { className: "flex flex-col items-center text-gray-800 mt-7 mx-5 pb-4 border-b border-gray-300" },
|
12
|
-
react_1.default.createElement(generic_browser_lib_1.Icon, { icon: type.code, resourceSource: "matrix", className: "w-14 h-14" }),
|
13
|
-
react_1.default.createElement("div", { className: "mt-4 font-semibold text-base" }, name)),
|
16
|
+
type.code === 'image' && url ? (react_1.default.createElement(ImageThumb, { url: url, name: name })) : (react_1.default.createElement(generic_browser_lib_1.Icon, { icon: type.code, resourceSource: "matrix", className: "w-14 h-14" })),
|
17
|
+
react_1.default.createElement("div", { className: "mt-4 font-semibold text-base break-word" }, name)),
|
14
18
|
react_1.default.createElement("div", { className: "text-gray-800 mx-6 mt-4" },
|
15
19
|
react_1.default.createElement("dl", { className: "flex flex-col text-sm" },
|
16
20
|
react_1.default.createElement("div", { className: "flex mb-2" },
|
@@ -1,8 +1,9 @@
|
|
1
|
+
import React from 'react';
|
1
2
|
import { Hierarchy } from '../types';
|
2
3
|
export interface ResourceBreadcrumbProps<T> {
|
3
4
|
hierarchy: Hierarchy<T>;
|
4
5
|
onBreadcrumbSelect: (node: T) => void;
|
5
6
|
onReturnToRoot: () => void;
|
6
7
|
}
|
7
|
-
declare const ResourceBreadcrumb: <T>({ hierarchy, onBreadcrumbSelect, onReturnToRoot }: ResourceBreadcrumbProps<T>) => JSX.Element;
|
8
|
+
declare const ResourceBreadcrumb: <T>({ hierarchy, onBreadcrumbSelect, onReturnToRoot }: ResourceBreadcrumbProps<T>) => React.JSX.Element;
|
8
9
|
export default ResourceBreadcrumb;
|
@@ -1,3 +1,4 @@
|
|
1
|
+
import React from 'react';
|
1
2
|
import { OverlayTriggerState } from 'react-stately';
|
2
3
|
import { DOMAttributes, FocusableElement } from '@react-types/shared';
|
3
4
|
import { Resource } from '../types';
|
@@ -13,5 +14,5 @@ export interface ResourceListProps {
|
|
13
14
|
handleReload: () => void;
|
14
15
|
error: Error | null;
|
15
16
|
}
|
16
|
-
declare const ResourceList: ({ resources, selectedResource, previewModalState, isLoading, onResourceSelect, onResourceDrillDown, allowedTypes, handleReturnToRoot, handleReload, error, }: ResourceListProps) => JSX.Element;
|
17
|
+
declare const ResourceList: ({ resources, selectedResource, previewModalState, isLoading, onResourceSelect, onResourceDrillDown, allowedTypes, handleReturnToRoot, handleReload, error, }: ResourceListProps) => React.JSX.Element;
|
17
18
|
export default ResourceList;
|
@@ -10,5 +10,5 @@ export type ResourcePickerProps = {
|
|
10
10
|
children: (onClose: () => void, titleProps: DOMAttributes) => React.ReactElement;
|
11
11
|
onClear: () => void;
|
12
12
|
};
|
13
|
-
declare const ResourcePicker: ({ resource, allowedTypes, error, isLoading, isDisabled, children, onClear, }: ResourcePickerProps) => JSX.Element;
|
13
|
+
declare const ResourcePicker: ({ resource, allowedTypes, error, isLoading, isDisabled, children, onClear, }: ResourcePickerProps) => React.JSX.Element;
|
14
14
|
export default ResourcePicker;
|
@@ -1,6 +1,7 @@
|
|
1
|
+
import React from 'react';
|
1
2
|
export type ErrorStateProps = {
|
2
3
|
error: Error;
|
3
4
|
isDisabled?: boolean;
|
4
5
|
onClear: () => void;
|
5
6
|
};
|
6
|
-
export declare const ErrorState: ({ error, isDisabled, onClear }: ErrorStateProps) => JSX.Element;
|
7
|
+
export declare const ErrorState: ({ error, isDisabled, onClear }: ErrorStateProps) => React.JSX.Element;
|
@@ -1 +1,2 @@
|
|
1
|
-
|
1
|
+
import React from 'react';
|
2
|
+
export declare const LoadingState: () => React.JSX.Element;
|
@@ -1,7 +1,8 @@
|
|
1
|
+
import React from 'react';
|
1
2
|
import { Resource } from '../../types';
|
2
3
|
export type SelectedStateProps = {
|
3
4
|
resource: Resource;
|
4
5
|
isDisabled?: boolean;
|
5
6
|
onClear: () => void;
|
6
7
|
};
|
7
|
-
export declare const SelectedState: ({ resource: { id, type, name, status, squizImage }, isDisabled, onClear, }: SelectedStateProps) => JSX.Element;
|
8
|
+
export declare const SelectedState: ({ resource: { id, type, name, status, squizImage }, isDisabled, onClear, }: SelectedStateProps) => React.JSX.Element;
|
@@ -1,3 +1,4 @@
|
|
1
|
+
import React from 'react';
|
1
2
|
import { DOMAttributes, FocusableElement } from '@react-types/shared';
|
2
3
|
import { Source, Resource, HydratedResourceReference } from '../types';
|
3
4
|
interface ResourcePickerContainerProps {
|
@@ -9,5 +10,5 @@ interface ResourcePickerContainerProps {
|
|
9
10
|
onChange(resource: HydratedResourceReference | null): void;
|
10
11
|
onClose: () => void;
|
11
12
|
}
|
12
|
-
declare function ResourcePickerContainer({ title, titleAriaProps, allowedTypes, onRequestSources, onRequestChildren, onChange, onClose, }: ResourcePickerContainerProps): JSX.Element;
|
13
|
+
declare function ResourcePickerContainer({ title, titleAriaProps, allowedTypes, onRequestSources, onRequestChildren, onChange, onClose, }: ResourcePickerContainerProps): React.JSX.Element;
|
13
14
|
export default ResourcePickerContainer;
|
@@ -1,3 +1,4 @@
|
|
1
|
+
import React from 'react';
|
1
2
|
import type { Source, ScopedSource } from '../types';
|
2
3
|
export default function SourceDropdown({ sources, selectedSource, isLoading, onRootSelect, onSourceSelect, }: {
|
3
4
|
sources: Source[];
|
@@ -5,4 +6,4 @@ export default function SourceDropdown({ sources, selectedSource, isLoading, onR
|
|
5
6
|
isLoading: boolean;
|
6
7
|
onRootSelect: () => void;
|
7
8
|
onSourceSelect: (source: ScopedSource) => void;
|
8
|
-
}): JSX.Element;
|
9
|
+
}): React.JSX.Element;
|
@@ -1,3 +1,4 @@
|
|
1
|
+
import React from 'react';
|
1
2
|
import { OverlayTriggerState } from 'react-stately';
|
2
3
|
import { DOMAttributes, FocusableElement } from '@react-types/shared';
|
3
4
|
import { Source, ScopedSource } from '../types';
|
@@ -9,5 +10,5 @@ export interface SourceListProps {
|
|
9
10
|
handleReload: () => void;
|
10
11
|
error: Error | null;
|
11
12
|
}
|
12
|
-
declare const SourceList: ({ sources, previewModalState, isLoading, onSourceSelect, handleReload, error, }: SourceListProps) => JSX.Element;
|
13
|
+
declare const SourceList: ({ sources, previewModalState, isLoading, onSourceSelect, handleReload, error, }: SourceListProps) => React.JSX.Element;
|
13
14
|
export default SourceList;
|
@@ -1,7 +1,8 @@
|
|
1
|
+
import React from 'react';
|
1
2
|
import { Status } from '../types';
|
2
3
|
export type StatusIndicatorProps = {
|
3
4
|
className?: string;
|
4
5
|
status: Status;
|
5
6
|
};
|
6
|
-
declare const StatusIndicator: ({ className, status }: StatusIndicatorProps) => JSX.Element;
|
7
|
+
declare const StatusIndicator: ({ className, status }: StatusIndicatorProps) => React.JSX.Element;
|
7
8
|
export default StatusIndicator;
|
package/lib/index.css
CHANGED
@@ -565,6 +565,9 @@
|
|
565
565
|
.squiz-rb-scope .h-9 {
|
566
566
|
height: 2.25rem;
|
567
567
|
}
|
568
|
+
.squiz-rb-scope .h-\[164px\] {
|
569
|
+
height: 164px;
|
570
|
+
}
|
568
571
|
.squiz-rb-scope .h-\[20px\] {
|
569
572
|
height: 20px;
|
570
573
|
}
|
@@ -583,6 +586,9 @@
|
|
583
586
|
.squiz-rb-scope .max-h-80 {
|
584
587
|
max-height: 20rem;
|
585
588
|
}
|
589
|
+
.squiz-rb-scope .max-h-full {
|
590
|
+
max-height: 100%;
|
591
|
+
}
|
586
592
|
.squiz-rb-scope .min-h-\[64px\] {
|
587
593
|
min-height: 64px;
|
588
594
|
}
|
@@ -643,6 +649,9 @@
|
|
643
649
|
.squiz-rb-scope .max-w-\[50rem\] {
|
644
650
|
max-width: 50rem;
|
645
651
|
}
|
652
|
+
.squiz-rb-scope .max-w-full {
|
653
|
+
max-width: 100%;
|
654
|
+
}
|
646
655
|
.squiz-rb-scope .flex-1 {
|
647
656
|
flex: 1 1 0%;
|
648
657
|
}
|
@@ -1019,6 +1028,13 @@
|
|
1019
1028
|
--tw-bg-opacity: 1;
|
1020
1029
|
background-color: rgb(247 247 247 / var(--tw-bg-opacity));
|
1021
1030
|
}
|
1031
|
+
.squiz-rb-scope .checkered-bg {
|
1032
|
+
--tw-bg-opacity: 1;
|
1033
|
+
background-color: rgb(255 255 255 / var(--tw-bg-opacity));
|
1034
|
+
background-size: 24px 24px;
|
1035
|
+
background-position: 0 0, 12px 12px;
|
1036
|
+
background-image: linear-gradient(45deg, #e0e0e0 25%, transparent 25%, transparent 75%, #e0e0e0 75%, #e0e0e0), linear-gradient(45deg, #e0e0e0 25%, transparent 25%, transparent 75%, #e0e0e0 75%, #e0e0e0);
|
1037
|
+
}
|
1022
1038
|
.squiz-rb-scope .spinner {
|
1023
1039
|
display: inline-block;
|
1024
1040
|
border-radius: 9999px;
|
@@ -1083,6 +1099,10 @@
|
|
1083
1099
|
.squiz-rb-scope .p-4\.5 {
|
1084
1100
|
padding: 18px;
|
1085
1101
|
}
|
1102
|
+
.squiz-rb-scope .break-word {
|
1103
|
+
word-break: break-word;
|
1104
|
+
overflow-wrap: anywhere;
|
1105
|
+
}
|
1086
1106
|
.squiz-rb-scope .before\:fixed::before {
|
1087
1107
|
content: var(--tw-content);
|
1088
1108
|
position: fixed;
|
package/lib/index.d.ts
CHANGED
@@ -1,3 +1,4 @@
|
|
1
|
+
import React from 'react';
|
1
2
|
import { HydratedResourceReference, Resource, ResourceReference, Source } from './types';
|
2
3
|
import { ResourceBrowserContext, ResourceBrowserContextProps } from './ResourceBrowserContext/ResourceBrowserContext';
|
3
4
|
export type { HydratedResourceReference, Resource, ResourceReference, Source, ResourceBrowserContextProps };
|
@@ -10,4 +11,4 @@ export type ResourceBrowserInputProps = {
|
|
10
11
|
onChange(resource: HydratedResourceReference | null): void;
|
11
12
|
onClear?(): void;
|
12
13
|
};
|
13
|
-
export declare const ResourceBrowserInput: ({ modalTitle, allowedTypes, onChange, value, isDisabled, onClear, }: ResourceBrowserInputProps) => JSX.Element;
|
14
|
+
export declare const ResourceBrowserInput: ({ modalTitle, allowedTypes, onChange, value, isDisabled, onClear, }: ResourceBrowserInputProps) => React.JSX.Element;
|
package/package.json
CHANGED
@@ -1,8 +1,12 @@
|
|
1
1
|
{
|
2
2
|
"name": "@squiz/resource-browser",
|
3
|
-
"version": "1.
|
3
|
+
"version": "1.66.1",
|
4
4
|
"main": "lib/index.js",
|
5
5
|
"types": "lib/index.d.ts",
|
6
|
+
"private": false,
|
7
|
+
"publishConfig": {
|
8
|
+
"access": "public"
|
9
|
+
},
|
6
10
|
"scripts": {
|
7
11
|
"compile": "npm run clean && npm run compile:styles && npm run compile:code",
|
8
12
|
"compile:code": "tsc",
|
@@ -16,7 +20,7 @@
|
|
16
20
|
"dependencies": {
|
17
21
|
"@mui/icons-material": "5.11.16",
|
18
22
|
"@squiz/dx-json-schema-lib": "^1.65.0",
|
19
|
-
"@squiz/generic-browser-lib": "^1.
|
23
|
+
"@squiz/generic-browser-lib": "^1.65.0",
|
20
24
|
"pretty-bytes": "5.6.0",
|
21
25
|
"react-aria": "3.23.1",
|
22
26
|
"react-responsive": "9.0.2",
|
@@ -35,8 +39,8 @@
|
|
35
39
|
"@testing-library/react": "14.0.0",
|
36
40
|
"@testing-library/user-event": "14.4.3",
|
37
41
|
"@types/postcss-js": "4.0.0",
|
38
|
-
"@types/react": "18.
|
39
|
-
"@types/react-dom": "18.
|
42
|
+
"@types/react": "^18.2.45",
|
43
|
+
"@types/react-dom": "^18.2.18",
|
40
44
|
"@vitejs/plugin-react-swc": "3.0.0",
|
41
45
|
"autoprefixer": "10.4.14",
|
42
46
|
"esbuild": "0.17.17",
|
@@ -19,7 +19,7 @@ describe('useResourcePath', () => {
|
|
19
19
|
});
|
20
20
|
});
|
21
21
|
|
22
|
-
it('setSource should update the source and clear the current hierarchy',
|
22
|
+
it('setSource should update the source and clear the current hierarchy', () => {
|
23
23
|
const { result } = renderHook(() => useResourcePath());
|
24
24
|
const source = mockScopedSource({
|
25
25
|
source: { id: '1', name: 'Test source' },
|
@@ -27,15 +27,15 @@ describe('useResourcePath', () => {
|
|
27
27
|
});
|
28
28
|
const resource = mockResource({ id: '3', name: 'Test resource 2' });
|
29
29
|
|
30
|
-
|
31
|
-
|
30
|
+
act(() => result.current.setSource(source));
|
31
|
+
act(() => result.current.push(resource));
|
32
32
|
|
33
33
|
// make sure the current resource/hierarchy is populated
|
34
34
|
expect(result.current.currentResource).toBe(resource);
|
35
35
|
expect(result.current.hierarchy).toHaveLength(2);
|
36
36
|
|
37
37
|
// set the source again
|
38
|
-
|
38
|
+
act(() => result.current.setSource(source));
|
39
39
|
|
40
40
|
// make sure the current resource and hierarchy are reset
|
41
41
|
expect(result.current.source).toBe(source);
|
@@ -43,15 +43,15 @@ describe('useResourcePath', () => {
|
|
43
43
|
expect(result.current.hierarchy).toEqual([{ key: 'source:1-resource:2', label: 'Test resource', node: source }]);
|
44
44
|
});
|
45
45
|
|
46
|
-
it('push should add the node to the hierarchy',
|
46
|
+
it('push should add the node to the hierarchy', () => {
|
47
47
|
const { result } = renderHook(() => useResourcePath());
|
48
48
|
const source = mockScopedSource({ source: { id: '1' } });
|
49
49
|
const site = mockResource({ id: '1', type: { code: 'site', name: 'Site' }, name: 'My site' });
|
50
50
|
const page = mockResource({ id: '2', type: { code: 'page', name: 'Page' }, name: 'My page' });
|
51
51
|
|
52
|
-
|
53
|
-
|
54
|
-
|
52
|
+
act(() => result.current.setSource(source));
|
53
|
+
act(() => result.current.push(site));
|
54
|
+
act(() => result.current.push(page));
|
55
55
|
|
56
56
|
expect(result.current.source).toBe(source);
|
57
57
|
expect(result.current.currentResource).toBe(page);
|
@@ -94,11 +94,7 @@ describe('useResourcePath', () => {
|
|
94
94
|
],
|
95
95
|
])(
|
96
96
|
'popUntil should remove from the hierarchy until the node being popped to is hit - %s',
|
97
|
-
|
98
|
-
description: string,
|
99
|
-
node: ScopedSource | Resource,
|
100
|
-
expectedHierarchy: Hierarchy<ScopedSource | Resource>,
|
101
|
-
) => {
|
97
|
+
(description: string, node: ScopedSource | Resource, expectedHierarchy: Hierarchy<ScopedSource | Resource>) => {
|
102
98
|
const { result } = renderHook(() => useResourcePath());
|
103
99
|
const source = mockScopedSource({ source: { id: '1' } });
|
104
100
|
const mockResources = [
|
@@ -107,16 +103,16 @@ describe('useResourcePath', () => {
|
|
107
103
|
mockResource({ id: '3', name: 'Resource 3' }),
|
108
104
|
];
|
109
105
|
|
110
|
-
|
111
|
-
|
112
|
-
|
113
|
-
|
106
|
+
act(() => result.current.setSource(source));
|
107
|
+
act(() => result.current.push(mockResources[0]));
|
108
|
+
act(() => result.current.push(mockResources[1]));
|
109
|
+
act(() => result.current.push(mockResources[2]));
|
114
110
|
|
115
111
|
// make sure hierarchy has expected length before popping
|
116
112
|
expect(result.current.source).toBe(source);
|
117
113
|
expect(result.current.hierarchy).toHaveLength(4);
|
118
114
|
|
119
|
-
|
115
|
+
act(() => result.current.popUntil(node));
|
120
116
|
|
121
117
|
expect(result.current.hierarchy).toEqual(expectedHierarchy);
|
122
118
|
},
|
@@ -38,6 +38,22 @@ function mockResource(properties: Partial<Resource> = {}): Resource {
|
|
38
38
|
};
|
39
39
|
}
|
40
40
|
|
41
|
+
function mockImageResource(properties: Partial<Resource> = {}): Resource {
|
42
|
+
return {
|
43
|
+
id: 'test-image-resource',
|
44
|
+
name: 'Test image resource',
|
45
|
+
type: { code: 'image', name: 'Image' },
|
46
|
+
status: { code: 'live', name: 'Live' },
|
47
|
+
url: 'https://www.rspcasa.org.au/wp-content/uploads/2020/10/Baby-goat-in-tree.jpg',
|
48
|
+
urls: [
|
49
|
+
'https://www.rspcasa.org.au/wp-content/uploads/2020/10/Baby-goat-in-tree.jpg',
|
50
|
+
'http://www.rspcasa.org.au/wp-content/uploads/2020/10/Baby-goat-in-tree.jpg',
|
51
|
+
],
|
52
|
+
childCount: 0,
|
53
|
+
...properties,
|
54
|
+
};
|
55
|
+
}
|
56
|
+
|
41
57
|
describe('PreviewPanel', () => {
|
42
58
|
it('Renders a message when no item selected', async () => {
|
43
59
|
const onSelect = jest.fn();
|
@@ -65,6 +81,33 @@ describe('PreviewPanel', () => {
|
|
65
81
|
});
|
66
82
|
});
|
67
83
|
|
84
|
+
it('Renders an image when an image is selected', async () => {
|
85
|
+
const onSelect = jest.fn();
|
86
|
+
const onClose = jest.fn();
|
87
|
+
const resource = mockImageResource();
|
88
|
+
|
89
|
+
render(
|
90
|
+
<PreviewPanelTestWrapper
|
91
|
+
constructFunction={(previewModalState, overlayProps) => {
|
92
|
+
return (
|
93
|
+
<PreviewPanel
|
94
|
+
resource={resource}
|
95
|
+
allowedTypes={undefined}
|
96
|
+
modalState={previewModalState}
|
97
|
+
previewModalOverlayProps={overlayProps}
|
98
|
+
onSelect={onSelect}
|
99
|
+
onClose={onClose}
|
100
|
+
/>
|
101
|
+
);
|
102
|
+
}}
|
103
|
+
/>,
|
104
|
+
);
|
105
|
+
|
106
|
+
await waitFor(() => {
|
107
|
+
expect(screen.queryByAltText(resource.name)).toBeTruthy();
|
108
|
+
});
|
109
|
+
});
|
110
|
+
|
68
111
|
it('Renders tablet / desktop very above 640px', async () => {
|
69
112
|
const onSelect = jest.fn();
|
70
113
|
const onClose = jest.fn();
|
@@ -46,6 +46,29 @@ Primary.args = {
|
|
46
46
|
allowedTypes: undefined,
|
47
47
|
};
|
48
48
|
|
49
|
+
export const ImageAsset = Template.bind({});
|
50
|
+
ImageAsset.args = {
|
51
|
+
resource: {
|
52
|
+
id: '104',
|
53
|
+
name: 'Little goat face',
|
54
|
+
type: {
|
55
|
+
code: 'image',
|
56
|
+
name: 'Image',
|
57
|
+
},
|
58
|
+
status: {
|
59
|
+
code: 'live',
|
60
|
+
name: 'Live',
|
61
|
+
},
|
62
|
+
url: 'https://www.rspcasa.org.au/wp-content/uploads/2020/10/Baby-goat-in-tree.jpg',
|
63
|
+
urls: [
|
64
|
+
'https://www.rspcasa.org.au/wp-content/uploads/2020/10/Baby-goat-in-tree.jpg',
|
65
|
+
'http://www.rspcasa.org.au/wp-content/uploads/2020/10/Baby-goat-in-tree.jpg',
|
66
|
+
],
|
67
|
+
childCount: 0,
|
68
|
+
},
|
69
|
+
allowedTypes: undefined,
|
70
|
+
};
|
71
|
+
|
49
72
|
export const NoSelected = Template.bind({});
|
50
73
|
NoSelected.args = {
|
51
74
|
...Primary.args,
|
@@ -8,12 +8,24 @@ type MatrixResourceProps = {
|
|
8
8
|
resource: Resource;
|
9
9
|
};
|
10
10
|
|
11
|
-
const
|
11
|
+
const ImageThumb = ({ url, name }: { url: string; name: string }) => {
|
12
|
+
return (
|
13
|
+
<div className="checkered-bg w-full h-[164px] overflow-hidden flex justify-center items-center">
|
14
|
+
<img src={url} className="max-w-full max-h-full" alt={name} />
|
15
|
+
</div>
|
16
|
+
);
|
17
|
+
};
|
18
|
+
|
19
|
+
const MatrixResource = ({ resource: { id, type, name, status, url } }: MatrixResourceProps) => {
|
12
20
|
return (
|
13
21
|
<div>
|
14
22
|
<div className="flex flex-col items-center text-gray-800 mt-7 mx-5 pb-4 border-b border-gray-300">
|
15
|
-
|
16
|
-
|
23
|
+
{type.code === 'image' && url ? (
|
24
|
+
<ImageThumb url={url} name={name} />
|
25
|
+
) : (
|
26
|
+
<Icon icon={type.code as IconOptions} resourceSource="matrix" className="w-14 h-14" />
|
27
|
+
)}
|
28
|
+
<div className="mt-4 font-semibold text-base break-word">{name}</div>
|
17
29
|
</div>
|
18
30
|
<div className="text-gray-800 mx-6 mt-4">
|
19
31
|
<dl className="flex flex-col text-sm">
|
@@ -0,0 +1,16 @@
|
|
1
|
+
$sds-grey-300: #e0e0e0;
|
2
|
+
|
3
|
+
.checkered-bg {
|
4
|
+
@apply bg-white;
|
5
|
+
background-size: 24px 24px;
|
6
|
+
background-position: 0 0, 12px 12px;
|
7
|
+
background-image: linear-gradient(
|
8
|
+
45deg,
|
9
|
+
$sds-grey-300 25%,
|
10
|
+
transparent 25%,
|
11
|
+
transparent 75%,
|
12
|
+
$sds-grey-300 75%,
|
13
|
+
$sds-grey-300
|
14
|
+
),
|
15
|
+
linear-gradient(45deg, $sds-grey-300 25%, transparent 25%, transparent 75%, $sds-grey-300 75%, $sds-grey-300);
|
16
|
+
}
|
@@ -75,7 +75,9 @@
|
|
75
75
|
"name": "Live"
|
76
76
|
},
|
77
77
|
"name": "Image",
|
78
|
-
"childCount": 0
|
78
|
+
"childCount": 0,
|
79
|
+
"url": "https://picsum.photos/200/150",
|
80
|
+
"urls": ["https://picsum.photos/200/150", "http://picsum.photos/200/150"]
|
79
81
|
},
|
80
82
|
{
|
81
83
|
"id": "105",
|
@@ -154,6 +156,19 @@
|
|
154
156
|
},
|
155
157
|
"name": "Word document",
|
156
158
|
"childCount": 0
|
159
|
+
},
|
160
|
+
{
|
161
|
+
"id": "111",
|
162
|
+
"type": {
|
163
|
+
"code": "page_content",
|
164
|
+
"name": "Content Page"
|
165
|
+
},
|
166
|
+
"status": {
|
167
|
+
"code": "live",
|
168
|
+
"name": "Live"
|
169
|
+
},
|
170
|
+
"name": "Content page",
|
171
|
+
"childCount": 0
|
157
172
|
}
|
158
173
|
]
|
159
174
|
},
|
@@ -457,6 +472,20 @@
|
|
457
472
|
"name": "Asset with an even longer title to make it is so long that it causes the container to grow in size. It is truly really just so long and I don't know what else I could possibly say about it to express just how long it is.",
|
458
473
|
"childCount": 456
|
459
474
|
},
|
475
|
+
{
|
476
|
+
"id": "903",
|
477
|
+
"type": {
|
478
|
+
"code": "image",
|
479
|
+
"name": "Image"
|
480
|
+
},
|
481
|
+
"status": {
|
482
|
+
"code": "live",
|
483
|
+
"name": "Live"
|
484
|
+
},
|
485
|
+
"name": "image_asset_with_a_silly_long_image_file_name_to_check_that_it_does_not_break_out_of_the_layout.jpg.",
|
486
|
+
"childCount": 456,
|
487
|
+
"url": "https://www.rspcasa.org.au/wp-content/uploads/2020/10/Baby-goat-in-tree.jpg"
|
488
|
+
},
|
460
489
|
{
|
461
490
|
"id": "904",
|
462
491
|
"type": {
|
@@ -9,8 +9,8 @@
|
|
9
9
|
"code": "under_construction",
|
10
10
|
"name": "Under Construction"
|
11
11
|
},
|
12
|
-
"url": "",
|
13
|
-
"urls": [],
|
12
|
+
"url": "https://picsum.photos/200/150",
|
13
|
+
"urls": ["https://picsum.photos/200/150", "http://picsum.photos/200/150"],
|
14
14
|
"childCount": 0,
|
15
15
|
"squizImage": {
|
16
16
|
"name": "Fancy music",
|
package/src/index.scss
CHANGED
@@ -6,6 +6,7 @@
|
|
6
6
|
// Components
|
7
7
|
@import './ResourceBreadcrumb/resource-breadcrumb';
|
8
8
|
@import './ResourcePicker/resource-picker';
|
9
|
+
@import './PreviewPanel/details/matrix-resource';
|
9
10
|
@import '@squiz/generic-browser-lib/src/Spinner/spinner';
|
10
11
|
@import '@squiz/generic-browser-lib/src/Skeleton/skeleton';
|
11
12
|
|
@@ -22,3 +23,11 @@ svg {
|
|
22
23
|
.p-4\.5 {
|
23
24
|
padding: 18px;
|
24
25
|
}
|
26
|
+
|
27
|
+
// In tailwind there is no break-word as it is deprecated, but break-words which is slightly different does not work here, so I have added the suggested combination here
|
28
|
+
// https://v1.tailwindcss.com/docs/word-break
|
29
|
+
// https://github.com/tailwindlabs/tailwindcss/discussions/2213
|
30
|
+
.break-word {
|
31
|
+
word-break: break-word;
|
32
|
+
overflow-wrap: anywhere;
|
33
|
+
}
|