Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feature/pt 2136 progress bar does not trigger any screen reader status #16398

Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions CHANGELOG-WIP.md
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
- Improved the accessibility of “More” and “Advanced” toggle triggers. ([#16293]](https://github.com/craftcms/cms/pull/16293))
- Improved the accessibility of the Craft Support widget. ([#16293]](https://github.com/craftcms/cms/pull/16293))
- Improved the accessibility of field translatable indicators and tooltips.
- Progress bars now announce their progress to screen readers. ([#16398](https://github.com/craftcms/cms/pull/16398))

### Administration
- Added the “Affiliated Site” native user field. ([#16174](https://github.com/craftcms/cms/pull/16174))
Expand Down Expand Up @@ -148,6 +149,7 @@
- `_includes/forms/autosuggest.twig` now supports a `suggestTemplates` variable.
- `_includes/forms/colorSelect.twig` now supports `options` and `withBlankOption` variables.
- `_includes/forms/selectize.twig` now supports a `color` property in option data, which can be set to a hex value or a color name.
- Added `Craft.IntervalManager`. ([#16398](https://github.com/craftcms/cms/pull/16398))
- Sortable checkbox selects now always display the selected options first on initial render.

### System
Expand Down
15 changes: 14 additions & 1 deletion packages/craftcms-webpack/Craft.d.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,10 @@
// Set up interfaces and types
interface ProgressBarInterface {
new ($element: JQuery, displaySteps?: boolean): ProgressBarInterface;
new (
$element: JQuery,
displaySteps?: boolean,
settings?: Object
): ProgressBarInterface;

$progressBar: JQuery;

Expand All @@ -13,6 +17,14 @@ interface ProgressBarInterface {
showProgressBar(): void;
}

interface IntervalManagerInterface {
new (settings?: Object): IntervalManagerInterface;

stop(): void;

start(): void;
}

type Site = {
handle: string;
id: number;
Expand All @@ -25,6 +37,7 @@ declare var Craft: {
csrfTokenName?: string;
csrfTokenValue?: string;
ProgressBar: ProgressBarInterface;
IntervalManager: IntervalManagerInterface;
t(category: string, message: string, params?: object): string;
sendActionRequest(method: string, action: string, options?: object): Promise;
initUiElements($container: JQuery): void;
Expand Down
4 changes: 4 additions & 0 deletions src/translations/en/app.php
Original file line number Diff line number Diff line change
Expand Up @@ -830,6 +830,7 @@
'Includes suspending, unsuspending, and unlocking user accounts.' => 'Includes suspending, unsuspending, and unlocking user accounts.',
'Incorrect current password.' => 'Incorrect current password.',
'Incorrect password.' => 'Incorrect password.',
'Indexing assets: {progress}' => 'Indexing assets: {progress}',
'Indigo' => 'Indigo',
'Information' => 'Information',
'Initial Rows' => 'Initial Rows',
Expand Down Expand Up @@ -1242,6 +1243,8 @@
'Primary fields' => 'Primary fields',
'Primary {type} page' => 'Primary {type} page',
'Primary' => 'Primary',
'Process complete' => 'Process complete',
'Processing' => 'Processing',
'Profile Twig templates when Dev Mode is disabled' => 'Profile Twig templates when Dev Mode is disabled',
'Profile' => 'Profile',
'Progress' => 'Progress',
Expand Down Expand Up @@ -2190,6 +2193,7 @@
'{name} should be at least {value}.' => '{name} should be at least {value}.',
'{name} sorted by {attribute}, {direction}' => '{name} sorted by {attribute}, {direction}',
'{nestedType} can only be created after the {ownerType} has been saved.' => '{nestedType} can only be created after the {ownerType} has been saved.',
'{num} percent complete' => '{num} percent complete',
'{num, number} {num, plural, =1{Available Update} other{Available Updates}}' => '{num, number} {num, plural, =1{Available Update} other{Available Updates}}',
'{num, number} {num, plural, =1{column} other{columns}}' => '{num, number} {num, plural, =1{column} other{columns}}',
'{num, number} {num, plural, =1{day} other{days}}' => '{num, number} {num, plural, =1{day} other{days}}',
Expand Down
2 changes: 1 addition & 1 deletion src/web/assets/assetindexes/dist/AssetIndexer.js

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion src/web/assets/assetindexes/dist/AssetIndexer.js.map

Large diffs are not rendered by default.

58 changes: 54 additions & 4 deletions src/web/assets/assetindexes/src/AssetIndexer.ts
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,7 @@ export class AssetIndexer {
private _priorityTasks: ConcurrentTask[] = [];
private _prunedSessionIds: number[] = [];
private _currentlyReviewing = false;
private intervalAnnouncer: IntervalManagerInterface | null = null;

private indexingSessions: {
[key: number]: AssetIndexingSession;
Expand All @@ -77,6 +78,7 @@ export class AssetIndexer {
this._maxConcurrentConnections = maxConcurrentConnections;
this.$indexingSessionTable = $indexingSessionTable;
this.indexingSessions = {};

let reviewSessionId: number = 0;

for (const sessionModel of sessions) {
Expand All @@ -101,6 +103,8 @@ export class AssetIndexer {
}

if (this._currentIndexingSession) {
this._createProgressAnnouncer();
this._startProgressAnnouncer();
this.performIndexingStep();
}
}
Expand All @@ -109,6 +113,17 @@ export class AssetIndexer {
return this._currentIndexingSession;
}

/**
* Get progress info for the current session
*/
getCurrentSessionProgressInfo(): string | null {
if (this.currentIndexingSession !== null) {
const session = this.indexingSessions[this.currentIndexingSession];
return session.getProgressInfo();
}
return null;
}

/**
* Update indexing session store
* @param session
Expand Down Expand Up @@ -261,6 +276,8 @@ export class AssetIndexer {
return;
}

this._stopProgressAnnouncer();

this._currentlyReviewing = true;
this.pruneWaitingTasks(session.getSessionId());
let $confirmBody = $('<div></div>');
Expand Down Expand Up @@ -478,6 +495,34 @@ export class AssetIndexer {
.then((response) => this.processSuccessResponse(response))
.catch(({response}) => this.processFailureResponse(response))
.finally(() => cb());

// Begin making intermittent announcements
if (!this.intervalAnnouncer) {
this._createProgressAnnouncer();
this._startProgressAnnouncer();
}
}

private _createProgressAnnouncer(): void {
this.intervalAnnouncer = new Craft.IntervalManager({
onInterval: () => {
if (this.currentIndexingSession !== null) {
Craft.cp.announce(
Craft.t('app', 'Indexing assets: {progress}', {
progress: this.getCurrentSessionProgressInfo(),
})
);
}
},
});
}

private _stopProgressAnnouncer(): void {
this.intervalAnnouncer?.stop();
}

private _startProgressAnnouncer(): void {
this.intervalAnnouncer?.start();
}

public performIndexingStep(): void {
Expand Down Expand Up @@ -646,6 +691,10 @@ class AssetIndexingSession {
return this.indexingSessionData.listEmptyFolders;
}

public getProgressInfo(): string {
return `${this.indexingSessionData.processedEntries} / ${this.indexingSessionData.totalEntries}`;
}

/**
* Get the remaining entry count for this sessions.
*/
Expand Down Expand Up @@ -698,7 +747,10 @@ class AssetIndexingSession {
).css('position', 'relative');
const progressBar = new Craft.ProgressBar(
$progressCell.find('.progressContainer'),
false
false,
{
announceProgress: false,
}
);

progressBar.setItemCount(this.indexingSessionData.totalEntries);
Expand All @@ -710,9 +762,7 @@ class AssetIndexingSession {
$progressCell.data('progressBar', progressBar);
$progressCell
.find('.progressContainer')
.append(
`<div class="progressInfo">${this.indexingSessionData.processedEntries} / ${this.indexingSessionData.totalEntries}</div>`
);
.append(`<div class="progressInfo">${this.getProgressInfo()}</div>`);
$tr.append($progressCell);

$tr.append('<td>' + this.getSessionStatusMessage() + '</td>');
Expand Down
2 changes: 1 addition & 1 deletion src/web/assets/clearcaches/dist/ClearCachesUtility.js

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading