summaryrefslogtreecommitdiffstats
path: root/testing/web-platform/tests/css/css-anchor-position/try-tactic-anchor.html
diff options
context:
space:
mode:
Diffstat (limited to 'testing/web-platform/tests/css/css-anchor-position/try-tactic-anchor.html')
-rw-r--r--testing/web-platform/tests/css/css-anchor-position/try-tactic-anchor.html260
1 files changed, 260 insertions, 0 deletions
diff --git a/testing/web-platform/tests/css/css-anchor-position/try-tactic-anchor.html b/testing/web-platform/tests/css/css-anchor-position/try-tactic-anchor.html
new file mode 100644
index 0000000000..8dc45dc6e8
--- /dev/null
+++ b/testing/web-platform/tests/css/css-anchor-position/try-tactic-anchor.html
@@ -0,0 +1,260 @@
+<!DOCTYPE html>
+<title>CSS Anchor Positioning: try-tactic, anchor()</title>
+<link rel="help" href="https://drafts.csswg.org/css-anchor-position-1/#typedef-position-try-options-try-tactic">
+<script src="/resources/testharness.js"></script>
+<script src="/resources/testharnessreport.js"></script>
+<style>
+ :root {
+ --anchor-left:anchor(left);
+ }
+ #cb {
+ position: absolute;
+ width: 400px;
+ height: 400px;
+ border: 1px solid black;
+ }
+ #anchor {
+ position: absolute;
+ left: 150px;
+ top: 150px;
+ width: 60px;
+ height: 70px;
+ background-color: coral;
+ anchor-name: --a;
+ }
+ #target, #ref {
+ position: absolute;
+ left: 450px; /* force fallback */
+ width: 40px;
+ height: 40px;
+ background-color: skyblue;
+ position-anchor: --a;
+ }
+ #ref {
+ background-color: seagreen;
+ }
+</style>
+<style id=style>
+</style>
+<div id=cb>
+ <div id=anchor></div>
+ <div id=target></div>
+ <div id=ref></div>
+</div>
+<script>
+
+// Verify that a given try-tactic + untransformed declaration equals
+// a reference element using `transformed` directly.
+function test_anchor_flip(try_tactic, untransformed, transformed) {
+ test((t) => {
+ style.textContent = `
+ @position-try --pf {
+ inset: auto;
+ ${untransformed}
+ }
+ #target {
+ position-try-options: --pf ${try_tactic};
+ }
+ @position-try --ref {
+ inset: auto;
+ ${transformed}
+ }
+ #ref {
+ position-try-options: --ref;
+ }
+ `;
+ assert_equals(target.offsetLeft, ref.offsetLeft, 'offsetLeft');
+ assert_equals(target.offsetTop, ref.offsetTop, 'offsetTop');
+ }, `${try_tactic}, ${untransformed}, ${transformed}`);
+}
+
+// These are the possible transformations between
+// anchor(left/right/top/bottom):
+//
+// ┌───┬────┬────┬────┬────┐
+// │ - │ L │ R │ T │ B │
+// │ L │ - │ LR │ LT │ LB │
+// │ R │ RL │ - │ RT │ RB │
+// │ T │ TL │ TR │ - │ TB │
+// │ B │ BL │ BR │ BT │ - │
+// └───┴────┴────┴────┴────┘
+
+// No flip, no transformation.
+test_anchor_flip('', 'right:anchor(left)', 'right:anchor(left)');
+
+// flip-block does not affect left-right.
+test_anchor_flip('flip-block', 'right:anchor(left)', 'right:anchor(left)');
+// flip-inline does not affect left-right.
+test_anchor_flip('flip-inline', 'bottom:anchor(top)', 'bottom:anchor(top)');
+
+// Note that the letters represent the arguments to the anchor() functions,
+// not the properties. For example, LR: anchor(left) => anchor(right).
+
+// LR
+test_anchor_flip('flip-inline', 'right:anchor(left)', 'left:anchor(right)');
+// RL
+test_anchor_flip('flip-inline', 'left:anchor(right)', 'right:anchor(left)');
+
+// LT
+test_anchor_flip('flip-start', 'right:anchor(left)', 'bottom:anchor(top)');
+// TL
+test_anchor_flip('flip-start', 'bottom:anchor(top)', 'right:anchor(left)');
+
+// LB
+test_anchor_flip('flip-inline flip-start', 'right:anchor(left)', 'top:anchor(bottom)');
+// BL
+test_anchor_flip('flip-start flip-inline', 'top:anchor(bottom)', 'right:anchor(left)');
+
+// RT
+test_anchor_flip('flip-start flip-block', 'left:anchor(right)', 'bottom:anchor(top)');
+// TR
+test_anchor_flip('flip-block flip-start', 'bottom:anchor(top)', 'left:anchor(right)');
+
+// RB
+test_anchor_flip('flip-start', 'left:anchor(right)', 'top:anchor(bottom)');
+// BR
+test_anchor_flip('flip-start', 'top:anchor(bottom)', 'left:anchor(right)');
+
+// TB
+test_anchor_flip('flip-block', 'bottom:anchor(top)', 'top:anchor(bottom)');
+// BT
+test_anchor_flip('flip-block', 'top:anchor(bottom)', 'bottom:anchor(top)');
+
+// Logical versions.
+//
+// These tests duplicate the above, but replace the input logical anchor()
+// functions.
+
+// LR
+test_anchor_flip('flip-inline', 'right:anchor(start)', 'left:anchor(right)');
+// RL
+test_anchor_flip('flip-inline', 'left:anchor(end)', 'right:anchor(left)');
+
+// LT
+test_anchor_flip('flip-start', 'right:anchor(start)', 'bottom:anchor(top)');
+// TL
+test_anchor_flip('flip-start', 'bottom:anchor(start)', 'right:anchor(left)');
+
+// LB
+test_anchor_flip('flip-inline flip-start', 'right:anchor(start)', 'top:anchor(bottom)');
+// BL
+test_anchor_flip('flip-start flip-inline', 'top:anchor(end)', 'right:anchor(left)');
+
+// RT
+test_anchor_flip('flip-start flip-block', 'left:anchor(end)', 'bottom:anchor(top)');
+// TR
+test_anchor_flip('flip-block flip-start', 'bottom:anchor(start)', 'left:anchor(right)');
+
+// RB
+test_anchor_flip('flip-start', 'left:anchor(end)', 'top:anchor(bottom)');
+// BR
+test_anchor_flip('flip-start', 'top:anchor(end)', 'left:anchor(right)');
+
+// TB
+test_anchor_flip('flip-block', 'bottom:anchor(start)', 'top:anchor(bottom)');
+// BT
+test_anchor_flip('flip-block', 'top:anchor(end)', 'bottom:anchor(top)');
+
+// The same again, except with self-start/self-end.
+
+// LR
+test_anchor_flip('flip-inline', 'right:anchor(self-start)', 'left:anchor(right)');
+// RL
+test_anchor_flip('flip-inline', 'left:anchor(self-end)', 'right:anchor(left)');
+
+// LT
+test_anchor_flip('flip-start', 'right:anchor(self-start)', 'bottom:anchor(top)');
+// TL
+test_anchor_flip('flip-start', 'bottom:anchor(self-start)', 'right:anchor(left)');
+
+// LB
+test_anchor_flip('flip-inline flip-start', 'right:anchor(self-start)', 'top:anchor(bottom)');
+// BL
+test_anchor_flip('flip-start flip-inline', 'top:anchor(self-end)', 'right:anchor(left)');
+
+// RT
+test_anchor_flip('flip-start flip-block', 'left:anchor(self-end)', 'bottom:anchor(top)');
+// TR
+test_anchor_flip('flip-block flip-start', 'bottom:anchor(self-start)', 'left:anchor(right)');
+
+// RB
+test_anchor_flip('flip-start', 'left:anchor(self-end)', 'top:anchor(bottom)');
+// BR
+test_anchor_flip('flip-start', 'top:anchor(self-end)', 'left:anchor(right)');
+
+// TB
+test_anchor_flip('flip-block', 'bottom:anchor(self-start)', 'top:anchor(bottom)');
+// BT
+test_anchor_flip('flip-block', 'top:anchor(self-end)', 'bottom:anchor(top)');
+
+
+function test_anchor_size_flip(try_tactic, flip_expected) {
+ test((t) => {
+ style.textContent = `
+ @position-try --pf {
+ inset: auto;
+ width: calc(anchor-size(width) + 20px);
+ height: anchor-size(height);
+ }
+ #target {
+ position-try-options: --pf ${try_tactic};
+ }
+ `;
+
+ let expected_width = anchor.offsetWidth + (flip_expected ? 0 : 20);
+ let expected_height = anchor.offsetHeight + (flip_expected ? 20 : 0);
+
+ assert_equals(target.offsetWidth, expected_width, 'offsetWidth');
+ assert_equals(target.offsetHeight, expected_height, 'offsetHeight');
+ }, try_tactic);
+}
+
+// No flip, no transformation.
+test_anchor_size_flip('', /* expect_flip */ false);
+
+// Note: only the cross-axis flips cause width/height to change.
+// LR, TB (and their reverse versions) are in-axis, other combinations are
+// cross-axis.
+
+// In-axis:
+
+// LR, RL
+test_anchor_size_flip('flip-inline', /* expect_flip */ false);
+// TB, BT
+test_anchor_size_flip('flip-block', /* expect_flip */ false);
+
+// Cross-axis:
+
+// LT, TL, RB, BR
+test_anchor_size_flip('flip-start', /* expect_flip */ true);
+
+// LB, BL
+test_anchor_size_flip('flip-inline flip-start', /* expect_flip */ true);
+
+// RT, TR
+test_anchor_size_flip('flip-start flip-block', /* expect_flip */ true);
+
+
+test((t) => {
+ style.textContent = `
+ @position-try --pf {
+ inset: auto;
+ right: var(--anchor-left);
+ }
+ #target {
+ position-try-options: --pf;
+ }
+ `;
+ // Initially positioned to the left of the anchor.
+ assert_equals(target.offsetLeft, 110, 'offsetLeft');
+
+ // Now positioned to the right of the anchor.
+ style.textContent += `
+ #target {
+ position-try-options: --pf flip-inline;
+ }
+ `;
+ assert_equals(target.offsetLeft, 210, 'offsetLeft');
+}, 'Can transform a value post-var-substitution');
+
+</script>