| 01-20-2008, 04:34 AM | #1 |
This spell creates a area of ice and then after a set amount of time changes it back to the original terrain. It works fine but if you cast the ability on the buttom left of the map it doesn't work. The first jass code is what (i think) is giving me problems and the second is the whole thing. Download the map if you don't want to go though the trouble of setting it up. JASS:loop //Changes the terrain back to normal depending on if ix/iy is 0 (no reset) or 1 (reset) loop if block[(i[2] * RADIUS) + i[1]] == 1 then //Just assume this is always true call SetTerrainType(x + I2R((i[1] * 128)), y - (I2R(i[2] * 128)), te[R2I(y / 128) - i[2]].t[R2I(x / 128) + i[1]], va[R2I(y / 128) - i[2]].v[R2I(x / 128) + i[1]], 1, 1) endif set i[1] = i[1] + 1 //Simply moves y to next place along its axis exitwhen i[1] == RADIUS * 2 endloop set i[2] = i[2] + 1 set i[1] = 0 exitwhen i[2] == RADIUS * 2 endloop JASS:scope Ice globals //You can edit anything here private constant integer AID_ABILITY = 'A000' //The ability private constant integer TID_TERRAINTYPE = 'Iice' //Whatever type of terrain you want to use. I can change this to use a list of different terrains and variances, just ask. private constant integer TID_VARIANCE = -1 //Each terrain type should have 18 variances. Use -1 for random variances private constant integer RADIUS = 3 //size/area affected; one equals one block (128x128); just do some testing with it and use lowest numbers private constant integer SHAPE = 1 //0=circle; 1=square; Should I add different shapes? private constant real RESET = 5.00 //How long to wait before changing the area back to normal for a level 1 ability private constant real RESET_PRELEVEL = -1.00 //How much time to add/subtract per level private constant integer MAP_SIZE_X = 32 //Width: Left/Right private constant integer MAP_SIZE_Y = 32 //Height: Up/Down endglobals private struct data //For each instace of the ability real x //simple casting point aligned to the grid real y //simple casting point aligned to the grid endstruct private struct terrain integer array t[MAP_SIZE_X] //Terrain Types endstruct private struct variance integer array v[MAP_SIZE_X] //Terrain Variances endstruct globals //Used for struct globals terrain array te //Used for terrain type storage. NOT PRIVATE; can be used by other triggers. variance array va //Used for terrain type storage. NOT PRIVATE; can be used by other triggers. private data array index //Index for the struct "data" endglobals private function TerrainReset takes nothing returns nothing //Changes a select area back to normal terrain local data s = index[0] local data s2 local integer array i //Loop array local real x = s.x - (RADIUS * 128) //Current struct instance local real y = s.y + (RADIUS * 128) //Changes the casting point to the top/left of the area effected (iced) local real x2 //Some other struct instance local real y2 //Some other struct instance local real array block //Used to keep track of which blocks should NOT be reset; 0=no reset, and 1=reset. set i[1] = 0 loop //Presets the reset/no-reset terrain thing to 1, which can be altered/changed later. set block[i[1]] = 1 set i[1] = i[1] + 1 exitwhen i[1] == (RADIUS + RADIUS) * (RADIUS + RADIUS) endloop set i[6] = 0 loop //Checks every struct to see if any will effect this one set i[6] = i[6] + 1 exitwhen index[i[6]] == null set s2 = index[i[6]] //Checks the distance between every other instance. Can't have the ice disappearing if another ability is over it. if SquareRoot((s2.x + s.x) * (s2.x + s.x) + (s2.y - s.y) * (s2.y - s.y)) <= RADIUS * 2 * 128 and s != s2 then set x2 = s2.x + (RADIUS * 2 * 128) //Same as above but for the infringing instance set y2 = s2.y - (RADIUS * 2 * 128) //Same as above set i[1] = 0 //x set i[2] = 0 //y set i[3] = 0 //x2 set i[4] = 0 //y2 set i[5] = 0 //Counter for wait/sleep call BJDebugMsg("2.1") //I used if statements instead of extra loops; It was confusing to read with all those loops. //Some extra code can be added to decrease the number of checks; simply change where x/y starts and ends to decrease the area that needs to be checked. loop loop loop loop if x - (i[1] * 128) == x2 - (i[3] * 128) and y + (i[2] * 128) == y2 + (i[4] * 128) then //Checks if the x/y points are equal to any of the tx/ty points set block[i[1] * RADIUS + i[2]] = 0 //Sets the terrain reset to no endif set i[3] = i[3] + 1 set i[5] = i[5] + 1 if i[5] == 2000 then set i[5] = 0 call TriggerSleepAction(0.01) endif exitwhen i[3] == RADIUS * 2 endloop set i[3] = 0 set i[4] = i[4] + 1 exitwhen i[4] == RADIUS * 2 endloop set i[1] = i[1] + 1 exitwhen i[1] == RADIUS * 2 endloop set i[1] = 0 set i[2] = i[2] + 1 exitwhen i[2] == RADIUS * 2 endloop endif endloop //This is the closing for the distance check loop and if statment set i[1] = 0 //X set i[2] = 0 //Y loop //Changes the terrain back to normal depending on if ix/iy is 0 (no reset) or 1 (reset) loop if block[(i[2] * RADIUS) + i[1]] == 1 then call SetTerrainType(x + I2R((i[1] * 128)), y - (I2R(i[2] * 128)), te[R2I(y / 128) - i[2]].t[R2I(x / 128) + i[1]], va[R2I(y / 128) - i[2]].v[R2I(x / 128) + i[1]], 1, 1) endif set i[1] = i[1] + 1 //Simply moves y to next place along its axis exitwhen i[1] == RADIUS * 2 endloop set i[2] = i[2] + 1 set i[1] = 0 exitwhen i[2] == RADIUS * 2 endloop call s.destroy() set i[1] = 0 //index number loop //Moves all the structs (integers) one index down on the array set i[1] = i[1] + 1 if index[i[1]] == null or index[i[1]] == 0 then set index[i[1] - 1] = 0 exitwhen true endif set index[i[1] - 1] = index[i[1]] endloop set index[0] = 0 call BJDebugMsg("Terrain Reset") endfunction private function Queue takes nothing returns nothing //A never stopping loop loop call TriggerSleepAction(0.50) if index[0] != 0 then call TerrainReset.execute() endif endloop endfunction private function TerrainChange takes nothing returns nothing //Changes a select area into ice terrain local integer i = 0 local real x = I2R(R2I(GetLocationX(GetSpellTargetLoc()) / 128) * 128) //Aligns the X point to the closest grid point of a multiple of 128 local real y = I2R(R2I(GetLocationY(GetSpellTargetLoc()) / 128) * 128) //Aligns the Y point to the closest grid point of a multiple of 128 call BJDebugMsg("First:" + R2S(x) + "/" + R2S(y)) call SetTerrainType(x, y, TID_TERRAINTYPE, TID_VARIANCE, RADIUS, SHAPE) //Change to use selective shapes and such call TriggerSleepAction(RESET + (RESET_PRELEVEL * GetUnitAbilityLevel(GetTriggerUnit(), GetSpellAbilityId()))) loop //Finds a empty index for the struct if index[i] == null or index[i] == 0 then set index[i] = data.create() set index[i].x = x set index[i].y = y exitwhen true endif set i = i + 1 endloop call BJDebugMsg("Terrain Changed") endfunction private function Conditions takes nothing returns boolean return GetSpellAbilityId() == AID_ABILITY endfunction public function InitTrig takes nothing returns nothing local trigger t1 = CreateTrigger() local integer array i local rect r = GetWorldBounds() local real x = GetRectMinX(r) local real y = GetRectMaxY(r) //------------------------------------------------ set i[1] = 0 loop call TriggerRegisterPlayerUnitEvent(t1, Player(i[1]), EVENT_PLAYER_UNIT_SPELL_CAST, null) set i[1] = i[1] + 1 exitwhen i[1] == 12 endloop call TriggerAddCondition(t1, Condition(function Conditions)) call TriggerAddAction(t1, function TerrainChange) //------------------------------------------------ call RemoveRect(r) set i[1] = 0 //X set i[2] = 0 //Y loop set te[i[2]] = terrain.create() set va[i[2]] = variance.create() loop set te[i[2]].t[i[1]] = GetTerrainType(x + (128 * i[1]), y - (128 * i[2])) set va[i[2]].v[i[1]] = GetTerrainVariance(x + (128 * i[1]), y - (128 * i[2])) set i[1] = i[1] + 1 exitwhen i[1] == MAP_SIZE_X + 1 endloop set i[1] = 0 set i[2] = i[2] + 1 exitwhen i[2] == MAP_SIZE_Y + 1 endloop set index[0] = 0 call Queue.execute() endfunction endscope |
| 01-20-2008, 10:25 AM | #2 |
Your function is totally obfuscated by the fact you are using a friging array instead of correctly named variables. |
| 01-20-2008, 10:32 AM | #3 | |
Quote:
|
| 01-20-2008, 07:36 PM | #4 |
@Vex - I don't understand. Do you know it's so messed up you can't read/understand it? Please clarify. @zen87 - Doesn't seem wrong to me. The map size can be anything from 32-256 (I think WE Unlimted can do larger?). Anyways, in a map of 32x32 (2944x2944 ingame) you have 1024 "blocks" which you need to save their information. Each block being 128x128 (that's the size each block of terrain is). Two arrays of 1024 would work for a 32x32 game, one to hold the terrain type, and the other the variance of the terrain. But, if you have a game of 256x256 you'd need an array of 65536, the games arrays stop at around 8100. To deal with the problem I could create a set of array in a box type (sorry I don't know the proper term). 256 arrays with a size of 256 each, but this would be troublesome, plus if the game was smaller you'd want the user to delect all those extra arrays. The solution is simple (I hope), use structs and create variable arrays as needed. I could be mistaken but aren't structs like variable arrays? |
