Блог Александра Божко
Архивы
Рубрики

FireMonkey

TListView является одним из ключевых компонентов для построения интерфейса мобильного приложения в FireMonkey. Компонент этот не самый простой в использовании, зачастую предполагает значительный объем кода, зато предоставляет разработчику значительную свободу действий. Конечно, в приложениях можно использовать и TListBox, где все намного проще. Но TListBox, возможно, хорош для отображения фиксированного количества записей,  для вывода данных из источников данных, однозначно нужно использовать  TListView.

Цитирую Ярослава Бровина:

Главные отличия TListView от TListBox в:

  1. TListBoxItem - контрол, TListViewItem - нет
  2. В TListBoxItem можно добавлять любые контролы, используя Parent. В TListVIewItem - нет.
  3. TListVIewItem хранит только данные для отображения
  4. TListVIewItem сам выполняет отрисовку хранимых данных через метод Render
  5. За счет собственно ручной отрисовки в TListVIewItem достигается прирост скорости и малое потребление памяти (хранение только актуальных данных)
  6. Чтобы создать свой вариант TListViewItem, нужно создать свой класс итема, в нем реализовать требуемые данные (например время) и создать in-place редактор для редактирования времени, зарегистрировать его и т. д.

 

Сам по себе факт повышения производительности и уменьшения потребления памяти – веский аргумент в пользу использования TListView. Но есть и еще кое что.

Во многих Android приложениях мне приходилось наблюдать следующую реализацию списков. При нажатии на элемент списка (Item, если придерживаться выбранной терминологии), производится определенное действие. Обычно вызывается новая форма для редактирования данных. Но при нажатии с удерживанием (Long Tap) производится совершенно другое действие. И эти события не пересекаются. Иными словами Android приложения умеют четко различать “длинное нажатие” от “обычного”. Более того, ни одно из этих событий не срабатывает при скроллинге списка. Наглядный пример – список писем в Яндекс Почта.

При попытке реализовать подобный функционал с помощью TListBox, я получил чехарду из накладывающихся друг на друга событий. Главной проблемой оказалось отделение скроллинга от обычного нажатия. В TListView, как оказалось, с этим проблем нет. Но правильно определить события – тоже задача довольно интересная. Дабы сэкономить время своим читателям, я поделюсь здесь результатами своих экспериментов. Читать далее

lost_timerПрежде чем продолжить рассказ о таймере – две новости.

Во-первых, вышел первый апдейт XE7. По традиции он доступен зарегистрированным пользователям. Список исправленных багов вы можете найти здесь. Мне хотелось посмотреть как поведет себя приложение в обновленной среде. Собственно, никаких исправлений вносить не пришлось, хотя поле для экспериментов осталось.

Вторая новость. Действие специальных предложений Embarcadero продлено до конца года:

  • возможен апгрейд с любой старой версии на новую версию XE7: Delphi, C++ Builder и RAD Studio.
  • покупатели редакций Enterprise, Ultimate и Architect получают бесплатную лицензию Rapid SQL XE6.

Ну, а теперь непосредственно к теме поста. В принципе, все, что нам осталось – попытаться запустить уже созданное приложение под Android. Для это используем то, о чем я писал в предыдущих постах. А именно новый FireUI. Я отлаживал данное приложение на Nexus 7, соответственно добавил представление Android 7″ Tablet. Дизайн пришлось “подрихтовать” лишь самую малость.

Читать далее

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

Обнаружение неподдерживаемых устройств

Вы наверняка знаете, что платформа поддерживает подавляющее большинство Android устройств. Но есть и устройства с архитектурой, не поддерживаемой FireMonkey. В частности таких:

  • ARMv6
  • Intel x86
  • MIPS

Естественно, мой шеф является счастливым обладателем одного из подобных аппаратов. После запуска приложения, собранного в XE5 на Motorola Atrix mb860 попросту появляется черный экран, без всяких дополнительных оповещений. В XE6 появились три небольших библиотеки, которые по умолчанию добавляются в проект. Благодаря им теперь, при попытке запустить приложение на неподдерживаемом устройстве теперь выводится сообщение

Application not supported by this device

Если нет необходимости использовать эти библиотеки (например, когда приложения будет запускаться на каком-то конкретном устройстве) их можно отключить в Deployment manager‘е.

delpoyment_manager

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

Компоненты для продажи цифрового контента и показа рекламы

В отличии от iOS приложений, монетизация Android приложений не всегда возможна путем продажи непосредственно приложения. Здесь и сами приложения дешевле и конкуренция выше. Поэтому для Android приложений часто используют схемы продажи цифрового контента или рекламы в приложениях.

В XE6 теперь появились компоненты TBannerAdd и TInAppPurchase, предназначенные для показа рекламы и продажи цифрового контента, соответственно. Компоненты можно использовать как в Android (для работы с GooglePlay и AdMob), так и в iOS приложениях (для работы с iTunes и iAd).

Новый FireMonkey стиль для Google Glass

Собственно, для того, что бы о чем-то здесь говорить нужно как минимум иметь очки Google. Тем не менее, понятно, что данное устройство поддерживается, а следовательно принцип “в ногу со временем” воплощается жизнь.

FMX.Grid

Изменения произошли в гриде. Вопрос этот довольно актуальный. Все-таки велико искушение перенести идеологию VCL приложений в FireMonkey. И если для мобильных приложений от использования грида  лучше отказаться, то для десктопных приложений он просто необходим. Качественных сторонних решений уровня гридов от DevExpress нет. А для серьезных приложений, работающих с данными нужна сетка отображения данных с серьезным функционалом.

В XE6 был расширен базовый класс TCustomGrid. В нем появились события OnDrawColumnCell и OnDrawColumnHeader и несколько новых свойств TCustomGrid.Options.

В новой версии TGrid появились обновленные редакторы для столбцов типа TTimeColumn и TDateColumn. А также были добавлены четыре новых события OnHeaderClick, OnSelectCell, OnColumnMoved и OnCreateCustomEditor.

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

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

 Новые контролы для отображения даты и времени

Вместо TCalendarEdit в XE6 появились TDateEdit и TTimeEdit. Сразу же “прикрутил” их в свое приложение. Реализация понравилась. Реагируют на разрешение устройства и в зависимости от него показывают календарь в развернутом либо урезанном виде.

FireMonkey DateEdit

FireMonkey DateEdit

Прочее

На самом деле небольших изменений в FireMonkey было сделано достаточно много. В основном они связаны с модификацией типов данных и добавлением новых методов и событий в некоторые классы (в частности обновился TWebBrowser).

Между тем, при переходе с XE5 особых проблем с совместимостью у меня не возникло. Я не буду здесь перечислять все изменения, они детально описаны в справке в разделе What’s New in Delphi and C++Builder XE6.

Отдельная тема, на мой взгляд, достойная обсуждения – FireDAC. Но об обновлениях в этой библиотеке доступа к данным мы поговорим не сегодня.

Субъективные впечатления

Безусловно сама среда при разработке мобильных приложений стала работать стабильнее. За пару недель плотной работы практически не было “вылетов” и “критических сбоев” в работе IDE. Дизайнер формы наконец-то стал работать с буфером обмена.

К сожалению, редактор Visual Binding при большом количестве объектов на форме по-прежнему притормаживает, поэтому “лишние” (не используемые) объекты лучше сразу делать невидимыми.

Но, повторюсь, что в целом, впечатление весьма благоприятное.

Не пропустите:

 

Создание FireMonkey приложения с использованием FireDAC. #0

Создание FireMonkey приложения с использованием FireDAC. #0.5

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

Простой редактор данных в таблице, обычно является частью комплексного приложения. Для редактирования таблиц я обычно использую отдельную форму. Начнем со списка продуктов.  Прежде всего, нам необходимо создать DataSet для доступа к данным таблицы. В нашем случае вполне можно воспользоваться компонентом TADTable. Поместим его в DataModule и укажем значение свойства Connection. В редакторе свойства TableName появится список таблиц, из которого выбираем таблицу Products. Если вы все сделали правильно, то сможете присвоить свойству Active значение True. Компонент лучше сразу переименовать (например, ADTProduct). После этого я, обычно, создаю для DataSet’а набор полей. Вызываем редактор полей (двойное нажатие мыши на компоненте) и в контекстном меню выбираем пункт Add All Fields.

(в настоящее время ссылка не доступна)

Для тех, кто не в курсе поясню суть данной операции. Здесь мы создаем предустановленный набор полей DataSet’a. Если мы этого не сделаем вручную в режиме проектирования, то, в принципе, ничего страшного не произойдет. В RunTime этот набор будет создан автоматически. Но я, все же, предпочитаю создавать его вручную. Причин тому несколько. Во-первых, так удобнее управлять набором полей, ведь мы можем создавать дополнительные (вычисляемые или lookUp) поля самостоятельно в режиме проектирования. Можем так же менять свойства самих полей. А кроме того, мы получаем возможность обращаться в коде к полям по имени компонента TField, что, на мой взгляд, существенно упрощает написание кода.

Как и в случае с VCL приложением, подключим к набору данных компонент TDataSource. Этот компонент обеспечит связь между набором данных и визуальными элементами управления. Свойство DataSet компонента должно ссылаться на наш набор данных (ADTProduct). Ниже я привожу фрагмент DFM файла

 

  object ADTProduct: TADTable
    IndexFieldNames = 'ID'
    Connection = ADConnection
    UpdateOptions.UpdateTableName = 'Product'
    TableName = 'Product'
    Left = 64
    Top = 192
    object ADTProductID: TADAutoIncField
      FieldName = 'ID'
      Origin = 'ID'
      ProviderFlags = [pfInWhere, pfInKey]
      ReadOnly = True
    end
    object ADTProductTitle: TStringField
      FieldName = 'Title'
      Origin = 'Title'
      Size = 50
    end

  object dsProduct: TDataSource
    DataSet = ADTProduct
    Left = 120
    Top = 192
  end

Обратите внимание на одну любопытную особенность, файл формы DataModule сохраняется не в формате FMX, как обычная FireMonkey форма, а в формате DFM, как и в VCL.

Следующим шагом будет создание процедуры открытия набора данных, которую мы должны будем вызывать в RunTime при запуске программы. Создадим ее в том же DataModul’е. Код процедуры предельно прост:

procedure TDM.ConnectToDB;
begin
  ADConnection.Open();
  ADTProduct.Open();
end;

Вызов процедуры разместим в обработчике события OnCreate для DataModule. Читать далее

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

Попытаюсь объяснить логику.

Если соблюдать все рекомендации по разработке приложений, то начинать следует с модели предметной области. Существует несколько разных подходов к моделированию и разных видов моделей. Остановимся на одном из самых популярных видов – ER модели, предполагающей определение сущностей и связей между ними. Обычно имена сущностей выражаются существительным в единственном числе.

Собственно, давайте определимся с этими сущностями и связями в нашей задаче. Думаю я на русском, поэтому сначала выделим и обзовем сущности по-русски.

Как процесс выглядит в реальности (без автоматизации)? Я беру лист бумаги и записываю на нем список продуктов, возможно с указанием их количества. С этим листом бумаги я иду в магазин и отмечаю, что куплено, что нет.

Очевидно, что первой сущностью будет сам ПРОДУКТ. Ведь набор наименований продуктов, в принципе, конечен. Да и при автоматизации процесса их удобно выбирать из предустановленного списка.

Я берусь утверждать, что сам листок с записями так же следует выделить в качестве сущности. Я завел машину и тут мне позвонил сосед. Ты, мол в супермаркет? Купи мне пиво и хлеб (с)… И я беру второй лист бумаги и пишу: “Продукты для соседа”. Ставлю дату (вот уже два атрибута у сущности!) и записываю чего он там хочет… Как означить эту сущность? СПИСОК ПРОДУКТОВ – плохая идея. Хотя бы потому, что набор экземпляров сущности ПРОДУКТ тоже а некотором смысле список продуктов. Поэтому более удачным названием будет СПИСОК ПОКУПОК (насколько может быть удачным имя сущности, содержащее слово СПИСОК).

Но нам потребуется и третья сущность. По идее, две первые сущности связаны отношением много-много, и на уровне логической модели ничего добавлять не надо. Но, у нас завис такой атрибут как количество покупаемого продукта. Поэтому вводим сущность, соответствующую записи в списке покупок. И опять логично бы было назвать эту сущность СПИСОК ПРОДУКТОВ и опять это не совсем хорошая идея. Я просто решил обозначить эту сущность комбинацией имен связанных сущностей – СПИСОК ПОКУПОК – ПРОДУКТ. А, поскольку это не совсем удобочитаемо, то просто – СПИСОК-ПРОДУКТ.

Возможно, название ПУНКТ СПИСКА ПРОДУКТОВ (Shoping List Item) тоже имеет право на существование.

ERModel

Теперь на основе полученной модели надо создать таблицы. Естественно, что их имена должны либо транслитерироваться, либо переводиться. Я выбрал последний вариант.

Product, ShopingList, List_Product.

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

Ну, и в контексте данного поста напомню о DB Meta Studio – утилите, которая позволяет вставлять в код элементы структуры БД по заранее заданному шаблону. Читатели моего блога могут получить утилиту в подарок.

Отдельное спасибо Николаю Звереву за присланный отзыв о DB Meta Studio.

Недавно нашел в просторах Рунета (не скажу, что совсем случайно) интересную программу. FireMonkey Style Editor – название говорит за себя. Программа предназначена для создания и редактирования FireMonkey стилей.

Работа с редактором довольно проста. Собственно, ничего сложного, загружаем существующий FireMonkey стиль и редактируем любой из компонентов, используя инспектор объектов, позволяющий менять свойства любого из элементов стилей. Все практически так же как и в естественной среде Delphi.

Список возможностей редактора (взято с сайта программы):

  • быстрый выбор нужного элемента стиля;
  • быстрый доступ к свойствам стиля через инспектор свойств;
  • фильтрация по стилю;
  • копирование, вставка, удаление элементов стиля;
  • добавление отдельных элементов из другого стиля;
  • предпросмотр готового стиля;
  • перетаскивание элементов в структуре стиля;
  • так же есть улучшенные диалоги (TBrush, TColor, TGradient, TPath, TImage);
  • поддержка стилей FireMonkey XE2, FireMonkey2.0 XE3.

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

Остается пожелать автору успешного развития его продукта.

Если вы хотите узнать больше о стилях в FireMonkey, рекомендую посмотреть запись вебинара “Стили FireMonkey с Евгением Крюковым”(в настоящее время ссылка не доступна).

11 октября в Харькове прошел семинар в рамках RAD Studio XE3 World Tour. Подробный отчет о семинаре вы можете увидеть на сайте http://delphixe.com.ua/.

Я на семинаре показывал небольшой пример, иллюстрирующий работу механизма Visual LiveBinding. Как и обещал, выкладываю видео и, собственно, сам пример.

В качестве СУБД я использовал SQLite, компоненты доступа, для чистоты эксперимента, от стороннего производителя – LiteDAC от DevArt.

Я полностью записал весь процесс создания приложения, который занял около 20 минут. Получилась небольшая иллюстрация того, что теперь в FireMonkey приложения для работы с БД можно создавать практически так же просто, как и в VCL. Я не буду здесь приводить развернутых описаний, лишь вкратце расскажу, суть происходящего на видео. Если у вас возникнут вопросы, вы можете задать их в комментариях.

Первый ролик показывает процесс подключения компонентов доступа к БД. По сути ничем не отличается от аналогичного процесса в VCL.

Ролик 1. Читать далее

Не скрою, что основной проблемой FireMonkey, в том виде, в котором платформа была презентована в RAD Studio XE2, лично мне виделась неудобная работа с БД. Прежде всего, речь идет о визуализации данных. Напомню, что в FireMonkey нет так называемых db-aware компонентов. Связывание производится с использованием механизма LiveBinding. Это вызывало определенные затруднения у разработчиков.

Естественно, именно работа с данными, это  первое, что я хотел посмотреть в FM2. К тому же, тех, кто планирует купить Delphi до 28 сентября ожидает подарок – TMS Grid for FireMonkey. Насколько мне известно, это единственный полноценный грид для FireMonkey от сторонних разработчиков.

Я сделал небольшое тестовое приложение. Для тестового примера я использовал БД  MS Access. Приведенное ниже видео демонстрирует настройку соединения.

Первое, что меня приятно приятно удивило это Visual LiveBinding. В своем примере я использовал TMS Grid for FireMonkey, который до 28 сентября прилагается в подарок к Delphi, C++ Builder и RAD Studio XE3. Подключение грида к источнику данных производится буквально с помощью пары щелчков мышки. По сути это не сложнее чем в VCL.

Читать далее

Итак, конкурс «FireMonkey для учебы» завершен. На этот раз, у читателей DelphiFeeds.ru и подписчиков страницы сайта на FaceBook есть возможность самим определить победителя. Для этого нужно принять участие в голосовании.

Здесь я продублирую список конкурсных работ и ссылки для скачивания.

Тесты по английскому от Евгения Чмель.

Программа использует СУБД, для запуска скомпилированной версии вы можете воспользоваться вторым архивом.

http://delphifeeds.ru/konkurs/echmel_funny_english.zip
http://delphifeeds.ru/konkurs/echmel_funny_english_install.zip

Движение робота. Виктор Погулкин.

“Направляю вам работу. Она 100% подойдет учебному процессу, т.к. такие задания в большом количестве содержатся в учебнике информатики для младших классов. Там надо из точки “а” в точку “б” проложить путь по клеточкам.

Здесь я сделал так – можно выбрать простой вид (как в учебнике), а можно и 3D – это сложнее. Дальше выбирается номер задания (к сожалению, успел сделать только 2) путем ввода 1 (по умолчанию стоит) или 2-ки в компонент “едет”. Потом ученик должен нажимая кнопки “вперед”, “назад”, “влево”, “вправо” запрограммировать робота (программа появляется в “листбоксе”). Потом нажимаем “запуск” и робот анимировано движется в направление цели.

Пока проверить можно только визуально, чего, в принципе, достаточно. Конечно, есть что доработать, но общая идея, я полагаю, достаточно хороша и будет понятна комиссии https://www.lechenievisraile.com/лечение-без-посредников.

http://delphifeeds.ru/konkurs/robot3dmove.zip

http://delphifeeds.ru/konkurs/robot_program_exe.zip

«Я математик».Владислав Баженов

Программа предназначена для тренировки устного счёта.
Описание и руководство пользователя внутри архива.
Ждем ваших комментариев.
http://delphifeeds.ru/konkurs/im_math.zip (Исполняемый файл и описание внутри)

Детский суфлер. Сергей Попов.

Программа, помогающая детям заучивать тексты различной сложности:
http://delphifeeds.ru/konkurs/detskiy_sufler.zip

http://delphifeeds.ru/konkurs/detskiy_sufler_exe.zip

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

“…какими свойствами определяются координаты поверхностей и условно центра фигуры после загрузки произвольного объекта DAE в Model3D во время исполнения программы? Т.к. даже центр объекта далеко не всегда совпадает с центром модели…”

Собственно, данный вопрос давно интересовал меня самого. Использование моделей, созданных во внешних 3D редакторах – мощный инструмент. Но для того, что бы он стал действительно полезным, нам необходимо правильно расположить модель на форме. Это не всегда просто сделать даже в режиме проектирования, не говоря уже о RunTime.

Google SketchUp 8

Google SketchUp 8

И, для того, чтобы  разобраться с данным вопросом, я решил провести несколько экспериментов. Для создания модели я использовал Google SketchUp 8, основное преимущество которого – бесплатность. Я  уже упоминал об этом редакторе ранее. Читать далее

Продукты DevArt
Купить онлайн:



Читай русскоязычные Delphi блоги
Каталог блогов Blogdir.ru
Яндекс.Метрика