Browse Source

Integrate @angular/aria tabs into permission management

Refactored the permission management component to use @angular/aria tab components for group navigation, improving accessibility and structure. Updated the template and styles to support ngTabs, TabList, Tab, TabPanel, and TabContent. Added @angular/aria as a peer dependency in package.json.
pull/24689/head
Fahri Gedik 2 weeks ago
parent
commit
c3f3edf13a
  1. 3
      npm/ng-packs/packages/permission-management/package.json
  2. 123
      npm/ng-packs/packages/permission-management/src/lib/components/permission-management.component.html
  3. 22
      npm/ng-packs/packages/permission-management/src/lib/components/permission-management.component.ts

3
npm/ng-packs/packages/permission-management/package.json

@ -10,6 +10,9 @@
"@abp/ng.theme.shared": "~10.1.0-rc.1",
"tslib": "^2.0.0"
},
"peerDependencies": {
"@angular/aria": "21.0.0"
},
"publishConfig": {
"access": "public"
},

123
npm/ng-packs/packages/permission-management/src/lib/components/permission-management.component.html

@ -43,18 +43,27 @@
<legend class="px-1 h5 mb-0">
{{ 'AbpPermissionManagement::PermissionGroup' | abpLocalization }}
</legend>
<div class="row">
<div class="row" ngTabs orientation="vertical">
<div class="col-md-4">
<div class="overflow-auto lpx-scroll-pills-container scroll-in-modal">
<ul class="nav nav-pills flex-column">
<div
class="overflow-auto lpx-scroll-pills-container scroll-in-modal"
ngTabList
orientation="vertical"
selectionMode="follow"
[selectedTab]="selectedGroup?.name"
(selectedTabChange)="onTabChange($event)"
>
<div class="nav nav-pills flex-column">
@for (group of permissionGroups(); track $index) {
<li class="border nav-item">
<div class="border nav-item">
@if ({ assignedCount: getAssignedCount(group.name) }; as count) {
<a
class="nav-link pointer"
[class.active]="selectedGroup?.name === group?.name"
(click)="onChangeGroup(group)"
(select)="setDisabled(group.permissions)"
<button
ngTab
[value]="group.name"
class="nav-link pointer text-start w-100"
#tab="ngTab"
[class.active]="tab.selected()"
type="button"
>
<div [class.font-weight-bold]="count.assignedCount">
{{ group?.displayName }}
@ -62,59 +71,65 @@
<span>({{ count.assignedCount }})</span>
}
</div>
</a>
</button>
}
</li>
</div>
}
</ul>
</div>
</div>
</div>
<div class="col-md-8 scroll-in-modal">
<div class="ps-1">
@if (selectedGroupPermissions.length) {
<div class="form-check mb-2">
<input
#selectAllInThisTabsRef
type="checkbox"
id="select-all-in-this-tabs"
name="select-all-in-this-tabs"
class="form-check-input"
[(ngModel)]="selectThisTab"
[disabled]="disableSelectAllTab"
(click)="onClickSelectThisTab()"
/>
<label class="form-check-label" for="select-all-in-this-tabs">{{
'AbpPermissionManagement::SelectAllInThisTab' | abpLocalization
}}</label>
</div>
<hr class="my-2" />
@for (permission of selectedGroupPermissions; track $index; let i = $index) {
<div [ngStyle]="permission.style" class="form-check mb-2">
<input
#permissionCheckbox
type="checkbox"
[checked]="getChecked(permission.name)"
[value]="getChecked(permission.name)"
[attr.id]="permission.name"
class="form-check-input"
[disabled]="isGrantedByOtherProviderName(permission.grantedProviders)"
(click)="onClickCheckbox(permission, permissionCheckbox.value)"
/>
<label class="form-check-label" [attr.for]="permission.name"
>{{ permission.displayName }}
@if (!hideBadges) {
@for (provider of permission.grantedProviders; track $index) {
<span class="badge bg-primary text-dark"
>{{ provider.providerName }}: {{ provider.providerKey }}</span
>
}
@for (group of permissionGroups(); track $index) {
<div ngTabPanel [value]="group.name">
<ng-template ngTabContent>
<div class="ps-1">
@if (selectedGroupPermissions.length) {
<div class="form-check mb-2">
<input
#selectAllInThisTabsRef
type="checkbox"
id="select-all-in-this-tabs"
name="select-all-in-this-tabs"
class="form-check-input"
[(ngModel)]="selectThisTab"
[disabled]="disableSelectAllTab"
(click)="onClickSelectThisTab()"
/>
<label class="form-check-label" for="select-all-in-this-tabs">{{
'AbpPermissionManagement::SelectAllInThisTab' | abpLocalization
}}</label>
</div>
<hr class="my-2" />
@for (permission of selectedGroupPermissions; track $index; let i = $index) {
<div [ngStyle]="permission.style" class="form-check mb-2">
<input
#permissionCheckbox
type="checkbox"
[checked]="getChecked(permission.name)"
[value]="getChecked(permission.name)"
[attr.id]="permission.name"
class="form-check-input"
[disabled]="isGrantedByOtherProviderName(permission.grantedProviders)"
(click)="onClickCheckbox(permission, permissionCheckbox.value)"
/>
<label class="form-check-label" [attr.for]="permission.name"
>{{ permission.displayName }}
@if (!hideBadges) {
@for (provider of permission.grantedProviders; track $index) {
<span class="badge bg-primary text-dark"
>{{ provider.providerName }}: {{ provider.providerKey }}</span
>
}
}
</label>
</div>
}
</label>
}
</div>
}
}
</div>
</ng-template>
</div>
}
</div>
</div>
</fieldset>

22
npm/ng-packs/packages/permission-management/src/lib/components/permission-management.component.ts

@ -34,6 +34,8 @@ import { PermissionManagement } from '../models';
import { NgStyle } from '@angular/common';
import { FormsModule } from '@angular/forms';
import { Tabs, TabList, Tab, TabPanel, TabContent } from '@angular/aria/tabs';
type PermissionWithStyle = PermissionGrantInfoDto & {
style: string;
};
@ -56,7 +58,7 @@ type PermissionWithGroupName = PermissionGrantInfoDto & {
max-height: calc(100vh - 23.1rem);
}
.lpx-scroll-pills-container ul {
.lpx-scroll-pills-container .nav-pills {
display: block;
overflow-y: auto;
}
@ -66,7 +68,7 @@ type PermissionWithGroupName = PermissionGrantInfoDto & {
.scroll-in-modal {
max-height: calc(100vh - 15rem);
}
.lpx-scroll-pills-container ul {
.lpx-scroll-pills-container .nav-pills {
max-height: 500px;
}
}
@ -81,12 +83,12 @@ type PermissionWithGroupName = PermissionGrantInfoDto & {
padding-bottom: 0 !important;
}
.lpx-scroll-pills-container ul li {
.lpx-scroll-pills-container .nav-item {
margin-bottom: 10px;
border-radius: 10px;
}
.lpx-scroll-pills-container ul li a.active {
.lpx-scroll-pills-container .nav-item .nav-link.active {
color: #fff !important;
border-color: #6c5dd3 !important;
background-color: #6c5dd3 !important;
@ -100,6 +102,11 @@ type PermissionWithGroupName = PermissionGrantInfoDto & {
LocalizationPipe,
ButtonComponent,
ModalCloseDirective,
Tabs,
TabList,
Tab,
TabPanel,
TabContent,
],
})
export class PermissionManagementComponent
@ -418,6 +425,13 @@ export class PermissionManagementComponent
this.onChangeGroup(this.selectedGroup);
}
onTabChange(groupName: string) {
const group = this.permissionGroups().find(g => g.name === groupName);
if (group) {
this.onChangeGroup(group);
}
}
onChangeGroup(group: PermissionGroupDto) {
this.setDisabled(group.permissions);
this.setSelectedGroup(group);

Loading…
Cancel
Save