Navigator: fix covering of an explicit UI-Coordinate
...especially to make the anchorage explicit
This commit is contained in:
parent
0ea5583b62
commit
e7ce82d17e
4 changed files with 60 additions and 37 deletions
|
|
@ -31,8 +31,6 @@
|
|||
#include "gui/interact/ui-coord-resolver.hpp"
|
||||
#include "lib/util.hpp"
|
||||
|
||||
#include <boost/noncopyable.hpp>
|
||||
|
||||
using util::isnil;
|
||||
using lib::Symbol;
|
||||
using lib::treeExplore;
|
||||
|
|
|
|||
|
|
@ -159,6 +159,7 @@ namespace interact {
|
|||
* @return the depth to which the given spec is _"covered"_ by the actual UI.
|
||||
* Can be zero, in which case the given coordinates can not be resolved
|
||||
* and addressed within the currently existing windows, panes and views.
|
||||
* @remark a depth > 0 also implies that the path can be _anchored._
|
||||
* @note this operation does not perform any _resolution_ or interpolation of wildcards,
|
||||
* it just matches explicit UI component names.
|
||||
* @see UICoordResolver for a facility to perform such a resolution and to navigate paths.
|
||||
|
|
@ -289,12 +290,22 @@ namespace interact {
|
|||
/* === mutation functions === */
|
||||
|
||||
/** mutate the path to get it totally covered
|
||||
* - make the anchorage explicit
|
||||
* - possibly match and expand any wildcards
|
||||
* - then truncate the UI-Coordinate spec to that part
|
||||
* actually covered by the UI
|
||||
* @note if the coordinate spec can not be covered at all,
|
||||
* it will be truncated to zero size
|
||||
*/
|
||||
UICoordResolver
|
||||
cover()
|
||||
{
|
||||
if (isCoveredPartially() and not res_.covfefe)
|
||||
truncateTo (res_.depth);
|
||||
{
|
||||
ASSERT (res_.anchor); // depth > 0 implies anchorage
|
||||
window (res_.anchor); // thus make this anchor explicit
|
||||
truncateTo (res_.depth);
|
||||
}
|
||||
else if (canCover())
|
||||
{
|
||||
ASSERT (res_.isResolved);
|
||||
|
|
|
|||
|
|
@ -67,6 +67,12 @@ namespace test {
|
|||
|
||||
/******************************************************************************//**
|
||||
* @test verify query and mutation of UICoord in relation to actual UI topology.
|
||||
* A UI-Coordinate resolver is a special builder, which is initialised by
|
||||
* the given coordinate spec, and also attached to a "location query API",
|
||||
* which allows to investigate the current actual UI structure. The builder
|
||||
* then exposes query and mutation operations, to determine to what extent
|
||||
* the coordinate spec is "covered" by the real UI, and to match and expand
|
||||
* any wildcards in the coordinate spec (pattern).
|
||||
*
|
||||
* @see UICoordResolver
|
||||
* @see navigator.hpp
|
||||
|
|
@ -294,7 +300,7 @@ namespace test {
|
|||
|
||||
|
||||
|
||||
/** @test patch matching algorithm to resolve UI coordinates with wildcards against the current UI structure tree.
|
||||
/** @test patch matching algorithm to resolve UI coordinates with wildcards against the current UI structure tree.
|
||||
* Since an UI coordinate path with gaps and wildcards could match anywhere, even several times, we need to perform
|
||||
* an exhaustive search with backtracking over the whole tree. By convention, we use the first maximal solution,
|
||||
* which can be just a partial solution, leaving an additional uncovered trailing part of the UI coordinate spec.
|
||||
|
|
@ -385,47 +391,57 @@ namespace test {
|
|||
CHECK (3 ==r12.coverDepth());
|
||||
CHECK ("UI:window-1[persp-A]-panelX.thirdView" == string(r12));
|
||||
|
||||
auto r12_covered = r12.cover();
|
||||
CHECK (r12_covered.isCovered());
|
||||
CHECK (r12_covered.isCoveredPartially());
|
||||
CHECK (3 ==r12_covered.coverDepth());
|
||||
CHECK ("UI:window-1[persp-A]-panelX" == string(r12_covered));
|
||||
r12.cover();
|
||||
CHECK (r12.isCovered());
|
||||
CHECK (r12.isCoveredPartially());
|
||||
CHECK (3 ==r12.coverDepth());
|
||||
CHECK ("UI:window-1[persp-A]-panelX" == string(r12));
|
||||
|
||||
|
||||
/* === expand anchor === */
|
||||
UICoordResolver r21 {UICoord::firstWindow().persp("persp-A"), tree};
|
||||
cout << r21.cover()<<endl; ///////////////////////////////////////////TODO doesn't work, yields UI:firstWindow[persp-A]
|
||||
CHECK ("UI:firstWindow[persp-A]" == string(r21));
|
||||
r21.cover();
|
||||
CHECK ("UI:window-1[persp-A]" == string(r21));
|
||||
|
||||
/* === expand anchor alone === */
|
||||
UICoordResolver r22 {UICoord::currentWindow(), tree};
|
||||
cout << r22.cover()<<endl; ///////////////////////////////////////////TODO doesn't work, yields UI:currentWindow
|
||||
CHECK ("UI:window-3" == string(r22.cover()));
|
||||
|
||||
|
||||
/* === interpolate a single gap === */
|
||||
UICoordResolver r31 {UICoord::window("window-1").view("secondView"), tree};
|
||||
CHECK("UI:window-1[persp-A]-panelX.secondView" == string(r31.cover()));
|
||||
CHECK ("UI:window-1[*]-*.secondView" == string(r31));
|
||||
CHECK (0 ==r31.coverDepth());
|
||||
CHECK (not r31.isCovered());
|
||||
CHECK (r31.canCover());
|
||||
r31.cover();
|
||||
CHECK (r31.isCovered());
|
||||
CHECK (4 == r31.coverDepth());
|
||||
CHECK ("UI:window-1[persp-A]-panelX.secondView" == string(r31));
|
||||
|
||||
/* === interpolate several gaps === */
|
||||
UICoordResolver r32 {UICoord().view("thirdView").path("sub"), tree};
|
||||
CHECK("UI:window-3[persp-C]-panelZ.thirdView.tab/sub" == string(r32.cover()));
|
||||
CHECK ("UI:window-3[persp-C]-panelZ.thirdView.tab/sub" == string(r32.cover()));
|
||||
|
||||
/* === interpolate anchor and consecutive wildcards === */
|
||||
UICoordResolver r33 {UICoord::firstWindow().tab(2), tree};
|
||||
CHECK("UI:window-1[persp-A]-panelZ.thirdView.#2" == string(r33.cover()));
|
||||
CHECK ("UI:window-1[persp-A]-panelZ.thirdView.#2" == string(r33.cover()));
|
||||
|
||||
/* === discriminate by anchor and fill second gap === */
|
||||
UICoordResolver r34 {UICoord::currentWindow().panel("panelZ").tab("tab"), tree};
|
||||
CHECK("UI:window-3[persp-C]-panelZ.thirdView.tab" == string(r34.cover())); // Note: rest of the path would also match on window-1, but currentWindow == window-3
|
||||
CHECK ("UI:currentWindow[*]-panelZ.*.tab" == string(r34));
|
||||
CHECK ("UI:window-3[persp-C]-panelZ.thirdView.tab" == string(r34.cover())); // Note: rest of the path would also match on window-1, but currentWindow == window-3
|
||||
|
||||
|
||||
/* === trailing wildcards stripped automatically === */
|
||||
UICoordResolver r41 {UICoord::window("window-2").append("*/*"), tree};
|
||||
CHECK("UI:window-2" == string(r41)); // Note: trailing wildcards are already discarded by PathArray / UICoord
|
||||
CHECK ("UI:window-2" == string(r41)); // Note: trailing wildcards are already discarded by PathArray / UICoord
|
||||
|
||||
auto r41_extended = r41.extend("*/*"); // if we now attempt to "sneak in" trailing wildcards...
|
||||
CHECK("UI:window-2[*]-*" == string(r41_extended));
|
||||
CHECK(not r41_extended.canCover()); // ...then the algorithm rejects any solution
|
||||
CHECK("UI:window-2" == string(r41_extended.cover())); // Note: but cover() will act on the previous coverage and just strip the extraneous suffix
|
||||
r41.extend("*/*"); // if we now attempt to "sneak in" trailing wildcards...
|
||||
CHECK ("UI:window-2[*]-*" == string(r41));
|
||||
CHECK (not r41.canCover()); // ...then the algorithm rejects any solution
|
||||
CHECK ("UI:window-2" == string(r41.cover())); // Note: but cover() will act on the previous coverage and just strip the extraneous suffix
|
||||
|
||||
/* === reject gap beyond existing real UI tree === */
|
||||
UICoordResolver r42 {UICoord::window("window-2").append("*/*/*/some/path"), tree};
|
||||
|
|
|
|||
|
|
@ -8766,15 +8766,13 @@
|
|||
<icon BUILTIN="button_ok"/>
|
||||
</node>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#fdfdcf" COLOR="#ff0000" CREATED="1515114713029" ID="ID_424458820" MODIFIED="1515114729586" TEXT="Ankern">
|
||||
<icon BUILTIN="flag-pink"/>
|
||||
<node BACKGROUND_COLOR="#fdfdcf" COLOR="#ff0000" CREATED="1514745345018" ID="ID_1229106293" MODIFIED="1515114727644" TEXT="fehlender Anker allein">
|
||||
<icon BUILTIN="flag-yellow"/>
|
||||
<icon BUILTIN="flag-pink"/>
|
||||
<node COLOR="#338800" CREATED="1515114713029" ID="ID_424458820" MODIFIED="1515204865644" TEXT="Ankern">
|
||||
<icon BUILTIN="button_ok"/>
|
||||
<node COLOR="#338800" CREATED="1514745345018" ID="ID_1229106293" MODIFIED="1515204862321" TEXT="fehlender Anker allein">
|
||||
<icon BUILTIN="button_ok"/>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#fdfdcf" COLOR="#ff0000" CREATED="1515114721228" ID="ID_1329702278" MODIFIED="1515114726603" TEXT="fehlender Anker">
|
||||
<icon BUILTIN="flag-yellow"/>
|
||||
<icon BUILTIN="flag-pink"/>
|
||||
<node COLOR="#338800" CREATED="1515114721228" ID="ID_1329702278" MODIFIED="1515204863932" TEXT="fehlender Anker">
|
||||
<icon BUILTIN="button_ok"/>
|
||||
</node>
|
||||
</node>
|
||||
<node COLOR="#338800" CREATED="1515114740273" ID="ID_224432926" MODIFIED="1515120853113" TEXT="interpolieren">
|
||||
|
|
@ -8855,16 +8853,16 @@
|
|||
</node>
|
||||
</node>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1508540835505" ID="ID_191493714" MODIFIED="1514748460975" TEXT="Zustand">
|
||||
<icon BUILTIN="flag-yellow"/>
|
||||
<node COLOR="#338800" CREATED="1508540835505" ID="ID_191493714" MODIFIED="1515204888544" TEXT="Zustand">
|
||||
<icon BUILTIN="button_ok"/>
|
||||
<node CREATED="1514748438984" ID="ID_84241950" MODIFIED="1514748444387" TEXT="reflektiert letzte Lösung"/>
|
||||
<node CREATED="1514748445520" ID="ID_728061293" MODIFIED="1514748446779" TEXT="swap(*this, Coverage)"/>
|
||||
<node BACKGROUND_COLOR="#fdfdcf" COLOR="#ff0000" CREATED="1514748450687" ID="ID_919694647" MODIFIED="1514748457327" TEXT="default: total">
|
||||
<icon BUILTIN="flag-pink"/>
|
||||
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1514748463645" ID="ID_2814761" MODIFIED="1514748469603" TEXT="TODO: ändern">
|
||||
<icon BUILTIN="flag-yellow"/>
|
||||
<node CREATED="1514748445520" ID="ID_728061293" MODIFIED="1515204926369" TEXT="*this = move (Coverage)"/>
|
||||
<node COLOR="#338800" CREATED="1514748450687" ID="ID_919694647" MODIFIED="1515204876780" TEXT="default: total">
|
||||
<icon BUILTIN="button_ok"/>
|
||||
<node COLOR="#338800" CREATED="1514748463645" ID="ID_2814761" MODIFIED="1515204880477" TEXT="TODO: ändern">
|
||||
<icon BUILTIN="button_ok"/>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1514748505488" ID="ID_947047856" MODIFIED="1514748548523" TEXT="TODO: API umstellen">
|
||||
<node COLOR="#338800" CREATED="1514748505488" ID="ID_947047856" MODIFIED="1515204882332" TEXT="TODO: API umstellen">
|
||||
<richcontent TYPE="NOTE"><html>
|
||||
<head>
|
||||
|
||||
|
|
@ -8882,7 +8880,7 @@
|
|||
</body>
|
||||
</html>
|
||||
</richcontent>
|
||||
<icon BUILTIN="flag-yellow"/>
|
||||
<icon BUILTIN="button_ok"/>
|
||||
</node>
|
||||
</node>
|
||||
</node>
|
||||
|
|
|
|||
Loading…
Reference in a new issue