commit
64a4edf178
33
.editorconfig
Normal file
33
.editorconfig
Normal file
@ -0,0 +1,33 @@
|
|||||||
|
root = true
|
||||||
|
|
||||||
|
# Global
|
||||||
|
[*]
|
||||||
|
indent_style = unset
|
||||||
|
indent_size = 4
|
||||||
|
tab_width = 4
|
||||||
|
end_of_line = lf
|
||||||
|
charset = utf-8
|
||||||
|
trim_trailing_whitespace = true
|
||||||
|
insert_final_newline = unset
|
||||||
|
|
||||||
|
# Unreal Engine 3 / Source
|
||||||
|
[*.uc]
|
||||||
|
indent_style = tab
|
||||||
|
|
||||||
|
[*.{uci,upkg}]
|
||||||
|
|
||||||
|
# Unreal Engine 3 / i18n
|
||||||
|
[*.{chn,cht,cze,dan,deu,dut,esl,esn,fra,frc,hun,int,ita,jpn,kor,pol,por,ptb,rus,tur,ukr}]
|
||||||
|
charset = utf-16le
|
||||||
|
|
||||||
|
# Other
|
||||||
|
[*.md]
|
||||||
|
indent_style = space
|
||||||
|
trim_trailing_whitespace = false
|
||||||
|
|
||||||
|
[*.yml]
|
||||||
|
indent_style = space
|
||||||
|
indent_size = 2
|
||||||
|
|
||||||
|
[*.{txt,cfg,conf}]
|
||||||
|
indent_style = tab
|
8
.github/issue_template.md
vendored
8
.github/issue_template.md
vendored
@ -1,8 +0,0 @@
|
|||||||
### Details
|
|
||||||
Tell us exactly what happens, every single detail that you can think of
|
|
||||||
|
|
||||||
### Screenshots
|
|
||||||
Provide a screenshot of the issue so we can debug it's not a user issue
|
|
||||||
|
|
||||||
### Steps to reproduce
|
|
||||||
Tell us how to reproduce the problem, step by step
|
|
74
.github/workflows/mega-linter.yml
vendored
Normal file
74
.github/workflows/mega-linter.yml
vendored
Normal file
@ -0,0 +1,74 @@
|
|||||||
|
---
|
||||||
|
name: MegaLinter
|
||||||
|
|
||||||
|
permissions: read-all
|
||||||
|
|
||||||
|
on:
|
||||||
|
push:
|
||||||
|
pull_request:
|
||||||
|
branches: [master]
|
||||||
|
|
||||||
|
env:
|
||||||
|
APPLY_FIXES: none
|
||||||
|
APPLY_FIXES_EVENT: pull_request
|
||||||
|
APPLY_FIXES_MODE: commit
|
||||||
|
DISABLE: SPELL
|
||||||
|
DISABLE_ERRORS_LINTERS: MARKDOWN_MARKDOWN_LINK_CHECK
|
||||||
|
EDITORCONFIG_EDITORCONFIG_CHECKER_FILTER_REGEX_EXCLUDE: 'xVoteAnnouncer.upk'
|
||||||
|
|
||||||
|
concurrency:
|
||||||
|
group: ${{ github.ref }}-${{ github.workflow }}
|
||||||
|
cancel-in-progress: true
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
build:
|
||||||
|
name: MegaLinter
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- name: Checkout Code
|
||||||
|
uses: actions/checkout@v3
|
||||||
|
with:
|
||||||
|
token: ${{ secrets.PAT || secrets.GITHUB_TOKEN }}
|
||||||
|
|
||||||
|
- name: MegaLinter
|
||||||
|
id: ml
|
||||||
|
uses: oxsecurity/megalinter@v6
|
||||||
|
env:
|
||||||
|
VALIDATE_ALL_CODEBASE: true
|
||||||
|
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||||
|
|
||||||
|
- name: Archive production artifacts
|
||||||
|
if: ${{ success() }} || ${{ failure() }}
|
||||||
|
uses: actions/upload-artifact@v3
|
||||||
|
with:
|
||||||
|
name: MegaLinter reports
|
||||||
|
path: |
|
||||||
|
megalinter-reports
|
||||||
|
mega-linter.log
|
||||||
|
|
||||||
|
- name: Create Pull Request with applied fixes
|
||||||
|
id: cpr
|
||||||
|
if: steps.ml.outputs.has_updated_sources == 1 && (env.APPLY_FIXES_EVENT == 'all' || env.APPLY_FIXES_EVENT == github.event_name) && env.APPLY_FIXES_MODE == 'pull_request' && (github.event_name == 'push' || github.event.pull_request.head.repo.full_name == github.repository)
|
||||||
|
uses: peter-evans/create-pull-request@v5
|
||||||
|
with:
|
||||||
|
token: ${{ secrets.PAT || secrets.GITHUB_TOKEN }}
|
||||||
|
commit-message: "[MegaLinter] Apply linters automatic fixes"
|
||||||
|
title: "[MegaLinter] Apply linters automatic fixes"
|
||||||
|
labels: bot
|
||||||
|
- name: Create PR output
|
||||||
|
if: steps.ml.outputs.has_updated_sources == 1 && (env.APPLY_FIXES_EVENT == 'all' || env.APPLY_FIXES_EVENT == github.event_name) && env.APPLY_FIXES_MODE == 'pull_request' && (github.event_name == 'push' || github.event.pull_request.head.repo.full_name == github.repository)
|
||||||
|
run: |
|
||||||
|
echo "Pull Request Number - ${{ steps.cpr.outputs.pull-request-number }}"
|
||||||
|
echo "Pull Request URL - ${{ steps.cpr.outputs.pull-request-url }}"
|
||||||
|
|
||||||
|
- name: Prepare commit
|
||||||
|
if: steps.ml.outputs.has_updated_sources == 1 && (env.APPLY_FIXES_EVENT == 'all' || env.APPLY_FIXES_EVENT == github.event_name) && env.APPLY_FIXES_MODE == 'commit' && github.ref != 'refs/heads/main' && (github.event_name == 'push' || github.event.pull_request.head.repo.full_name == github.repository)
|
||||||
|
run: sudo chown -Rc $UID .git/
|
||||||
|
- name: Commit and push applied linter fixes
|
||||||
|
if: steps.ml.outputs.has_updated_sources == 1 && (env.APPLY_FIXES_EVENT == 'all' || env.APPLY_FIXES_EVENT == github.event_name) && env.APPLY_FIXES_MODE == 'commit' && github.ref != 'refs/heads/main' && (github.event_name == 'push' || github.event.pull_request.head.repo.full_name == github.repository)
|
||||||
|
uses: stefanzweifel/git-auto-commit-action@v4
|
||||||
|
with:
|
||||||
|
branch: ${{ github.event.pull_request.head.ref || github.head_ref || github.ref }}
|
||||||
|
commit_message: "[MegaLinter] Apply linters fixes"
|
||||||
|
commit_user_name: megalinter-bot
|
||||||
|
commit_user_email: nicolas.vuillamy@ox.security
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
40
README.md
40
README.md
@ -1,9 +1,11 @@
|
|||||||
[![](PublicationContent/mutbanner.png)](https://steamcommunity.com/sharedfiles/filedetails/?id=2085786712)
|
# Server Extension
|
||||||
|
|
||||||
|
[![Banner](PublicationContent/mutbanner.png)](https://steamcommunity.com/sharedfiles/filedetails/?id=2085786712)
|
||||||
|
|
||||||
[![Steam Workshop](https://img.shields.io/static/v1?message=workshop&logo=steam&labelColor=gray&color=blue&logoColor=white&label=steam%20)](https://steamcommunity.com/sharedfiles/filedetails/?id=2085786712)
|
[![Steam Workshop](https://img.shields.io/static/v1?message=workshop&logo=steam&labelColor=gray&color=blue&logoColor=white&label=steam%20)](https://steamcommunity.com/sharedfiles/filedetails/?id=2085786712)
|
||||||
[![Steam Subscriptions](https://img.shields.io/steam/subscriptions/2085786712)](https://steamcommunity.com/sharedfiles/filedetails/?id=2085786712)
|
[![Steam Subscriptions](https://img.shields.io/steam/subscriptions/2085786712)](https://steamcommunity.com/sharedfiles/filedetails/?id=2085786712)
|
||||||
[![Steam Favorites](https://img.shields.io/steam/favorites/2085786712)](https://steamcommunity.com/sharedfiles/filedetails/?id=2085786712)
|
[![Steam Favorites](https://img.shields.io/steam/favorites/2085786712)](https://steamcommunity.com/sharedfiles/filedetails/?id=2085786712)
|
||||||
[![Steam Update Date](https://img.shields.io/steam/update-date/2085786712)](https://steamcommunity.com/sharedfiles/filedetails/?id=2085786712)
|
[![MegaLinter](https://github.com/GenZmeY/KF2-Server-Extension/actions/workflows/mega-linter.yml/badge.svg?branch=master)](https://github.com/GenZmeY/KF2-Server-Extension/actions/workflows/mega-linter.yml)
|
||||||
[![GitHub tag (latest by date)](https://img.shields.io/github/v/tag/GenZmeY/KF2-Server-Extension)](https://github.com/GenZmeY/KF2-Server-Extension/tags)
|
[![GitHub tag (latest by date)](https://img.shields.io/github/v/tag/GenZmeY/KF2-Server-Extension)](https://github.com/GenZmeY/KF2-Server-Extension/tags)
|
||||||
[![GitHub top language](https://img.shields.io/github/languages/top/GenZmeY/KF2-Server-Extension)](https://docs.unrealengine.com/udk/Three/WebHome.html)
|
[![GitHub top language](https://img.shields.io/github/languages/top/GenZmeY/KF2-Server-Extension)](https://docs.unrealengine.com/udk/Three/WebHome.html)
|
||||||
[![GitHub](https://img.shields.io/github/license/GenZmeY/KF2-Server-Extension)](LICENSE)
|
[![GitHub](https://img.shields.io/github/license/GenZmeY/KF2-Server-Extension)](LICENSE)
|
||||||
@ -16,7 +18,7 @@
|
|||||||
|
|
||||||
*This is a further development of the ServerExt mutator from [Marco](https://forums.tripwireinteractive.com/index.php?threads/mutator-server-extension-mod.109463) and [Forrest Mark X](https://github.com/ForrestMarkX/KF2-Server-Extension).*
|
*This is a further development of the ServerExt mutator from [Marco](https://forums.tripwireinteractive.com/index.php?threads/mutator-server-extension-mod.109463) and [Forrest Mark X](https://github.com/ForrestMarkX/KF2-Server-Extension).*
|
||||||
|
|
||||||
# Features
|
## Features
|
||||||
- RPG elements (traits and stats);
|
- RPG elements (traits and stats);
|
||||||
- New menu system;
|
- New menu system;
|
||||||
- Scoreboard that supports unlimited playercount on server;
|
- Scoreboard that supports unlimited playercount on server;
|
||||||
@ -33,7 +35,7 @@ The full changelog is available on [steam workshop](https://steamcommunity.com/s
|
|||||||
|
|
||||||
**Note:** If you want to build/test/brew/publish a mutator without git-bash and/or scripts, follow [these instructions](https://tripwireinteractive.atlassian.net/wiki/spaces/KF2SW/pages/26247172/KF2+Code+Modding+How-to) instead of what is described here.
|
**Note:** If you want to build/test/brew/publish a mutator without git-bash and/or scripts, follow [these instructions](https://tripwireinteractive.atlassian.net/wiki/spaces/KF2SW/pages/26247172/KF2+Code+Modding+How-to) instead of what is described here.
|
||||||
|
|
||||||
# Build
|
## Build
|
||||||
1. Install [Killing Floor 2](https://store.steampowered.com/app/232090/Killing_Floor_2/), Killing Floor 2 - SDK and [git for windows](https://git-scm.com/download/win);
|
1. Install [Killing Floor 2](https://store.steampowered.com/app/232090/Killing_Floor_2/), Killing Floor 2 - SDK and [git for windows](https://git-scm.com/download/win);
|
||||||
2. open git-bash and go to any folder where you want to store ServerExt sources:
|
2. open git-bash and go to any folder where you want to store ServerExt sources:
|
||||||
`cd <ANY_FOLDER_YOU_WANT>`
|
`cd <ANY_FOLDER_YOU_WANT>`
|
||||||
@ -46,29 +48,13 @@ The full changelog is available on [steam workshop](https://steamcommunity.com/s
|
|||||||
5. The compiled files will be here:
|
5. The compiled files will be here:
|
||||||
`C:\Users\<USERNAME>\Documents\My Games\KillingFloor2\KFGame\Unpublished\BrewedPC\Script\`
|
`C:\Users\<USERNAME>\Documents\My Games\KillingFloor2\KFGame\Unpublished\BrewedPC\Script\`
|
||||||
|
|
||||||
# Testing
|
## Using and configuring ServerExt
|
||||||
Open git-bash in the ServerExt source folder and run command:
|
|
||||||
`./tools/builder -t`
|
|
||||||
(or `./tools/builder -ct` if you haven't compiled the mutator yet)
|
|
||||||
|
|
||||||
A local single-user test will be launched with parameters from `builder.cfg` (edit this file if you want to test mutator with different parameters).
|
|
||||||
|
|
||||||
# Using and configuring ServerExt
|
|
||||||
A detailed manual is available on the [mod page](https://steamcommunity.com/sharedfiles/filedetails/?id=2085786712) in the steam workshop.
|
A detailed manual is available on the [mod page](https://steamcommunity.com/sharedfiles/filedetails/?id=2085786712) in the steam workshop.
|
||||||
|
|
||||||
# Publication in steam workshop
|
## Contributing
|
||||||
1. Modify the publish files if necessary, they are in the `PublicationContent`:
|
|
||||||
> description.txt
|
|
||||||
> preview.png
|
|
||||||
> tags.txt
|
|
||||||
> title.txt
|
|
||||||
|
|
||||||
2. Run this command in the source folder: `./tools/builder -cbu`
|
|
||||||
|
|
||||||
# Contributing
|
|
||||||
**Participation is welcome!**
|
**Participation is welcome!**
|
||||||
|
|
||||||
## Bug reports
|
### Bug reports
|
||||||
If you find a bug, go to the [issue page](https://github.com/GenZmeY/KF2-Server-Extension/issues) and check if there is a description of your bug. If not, create a new issue.
|
If you find a bug, go to the [issue page](https://github.com/GenZmeY/KF2-Server-Extension/issues) and check if there is a description of your bug. If not, create a new issue.
|
||||||
Describe what the bug looks like and how we can reproduce it.
|
Describe what the bug looks like and how we can reproduce it.
|
||||||
Attach screenshots if you think it might help.
|
Attach screenshots if you think it might help.
|
||||||
@ -77,12 +63,12 @@ If it's a crash issue, be sure to include the `Launch.log` and `Launch_2.log` fi
|
|||||||
`C:\Users\<USERNAME>\Documents\My Games\KillingFloor2\KFGame\Logs\`
|
`C:\Users\<USERNAME>\Documents\My Games\KillingFloor2\KFGame\Logs\`
|
||||||
Please note that these files are overwritten every time you start the game/server. Therefore, you must take these files immediately after the game crashes in order not to lose information.
|
Please note that these files are overwritten every time you start the game/server. Therefore, you must take these files immediately after the game crashes in order not to lose information.
|
||||||
|
|
||||||
## Localization
|
### Localization
|
||||||
The mutator supports localization and you can help translate it into other languages.
|
The mutator supports localization and you can help translate it into other languages.
|
||||||
It does not require any special knowledge or programming skills, so you just need to know the language into which you will translate.
|
It does not require any special knowledge or programming skills, so you just need to know the language into which you will translate.
|
||||||
Here's a quick guide on how to do it: [localization guide](https://steamcommunity.com/workshop/filedetails/discussion/2085786712/2942494909176752884)
|
Here's a quick guide on how to do it: [localization guide](https://steamcommunity.com/workshop/filedetails/discussion/2085786712/2942494909176752884)
|
||||||
|
|
||||||
## Contribute code
|
### Contribute code
|
||||||
You can help improve ServerExt by fixing bugs and adding new features.
|
You can help improve ServerExt by fixing bugs and adding new features.
|
||||||
Before making a pull request, make sure that:
|
Before making a pull request, make sure that:
|
||||||
1. Your code is working correctly.
|
1. Your code is working correctly.
|
||||||
@ -91,8 +77,8 @@ Before making a pull request, make sure that:
|
|||||||
In the description of the pull request, describe the changes you made.
|
In the description of the pull request, describe the changes you made.
|
||||||
|
|
||||||
|
|
||||||
# License
|
## License
|
||||||
[GNU GPLv3](LICENSE)
|
[![license](https://www.gnu.org/graphics/gplv3-with-text-136x68.png)](LICENSE)
|
||||||
|
|
||||||
***
|
***
|
||||||
|
|
||||||
|
@ -46,4 +46,5 @@ final function SaveData(FMyCustomChar R)
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -7,4 +7,5 @@ protected function SpecialCringeEffectsfor (Actor Victim, float VictimDist)
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -31,4 +31,5 @@ function UpdateGrenades()
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -44,4 +44,5 @@ function UpdatePlayerInfo(optional bool bForceUpdate)
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -88,4 +88,5 @@ simulated function SetWeaponGroupList(out array<KFWeapon> WeaponList, byte Group
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -62,4 +62,5 @@ function Callback_Equip(int ItemDefinition)
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -98,7 +98,6 @@ function AttachWeaponByItemDefinition(int ItemDefinition)
|
|||||||
|
|
||||||
//setweapon skin
|
//setweapon skin
|
||||||
WeaponAttachment.SetWeaponSkin(ItemDefinition);
|
WeaponAttachment.SetWeaponSkin(ItemDefinition);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
|
@ -7,4 +7,5 @@ static simulated event bool IsABoss()
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -47,4 +47,5 @@ function PlayAnimation()
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -52,4 +52,5 @@ function SetPerkList()
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -1347,5 +1347,4 @@ defaultproperties
|
|||||||
Skins.Add((Id=5303, Weapondef=class'KFWeapDef_AA12', MIC_1P=("WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_1P_Mint_MIC"), MIC_3P="WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_3P_Mint_MIC", MIC_Pickup="WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_3P_Pickup_MIC"))
|
Skins.Add((Id=5303, Weapondef=class'KFWeapDef_AA12', MIC_1P=("WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_1P_Mint_MIC"), MIC_3P="WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_3P_Mint_MIC", MIC_Pickup="WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_3P_Pickup_MIC"))
|
||||||
Skins.Add((Id=5302, Weapondef=class'KFWeapDef_AA12', MIC_1P=("WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_1P_FieldTested_MIC"), MIC_3P="WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_3P_FieldTested_MIC", MIC_Pickup="WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_3P_Pickup_MIC"))
|
Skins.Add((Id=5302, Weapondef=class'KFWeapDef_AA12', MIC_1P=("WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_1P_FieldTested_MIC"), MIC_3P="WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_3P_FieldTested_MIC", MIC_Pickup="WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_3P_Pickup_MIC"))
|
||||||
Skins.Add((Id=5301, Weapondef=class'KFWeapDef_AA12', MIC_1P=("WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_1P_BattleScarred_MIC"), MIC_3P="WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_3P_BattleScarred_MIC", MIC_Pickup="WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_3P_Pickup_MIC"))
|
Skins.Add((Id=5301, Weapondef=class'KFWeapDef_AA12', MIC_1P=("WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_1P_BattleScarred_MIC"), MIC_3P="WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_3P_BattleScarred_MIC", MIC_Pickup="WEP_SkinSet17_MAT.sports_aa12.Vault_Sports_AA12_3P_Pickup_MIC"))
|
||||||
|
|
||||||
}
|
}
|
@ -7,6 +7,7 @@ function SpecialMoveStarted(bool bForced, Name PrevMove)
|
|||||||
|
|
||||||
function SpecialMoveEnded(Name PrevMove, Name NextMove)
|
function SpecialMoveEnded(Name PrevMove, Name NextMove)
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
|
@ -2,4 +2,5 @@ class Ext_TGroupMonster extends Ext_TGroupBase;
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -33,4 +33,5 @@ static final function byte GetMaxLimit(Ext_PerkBase Perk)
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -2,4 +2,5 @@ class Ext_TGroupZEDTime extends Ext_TGroupBase;
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -24,4 +24,5 @@ function Timer()
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -8,4 +8,5 @@ var class<Ext_TraitBase> TraitClass;
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -59,4 +59,5 @@ function PreClientTravel(string PendingURL, ETravelType TravelType, bool bIsSeam
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -53,4 +53,5 @@ function DrawMenu()
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -90,4 +90,5 @@ function HandleMouseClick(bool bRight);
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -56,4 +56,5 @@ function PreDraw()
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -1,928 +0,0 @@
|
|||||||
//====================================================================
|
|
||||||
// HTML Text box, written by Marco
|
|
||||||
// Simply call SetContents to change window contents.
|
|
||||||
// Only callback available is for LaunchKFURL.
|
|
||||||
// ====================================================================
|
|
||||||
class KFGUI_HTMLTextBox extends KFGUI_MultiComponent;
|
|
||||||
|
|
||||||
struct FTextLine
|
|
||||||
{
|
|
||||||
var string Text,URL;
|
|
||||||
var color Color,ALColor;
|
|
||||||
var Font Font;
|
|
||||||
var float FontScale;
|
|
||||||
var byte Align,FontSize;
|
|
||||||
var int X,Y,XS,YS,Tab,TOffset;
|
|
||||||
var byte LineSkips;
|
|
||||||
var array<int> ImgList;
|
|
||||||
var bool bHasURL,bSplit;
|
|
||||||
};
|
|
||||||
var array<FTextLine> Lines;
|
|
||||||
|
|
||||||
struct FImageEntry
|
|
||||||
{
|
|
||||||
var Surface Img;
|
|
||||||
var int X,Y,XS,YS,YOffset,XOffset;
|
|
||||||
var byte Align,Style;
|
|
||||||
};
|
|
||||||
var array<FImageEntry> Images;
|
|
||||||
|
|
||||||
var FImageEntry BgImage;
|
|
||||||
var float OldXSize,OldYSize;
|
|
||||||
var int YSize,HoverOverLinkLine,OldHoverLine;
|
|
||||||
var() Color BGColor,WhiteColor,BlueColor,RedColor;
|
|
||||||
var KFGUI_ScrollBarV MyScrollBar;
|
|
||||||
var string TitleString;
|
|
||||||
var int CurTab;
|
|
||||||
var byte DefaultFontSize;
|
|
||||||
var bool bNeedsInit,bHasSplitLines,bNeedScrollbar;
|
|
||||||
|
|
||||||
function InitMenu()
|
|
||||||
{
|
|
||||||
Super.InitMenu();
|
|
||||||
|
|
||||||
MyScrollBar = KFGUI_ScrollBarV(FindComponentID('Scrollbar'));
|
|
||||||
}
|
|
||||||
|
|
||||||
final function int AddText( string Input, color TextColor, byte TextAlign, byte FontSize, out byte NumSkips )
|
|
||||||
{
|
|
||||||
local int i;
|
|
||||||
|
|
||||||
i = Lines.Length;
|
|
||||||
Lines.Length = i+1;
|
|
||||||
Lines[i].Text = Input;
|
|
||||||
Lines[i].Color = TextColor;
|
|
||||||
Lines[i].Align = TextAlign;
|
|
||||||
Lines[i].FontSize = FontSize;
|
|
||||||
Lines[i].LineSkips = NumSkips;
|
|
||||||
Lines[i].Tab = CurTab;
|
|
||||||
NumSkips = 0;
|
|
||||||
return i;
|
|
||||||
}
|
|
||||||
final function string ParseLinkType( string URL )
|
|
||||||
{
|
|
||||||
if( InStr(URL,"//")>0 )
|
|
||||||
return URL;
|
|
||||||
if( Left(URL,4)~="ftp." )
|
|
||||||
return "ftp://"$URL;
|
|
||||||
return "http://"$URL;
|
|
||||||
}
|
|
||||||
final function AddImage( string Input )
|
|
||||||
{
|
|
||||||
local string Temp;
|
|
||||||
local byte Align,Sty;
|
|
||||||
local Material M;
|
|
||||||
local int X,Y,XS,YS,i,j,z;
|
|
||||||
|
|
||||||
Align = 3;
|
|
||||||
Temp = GetOption(Input, "ALIGN=");
|
|
||||||
if (Temp != "")
|
|
||||||
{
|
|
||||||
switch( Caps(Temp) )
|
|
||||||
{
|
|
||||||
case "LEFT":
|
|
||||||
case "0":
|
|
||||||
Align = 0;
|
|
||||||
break;
|
|
||||||
case "CENTER":
|
|
||||||
case "1":
|
|
||||||
Align = 1;
|
|
||||||
break;
|
|
||||||
case "RIGHT":
|
|
||||||
case "2":
|
|
||||||
Align = 2;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Temp = GetOption(Input, "STYLE=");
|
|
||||||
if (Temp != "")
|
|
||||||
{
|
|
||||||
switch( Caps(Temp) )
|
|
||||||
{
|
|
||||||
case "NORMAL":
|
|
||||||
case "0":
|
|
||||||
Sty = 0;
|
|
||||||
break;
|
|
||||||
case "STRETCH":
|
|
||||||
case "1":
|
|
||||||
Sty = 1;
|
|
||||||
break;
|
|
||||||
case "TILEDX":
|
|
||||||
case "2":
|
|
||||||
Sty = 2;
|
|
||||||
break;
|
|
||||||
case "TILEDY":
|
|
||||||
case "3":
|
|
||||||
Sty = 3;
|
|
||||||
break;
|
|
||||||
case "TILED":
|
|
||||||
case "4":
|
|
||||||
Sty = 4;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Temp = GetOption(Input, "SRC=");
|
|
||||||
if (Temp != "")
|
|
||||||
M = Surface(DynamicLoadObject(Temp,Class'Surface'));
|
|
||||||
if( M==None )
|
|
||||||
M = class'Canvas'.Default.DefaultTexture;
|
|
||||||
X = int(GetOption(Input, "VSPACE="));
|
|
||||||
Y = int(GetOption(Input, "HSPACE="));
|
|
||||||
XS = int(GetOption(Input, "WIDTH="));
|
|
||||||
YS = int(GetOption(Input, "HEIGHT="));
|
|
||||||
|
|
||||||
if( XS==0 )
|
|
||||||
XS = M.GetSurfaceWidth();
|
|
||||||
if( YS==0 )
|
|
||||||
YS = M.GetSurfaceHeight();
|
|
||||||
|
|
||||||
i = Images.Length;
|
|
||||||
Images.Length = i+1;
|
|
||||||
Images[i].Img = M;
|
|
||||||
Images[i].XOffset = X;
|
|
||||||
Images[i].YOffset = Y;
|
|
||||||
Images[i].XS = XS;
|
|
||||||
Images[i].YS = YS;
|
|
||||||
Images[i].Style = Sty;
|
|
||||||
Images[i].Align = Align;
|
|
||||||
j = Lines.Length-1;
|
|
||||||
z = Lines[j].ImgList.Length;
|
|
||||||
Lines[j].ImgList.Length = z+1;
|
|
||||||
Lines[j].ImgList[z] = i;
|
|
||||||
}
|
|
||||||
final function SetContents( string Input )
|
|
||||||
{
|
|
||||||
local string LeftText,HTML,RightText,Output,Temp,Link;
|
|
||||||
local int Index;
|
|
||||||
local color TextColor,LinkColor,ALinkColor,OrgTextColor;
|
|
||||||
local byte Alignment,FontScaler,NextLineSkips;
|
|
||||||
|
|
||||||
CurTab = 0;
|
|
||||||
BGColor.A = 0;
|
|
||||||
BgImage.Img = None;
|
|
||||||
Lines.Length = 0;
|
|
||||||
Images.Length = 0;
|
|
||||||
TitleString = "";
|
|
||||||
bHasSplitLines = false;
|
|
||||||
bNeedsInit = true;
|
|
||||||
|
|
||||||
// First remove new liners
|
|
||||||
Input = Repl(Input, Chr(13)$Chr(10), "");
|
|
||||||
Input = Repl(Input, Chr(13), "");
|
|
||||||
Input = Repl(Input, Chr(10), "");
|
|
||||||
Input = Repl(Input, Chr(9), " ");
|
|
||||||
Input = Repl(Input, "\\n", "<BR>");
|
|
||||||
|
|
||||||
TextColor = WhiteColor;
|
|
||||||
OrgTextColor = WhiteColor;
|
|
||||||
LinkColor = BlueColor;
|
|
||||||
ALinkColor = RedColor;
|
|
||||||
FontScaler = 3;
|
|
||||||
DefaultFontSize = 3;
|
|
||||||
Index = -1;
|
|
||||||
|
|
||||||
while (Input != "")
|
|
||||||
{
|
|
||||||
ParseHTML(Input, LeftText, HTML, RightText);
|
|
||||||
|
|
||||||
switch (GetTag(HTML))
|
|
||||||
{
|
|
||||||
// multiline HTML tags
|
|
||||||
case "P":
|
|
||||||
Output $= LeftText;
|
|
||||||
if( Output!="" )
|
|
||||||
{
|
|
||||||
Index = AddText(Output,TextColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
NextLineSkips = 2;
|
|
||||||
Output = "";
|
|
||||||
}
|
|
||||||
else ++NextLineSkips;
|
|
||||||
break;
|
|
||||||
case "BR":
|
|
||||||
Output $= LeftText;
|
|
||||||
if( Output!="" )
|
|
||||||
{
|
|
||||||
Index = AddText(Output,TextColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
NextLineSkips = 1;
|
|
||||||
Output = "";
|
|
||||||
}
|
|
||||||
else ++NextLineSkips;
|
|
||||||
break;
|
|
||||||
case "BODY":
|
|
||||||
Temp = GetOption(HTML, "BGCOLOR=");
|
|
||||||
if (Temp != "")
|
|
||||||
BGColor = ParseColor(Temp);
|
|
||||||
|
|
||||||
Temp = GetOption(HTML, "LINK=");
|
|
||||||
if (Temp != "")
|
|
||||||
LinkColor = ParseColor(Temp);
|
|
||||||
|
|
||||||
Temp = GetOption(HTML, "ALINK=");
|
|
||||||
if (Temp != "")
|
|
||||||
ALinkColor = ParseColor(Temp);
|
|
||||||
|
|
||||||
Temp = GetOption(HTML, "TEXT=");
|
|
||||||
if (Temp != "")
|
|
||||||
{
|
|
||||||
TextColor = ParseColor(Temp);
|
|
||||||
OrgTextColor = TextColor;
|
|
||||||
}
|
|
||||||
|
|
||||||
Temp = GetOption(HTML, "SIZE=");
|
|
||||||
if (Temp != "")
|
|
||||||
{
|
|
||||||
FontScaler = int(Temp);
|
|
||||||
DefaultFontSize = FontScaler;
|
|
||||||
}
|
|
||||||
|
|
||||||
Temp = GetOption(Input, "IMG=");
|
|
||||||
if (Temp != "")
|
|
||||||
{
|
|
||||||
if( BGColor.A==0 )
|
|
||||||
BGColor = Class'Hud'.Default.WhiteColor;
|
|
||||||
BgImage.Img = Surface(DynamicLoadObject(Temp,Class'Surface'));
|
|
||||||
if( BgImage.Img==None )
|
|
||||||
BgImage.Img = Class'Canvas'.Default.DefaultTexture;
|
|
||||||
BgImage.X = BgImage.Img.GetSurfaceWidth();
|
|
||||||
BgImage.Y = BgImage.Img.GetSurfaceHeight();
|
|
||||||
switch( Caps(GetOption(Input, "IMGSTYLE=")) )
|
|
||||||
{
|
|
||||||
case "TILED":
|
|
||||||
BgImage.XS = BgImage.X;
|
|
||||||
BgImage.YS = BgImage.Y;
|
|
||||||
BgImage.Style = 1;
|
|
||||||
Temp = GetOption(Input, "TILEX=");
|
|
||||||
if (Temp != "")
|
|
||||||
BgImage.XS = int(Temp);
|
|
||||||
Temp = GetOption(Input, "TILEY=");
|
|
||||||
if (Temp != "")
|
|
||||||
BgImage.YS = int(Temp);
|
|
||||||
break;
|
|
||||||
case "FITX":
|
|
||||||
BgImage.Style = 2;
|
|
||||||
break;
|
|
||||||
case "FITY":
|
|
||||||
BgImage.Style = 3;
|
|
||||||
break;
|
|
||||||
default: // FIT
|
|
||||||
BgImage.Style = 0;
|
|
||||||
}
|
|
||||||
BgImage.Align = 0;
|
|
||||||
if( GetOption(Input, "IMGLOCK=")=="0" )
|
|
||||||
BgImage.Align = 1;
|
|
||||||
}
|
|
||||||
Output $= LeftText;
|
|
||||||
break;
|
|
||||||
case "CENTER":
|
|
||||||
Output $= LeftText;
|
|
||||||
if ( Output!="" )
|
|
||||||
{
|
|
||||||
Index = AddText(Output,TextColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
Output = "";
|
|
||||||
}
|
|
||||||
NextLineSkips = Max(NextLineSkips,1);
|
|
||||||
Alignment = 1;
|
|
||||||
break;
|
|
||||||
case "RIGHT":
|
|
||||||
Output $= LeftText;
|
|
||||||
if ( Output!="" )
|
|
||||||
{
|
|
||||||
Index = AddText(Output,TextColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
Output = "";
|
|
||||||
}
|
|
||||||
NextLineSkips = Max(NextLineSkips,1);
|
|
||||||
Alignment = 2;
|
|
||||||
break;
|
|
||||||
case "/CENTER":
|
|
||||||
case "/RIGHT":
|
|
||||||
Index = AddText(Output $ LeftText,TextColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
++NextLineSkips;
|
|
||||||
Alignment = 0;
|
|
||||||
Output = "";
|
|
||||||
break;
|
|
||||||
// Inline HTML tags
|
|
||||||
case "H1":
|
|
||||||
Output $= LeftText;
|
|
||||||
if ( Output!="" )
|
|
||||||
{
|
|
||||||
Index = AddText(Output,TextColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
Output = "";
|
|
||||||
}
|
|
||||||
NextLineSkips = Max(NextLineSkips,1);
|
|
||||||
FontScaler = 5;
|
|
||||||
Alignment = 1;
|
|
||||||
break;
|
|
||||||
case "/H1":
|
|
||||||
Index = AddText(Output $ LeftText,TextColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
++NextLineSkips;
|
|
||||||
Output = "";
|
|
||||||
FontScaler = DefaultFontSize;
|
|
||||||
Alignment = 0;
|
|
||||||
break;
|
|
||||||
case "FONT":
|
|
||||||
Output $= LeftText;
|
|
||||||
if( Output!="" )
|
|
||||||
{
|
|
||||||
Index = AddText(Output,TextColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
Output = "";
|
|
||||||
}
|
|
||||||
Temp = GetOption(HTML, "COLOR=");
|
|
||||||
if (Temp != "")
|
|
||||||
TextColor = ParseColor(Temp);
|
|
||||||
Temp = GetOption(HTML, "SIZE=");
|
|
||||||
if (Temp != "")
|
|
||||||
FontScaler = int(Temp);
|
|
||||||
break;
|
|
||||||
case "/FONT":
|
|
||||||
Output $= LeftText;
|
|
||||||
if( Output!="" )
|
|
||||||
{
|
|
||||||
Index = AddText(Output,TextColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
Output = "";
|
|
||||||
}
|
|
||||||
TextColor = OrgTextColor;
|
|
||||||
FontScaler = DefaultFontSize;
|
|
||||||
break;
|
|
||||||
case "TAB":
|
|
||||||
Output $= LeftText;
|
|
||||||
if( Output!="" )
|
|
||||||
{
|
|
||||||
Index = AddText(Output,TextColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
Output = "";
|
|
||||||
}
|
|
||||||
CurTab = int(GetOption(HTML, "X="));
|
|
||||||
break;
|
|
||||||
case "/TAB":
|
|
||||||
Output $= LeftText;
|
|
||||||
if( Output!="" )
|
|
||||||
{
|
|
||||||
Index = AddText(Output,TextColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
Output = "";
|
|
||||||
}
|
|
||||||
CurTab = 0;
|
|
||||||
break;
|
|
||||||
case "TITLE":
|
|
||||||
Output $= LeftText;
|
|
||||||
break;
|
|
||||||
case "/TITLE":
|
|
||||||
TitleString = LeftText;
|
|
||||||
break;
|
|
||||||
case "A":
|
|
||||||
Output $= LeftText;
|
|
||||||
if( Output!="" )
|
|
||||||
{
|
|
||||||
Index = AddText(Output,TextColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
Output = "";
|
|
||||||
}
|
|
||||||
Link = GetOption(HTML, "HREF=");
|
|
||||||
break;
|
|
||||||
case "/A":
|
|
||||||
Output $= LeftText;
|
|
||||||
Index = AddText(Output,LinkColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
Lines[Index].ALColor = ALinkColor;
|
|
||||||
Lines[Index].bHasURL = true;
|
|
||||||
if( Link=="" )
|
|
||||||
Lines[Index].URL = ParseLinkType(Output);
|
|
||||||
else Lines[Index].URL = ParseLinkType(Link);
|
|
||||||
Output = "";
|
|
||||||
FontScaler = DefaultFontSize;
|
|
||||||
Alignment = 0;
|
|
||||||
break;
|
|
||||||
case "IMG":
|
|
||||||
Output $= LeftText;
|
|
||||||
if( Output!="" || NextLineSkips>0 )
|
|
||||||
AddText(Output,TextColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
Output = "";
|
|
||||||
AddImage(HTML);
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
Output = Output $ LeftText;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
Input = RightText;
|
|
||||||
}
|
|
||||||
AddText(Output,TextColor,Alignment,FontScaler,NextLineSkips);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Get the next HTML tag, the text before it and everthing after it.
|
|
||||||
final function ParseHTML(string Input, out string LeftText, out string HTML, out string RightText)
|
|
||||||
{
|
|
||||||
local int i;
|
|
||||||
|
|
||||||
i = InStr(Input, "<");
|
|
||||||
if (i == -1)
|
|
||||||
{
|
|
||||||
LeftText = Input;
|
|
||||||
HTML = "";
|
|
||||||
RightText = "";
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
LeftText = Left(Input, i);
|
|
||||||
HTML = Mid(Input, i);
|
|
||||||
|
|
||||||
i = InStr(HTML, ">");
|
|
||||||
if (i == -1)
|
|
||||||
{
|
|
||||||
RightText = "";
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
RightText = Mid(HTML, i+1);
|
|
||||||
HTML = Left(HTML, i+1);
|
|
||||||
}
|
|
||||||
final function string GetTag(string HTML)
|
|
||||||
{
|
|
||||||
local int i;
|
|
||||||
|
|
||||||
if (HTML == "")
|
|
||||||
return "";
|
|
||||||
|
|
||||||
HTML = Mid(HTML, 1); // lose <
|
|
||||||
|
|
||||||
i = FirstMatching(InStr(HTML, ">"), InStr(HTML, " "));
|
|
||||||
if (i == -1)
|
|
||||||
return Caps(HTML);
|
|
||||||
else
|
|
||||||
return Caps(Left(HTML, i));
|
|
||||||
}
|
|
||||||
final function string GetOption(string HTML, string Option)
|
|
||||||
{
|
|
||||||
local int i, j;
|
|
||||||
local string s;
|
|
||||||
|
|
||||||
i = InStr(Caps(HTML), Caps(Option));
|
|
||||||
|
|
||||||
if (i == 1 || Mid(HTML, i-1, 1) == " ")
|
|
||||||
{
|
|
||||||
s = Mid(HTML, i+Len(Option));
|
|
||||||
j = FirstMatching(InStr(s, ">"), InStr(s, " "));
|
|
||||||
s = Left(s, j);
|
|
||||||
|
|
||||||
if (Left(s, 1) == "\"")
|
|
||||||
s = Mid(s, 1);
|
|
||||||
|
|
||||||
if (Right(s, 1) == "\"")
|
|
||||||
s = Left(s, Len(s) - 1);
|
|
||||||
|
|
||||||
return s;
|
|
||||||
}
|
|
||||||
return "";
|
|
||||||
}
|
|
||||||
final function int FirstMatching(int i, int j)
|
|
||||||
{
|
|
||||||
if (i == -1)
|
|
||||||
return j;
|
|
||||||
if (j == -1)
|
|
||||||
return i;
|
|
||||||
return Min(i, j);
|
|
||||||
}
|
|
||||||
final function Color ParseColor(string S)
|
|
||||||
{
|
|
||||||
local Color C;
|
|
||||||
local int i;
|
|
||||||
|
|
||||||
S = Caps(S);
|
|
||||||
if (Left(S, 1) == "#")
|
|
||||||
{
|
|
||||||
C.R = (GetHexDigit(Mid(S, 1, 1)) << 4) + GetHexDigit(Mid(S, 2, 1));
|
|
||||||
C.G = (GetHexDigit(Mid(S, 3, 1)) << 4) + GetHexDigit(Mid(S, 4, 1));
|
|
||||||
C.B = (GetHexDigit(Mid(S, 5, 1)) << 4) + GetHexDigit(Mid(S, 6, 1));
|
|
||||||
}
|
|
||||||
else if (Left(S, 4) == "RGB(")
|
|
||||||
{
|
|
||||||
S = Mid(S, 4);
|
|
||||||
i = InStr(S,",");
|
|
||||||
C.R = int(Left(S,i));
|
|
||||||
S = Mid(S,i+1);
|
|
||||||
i = InStr(S,",");
|
|
||||||
C.G = int(Left(S,i));
|
|
||||||
C.B = int(Mid(S,i+1));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
switch( S )
|
|
||||||
{
|
|
||||||
case "RED":
|
|
||||||
C.R = 255;
|
|
||||||
C.G = 0;
|
|
||||||
C.B = 0;
|
|
||||||
break;
|
|
||||||
case "BLUE":
|
|
||||||
C.R = 0;
|
|
||||||
C.G = 0;
|
|
||||||
C.B = 255;
|
|
||||||
break;
|
|
||||||
case "GREEN":
|
|
||||||
C.R = 0;
|
|
||||||
C.G = 255;
|
|
||||||
C.B = 0;
|
|
||||||
break;
|
|
||||||
case "YELLOW":
|
|
||||||
C.R = 255;
|
|
||||||
C.G = 255;
|
|
||||||
C.B = 0;
|
|
||||||
break;
|
|
||||||
case "BLACK":
|
|
||||||
C.R = 0;
|
|
||||||
C.G = 0;
|
|
||||||
C.B = 0;
|
|
||||||
break;
|
|
||||||
default: // WHITE
|
|
||||||
C.R = 255;
|
|
||||||
C.G = 255;
|
|
||||||
C.B = 255;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
C.A = 255;
|
|
||||||
|
|
||||||
return C;
|
|
||||||
}
|
|
||||||
final function byte GetHexDigit(string D)
|
|
||||||
{
|
|
||||||
local byte i;
|
|
||||||
|
|
||||||
i = Asc(D);
|
|
||||||
if( i>=48 && i<=57 ) // i>='0' && i<='9'
|
|
||||||
return (i-48); // i-'0'
|
|
||||||
return Min(i-55,15); // i-('A'-10)
|
|
||||||
}
|
|
||||||
|
|
||||||
final function SplitLine( int iLine, int iOffset )
|
|
||||||
{
|
|
||||||
local int i;
|
|
||||||
local string S;
|
|
||||||
|
|
||||||
++iLine;
|
|
||||||
Lines.Insert(iLine,1);
|
|
||||||
S = Lines[iLine-1].Text;
|
|
||||||
for( i=iOffset; i<Len(S); ++i )
|
|
||||||
if( Mid(S,i,1)!=" " )
|
|
||||||
break;
|
|
||||||
Lines[iLine].Text = Mid(S,i);
|
|
||||||
Lines[iLine-1].Text = Left(S,iOffset);
|
|
||||||
Lines[iLine].URL = Lines[iLine-1].URL;
|
|
||||||
Lines[iLine].Color = Lines[iLine-1].Color;
|
|
||||||
Lines[iLine].ALColor = Lines[iLine-1].ALColor;
|
|
||||||
Lines[iLine].Align = Lines[iLine-1].Align;
|
|
||||||
Lines[iLine].FontSize = Lines[iLine-1].FontSize;
|
|
||||||
Lines[iLine].Tab = Lines[iLine-1].Tab;
|
|
||||||
Lines[iLine].LineSkips = 1;
|
|
||||||
Lines[iLine].bHasURL = Lines[iLine-1].bHasURL;
|
|
||||||
Lines[iLine].bSplit = true;
|
|
||||||
bHasSplitLines = true;
|
|
||||||
}
|
|
||||||
final protected function InitHTMLArea()
|
|
||||||
{
|
|
||||||
local float XS,YS;
|
|
||||||
local int i,j,X,Y,iStart,BestHeight,FontSize,PrevY,Remain,iLastWord,iLen,z,ImgHeight;
|
|
||||||
|
|
||||||
// Used to detect resolution changes when text needs realignment.
|
|
||||||
OldXSize = CompPos[2];
|
|
||||||
OldYSize = CompPos[3];
|
|
||||||
|
|
||||||
// Merge splitted lines again
|
|
||||||
if( bHasSplitLines )
|
|
||||||
{
|
|
||||||
bHasSplitLines = false;
|
|
||||||
for( i=1; i<Lines.Length; ++i )
|
|
||||||
{
|
|
||||||
if( Lines[i].bSplit )
|
|
||||||
{
|
|
||||||
Lines[i-1].Text @= Lines[i].Text;
|
|
||||||
Lines.Remove(i--,1);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Setup background image scaling
|
|
||||||
if( BgImage.Img!=None )
|
|
||||||
{
|
|
||||||
switch( BgImage.Style )
|
|
||||||
{
|
|
||||||
case 1: // Tiled
|
|
||||||
if( BgImage.X==BgImage.XS )
|
|
||||||
BgImage.XOffset = Canvas.ClipX;
|
|
||||||
else
|
|
||||||
{
|
|
||||||
XS = Canvas.ClipX / float(BgImage.XS) * float(BgImage.X);
|
|
||||||
BgImage.XOffset = XS;
|
|
||||||
}
|
|
||||||
if( BgImage.Y==BgImage.YS )
|
|
||||||
BgImage.YOffset = Canvas.ClipY;
|
|
||||||
else
|
|
||||||
{
|
|
||||||
XS = Canvas.ClipY / float(BgImage.YS) * float(BgImage.Y);
|
|
||||||
BgImage.YOffset = XS;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case 2: // Fit X
|
|
||||||
XS = Canvas.ClipY * (Canvas.ClipX / float(BgImage.X));
|
|
||||||
BgImage.YS = XS;
|
|
||||||
break;
|
|
||||||
case 3: // Fit Y
|
|
||||||
XS = Canvas.ClipX * (Canvas.ClipY / float(BgImage.Y));
|
|
||||||
BgImage.XS = XS;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
FontSize = Owner.CurrentStyle.DefaultFontSize;
|
|
||||||
|
|
||||||
Canvas.SetPos(0,0);
|
|
||||||
if( Lines.Length>0 )
|
|
||||||
{
|
|
||||||
while( true )
|
|
||||||
{
|
|
||||||
if( i>=Lines.Length || (i>0 && Lines[i].LineSkips>0) )
|
|
||||||
{
|
|
||||||
for( j=iStart; j<i; ++j )
|
|
||||||
{
|
|
||||||
switch( Lines[j].Align )
|
|
||||||
{
|
|
||||||
case 0: // Left
|
|
||||||
Lines[j].X = Lines[j].TOffset;
|
|
||||||
break;
|
|
||||||
case 1: // Center
|
|
||||||
Lines[j].X = (Canvas.ClipX-X+Lines[j].TOffset)/2;
|
|
||||||
break;
|
|
||||||
case 2: // Right
|
|
||||||
Lines[j].X = Canvas.ClipX-X+Lines[j].TOffset;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if( i>=Lines.Length )
|
|
||||||
break;
|
|
||||||
X = 0;
|
|
||||||
iStart = i;
|
|
||||||
PrevY = BestHeight;
|
|
||||||
BestHeight = 0;
|
|
||||||
}
|
|
||||||
if( Lines[i].FontSize>=247 )
|
|
||||||
Lines[i].Font = Owner.CurrentStyle.PickFont(Max(Lines[i].FontSize-247,0),Lines[i].FontScale);
|
|
||||||
else Lines[i].Font = Owner.CurrentStyle.PickFont(Max(FontSize+Lines[i].FontSize,0),Lines[i].FontScale);
|
|
||||||
Canvas.Font = Lines[i].Font;
|
|
||||||
if( Lines[i].Text=="" )
|
|
||||||
{
|
|
||||||
Canvas.TextSize("ABC",XS,YS,Lines[i].FontScale,Lines[i].FontScale);
|
|
||||||
XS = 0;
|
|
||||||
}
|
|
||||||
else Canvas.TextSize(Lines[i].Text,XS,YS,Lines[i].FontScale,Lines[i].FontScale);
|
|
||||||
if( Lines[i].LineSkips>0 )
|
|
||||||
{
|
|
||||||
if( PrevY==0 )
|
|
||||||
PrevY = YS;
|
|
||||||
Y+=(PrevY*Lines[i].LineSkips);
|
|
||||||
}
|
|
||||||
X = Max(X,Lines[i].Tab);
|
|
||||||
Lines[i].TOffset = X;
|
|
||||||
Lines[i].Y = Y;
|
|
||||||
Lines[i].YS = YS;
|
|
||||||
BestHeight = Max(BestHeight,YS);
|
|
||||||
if( (X+XS)>Canvas.ClipX )
|
|
||||||
{
|
|
||||||
// Split to next row.
|
|
||||||
Remain = Canvas.ClipX-X;
|
|
||||||
iLastWord = 0;
|
|
||||||
iLen = Len(Lines[i].Text);
|
|
||||||
for( j=1; j<iLen; ++j )
|
|
||||||
{
|
|
||||||
Canvas.TextSize(Left(Lines[i].Text,j),XS,YS,Lines[i].FontScale,Lines[i].FontScale);
|
|
||||||
if( Remain<XS )
|
|
||||||
{
|
|
||||||
if( iLastWord==0 ) // Must cut off a word now.
|
|
||||||
SplitLine(i,Max(j-1,0));
|
|
||||||
else SplitLine(i,iLastWord);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if( Mid(Lines[i].Text,j,1)==" " )
|
|
||||||
iLastWord = j+1;
|
|
||||||
}
|
|
||||||
Canvas.TextSize(Lines[i].Text,XS,YS,Lines[i].FontScale,Lines[i].FontScale);
|
|
||||||
}
|
|
||||||
Lines[i].XS = XS;
|
|
||||||
X+=XS;
|
|
||||||
|
|
||||||
for( j=0; j<Lines[i].ImgList.Length; ++j )
|
|
||||||
{
|
|
||||||
z = Lines[i].ImgList[j];
|
|
||||||
if( Images[z].Align==3 )
|
|
||||||
Images[z].X = X+Images[z].XOffset;
|
|
||||||
else Images[z].X = Images[z].XOffset;
|
|
||||||
Images[z].Y = Y+Images[z].YOffset;
|
|
||||||
ImgHeight = Max(ImgHeight,Images[z].Y+Images[z].YS);
|
|
||||||
}
|
|
||||||
++i;
|
|
||||||
}
|
|
||||||
YSize = Max(Y+BestHeight,ImgHeight);
|
|
||||||
}
|
|
||||||
else YSize = 0;
|
|
||||||
|
|
||||||
bNeedScrollbar = (YSize>Canvas.ClipY);
|
|
||||||
if( bNeedScrollbar )
|
|
||||||
{
|
|
||||||
MyScrollBar.SetDisabled(false);
|
|
||||||
MyScrollBar.UpdateScrollSize(0,YSize,Canvas.ClipY,512);
|
|
||||||
}
|
|
||||||
else MyScrollBar.SetDisabled(true);
|
|
||||||
}
|
|
||||||
simulated final function DrawTileStretchedClipped( Surface M, float XS, float YS )
|
|
||||||
{
|
|
||||||
Canvas.CurX += Canvas.OrgX;
|
|
||||||
Canvas.CurY += Canvas.OrgY;
|
|
||||||
if( Canvas.CurX<Canvas.OrgX )
|
|
||||||
{
|
|
||||||
XS-=(Canvas.OrgX-Canvas.CurX);
|
|
||||||
Canvas.CurX = Canvas.OrgX;
|
|
||||||
}
|
|
||||||
if( Canvas.CurY<Canvas.OrgY )
|
|
||||||
{
|
|
||||||
YS-=(Canvas.OrgY-Canvas.CurY);
|
|
||||||
Canvas.CurY = Canvas.OrgY;
|
|
||||||
}
|
|
||||||
if( (Canvas.CurX+XS)>Canvas.ClipX )
|
|
||||||
XS = (Canvas.ClipX-Canvas.CurX);
|
|
||||||
if( (Canvas.CurY+YS)>Canvas.ClipY )
|
|
||||||
YS = (Canvas.ClipY-Canvas.CurY);
|
|
||||||
if( Texture(M)!=None )
|
|
||||||
Canvas.DrawTileStretched(Texture(M),XS,YS);
|
|
||||||
}
|
|
||||||
function DrawMenu()
|
|
||||||
{
|
|
||||||
local float YS;
|
|
||||||
local int i,YOffset,MX,MY;
|
|
||||||
local bool bMouseOnClient;
|
|
||||||
|
|
||||||
if( bNeedsInit || OldXSize!=CompPos[2] || OldYSize!=CompPos[3] )
|
|
||||||
{
|
|
||||||
bNeedsInit = false;
|
|
||||||
InitHTMLArea();
|
|
||||||
}
|
|
||||||
if( bNeedScrollbar )
|
|
||||||
YOffset = MyScrollBar.CurrentScroll;
|
|
||||||
|
|
||||||
if( BGColor.A>0 )
|
|
||||||
{
|
|
||||||
C.SetPos(0,0);
|
|
||||||
C.DrawColor = BGColor;
|
|
||||||
|
|
||||||
if( BgImage.Img!=None )
|
|
||||||
{
|
|
||||||
if( BgImage.Align==1 ) // not locked on screen.
|
|
||||||
MX = YOffset;
|
|
||||||
switch( BgImage.Style )
|
|
||||||
{
|
|
||||||
case 0: // Stretched to fit
|
|
||||||
C.DrawTileClipped(BgImage.Img,C.ClipX,C.ClipY,0,MX,BgImage.X,BgImage.Y);
|
|
||||||
break;
|
|
||||||
case 1: // Tiled
|
|
||||||
C.DrawTileClipped(BgImage.Img,C.ClipX,C.ClipY,0,MX,BgImage.XOffset,BgImage.YOffset);
|
|
||||||
break;
|
|
||||||
case 2: // Fit X
|
|
||||||
C.DrawTileClipped(BgImage.Img,C.ClipX,C.ClipY,0,MX,BgImage.X,BgImage.YS);
|
|
||||||
break;
|
|
||||||
case 3: // Fit Y
|
|
||||||
C.DrawTileClipped(BgImage.Img,C.ClipX,C.ClipY,0,MX,BgImage.XS,BgImage.Y);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else C.DrawTile(Texture'WhiteTexture',C.ClipX,C.ClipY,0,0,1,1);
|
|
||||||
}
|
|
||||||
MX = Controller.MouseX-C.OrgX;
|
|
||||||
MY = Controller.MouseY-C.OrgY;
|
|
||||||
bMouseOnClient = (MX>=0 && MX<=C.ClipX && MY>=0 && MY<=C.ClipY);
|
|
||||||
HoverOverLinkLine = -1;
|
|
||||||
MY+=YOffset;
|
|
||||||
|
|
||||||
C.DrawColor = Class'HUD'.Default.WhiteColor;
|
|
||||||
for( i=0; i<Images.Length; ++i )
|
|
||||||
{
|
|
||||||
C.CurY = Images[i].Y-YOffset;
|
|
||||||
if( (C.CurY+Images[i].YS)<0 || C.CurY>C.ClipY )
|
|
||||||
continue;
|
|
||||||
switch( Images[i].Align )
|
|
||||||
{
|
|
||||||
case 0: // Left
|
|
||||||
case 3: // Unaligned, postition after text.
|
|
||||||
C.CurX = 0;
|
|
||||||
break;
|
|
||||||
case 1: // Center
|
|
||||||
C.CurX = (C.ClipX-Images[i].XS)/2;
|
|
||||||
break;
|
|
||||||
case 1: // Right
|
|
||||||
C.CurX = C.ClipX-Images[i].XS;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
C.CurX += Images[i].X;
|
|
||||||
switch( Images[i].Style )
|
|
||||||
{
|
|
||||||
case 1: // Stretched
|
|
||||||
DrawTileStretchedClipped(C,Images[i].Img,Images[i].XS,Images[i].YS);
|
|
||||||
break;
|
|
||||||
case 2: // Tiled on X axis
|
|
||||||
C.DrawTileClipped(Images[i].Img,Images[i].XS,Images[i].YS,0,0,Images[i].XS,Images[i].Img.MaterialVSize());
|
|
||||||
break;
|
|
||||||
case 3: // Tiled on Y axis
|
|
||||||
C.DrawTileClipped(Images[i].Img,Images[i].XS,Images[i].YS,0,0,Images[i].Img.MaterialUSize(),Images[i].YS);
|
|
||||||
break;
|
|
||||||
case 4: // Fully tiled
|
|
||||||
C.DrawTileClipped(Images[i].Img,Images[i].XS,Images[i].YS,0,0,Images[i].XS,Images[i].YS);
|
|
||||||
break;
|
|
||||||
default: // Normal
|
|
||||||
C.DrawTileClipped(Images[i].Img,Images[i].XS,Images[i].YS,0,0,Images[i].Img.MaterialUSize(),Images[i].Img.MaterialVSize());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
for( i=0; i<Lines.Length; ++i )
|
|
||||||
{
|
|
||||||
C.SetPos(Lines[i].X,Lines[i].Y-YOffset);
|
|
||||||
if( (C.CurY+Lines[i].YS)<0 || Lines[i].Text=="" )
|
|
||||||
continue;
|
|
||||||
if( C.CurY>C.ClipY )
|
|
||||||
break;
|
|
||||||
|
|
||||||
// Check if mouse hovers over URL
|
|
||||||
if( bMouseOnClient && Lines[i].bHasURL && MX>=Lines[i].X && MX<=(Lines[i].X+Lines[i].XS)
|
|
||||||
&& MY>=Lines[i].Y && MY<=(Lines[i].Y+Lines[i].YS) )
|
|
||||||
{
|
|
||||||
HoverOverLinkLine = i;
|
|
||||||
bMouseOnClient = false; // No need to check on rest anymore.
|
|
||||||
C.DrawColor = Lines[i].ALColor;
|
|
||||||
}
|
|
||||||
else C.DrawColor = Lines[i].Color;
|
|
||||||
|
|
||||||
C.Font = Lines[i].Font;
|
|
||||||
C.DrawTextClipped(Lines[i].Text);
|
|
||||||
if( Lines[i].bHasURL )
|
|
||||||
{
|
|
||||||
YS = Max(Lines[i].YS/15,1);
|
|
||||||
C.SetPos(Lines[i].X,Lines[i].Y+Lines[i].YS-(YS*2)-YOffset);
|
|
||||||
if( C.CurY<C.ClipY )
|
|
||||||
C.DrawTileClipped(Texture'WhiteTexture',Lines[i].XS,YS,0,0,1,1);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if( OldHoverLine!=HoverOverLinkLine )
|
|
||||||
{
|
|
||||||
OldHoverLine = HoverOverLinkLine;
|
|
||||||
if( HoverOverLinkLine>=0 )
|
|
||||||
{
|
|
||||||
Controller.PlayInterfaceSound(CS_Hover);
|
|
||||||
SetToolTipText(Lines[HoverOverLinkLine].URL);
|
|
||||||
}
|
|
||||||
else SetToolTipText("");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
function bool LaunchURL(GUIComponent Sender)
|
|
||||||
{
|
|
||||||
if( HoverOverLinkLine>=0 )
|
|
||||||
{
|
|
||||||
if( Left(Lines[HoverOverLinkLine].URL,8)~="kfurl://" )
|
|
||||||
LaunchKFURL(Mid(Lines[HoverOverLinkLine].URL,8));
|
|
||||||
else if( Left(Lines[HoverOverLinkLine].URL,5)~="kf://" )
|
|
||||||
ChangeGameURL(Mid(Lines[HoverOverLinkLine].URL,5));
|
|
||||||
else LaunchURLPage(Lines[HoverOverLinkLine].URL);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
delegate LaunchKFURL( string URL );
|
|
||||||
delegate ChangeGameURL( string URL )
|
|
||||||
{
|
|
||||||
Class'SRLevelCleanup'.Static.AddSafeCleanup(PlayerOwner(),URL);
|
|
||||||
}
|
|
||||||
delegate LaunchURLPage( string URL )
|
|
||||||
{
|
|
||||||
PlayerOwner().Player.Console.DelayedConsoleCommand("START "$URL);
|
|
||||||
}
|
|
||||||
|
|
||||||
defaultproperties
|
|
||||||
{
|
|
||||||
bNeedsInit=true
|
|
||||||
|
|
||||||
PropagateVisibility=true
|
|
||||||
OnDraw=RenderHTMLText
|
|
||||||
OnClick=LaunchURL
|
|
||||||
Begin Object Class=GUIVertScrollBar Name=TheScrollbar
|
|
||||||
bBoundToParent=true
|
|
||||||
bScaleToParent=true
|
|
||||||
WinWidth=0.03
|
|
||||||
WinLeft=0.97
|
|
||||||
WinTop=0.0
|
|
||||||
WinHeight=1.0
|
|
||||||
bVisible=true
|
|
||||||
PropagateVisibility=true
|
|
||||||
OnPreDraw=TheScrollbar.GripPreDraw
|
|
||||||
End Object
|
|
||||||
MyScrollBar=TheScrollbar
|
|
||||||
StyleName="NoBackground"
|
|
||||||
bAcceptsInput=True
|
|
||||||
Begin Object Class=GUIToolTip Name=GUIListBoxBaseToolTip
|
|
||||||
ExpirationSeconds=0
|
|
||||||
End Object
|
|
||||||
ToolTip=GUIListBoxBaseToolTip
|
|
||||||
|
|
||||||
WhiteColor=(R=255,G=255,B=255,A=255)
|
|
||||||
BlueColor=(R=0,G=0,B=255,A=255)
|
|
||||||
RedColor=(R=255,G=0,B=0,A=255)
|
|
||||||
}
|
|
@ -64,4 +64,5 @@ function DrawMenu()
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -2,4 +2,5 @@ Class KFGUI_ScrollBarH extends KFGUI_ScrollBarBase;
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -49,4 +49,5 @@ function DrawMenu()
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -64,4 +64,5 @@ function PreDraw()
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -68,4 +68,5 @@ final function RenderProgress()
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -2,4 +2,5 @@ Class SRPerkManager extends ExtPerkManager;
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -257,4 +257,5 @@ function SetSaveVersion(int Num)
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
@ -34,4 +34,5 @@ event AllowBroadcastLocalizedTeam(int TeamIndex, actor Sender, class<LocalMessag
|
|||||||
|
|
||||||
defaultproperties
|
defaultproperties
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
Loading…
x
Reference in New Issue
Block a user