Старый компьютер с оконным интерфейсом и современный ноутбук, вокруг светящиеся контуры фокуса, наушники и лупа: доступность бизнес-приложения для клавиатуры, скринридера и увеличения

Доступность legacy-приложений на WinForms, VB6 и Web Forms: аудит по WCAG 2.2 и ГОСТ и план исправлений

РубрикаМодернизацияУровеньСредний Чтение14 минОпубликовано ТегиДоступностьWCAGWinFormsWeb Forms

Старое приложение на WinForms, VB6 или Web Forms внезапно должно соответствовать ГОСТ Р 52872-2019 или WCAG: этого требует тендер, сотрудник со скринридером или клиент из ЕС. Разбираем, какие стандарты применимы к десктопу и вебу, как провести аудит за несколько дней, что исправляется свойствами и разметкой, а что придётся перепроектировать.

Главное. Для legacy-приложения рабочая цель — WCAG 2.2 уровня AA, на WCAG основаны и ГОСТ Р 52872-2019, и европейский EN 301 549. В WinForms и Web Forms большая часть проблем закрывается свойствами контролов и правкой разметки: имена для скринридера, порядок табуляции, системные цвета, связанные подписи, заголовки таблиц. В VB6 возможности ограничены клавиатурой и контрастом. Экраны на самописных и сторонних контролах без поддержки доступности перепроектируют и заменяют поэкранно.

Старое корпоративное приложение на WinForms, VB6 или ASP.NET Web Forms обычно писали под одного «среднего» пользователя: мышь, обычное зрение, стандартная тема Windows. Пока программа работала внутри компании, вопрос доступности не поднимался. Он возникает внезапно: в тендере появляется требование соответствия ГОСТ Р 52872-2019 или WCAG, в компанию приходит сотрудник со скринридером или европейский клиент ссылается на European Accessibility Act.

Хорошая новость: большую часть проблем в legacy-приложении можно исправить без переписывания, свойствами контролов и правкой разметки. Плохая: аудит почти всегда находит экраны, которые нужно перепроектировать, а не подкрасить. Здесь нужен взгляд дизайнера, и если своего в команде нет, разумно отдать UX-аудит и проектирование доступных интерфейсов внешней команде, а за разработчиками оставить исправления в коде и регрессионные проверки.

Ниже — какие стандарты применимы к десктопному и веб-приложению, как провести аудит своими силами за несколько дней, что конкретно исправлять в WinForms, VB6 и Web Forms и как встроить доступность в план модернизации. Общие вопросы обновления интерфейса разобраны в статье о редизайне WinForms- и VB6-приложения, здесь фокус только на доступности.

Что такое доступность приложения и кому она нужна?

Доступность (accessibility, a11y) — это возможность пользоваться программой людям с нарушениями зрения, слуха, моторики и когнитивных функций, а также всем, кто работает в неудобных условиях: без мыши, на мониторе с высоким масштабом, при ярком солнце. На практике это сводится к четырём проверяемым вещам: программу можно полностью пройти с клавиатуры, скринридер правильно называет каждый элемент, текст читается при высоком контрасте и увеличении, а важная информация не передаётся только цветом или звуком.

Кому это нужно в мире legacy-систем:

  • Госзаказчикам и подрядчикам. В технических заданиях на доработку систем для госорганов всё чаще встречается ссылка на ГОСТ Р 52872-2019 или уровень WCAG AA.
  • Экспортёрам ПО и сервисов в ЕС. С 28 июня 2025 года действует European Accessibility Act, требования детализирует стандарт EN 301 549, и он распространяется не только на сайты, но и на программное обеспечение.
  • Работодателям. Сотрудник с нарушением зрения не сможет вести учёт в программе, где половина полей для скринридера безымянна.
  • Всем пользователям. Полная клавиатурная навигация ускоряет работу операторов, которые вводят сотни документов в день, а корректный масштаб нужен любому, у кого 4K-монитор.

Какие стандарты применяются: WCAG 2.2, ГОСТ Р 52872-2019, EN 301 549, Section 508

Все действующие стандарты так или иначе опираются на WCAG — руководство W3C с тремя уровнями соответствия: A (минимум), AA (рабочая цель почти всех требований) и AAA (максимум, целиком почти недостижим). Различаются они редакцией WCAG и тем, как переносят веб-критерии на десктоп.

СтандартГде применяетсяОсноваДесктопные приложения
WCAG 2.2Международная рекомендация W3C, октябрь 2023 годаСама является основойНаписан для веба, но критерии применимы к любому интерфейсу
ГОСТ Р 52872-2019Россия, национальный стандартWCAG 2.1Да: в названии прямо указаны приложения для стационарных и мобильных устройств и иные интерфейсы
EN 301 549Евросоюз, гармонизированный стандарт к European Accessibility ActWCAG 2.1 AA плюс свои разделыДа, отдельная глава о программном обеспечении, не относящемся к вебу
Section 508США, федеральные закупки ИТWCAG 2.0 AAДа, критерии WCAG применяются и к не-веб ПО

Практический вывод: если требование сформулировано как «соответствие ГОСТ» или «WCAG AA», ориентируйтесь на WCAG 2.2 уровня AA — он включает требования 2.1 и добавляет несколько новых. Полный перечень критериев с пояснениями есть в официальном тексте WCAG 2.2. Для legacy-интерфейсов из новых критериев 2.2 чаще всего «стреляют» три:

  • 2.5.8 Размер цели. Кликабельный элемент не меньше 24×24 пикселей или с достаточным отступом от соседей. Мелкие иконки в тулбарах старых программ и крошечные чекбоксы в гридах обычно не проходят.
  • 2.4.11 Фокус не перекрыт. Элемент в фокусе не должен целиком прятаться под закреплённой панелью, всплывающим окном или шапкой страницы.
  • 3.3.7 Повторный ввод. Данные, которые пользователь уже вводил в этом же процессе, не надо требовать заново — типичная боль многошаговых мастеров в учётных системах.

Как провести аудит доступности legacy-приложения своими силами?

Полный экспертный аудит занимает недели, но первичную картину команда получает за 2–5 дней. Автоматические инструменты находят только часть проблем, поэтому аудит всегда комбинированный: сканер плюс ручные сценарии.

  1. Выберите 5–10 ключевых сценариев. Не экраны, а задачи: «создать счёт», «найти клиента и изменить контакт», «выгрузить отчёт за месяц». Аудит по сценариям сразу показывает, где пользователь застрянет.
  2. Пройдите каждый сценарий только с клавиатуры. Отключите мышь. Фиксируйте, куда не попадает фокус, где его не видно, где порядок табуляции прыгает по форме и где нельзя закрыть диалог.
  3. Пройдите сценарии со скринридером. Встроенный «Экранный диктор» Windows включается сочетанием Win + Ctrl + Enter, бесплатный NVDA ставится за пять минут. Слушайте, называет ли он поля, кнопки и состояние флажков.
  4. Проверьте отображение. Включите высококонтрастную тему Windows и масштаб 150–200 %. Ищите обрезанный текст, исчезнувшие рамки, жёстко заданные цвета, которые не меняются вместе с темой.
  5. Запустите автоматическую проверку. Для десктопа — Accessibility Insights for Windows (режим FastPass) или Inspect из Windows SDK, для веба — Accessibility Insights for Web, axe DevTools или проверка доступности в Lighthouse.
  6. Сведите находки в реестр. По каждой проблеме — сценарий, экран, критерий WCAG, серьёзность (блокирует задачу или мешает) и оценка: исправляется свойством, правкой разметки или требует перепроектирования экрана.

Последняя колонка реестра определяет бюджет. Свойства и разметку правят разработчики за дни, а экраны, которые невозможно пройти без мыши или где смысл передаётся только цветом, нужно проектировать заново. Такой реестр удобно вести рядом с техническим аудитом кода — см. чек-лист аудита legacy-кодовой базы на VB.NET: часть проблем доступности упирается в те же самописные контролы и сторонние компоненты.

Типичные проблемы доступности в WinForms, VB6 и Web Forms

У каждой технологии свой набор «родовых травм». Таблица поможет быстро понять, что искать в первую очередь.

ПроблемаWinFormsVB6ASP.NET Web Forms
Поля без имени для скринридераНе заполнен AccessibleName, подпись не стоит перед полем в порядке табуляцииLabel — безоконный контрол, скринридер его не видит и часто объявляет поле без имениasp:Label без AssociatedControlID рендерится в span, а не в label
Клавиатурная навигацияХаотичный TabIndex, контролы с TabStop = False, действия только по двойному щелчкуТо же плюс действия в событиях MouseDown и Click на картинкахСсылки-кнопки на JavaScript без href, ловушки фокуса в модальных окнах
Цвет и контрастЖёстко заданные BackColor и ForeColor, игнорирование высококонтрастной темыТо же, плюс фоновые картинки формСерый текст на сером, ошибки валидации только красным цветом
Самописные и сторонние контролыOwner-draw контролы без AccessibleObject невидимы для вспомогательных технологийOCX-гриды и календари почти не поддерживают MSAAСтарые версии сторонних наборов контролов с табличной вёрсткой
Динамические измененияСтатус в строке состояния не озвучиваетсяСообщения только звуком BeepОбновления UpdatePanel не объявляются скринридеру
МасштабОбрезанный текст при 150–200 %, если режим DPI не настроенПриложение не DPI-aware, Windows растягивает его картинкойФиксированная ширина в пикселях, горизонтальная прокрутка

Как исправить доступность в WinForms на VB.NET?

WinForms даёт для доступности почти всё необходимое: стандартные контролы поддерживают Microsoft UI Automation, а недостающее дописывается свойствами. Список свойств и их назначение есть в документации Microsoft по свойствам доступности контролов. Порядок работ обычно такой.

  1. Имена и описания. Для каждого поля, кнопки-иконки и картинки заполните AccessibleName, при необходимости AccessibleDescription. Подпись Label ставьте непосредственно перед полем в порядке табуляции.
  2. Клавиши доступа. Символ & в тексте подписи и кнопки задаёт сочетание Alt + буква; у Label включите UseMnemonic, чтобы фокус переходил к следующему полю.
  3. Порядок табуляции. В дизайнере Visual Studio включите режим «Порядок перехода по Tab» и выстройте его по смыслу формы, сверху вниз и слева направо.
  4. Системные цвета. Не задавайте цвета жёстко либо переключайтесь на SystemColors, когда включена высококонтрастная тема.
  5. Самописные контролы. Для owner-draw контрола переопределите CreateAccessibilityInstance и верните наследника AccessibleObject с корректными именем, ролью и состоянием.

Минимальный пример: имена для полей и реакция на смену контрастной темы без перезапуска программы.

frmCustomer.vbVB.NET
Imports Microsoft.Win32

Public Class frmCustomer
    Public Sub New()
        InitializeComponent()
        ' Имена для скринридера: кнопка-иконка и поле без видимой подписи
        btnFind.AccessibleName = "Найти клиента"
        txtInn.AccessibleName = "ИНН клиента"
        txtInn.AccessibleDescription = "10 или 12 цифр"
        lblName.Text = "&Наименование"   ' Alt+Н переводит фокус в поле
        lblName.UseMnemonic = True
        ApplyColors()
        AddHandler SystemEvents.UserPreferenceChanged, AddressOf OnPrefsChanged
    End Sub

    Private Sub ApplyColors()
        If SystemInformation.HighContrast Then
            pnlHeader.BackColor = SystemColors.Window
            pnlHeader.ForeColor = SystemColors.WindowText
        Else
            pnlHeader.BackColor = Color.FromArgb(0, 64, 128)
            pnlHeader.ForeColor = Color.White
        End If
    End Sub

    Private Sub OnPrefsChanged(sender As Object, e As UserPreferenceChangedEventArgs)
        ApplyColors()
    End Sub

    Protected Overrides Sub OnFormClosed(e As FormClosedEventArgs)
        ' Системное событие статическое: без отписки форма не освободится
        RemoveHandler SystemEvents.UserPreferenceChanged, AddressOf OnPrefsChanged
        MyBase.OnFormClosed(e)
    End Sub
End Class

Отдельно о версии платформы. Если приложение остаётся на .NET Framework, улучшения доступности WinForms из версий 4.7.1, 4.7.2 и 4.8 (подсказки при навигации с клавиатуры, LiveRegion, события уведомлений, исправления в DataGridView и ToolStrip) включаются переключателями в конфигурации. Без них даже правильно заполненные свойства работают по старым правилам.

App.configXML
<configuration>
  <runtime>
    <AppContextSwitchOverrides value="Switch.UseLegacyAccessibilityFeatures=false;Switch.UseLegacyAccessibilityFeatures.2=false;Switch.UseLegacyAccessibilityFeatures.3=false;Switch.System.Windows.Forms.UseLegacyToolTipDisplay=false" />
  </runtime>
</configuration>

Подробности по каждому переключателю — в обзоре нововведений доступности в .NET Framework. В WinForms на современном .NET эти улучшения включены всегда, и это ещё один аргумент за переход; как его пройти, описано в статье о переносе WinForms на VB.NET на новый .NET.

Что можно сделать с доступностью VB6-приложения?

Здесь честный ответ скромнее. VB6 опирается на старый интерфейс Microsoft Active Accessibility, и возможности влиять на то, что «видит» скринридер, у него ограничены. Стандартные контролы вроде TextBox и CommandButton — это обычные окна Windows, их вспомогательные технологии понимают. Безоконные Label, Image, Shape и Line для них не существуют, а большинство OCX-гридов и календарей поддерживают MSAA плохо или никак.

Что реально сделать без переписывания:

  • выстроить TabIndex по смыслу формы и убрать действия, доступные только мышью;
  • добавить клавиши доступа через & в подписях и пунктах меню;
  • заменить важные картинки-кнопки на CommandButton с текстом;
  • убрать жёсткие цвета там, где они не несут смысла, и продублировать цветовые статусы текстом;
  • заменить сообщения звуком на видимые сообщения в окне или строке состояния;
  • проверить работу при масштабе 150 % с манифестом DPI-awareness или без него — что для конкретной программы меньшее зло.

Если по требованиям нужен уровень AA, а ключевые экраны построены на OCX-гридах, доработками VB6 его не достичь. Тогда доступность становится ещё одним аргументом в решении о миграции — вместе с поддержкой платформы и безопасностью.

Как исправить доступность в ASP.NET Web Forms?

Web Forms генерирует HTML, а значит, к нему применимы все веб-инструменты проверки. Большинство проблем решается правкой разметки страниц и шаблонов, без изменения логики.

Orders.aspxASPX
<%-- Подпись связана с полем: рендерится <label for="..."> --%>
<asp:Label runat="server" AssociatedControlID="txtCustomer" Text="Клиент" />
<asp:TextBox runat="server" ID="txtCustomer" aria-describedby="custHint" />
<span id="custHint">Название или ИНН</span>

<%-- Таблица с настоящими заголовками столбцов (th scope="col") --%>
<asp:GridView runat="server" ID="gvOrders" UseAccessibleHeader="true"
    Caption="Заказы за выбранный период" OnPreRender="gvOrders_PreRender" />

<%-- Результат частичного обновления объявляется скринридеру --%>
<div aria-live="polite">
  <asp:UpdatePanel runat="server" ID="upTotals">...</asp:UpdatePanel>
</div>

Чтобы заголовок GridView попал в thead, в обработчике PreRender выставьте gvOrders.HeaderRow.TableSection = TableRowSection.TableHeader. Ещё несколько пунктов, которые закрывают большую часть находок сканера:

  • Режим рендеринга. Атрибут controlRenderingCompatibilityVersion="4.0" в web.config убирает часть устаревшей разметки, а RenderingMode="List" у asp:Menu выводит меню списком вместо таблиц.
  • Альтернативный текст. У asp:Image и asp:ImageButton заполните AlternateText; декоративным картинкам — пустой, чтобы скринридер их пропускал.
  • Ошибки валидации. Текст ошибки должен быть рядом с полем и связан с ним через aria-describedby, а не только подсвечен красным; ValidationSummary выводите в начале формы.
  • Язык и заголовки. Атрибут lang у html, уникальный title на каждой странице и логичная иерархия заголовков в мастер-странице.
  • Кнопки и ссылки. LinkButton, работающий через __doPostBack, с клавиатуры доступен, но для скринридера это ссылка; там, где действие меняет данные, используйте asp:Button.

Если Web Forms всё равно предстоит переносить, доступность лучше заложить в требования к новому интерфейсу сразу: исправлять её после переезда дороже. Порядок миграции разобран в пошаговом плане перехода с Web Forms на ASP.NET Core и Blazor.

Исправлять старое приложение или закладывать доступность в новое?

Решение зависит от того, сколько находок закрывается свойствами и разметкой, а сколько требует перепроектирования экранов.

СитуацияРекомендация
WinForms или Web Forms, проблемы в основном в именах, порядке табуляции и контрастеИсправлять в текущем приложении: обычно это недели работы разработчика
Ключевые сценарии завязаны на самописные или сторонние контролы без поддержки доступностиЗаменить контролы поэкранно, начиная с самых используемых сценариев
VB6 с OCX-гридами и требование уровня AAЗакладывать доступность в новое приложение, в старом — только клавиатура и контраст
Миграция уже запланированаВнести WCAG 2.2 AA в требования к новому интерфейсу и проверять каждый модуль при приёмке

Во всех случаях полезно, чтобы доступность проверял не только разработчик. Дизайнер видит то, что не ловит сканер: перегруженные формы, неочевидный порядок действий, статусы, понятные только по цвету. Именно эти находки чаще всего и требуют перепроектирования, а не правки свойств.

Чек-лист доступности перед релизом

  • каждый ключевой сценарий проходится только с клавиатуры, фокус всегда виден;
  • скринридер называет все поля, кнопки, флажки и их состояние;
  • контраст текста не ниже 4,5:1, крупного текста и элементов интерфейса — не ниже 3:1;
  • в высококонтрастной теме Windows и при масштабе 200 % ничего не исчезает и не обрезается;
  • ошибки ввода описаны текстом рядом с полем, а не только цветом;
  • кликабельные элементы не меньше 24×24 пикселей или разнесены друг от друга;
  • важные события не передаются только звуком;
  • реестр находок с критериями WCAG обновлён, нерешённые пункты внесены в план.

Как это делают сегодня

Типичный подход 2026 года: целевой уровень — WCAG 2.2 AA, аудит по 5–10 ключевым сценариям с клавиатурой, «Экранным диктором» или NVDA и Accessibility Insights, реестр находок с критериями WCAG. Быстрые исправления — свойствами WinForms и разметкой Web Forms в текущем приложении, а экраны на недоступных контролах перепроектируются и заменяются поэкранно или закладываются в требования к новому интерфейсу при миграции.

Вопросы и ответы

Обязательно ли соблюдать ГОСТ Р 52872-2019 для внутреннего корпоративного приложения?

Национальный стандарт сам по себе применяется добровольно. Обязательным его делают требования заказчика: техническое задание госоргана, условия тендера или договор. Для внутреннего приложения это решение компании, но если в ней работают сотрудники с нарушениями зрения или моторики, базовые требования стоит выполнить в любом случае.

Применим ли WCAG к десктопным приложениям, а не только к сайтам?

Да. WCAG написан для веба, но его критерии описывают интерфейс в целом: клавиатуру, имена элементов, контраст, масштаб. ГОСТ Р 52872-2019, EN 301 549 и Section 508 прямо распространяют эти требования на приложения для стационарных устройств, включая десктопные программы.

Какими инструментами проверить доступность WinForms-приложения?

Accessibility Insights for Windows в режиме FastPass и утилитой Inspect из Windows SDK, плюс ручной проход ключевых сценариев с клавиатуры и со скринридером: встроенным «Экранным диктором» или бесплатным NVDA. Автоматические проверки находят только часть проблем, поэтому ручные сценарии обязательны.

Можно ли сделать VB6-приложение полностью доступным?

Как правило, нет. VB6 опирается на старый Microsoft Active Accessibility, безоконные контролы вроде Label для скринридеров невидимы, а OCX-гриды поддерживают его слабо. Реально улучшить клавиатурную навигацию, клавиши доступа, контраст и сообщения. Для уровня AA ключевые экраны придётся переносить на современную платформу.

Сколько времени занимает аудит и исправление доступности?

Первичный аудит по 5–10 ключевым сценариям занимает 2–5 дней. Исправления свойствами и разметкой в WinForms и Web Forms обычно укладываются в несколько недель. Срок сильно растёт, если ключевые сценарии построены на самописных или сторонних контролах: их приходится заменять или перепроектировать экраны.

Что изменилось в WCAG 2.2 по сравнению с WCAG 2.1?

Добавлено девять критериев и снят устаревший критерий о синтаксическом разборе разметки. Для старых интерфейсов важнее всего минимальный размер кликабельной цели 24×24 пикселя, требование не перекрывать элемент в фокусе и запрет заставлять пользователя повторно вводить уже введённые данные в том же процессе.

Читайте также