Skip to content

Commit

Permalink
Added Menu#ImageSelectorArray
Browse files Browse the repository at this point in the history
  • Loading branch information
Sicdex committed Jun 18, 2024
1 parent 6931485 commit 99e19b1
Show file tree
Hide file tree
Showing 6 changed files with 297 additions and 28 deletions.
8 changes: 7 additions & 1 deletion wrapper/Data/ImageData.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ export const Paths = new (class BaseImageData {

public readonly Icons = {
topbar_mana: `${this.reborn}/topbar_mana_psd.vtex_c`,
invoker_cataclysm: `${this.AbilityIcons}/invoker/magus_apex/invoker_sun_strike_png.vtex_c`,
topbar_health: `${this.reborn}/topbar_health_psd.vtex_c`,
topbar_health_dire: `${this.reborn}/topbar_health_dire_psd.vtex_c`,
topbar_health_colorblind: `${this.reborn}/topbar_health_colorblind_psd.vtex_c`,
Expand Down Expand Up @@ -121,7 +122,12 @@ const getTexturePath = (name: string, isItem = false): string => {
return abilityData.TexturePath
}
if (!isItem) {
return Paths.AbilityIcons + "/" + name + "_png.vtex_c"
switch (name) {
case "invoker_cataclysm":
return Paths.Icons.invoker_cataclysm
default:
return Paths.AbilityIcons + "/" + name + "_png.vtex_c"
}
}
name = !name.includes("recipe_")
? name.replace("item_", "")
Expand Down
22 changes: 13 additions & 9 deletions wrapper/Menu/DynamicImageSelector.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,16 @@
import { Color } from "../Base/Color"
import { Rectangle } from "../Base/Rectangle"
import { Vector2 } from "../Base/Vector2"
import {
GetHeroTexture,
GetItemTexture,
GetRuneTexture,
GetSpellTexture
} from "../Data/ImageData"
import { GUIInfo } from "../GUI/GUIInfo"
import { EventsSDK } from "../Managers/EventsSDK"
import { InputEventSDK, InputManager, VKeys } from "../Managers/InputManager"
import { RendererSDK } from "../Native/RendererSDK"
import { AbilityData } from "../Objects/DataBook/AbilityData"
import { Base, IMenu } from "./Base"

type IDefaultValues = Map<
Expand Down Expand Up @@ -165,17 +170,16 @@ export class DynamicImageSelector extends Base {
continue
}
let path = name
if (path.startsWith("rune_")) {
path = `panorama/images/spellicons/${path}_png.vtex_c`
if (!path.startsWith("npc_dota_hero_")) {
path = path.startsWith("item_")
? GetItemTexture(path)
: GetSpellTexture(path)
} else if (path.startsWith("rune_")) {
path = GetRuneTexture(path)
} else if (path.startsWith("item_bottle_")) {
path = `panorama/images/items/${path.substring(5)}_png.vtex_c`
} else if (!path.startsWith("npc_dota_hero_")) {
const abil = AbilityData.GetAbilityByName(path)
if (abil !== undefined) {
path = abil.TexturePath
}
} else {
path = `panorama/images/heroes/${path}_png.vtex_c`
path = GetHeroTexture(path)
}
const pathIamgeSize = RendererSDK.GetImageSize(path)
this.imageSize.x = Math.max(
Expand Down
22 changes: 13 additions & 9 deletions wrapper/Menu/ImageSelector.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,15 @@
import { Color } from "../Base/Color"
import { Rectangle } from "../Base/Rectangle"
import { Vector2 } from "../Base/Vector2"
import {
GetHeroTexture,
GetItemTexture,
GetRuneTexture,
GetSpellTexture
} from "../Data/ImageData"
import { GUIInfo } from "../GUI/GUIInfo"
import { EventsSDK } from "../Managers/EventsSDK"
import { RendererSDK } from "../Native/RendererSDK"
import { AbilityData } from "../Objects/DataBook/AbilityData"
import { Base, IMenu } from "./Base"

// every icon: 32x32, 1x1 border
Expand Down Expand Up @@ -115,17 +120,16 @@ export class ImageSelector extends Base {

for (let index = 0, end = values.length; index < end; index++) {
let path = values[index]
if (path.startsWith("rune_")) {
path = `panorama/images/spellicons/${path}_png.vtex_c`
if (!path.startsWith("npc_dota_hero_")) {
path = path.startsWith("item_")
? GetItemTexture(path)
: GetSpellTexture(path)
} else if (path.startsWith("rune_")) {
path = GetRuneTexture(path)
} else if (path.startsWith("item_bottle_")) {
path = `panorama/images/items/${path.substring(5)}_png.vtex_c`
} else if (!path.startsWith("npc_dota_hero_")) {
const abil = AbilityData.GetAbilityByName(path)
if (abil !== undefined) {
path = abil.TexturePath
}
} else {
path = `panorama/images/heroes/${path}_png.vtex_c`
path = GetHeroTexture(path)
}
const pathIamgeSize = RendererSDK.GetImageSize(path)
this.imageSize.x = Math.max(
Expand Down
234 changes: 234 additions & 0 deletions wrapper/Menu/ImageSelectorArr.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,234 @@
import { Color } from "../Base/Color"
import { Rectangle } from "../Base/Rectangle"
import { Vector2 } from "../Base/Vector2"
import {
GetHeroTexture,
GetItemTexture,
GetRuneTexture,
GetSpellTexture
} from "../Data/ImageData"
import { GUIInfo } from "../GUI/GUIInfo"
import { EventsSDK } from "../Managers/EventsSDK"
import { RendererSDK } from "../Native/RendererSDK"
import { Base, IMenu } from "./Base"

// every icon: 32x32, 1x1 border
export class ImageSelectorArray extends Base {
public static OnWindowSizeChanged(): void {
ImageSelectorArray.imageBorderWidth = GUIInfo.ScaleWidth(2)
ImageSelectorArray.imageGap = GUIInfo.ScaleWidth(2)
ImageSelectorArray.baseImageHeight = GUIInfo.ScaleHeight(32)
ImageSelectorArray.randomHeightValue = GUIInfo.ScaleHeight(40)
}

private static imageBorderWidth = 0
private static imageGap = 0
private static baseImageHeight = 0
private static randomHeightValue = 0
private static readonly elementsPerRow = 5
private static readonly imageActivatedBorderColor = new Color(104, 4, 255)

public enabledValues: [string, boolean][]
protected readonly imageSize = new Vector2()
protected renderedPaths: string[] = []

constructor(
parent: IMenu,
name: string,
public values: string[],
public readonly defaultValues: [string, boolean][] = [],
tooltip = ""
) {
super(parent, name, tooltip)
this.enabledValues = defaultValues
}

// TODO: check current state
public get IsZeroSelected(): boolean {
const arr = this.enabledValues
for (let index = arr.length - 1; index > -1; index--) {
const [, state] = arr[index]
if (state) {
return false
}
}
return true
}

public get IconsRect() {
const basePos = this.Position.Add(this.textOffset).AddScalarY(this.nameSize.y + 3)
return new Rectangle(
basePos,
basePos
.Add(
this.imageSize
.AddScalar(
ImageSelectorArray.imageBorderWidth * 2 +
ImageSelectorArray.imageGap
)
.MultiplyScalarX(
Math.min(
this.values.length,
ImageSelectorArray.elementsPerRow
)
)
.MultiplyScalarY(
Math.ceil(
this.values.length / ImageSelectorArray.elementsPerRow
)
)
)
.SubtractScalar(
(ImageSelectorArray.elementsPerRow - 1) * ImageSelectorArray.imageGap
)
)
}

public get ConfigValue() {
return this.enabledValues
}
public set ConfigValue(value) {
if (
this.ShouldIgnoreNewConfigValue ||
value === undefined ||
!Array.isArray(value)
) {
return
}
this.enabledValues = value
}

public get ClassPriority(): number {
return 6
}

public Update(): boolean {
if (!super.Update()) {
return false
}

const values = this.values
this.imageSize.x = this.imageSize.y = ImageSelectorArray.baseImageHeight
this.renderedPaths = []

for (let index = 0, end = values.length; index < end; index++) {
let path = values[index]
if (!path.startsWith("npc_dota_hero_")) {
path = path.startsWith("item_")
? GetItemTexture(path)
: GetSpellTexture(path)
} else if (path.startsWith("rune_")) {
path = GetRuneTexture(path)
} else if (path.startsWith("item_bottle_")) {
path = `panorama/images/items/${path.substring(5)}_png.vtex_c`
} else {
path = GetHeroTexture(path)
}
const pathIamgeSize = RendererSDK.GetImageSize(path)
this.imageSize.x = Math.max(
this.imageSize.x,
ImageSelectorArray.baseImageHeight * (pathIamgeSize.x / pathIamgeSize.y)
)
this.renderedPaths.push(path)
}
this.Size.x =
Math.max(
this.nameSize.x,
Math.min(this.values.length, ImageSelectorArray.elementsPerRow) *
(this.imageSize.x +
ImageSelectorArray.imageBorderWidth * 2 +
ImageSelectorArray.imageGap)
) +
this.textOffset.x * 2
this.Size.y =
Math.ceil(this.values.length / ImageSelectorArray.elementsPerRow) *
(this.imageSize.y +
ImageSelectorArray.imageBorderWidth * 2 +
ImageSelectorArray.imageGap) +
ImageSelectorArray.randomHeightValue
return true
}

public IsEnabled(value: string): boolean {
return this.enabledValues.some(([name, state]) => name === value && state)
}

public IsEnabledID(id: number): boolean {
return this.IsEnabled(this.values[id])
}

public Render(): void {
super.Render()
this.RenderTextDefault(this.Name, this.Position.Add(this.textOffset))
const basePos = this.IconsRect.pos1
for (let index = 0, end = this.values.length; index < end; index++) {
const imagePath = this.renderedPaths[index]
if (imagePath === undefined) {
continue
}
const size = this.imageSize,
pos = new Vector2(
index % ImageSelectorArray.elementsPerRow,
Math.floor(index / ImageSelectorArray.elementsPerRow)
)
.Multiply(
this.imageSize.AddScalar(
ImageSelectorArray.imageBorderWidth * 2 +
ImageSelectorArray.imageGap
)
)
.Add(basePos)

RendererSDK.Image(
imagePath,
pos,
-1,
size,
Color.White,
0,
undefined,
!this.IsEnabled(this.values[index])
)

if (this.IsEnabled(this.values[index])) {
RendererSDK.OutlinedRect(
pos,
size,
ImageSelectorArray.imageBorderWidth,
ImageSelectorArray.imageActivatedBorderColor
)
}
}
}

public OnMouseLeftDown(): boolean {
return !this.IconsRect.Contains(this.MousePosition)
}

public OnMouseLeftUp(): boolean {
const rect = this.IconsRect
if (!rect.Contains(this.MousePosition)) {
return false
}
const off = rect.GetOffset(this.MousePosition)
for (let i = 0, end = this.values.length; i < end; i++) {
const basePos = new Vector2(
i % ImageSelectorArray.elementsPerRow,
Math.floor(i / ImageSelectorArray.elementsPerRow)
).Multiply(
this.imageSize.AddScalar(
ImageSelectorArray.imageBorderWidth * 2 + ImageSelectorArray.imageGap
)
)
if (!new Rectangle(basePos, basePos.Add(this.imageSize)).Contains(off)) {
continue
}
this.enabledValues[i][1] = !this.IsEnabled(this.values[i])
this.TriggerOnValueChangedCBs()
break
}
return false
}
}

EventsSDK.on("WindowSizeChanged", () => ImageSelectorArray.OnWindowSizeChanged())
Loading

0 comments on commit 99e19b1

Please sign in to comment.