Author Topic: [Suggestion] Addition to rects in mapScripts  (Read 1487 times)

Offline Finnik

  • Colonel
  • ****
  • Posts: 490
  • Finnik#0257
    • View Profile
[Suggestion] Addition to rects in mapScripts
« on: January 11, 2020, 07:57:02 pm »
I've spent some time researching the problem, and I would like to discuss it. Let's look at vanilla urban terrain mapScript:

Code: [Select]
  - type: URBAN
    commands:
    - type: addCraft
    - type: addLine
      label: 1
      direction: vertical
      executionChances: 50
      rects:
        - [1, 1, 4, 1]
    - type: addLine
      label: 2
      conditionals: -1
      executionChances: 50
      direction: horizontal
      rects:
        - [1, 1, 1, 4]
    - type: addLine
      conditionals: [-1, -2]
      direction: both
      rects:
        - [1, 1, 4, 4]
    - type: addBlock
      size: 2
      executions: 4
    - type: fillArea
      blocks: [3, 4, 10, 11, 12, 13, 14]
      freqs: [3, 3, 2, 2, 2, 2, 2]
Here rects numbers like [1, 1, 4, 4] suppose you have constant map size, but it is defined in alienDeployment. If we will want to use this script in multiple deployments we will need to make copies of this script for each map size, which makes mod far less manageable, especially if we have complicated scripts. For example, we want to use the complex script for urban maps with map sizes from 40 (where you need to capture single or 2 enemy units) to 80, where there are huge war actions. It would be cool if we can define a number for rect from map size, for example, mapsize - 1. I've thought about it for some time and here what I'm suggesting.
As game expect rect numbers to be integers, we can use negative values for that. As we need to keep 0, you know, as 0, I suggest to treat value '-1' equal to map size, '-2' as map size - 1 and so on (if i < 0; i=mapsize - i + 1).
Thus, suggesting syntax would be like
Code: [Select]
    - type: addCraft
      rects:
        - [1, 1, -2, -2]
That makes sure we will not place xcom craft near the map border no matter what map sizes are. That can make sense if its map is. for example, a cave exists to all sides, and you don't want it to lead nowhere. Speaking of cave maps, there could be a funny script that will make a cave with no exits outside of the map:

Code: [Select]
  - type: TEST_CAVE_SCRIPT
    commands:
    - type: addCraft #handle xcom spawn
      rects:
        - [1, 1, -2, -2]
    - type: addLine
      direction: both
      verticalGroup: 4 #west border group
      horizontalGroup: 5 #north border group
      crossingGroup: 6 #NW corner group
      rects:
        - [0, 0, 1, 1] #places it to upper NW map corner
    - type: addLine
      direction: both
      verticalGroup: 7 #east border group
      horizontalGroup: 8 #soth border group
      crossingGroup: 9 #SE corner group
      rects:
        - [-2, -2, -1, -1] #places it to upper SE map corner
    - type: removeBlock #handle NE corner
      rects:
        - [-2, 0, -1, 0]
    - type: addBlock
      rects:
        - [-2, 0, -1, 0]
      groups: 10
    - type: removeBlock #handle SW corner
      rects:
        - [0, -2, 0, -1]
    - type: addBlock
      rects:
        - [0, -2, 0, -1]
      groups: 11
    - type: fillArea
      rects:
        - [1, 1, -2, -2]
      groups: [3]

I was looking to code and I'm confused with mapScripts, I'm not sure how ti do that elegant way. Rects processing is called multiple times by commands with a little difference. Probably I should make some method to process negative values before general processing, but i don't know how to insert it to selectPosition method same way and constructions like this look ugly to me:
Code: [Select]
bool BattlescapeGenerator::removeBlocks(MapScript *command)
{
std::vector<std::pair<int, int> > deleted;
bool success = false;

for (std::vector<SDL_Rect*>::const_iterator k = command->getRects()->begin(); k != command->getRects()->end(); ++k)
{
if ((*k)->x < 0) {
(*k)->x = (*k)->x - _mapsize_x + 1;
}
if ((*k)->y < 0) {
(*k)->y = (*k)->y - _mapsize_y + 1;
}
if ((*k)->w < 0) {
(*k)->w = (*k)->w - _mapsize_x + 1;
}
if ((*k)->h < 0) {
(*k)->h = (*k)->h - _mapsize_y + 1;
}
for (int x = (*k)->x; x != (*k)->x + (*k)->w && x != _mapsize_x / 10; ++x)
{
for (int y = (*k)->y; y != (*k)->y + (*k)->h && y != _mapsize_y / 10; ++y)

I wonder if i can place some processing in getRects method itself, but for it I need to transfer mapsize we have to it as arguments. Also, I think I should not place such calculations to a Mod part. I would be glad for any feedback and if the idea itself is worthful - some coding advice to implement it in a good way.

Offline Solarius Scorch

  • Global Moderator
  • Commander
  • *****
  • Posts: 11408
  • WE MUST DISSENT
    • View Profile
    • Nocturmal Productions modding studio website
Re: [Suggestion] Addition to rects in mapScripts
« Reply #1 on: January 11, 2020, 11:10:31 pm »
I can't say I understand the code, but I certainly understand the benefit.