%autonomous vehicles
clear all;
close all;
Vissim = actxserver('Vissim.Vissim.700'); % Start Vissim
Vissim.LoadNet
sim=Vissim.simulation;
vnet=Vissim.Net;
SC_number = 1;
SignalController = vnet.SignalControllers.ItemByKey(SC_number);
SG(1)=SignalController.SGs.ItemByKey(1);
SG(2)=SignalController.SGs.ItemByKey(2);
SH_1=vnet.SignalHeads.ItemByKey(1);
SH_1pos=get(SH_1, 'AttValue', 'Pos');
dets=SignalController.Detectors;
det_all=dets.GetAll;
det_1=det_all{1};
det_2=det_all{2};
det_1pos=get(det_1, 'AttValue', 'Pos');
v_veh = 58;
s = SH_1pos - det_1pos - 10;
v = v_veh/3.6;
t = floor(s/v)-1;
period_time=3600;
sim.set('AttValue', 'SimPeriod', period_time);
sim.get('AttValue', 'SimPeriod')
step_time=10;
sim.set('AttValue', 'SimRes', step_time);
max_cores=4;
sim.set('AttValue', 'NumCores', max_cores);
vehins=vnet.VehicleInputs;
load vehs.txt
veh_id = 1;
vehin(1)=vehins.ItemByKey(1);
Veh_composition_number = 2;
Rel_Flows = vnet.VehicleCompositions.ItemByKey(Veh_composition_number).VehCompRelFlows.GetAll;
set(Rel_Flows{1}, 'AttValue', 'VehType',        100); 
set(Rel_Flows{1}, 'AttValue', 'DesSpeedDistr',   1047);
set(Rel_Flows{1}, 'AttValue', 'RelFlow',        1);
vehin(1).set('AttValue', 'VehComp(1)', 2);
vehin(1).set('AttValue', 'Volume(1)', vehs(1,veh_id));
pedins=vnet.PedestrianInputs;
pedin(1)=pedins.ItemByKey(1);
pedin(1).set('AttValue', 'Volume(1)', 1000);
pedin(2)=pedins.ItemByKey(2);
pedin(2).set('AttValue', 'Volume(1)', 1100);
verify = 1;
time = 0;
tsg1 = 17;
tsg1max = 45;
tsg2min = 2;
sg1_time = 0;
sg2_time = 0;
relative_time = 0;
t12 = 0;
t21 = 0;
stage = 2;
demand = 0;
transition = 3;
shift = t - (transition+1);
wait = 0;
for i=0:(period_time*step_time)
sim.RunSingleStep;
if rem(i/step_time, verify)==0
   time=time+1;   
   if stage == 1
    detect=det_1.get('AttValue', 'Detection'); 
    if detect == 1
        relative_time = 0;
    end
    if (relative_time >= (t-1)) 
        stage = 12;
        t12 = 0;
        sg1_time = 0;
        relative_time = 0;
        demand = 0;
    elseif (sg1_time > tsg1max)
        stage = 12;
        t12 = 0;
        sg1_time = 0;
        relative_time = 0;
        demand = 0;
    else
    SG(1).set('AttValue', 'State', 3);
    SG(2).set('AttValue', 'State', 1);
    sg1_time = sg1_time+1;
    relative_time = relative_time + 1;
    end
   end
   if stage == 2
       detect=det_1.get('AttValue', 'Detection');
       detect2=det_2.get('AttValue', 'Detection');
       if (detect == 1) || (demand == 1) || (detect2 == 1)
           if t >= tsg2min
               if (wait >= shift) && (sg2_time > tsg2min)
                   stage = 21;
                   sg2_time = 0;
                   t21 = 0;
                   wait = 0;
               else
                   SG(1).set('AttValue', 'State', 1);
                   SG(2).set('AttValue', 'State', 3);
                   sg2_time = sg2_time+1;
                   wait = wait + 1;
               end
           elseif (sg2_time >= tsg2min)
               stage = 21;
               sg2_time = 0;
               t21 = 0;               
           else
               SG(1).set('AttValue', 'State', 1);
               SG(2).set('AttValue', 'State', 3);
               sg2_time = sg2_time+1;               
           end
           demand = 1;
       else
           SG(1).set('AttValue', 'State', 1);
           SG(2).set('AttValue', 'State', 3);
           sg2_time = sg2_time+1; 
       end
   end
   if stage == 12
    if (t12 == 0) || (t12 == 1)
     SG(1).set('AttValue', 'State', 4); 
     SG(2).set('AttValue', 'State', 1);  
    end
    if t12 == 2
     SG(1).set('AttValue', 'State', 1); 
     SG(2).set('AttValue', 'State', 1);
     stage = 2;
     sg2_time = 0;
    end
    t12 = t12 + 1;
   end
   if stage == 21
    if t21 < transition
     SG(1).set('AttValue', 'State', 1);
     SG(2).set('AttValue', 'State', 1);   
    end
    if t21 == transition
     SG(1).set('AttValue', 'State', 2);
     SG(2).set('AttValue', 'State', 1);
     stage = 1;
     sg1_time = 0;
     demand = 0;
    end
    t21 = t21 + 1;
   end   
vehin(1).set('AttValue', 'Volume(1)', vehs(1,veh_id));  
    if veh_id < length(vehs)
                veh_id = veh_id + 1;
    end  
end 
end
