Is it logic or should it be changed?

Discussion and feedback on Construct 2

Post » Wed Nov 30, 2016 5:22 pm

So I was doing some C2'ing and ran into a problem which I thought was a bit weird or maybe not very logic in my opinion. So I recreated it with a small example. Now its not the biggest problem in the world, but on the other hand it could lead to some very annoying problems that is hard to spot, if you are not aware of it. Anyway here is the small test program, which basically just check whether two sprites are overlapping or not, in case they are, it will write in the text box "Is overlapping" and vice versa:

Image

However if I enable the "On start of layout" and destroy the green sprite. It will no longer be able to detect whether or not these two sprites are overlapping. Which at least to me seems a bit illogic. Because clearly these two sprites are not overlapping if one of them doesn't even exist, so in my opinion it should see the condition (2) as being true and therefore write in the text that they are not overlapping.

The reason I would suggest making it so, is because there could be cases in more advanced programs where you would like to check whether one unit might not overlap another and if that's not the case it should do something. However if the unit you are checking for overlaps doesn't exist for whatever reason, lets say the player destroyed them all. Obvious you would want to execute whatever code needed when they are not overlapping. But since it works the way it does the code would not execute, which could result in unwanted/unneeded bugs.

So wouldn't it be logic to change the way it works so in cases where an object doesn't exits and you test whether its not overlapping another object, it would always be true rather than seeing the condition as being false?
B
44
S
11
G
2
Posts: 1,182
Reputation: 6,838

Post » Wed Nov 30, 2016 5:33 pm

You have to keep in mind that C2 is very "picking" driven. It picks objects to work with. Event two says "Pick the Sprite and Sprite2 that don't overlap" - there are none, since there are no Sprites to pick, so that fails. The next also obviously fails since there are no Sprites again to test, so neither condition can succeed.
You would never do it this way anyway. You would check for overlapping first, Else just do whatever. You don't need a second condition.
This isn't going to change, as the whole engine relies on the "picking" concept.
ImageImageImage
B
71
S
21
G
231
Posts: 3,688
Reputation: 129,352

Post » Wed Nov 30, 2016 8:00 pm

blackhornet wrote:You have to keep in mind that C2 is very "picking" driven. It picks objects to work with. Event two says "Pick the Sprite and Sprite2 that don't overlap" - there are none, since there are no Sprites to pick, so that fails. The next also obviously fails since there are no Sprites again to test, so neither condition can succeed.
You would never do it this way anyway. You would check for overlapping first, Else just do whatever. You don't need a second condition.
This isn't going to change, as the whole engine relies on the "picking" concept.


I get what you mean, but think it comes down to how the inverse functionality works. Lets say I wanted to get all Green sprites that are not overlapping the blue sprite. If we assume there are 5 Green sprites on the layout not overlapping the blue sprite, I could inverse the condition and it would return 5, which could be used with PickedCount, just as I could if it weren't Inversed.

So I don't think it would affect picking a great deal (Might be wrong though :D) because if we assume it worked the way I suggested, it would do the check and since there are no Green sprites it would check true in the condition but the PickedCount would be 0. And it would be no different than how it is now. I could do Green.<Variable> = 1 etc. Obviously nothing would happen, but just as you can do "Sprite_1 is overlapping Sprite_2 else Sprite_1.<Variable> = 1 (Assuming that Sprite_1 doesn't exists)

I know you can test vs. non overlapping other ways and get the number, so im not really looking for alternatives!! Its more in general. :)
B
44
S
11
G
2
Posts: 1,182
Reputation: 6,838

Post » Wed Nov 30, 2016 10:14 pm

If you are only interested in the logical part of the condition ...
and if there is only max 1 instance of both objects in the layout ...
then the correct game logic is this

https://www.dropbox.com/s/qiat3prvjajmi ... .capx?dl=0

Mostly there are more instances in the layout, usually created during run time, and a bit more then very often you want to run actions on the objects picked by the conditions. One by one in a for each or all at once.

Why make an exception for a rare case ?
B
33
S
18
G
28
Posts: 2,493
Reputation: 20,950

Post » Wed Nov 30, 2016 11:43 pm

99Instances2Go wrote:If you are only interested in the logical part of the condition ...
and if there is only max 1 instance of both objects in the layout ...
then the correct game logic is this

https://www.dropbox.com/s/qiat3prvjajmi ... .capx?dl=0

Mostly there are more instances in the layout, usually created during run time, and a bit more then very often you want to run actions on the objects picked by the conditions. One by one in a for each or all at once.

Why make an exception for a rare case ?

Im not really sure I understand what you mean?

From what I can see in your example you have simply pushed the problem by adding additional conditions. Furthermore wouldn't you agree that the way you are forced to coded it is not really an "elegant" or a logic way to do it.
Meaning its like doing

If
[X = Y then something]
else
[X not = Y then something]
else
[Y not = X then something]

And you could continue doing this depending on the amount of objects, families etc. you have in the game. Which is not really the point as I see it. Don't get me wrong I understand why you do it the way you did. But all those conditions could or should be combined into a single condition rather than having to go through all these else conditions, I think.

You are correct you could use for each and so forth to get it working. But as I mentioned above, lets say you have 5 Green sprites and want to know how many of them are not overlapping your Blue sprite under varies conditions, either if the there are no Green sprites in the game or if there are no blue sprites in the game and lets say you don't know whether there are some of them or which type, or whether there are any of them.

Obviously you can figure this out, by adding a bunch of code. However being able to simple use an inversed "Is overlapping" condition would be able to give you this answer with one check regardless of the amount of sprites and types or whether there are any at all.

I don't really see it as being a rare case, you can easily imagine situations where there might not be any enemy units, structures, power ups, bullets and so forth. And if you have code in your program that depends on whether something is overlapping something else or not, it would fail if you use an inversed condition when there are no object of the given type.

The best work around for it as I see it is to simply not use "Inversed" conditions on the top level, so you are always sure that some sort of picking have been done first. But still think that it should work the way I suggested simply because it seems most logic, at least to me. :)
B
44
S
11
G
2
Posts: 1,182
Reputation: 6,838

Post » Thu Dec 01, 2016 5:05 pm

Dont need a work around, consider proper picking. Conditions or not IF - THEN.

https://www.scirra.com/manual/75/how-events-work
B
33
S
18
G
28
Posts: 2,493
Reputation: 20,950

Post » Thu Dec 01, 2016 8:26 pm

99Instances2Go wrote:Dont need a work around, consider proper picking. Conditions or not IF - THEN.

https://www.scirra.com/manual/75/how-events-work

I don't think you really understand what im talking about and appreciate you "clever" comments regarding picking. :) However there is nothing wrong with picking in such way, its a condition like any other condition.

If you read the section in the manual about using inversed functionality:

Image

I find it sort of strange that they would use the exact same example as I did, if it were considered bad picking to do so, even if its just an example. However it mentions nothing about the problem I talk about here or that an issue could occur in case there are no monsters available, so I think its relevant to explore this issue. So please stick to the topic.
B
44
S
11
G
2
Posts: 1,182
Reputation: 6,838

Post » Thu Dec 01, 2016 11:04 pm

Dude.

ObjectA Is overlapping ObjectB

This picks all ObjectA's that overlap any ObjectB. And all ObjectB that overlap any ObjectA. It is in the first place about picking.
Secondly, yes, when there is no object ObjectA picked or/and no ObjectB, the condition marks itself as not do-able: or the logical state untrue.
(handy to follow up with an else)

True or untrue depends on the resulting picklist, not on a Basic wise IF statement.

When the condition is true, it runs its actions/subs, and in most cases we use the list of the picked objects to work with.
Or we refine the picklist with more conditions.
When the condition is untrue, it will not run its actions.

You are addressing an unreferenced object in an action. Therefor you only use, what you perceive as, the logical part of the condition. The IF THEN as you like to call it.

Addressing unreferenced objects is always something that you need to think trough.

I showed you in a capx how to deal with that. I think that was helpful and on topic.
B
33
S
18
G
28
Posts: 2,493
Reputation: 20,950

Post » Fri Dec 02, 2016 12:33 am

99Instances2Go wrote:Dude.

ObjectA Is overlapping ObjectB

This picks all ObjectA's that overlap any ObjectB. And all ObjectB that overlap any ObjectA. It is in the first place about picking.
Secondly, yes, when there is no object ObjectA picked or/and no ObjectB, the condition marks itself as not do-able: or the logical state untrue.
(handy to follow up with an else)

True or untrue depends on the resulting picklist, not on a Basic wise IF statement.

When the condition is true, it runs its actions/subs, and in most cases we use the list of the picked objects to work with.
Or we refine the picklist with more conditions.
When the condition is untrue, it will not run its actions.

You are addressing an unreferenced object in an action. Therefor you only use, what you perceive as, the logical part of the condition. The IF THEN as you like to call it.

Addressing unreferenced objects is always something that you need to think trough.

I showed you in a capx how to deal with that. I think that was helpful and on topic.


But it comes down to what you expect of the default answer that you get to your conditions and how it is handled in C2 as I see it.

For example, when you do:

If Object1 is overlapping Object2 then do something

In this case its perfectly fine if non of the objects exists, because if they don't the default answer that you get from C2 fits the question. So you get an answer that this condition is false. But since that is the exact answer you would expect to get in case one or non of these objects exists you tend to see it as being correct. And it is correct logically, if non of these objects exists obviously none of them are overlapping, therefore any actions related to this statement shouldn't be done either.

But when you inverse the condition:

If Object1 is not overlapping Object2 then do something

The logic behind this statement should be same as above. Because again if one or none of these objects exists they surely are not overlapping and therefore this condition is true. Just as if you did the check and in the start of layout destroyed Object2, then the above condition would also check true. The reason you don't see anything wrong with that, is because if Object2 doesn't exists how would Object1 be able to overlap it, therefore it has to be true. Which makes perfect sense because its the logical way you would expect it to work. But the default way that C2 check these conditions from what I can see, is that it only fits a non inverted condition. So to apply the same logic to both of them, it shouldn't matter whether its object1 or object2 that doesn't exists. The default answer that you expect from C2 should handle both types of conditions.

You are addressing an unreferenced object in an action. Therefor you only use, what you perceive as, the logical part of the condition. The IF THEN as you like to call it.


But there are no problem in addressing an unreferenced object, even if you might not notice it. if you do the following:

On start of layout
Destroy Object1

If
Object1.variable = 2
Else
Set Object1.variable = 2

C2 have no problem doing something like this even though no object exist and none are picked in the else. You can still add code to change one of its variables, position, etc. It is simply ignored. So there would be no difference in these two.

Where you might have a point as I see it when it comes to picking, is whether C2 can handle 0 picked objects. Because if you add actions to it, for instant "Set Object1.Position = X,Y" you obviously don't want all Object1's to go to that position. So it should be able to know if an inversed condition picked 0 objects and if that's the case it should not apply any actions related to these types of objects. Maybe its not possible to work with 0 picks, I don't know how that is handled in C2.
Last edited by nimos100 on Sat Dec 03, 2016 11:38 am, edited 2 times in total.
B
44
S
11
G
2
Posts: 1,182
Reputation: 6,838

Post » Fri Dec 02, 2016 1:54 pm

The 'invert' inverts the picking.

The logical 'invert', which is not really an invert - rather an 'if not true then', is ELSE.
B
33
S
18
G
28
Posts: 2,493
Reputation: 20,950

Next

Return to Construct 2 General

Who is online

Users browsing this forum: Lancifer, lukewasthefish and 9 guests