winforms 如何知道用户何时可以使用强制的ScrollBar滚动RichTextBox

w8rqjzmb  于 2022-11-16  发布在  其他
关注(0)|答案(1)|浏览(171)

我 需要 将 ScrollBars 设置 为 ForcedBoth , 但 我 还 想 知道 ScrollBars 的 句柄 何时 可见 以及 用户 何时 可以 滚动 。
两 个 滚动 条 的 布尔 值
此处 用户 无法 滚动 :

在 这里 , 他们 可以 :

我 正在 尝试 创建 从 RichTextBox 派生 的 自 定义 滚动 条 。
我 通过 在 原始 滚动 条 上 覆盖 面板 并 禁用 它们 ( 这样 你 就 可以 使用 原始 滚动 条 ) , 同时 获得 不同 的 视觉 效果 ( 覆盖 的 面板 ) 。
我 让 一切 工作 , 除了 我 需要 禁用 其中 一 个 面板 ( 句柄 面板 ) 时 , RichTextBox 的 滚动 条 被 禁用 。
我 尝试 了 Win32 API 中 的 GetScrollInfo , 但 在 放大 RichTextBox 或 一 次 删除 一 堆 行 时 , 结果 不 一致 。

b5buobof

b5buobof1#

如果这确实是您需要了解的有关RichTextBox的ScrollBars状态的信息,请使用GetScrollBarInfo()获取此信息,然后测试存储在返回的SCROLLBARINFO结构的rgstate组件中的值。

  • 当ScrollBar被禁用时,rgstate[0]被设置为STATE_SYSTEM_UNAVAILABLE;在这种情况下,索引2处值(页面元素)应设置为STATE_SYSTEM_INVISIBLE
  • 当ScrollBar不存在时,相同的值为STATE_SYSTEM_INVISIBLE
  • 否则为0(此处设置为SBIdObj.STATE_SYSTEM_AVAILABLE = 0x00000000

可用于测试ScrollBars的示例方法。将其称为,例如:

var result = GetScrollBarsState(myRichTextBox.Handle);

它返回一个命名元组,其中两个ScrollBar的状态都设置为当前的SBIdObj

public (SBRgState Vertical, SBRgState Horizontal) GetScrollBarsState(IntPtr controlHandle)
{
    var sbi = new SCROLLBARINFO() { cbSize = Marshal.SizeOf<SCROLLBARINFO>() };

    bool result = GetScrollBarInfo(controlHandle, SBIdObj.OBJID_VSCROLL, ref sbi);
    if (!result) throw new Exception("Failed to retrieve vertical ScrollBar info");
    var vert = (SBRgState)sbi.rgstate[0];

    result = GetScrollBarInfo(controlHandle, SBIdObj.OBJID_HSCROLL, ref sbi);
    if (!result) throw new Exception("Failed to retrieve horizontal ScrollBar info");
    var horz = (SBRgState)sbi.rgstate[0];
    return (vert, horz);
}

声明:

[DllImport("User32.dll", CharSet = CharSet.Auto, SetLastError = true)]
internal static extern bool GetScrollBarInfo(IntPtr hWnd, SBIdObj idObject, ref SCROLLBARINFO psbi);

[StructLayout(LayoutKind.Sequential)]
public struct SCROLLBARINFO {
    public int cbSize;
    public Rectangle rcScrollBar;
    public int dxyLineButton;
    public int xyThumbTop;
    public int xyThumbBottom;
    public int reserved;
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 6)]
    public int[] rgstate;
}

// GetScrollBarInfo idObject
public enum SBIdObj : uint {
    OBJID_HSCROLL = 0xFFFFFFFA,
    OBJID_VSCROLL = 0xFFFFFFFB,
    OBJID_CLIENT = 0xFFFFFFFC
}

// SCROLLBARINFO rgstate flags
[Flags]
public enum SBRgState {
    STATE_SYSTEM_AVAILABLE = 0x00000000,
    STATE_SYSTEM_UNAVAILABLE = 0x00000001,
    STATE_SYSTEM_PRESSED = 0x00000008,
    STATE_SYSTEM_INVISIBLE = 0x00008000,
    STATE_SYSTEM_OFFSCREEN = 0x00010000,
}

相关问题