Skip to content

Version 1.0.0

Choose a tag to compare

@github-actions github-actions released this 08 Sep 12:22
· 6 commits to master since this release
v1.0.0
cdc61c0

First stable release. The public API is settled; see the versioning note above.

Added

  • NativeListView follows the system theme, which is a consequence of the above rather than a
    separate feature. Left alone the colors resolve through SystemColors, which WinForms remaps
    for the application's color mode, so the list now goes dark with the rest of a dark-mode
    application and honors a high-contrast theme. Previously nothing was pushed at all and the
    control fell back on the raw GetSysColor(COLOR_WINDOW), which stays white however the
    application is themed — a white list in a dark window. The visual style is chosen to match
    (DarkMode_Explorer rather than Explorer), without which the header, the scroll bars and
    the hover highlight stay light on an otherwise dark list, and both are re-applied on
    WM_SYSCOLORCHANGE so a theme switched while the application is running is followed.
  • NativeListViewColumn.Alignment is settable rather than constructor-only, which is what
    every other column property already was. Assigning it preserves the sort arrow, which shares
    the same Win32 format word and a plain write would have cleared. Like Width, it reads back
    from the control while the column is in one, so it cannot drift from what the control holds.
  • A runnable sample application under samples/, and a listening script beside it, so the
    claims this library makes about screen readers can be checked rather than taken on trust. It
    carries an English and a Hebrew catalog with a language switch, so the right-to-left support -
    previously the least verified part of the library - can be exercised against real
    right-to-left text and real non-Latin mnemonics rather than a mirrored English layout.
  • Designer metadata on NativeListView: categories and descriptions on its properties and
    events, so they no longer land under Misc in the Properties window with no explanation.
  • Parameter and return documentation across the public API. Every public member already had a
    summary, which is all the compiler checks; what a caller sees in a signature help popup is
    the parameter list, and that was blank.
  • Package icon and package title.

Changed

  • Breaking. ContextMenuRequest is now NativeContextMenuRequest, so every public type in
    the menu API carries the same prefix.
  • Breaking. NativeListViewColumn rejects a null header text rather than silently treating
    it as empty, which is the policy the menu API already had.
  • Breaking. NativeListView.SetInsertionMark and ClearInsertionMark are removed. They
    never worked: Win32 does not support an insertion mark in report view, which is the only view
    this control has, so LVM_SETINSERTMARK returned FALSE and the control stored nothing. A
    method that silently does nothing is worse than no method. Draw a drop indicator from
    GetItemBounds, which reports the row rectangle for exactly that purpose.
  • NativeListViewColumn.Width, Alignment and SortOrder all read back from the control while
    the column is in one, so none of them can drift from what the control actually holds.
  • Breaking. AccelConverter.ConvertKey returns a named AcceleratorEntry struct rather
    than a bare tuple, whose element names are compiler metadata a generic signature can lose.
  • Breaking. MenuSpecValidator.Validate throws ArgumentException rather than
    InvalidOperationException for a malformed spec. The spec is the argument, and
    ArgumentException is what a caller's exception filter will be written against.
  • AssemblyVersion is pinned to {Major}.0.0.0 rather than tracking the patch number, so a
    patch release no longer changes the binding identity. FileVersion and InformationalVersion
    still carry the full version.

Fixed

  • Menu tracking is per-thread rather than per-process. TrackPopupMenuEx runs its nested loop
    on the calling thread and the HMENU it displays belongs to that thread, but the guard that
    stops a menu being rebuilt while it is on screen used a process-wide counter. WinForms allows
    more than one UI thread, each with its own pump, so a popup open on one of them made
    Rebuild throw on another that had no menu open at all. Found by a test run that failed on
    one machine and passed on another, which is what a race looks like.
  • NativeListView.BackColor and ForeColor did nothing. The list window paints itself, and
    nothing was ever pushed across; they are now applied with LVM_SETBKCOLOR,
    LVM_SETTEXTBKCOLOR and LVM_SETTEXTCOLOR. Both default to the window colors rather than
    inheriting the parent's dialog gray, matching what a WinForms ListView does, and assigning
    Color.Empty resets them.
  • Menu accelerators now decide whether a keystroke is theirs by asking whether the message is
    aimed at the owning form or anything inside it, rather than by consulting Form.ActiveForm.
    That property answers a different question and got this one wrong in two shipping cases: for
    an MDI child it names the MDI parent, so a child's own menu bar never fired; and it is null
    whenever the active window is not a WinForms Form, which is the normal state of a mixed WPF
    or native host. Modal dialogs are still excluded, because a dialog is owned by the form but is
    not a child of it. This removes the last of the limitations previously tracked for 1.0.
  • A keyboard-invoked NativeContextMenu now anchors at the focused row of a NativeListView,
    as it already did for a WinForms ListView, TreeView and ListBox. NativeListView is a
    Control rather than a ListView, so it had been falling through to the control's top-left
    corner — the library's own list control was the one case its context menus did not know about.
  • Clearing NativeListView.AccessibleName now reaches the list window. The name was only ever
    pushed when non-empty, so a reader went on announcing a name the application had taken away.
  • NativeMenuSpec rejects a null item label at the builder call. It previously survived until
    validation walked the tree for mnemonics, and the exception then named a parameter of a
    formatter the caller never called.