// File: /workspace/github_cpp_makefile_star2_O3/Ciaxur[P]yagb-emu/include/imgui/imgui.cpp
// Function: ImGui::NavScoreItem(ImGuiNavMoveResult*, ImRect)
static bool ImGui::NavScoreItem(ImGuiNavMoveResult* result, ImRect cand)
{
    ImGuiContext& g = *GImGui;
    ImGuiWindow* window = g.CurrentWindow;
    if (g.NavLayer != window->DC.NavLayerCurrent)
        return false;

    const ImRect& curr = g.NavScoringRect; // Current modified source rect (NB: we've applied Max.x = Min.x in NavUpdate() to inhibit the effect of having varied item width)
    g.NavScoringCount++;

    // When entering through a NavFlattened border, we consider child window items as fully clipped for scoring
    if (window->ParentWindow == g.NavWindow)
    {
        IM_ASSERT((window->Flags | g.NavWindow->Flags) & ImGuiWindowFlags_NavFlattened);
        if (!window->ClipRect.Overlaps(cand))
            return false;
        cand.ClipWithFull(window->ClipRect); // This allows the scored item to not overlap other candidates in the parent window
    }

    // We perform scoring on items bounding box clipped by the current clipping rectangle on the other axis (clipping on our movement axis would give us equal scores for all clipped items)
    // For example, this ensure that items in one column are not reached when moving vertically from items in another column.
    NavClampRectToVisibleAreaForMoveDir(g.NavMoveClipDir, cand, window->ClipRect);

    // Compute distance between boxes
    // FIXME-NAV: Introducing biases for vertical navigation, needs to be removed.
    float dbx = NavScoreItemDistInterval(cand.Min.x, cand.Max.x, curr.Min.x, curr.Max.x);
    float dby = NavScoreItemDistInterval(ImLerp(cand.Min.y, cand.Max.y, 0.2f), ImLerp(cand.Min.y, cand.Max.y, 0.8f), ImLerp(curr.Min.y, curr.Max.y, 0.2f), ImLerp(curr.Min.y, curr.Max.y, 0.8f)); // Scale down on Y to keep using box-distance for vertically touching items
    if (dby != 0.0f && dbx != 0.0f)
        dbx = (dbx / 1000.0f) + ((dbx > 0.0f) ? +1.0f : -1.0f);
    float dist_box = ImFabs(dbx) + ImFabs(dby);

    // Compute distance between centers (this is off by a factor of 2, but we only compare center distances with each other so it doesn't matter)
    float dcx = (cand.Min.x + cand.Max.x) - (curr.Min.x + curr.Max.x);
    float dcy = (cand.Min.y + cand.Max.y) - (curr.Min.y + curr.Max.y);
    float dist_center = ImFabs(dcx) + ImFabs(dcy); // L1 metric (need this for our connectedness guarantee)

    // Determine which quadrant of 'curr' our candidate item 'cand' lies in based on distance
    ImGuiDir quadrant;
    float dax = 0.0f, day = 0.0f, dist_axial = 0.0f;
    if (dbx != 0.0f || dby != 0.0f)
    {
        // For non-overlapping boxes, use distance between boxes
        dax = dbx;
        day = dby;
        dist_axial = dist_box;
        quadrant = ImGetDirQuadrantFromDelta(dbx, dby);
    }
    else if (dcx != 0.0f || dcy != 0.0f)
    {
        // For overlapping boxes with different centers, use distance between centers
        dax = dcx;
        day = dcy;
        dist_axial = dist_center;
        quadrant = ImGetDirQuadrantFromDelta(dcx, dcy);
    }
    else
    {
        // Degenerate case: two overlapping buttons with same center, break ties arbitrarily (note that LastItemId here is really the _previous_ item order, but it doesn't matter)
        quadrant = (window->DC.LastItemId < g.NavId) ? ImGuiDir_Left : ImGuiDir_Right;
    }

#if IMGUI_DEBUG_NAV_SCORING
    char buf[128];
    if (IsMouseHoveringRect(cand.Min, cand.Max))
    {
        ImFormatString(buf, IM_ARRAYSIZE(buf), "dbox (%.2f,%.2f->%.4f)\ndcen (%.2f,%.2f->%.4f)\nd (%.2f,%.2f->%.4f)\nnav %c, quadrant %c", dbx, dby, dist_box, dcx, dcy, dist_center, dax, day, dist_axial, "WENS"[g.NavMoveDir], "WENS"[quadrant]);
        ImDrawList* draw_list = GetForegroundDrawList(window);
        draw_list->AddRect(curr.Min, curr.Max, IM_COL32(255,200,0,100));
        draw_list->AddRect(cand.Min, cand.Max, IM_COL32(255,255,0,200));
        draw_list->AddRectFilled(cand.Max - ImVec2(4, 4), cand.Max + CalcTextSize(buf) + ImVec2(4, 4), IM_COL32(40,0,0,150));
        draw_list->AddText(g.IO.FontDefault, 13.0f, cand.Max, ~0U, buf);
    }
    else if (g.IO.KeyCtrl) // Hold to preview score in matching quadrant. Press C to rotate.
    {
        if (IsKeyPressedMap(ImGuiKey_C)) { g.NavMoveDirLast = (ImGuiDir)((g.NavMoveDirLast + 1) & 3); g.IO.KeysDownDuration[g.IO.KeyMap[ImGuiKey_C]] = 0.01f; }
        if (quadrant == g.NavMoveDir)
        {
            ImFormatString(buf, IM_ARRAYSIZE(buf), "%.0f/%.0f", dist_box, dist_center);
            ImDrawList* draw_list = GetForegroundDrawList(window);
            draw_list->AddRectFilled(cand.Min, cand.Max, IM_COL32(255, 0, 0, 200));
            draw_list->AddText(g.IO.FontDefault, 13.0f, cand.Min, IM_COL32(255, 255, 255, 255), buf);
        }
    }
#endif

    // Is it in the quadrant we're interesting in moving to?
    bool new_best = false;
    if (quadrant == g.NavMoveDir)
    {
        // Does it beat the current best candidate?
        if (dist_box < result->DistBox)
        {
            result->DistBox = dist_box;
            result->DistCenter = dist_center;
            return true;
        }
        if (dist_box == result->DistBox)
        {
            // Try using distance between center points to break ties
            if (dist_center < result->DistCenter)
            {
                result->DistCenter = dist_center;
                new_best = true;
            }
            else if (dist_center == result->DistCenter)
            {
                // Still tied! we need to be extra-careful to make sure everything gets linked properly. We consistently break ties by symbolically moving "later" items
                // (with higher index) to the right/downwards by an infinitesimal amount since we the current "best" button already (so it must have a lower index),
                // this is fairly easy. This rule ensures that all buttons with dx==dy==0 will end up being linked in order of appearance along the x axis.
                if (((g.NavMoveDir == ImGuiDir_Up || g.NavMoveDir == ImGuiDir_Down) ? dby : dbx) < 0.0f) // moving bj to the right/down decreases distance
                    new_best = true;
            }
        }
    }

    // Axial check: if 'curr' has no link at all in some direction and 'cand' lies roughly in that direction, add a tentative link. This will only be kept if no "real" matches
    // are found, so it only augments the graph produced by the above method using extra links. (important, since it doesn't guarantee strong connectedness)
    // This is just to avoid buttons having no links in a particular direction when there's a suitable neighbor. you get good graphs without this too.
    // 2017/09/29: FIXME: This now currently only enabled inside menu bars, ideally we'd disable it everywhere. Menus in particular need to catch failure. For general navigation it feels awkward.
    // Disabling it may lead to disconnected graphs when nodes are very spaced out on different axis. Perhaps consider offering this as an option?
    if (result->DistBox == FLT_MAX && dist_axial < result->DistAxial)  // Check axial match
        if (g.NavLayer == ImGuiNavLayer_Menu && !(g.NavWindow->Flags & ImGuiWindowFlags_ChildMenu))
            if ((g.NavMoveDir == ImGuiDir_Left && dax < 0.0f) || (g.NavMoveDir == ImGuiDir_Right && dax > 0.0f) || (g.NavMoveDir == ImGuiDir_Up && day < 0.0f) || (g.NavMoveDir == ImGuiDir_Down && day > 0.0f))
            {
                result->DistAxial = dist_axial;
                new_best = true;
            }

    return new_best;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
pushq %rbx
subq $0x18, %rsp
movlps %xmm0, -0x18(%rbp)
movlps %xmm1, -0x10(%rbp)
movq 0x9f301(%rip), %rax     # 0xfbcd0
movq 0x1ae0(%rax), %rsi
movl 0x1cdc(%rax), %ecx
cmpl 0x14c(%rsi), %ecx
jne 0x5cb11
movaps %xmm0, %xmm5
shufps $0x55, %xmm0, %xmm5     # xmm5 = xmm5[1,1],xmm0[1,1]
movaps %xmm1, %xmm3
incl 0x1cd8(%rax)
shufps $0x55, %xmm1, %xmm3     # xmm3 = xmm3[1,1],xmm1[1,1]
movq 0x1c90(%rax), %rdx
cmpq %rdx, 0x388(%rsi)
je 0x5ca46
movaps %xmm3, %xmm2
movaps %xmm5, %xmm4
leaq 0x258(%rsi), %r10
cmpl $0x1, 0x1d18(%rax)
ja 0x5cb1a
leaq -0xc(%rbp), %r8
leaq -0x14(%rbp), %r9
leaq 0x25c(%rsi), %rbx
movl $0xc, %r11d
movaps %xmm2, %xmm1
movaps %xmm4, %xmm0
jmp 0x5cb2b
movl 0xc(%rdx), %r8d
orl 0xc(%rsi), %r8d
btl $0x17, %r8d
jae 0x5ce22
movss 0x264(%rsi), %xmm2
ucomiss %xmm5, %xmm2
jbe 0x5cb11
movss 0x25c(%rsi), %xmm2
ucomiss %xmm2, %xmm3
jbe 0x5cb11
movss 0x260(%rsi), %xmm4
ucomiss %xmm0, %xmm4
jbe 0x5cb11
movss 0x258(%rsi), %xmm6
ucomiss %xmm6, %xmm1
jbe 0x5cb11
ucomiss %xmm5, %xmm2
movsd 0x260(%rsi), %xmm7
movaps %xmm7, %xmm8
shufps $0x55, %xmm7, %xmm8     # xmm8 = xmm8[1,1],xmm7[1,1]
movaps %xmm2, %xmm4
ja 0x5caba
movaps %xmm8, %xmm4
minss %xmm5, %xmm4
movaps %xmm7, %xmm5
minss %xmm0, %xmm5
cmpltss %xmm6, %xmm0
movaps %xmm0, %xmm9
andnps %xmm5, %xmm9
andps %xmm6, %xmm0
orps %xmm9, %xmm0
movaps %xmm0, %xmm5
unpcklps %xmm4, %xmm5            # xmm5 = xmm5[0],xmm4[0],xmm5[1],xmm4[1]
movlps %xmm5, -0x18(%rbp)
ucomiss %xmm3, %xmm2
ja 0x5caed
minss %xmm3, %xmm8
movaps %xmm8, %xmm2
minss %xmm1, %xmm7
cmpltss %xmm6, %xmm1
movaps %xmm1, %xmm3
andnps %xmm7, %xmm3
andps %xmm6, %xmm1
orps %xmm3, %xmm1
movaps %xmm1, %xmm3
unpcklps %xmm2, %xmm3            # xmm3 = xmm3[0],xmm2[0],xmm3[1],xmm2[1]
movlps %xmm3, -0x10(%rbp)
jmp 0x5ca12
xorl %eax, %eax
addq $0x18, %rsp
popq %rbx
popq %rbp
retq
leaq -0x18(%rbp), %r9
movl $0x8, %r11d
leaq -0x10(%rbp), %r8
movq %r10, %rbx
movss (%rbx), %xmm2
movss (%r10,%r11), %xmm3
movaps %xmm3, %xmm4
minss %xmm0, %xmm4
cmpltss %xmm2, %xmm0
movaps %xmm0, %xmm5
andnps %xmm4, %xmm5
andps %xmm2, %xmm0
orps %xmm5, %xmm0
movss %xmm0, (%r9)
minss %xmm1, %xmm3
cmpltss %xmm2, %xmm1
movaps %xmm1, %xmm0
andnps %xmm3, %xmm0
andps %xmm2, %xmm1
orps %xmm0, %xmm1
movss %xmm1, (%r8)
movss -0x18(%rbp), %xmm0
movss -0x10(%rbp), %xmm5
movss 0x1cc8(%rax), %xmm4
movss 0x1cd0(%rax), %xmm6
ucomiss %xmm5, %xmm4
jbe 0x5cb94
movaps %xmm5, %xmm2
subss %xmm4, %xmm2
jmp 0x5cba3
xorps %xmm2, %xmm2
ucomiss %xmm6, %xmm0
jbe 0x5cba3
movaps %xmm0, %xmm2
subss %xmm6, %xmm2
movss -0x14(%rbp), %xmm1
movss -0xc(%rbp), %xmm8
movaps %xmm8, %xmm7
subss %xmm1, %xmm7
movss 0x58441(%rip), %xmm13   # 0xb5000
movss 0x58d2c(%rip), %xmm11   # 0xb58f4
movaps %xmm7, %xmm3
mulss %xmm11, %xmm3
addss %xmm1, %xmm3
movss 0x1ccc(%rax), %xmm9
movss 0x1cd4(%rax), %xmm10
movaps %xmm10, %xmm12
subss %xmm9, %xmm12
movaps %xmm12, %xmm14
mulss %xmm13, %xmm14
addss %xmm9, %xmm14
ucomiss %xmm3, %xmm14
jbe 0x5cc0a
subss %xmm14, %xmm3
jmp 0x5cc2b
mulss %xmm13, %xmm7
addss %xmm1, %xmm7
mulss %xmm11, %xmm12
addss %xmm9, %xmm12
ucomiss %xmm12, %xmm7
jbe 0x5cc73
subss %xmm12, %xmm7
movaps %xmm7, %xmm3
xorps %xmm7, %xmm7
movaps %xmm3, %xmm11
cmpneqss %xmm7, %xmm11
movd %xmm11, %r8d
andl $0x1, %r8d
ucomiss %xmm7, %xmm2
jne 0x5cc48
jnp 0x5cc79
ucomiss %xmm7, %xmm3
jne 0x5cc4f
jnp 0x5cc79
xorl %r8d, %r8d
ucomiss %xmm7, %xmm2
seta %r8b
divss 0x58373(%rip), %xmm2    # 0xb4fd4
leaq 0x594cc(%rip), %r9      # 0xb6134
addss (%r9,%r8,4), %xmm2
movb $0x1, %r8b
jmp 0x5cc79
xorps %xmm3, %xmm3
xorl %r8d, %r8d
movaps 0x58b4f(%rip), %xmm11   # 0xb57d0
movaps %xmm2, %xmm12
andps %xmm11, %xmm12
movaps %xmm3, %xmm13
andps %xmm11, %xmm13
movaps %xmm13, %xmm7
addss %xmm12, %xmm7
addss %xmm5, %xmm0
addss %xmm6, %xmm4
subss %xmm4, %xmm0
addss %xmm8, %xmm1
addss %xmm10, %xmm9
subss %xmm9, %xmm1
movaps %xmm0, %xmm6
andps %xmm11, %xmm6
andps %xmm1, %xmm11
movaps %xmm6, %xmm5
addss %xmm11, %xmm5
testb %r8b, %r8b
jne 0x5cd00
xorps %xmm4, %xmm4
ucomiss %xmm4, %xmm2
jne 0x5cd00
jp 0x5cd00
ucomiss %xmm4, %xmm0
jne 0x5cd2c
jp 0x5cd2c
ucomiss %xmm4, %xmm1
jne 0x5cd2c
jp 0x5cd2c
movl 0x124(%rsi), %esi
xorl %r8d, %r8d
cmpl 0x1c98(%rax), %esi
setae %r8b
xorps %xmm0, %xmm0
xorps %xmm1, %xmm1
jmp 0x5cd4d
xorps %xmm0, %xmm0
xorl %r8d, %r8d
ucomiss %xmm0, %xmm2
seta %r8b
xorl %esi, %esi
ucomiss %xmm0, %xmm3
seta %sil
orl $0x2, %esi
ucomiss %xmm13, %xmm12
cmovbel %esi, %r8d
movaps %xmm2, %xmm0
movaps %xmm3, %xmm1
movaps %xmm7, %xmm4
jmp 0x5cd4d
xorl %r8d, %r8d
ucomiss %xmm4, %xmm0
seta %r8b
xorl %esi, %esi
ucomiss %xmm4, %xmm1
seta %sil
orl $0x2, %esi
ucomiss %xmm11, %xmm6
cmovbel %esi, %r8d
movaps %xmm5, %xmm4
movl 0x1d10(%rax), %esi
movss 0x10(%rdi), %xmm6
cmpl %esi, %r8d
jne 0x5cda5
ucomiss %xmm7, %xmm6
jbe 0x5cd71
movss %xmm7, 0x10(%rdi)
movss %xmm5, 0x14(%rdi)
jmp 0x5ce1b
ucomiss %xmm6, %xmm7
jne 0x5cda5
jp 0x5cda5
movss 0x14(%rdi), %xmm7
ucomiss %xmm5, %xmm7
jbe 0x5cd89
movss %xmm5, 0x14(%rdi)
jmp 0x5cda1
ucomiss %xmm7, %xmm5
jne 0x5cda5
jp 0x5cda5
testb $0x2, %r8b
jne 0x5cd99
movaps %xmm2, %xmm3
xorps %xmm2, %xmm2
ucomiss %xmm3, %xmm2
jbe 0x5cda5
movb $0x1, %al
jmp 0x5cda7
xorl %eax, %eax
ucomiss 0x58a92(%rip), %xmm6    # 0xb5840
jne 0x5cb13
jp 0x5cb13
cmpl $0x1, %ecx
jne 0x5cb13
movss 0x18(%rdi), %xmm2
ucomiss %xmm4, %xmm2
jbe 0x5cb13
testb $0x10, 0xf(%rdx)
jne 0x5cb13
testl %esi, %esi
jne 0x5cde7
xorps %xmm2, %xmm2
ucomiss %xmm0, %xmm2
ja 0x5ce16
cmpl $0x1, %esi
jne 0x5cdf4
xorps %xmm2, %xmm2
ucomiss %xmm2, %xmm0
ja 0x5ce16
cmpl $0x2, %esi
jne 0x5ce01
xorps %xmm0, %xmm0
ucomiss %xmm1, %xmm0
ja 0x5ce16
cmpl $0x3, %esi
jne 0x5cb13
xorps %xmm0, %xmm0
ucomiss %xmm0, %xmm1
jbe 0x5cb13
movss %xmm4, 0x18(%rdi)
movb $0x1, %al
jmp 0x5cb13
leaq 0x5d39f(%rip), %rdi     # 0xba1c8
leaq 0x59335(%rip), %rsi     # 0xb6165
leaq 0x5d3d6(%rip), %rcx     # 0xba20d
movl $0x20fb, %edx           # imm = 0x20FB
callq 0xc140