534 |
public: |
public: |
535 |
Bridge(bool open=true); |
Bridge(bool open=true); |
536 |
private: |
private: |
537 |
enum State { OPEN, CLOSED, OPENING, CLOSING } state; |
enum State { |
538 |
|
OPEN, CLOSED, OPENING, CLOSING, // normal states |
539 |
|
CLOSING_BYSTONE, CLOSED_BYSTONE // when stones are moved onto the bridge |
540 |
|
} state; |
541 |
|
// the BYSTONE-states look like closed, but act like open |
542 |
|
|
543 |
char get_type() const { |
char get_type() const { |
544 |
string type = "a"; |
string type = "a"; |
550 |
void on_actorhit(Actor* a) {if (state!=CLOSED) SendMessage(a, "fall");} |
void on_actorhit(Actor* a) {if (state!=CLOSED) SendMessage(a, "fall");} |
551 |
void message(const string &m, const Value &); |
void message(const string &m, const Value &); |
552 |
void init_model(); |
void init_model(); |
553 |
|
void stone_change(Stone *st); |
554 |
|
|
555 |
void change_state( State newstate); |
void change_state( State newstate); |
556 |
void animcb(); |
void animcb(); |
563 |
state=open ? OPEN : CLOSED; |
state=open ? OPEN : CLOSED; |
564 |
} |
} |
565 |
|
|
566 |
|
void Bridge::stone_change(Stone *st) { |
567 |
|
if (st && !st->is_floating()) { |
568 |
|
if (state == OPEN || state == OPENING) { |
569 |
|
change_state(CLOSING_BYSTONE); |
570 |
|
} |
571 |
|
} |
572 |
|
else { |
573 |
|
if (state == CLOSED_BYSTONE || state == CLOSING_BYSTONE) { |
574 |
|
change_state(OPENING); |
575 |
|
} |
576 |
|
} |
577 |
|
} |
578 |
|
|
579 |
void Bridge::message(const string &m, const Value &) |
void Bridge::message(const string &m, const Value &) |
580 |
{ |
{ |
581 |
if (m == "open" && (state==CLOSED || state==CLOSING)) |
if (m == "open" && (state==CLOSED || state==CLOSING)) |
582 |
change_state(OPENING); |
change_state(OPENING); |
583 |
else if (m=="close" && (state==OPEN || state==OPENING)) |
else if (m=="close") |
584 |
change_state(CLOSING); |
switch (state) { |
585 |
else if (m=="openclose" || m=="signal") { |
case OPEN: |
586 |
if (state==OPEN || state==OPENING) |
case OPENING: |
587 |
change_state(CLOSING); |
case CLOSING_BYSTONE: |
588 |
else |
change_state(CLOSING); |
589 |
change_state(OPENING); |
break; |
590 |
} |
case CLOSED_BYSTONE: |
591 |
|
change_state(CLOSED); |
592 |
|
break; |
593 |
|
case CLOSED: |
594 |
|
case CLOSING: |
595 |
|
break; // already closed |
596 |
|
|
597 |
|
} |
598 |
|
else if (m=="openclose" || m=="signal") |
599 |
|
switch (state) { |
600 |
|
case OPEN: |
601 |
|
case OPENING: |
602 |
|
case CLOSING_BYSTONE: |
603 |
|
change_state(CLOSING); |
604 |
|
break; |
605 |
|
case CLOSED_BYSTONE: |
606 |
|
change_state(CLOSED); |
607 |
|
break; |
608 |
|
case CLOSED: |
609 |
|
case CLOSING: |
610 |
|
change_state(OPENING); |
611 |
|
break; |
612 |
|
} |
613 |
} |
} |
614 |
|
|
615 |
void Bridge::actor_enter(Actor *a) |
void Bridge::actor_enter(Actor *a) |
629 |
|
|
630 |
void Bridge::change_state( State newstate) |
void Bridge::change_state( State newstate) |
631 |
{ |
{ |
632 |
string mname = string("fl-bridge")+get_type(); |
if (state != newstate) { |
633 |
switch( newstate) { |
string mname = string("fl-bridge")+get_type(); |
634 |
case OPENING: |
|
635 |
if( state == CLOSING) |
switch( newstate) { |
636 |
get_model()->reverse(); |
case OPENING: { |
637 |
else |
Stone *st = GetStone(get_pos()); |
638 |
set_anim(mname+"-opening"); |
if (st && !st->is_floating()) { |
639 |
break; |
if (state == CLOSED || state == CLOSED_BYSTONE) |
640 |
case CLOSING: |
newstate = CLOSED_BYSTONE; |
641 |
if( state == OPENING) |
else if (state == CLOSING || state == CLOSING_BYSTONE) |
642 |
get_model()->reverse(); |
newstate = CLOSING_BYSTONE; |
643 |
else |
// here the model is already correct! |
644 |
set_anim(mname+"-closing"); |
} |
645 |
break; |
else { // no stone or floating stone : |
646 |
case OPEN: |
if( state == CLOSING || state == CLOSING_BYSTONE) |
647 |
case CLOSED: |
get_model()->reverse(); |
648 |
state=newstate; |
else |
649 |
init_model(); |
set_anim(mname+"-opening"); |
650 |
break; |
} |
651 |
|
break; |
652 |
|
} |
653 |
|
case CLOSING: |
654 |
|
case CLOSING_BYSTONE: |
655 |
|
if( state == OPENING) |
656 |
|
get_model()->reverse(); |
657 |
|
else if (state != CLOSING && state != CLOSING_BYSTONE) |
658 |
|
set_anim(mname+"-closing"); |
659 |
|
break; |
660 |
|
case OPEN: |
661 |
|
case CLOSED: |
662 |
|
case CLOSED_BYSTONE: |
663 |
|
state = newstate; |
664 |
|
init_model(); |
665 |
|
break; |
666 |
|
} |
667 |
|
state = newstate; |
668 |
} |
} |
|
state=newstate; |
|
669 |
} |
} |
670 |
|
|
671 |
void Bridge::animcb() |
void Bridge::animcb() |
672 |
{ |
{ |
673 |
if (state==OPENING) |
switch (state) { |
674 |
change_state(OPEN); |
case OPENING: change_state(OPEN); break; |
675 |
if (state==CLOSING) |
case CLOSING: change_state(CLOSED); break; |
676 |
change_state(CLOSED); |
case CLOSING_BYSTONE: change_state(CLOSED_BYSTONE); break; |
677 |
|
default : assert(0); break; |
678 |
|
} |
679 |
} |
} |
680 |
|
|
681 |
|
|