Skip to content

Add click-to-cast target selection and the original casting flow - #420

Open
RahulDNair wants to merge 7 commits into
vE5li:mainfrom
RahulDNair:click-to-cast
Open

Add click-to-cast target selection and the original casting flow#420
RahulDNair wants to merge 7 commits into
vE5li:mainfrom
RahulDNair:click-to-cast

Conversation

@RahulDNair

Copy link
Copy Markdown

What this adds

The complete skill-casting flow of the original client, reimplemented clean-room from observed behavior (no code was taken from other clients — behavior was studied via roBrowserLegacy's semantics and verified against rAthena's server implementation):

  • Click-to-cast target selection: clicking a skill in the hotbar (or pressing its function key) switches to a target selection mouse mode using the original client's target cursor from cursors.act. The next left click casts at the entity or tile under the cursor; right click or escape cancels. Self-cast skills fire immediately, passives do nothing.
  • Function key hotbar: all ten hotbar slots are now mapped to F1–F10 (previously J/L/U covered three slots with instant casting). Keys and clicks share one code path.
  • Cast level adjustment: while selecting a target, the mouse wheel adjusts the level the skill will be cast at (clamped to [1, learned level]), displayed next to the cursor — the classic "level 7 bolt" trade-off between cast speed and damage.
  • Walk into cast range: casting at an out-of-range target walks the player toward it and sends the cast request immediately. rAthena remembers skill requests received while walking (ud->stepaction) and executes them per walk step against the target's current position, so the cast follows moving targets and fires as early as possible. Ground skills included. This deliberately relies on the server's step-action machinery rather than a client-side buffer (which would double-cast).
  • Ground-skill cell indicator: the hovered tile is highlighted while targeting a ground skill.

Fixes found along the way

  • Skills at maximum level could not be dragged to the hotbar — the pickup handler rejected skills whose upgradable flag was false, which is every maxed skill. It now only rejects unlearned skills.
  • The target cursor rendered the wrong sprite action — the cursor direction workaround maps action indices correctly only for the states used so far (the index wraps modulo the action count); the target cursor is action 10 and rendered action 3. Even-numbered states need direction zero.
  • Skill damage was invisibleZC_NOTIFY_SKILL2 (0x01DE) was registered as a noop, so skill hits showed no damage numbers and no hit reaction. It now emits the same damage event as auto attacks.

Tested

Live against a local rAthena (PACKETVER 20220406): bolt skills at both level extremes (visibly different cast time and damage), targeting cancel via escape/right-click, casting at moving targets while walking into range, ground skill placement, drag-and-drop and slot swapping unchanged.

Known follow-ups (out of scope here)

  • The original client gates level adjustment per skill (bSeperateLv); this PR allows it on any targeted skill, and the server clamps regardless.
  • The original client shows the skill name and description overlay during target selection.
  • Support-priority entity picking during friendly-skill targeting.

This builds on the same play-testing effort as #419 but is independent of it.

🤖 Generated with Claude Code

RahulDNair and others added 7 commits August 2, 2026 22:03
Clicking a skill in the hotbar now enters a target selection mode:
the cursor changes to the target cursor from cursors.act, the next
left click casts the skill at the entity or tile under the cursor,
and right click or escape cancels the selection. Self cast skills
are used immediately without target selection, and passive skills
do nothing. Ground skills show the tile indicator on the hovered
cell while selecting. Dragging skills between hotbar slots and the
existing cast hotkeys are unchanged.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Picking up a skill from the skill tree was rejected whenever the
skill could no longer be upgraded, which made every skill at its
maximum level impossible to drag to the hotbar. The check now only
rejects skills that have not been learned at all.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The skill damage packet was registered as a noop, so skills dealt
damage without any visual feedback. It now emits the same damage
event as auto attacks, showing damage numbers and playing the hit
animation on the target.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The hotbar cast keys were J, L, and U for the first three slots and
cast instantly at the hovered target. All ten slots are now mapped to
F1 through F10 and behave like the original client: pressing a
function key or clicking the slot uses the skill, which either casts
a self cast skill immediately or starts the target selection mode.
The hotbar click and function keys share one code path.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The cursor render direction workaround only maps even numbered
cursor states correctly when the direction is zero, since the action
index wraps modulo the action count. The target cursor is action 10,
so it rendered action 3 instead. It now uses direction zero like the
other even numbered states.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
While selecting a skill target, scrolling now adjusts the level the
skill will be cast at, clamped between one and the level the skill
was placed in the hotbar with, and the chosen level is displayed
next to the cursor, like in the original client. Casting a bolt at a
lower level trades damage for cast speed.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Casting a skill on a target that is out of range now walks the
player towards the target and sends the cast request right away,
like in the original client. rAthena remembers skill requests
received while walking and executes them as soon as the target is
in range, re-checking against the target's current position at
every step, so the cast is not lost when the target moves. This
works for entity targets and ground skills, using the cast range
the server sends for the learned skill level.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant