MOBILE-4248 mod-data-action: Add actions menu to action

main
Alfonso Salces 2023-04-20 15:33:54 +02:00
parent 19625470ee
commit 01561748d7
8 changed files with 91 additions and 6 deletions

View File

@ -568,6 +568,7 @@
"addon.mod_data.search": "data",
"addon.mod_data.searchbytagsnotsupported": "local_moodlemobileapp",
"addon.mod_data.selectedrequired": "data",
"addon.mod_data.showmore": "data",
"addon.mod_data.single": "data",
"addon.mod_data.tagarea_data_records": "data",
"addon.mod_data.timeadded": "data",

View File

@ -23,12 +23,15 @@ import {
AddonModDataAction,
AddonModDataData,
AddonModDataEntry,
AddonModDataGetDataAccessInformationWSResponse,
AddonModDataProvider,
AddonModDataTemplateMode,
} from '../../services/data';
import { AddonModDataHelper } from '../../services/data-helper';
import { AddonModDataOffline } from '../../services/data-offline';
import { AddonModDataModuleHandlerService } from '../../services/handlers/module';
import { CoreDomUtils } from '@services/utils/dom';
import { AddonModDataActionsMenuComponent, AddonModDataActionsMenuItem } from '../actionsmenu/actionsmenu';
/**
* Component that displays a database action.
@ -39,6 +42,7 @@ import { AddonModDataModuleHandlerService } from '../../services/handlers/module
})
export class AddonModDataActionComponent implements OnInit {
@Input() access?: AddonModDataGetDataAccessInformationWSResponse; // Access info.
@Input() mode!: AddonModDataTemplateMode; // The render mode.
@Input() action!: AddonModDataAction; // The field to render.
@Input() entry!: AddonModDataEntry; // The value of the field.
@ -139,4 +143,66 @@ export class AddonModDataActionComponent implements OnInit {
CoreEvents.trigger(AddonModDataProvider.ENTRY_CHANGED, { dataId: dataId, entryId: entryId }, this.siteId);
}
/**
* Open actions menu popover.
*/
async actionsMenu(): Promise<void> {
const items: AddonModDataActionsMenuItem[] = [];
if (this.entry.canmanageentry) {
items.push(
this.entry.deleted
? {
action: () => this.undoDelete(),
text: 'core.restore',
icon: 'fas-rotate-left',
}
: {
action: () => this.deleteEntry(),
text: 'core.delete',
icon: 'fas-trash',
},
);
if (!this.entry.deleted) {
items.unshift({
action: () => this.editEntry(),
text: 'core.edit',
icon: 'fas-pen',
});
}
}
if (this.database.approval && this.access?.canapprove && !this.entry.deleted) {
items.push(
!this.entry.approved
? {
action: () => this.approveEntry(),
text: 'addon.mod_data.approve',
icon: 'fas-thumbs-up',
}
: {
action: () => this.disapproveEntry(),
text: 'addon.mod_data.disapprove',
icon: 'far-thumbs-down',
},
);
}
if (this.mode === AddonModDataTemplateMode.LIST) {
items.unshift({
action: () => this.viewEntry(),
text: 'addon.mod_data.showmore',
icon: 'fas-magnifying-glass-plus',
});
}
await CoreDomUtils.openPopover({
component: AddonModDataActionsMenuComponent,
componentProps: { items },
showBackdrop: true,
id: 'actionsmenu-popover',
});
}
}

View File

@ -1,4 +1,10 @@
<ion-button size="small" *ngIf="action == 'more'" fill="clear" (click)="viewEntry()" [attr.aria-label]="'addon.mod_data.more' | translate">
<ion-button size="small" *ngIf="action == 'actionsmenu'" fill="clear" (click)="actionsMenu()"
[attr.aria-label]="'addon.mod_data.actions' | translate">
<ion-icon name="fas-ellipsis-vertical" slot="icon-only" aria-hidden="true"></ion-icon>
</ion-button>
<ion-button size="small" *ngIf="action == 'more'" fill="clear" (click)="viewEntry()"
[attr.aria-label]="'addon.mod_data.showmore' | translate">
<ion-icon name="fas-magnifying-glass-plus" slot="icon-only" aria-hidden="true"></ion-icon>
</ion-button>

View File

@ -95,6 +95,7 @@ export class AddonModDataIndexComponent extends CoreCourseModuleMainActivityComp
database: AddonModDataData;
title: string;
group: number;
access: AddonModDataGetDataAccessInformationWSResponse | undefined;
gotoEntry: (entryId: number) => void;
};
@ -348,7 +349,7 @@ export class AddonModDataIndexComponent extends CoreCourseModuleMainActivityComp
this.entries.forEach((entry, index) => {
entriesById[entry.id] = entry;
const actions = AddonModDataHelper.getActions(this.database!, this.access!, entry);
const actions = AddonModDataHelper.getActions(this.database!, this.access!, entry, AddonModDataTemplateMode.LIST);
const options: AddonModDatDisplayFieldsOptions = {};
if (!this.search.searching) {
options.offset = this.search.page * AddonModDataProvider.PER_PAGE + index - numOfflineEntries;
@ -375,6 +376,7 @@ export class AddonModDataIndexComponent extends CoreCourseModuleMainActivityComp
database: this.database!,
title: this.module.name,
group: this.selectedGroup,
access: this.access,
gotoEntry: (entryId) => this.gotoEntry(entryId),
};
} else if (!this.search.searching) {

View File

@ -1,4 +1,5 @@
{
"actions": "Actions menu",
"addentries": "Add entries",
"advancedsearch": "Advanced search",
"alttext": "Alternative text",
@ -42,6 +43,7 @@
"search": "Search",
"searchbytagsnotsupported": "Sorry, searching by tags is not supported by the app.",
"selectedrequired": "All selected required",
"showmore": "Show more",
"single": "View single",
"tagarea_data_records": "Data records",
"timeadded": "Time added",

View File

@ -86,6 +86,7 @@ export class AddonModDataEntryPage implements OnInit, OnDestroy {
database: AddonModDataData;
title: string;
group: number;
access: AddonModDataGetDataAccessInformationWSResponse | undefined;
};
ratingInfo?: CoreRatingInfo;
@ -187,7 +188,7 @@ export class AddonModDataEntryPage implements OnInit, OnDestroy {
this.selectedGroup = CoreGroups.validateGroupId(this.selectedGroup, this.groupInfo);
const actions = AddonModDataHelper.getActions(this.database, this.access, this.entry!);
const actions = AddonModDataHelper.getActions(this.database, this.access, this.entry!, AddonModDataTemplateMode.SHOW);
const template = AddonModDataHelper.getTemplate(this.database, AddonModDataTemplateType.SINGLE, this.fieldsArray);
this.entryHtml = AddonModDataHelper.displayShowFields(
@ -215,6 +216,7 @@ export class AddonModDataEntryPage implements OnInit, OnDestroy {
database: this.database,
title: this.title,
group: this.selectedGroup,
access: this.access,
};
if (this.logAfterFetch) {

View File

@ -234,7 +234,7 @@ export class AddonModDataHelperProvider {
render = Translate.instant('addon.mod_data.' + (entry.approved ? 'approved' : 'notapproved'));
} else {
render = `<addon-mod-data-action action="${action}" [entry]="entries[${entry.id}]" mode="${mode}" ` +
'[database]="database" [title]="title" ' +
'[database]="database" [access]="access" [title]="title" ' +
(options.offset !== undefined ? `[offset]="${options.offset}" ` : '') +
(options.sortBy !== undefined ? `[sortBy]="${options.sortBy}" ` : '') +
(options.sortDirection !== undefined ? `sortDirection="${options.sortDirection}" ` : '') +
@ -407,6 +407,7 @@ export class AddonModDataHelperProvider {
database: AddonModDataData,
accessInfo: AddonModDataGetDataAccessInformationWSResponse,
entry: AddonModDataEntry,
mode: AddonModDataTemplateMode,
): Record<AddonModDataAction, boolean> {
return {
add: false, // Not directly used on entries.
@ -426,6 +427,10 @@ export class AddonModDataHelperProvider {
approvalstatus: database.approval,
comments: database.comments,
actionsmenu: entry.canmanageentry
|| (database.approval && accessInfo.canapprove && !entry.deleted)
|| mode === AddonModDataTemplateMode.LIST,
// Unsupported actions.
delcheck: false,
export: false,
@ -497,7 +502,7 @@ export class AddonModDataHelperProvider {
html.push(
'<tr class="lastrow">',
'<td class="controls template-field cell c0 lastcol" style="" colspan="2">',
'##edit## ##more## ##delete## ##approve## ##disapprove## ##export##',
'##actionsmenu## ##edit## ##more## ##delete## ##approve## ##disapprove## ##export##',
'</td>',
'</tr>',
);
@ -505,7 +510,7 @@ export class AddonModDataHelperProvider {
html.push(
'<tr class="lastrow">',
'<td class="controls template-field cell c0 lastcol" style="" colspan="2">',
'##edit## ##delete## ##approve## ##disapprove## ##export##',
'##actionsmenu## ##edit## ##delete## ##approve## ##disapprove## ##export##',
'</td>',
'</tr>',
);

View File

@ -62,6 +62,7 @@ export enum AddonModDataAction {
APPROVALSTATUS = 'approvalstatus',
DELCHECK = 'delcheck', // Unused.
EXPORT = 'export', // Unused.
ACTIONSMENU = 'actionsmenu',
}
export enum AddonModDataTemplateType {