/*
- * Copyright (c) 2021 Samsung Electronics Co., Ltd.
+ * Copyright (c) 2024 Samsung Electronics Co., Ltd.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
#include <memory>
// INTERNAL INCLUDES
+#include <dali/devel-api/adaptor-framework/window-devel.h>
#include <dali/public-api/adaptor-framework/timer.h>
using namespace Dali::Accessibility;
if(functor)
{
functor();
- functor = {};
+ functor = {};
countdown = countdownBase;
}
else
void BridgeBase::ForceDown()
{
Bridge::ForceDown();
+ tickTimer.Reset();
+ mCoalescableMessages.clear();
mRegistry = {};
mDbusServer = {};
mConnectionPtr = {};
}
}
-void BridgeBase::RegisterDefaultLabel(Accessible* object)
+void BridgeBase::CompressDefaultLabels()
{
- if(std::find(mDefaultLabels.begin(), mDefaultLabels.end(), object) == mDefaultLabels.end())
- {
- mDefaultLabels.push_back(object);
- }
+ // Remove entries for objects which no longer exist
+ mDefaultLabels.remove_if([](const DefaultLabelType& label) {
+ // Check 1) window's weak handle; 2) accessible's ref object
+ return !label.first.GetBaseHandle() || label.second.expired();
+ });
}
-void BridgeBase::UnregisterDefaultLabel(Accessible* object)
+void BridgeBase::RegisterDefaultLabel(std::shared_ptr<Accessible> object)
{
- auto it = std::find(mDefaultLabels.begin(), mDefaultLabels.end(), object);
- if(it != mDefaultLabels.end())
+ CompressDefaultLabels();
+
+ Dali::WeakHandle<Dali::Window> window = GetWindow(object.get());
+ if(!window.GetBaseHandle()) // true also if `object` is null
+ {
+ DALI_LOG_ERROR("Cannot register default label: object does not belong to any window");
+ return;
+ }
+
+ auto it = std::find_if(mDefaultLabels.begin(), mDefaultLabels.end(), [&object](const DefaultLabelType& label) {
+ auto labelPtr = label.second.lock();
+ return labelPtr && object == labelPtr;
+ });
+
+ if(it == mDefaultLabels.end())
{
- mDefaultLabels.erase(it);
+ mDefaultLabels.push_back({window, object});
+ }
+ else if(it->first != window)
+ {
+ // TODO: Tentative implementation. It is yet to be specified what should happen
+ // when the same object is re-registered as a default label for another window.
+ *it = {window, object};
+ }
+ else // it->first == window && it->second == object
+ {
+ // Nothing to do
}
}
-Accessible* BridgeBase::GetDefaultLabel(Accessible* root) const
+void BridgeBase::UnregisterDefaultLabel(std::shared_ptr<Accessible> object)
{
- // TODO (multi-window support): Change mDefaultLabels to a collection of vectors
- // (one per window) and select the right one based on the window that 'root' belongs to.
- return mDefaultLabels.empty() ? root : mDefaultLabels.back();
+ CompressDefaultLabels();
+
+ mDefaultLabels.remove_if([&object](const DefaultLabelType& label) {
+ auto labelPtr = label.second.lock();
+ return labelPtr && object == labelPtr;
+ });
+}
+
+Accessible* BridgeBase::GetDefaultLabel(Accessible* root)
+{
+ CompressDefaultLabels();
+
+ Dali::WeakHandle<Dali::Window> window = GetWindow(root);
+ if(!window.GetBaseHandle())
+ {
+ return root;
+ }
+
+ auto it = std::find_if(mDefaultLabels.rbegin(), mDefaultLabels.rend(), [&window](const DefaultLabelType& label) {
+ return window == label.first;
+ });
+
+ Accessible* rawPtr = root;
+ if(it != mDefaultLabels.rend())
+ {
+ if(auto labelPtr = it->second.lock())
+ {
+ rawPtr = labelPtr.get();
+ }
+ }
+
+ return rawPtr;
}
std::string BridgeBase::StripPrefix(const std::string& path)
}
auto it = mData->mKnownObjects.find(static_cast<Accessible*>(accessible));
- if(it == mData->mKnownObjects.end() || (*it)->IsHidden())
+ if(it == mData->mKnownObjects.end() || (!mApplication.mShouldIncludeHidden && (*it)->IsHidden()))
{
throw std::domain_error{"unknown object '" + path + "'"};
}
item->GetDescription(),
item->GetStates().GetRawData());
}
+
+Dali::WeakHandle<Dali::Window> BridgeBase::GetWindow(Dali::Accessibility::Accessible* accessible)
+{
+ Dali::WeakHandle<Dali::Window> windowHandle;
+ Dali::Actor actor = accessible ? accessible->GetInternalActor() : Dali::Actor();
+
+ if(actor)
+ {
+ Dali::Window window = Dali::DevelWindow::Get(actor);
+ windowHandle = {window};
+ }
+
+ return windowHandle;
+}