diff --git a/projects/aca-content/assets/app.extensions.json b/projects/aca-content/assets/app.extensions.json
index 9c0d7fff4d..51de285a05 100644
--- a/projects/aca-content/assets/app.extensions.json
+++ b/projects/aca-content/assets/app.extensions.json
@@ -1240,6 +1240,18 @@
"visible": "showInfoSelectionButton"
}
},
+ {
+ "id": "app.toolbar.aspects",
+ "order": 160,
+ "title": "APP.ACTIONS.ADD_ASPECTS",
+ "icon": "playlist_add",
+ "actions": {
+ "click": "ASPECT_LIST"
+ },
+ "rules": {
+ "visible": "canEditAspects"
+ }
+ },
{
"id": "app.sidebar.expand",
"order": 200,
@@ -1249,7 +1261,7 @@
"click": "EXPAND_INFO_DRAWER"
},
"rules": {
- "visible": "app.navigation.isNotLibraries"
+ "visible": "canShowExpand"
}
}
],
diff --git a/projects/aca-content/assets/i18n/en.json b/projects/aca-content/assets/i18n/en.json
index bab98e67e3..faf977f981 100644
--- a/projects/aca-content/assets/i18n/en.json
+++ b/projects/aca-content/assets/i18n/en.json
@@ -259,7 +259,8 @@
"LEAVE": "Leave Library",
"EDIT_OFFLINE": "Edit Offline",
"EDIT_OFFLINE_CANCEL": "Cancel Editing",
- "CHANGE_ASPECT": "Edit Aspects"
+ "CHANGE_ASPECT": "Edit Aspects",
+ "ADD_ASPECTS": "Add Aspects"
},
"DIALOGS": {
"CONFIRM_PURGE": {
@@ -394,7 +395,7 @@
},
"INFO_DRAWER": {
"TITLE": "Details",
- "CLOSE": "Close",
+ "REDUCE_PANEL": "Reduce panel",
"DATA_LOADING": "Data is loading",
"TABS": {
"PROPERTIES": "Properties",
@@ -402,7 +403,7 @@
"VERSIONS": "Versions",
"COMMENTS": "Comments",
"PERMISSIONS": "Permissions",
- "EXPAND": "Expand"
+ "EXPAND": "Expand panel"
}
},
"TOOLTIPS": {
diff --git a/projects/aca-content/src/lib/aca-content.module.ts b/projects/aca-content/src/lib/aca-content.module.ts
index 47dd3bc2f7..c0163de6c7 100644
--- a/projects/aca-content/src/lib/aca-content.module.ts
+++ b/projects/aca-content/src/lib/aca-content.module.ts
@@ -192,6 +192,7 @@ export class ContentServiceExtensionModule {
canToggleFavorite: rules.canToggleFavorite,
isLibraryManager: rules.isLibraryManager,
canEditAspects: rules.canEditAspects,
+ canShowExpand: rules.canShowExpand,
canInfoPreview: rules.canInfoPreview,
showInfoSelectionButton: rules.showInfoSelectionButton,
diff --git a/projects/aca-content/src/lib/components/details/details.component.html b/projects/aca-content/src/lib/components/details/details.component.html
index 2d9dda876a..d2b2b752b5 100644
--- a/projects/aca-content/src/lib/components/details/details.component.html
+++ b/projects/aca-content/src/lib/components/details/details.component.html
@@ -12,14 +12,17 @@
-
{{ 'APP.INFO_DRAWER.TITLE' | translate }}
-
+
diff --git a/projects/aca-content/src/lib/components/details/details.component.scss b/projects/aca-content/src/lib/components/details/details.component.scss
index 778bead773..4e76575e86 100644
--- a/projects/aca-content/src/lib/components/details/details.component.scss
+++ b/projects/aca-content/src/lib/components/details/details.component.scss
@@ -1,19 +1,29 @@
app-details-manager {
- .aca-close-details-button {
- margin-right: 15px;
- margin-top: 2px;
- outline: none;
- border-radius: 4px;
-
- &:focus {
- background-color: var(--theme-selected-background-color);
- outline: 2px solid var(--theme-blue-button-color);
- border-radius: 4px;
- }
+ .acs-details-buttons {
+ display: flex;
- &:focus-visible {
- outline: 2px solid var(--theme-blue-button-color);
+ .aca-close-details-button {
+ margin-right: 15px;
+ margin-top: 12px;
+ outline: none;
border-radius: 4px;
+
+ &:focus {
+ background-color: var(--theme-selected-background-color);
+ outline: 2px solid var(--theme-blue-button-color);
+ border-radius: 4px;
+ }
+
+ &:focus-visible {
+ outline: 2px solid var(--theme-blue-button-color);
+ border-radius: 4px;
+ margin-top: 12px;
+
+ &:focus-visible {
+ outline: 2px solid var(--theme-blue-button-color);
+ border-radius: 4px;
+ }
+ }
}
}
}
diff --git a/projects/aca-content/src/lib/components/details/details.component.spec.ts b/projects/aca-content/src/lib/components/details/details.component.spec.ts
index 0988ca7033..6911afef2e 100644
--- a/projects/aca-content/src/lib/components/details/details.component.spec.ts
+++ b/projects/aca-content/src/lib/components/details/details.component.spec.ts
@@ -26,7 +26,7 @@ import { ComponentFixture, TestBed } from '@angular/core/testing';
import { AppTestingModule } from '../../testing/app-testing.module';
import { DetailsComponent } from './details.component';
import { ActivatedRoute } from '@angular/router';
-import { of, Subject } from 'rxjs';
+import { BehaviorSubject, of, Subject } from 'rxjs';
import { NO_ERRORS_SCHEMA } from '@angular/core';
import { Store } from '@ngrx/store';
import { ContentApiService } from '@alfresco/aca-shared';
@@ -49,6 +49,15 @@ describe('DetailsComponent', () => {
select: () => mockStream
};
+ const extensionsServiceMock = {
+ getAllowedSidebarActions: jasmine.createSpy('getAllowedSidebarActions')
+ };
+
+ const mockAspectActions = [];
+
+ const mockObservable = new BehaviorSubject(mockAspectActions);
+ extensionsServiceMock.getAllowedSidebarActions.and.returnValue(mockObservable);
+
beforeEach(() => {
TestBed.configureTestingModule({
imports: [AppTestingModule, DetailsComponent],
@@ -128,4 +137,12 @@ describe('DetailsComponent', () => {
fixture.detectChanges();
expect(store.dispatch).toHaveBeenCalledWith(new SetSelectedNodesAction([node]));
});
+
+ it('should set aspectActions from extensions', () => {
+ extensionsServiceMock.getAllowedSidebarActions.and.returnValue(of(mockAspectActions));
+ fixture.detectChanges();
+ fixture.whenStable().then(() => {
+ expect(component.aspectActions).toEqual(mockAspectActions);
+ });
+ });
});
diff --git a/projects/aca-content/src/lib/components/details/details.component.ts b/projects/aca-content/src/lib/components/details/details.component.ts
index a025c0409c..07a364e846 100644
--- a/projects/aca-content/src/lib/components/details/details.component.ts
+++ b/projects/aca-content/src/lib/components/details/details.component.ts
@@ -36,6 +36,8 @@ import { MatProgressBarModule } from '@angular/material/progress-bar';
import { MatButtonModule } from '@angular/material/button';
import { MetadataTabComponent } from '../info-drawer/metadata-tab/metadata-tab.component';
import { CommentsTabComponent } from '../info-drawer/comments-tab/comments-tab.component';
+import { takeUntil } from 'rxjs/operators';
+import { ContentActionRef } from '@alfresco/adf-extensions';
@Component({
standalone: true,
@@ -63,6 +65,7 @@ export class DetailsComponent extends PageComponent implements OnInit, OnDestroy
isLoading: boolean;
onDestroy$ = new Subject();
activeTab = 1;
+ aspectActions: Array = [];
constructor(private route: ActivatedRoute, private contentApi: ContentApiService) {
super();
@@ -85,6 +88,12 @@ export class DetailsComponent extends PageComponent implements OnInit, OnDestroy
this.store.dispatch(new SetSelectedNodesAction([{ entry: this.node }]));
});
});
+ this.extensions
+ .getAllowedSidebarActions()
+ .pipe(takeUntil(this.onDestroy$))
+ .subscribe((aspectActions) => {
+ this.aspectActions = aspectActions;
+ });
}
setActiveTab(tabName: string) {
diff --git a/projects/aca-content/src/lib/components/info-drawer/metadata-tab/metadata-tab.component.spec.ts b/projects/aca-content/src/lib/components/info-drawer/metadata-tab/metadata-tab.component.spec.ts
index f990d7b3d5..4d01789afc 100644
--- a/projects/aca-content/src/lib/components/info-drawer/metadata-tab/metadata-tab.component.spec.ts
+++ b/projects/aca-content/src/lib/components/info-drawer/metadata-tab/metadata-tab.component.spec.ts
@@ -256,7 +256,7 @@ describe('MetadataTabComponent', () => {
});
it('show pass empty when store is in initial state', () => {
- const initialState = fixture.debugElement.query(By.css('adf-content-metadata-card'));
+ const initialState = fixture.debugElement.query(By.css('adf-content-metadata'));
expect(initialState.componentInstance.displayAspect).toBeFalsy();
});
@@ -266,7 +266,7 @@ describe('MetadataTabComponent', () => {
expect(aspect).toBe('EXIF');
});
fixture.detectChanges();
- const initialState = fixture.debugElement.query(By.css('adf-content-metadata-card'));
+ const initialState = fixture.debugElement.query(By.css('adf-content-metadata'));
expect(initialState.componentInstance.displayAspect).toBe('EXIF');
});
});
diff --git a/projects/aca-content/src/lib/components/info-drawer/metadata-tab/metadata-tab.component.ts b/projects/aca-content/src/lib/components/info-drawer/metadata-tab/metadata-tab.component.ts
index dfcaad995f..2a5654fae3 100644
--- a/projects/aca-content/src/lib/components/info-drawer/metadata-tab/metadata-tab.component.ts
+++ b/projects/aca-content/src/lib/components/info-drawer/metadata-tab/metadata-tab.component.ts
@@ -39,27 +39,36 @@ import { Actions, ofType } from '@ngrx/effects';
imports: [CommonModule, ContentMetadataModule],
selector: 'app-metadata-tab',
template: `
-
-
+
`,
encapsulation: ViewEncapsulation.None,
host: { class: 'app-metadata-tab' }
})
export class MetadataTabComponent implements OnInit, OnDestroy {
protected onDestroy$ = new Subject();
-
@Input()
node: Node;
displayAspect$: Observable;
canUpdateNode = false;
editable = false;
+ editableTags = false;
+ editableCategories = false;
+ group: any = {
+ editable: false
+ };
constructor(
private permission: NodePermissionService,
@@ -91,6 +100,9 @@ export class MetadataTabComponent implements OnInit, OnDestroy {
this.checkIfNodeIsUpdatable(updatedNode?.payload.entry);
if (!this.canUpdateNode) {
this.editable = false;
+ this.editableTags = false;
+ this.editableCategories = false;
+ this.group.editable = false;
}
});
}
diff --git a/projects/aca-content/src/lib/components/toolbar/toggle-edit-offline/toggle-edit-offline.component.spec.ts b/projects/aca-content/src/lib/components/toolbar/toggle-edit-offline/toggle-edit-offline.component.spec.ts
index e061c2a599..c1dc90e3e8 100644
--- a/projects/aca-content/src/lib/components/toolbar/toggle-edit-offline/toggle-edit-offline.component.spec.ts
+++ b/projects/aca-content/src/lib/components/toolbar/toggle-edit-offline/toggle-edit-offline.component.spec.ts
@@ -29,6 +29,7 @@ import { Store } from '@ngrx/store';
import { NodeEntry } from '@alfresco/js-api';
import { DownloadNodesAction, EditOfflineAction, SnackbarErrorAction } from '@alfresco/aca-shared/store';
import { AppTestingModule } from '../../../testing/app-testing.module';
+import { AppExtensionService } from '@alfresco/aca-shared';
describe('ToggleEditOfflineComponent', () => {
let fixture: ComponentFixture;
@@ -38,6 +39,10 @@ describe('ToggleEditOfflineComponent', () => {
let selectSpy: jasmine.Spy;
let selection: any;
+ const extensionsMock = {
+ updateSidebarActions: jasmine.createSpy('updateSidebarActions')
+ };
+
beforeEach(() => {
TestBed.configureTestingModule({
imports: [AppTestingModule, ToggleEditOfflineComponent],
@@ -48,6 +53,10 @@ describe('ToggleEditOfflineComponent', () => {
select: () => {},
dispatch: () => {}
}
+ },
+ {
+ provide: AppExtensionService,
+ useValue: extensionsMock
}
]
});
@@ -133,4 +142,14 @@ describe('ToggleEditOfflineComponent', () => {
})
]);
});
+
+ it('should call updateSidebarActions on click', async () => {
+ selectSpy.and.returnValue(of(selection));
+ fixture.detectChanges();
+
+ await component.onClick();
+ fixture.detectChanges();
+
+ expect(extensionsMock.updateSidebarActions).toHaveBeenCalled();
+ });
});
diff --git a/projects/aca-content/src/lib/components/toolbar/toggle-edit-offline/toggle-edit-offline.component.ts b/projects/aca-content/src/lib/components/toolbar/toggle-edit-offline/toggle-edit-offline.component.ts
index 2862777322..40410b94b5 100644
--- a/projects/aca-content/src/lib/components/toolbar/toggle-edit-offline/toggle-edit-offline.component.ts
+++ b/projects/aca-content/src/lib/components/toolbar/toggle-edit-offline/toggle-edit-offline.component.ts
@@ -33,7 +33,7 @@ import {
import { NodeEntry, SharedLinkEntry, Node, NodesApi } from '@alfresco/js-api';
import { Component, OnInit, ViewEncapsulation } from '@angular/core';
import { Store } from '@ngrx/store';
-import { isLocked } from '@alfresco/aca-shared';
+import { AppExtensionService, isLocked } from '@alfresco/aca-shared';
import { AlfrescoApiService } from '@alfresco/adf-core';
import { CommonModule } from '@angular/common';
import { TranslateModule } from '@ngx-translate/core';
@@ -59,7 +59,7 @@ export class ToggleEditOfflineComponent implements OnInit {
nodeTitle = '';
isNodeLocked = false;
- constructor(private store: Store, private alfrescoApiService: AlfrescoApiService) {
+ constructor(private store: Store, private alfrescoApiService: AlfrescoApiService, private extensions: AppExtensionService) {
this.nodesApi = new NodesApi(this.alfrescoApiService.getInstance());
}
@@ -73,6 +73,7 @@ export class ToggleEditOfflineComponent implements OnInit {
async onClick() {
await this.toggleLock(this.selection);
+ this.extensions.updateSidebarActions();
}
private async toggleLock(node: NodeEntry | SharedLinkEntry) {
diff --git a/projects/aca-content/src/lib/ui/overrides/adf-style-fixes.theme.scss b/projects/aca-content/src/lib/ui/overrides/adf-style-fixes.theme.scss
index 5a3514d2dd..0daf5ea047 100644
--- a/projects/aca-content/src/lib/ui/overrides/adf-style-fixes.theme.scss
+++ b/projects/aca-content/src/lib/ui/overrides/adf-style-fixes.theme.scss
@@ -12,3 +12,34 @@
}
}
}
+
+.adf-info-drawer-layout-content .app-metadata-tab .adf-metadata-properties .mat-expansion-panel {
+ border: 1px solid var(--theme-metadata-property-panel-border-color);
+ border-radius: 12px;
+ margin-bottom: 12px;
+
+ .mat-expansion-panel-header {
+ border-radius: 12px;
+ }
+}
+
+.acs-details-container {
+ .mat-tab-body-content {
+ .adf-metadata-properties {
+ .mat-expansion-panel {
+ width: 755px;
+ border: 1px solid var(--theme-metadata-property-panel-border-color);
+ margin: 24px;
+ border-radius: 12px;
+
+ .mat-expansion-panel-header {
+ border-radius: 12px;
+ }
+
+ .adf-metadata-properties-group-title {
+ width: 548px;
+ }
+ }
+ }
+ }
+}
diff --git a/projects/aca-content/src/lib/ui/variables/variables.scss b/projects/aca-content/src/lib/ui/variables/variables.scss
index 8a11c08041..45bcc8ecd8 100644
--- a/projects/aca-content/src/lib/ui/variables/variables.scss
+++ b/projects/aca-content/src/lib/ui/variables/variables.scss
@@ -36,6 +36,9 @@ $page-layout-header-background-color: #fff;
$search-chip-icon-color: #757575;
$disabled-chip-background-color: #f5f5f5;
$contrast-gray: #646569;
+$metadata-property-panel-border-color: rgba(0, 0, 0, 0.12);
+$metadata-buttons-background-color: rgba(33, 33, 33, 0.05);
+$metadata-action-button-clear-color: #212328b2;
// CSS Variables
$defaults: (
@@ -76,7 +79,10 @@ $defaults: (
--theme-page-layout-header-background-color: $page-layout-header-background-color,
--theme-search-chip-icon-color: $search-chip-icon-color,
--theme-disabled-chip-background-color: $disabled-chip-background-color,
- --theme-contrast-gray: $contrast-gray
+ --theme-contrast-gray: $contrast-gray,
+ --theme-metadata-property-panel-border-color: $metadata-property-panel-border-color,
+ --theme-metadata-buttons-background-color: $metadata-buttons-background-color,
+ --theme-metadata-action-button-clear-color: $metadata-action-button-clear-color
);
// propagates SCSS variables into the CSS variables scope
diff --git a/projects/aca-shared/rules/src/app.rules.spec.ts b/projects/aca-shared/rules/src/app.rules.spec.ts
index 6e5d538d1f..68713f275e 100644
--- a/projects/aca-shared/rules/src/app.rules.spec.ts
+++ b/projects/aca-shared/rules/src/app.rules.spec.ts
@@ -121,6 +121,28 @@ describe('app.evaluators', () => {
});
});
+ describe('canShowExpand', () => {
+ it('should return false when isLibraries returns true', () => {
+ const context: any = {
+ navigation: {
+ url: '/libraries'
+ }
+ };
+
+ expect(app.canShowExpand(context)).toBe(false);
+ });
+
+ it('should return false when isDetails returns true', () => {
+ const context: any = {
+ navigation: {
+ url: '/details'
+ }
+ };
+
+ expect(app.canShowExpand(context)).toBe(false);
+ });
+ });
+
describe('hasLockedFiles', () => {
it('should return [false] if selection not present', () => {
const context: any = {};
diff --git a/projects/aca-shared/rules/src/app.rules.ts b/projects/aca-shared/rules/src/app.rules.ts
index 71333f4bc6..bf06469f2d 100644
--- a/projects/aca-shared/rules/src/app.rules.ts
+++ b/projects/aca-shared/rules/src/app.rules.ts
@@ -511,6 +511,8 @@ export const canEditAspects = (context: RuleContext): boolean =>
repository.isMajorVersionAvailable(context, '7')
].every(Boolean);
+export const canShowExpand = (context: RuleContext): boolean => [!navigation.isLibraries(context), !navigation.isDetails(context)].every(Boolean);
+
/**
* Checks if user can manage permissions for the selected node.
* JSON ref: `canManagePermissions`
diff --git a/projects/aca-shared/rules/src/navigation.rules.spec.ts b/projects/aca-shared/rules/src/navigation.rules.spec.ts
index b0cae7b299..9582223e44 100644
--- a/projects/aca-shared/rules/src/navigation.rules.spec.ts
+++ b/projects/aca-shared/rules/src/navigation.rules.spec.ts
@@ -225,6 +225,28 @@ describe('navigation.evaluators', () => {
});
});
+ describe('isDetails', () => {
+ it('should return true if url includes with `/details`', () => {
+ const context: any = {
+ navigation: {
+ url: '/details/path'
+ }
+ };
+
+ expect(app.isDetails(context)).toBe(true);
+ });
+
+ it('should return false if url not includes with `/details`', () => {
+ const context: any = {
+ navigation: {
+ url: '/path'
+ }
+ };
+
+ expect(app.isDetails(context)).toBe(false);
+ });
+ });
+
describe('isRecentFiles', () => {
it('should return [true] if url starts with `/recent-files`', () => {
const context: any = {
diff --git a/projects/aca-shared/rules/src/navigation.rules.ts b/projects/aca-shared/rules/src/navigation.rules.ts
index 02d6a6df93..a26d8a2366 100644
--- a/projects/aca-shared/rules/src/navigation.rules.ts
+++ b/projects/aca-shared/rules/src/navigation.rules.ts
@@ -110,6 +110,11 @@ export function isLibraryContent(context: RuleContext): boolean {
return url && (url.endsWith('/libraries') || url.includes('/libraries/') || url.startsWith('/search-libraries'));
}
+export function isDetails(context: RuleContext): boolean {
+ const { url } = context.navigation;
+ return url?.includes('/details');
+}
+
/**
* Checks if the activated route is neither **Libraries** nor **Library Search Results**.
* JSON ref: `app.navigation.isNotLibraries`
diff --git a/projects/aca-shared/src/lib/services/app.extension.service.ts b/projects/aca-shared/src/lib/services/app.extension.service.ts
index 393c0339e7..0677bd9ad2 100644
--- a/projects/aca-shared/src/lib/services/app.extension.service.ts
+++ b/projects/aca-shared/src/lib/services/app.extension.service.ts
@@ -348,6 +348,10 @@ export class AppExtensionService implements RuleContext {
};
}
+ updateSidebarActions() {
+ this._sidebarActions.next(this.loader.getContentActions(this.config, 'features.sidebar.toolbar'));
+ }
+
getCreateActions(): Observable> {
return this._createActions.pipe(
map((createActions) =>