Regular transporter 'Send to' code

All topics on coding 4Dscript in Enterprise Dynamics.
Post Reply
EvelineHermans
Posts: 28
Joined: Tuesday 28 July, 2015 - 10:34

Regular transporter 'Send to' code

Post by EvelineHermans »

Hello,

I observe a problem with a regulartransporter (not an advanced). The transporter can pick up 3 different products to transport them to 3 different reservoirs:
- Product 1 goes to reservoir 1 (ch.1)
- Product 2 to reservoir 2 (ch.2)
- Product 3 to reservoir 3 (ch.3)

If the level in one of the reservoirs reaches a certain point, the inlet will close and thus no new product is accepted. Unfortunately my transporter doesn't pick that up so it then continues waiting till the level in the reservoir decreases.

Is it possible to write a 4D script that I can put in the Send to of the transporter containing:
* Send by label value (direct) (option 7)
* Only transport if level in reservoir is equal to or below X (and if more levels are equal or below X: transport to the reservoir with the lowest level).

Hope my explaination is clear!

Thanks in advance for the answer,

Eveline
User avatar
HarryBunnik
Posts: 362
Joined: Monday 07 February, 2011 - 11:22

Re: Regular transporter 'Send to' code

Post by HarryBunnik »

Ha Eveline,

Can you give me a basic model in which it occurs? Then I can think of some code to work around this.

Cheers,

Harry
EvelineHermans
Posts: 28
Joined: Tuesday 28 July, 2015 - 10:34

Re: Regular transporter 'Send to' code

Post by EvelineHermans »

Yes.. I attached a simplified model where the problem occurs.
The problem seems to occur after 1 product left the assembler. The transporter then cannot unload at server6, since reservoir9 is still full, but reservoir7 is too empty to let the process continue.

Thanks!

Eveline
Transporter_unload_problem.mod
(26.21 KiB) Downloaded 327 times
User avatar
HarryBunnik
Posts: 362
Joined: Monday 07 February, 2011 - 11:22

Re: Regular transporter 'Send to' code

Post by HarryBunnik »

Hello Eveline,

I had a look at your problem and indeed, the main thing you have to do is to check on the content of the reservoir (max allowed value is stored in an attribute of the reservoir names [Max.]. So to check on this, I've written the following code for the SendTo statement of the transporter.

Code: Select all

Do( 
  var([atmReservoir], vbAtom), 
  
  atmReservoir := Out(1, Out(Label([transporter], first(c)), c)),

  LoopUntil(
    Content(atmReservoir) < Att([Max.], atmReservoir),
    Do(
      Label([transporter], first(c)) := Mod(Label([transporter], first(c)), NrOc(c)) + 1,
      atmReservoir := out(1, out(Label([transporter], first(c)), c))
    ), 
    NrOc(c)
  ),
  Label([transporter], first(c))
)
I first assign the preferred reservoir to a local variable named "atmReservoir". I use a LoopUnitl, so I can loop easily over all the outgoing channels of the transporter and stop when the best one is found. If the desired reservoir has space, the loop is interrupted and the label is accepted to send the product to. If not, I look for the next out going channel and it's related reservoir. With using the Modulo I restart at the first out channel when I've reached the highest out channel (in your case third).

When no fitting reservoir is found, the transporter will continue to the original intended reservoir and wait there.

I hope this helps you further,

Cheers,

Harry
EvelineHermans
Posts: 28
Joined: Tuesday 28 July, 2015 - 10:34

Re: Regular transporter 'Send to' code

Post by EvelineHermans »

Thanks a lot!! A short question that continues on the one above..

I encounter "the problem" again when I use a flow (a flow that is not 0, but let's say 40) for the reservoir.
Is there a way to check the content of the reservoir at every product that exits in these reservoirs (i.e. check the content more often)?

Cheers
Eveline
User avatar
HarryBunnik
Posts: 362
Joined: Monday 07 February, 2011 - 11:22

Re: Regular transporter 'Send to' code

Post by HarryBunnik »

Ha Eveline,

I think that you also will have to check what is in the server and how many more products are waiting in there, to be placed into the reservoir. That way you might be able to avoid waiting at a busy server that will stay busy for quite a bit longer.

So instead of only checking on the content of the reservoir, you also have to check the content of the server and take that in account. I'm only not entirely sure what the flow of the reservoir has to do with this, so perhaps I'm misunderstanding the problem.

Cheers,

Harry
EvelineHermans
Posts: 28
Joined: Tuesday 28 July, 2015 - 10:34

Re: Regular transporter 'Send to' code

Post by EvelineHermans »

Of course you were right, my explaination was not correct ;-) Thanks, it seems to work correctly with the following code:

Code: Select all

Do( 
  var([atmReservoir], vbAtom), 
  var([atmServer], vbAtom),
  
  atmReservoir := Out(1, Out(Label([transporter1], first(c)), c)),
  atmServer := Out(1,c),

LoopUntil(
Content(atmReservoir) < Att([Max.], atmReservoir),
Do(
Label([transporter], first(c)) := Mod(Label([transporter], first(c)), NrOc(c)) + 1,
atmReservoir := out(1, out(Label([transporter1], first(c)), c)),
atmServer := Out(Label([transporter1], first(c)),c)
), 
NrOc(c)
),
Label([transporter], first(c))
)

Is there also a way to not "continue to the original intended reservoir and wait there" if no fitting reservoir is found, but instead just close all inputchannels of the transporter until a fitting reservoir is found? The waiting keeps my HR busy, while I need them for other actions if possible.
I tried to rewrite your code into an If() code, but it doesn't work out the way I want to, since the condition-check [content < max. content] is evaluated within the Do().

Cheers,
Eveline
EvelineHermans
Posts: 28
Joined: Tuesday 28 July, 2015 - 10:34

Re: Regular transporter 'Send to' code

Post by EvelineHermans »

Sorry, made a little mistake in the code. The code below is working nicely:

Code: Select all

Do( 
  var([atmReservoir], vbAtom), 
  var([atmServer], vbAtom),
  
  atmReservoir := Out(1, Out(Label([transporter], first(c)), c)),
  atmServer := Out(Label([transporter], first(c)),c),

LoopUntil(
Content(atmReservoir) < Att([Max.], atmReservoir),
Do(
Label([transporter], first(c)) := Mod(Label([transporter], first(c)), NrOc(c)) + 1,
atmReservoir := out(1, out(Label([transporter], first(c)), c)),
atmServer := Out(Label([transporter], first(c)),c)
), 
NrOc(c)
),
Label([transporter], first(c))
)
Post Reply