SymbolShift Posted April 28, 2022 Author Report Share Posted April 28, 2022 1 hour ago, Norman Sword said: Assuming you can draw the rope. Starting at the top we count the pixels drawn for the rope draw. If Not attached to the rope. Each cell drawn is tested for collision. if collision then willy is attached to the rope at that point. If attached to the rope. The cell that is assigned as the collision point (as above) is used as the x,y position to draw Willy - (slight shift adjustment needed in zx spectrum code) To move on the rope the point of collision is moved up or down the rope To detach from the rope. A timer is set and Willy is cell aligned and exits from the rope. Thanks again, that's good info. I might give the rope a go later on. I checked in an emulator, and the JSW rope is a lot more "flowing" than I remember (almost like a wind is blowing it as it swings), so I'm not terribly sure on how to reproduce that. Is there a simple breakdown on how the rope pixels are generated, to create that wind-flowing/swinging pattern? jetsetdanny 1 Quote Link to comment Share on other sites More sharing options...
Norman Sword Posted April 28, 2022 Report Share Posted April 28, 2022 (edited) The rope is very simple in operation. Matthews code does its best to obscure that simplicity. The rope data has offsets for x and y. - the data below is padded out to 256 bytes rope_table_X: DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00 DATA &H01,&H01,&H01,&H01,&H01,&H01,&H01,&H01 DATA &H01,&H01,&H01,&H01,&H02,&H02,&H02,&H02 DATA &H02,&H02,&H02,&H02,&H02,&H02,&H02,&H02 DATA &H02,&H02,&H02,&H02,&H02,&H02,&H02,&H02 DATA &H02,&H02,&H01,&H02,&H02,&H01,&H01,&H02 DATA &H01,&H01,&H02,&H02,&H03,&H02,&H03,&H02 DATA &H03,&H03,&H03,&H03,&H03,&H03 ;================== DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00 DATA &H00,&H00 ' y-coordinate shift rope_table_Y: DATA &H06,&H06,&H06,&H06,&H06,&H06,&H06,&H06 DATA &H06,&H06,&H06,&H06,&H06,&H06,&H06,&H06 DATA &H06,&H06,&H06,&H06,&H06,&H06,&H06,&H06 DATA &H06,&H06,&H06,&H06,&H06,&H06,&H06,&H06 DATA &H06,&H06,&H06,&H06,&H06,&H06,&H06,&H06 DATA &H06,&H06,&H06,&H06,&H06,&H06,&H06,&H06 DATA &H04,&H06,&H06,&H04,&H06,&H04,&H06,&H04 DATA &H06,&H04,&H04,&H04,&H06,&H04,&H04,&H04 DATA &H04,&H04,&H04,&H04,&H04,&H04,&H04,&H04 DATA &H04,&H04,&H04,&H04,&H04,&H04,&H04,&H04 DATA &H04,&H04,&H04,&H04,&H04,&H04 ;=========== DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00 DATA &H00,&H00 simple logic for animation A pointer is set as an offset into the data (as above) The pointer has two other variables - side and step The step is added to the offset. if the offset is now 0 then reverse the step and reverse the side - simply negate the side and step. if the offset is maximum the reverse the step- Simply negate the step The above is the core logic for animation -------------------------- To draw- start x=128; start y=0: loop draw point x,y Take the offset into the above data - find the x entry - delta x- and if side is 1 add delta x to x ; if side is -1 deduct delta x from x Take the offset into the above data : find the y entry and add to the y add 1 to the offset loop for the length of the rope the above will need adjustments, with the size of steps and length of rope etc =but will draw the rope. Edited April 28, 2022 by Norman Sword Spider, MtM, SymbolShift and 1 other 1 3 Quote Link to comment Share on other sites More sharing options...
CPL Posted April 28, 2022 Report Share Posted April 28, 2022 (edited) OK. I'll try and explain as best I can how I've done it from a GMS2 perspective. I'm a hobbyist coder in games terms and a bit messy in all honesty, so apologies for inconsistent naming schemes. I have a SPRITE defined for a single rope segment - in my version it's a 4x4 white square because I've done everything at 4x resolution in case I ever want to do an 'HD' version in future. eg. Willy's sprite is 64x64. I have 2 OBJECTS defined - one I call a "RopeGenerator", and another which I call "RopeSpriteSegment". The RopeGenerator is the object which actually gets put into the room. The RopeSpriteSegment has no code in it, but has two Variable Definitions - "parent_instance" and "segment_id". I've attached a very roughly commented extract from various GMS scripts shoved into a .txt file which drive the ropes / player in my remake. You'll probably have to work a fair few bits out yourself to relate it to your code, but it should give you a starting point and at least let you understand how the ropes are formed. When I saw how simple and elegantly Matthew Smith had done the rope I was really quite impressed. EDIT: Sorry there are a few typos in the text file I've just seen - 32 vs 33 segments (yay off by one errors!) etc, but the gist is there. RopeCode.txt Edited April 28, 2022 by CPL jetsetdanny and Spider 2 Quote Link to comment Share on other sites More sharing options...
CPL Posted April 28, 2022 Report Share Posted April 28, 2022 You should be able to see that the rope_X_Table and rope_Y_Table are just the data lists NormanSword has put above in array form. Spider and jetsetdanny 2 Quote Link to comment Share on other sites More sharing options...
SymbolShift Posted April 28, 2022 Author Report Share Posted April 28, 2022 (edited) Thanks to Norman and CPL for sharing this valuable information. I think I have enough to "give it a go", but will probably end up with a list of questions 😁 When you think about it, Matthew Smith was a clever bugger, working out all this stuff in the early 80's, in Z80 assembler, considering his age. Using tables to store the rope pattern makes total sense, rather than some complex maths formula. I always assumed it used a Sine wave algorithm to generate the swing. The GMS2 code snippets provided by CPL will be super helpful also. I am also a "hobbyist coder" and would never call myself a proper programmer, so I will excuse your messy code 😄 Edited April 28, 2022 by SymbolShift jetsetdanny and Spider 2 Quote Link to comment Share on other sites More sharing options...
IRF Posted May 1, 2022 Report Share Posted May 1, 2022 On 4/28/2022 at 8:55 PM, SymbolShift said: Matthew Smith was a clever bugger Was he a clever de-bugger though? 😄 Spider, jetsetdanny and SymbolShift 1 2 Quote Link to comment Share on other sites More sharing options...
SymbolShift Posted May 14, 2022 Author Report Share Posted May 14, 2022 After implementing my rope, I am still somewhat bewildered as to why Matthew Smith used the control system he used for climbing up/down the rope. The climbing logic used in JSW is... Rope swinging left: left key = climb down / right key = climb up Rope swinging right: left key = climb up / right key = climb down Anyone I know who jumps on a rope for the first time is totally baffled on how to control Willy, as the climbing direction reverses when the swing direction changes. That said, after a while, you do eventually get used to it. I have coded the above method in my game (since it's true to JSW), but I did try a simplified version (left = up, right = down, no matter what swinging direction) and it seemed way more logical. I wonder if there was a valid reason that Matthew Smith programmed it this way. Maybe there IS a reason? or maybe it's just a side-effect of lazy coding? Would love to hear any thoughts on this. jetsetdanny and Spider 2 Quote Link to comment Share on other sites More sharing options...
Spider Posted May 14, 2022 Report Share Posted May 14, 2022 It does catch the un-initiated out ! I'd speculate it was done that way to make it harder to control him on a rope, as it seems easier to code it as a fixed method , at least from a players perspective. I can see the logic in some ways if you think of it differently in that JSW does not have an up/down control so to reverse left/right for rope climbing/descending does make a bit of sense too. Have you compared this to JSW2 or perhaps JSW on other platforms ? I can't recall immediately offhand if they differ and I don't have access at this moment to check for instance the BBC or CBM version out. SymbolShift 1 Quote Link to comment Share on other sites More sharing options...
MtM Posted May 14, 2022 Report Share Posted May 14, 2022 1 hour ago, SymbolShift said: After implementing my rope, I am still somewhat bewildered as to why Matthew Smith used the control system he used for climbing up/down the rope. The climbing logic used in JSW is... Rope swinging left: left key = climb down / right key = climb up Rope swinging right: left key = climb up / right key = climb down Anyone I know who jumps on a rope for the first time is totally baffled on how to control Willy, as the climbing direction reverses when the swing direction changes. That said, after a while, you do eventually get used to it. I have coded the above method in my game (since it's true to JSW), but I did try a simplified version (left = up, right = down, no matter what swinging direction) and it seemed way more logical. I wonder if there was a valid reason that Matthew Smith programmed it this way. Maybe there IS a reason? or maybe it's just a side-effect of lazy coding? Would love to hear any thoughts on this. It always seemed fairly intuitive to me for some reason, I don't know why. Maybe that was the same reason for MS? Spider, SymbolShift and jetsetdanny 3 Quote Link to comment Share on other sites More sharing options...
Norman Sword Posted May 14, 2022 Report Share Posted May 14, 2022 (edited) Taking the actual code used to control Willy on the rope . It took me all of 1 second to change the logic. This original is deliberate and very logical in the manor of control. Walking up a stair you press against the stair, to move down a rope you press against the rope. Which to me is reverse logic, but still a consistant logic. To modify to play as you mentioned is the lazy way of coding the movement and not the other way around. Note the ease of modification Part of the rope swing LD A,(willy_dir) ; #9375 ;#85D0 Pick up Willy's direction and movement flags from #85D0 BIT 1,A ; #9378 ; Is Willy moving up or down the rope? JR Z,next_entity_draw ; #937A ;#93b3 If not, jump to consider the next entity ;CHANGE CODE FROM ; RRCA ; #937C ; XOR Willy's direction bit (0=facing right, 1=facing left) with the rope's direction bit ;; ;; ; (0=swinging right to left, 1=swinging left to right) ; XOR (IX+rope00) ; #937D ; ; RLCA ; #9380 ; ; RLCA ; #9381 ; Now A=1 if Willy is facing the same direction as the rope is swinging (he will move down the rope), ;; ;; ; or -1 otherwise (he will move up the rope) ; CHANGE CODE TO RLCA ; #937C NOP ; #937D NOP ; #937E NOP ; #937F NOP ; #9380 NOP ; #9381 ;>> back to the normal logic AND #02 ; 9382 ; DEC A ; 9384 ; included is a file with the rope swinging in such a way. NOTE this file is so close to the original --- it might still have the attic bug --- I can not remember. Addendum:- easier is to just zero out #937c, #937d, #937e, #937f, #9380. -- five 0(zero) pokes. jsw rope swing.tap Edited May 15, 2022 by Norman Sword Deleted excess code information. Spider, jetsetdanny and SymbolShift 2 1 Quote Link to comment Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.