Вставка текстовых полей Winforms ненадежна?

У нас есть стандартное текстовое поле в приложении Winforms, которое отвечает на вставить (как контекстное меню, так и CTRL + V) обычным способом (то есть, пасты) в нашей среде разработки.

На одном сайте клиента паста в основном полностью игнорируется (ведет себя так, как будто в буфере обмена ничего нет). Мы протестировали его как с однострочными, так и с многострочными версиями TextBox, и мы создали автономное приложение только с несколькими текстовыми блоками, и на этом одном клиентском сайте проблема сохраняется. Вставка в основном не работает.

В дальнейшем тестировании мы обнаруживаем, что просто запрашиваем содержимое буфера обмена в тестовом winforms приложении, оно возвращается как пустая строка. Двойная проверка с помощью Блокнота мы находим там определенно что-то в буфере обмена.

Здесь мы проверили:

  • В тестах мы гарантируем, что источник буфера обмена находится в Notepad или действительно внутри самого текстового поля, поэтому мы знаем, что это не что-то странное из HTML/Word
  • Мы всегда можем вводить текст в текстовое поле, так что это не так, как если бы текстовое поле не позволяло изменять
  • Количество текста Мы пробовали его с большим и небольшим количеством текста в буфере обмена, не имеет значения
  • Правая кличка по сравнению с CTRL + V: они либо работают, либо не работают, поэтому все те сообщения, которые находятся на пути к исправлению того или другого, нам не помогают
  • Поиск шаблонов Я думаю, что если он не сработает, когда он не будет работать снова, пока приложение не будет перезапущено, но я не уверен
  • Когда проблема с пастой возникает, вырезать и копировать не влияют и продолжают работать
  • Функция вставки клиентских машин определенно работает с другими приложениями, "Блокнотом", "Офис" и т.д.

Помните, что одно и то же скомпилированное приложение всегда успешно вставляется в наши dev-машины и иногда успешно вставляется на клиентские машины! Это то, что делает его настолько загадочным.

Во всех случаях мы проверили, что есть что-то в буфере обмена, вставляя в блокнот вместе с нашим приложением.

Кто-нибудь еще видел это и/или может предложить объяснение?

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

Класс Clipboard может использоваться только в потоках, установленных в одну цепочку (STA). Чтобы использовать этот класс, убедитесь, что ваш основной метод отмечен атрибутом STAThreadAttribute.

Итак, в проекте Winforms без основного потока - просто форма запуска, где вы помещаете этот атрибут? И почему нам это не нужно на dev-машинах? И почему нам никогда не приходилось использовать его в любом из бесчисленных других приложений Winforms, которые мы создали?

Ответ 1

У меня есть фантастический брандмауэр, который также способен блокировать приложения от просмотра данных в буфере обмена на основе каждого приложения.

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

У клиента может быть что-то подобное установленное, с помощью Notepad, разрешенного в правилах.

Ответ 2

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

Некоторые предпосылки. Элемент управления TextBox в приложении Winforms - это тот же самый компонент, который использует Блокнот, чтобы вы могли редактировать текст. Основным компонентом является элемент управления Edit, он был стандартным компонентом в Windows с версии 1.0. Обратите внимание, как контекстное меню, которое вы получаете, когда вы щелкните правой кнопкой мыши TextBox и Блокнот, идентичен. В этом меню нет различия между командой Paste и нажатием Ctrl + V, они оба вызывают сообщение WM_PASTE для отправки в собственный редактор Edit, Что внутренне связано с буфером обмена, этот код полностью находится за пределами вашей досягаемости и работает идентично в "Блокноте", как в вашей программе.

Проблема с квартирной квартирой маловероятна, у клиента также должна быть проблема с командой Копировать, и вы должны были заметить это раньше. В С# он устанавливается атрибутом [STAThread] в методе Main(), он генерируется компилятором в VB.NET.

Существует множество утилит, которые могут привести к неправильному использованию буфера обмена. Первыми и прежде всего являются буфера обмена, программы, которые подключаются к уведомлениям буфера обмена. AddClipboardFormatListener() - базовая функция winapi. Они, как правило, делают что-то вроде "улучшения" буфера обмена, позволяя ему хранить более одного элемента или давать другое представление о том, что находится в буфере обмена. Они имеют тенденцию дестабилизировать машину, не передавая уведомления следующему зрителю должным образом или нарушая цепочку зрителей, не отменив их правильно. Такая сломанная цепочка сама по себе является причиной того, что "работает нормально в" Блокноте ", а не в моей".

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

Ответ 3

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

Что вы можете сделать, так это узнать, что любое другое приложение на клиентской машине имеет доступ к буферу. Вы можете проверить диспетчер задач или запущенный процесс. Это может помочь вам.

Я столкнулся с аналогичной проблемой с приложением Snagit. Это приложение мешало моей программе устанавливать текст буфера обмена для их собственного использования.