common Accessor: Add access api that with data parameter

It supports data parameters that
can pass user data to the callback function.

std::unique_ptr<Picture> access(std::unique_ptr<Picture> picture, bool(*func)(const Paint* paint, void* data), void* data) noexcept;
This commit is contained in:
JunsuChoi 2022-11-18 00:09:35 -08:00 committed by Hermet Park
parent a863f29512
commit 6e26aab1b6
2 changed files with 51 additions and 0 deletions

View file

@ -1614,6 +1614,19 @@ public:
*/
std::unique_ptr<Picture> access(std::unique_ptr<Picture> picture, bool(*func)(const Paint* paint)) noexcept;
/**
* @brief Access the Picture scene stree nodes.
*
* @param[in] picture The picture node to traverse the internal scene-tree.
* @param[in] func The callback function calling for every paint nodes of the Picture.
* @param[in] data Data will be passed to callback function.
*
* @return Return the given @p picture instance.
*
* @note The bitmap based picture might not have the scene-tree.
*/
std::unique_ptr<Picture> access(std::unique_ptr<Picture> picture, bool(*func)(const Paint* paint, void* data), void* data) noexcept;
/**
* @brief Creates a new Accessor object.
*

View file

@ -42,6 +42,24 @@ static bool accessChildren(Iterator* it, bool(*func)(const Paint* paint), Iterat
}
static bool accessChildren(Iterator* it, bool(*func)(const Paint* paint, void* data), IteratorAccessor& itrAccessor, void* data)
{
while (auto child = it->next()) {
//Access the child
if (!func(child, data)) return false;
//Access the children of the child
if (auto it2 = itrAccessor.iterator(child)) {
if (!accessChildren(it2, func, itrAccessor, data)) {
delete(it2);
return false;
}
delete(it2);
}
}
return true;
}
/************************************************************************/
/* External Class Implementation */
/************************************************************************/
@ -66,6 +84,26 @@ unique_ptr<Picture> Accessor::access(unique_ptr<Picture> picture, bool(*func)(co
}
unique_ptr<Picture> Accessor::access(unique_ptr<Picture> picture, bool(*func)(const Paint* paint, void* data), void* data) noexcept
{
auto p = picture.get();
if (!p || !func) return picture;
//Use the Preorder Tree-Search
//Root
if (!func(p, data)) return picture;
//Children
IteratorAccessor itrAccessor;
if (auto it = itrAccessor.iterator(p)) {
accessChildren(it, func, itrAccessor, data);
delete(it);
}
return picture;
}
Accessor::~Accessor()
{