Some way to attach code to struct?

Vexorian

Why no custom sig?
Reaction score
187
Yeah well, that's an excuse rather than a reason. Globals are useless.

If I was your user, assuming you are making a projectile system, I would like sometimes to make a spell in which a unit throws grenades to a target point for 30 seconds, on impact a grenade does damage and perhaps something. Multi instancibility demands that every grenade keeps its own data, also, every grenade requires at least 2 data fields, unit of origin and level of the spell...

But I made spells in which I even needed 10 different fields...

Passing globals to the user was not that good even in pre-vJass era, right now it looks like quite a bad thing to do since you can pass arguments now...

Edit: If you still don't want interfaces, make sure to at least give users a chance to specify their own integer field , and lamely pass such field with your globals...
 

Trollvottel

never aging title
Reaction score
262
Yeah well, that's an excuse rather than a reason. Globals are useless.

If I was your user, assuming you are making a projectile system, I would like sometimes to make a spell in which a unit throws grenades to a target point for 30 seconds, on impact a grenade does damage and perhaps something. Multi instancibility demands that every grenade keeps its own data, also, every grenade requires at least 2 data fields, unit of origin and level of the spell...

But I made spells in which I even needed 10 different fields...

Passing globals to the user was not that good even in pre-vJass era, right now it looks like quite a bad thing to do since you can pass arguments now...

Edit: If you still don't want interfaces, make sure to at least give users a chance to specify their own integer field , and lamely pass such field with your globals...


hm the integer field for the level or something like this? well i could do that, yeah. i'd use interfaces if i had an idea how to use them to attach a function to them, but i haven't so i am kinda forced not to use them :eek:
 

Trollvottel

never aging title
Reaction score
262
hm the longer i think about it the better find it. so i have to attach the interface to my struct?
 

Magentix

if (OP.statement == false) postCount++;
Reaction score
107
Make an interface interfaceName and then write extends interfaceName behind the structname of every struct that uses it.

JASS:
interface Object
    method move takes nothing returns nothing
endinterface

// Struct where move() moves it to x and y
struct Instance1 extends Object
    real x = 1.00
    real y = 1.00
    unit thisUnit

    method move takes nothing returns nothing
        call SetUnitX(.thisUnit,.x)
        call SetUnitY(.thisUnit,.y)
    endmethod
endstruct

// Struct where move() moves it to the center of the map
struct Instance2 extends Object
    unit thisUnit

    method move takes nothing returns nothing
        call SetUnitX(.thisUnit,0.00)
        call SetUnitY(.thisUnit,0.00)
    endmethod
endstruct
 

Trollvottel

never aging title
Reaction score
262
yes i already knew that but thank you.


i meant it like this:
JASS:
interface someinterface 
method myfunc takes nothing returns nothing
endinterface


function ThrowAndDo takes args....., SomeInterface func returns nothing
 ....blahblah....
endfunction


JASS:
struct test extends someinterface
  method myfunc takes nothing returns nothing
    // actions here
  endmethod
endstruct

function test
 local test struct = test.create()
 call ThrowAndDo(.....,struct) 
endfunction


would that work?
 

Magentix

if (OP.statement == false) postCount++;
Reaction score
107
I'm not sure, but you can do it like this:

JASS:
interface someinterface 
method myfunc takes nothing returns nothing
endinterface

struct test extends someinterface
  method myfunc takes nothing returns nothing
    // actions here
  endmethod
endstruct

function ThrowAndDo takes args....., someinterface s returns nothing
 ....blahblah....
    call s.myfunc() // Use this instead of "code myfunc" inside a Timercallback,  ForGroup, etc...
endfunction

function testInterface
 local test s = someinterface.create()
 call ThrowAndDo(.....,s) 
endfunction


Edit: I realise it's "the same", but I wanted to show you where the myfunc is used.
 

Trollvottel

never aging title
Reaction score
262
ok thx well its not used there its only stored there and called later but now i know how to do it, thanks
 

Cohadar

master of fugue
Reaction score
209
Edit: I mean, if you were to ask a user, what's better:

"make a boolexpr and add it as an argument to my function"
"Add your function as code argument to my function"
"Type FunctionInterfaceName.functionname "

All three of them look like equal non-sense to me. But at least the function interface will save every one work, you will not have to bother creating triggers at map init your self. And you can just as easily decide between .evaluate or .execute.

I was thinking on making just functionname work, or perhaps I'll make up something like "somekeyword functionname" to make it look like Jass' code but I've been too busy.

The amount of work has absolutely no impact on me as a system maker.
My primary concern is how easy it is for others to use my systems.
In the case of TT I had exact same choices you mentioned:
JASS:

call TT_Start(Condition(function userFunc), data)
call TT_Start(function userFunc, data)
call TT_Start( TT_Ifunction.userFunc, data)


I think it is obvious why I picked passing function as code in spite of the extra work for me.

My claim that function interfaces (in the state they are now) fail as a syntax sugar still stands.
You cannot blame it on people that they are simply making excuses not to learn it because of the number of people that learned and use structs.

Therefore I suggest you make the keyword ifunction.
(using bare function name would just create you too much problems.)

and with that keyword the difference between native jass and function interfaces would be this:

Code:
[COLOR="Blue"]call[/COLOR] TT_Start([B]function[/B] userFunc, data)
[COLOR="Blue"]call[/COLOR] TT_Start([B]ifunction[/B] userFunc, data)

Now THAT is what I call a syntax sugar.
 

Trollvottel

never aging title
Reaction score
262
hm i dont know. it is even more work for me and for every user of the system to use these interfaces and the only and only difference is that i have no globals, but struct members. it seems that i cant use waits in methods, but i wouldnt use waits in my old way too, because it used globals. so its just more work and harder to understand for not so expierienced jassers if I use interfaces IMHO.
 

Waaaaagh

I lost all my rep and my title being a jerk
Reaction score
70
JASS:
function interface ifunction takes TYPE t returns TYPE


And just how does your 'ifunction' keyword work? The thing that makes function interfaces work is that they are the same somehow. If, instead of taking specific arguments, it could take anything, it loses its value as an interface. So, ifunction is useless. If you want to use it, go right ahead. Type the line of code above. But, currently, the name of the interface defines the parameters AND the fact that it's an interface. If we could remove that period, then yah, syntax sugar. But your 'ifunction' is either supurflous, or retarded.

Structs are still way better for this sort of thing, from a syntax view. They look so nice.

JASS:
struct ObjectData
    unit Unit
    vector Position
    vector Velocity
    vector Acceleration
    ObjectType Object
endstruct

interface ObjectType
    ObjectData TriggerObject
    ObjectData OtherObject

    method onBounce takes nothing returns nothing defualts nothing
    method onCollide takes nothing returns nothing defaults nothing
    method onTimeStep takes nothing returns nothing defaults nothing
endinterface

struct Ball extends ObjectType
    real Points

    method onBounce takes nothing returns nothing
        call .TriggerObject.destroy()
    endmethod

    method onCollide takes nothing returns nothing
        set .OtherObject.Object.Points = .OtherObject.Object.Points + .TriggerObject.Points
        call .TriggerObject.destroy()   
    endmethod

    method onTimeStep takes nothing returns nothing
        set .Points = .Points+1
    endmethod
endstruct


Of course, that's a terrible way to do it, but I think it looks nice. That's my opinion though. Also, the example won't work cause it takes 2 in a collision, and both would be destroyed. Wtv. :/
 

Trollvottel

never aging title
Reaction score
262
it looks nice is no argument. and if it is an argument it is a very bad. why should i write tons of text just to have the code look more nicely? even the user had to type more and it would be more complicated for him.

if you had the choice between

1. creating a struct with your function
2. creating the struct in your function where you call the function to throw

and

1.creating the function and use it as argument

with exactly the same effect, which one would you choose?
 

Waaaaagh

I lost all my rep and my title being a jerk
Reaction score
70
The point is that, since Ball extends ObjectType, you can loop through ObjectType in the background, and automatically acquire ObjectType. But either way, just making the function is prolly a better enduser interface.
 

Cohadar

master of fugue
Reaction score
209
hm i dont know. it is even more work for me and for every user of the system to use these interfaces and the only and only difference is that i have no globals, but struct members. it seems that i cant use waits in methods, but i wouldnt use waits in my old way too, because it used globals. so its just more work and harder to understand for not so expierienced jassers if I use interfaces IMHO.

I agree. (that talk was between Vexorian and me)


@Waaaaagh
You totally did not understand what I was talking about.
 

Cohadar

master of fugue
Reaction score
209
But, currently, the name of the interface defines the parameters AND the fact that it's an interface.

no, the NameOfTheInterface.NameOfTheFunction defines that,
For example:
JASS:

function interface IBinary takes integer a, integer b returns integer
//--------
function Add takes integer a, integer b returns integer
function Sub takes integer a, integer b returns integer
//--------
call IBinary.Add(3,4).evaluate()
call IBinary.Sub(3,4).evaluate()
//--------
function ParamFunc takes IBinary operation, integer a, integer b returns integer
call ParamFunc(IBinary.Add, 3, 4)


As opposed to:
JASS:

function interface IBinary takes integer a, integer b returns integer
//--------
function Add takes integer a, integer b returns integer
function Sub takes integer a, integer b returns integer
//--------
call Add(3,4).evaluate()
call Sub(3,4).evaluate()
//--------
function ParamFunc takes IBinary operation, integer a, integer b returns integer
call ParamFunc(ifunction Add, 3, 4)


The difference being that calls are independent of IBinary keyword.
This is of course harder to make because compiler must remember interface names and use them in current context to link to appropriate functions.

Well it is all meh.
 

Waaaaagh

I lost all my rep and my title being a jerk
Reaction score
70
But if we are going to do that, why not take out the ifunction 'code', and just use straight function? That way, it would just check to see if the function follows the rules, and then, if not, report an error. We start to do it dynamically, rather than having to sort of 'declare' each one.
 

Cohadar

master of fugue
Reaction score
209
Hm, yes, no, maybe, depends, it does not matter.
Because none of us is making the jasshelper compiler, Vexorian is.

So I will just leave it up to him.
Ok so he could have done some things better, but it is the best thing we got so far, and I don't really have problems with all of this because the fact some things in vJass are not noob-friendly has no effect on me :)
 
General chit-chat
Help Users
  • No one is chatting at the moment.

      The Helper Discord

      Staff online

      Members online

      Affiliates

      Hive Workshop NUON Dome World Editor Tutorials

      Network Sponsors

      Apex Steel Pipe - Buys and sells Steel Pipe.
      Top