9#include <QCoreApplication>
11#include <QtCore/QJniEnvironment>
12#include <QtCore/QJniObject>
25 file.replace(
"//"_L1,
"/"_L1);
26 if (
file.startsWith(u
'/'))
28 if (
file.endsWith(u
'/'))
36 path.replace(
"//"_L1,
"/"_L1);
50 if (
name.endsWith(u
'/')) {
68 QSharedPointer<FolderIterator> *folder = m_assetsCache.object(
path);
71 if ((*folder)->empty() || !m_assetsCache.insert(
path, folder)) {
72 QSharedPointer<FolderIterator>
res = *folder;
77 return clone ? QSharedPointer<FolderIterator>{
new FolderIterator{*(*folder)}} : *folder;
83 return AssetItem::Type::Folder;
90 return val.name < assetItem.name;
93 return AssetItem::Type::Invalid;
94 if (!fullPath.isEmpty())
95 fullPath.append(u
'/');
105 , m_path(
other.m_path)
115 "(Landroid/content/res/AssetManager;Ljava/lang/String;)[Ljava/lang/String;",
117 if (
files.isValid()) {
119 jobjectArray jFiles =
files.object<jobjectArray>();
120 const jint nFiles = env->GetArrayLength(jFiles);
121 for (
int i = 0;
i < nFiles; ++
i) {
122 AssetItem item{QJniObject::fromLocalRef(env->GetObjectArrayElement(jFiles,
i)).toString()};
124 return a.name <
b.name;
129 m_path.
replace(
"//"_L1,
"/"_L1);
134 if (m_index < 0 || m_index >=
size())
136 return at(m_index).name;
140 if (m_index < 0 || m_index >=
size())
142 return m_path +
at(m_index).name;
157 static QCache<QString, QSharedPointer<FolderIterator>> m_assetsCache;
158 static QMutex m_assetsCacheMutex;
161QCache<QString, QSharedPointer<FolderIterator>> FolderIterator::m_assetsCache(std::max(50,
qEnvironmentVariableIntValue(
"QT_ANDROID_MAX_ASSETS_CACHE_SIZE")));
162Q_CONSTINIT
QMutex FolderIterator::m_assetsCacheMutex;
182 if (!m_currentIterator)
189 if (!m_currentIterator)
196 return m_currentIterator ? m_currentIterator->
advance() :
false;
200 QSharedPointer<FolderIterator> m_currentIterator;
207 : m_assetManager(assetManager)
217 bool open(QIODevice::OpenMode openMode, std::optional<QFile::Permissions> permissions)
override
224 m_assetFile = AAssetManager_open(m_assetManager, m_fileName.
toUtf8(), AASSET_MODE_BUFFER);
231 AAsset_close(m_assetFile);
241 return m_assetInfo->
size;
248 return AAsset_seek(m_assetFile, 0, SEEK_CUR);
255 return pos == AAsset_seek(m_assetFile,
pos, SEEK_SET);
262 return AAsset_read(m_assetFile,
data, maxlen);
276 if (m_assetInfo->
type == AssetItem::Type::File)
278 else if (m_assetInfo->
type == AssetItem::Type::Folder)
294 return m_fileName.
mid(
pos + 1);
318 QSharedPointer<AssetItem> *assetInfoPtr = m_assetsInfoCache.object(m_fileName);
320 m_assetInfo = *assetInfoPtr;
325 QSharedPointer<AssetItem> *newAssetInfoPtr =
new QSharedPointer<AssetItem>(
new AssetItem);
327 m_assetInfo = *newAssetInfoPtr;
328 m_assetInfo->
name = m_fileName;
329 m_assetInfo->
type = AssetItem::Type::Invalid;
331 m_assetFile = AAssetManager_open(m_assetManager, m_fileName.
toUtf8(), AASSET_MODE_BUFFER);
334 m_assetInfo->
type = AssetItem::Type::File;
335 m_assetInfo->
size = AAsset_getLength(m_assetFile);
337 auto *assetDir = AAssetManager_openDir(m_assetManager, m_fileName.
toUtf8());
339 if (AAssetDir_getNextFileName(assetDir)
344 m_assetInfo->
type = AssetItem::Type::Folder;
346 AAssetDir_close(assetDir);
351 m_assetsInfoCache.insert(m_fileName, newAssetInfoPtr);
358 if (m_assetInfo && m_assetInfo->
type == AssetItem::Type::Folder)
359 return std::make_unique<AndroidAbstractFileEngineIterator>(
filters, filterNames, m_fileName);
364 AAsset *m_assetFile =
nullptr;
365 AAssetManager *m_assetManager =
nullptr;
368 QSharedPointer<AssetItem> m_assetInfo;
370 static QCache<QString, QSharedPointer<AssetItem>> m_assetsInfoCache;
371 static QMutex m_assetsInfoCacheMutex;
374QCache<QString, QSharedPointer<AssetItem>> AndroidAbstractFileEngine::m_assetsInfoCache(std::max(200,
qEnvironmentVariableIntValue(
"QT_ANDROID_MAX_FILEINFO_ASSETS_CACHE_SIZE")));
375Q_CONSTINIT
QMutex AndroidAbstractFileEngine::m_assetsInfoCacheMutex;
382std::unique_ptr<QAbstractFileEngine>
393 if (
path.startsWith(u
'/'))
395 if (
path.endsWith(u
'/'))
397 return std::make_unique<AndroidAbstractFileEngine>(m_assetManager,
path);
bool advance() override
This pure virtual function advances the iterator to the next directory entry; if the operation was su...
AndroidAbstractFileEngineIterator(QDir::Filters filters, const QStringList &nameFilters, const QString &path)
QString currentFileName() const override
This pure virtual function returns the name of the current directory entry, excluding the path.
QString currentFilePath() const override
Returns the path to the current directory entry.
QFileInfo currentFileInfo() const override
The virtual function returns a QFileInfo for the current directory entry.
~AndroidAbstractFileEngine()
void setFileName(const QString &file) override
Sets the file engine's file name to file.
FileFlags fileFlags(FileFlags type=FileInfoAll) const override
This function should return the set of OR'd flags that are true for the file engine's file,...
qint64 size() const override
Returns the size of the file.
qint64 pos() const override
Returns the current file position.
bool caseSensitive() const override
Should return true if the underlying file system is case-sensitive; otherwise return false.
bool seek(qint64 pos) override
Sets the file position to the given offset.
qint64 read(char *data, qint64 maxlen) override
Reads a number of characters from the file into data.
IteratorUniquePtr beginEntryList(const QString &, QDir::Filters filters, const QStringList &filterNames) override
Returns a QAbstractFileEngine::IteratorUniquePtr, that can be used to iterate over the entries in pat...
bool close() override
Closes the file, returning true if successful; otherwise returns false.
bool open(QIODevice::OpenMode openMode, std::optional< QFile::Permissions > permissions) override
Opens the file in the specified mode.
QString fileName(FileName file=DefaultName) const override
Return the file engine's current file name in the format specified by file.
AndroidAbstractFileEngine(AAssetManager *assetManager, const QString &fileName)
std::unique_ptr< QAbstractFileEngine > create(const QString &fileName) const override
If this file handler can handle fileName, this method creates a file engine and returns it wrapped in...
AndroidAssetsFileEngineHandler()
static QSharedPointer< FolderIterator > fromCache(const QString &path, bool clone)
QString currentFilePath() const
FolderIterator(const QString &path)
static AssetItem::Type fileType(const QString &filePath)
FolderIterator(const FolderIterator &other)
QString currentFileName() const
The QAbstractFileEngineIterator class provides an iterator interface for custom file engines.
QDir::Filters filters() const
Returns the entry filters for this iterator.
QStringList nameFilters() const
Returns the name filters for this iterator.
\inmodule QtCore \reentrant
std::unique_ptr< Iterator > IteratorUniquePtr
FileName
These values are used to request a file name in a particular format.
bool remove()
Removes the file specified by fileName().
qsizetype size() const noexcept
iterator insert(qsizetype i, parameter_type t)
bool empty() const noexcept
\macro QT_RESTRICTED_CAST_FROM_ASCII
QString left(qsizetype n) const &
qsizetype lastIndexOf(QChar c, Qt::CaseSensitivity cs=Qt::CaseSensitive) const noexcept
QString & replace(qsizetype i, qsizetype len, QChar after)
void chop(qsizetype n)
Removes n characters from the end of the string.
QStringList split(const QString &sep, Qt::SplitBehavior behavior=Qt::KeepEmptyParts, Qt::CaseSensitivity cs=Qt::CaseSensitive) const
Splits the string into substrings wherever sep occurs, and returns the list of those strings.
QString mid(qsizetype position, qsizetype n=-1) const &
bool isEmpty() const noexcept
Returns true if the string has no characters; otherwise returns false.
QString & remove(qsizetype i, qsizetype len)
Removes n characters from the string, starting at the given position index, and returns a reference t...
QByteArray toUtf8() const &
QSet< QString >::iterator it
Combined button and popup list for selecting options.
jclass applicationClass()
AAssetManager * assetManager()
static QString prefixedPath(QString path)
static const int prefixSize
static const auto assetsPrefix
static QString cleanedAssetPath(QString file)
GLboolean GLboolean GLboolean b
GLboolean GLboolean GLboolean GLboolean a
[7]
GLenum GLuint GLintptr GLsizeiptr size
[1]
GLint GLsizei GLsizei GLenum GLenum GLsizei void * data
GLsizei const GLuint * paths
GLsizei const GLchar *const * path
Q_CORE_EXPORT int qEnvironmentVariableIntValue(const char *varName, bool *ok=nullptr) noexcept
const QStringList filters({"Image files (*.png *.xpm *.jpg)", "Text files (*.txt)", "Any files (*)" })
[6]
AssetItem(const QString &rawName)