2013-07-31 2 views
-1

Я новичок в VB и .Net, и у меня есть задача, которую я не могу продолжить.доступ к динамически созданным элементам формы из потока в vb.net

  1. Начальная тема, когда screen1 Loads. Затем пользователь переходит к экрану2.
  2. На экране2 поток по-прежнему работает позади. когда пользователь выполняет действие (например, щелчок) на экране2, он вызывает поток для доступа к элементам на экране2
  3. Элементы на экране 2 динамически создаются и не предназначены для IDE.

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

Если мой вопрос слишком прост, пожалуйста, простите меня. Если это не ясно, сообщите мне, и я буду перефразировать его.

Примечание: Элемент, о котором я говорю, представляет собой в основном коробку с картинками внутри панели макета потока.

Заранее благодарен Вся помощь с нетерпением (грызущие гвозди сейчас) ждут и очень ценятся.

EDIT

  1. Допустим, поток называется ctThread был запущен в приборную панель экрана

    ctThread.start()

  2. Этот поток работает бесконечно, ожидая события триггера.

  3. Между тем пользователь перешел на экран под названием QuizScreen и на этом экране (форма) Мне нужно обновить некоторые динамически созданные элементы, имена которых я знаю.

  4. Итак, когда время подходит для ctThread, который ждет (Threadener Thread), он будет вызывать sub ниже.

Sub

public sub changeComputerStatus(ByVal node) 
    Dim flowpanel As FlowLayoutPanel = CType(QuizScreen.FlowLayoutPanel1.Controls("flow_" + node), FlowLayoutPanel) 
    Dim pictControl As PictureBox = CType(flowpanel.Controls("pict_" + node), PictureBox) 
    pictControl.Image = System.Drawing.Image.FromFile(Application.StartupPath & "\images\application-on.png") 
end sub 

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

Примечание: этот поток был запущен на экране под названием приборной панели, и пользователь теперь находится на другом экране QuizScreen.

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

+1

С какой частью этой задачи возникают проблемы? Вы пробовали это, и он работает неправильно? Или вы получаете сообщение об ошибке? Или вы просто просите общих советов о том, как вообще делать что-то подобное? –

+0

Привет, Стивен, спасибо за ответ. Я получаю сообщение об ошибке при попытке доступа к динамически создаваемому элементу. Ошибка: «Ссылка на объект не установлена ​​в экземпляр объекта». Если я попытаюсь получить доступ к одному и тому же элементу (динамическому элементу), используя событие в форме, я могу это сделать. Но при попытке одного и того же кода внутри потока. он почему-то не находит элемент. –

+0

Я - веб-разработчик (php/python), в основном пойманный в проекте vb.net. Разработка приложений для меня совершенно новая. –

ответ

1

Две вещи.

  1. Главное, что вы должны знать, это то, что вы не можете напрямую обращаться к свойствам элемента управления из фонового потока. Элементы управления могут управляться только из потока пользовательского интерфейса переднего плана. Чтобы получить доступ к элементам управления из фонового потока, вам необходимо использовать некоторую форму асинхронного программирования, например. создание делегатов a la .NET 1.x - 3.5 или используя новые ключевые слова Task<T> и async и await.

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

UPDATE:

Чтобы ответить на этот вопрос в комментарии OP в поле ниже: вы можете также Invoke метод на объекте UI. В принципе, вы говорите .NET, чтобы он запускал вызванный метод, и он запускается в потоке создания объекта пользовательского интерфейса (в данном случае - в потоке пользовательского интерфейса), который вы хотите. Это позволит вам (в зависимости от метода или свойства, вызванного) «обновить» элемент управления «из фона» —, это все ловкость рук; при вызове метода в объекте пользовательского интерфейса invkoked-метод запускается в потоке пользовательского интерфейса, возможно, используя данные, переданные в указанный метод из фоновой задачи.

Кроме того, проверьте документацию MSDN на BacgkroundWorker (это была введена в .NET 2.0 и заменяется на async и await ключевых слов наряду с Task<T> в .NET 4.5). Существует много документации, которая объясняет, как именно вы делаете. Это не сложно найти, выполнив быстрый поиск в MSDN или Bing (или в предпочитаемой вами поисковой системе).

+0

Дорогой @fourpastmidnight Его долгое время с тех пор, как я это увидел. Поскольку меня перевели на другую задачу, я оставил это. Теперь я вернусь к первоначальной задаче. Поэтому спасибо за ответ в первую очередь. Но в четыре недели я использовал делегатов, и он все еще не работает. –