Перейти к содержанию
Fire Monkey от А до Я

Martifan

Пользователи
  • Постов

    396
  • Зарегистрирован

  • Посещение

  • Победитель дней

    16

Активность репутации

  1. Thanks
    Martifan получил реакцию от Hevard в Размер приложения   
    Скорее всего, увеличение размера исходного кода произошло из-за следующих причин:
    1. Разница в размере типов PChar и PAnsiChar. В Delphi 2009 и более поздних версиях PChar был заменен на PAnsiChar для совместимости с Unicode. Размер PAnsiChar в 2 раза больше чем PChar.
    2. Автоматическая конвертация строковых литералов в Unicode. В новых версиях Delphi строковые литералы имеют тип UnicodeString вместо AnsiString. Это также увеличивает размер.
    3. Добавление префиксов перед строковыми литералами. Для совместимости с Unicode Delphi автоматически добавляет префиксы перед строками, например 'U', 'L', etc. Это тоже увеличивает размер кода.
    4. Выравнивание данных. Компилятор может добавлять выравнивание в памяти для некоторых типов, например для PAnsiChar.
    5. Другие изменения в формате объектного кода. Например, более длинные имена классов/методов.
    Таким образом, переход на новые версии Delphi с Unicode поддержкой может привести к значительному увеличению размера исходного кода из-за несовместимости строк, упаковки данных и других факторов. Это нормальное явление, цена прогресса.
  2. Like
    Martifan получил реакцию от AngryOwl в Рисование на неклиентской часть окна   
    К сожалению, в FireMonkey для Windows нет встроенной поддержки для размещения компонентов или рисования на заголовке окна (title bar).
    Однако, есть несколько возможных вариантов для достижения похожего эффекта:
    Создать собственный кастомный компонент на основе TControl, который будет перекрывать заголовок окна и имитировать его. Можно нарисовать свой фон, кнопки и т.д. Использовать Windows API функции для настройки и изменения заголовка окна. Например, SetWindowText, SetWindowLong и другие. Это более сложный подход, но дает больше контроля. Рассмотреть сторонние компоненты и библиотеки. Возможно, кто-то уже реализовал похожую функциональность для FireMonkey. Попробовать поместить TControlAboveTarget на TForm и настроить его позицию/размер чтобы перекрывал заголовок. Не идеальный вариант, но может сработать. Так что в целом это возможно реализовать в FireMonkey, но нет встроенного прямого решения как в VCL. Придется поиграться с кастомными компонентами и низкоуровневым API.
  3. Thanks
    Martifan отреагировална OnePeople в Рисование на неклиентской часть окна   
    Или просто сделайте borderstyle формы none. И сами сделайте рамки, кнопки закрыть, свернуть и т.д.
  4. Like
    Martifan получил реакцию от OnePeople в splash_image_def rad 11.3   
    К сожалению, вы не можете использовать прямые значения цвета в теге android:drawable. Этот атрибут предназначен для ссылок на ресурсы, а не для прямых значений цвета.
    Однако вы можете определить свой собственный цвет в ресурсах вашего приложения и ссылаться на него. Для этого выполните следующие шаги:
    1. Откройте файл res/values/colors.xml в вашем проекте. Если этот файл не существует, создайте его.
    2. В файле colors.xml определите свой собственный цвет, как показано ниже:
    <?xml version="1.0" encoding="utf-8"?> <resources> <color name="my_custom_color">#0066cc</color> </resources> Теперь вы можете использовать свой пользовательский цвет в файле splash_image_def:
     
    <item android:drawable="@color/my_custom_color" /> учтите, что названия ресурсов не должны начинаться с цифры и не должны содержать символов, кроме букв (a-z), цифр (0-9) и подчеркивания (_).
    Ваш код может выглядеть следующим образом:
     
    <?xml version="1.0" encoding="utf-8"?> <layer-list xmlns:android="http://schemas.android.com/apk/res/android"> <item android:drawable="@color/my_custom_color" /> <item> <bitmap android:gravity="center" android:src="@mipmap/ic_launcher" /> </item> </layer-list>  
  5. Like
    Martifan получил реакцию от Hevard в Размер компилируемого файла   
    Когда вы говорите, что приложения на Андроиде весят 400КБ и используют библиотеки Java размером 2ГБ, вы, по-видимому, имеете в виду разницу между размером исполняемого файла приложения и размером всех библиотек, которые оно может использовать во время выполнения.
    Современные фреймворки, такие как Java для Android или .NET, часто используют большое количество библиотек, которые содержат общий код, используемый многими приложениями. Эти библиотеки обычно устанавливаются один раз и затем используются множеством приложений, поэтому их размер не влияет на размер каждого отдельного приложения.
    С другой стороны, приложения, созданные с использованием Delphi, обычно компилируются в нативный код и включают в себя все необходимые библиотеки и зависимости. Это может привести к тому, что исполняемые файлы будут больше, чем если бы они использовали общие библиотеки, но они не зависят от установленных библиотек времени выполнения.
    С точки зрения конечного пользователя, размер приложения часто не является ключевым фактором, особенно с учетом того, что современные устройства имеют большое количество памяти. Однако для разработчиков может быть важно минимизировать размер приложения, чтобы сократить время загрузки и уменьшить использование ресурсов.
    В итоге, вопрос "маленькие или большие приложения" зависит от контекста и требований конкретного приложения. В некоторых случаях использование общих библиотек может быть выгодно, в других - предпочтительнее иметь самодостаточное приложение с включенными в него всеми необходимыми библиотеками.
  6. Like
    Martifan получил реакцию от Letter в Протестировать приложение   
    Для тестирования приложения, написанного на Delphi 10.4 для Android, можно использовать различные инструменты и ресурсы.
    Реальные устройства: Тестирование на реальных устройствах позволяет вам увидеть, как приложение будет работать в реальных условиях. Используйте устройства с различными характеристиками экрана, версиями ОС и производительностью для более обширного тестирования.
    Эмуляторы Android: Эмуляторы позволяют вам запускать приложения Android на компьютере. Вы можете настроить эмуляторы с различными размерами экрана, разрешениями и плотностью пикселей.
    Android Studio: Это официальная среда разработки для Android, и она включает в себя эмулятор Android. Вы можете создать различные виртуальные устройства с разными характеристиками для тестирования вашего приложения.
    Genymotion: Это еще одна популярная среда для эмуляции Android-устройств. Она предлагает некоторые функции, которые могут быть полезны для разработчиков, такие как встроенные инструменты для тестирования GPS и акселерометра.
    Сервисы облачного тестирования: Если вы не хотите заниматься настройкой эмуляторов или не имеете доступа к множеству реальных устройств, вы можете воспользоваться сервисами облачного тестирования.
    Firebase Test Lab: Это услуга от Google, которая позволяет вам тестировать ваше приложение на реальных устройствах, хостед в облаке Google.
    AWS Device Farm: Это услуга от Amazon, которая позволяет вам тестировать и взаимодействовать с вашим Android-приложением на множестве реальных устройств.
    При тестировании приложения уделите внимание таким аспектам как адаптивный дизайн, работоспособность на различных версиях ОС и корректность работы функционала.
  7. Thanks
    Martifan отреагировална OnePeople в Компиляция приложения android   
    Нигде в деплоймент не указана внешняя память ???????
    Вообще то requestLegacyExternalStorage это параметр у вас в AndroidManifest.xml
  8. Thanks
    Martifan отреагировална OnePeople в Компиляция приложения android   
    Ну у вас в настройках sdk API-Level location версии 26, а был наверное 29 и выше вот ошибки и небыло
  9. Haha
    Martifan отреагировална OnePeople в Анимация модального окна   
    Не по теме, но у оператора от таких цветов в конце дня нет желания кого-нибудь убить? 
  10. Like
    Martifan получил реакцию от Alisson R Oliveira в Запись звука как на диктофоне   
    В Delphi для усиления звука записи можно воспользоваться классом TAudioCaptureDevice и его свойством Volume. Это свойство позволяет установить уровень громкости для записи звука. Чем выше значение Volume, тем громче будет записанный звук.
    Вот пример, как можно использовать свойство Volume:
     
    uses FMX.AudioCapture, System.SysUtils; procedure RecordAudio(const AFileName: string; const AVolume: Single); var AudioCapture: TAudioCaptureDevice; begin AudioCapture := TAudioCaptureDevice.Create(nil); try AudioCapture.FileName := AFileName; AudioCapture.PauseLength := 0; AudioCapture.Volume := AVolume; // Установка уровня громкости AudioCapture.Active := True; Sleep(5000); // Запись в течение 5 секунд AudioCapture.Active := False; finally AudioCapture.Free; end; end; procedure TForm1.Button1Click(Sender: TObject); begin // Задайте путь и имя файла, в который будет сохранен звук // Укажите значение громкости от 0 до 1 (например, 0.5 для половины максимальной громкости) RecordAudio('/sdcard/MyRecording.wav', 0.8); ShowMessage('Запись завершена.'); end; В этом примере в процедуре RecordAudio добавлен дополнительный параметр AVolume, который позволяет задать уровень громкости записи. Значение AVolume должно быть в диапазоне от 0 до 1, где 0 соответствует минимальной громкости, а 1 - максимальной.
    Вы можете экспериментировать с различными значениями AVolume, чтобы найти наиболее подходящий уровень усиления звука для вашего приложения и устройства.
  11. Like
    Martifan получил реакцию от Letter в Запись звука как на диктофоне   
    В Delphi для усиления звука записи можно воспользоваться классом TAudioCaptureDevice и его свойством Volume. Это свойство позволяет установить уровень громкости для записи звука. Чем выше значение Volume, тем громче будет записанный звук.
    Вот пример, как можно использовать свойство Volume:
     
    uses FMX.AudioCapture, System.SysUtils; procedure RecordAudio(const AFileName: string; const AVolume: Single); var AudioCapture: TAudioCaptureDevice; begin AudioCapture := TAudioCaptureDevice.Create(nil); try AudioCapture.FileName := AFileName; AudioCapture.PauseLength := 0; AudioCapture.Volume := AVolume; // Установка уровня громкости AudioCapture.Active := True; Sleep(5000); // Запись в течение 5 секунд AudioCapture.Active := False; finally AudioCapture.Free; end; end; procedure TForm1.Button1Click(Sender: TObject); begin // Задайте путь и имя файла, в который будет сохранен звук // Укажите значение громкости от 0 до 1 (например, 0.5 для половины максимальной громкости) RecordAudio('/sdcard/MyRecording.wav', 0.8); ShowMessage('Запись завершена.'); end; В этом примере в процедуре RecordAudio добавлен дополнительный параметр AVolume, который позволяет задать уровень громкости записи. Значение AVolume должно быть в диапазоне от 0 до 1, где 0 соответствует минимальной громкости, а 1 - максимальной.
    Вы можете экспериментировать с различными значениями AVolume, чтобы найти наиболее подходящий уровень усиления звука для вашего приложения и устройства.
  12. Like
    Martifan получил реакцию от krapotkin в анимация не анимирует по андроидом   
    Ваши проблемы с анимацией могут быть связаны с несколькими вещами.
    Во-первых, стоит отметить, что метод AnimateFloatWait помечен как устаревший, и рекомендуется использовать Ani.TAnimator вместо него.
    Ani.TAnimator.AnimateFloat создает и запускает объект TFloatAnimation. Он устанавливает свойства анимации и начинает анимацию. Однако стоит заметить, что если объект не видим в момент вызова этого метода, анимация не запускается: анимация создается, но не выполняется.
    Вторым фактором может быть то, как Android обрабатывает анимацию. Android может иметь разные характеристики производительности и отображения, которые влияют на то, как анимация выполняется на устройстве.
    Также, есть пример использования анимации в Delphi для Android, который может быть полезен. Get access to over 100 FireMonkey cross platform samples for Android, IOS, OSX, Windows, and Linux!
    Следовательно, я бы посоветовал начать с применения Ani.TAnimator.AnimateFloat вместо AnimateFloatWait, и убедиться, что объект, который вы пытаетесь анимировать, видим на экране во время начала анимации. Если проблема продолжает сохраняться, вам может потребоваться более детальное исследование спецификаций Android и как он обрабатывает анимацию в Delphi.
  13. Like
    Martifan получил реакцию от AngryOwl в Теряются Push уведомления   
    Firebase Cloud Messaging (FCM) предоставляет возможность установить приоритет сообщения, но это не гарантирует, что все сообщения будут доставлены в определенном порядке или что все сообщения будут доставлены вообще.
    Когда устройство находится в режиме отключения от интернета, FCM хранит только последнее сообщение для каждого топика. Это означает, что если вы отправляете три разных уведомления на одно и то же устройство, когда оно отключено от интернета, FCM сохранит только последнее уведомление. Когда устройство снова подключается к интернету, оно получит только это последнее уведомление.
    Если вам нужно, чтобы все уведомления были доставлены, вам нужно будет реализовать свою собственную систему очереди на стороне клиента. Это может включать в себя сохранение уведомлений в локальной базе данных на устройстве и отображение их в нужном порядке, когда устройство подключается к интернету.
  14. Like
    Martifan получил реакцию от krapotkin в Как разрешить имя хоста в ip адрес на Андроиде?   
    В контексте Delphi, вы можете использовать Indy компоненты для этого. TIdStack имеет метод ResolveHost() который может быть использован для разрешения имени хоста.
     
    var GStack: TIdStack; begin GStack := TIdStack.Create; try ShowMessage(GStack.ResolveHost('localhost', Id_IPv4).ToString); finally GStack.Free; end; end; Учтите, что разрешение имени хоста в IP-адрес не гарантирует, что хост будет доступен для подключения. Если имя хоста не может быть разрешено, будет вызвано исключение UnknownHostException.
    Также обратите внимание, что операции с сетью, такие как разрешение имени хоста, могут быть медленными, и рекомендуется выполнять их в фоновом потоке, чтобы не блокировать главный поток приложения.
    По поводу вашей проблемы с локальной сетью - возможно, имя хоста, которое вы пытаетесь разрешить, не зарегистрировано в локальном DNS. В этом случае, вы можете попробовать использовать полное доменное имя (FQDN) хоста, или использовать прямой IP-адрес, если он известен.
    Если метод разрешения имен не работает для локальной сети, вероятно, проблема связана с настройками DNS в вашей локальной сети. Имена хостов в локальной сети обычно разрешаются с помощью механизма DNS, поэтому если ваш DNS сервер или файлы hosts не содержат соответствующих записей для имени хоста, который вы пытаетесь разрешить, то метод разрешения имен вернет ошибку.
    Если вы контролируете настройки DNS в вашей локальной сети, вы можете добавить соответствующие записи для всех хостов, которые вы хотите разрешать.
    Кроме того, некоторые системы поддерживают механизмы обнаружения служб на локальной сети, такие как mDNS (Multicast DNS), который используется в протоколе Zeroconf/Bonjour. Если ваши устройства и приложения поддерживают mDNS, вы можете использовать имена хостов с суффиксом .local для разрешения имён в локальной сети.
    Пожалуйста, учтите, что разрешение имён хостов в IP-адреса - это сложная область, которая зависит от многих факторов, включая конфигурацию вашей сети, настройки DNS, поддержку протоколов обнаружения служб и т.д. Если вы столкнулись с проблемами, вам может потребоваться обратиться к системному администратору или к специалисту по сетям для получения помощи.
  15. Like
    Martifan получил реакцию от krapotkin в Размер компилируемого файла   
    Когда вы говорите, что приложения на Андроиде весят 400КБ и используют библиотеки Java размером 2ГБ, вы, по-видимому, имеете в виду разницу между размером исполняемого файла приложения и размером всех библиотек, которые оно может использовать во время выполнения.
    Современные фреймворки, такие как Java для Android или .NET, часто используют большое количество библиотек, которые содержат общий код, используемый многими приложениями. Эти библиотеки обычно устанавливаются один раз и затем используются множеством приложений, поэтому их размер не влияет на размер каждого отдельного приложения.
    С другой стороны, приложения, созданные с использованием Delphi, обычно компилируются в нативный код и включают в себя все необходимые библиотеки и зависимости. Это может привести к тому, что исполняемые файлы будут больше, чем если бы они использовали общие библиотеки, но они не зависят от установленных библиотек времени выполнения.
    С точки зрения конечного пользователя, размер приложения часто не является ключевым фактором, особенно с учетом того, что современные устройства имеют большое количество памяти. Однако для разработчиков может быть важно минимизировать размер приложения, чтобы сократить время загрузки и уменьшить использование ресурсов.
    В итоге, вопрос "маленькие или большие приложения" зависит от контекста и требований конкретного приложения. В некоторых случаях использование общих библиотек может быть выгодно, в других - предпочтительнее иметь самодостаточное приложение с включенными в него всеми необходимыми библиотеками.
  16. Like
    Martifan получил реакцию от Letter в Запрет ввода определенных символов в TEdit   
    если правильно понял вам нужна это:   в FireMonkey и в Android свойстве TEdit добавлена FilterChar и выглядит это так: procedure TForm1.FormCreate(Sender: TObject); begin   Edit1.FilterChar:= '0123456789'; end;
  17. Like
    Martifan получил реакцию от Hevard в Как поменять надписи для кнопок в MessageDlg?   
    Извините я сам нашел решение если кому пригодится:
     
    1. находим файл FMX.Consts.pas
    2. Положи его в папку с проектом.
    3. Menu Project->Add to Project - добавь этот файл.
    4. Сохрани проект. Закрой проект. Открой проект заново.
    5. Menu -> Project -> Build All Project
    6. Запускаем.
  18. Thanks
    Martifan получил реакцию от Hevard в Аналог WriteLn в TFile?   
    Для работы с файлами в современных версиях Delphi я рекомендую использовать классы TStringList или TFileStream. TStringList подходит для работы с текстовыми файлами, а TFileStream для работы с двоичными файлами.
    Вот пример кода, как выгрузить динамический массив в текстовый файл, используя TStringList:
    uses Classes, SysUtils; var IndexData: array of array of Integer; IndexFile: TStringList; I, QNum, URes, RAns: Integer; begin SetLength(IndexData, 5, 4); // Задаем размер массива IndexFile := TStringList.Create; try for I := 0 to High(IndexData) do begin // Записываем данные в массив (для примера, используем случайные значения) IndexData[I, 0] := I; IndexData[I, 1] := QNum; IndexData[I, 2] := URes; IndexData[I, 3] := RAns; // Добавляем данные из массива в строку IndexFile IndexFile.Add(IntToStr(IndexData[I, 0]) + ', ' + IntToStr(IndexData[I, 1]) + ', ' + IntToStr(IndexData[I, 2]) + ', ' + IntToStr(IndexData[I, 3])); end; // Сохраняем данные в файл IndexFile.SaveToFile('DB\Index.tmp'); finally IndexFile.Free; end; end. Когда вы используете класс TStringList, вам не нужно заботиться о закрытии файла. TStringList.SaveToFile автоматически закрывает файл после записи. Метод TStringList.Free очищает память, выделенную для объекта.
  19. Like
    Martifan получил реакцию от Sergey S в Как правильно назначить TThread Policy and Priority в Linux   
    Для установки приоритета потока в Linux в Delphi можно использовать функцию pthread_setschedparam(). Эта функция позволяет задать приоритет потока в соответствии с POSIX-стандартом.
    Пример использования функции pthread_setschedparam() для установки приоритета потока можно найти в следующем коде:
    uses Posix.Sched; var Params: sched_param; ThreadId: pthread_t; begin ThreadId := pthread_self(); Params.sched_priority := 10; // устанавливаем приоритет 10 if pthread_setschedparam(ThreadId, SCHED_FIFO, @Params) <> 0 then raise Exception.Create('Error setting thread priority'); end; В этом примере мы устанавливаем приоритет потока на уровне 10 с помощью структуры sched_param. Далее мы используем функцию pthread_setschedparam() для установки приоритета нашему потоку, и если функция возвращает значение отличное от 0, то возникает исключение.
    Обратите внимание, что установка приоритета потока может быть опасной, поскольку это может привести к проблемам с производительностью системы или блокировке других потоков. Поэтому необходимо использовать эту функцию осторожно и только в случае крайней необходимости.
  20. Like
    Martifan получил реакцию от GASCHE в Запрет ввода определенных символов в TEdit   
    если правильно понял вам нужна это:   в FireMonkey и в Android свойстве TEdit добавлена FilterChar и выглядит это так: procedure TForm1.FormCreate(Sender: TObject); begin   Edit1.FilterChar:= '0123456789'; end;
  21. Thanks
    Martifan отреагировална gonzales в StatusBar Color   
    Долго бился со следующим, есть три типа устройств: 1. где отсутствует NavBar физически, 2. где он есть и всегда включен, 3. где он есть, но его можно выключить в настройках. В результате добился нормальной работы окраски NavBar на всех типах. Немного изменил код, приведенный Равилем из примера Update2
    function hasNavbar(out navBarHeight: Integer): boolean; // uses Androidapi.JNI.Util, {$IFDEF ANDROID} var Window: JWindowExt; realSize: JPoint; screenSize: JPoint; metrics: JDisplayMetrics; difference, resourceID: Integer; {$ENDIF} begin Result := false; navBarHeight := 0; {$IFDEF ANDROID} metrics := TJDisplayMetrics.Create; realSize := TJPoint.Create; screenSize := TJPoint.Create; Window := GetWindowExt; Window.getWindowManager.getDefaultDisplay.getRealMetrics(metrics); realSize.x := metrics.widthPixels; realSize.y := metrics.heightPixels; Window.getWindowManager.getDefaultDisplay.getSize(screenSize); if realSize.y <> screenSize.y then begin difference := realSize.y - screenSize.y; resourceID := TAndroidHelper.Activity.getResources.getIdentifier(StringToJString('navigation_bar_height'), StringToJString('dimen'), StringToJString('android')); if resourceID > 0 then navBarHeight := Trunc(TAndroidHelper.Activity.getResources.getDimensionPixelSize(resourceID)); if navBarHeight > 0 then if difference < navBarHeight then begin navBarHeight := 0; Result := false; end else Result := true; end else begin navBarHeight := 0; Result := false; end; {$ENDIF} end;  
  22. Like
    Martifan получил реакцию от Ingalime в Как получить IMEI?   
    а для Android:
     
    Uses Androidapi.JNI.Telephony, Androidapi.JNI.JavaTypes, Androidapi.Helpers, Androidapi.JNI.GraphicsContentViewText;   function TfMain.GetMyImei: string;   var   TelephonyObj: JObject;   TelephonyManager: JTelephonyManager; begin   Result := '';   TelephonyObj := SharedActivityContext.getSystemService(TJContext.JavaClass.TELEPHONY_SERVICE);   TelephonyManager := TJTelephonyManager.Wrap((TelephonyObj as ILocalObject).GetObjectID);   Result := JStringToString(TelephonyManager.getDeviceId); end;
  23. Like
    Martifan получил реакцию от panmilkos в StatusBar Color   
    Доброго времени сутки.
    На Samsung Galaxy S8 Edge проект когда открываю выдаёт вот так:
     
    кто в курсе почему так происходит? вроде красный панель доле перекрывать NavigationBar?
    заранее спасибо
  24. Like
    Martifan отреагировална Edward Tarasov в TThread В фоновом режиме   
    Сам недавно бился с этим вопросом. ответ нашел на этом форуме.
    Но после долгого гугления вопроса сложилось впечатление, что на сегодняшний день из ios можно выжать максимум три минуты работы приложения в фоне, потом приложение перестает реагировать. в моем случае было необходимо передавать координаты. Что только не перепробовал - три минуты и все. можно мухлевать: Воспроизводить аудио или записывать с микрофона - но ребята из apple при публикации к такому отнесутся не очень. вот исходники которые нарыл - пример отрабатывает в фоне три минуты
     
    BackgroundTaskManager.zip
  25. Like
    Martifan отреагировална Ronalds Rizakovs в Ping на Android или на iOS   
    У меня была похожая проблема - проверить доступен ли хост. 
    Как я понял TIdICMPClient работает лиш при наличии root. Даже под win надо "as administrator" запускать.
    Были варианты вызвать системную команду PING и анализировать результат, но сложно. 
    Проблему обошол  с помощью IdTCPClient.
    function CheckInternet: boolean;
    begin
    result:=false;
    try
    IdTCPClient1.ReadTimeout:=200;
    IdTCPClient1.ConnectTimeout:=200;
    IdTCPClient1.Port:=Port;
    IdTCPClient1.Host:=Server;
    IdTCPClient1.Connect;
    IdTCPClient1.Disconnect;
    result:=true;
    except
    result:=false;
    end;
    end;
    Если надо время отклика проверит - не подойдот. А для доступности по моему ок!  
     
×
×
  • Создать...