412 000 произведений, 108 200 авторов.

Электронная библиотека книг » Иво Салмре » Программирование мобильных устройств на платформе .NET Compact Framework » Текст книги (страница 62)
Программирование мобильных устройств на платформе .NET Compact Framework
  • Текст добавлен: 18 июля 2025, 02:31

Текст книги "Программирование мобильных устройств на платформе .NET Compact Framework"


Автор книги: Иво Салмре



сообщить о нарушении

Текущая страница: 62 (всего у книги 69 страниц)

Сетевые телеконференции

Для .NET Compact Framework существует много активных форумов, действующих по принципу "спрашивайте – ответим". Доступ к ним можно получить либо с помощью программы для работы с группами новостей, либо через Web-сайт http://msdn.microsoft.com/newsgroups/.

Можно указать еще несколько форумов, посвященных данной тематике:

■ microsoft.public.dotnet.framework.compactframework

■ microsoft.public.pocketpc.developer

■ microsoft.public.pocketpc.developer.networking

■ microsoft.public.smartphone.developer

Как и в случае любого форума или обсуждения, вопросы и ответы, которые вы встретите там, могут быть как интересными, так и не представляющими никакого интереса. Форумы – великолепное место для поиска подсказок и идей, которые помогут вам преодолеть проблемы, тормозящие дальнейшую работу, но там вы найдете исключительно информацию, которая предоставляется "без обещания компенсации возможного ущерба и без гарантий достоверности".

Общие вопросы разработки мобильных приложений

Самые последние замечательные новости о .NET Compact Framework и других технологиях разработки мобильного программного обеспечения, используемых компанией Microsoft, появляются на следующих Web-сайтах:

http://msdn.microsoft.com/mobility/

http://msdn.microsoft.com/mobility/prodtechinfo/devtools/netcf/faq/default.aspx

Для разработки приложений Microsoft Smartphone с использованием Visual Studio Net 2003 вам потребуется установить пакет SDK для Windows Mobile 2003-based Smartphones, доступный для загрузки по следующему адресу:

http://msdn.microsoft.com/mobility/windowsmobile/downloads/

Для просмотра постоянно обновляемого документа Wiki, содержащего ответы на наиболее часто задаваемые вопросы, посетите следующий сайт:

http://wiki.opennetcf.org/ow.asp?CompactFrameworkFAQ

Особенности взаимодействия с собственным кодом

Вызов собственного кода (native code) из VB.NET или C# не представляет особых сложностей, но вам следует знать о некоторых частных правилах и устоявшихся приемах. Лучше всего изучать это на примерах.

■ Основы работы с собственными кодами в среде .NET Compact Framework

An Introduction to P/Invoke and Marshalling on the Microsoft .NET Compact Framework

Авторы: Jon Box, Dan Fox; Quilogy

http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnnetcomp/html/netcfintrointerp.asp

■ Тонкости работы с собственными кодами в среде .NET Compact Framework

Advanced P/Invoke on the Microsoft .NET Compact Framework

Авторы: Jon Box, Dan Fox; Quilogy

http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnnetcomp/html/netcfadvinterop.asp

■ Передача асинхронных сообщений из собственного кода в управляемый код при помощи .NET Compact Framework

Asynchronous Callbacks from Native Win32 Code Автор: Maarten Struys; PTS Software

http://msdn.microsoft.corn/library/default.asp?url=/library/en-us/dnnetcomp/html/AsynchCallbacks.asp

Работа с операторами мобильных сетей

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

■ Сокращенная ссылка, которая переадресует вас на более подробное содержимое, указанное далее:

Сокращенный URL-адрес Mobile2Market

http://www.mobile2market.com

■ Сертификация от Mobile2Market и маркетинговая программа

http://msdn.microsoft.com/mobility/windowsmobile/partners/mobile2market/default.aspx

■ Список операторов мобильных сетей, рекомендации по отдельным операторам и контактная информация

http://msdn.microsoft.com/mobility/windowsmobile/partners/mobile2market/smartphoneapps/default.aspx

Развертывание и установка

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

Инструкции по развертыванию и установке приложений .NET Compact Framework хорошо изложены в документации продукту MSDN, которая поставляется вместе с Visual Studio .NET. С неплохим примером развертывания приложения на устройствах вы можете ознакомиться в оперативной справочной документации, последовательно выбрав следующие разделы: Visual Studio .NET→Developing with Visual Studio .NET→Designing Distributed Applications→Developing for Devices→Samples and Walkthroughs→Smart Device Walkthroughs→Generating Custom CAB Files for Device Projects (Visual Studio .NET→Разработка с помощью Visual Studio .NET→Проектирование распределенных приложений→Разработка для устройств→Примеры и анализ→Анализ интеллектуальных устройств→Генерация пользовательских CAB-файлов для проектов, ориентированных на устройства).

Пошаговый разбор создания инсталляционного приложения для Pocket PC

Developing and Deploying Pocket PC Setup Applications

Автор: Ralph Arvesen; Vertigo Software, Inc.

http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnnetcomp/html/netcfdeployment.asp

Подробное описание динамической установки .NET Compact Framework на устройствах на тот случай, если это вам когда-либо понадобится

Creating an MSI Package That Detects and Updates the .NET Compact Framework

Автор: Stan Adermann; Microsoft Corporation

http://msdn.microsoft.com/library/default.asp?url=/library/ en-us/dnnetcomp/html/netcfdepl.asp

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

http://www.installshield.com

Примечание. Я указал здесь InstallShield, учитывая широкую известность и популярность этого средства установки. Если вы используете другие инсталляционные программы, то, безусловно, вам стоит посетить соответствующие Web-сайты, чтобы узнать, поддержку каких мобильных устройств они предлагают.

Оптимизация производительности

В указанной ниже статье вы найдете превосходные советы и описания эффективных практических методов настройки производительности приложений, а также подробное изложение методик получения данных профилирования приложений с помощью .NET Compact Framework, которые вы сможете применить для анализа производительности приложений. Эта прекрасная статья поможет вам сохранять "дух производительности" в процессе разработки мобильных приложений.

Developing Well-Performing .NET Compact Framework Applications

Авторы: Dan Fox, Jon Box; Quilogy

http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnnetcomp/html/netcfperf.asp

ПРИЛОЖЕНИЕ Б
Примеры программ на языке Visual Basic .NET

Почему именно VB.NET и С#?

Споры между разработчиками программ на языках VB.NET и С# никогда не прекращается, и это неплохо! Представителям обоих лагерей есть чему поучиться друг у друга. Что касается меня, то, поработав с обоими языками в течение многих лет, и в частности, имея опыт работы в составе группы разработчиков на Visual Basic, могу поделиться следующими наблюдениями. Каждый из этих языков может быть использован для решения практически любой задачи программирования – все дело в акцентах. Я обнаружил, что Visual Basic .NET с его традиционным для Visual Basic акцентом на продуктивности программирования великолепно приспособлен для разработки конечных приложений.

С другой стороны, преимуществом С# является его строгость, что делает его более приспособленным для проектирования каркасов приложений. По всей видимости, оба языка в равной степени хорошо приспособлены для проектирования повторно используемых компонент, которые занимают промежуточное положение между независимыми приложениями и обширными библиотеками программ. Кроме того, оба языка предлагают опции, отличные от используемых по умолчанию, которые сближают подходы, основанные на использовании каждого из них. Так, в Visual Basic .NET имеется директива Option Strict On, которую я настоятельно рекомендую помещать в начале любого модуля, который вы пишете, в качестве меры, позволяющей вылавливать многие виды распространенных синтаксических и логических ошибок. Помимо этого, оба языка учатся друг у друга, заимствуя каждый с выходом очередной новой версии нечто полезное, что впервые было предложено в другом языке; это порождает хороший дух соперничества между этими двумя языками.

В Visual Basic .NET мне особенно нравятся возможности, относящиеся к обработке событий; ключевые слова AddHandler и Handles (используемые в приведенных ниже кодах) гораздо более элегантны и декларативны, чем их текущие варианты, используемые в С#. Поскольку удобнее всего работать с примерами, которые написаны на наиболее привычном языке, я поместил в данное приложение VB.NET-версии почти всех листингов, приведенных в основной части книги.

Не включены в приложение только листинги примеров, которые, либо в силу малости их размера, либо в силу того, что они должны быть одинаково хорошо понятны разработчикам, принадлежащим любому лагерю, автор счел слишком тривиальными, чтобы тратить время на их трансляцию. Везде, где только возможно, соблюдается практика записи кода, принятая в Visual Basic, в том смысле, что приведенный ниже код является не результатом прямой трансляции кода, написанного на языке C#, а скорее его "VB-версией"; в то же время, оба вида примеров функционально эквивалентны друг другу, и тем, для кого представляет интерес сравнение возможностей языков Visual Basic и C#, чтобы решить для себя, какой из них выбрать, сделать это не составит труда. Удачного программирования!

Примеры к главе 5 (конечные автоматы)
Листинг 5.1. Простой код конечного автомата для игры с множественным выбором

Option Explicit On

Class MyStateMachineClass

Private Enum GameState

 StartScreen

 AskQuestion

 CongratulateUser

 ScoldUser

End Enum

Private m_CurrentGameStateAs GameState

'–

'Конечный автомат, воздействующий на пользовательский интерфейс и

'управляющий переходами приложения в другие состояния в соответствии с

'текущим режимом работы пользователя

'–

Private Sub StateChangeForGame(ByVal newGameUIState _

 As GameState)

 'Определить, в какое состояние переходит приложение

 Select Case (newGameUIState)

 Case GameState.StartScreen

  'Если переход в данное состояние осуществляется из состояния,

  'для которого это запрещено, возбудить исключение

  If ((m_CurrentGameState <> GameState.CongratulateUser) _

   AndAlso (m_CurrentGameState <> GameState.ScoldUser)) Then

   Throw New System.Exception("Запрещённое изменение состояния!")

  End If

  'ЧТО СДЕЛАТЬ: Поместите сюда код, выполняющий следующие операции:

  ' 1. Скрытие (Hide), отображение (Show) и перемещение (Move)

  ' элементов управления пользовательского интерфейса

  ' 2. Настройка переменных/состояний игры, соответствующих

  ' данному режиму работы

  ' SetUpGameStateForStartScreen()

 Case GameState.AskQuestion

  'Если переход в данное состояние осуществляется из состояния,

  'для которого это запрещено, возбудить исключение

  If ((m_CurrentGameState <> GameState.StartScreen) _

   AndAlso (m_CurrentGameState <> GameState.CongratulateUser) _

   AndAlso (m_CurrentGameState <> GameState.ScoldUser)) Then

   Throw New System.Exception("Запрещённое изменение состояния!")

  End If

  'ЧТО СДЕЛАТЬ: Поместите сюда код, выполняющий следующие операции:

  ' 1. Скрытие (Hide), отображение (Show) и перемещение (Move)

  ' элементов управления пользовательского интерфейса

  ' 2. Настройка переменных/состояний игры, соответствующих

  ' данному режиму работы

  '

  ' SetUpGameStateForAskQuestion()

 Case GameState.CongratulateUser

  'Если переход в данное состояние осуществляется из состояния,

  'для которого это запрещено, возбудить исключение

  If (m_CurrentGameState <> GameState.AskQuestion) Then

   Throw New System.Exception("Запрещённое изменение состояния!")

  End If

  'ЧТО СДЕЛАТЬ: Поместите сюда код, выполняющий следующие операции:

  ' 1. Скрытие (Hide), отображение (Show) и перемещение (Move)

  ' элементов управления пользовательского интерфейса

  ' 2. Настройка переменных/состояний игры, соответствующих

  ' данному режиму работы

  '

  ' SetUpGameStateForCongratulateUser()

 Case GameState.ScoldUser

  'Если переход в данное состояние осуществляется из состояния,

  'для которого это запрещено, возбудить исключение

  If (m_CurrentGameState <> GameState.AskQuestion) Then

   Throw New System.Exception("Запрещённое изменение состояния!")

  End If

  'ЧТО СДЕЛАТЬ: Поместите сюда код, выполняющий следующие операции:

  ' 1. Скрытие (Hide), отображение (Show) и перемещение (Move)

  ' элементов управления пользовательского интерфейса

  ' 2. Настройка переменных/состояний игры, соответствующих

  ' данному режиму работы

  ' SetUpGameStateForScoldUser()

 Case Else

  Throw New System.Exception("Наизвестное состояние!")

 End Select

 'Сохранить запрошенное новое состояние в качестве текущего

 m_CurrentGameState = newGameUIState

End Sub

End Class

Листинг 5.2. Неявное изменение состояния приложения (неудачный подход)

'Код, выполняющийся при загрузке формы

Private Sub Form1_Load(ByVal senderAs System.Object,ByVal _

 e As System.EventArgs) Handles MyBase.Load

 TextBox1.Visible = True

 ListBox1.Visible = False

End Sub

'Данные

Private m_someImportantInfoAs String

'Пользователь щелкнул на кнопке и хочет перейти к выполнению

'следующего шага данного приложения. Скрыть текстовое окно и отобразить

'окно списка в отведенном для этого месте.

Private Sub Button1_Click(ByVal senderAs System.Object,ByVal _

 e As System.EventArgs) Handles Button1.Click

 m_someImportantInfo = TextBox1.Text

 TextBox1.Visible = False

 ListBox1.Visible =True

End Sub

Листинг 5.3. Явное изменение состояния приложения (удачный подход)

Private m_someImportantInfo As String

'Определить состояния, в которых может находиться приложение

Enum MyStates

 step1

 step2

End Enum

'–

'Главная функция, которая

'вызывается всякий раз, когда возникает необходимость

'в изменении состояния приложения

'–

Sub ChangeApplicationState(ByVal newStateAs MyStates)

 Select Case newState

 Case MyStates.step1

  TextBox1.Visible = True

  ListBox1.Visible = False

 Case MyStates.step2

  m_someImportantInfo = TextBox1.Text

  TextBox1.Visible = False

  ListBox1.Visible = True

 End Select

End Sub

'–

'Пользователь щелкнул на кнопке и хочет перейти к выполнению

'следующего шага данного приложения. Скрыть текстовое окно и отобразить

'окно списка в отведенном для этого месте.

'–

Private Sub button1_Click(ByVal sender As Object, ByVal e As System.EventArgs)

 'Вызвать главную функцию для изменения состояния

 ChangeApplicationState(MyStates.step2)

End Sub

'–

'Код, выполняющийся при загрузке формы

'–

Private Sub Forml_Load(ByVal sender As Object, _

 ByVal eAs System.EventArgs)

 'Вызвать главную функцию для изменения состояния

 ChangeApplicationState(MyStates.step1)

End Sub

Листинг 5.4. Код программы нахождения простых чисел, предназначенный для выполнения фоновым потоком

Option Strict On

Imports System

Public Class FindNextPrimeNumber

'Определить возможные состояния

Public Enum ProcessingState

 notYetStarted

 waitingToStartAsync

 lookingForPrime

 foundPrime

 requestAbort

 aborted

End Enum

Private m_startTickCount As Integer

Private m_endTickCount As Integer

Private m_startPoint As Long

Private m_NextHighestPrime As Long

Private m_processingState As ProcessingState

'–

'Простейший конечный автомат

'–

Public Sub setProcessingState(ByVal nextState As ProcessingState)

 '–

 'Простейший защитный код, гарантирующий

 'невозможность перехода в другое состояние в случае успешного

 'завершения задачи или успешной отмены ее выполнения

 '–

 Dim currentState As ProcessingState

 currentState = getProcessingState()

 If ((currentState = ProcessingState.aborted) _

  OrElse (currentState = ProcessingState.foundPrime)) Then

  Return

 End If

 'Безопасное параллельное выполнение потоков

 SyncLock (Me)

  'Разрешить изменение состояния

  m_processingState = nextState

 End SyncLock

End Sub

Public Function getProcessingState() As ProcessingState

 Dim currentState As ProcessingState

 'Безопасное параллельное выполнение потоков

 SyncLock (Me)

  currentState = m_processingState

 End SyncLock

 Return currentState

End Function

Public Function getTickCountDelta() As Integer

 If (getProcessingState() = _

  ProcessingState.lookingForPrime) Then

  Throw New Exception( _

   "Продолжается поиск простого числа! Окончательное время еще не вычислено")

 End If

 Return m_endTickCount – m_startTickCount

End Function

'–

'Возвращает простое число

'–

Public Function getPrime() As Long

 If (getProcessingState() <> ProcessingState.foundPrime) Then

  Throw New Exception("Простое число еще не найдено!")

 End If

 Return m_NextHighestPrime

End Function

'Конструктор класса

Public Sub New(ByVal startPoint As Long)

 setProcessingState(ProcessingState.notYetStarted)

 m_startPoint = startPoint

End Sub

'–

'Создает новый рабочий поток, который будет вызывать функцию

'findNextHighestPrime()

'–

Public Sub findNextHighestPrime_Async()

 Dim threadStartAs System.Threading.ThreadStart

 threadStart = _

  New System.Threading.ThreadStart( _

  AddressOf findNextHighestPrime)

 Dim newThread As System.Threading.Thread

 newThread = New System.Threading.Thread(threadStart)

 'Состояние должно отвечать, что поиск продолжается

 setProcessingState(ProcessingState.waitingToStartAsync)

 newThread.Start()

End Sub

'–

'Основной рабочий поток. Этот поток запускает поиск очередного

'простого числа и выполняется до тех пор, пока не произойдет

'одно из следующих двух событий:

' (а) найдено очередное простое число

' (b) от внешнего (по отношению к данному) потока поступила команда

' прекратить выполнение

'–

Public Sub findNextHighestPrime()

 'Если поступила команда прекратить выполнение, то поиск даже

 'не должен начинаться

 If (getProcessingState() = ProcessingState.requestAbort) Then

  GoTo finished_looking

 End If

 'Состояние должно отвечать, что поиск продолжается

 setProcessingState(ProcessingState.lookingForPrime)

 m_startTickCount = System.Environment.TickCount

 Dim currentItemAs Long

 'Проверить, является ли число нечетным

 If ((m_startPointAnd 1) = 1) Then

  'Число является нечетным, начать поиск со следующего нечетного числа

  currentItem = m_startPoint + 2

 Else

  'Число является четным, начать поиск со следующего нечетного числа

  currentItem = m_startPoint + 1

 End If

 'Приступить к поиску простого числа

 While (getProcessingState() = ProcessingState.lookingForPrime)

  'В случае нахождения простого числа возвратить его

  If (isItemPrime(currentItem) = True) Then

   m_NextHighestPrime = currentItem

   'Обновить состояние

   setProcessingState(ProcessingState.foundPrime)

  End If

  currentItem = currentItem + 2

 End While

finished_looking:

 'Выход. К этому моменту либо от другого потока поступила

 'команда прекратить поиск, либо было найдено и записано

 'следующее наибольшее простое число

 'Зафиксировать время

 m_endTickCount = System.Environment.TickCount

 'Если поступил запрос прекратить выполнение,

 'сообщить, что выполнение процесса прекращено

 If (getProcessingState() = ProcessingState.requestAbort) Then

  setProcessingState(ProcessingState.aborted)

 End If

End Sub

'Вспомогательная функция, которая проверяет, является

'ли число простым

Private Function isItemPrime(ByVal potentialPrime As Long) As Boolean

 'Если число – четное, значит, оно не является простым

 If ((potentialPrime And 1) = 0) Then

  Return False

 End If

 'Продолжать поиск до тех пор, пока не будет превышено значение

 'квадратного корня из числа

 Dim end_point_of_searchAs Long end_point_of_search = _

  CLng(System.Math.Sqrt(potentialPrime) + 1)

 Dim current_test_itemAs Long = 3

 While (current_test_item <= end_point_of search)

  '–

  'Проверить, не поступила ли команда прекратить выполнение!

  '–

  If (getProcessingState() <> ProcessingState.lookingForPrime) Then

   Return False

  End If

  'Если число делится без остатка,

  'значит, оно не является простым

  If (potentialPrimeMod current_test_item = 0) Then

   Return False

  End If

  'Увеличить число на два

  current_test_item = current test_item + 2

 End While

 'Число является простым

 Return True

End Function

End Class

Листинг 5.5. Тестовая программа, которая вызывает на выполнение приведенный выше код фонового потока, осуществляющего поиск простого числа

'–

'Код, обрабатывающий событие щелчка на кнопке Button1 формы

'Вызвать из этого потока функцию поиска простого числа!

'(Это приведет к блокированию потока)

'–

Private Sub Button1_Click(ByVal senderAs System.Object, _

 ByVal e As System.EventArgs) Handles Button1.Click

 Dim testItem As Long

 testItem = System.Convert.ToInt64("123456789012345")

 Dim nextPrimeFinder As FindNextPrimeNumber

 nextPrimeFinder = New FindNextPrimeNumber(testItem)

 nextPrimeFinder.findNextHighestPrime()

 Dim nextHighestPrime As Long

 nextHighestPrime = nextPrimeFinder.getPrime()

 MsgBox(CStr(nextHighestPrime))

 'Сколько времени заняли вычисления?

 Dim calculation_time As Integer

 calculationtime = nextPrimeFinder.getTickCountDelta()

 MsgBox(CStr(calculation time) + " мс")

End Sub

'–

'Код, обрабатывающий событие щелчка на кнопке Button2 формы

'Вызвать функцию поиска простого числа из другого потока!

'(Данный поток блокироваться не будет)

'Для отслеживания состояния выполнения задачи используем конечный автомат

'–

Private Sub Button2_Click(ByVal senderAs System.Object, _

 ByVal eAs System.EventArgs) Handles Button2.Click

 Dim testItem As Long

 testItem = System.Convert.ToInt64("123456789012345")

 Dim nextPrimeFinderAs FindNextPrimeNumber

 nextPrimeFinder = New FindNextPrimeNumber(testItem)

 '–

 'Выполнить обработку в другом потоке

 '–

 nextPrimeFinder.findNextHighestPrime_Async()

 'Войти в цикл и ожидать до тех пор, пока не будет найдено простое число

 'или выполнение не будет прекращено

 While ((nextPrimeFinder.getProcessingState() <> _

  FindNextPrimeNumber.ProcessingState.foundPrime) And _

  (nextPrimeFinder.getProcessingState() <> _

  FindNextPrimeNumber.ProcessingState.aborted))

  'ТОЛЬКО В ТЕСТОВОМ КОДЕ:

  'Отобразить окно сообщений и предоставить пользователю возможность

  'убрать его с экрана.

  'Это позволяет организовать паузу

  MsgBox("Поиск продолжается... Щелкните на кнопке OK")

  'Мы могли бы прекратить поиск путем следующего вызова функции:

  'nextPrimeFinder.setProcessingState(

  ' FindNextPrimeNumber.ProcessingState.requestAbort)

 End While

 'Осуществить корректный выход в случае прекращения поиска

 If (nextPrimeFinder.getProcessingState() = _

  FindNextPrimeNumber.ProcessingState.aborted) Then

  MsgBox("Поиск прекращен!")

  Return

 End If

 Dim nextHighestPrime As Long

 nextHighestPrime = nextPrimeFinder.getPrime()

 MsgBox(CStr(nextHighestPrime))

 'Сколько времени заняли вычисления?

 Dim calculation_time As Integer

 calculation_time = nextPrimeFinder.getTickCountDelta()

 MsgBox(CStr(calculation_time) + " мс")

End Sub


    Ваша оценка произведения:

Популярные книги за неделю