AltSystem/docs/5-build_skills.md
Gonçalo Correia 6ebb92c62b feat/redesign (#1)
Reviewed-on: #1
Co-authored-by: Gonçalo Correia <goncalojoaocorreia@gmail.com>
Co-committed-by: Gonçalo Correia <goncalojoaocorreia@gmail.com>
2026-05-15 14:53:15 +01:00

8.2 KiB
Executable file
Raw Blame History

Feature: Build Skills tab

The second tab of the addon will follow these designs.

Acceptance Criteria

  • This screen should show the same skills we use in the main screen, which come from the TRP profile
  • The skills should be sorted by level
  • The skill list should be scrollable, with the "Save" button pinned/sticky to the bottom

Editing skills

  • The user should be able to edit the name, level, and numerical score of each skill
  • Edits should not be saved until the user explicitly clicks the "Save" button

Skill Level and Value

  • When a skill level is selected, the numerical score dropdown should update to only allow values within the skill level
    • Inept: 0
    • Novice: 1-5
    • Adept: 6-10
    • Expert: 11-19
    • Master: 20

Deleting skills

  • Clicking the "Delete" button should remove the skill from the list

Adding Skills

  • Clicking the "Add a Row" button should add a new skill row to the list
  • Default values for the new skill should be:
    • Name: Skillname
    • Level: Novice
    • Value: 1

Saving Skills

  • When clicking the "Save" button:
    • Newly added skills should be added to the TRP profile
    • Existing skills should be updated in the TRP profile
    • Skills that were deleted should also be removed from the TRP profile
  • Icons should not be changed

References

  • Refer to Data.lua for details on how we currently fetch the skills from TRP
  • Refer to the TRP3 source code in case it's necessary here

Implementation Plan

1. Add a SaveSkills function to Data.lua

  • Create AltSystem.Data:SaveSkills(editedSkills) that writes skills back to the TRP3 profile
  • Access the TRP3 profile via TRP3_API.profile.getData("player/characteristics") to get the characteristics.PS (personality traits) array
  • For each edited skill, update or insert entries in PS:
    • LT = skill name
    • RT = level keyword (e.g. "Novice", "Adept", etc.)
    • V2 = numeric value (020)
    • IC = preserve existing icon (do not change); for new skills, use a sensible default icon (e.g. "inv_misc_questionmark")
  • Remove any PS entries that were deleted by the user
  • After writing, call TRP3_API.dashboard.showCharacteristics() or fire the appropriate TRP3 event if needed to refresh TRP3's own UI
  • Edge case: If the TRP3 API is unavailable, show a warning message and abort save

2. Extract skill-level constants into shared lookup tables in Data.lua

  • The acceptance criteria defines value ranges per level (Inept: 0, Novice: 15, Adept: 610, Expert: 1119, Master: 20)
  • SKILL_KEYWORD_RANGES already exists but excludes Inept/Master min-max correctly for the Build tab's needs; extend or create a new table AltSystem.Data.SkillValueRanges that is accessible from UI.lua:
    { Inept = {min=0, max=0}, Novice = {min=1, max=5}, Adept = {min=6, max=10}, Expert = {min=11, max=19}, Master = {min=20, max=20} }
    
  • Create AltSystem.Data.SkillLevelOrder — an ordered array {"Inept", "Novice", "Adept", "Expert", "Master"} for populating the level dropdown in display order
  • Create a helper AltSystem.Data:GetDefaultValueForLevel(level) that returns the minimum value for that level (used when the user changes level to auto-set the value)

3. Add a function to read raw skills (with numeric values) from TRP3 in Data.lua

  • Currently RefreshSkills() converts TRP3 traits into {name, level, modifier} — the Build tab needs the raw numeric value and the icon as well
  • Create AltSystem.Data:GetEditableSkills() that returns an array of {name, level, value, icon} for each valid skill trait in the TRP3 profile (excluding Base Roll and Unskilled, which are system-generated entries)
  • Sort the returned skills by level using AltSystem.Data.SkillLevelOrder ordering (Inept first, Master last) — matching the acceptance criteria "sorted by level"
  • Reuse existing helpers FindSkillKeyword and ParseSkillLevel (promote them from local to module-level if needed, or call internally)

4. Build the Build Skills tab UI (new file: BuildSkillsUI.lua)

  • Create a new file to keep UI.lua manageable; register it in AltSystem.toc between UI.lua and Roll.lua
  • Create AltSystem:CreateBuildSkillsContent(parentFrame) called from CreateMainFrame in UI.lua (replacing the placeholder)
  • Layout structure:
    • Info text at top — two golden/yellow paragraphs explaining that skills come from TRP (matches mockup)
    • "Skill list" section header
    • Column headers: Name, Level, Value (bold golden text)
    • Scrollable skill list — a ScrollFrame containing dynamically created skill rows
    • "Add A Row" button — anchored below the last skill row, inside the scroll child
    • "Save Skills to TRP" button — pinned/sticky at the bottom of the tab, outside the scroll frame

5. Implement editable skill rows

  • Each skill row is a frame containing:
    • Name: EditBox (text input) — pre-filled with current skill name
    • Level: DropdownButton (WowStyle1DropdownTemplate) — options: Inept, Novice, Adept, Expert, Master
    • Value: DropdownButton — options dynamically generated based on selected level (e.g. Novice → 1,2,3,4,5)
    • Delete button: A button with a trash-can icon/red texture that removes the row
  • Store all row data in a local working copy array (editableSkills), not directly in AltSystem.Data.Skills
  • When the level dropdown changes:
    • Update the value dropdown options to only show valid values for the new level
    • Auto-set the value to the minimum for that level (e.g. switching to Adept → value becomes 6)
  • Row management:
    • CreateSkillRow(parent, index, skillData) — creates or recycles a row frame
    • RefreshSkillRows() — rebuilds/repositions all rows and updates scroll child height
    • Deleting a row removes it from editableSkills and calls RefreshSkillRows()

6. Implement "Add A Row" functionality

  • Clicking "Add A Row" inserts a new entry into editableSkills:
    • { name = "Skillname", level = "Novice", value = 1, icon = "inv_misc_questionmark", isNew = true }
  • Calls RefreshSkillRows() to render the new row
  • The scroll frame should auto-scroll to show the new row

7. Implement "Save Skills to TRP" functionality

  • On click, call AltSystem.Data:SaveSkills(editableSkills) which:
    1. Reads current characteristics.PS from TRP3
    2. Rebuilds the PS array: keeps non-skill traits untouched, updates/adds/removes skill traits based on editableSkills
    3. Writes the updated PS back to the TRP3 profile data
    4. Calls RefreshSkills() so the Use Skills tab dropdown reflects the changes immediately
  • Show a confirmation message (print to chat or a brief on-screen text) on successful save
  • Edge cases:
    • Empty skill list: allowed — just remove all skill traits from PS
    • Duplicate skill names: allowed (TRP3 doesn't enforce uniqueness)
    • Unsaved changes + tab switch: no confirmation dialog required (per spec, changes are just lost)

8. Wire up tab switching to populate Build Skills tab

  • In SelectTab(2) (UI.lua), call AltSystem:RefreshBuildSkillsList() to reload skills from TRP3 into the working copy
  • This ensures the Build tab always shows the latest TRP3 data when opened, and any unsaved edits are discarded on tab switch

9. Update AltSystem.toc

  • Add BuildSkillsUI.lua to the file list (after UI.lua, before Roll.lua)

10. Testing checklist

  • Build Skills tab shows skills from TRP3 profile, sorted by level
  • Skill name is editable via text input
  • Level dropdown shows all 5 levels; changing level updates value dropdown options and auto-selects minimum value
  • Value dropdown only shows values valid for the current level
  • Delete button removes the row immediately
  • "Add A Row" adds a row with defaults (Skillname, Novice, 1)
  • Skill list scrolls when rows exceed visible area
  • "Save" button is always visible (pinned to bottom)
  • Save writes correct data to TRP3 profile (LT, RT, V2, IC preserved)
  • Save does not modify icons of existing skills
  • After save, Use Skills tab dropdown reflects the updated skills
  • Switching tabs discards unsaved changes and reloads from TRP3
  • Works correctly with 0 skills (empty profile)
  • Works correctly with many skills (20+) — scroll behavior