首先,我们需要定义输入和输出端口:

module traffic_light_controller(
    input clk,
    input reset,
    output reg [2:0] east_west, // 红绿黄 0 1 2
    output reg [2:0] north_south, // 红绿黄 0 1 2
    output reg [3:0] time // 显示剩余时间
);

接下来,我们定义一些常量:

parameter GREEN_TIME = 5;
parameter YELLOW_TIME = 3;
parameter RED_TIME = 8;

parameter EAST_WEST_GREEN = 1;
parameter EAST_WEST_YELLOW = 2;
parameter EAST_WEST_RED = 0;

parameter NORTH_SOUTH_GREEN = 2;
parameter NORTH_SOUTH_YELLOW = 1;
parameter NORTH_SOUTH_RED = 0;

接着,我们需要定义一些状态变量:

reg [2:0] east_west_state;
reg [2:0] north_south_state;

reg [3:0] east_west_time;
reg [3:0] north_south_time;

然后,我们需要写一个状态机来控制交通灯的状态:

always @(posedge clk, posedge reset) begin
    if (reset) begin // 复位状态
        east_west_state <= EAST_WEST_RED;
        north_south_state <= NORTH_SOUTH_GREEN;
        east_west_time <= GREEN_TIME;
        north_south_time <= GREEN_TIME;
    end else begin
        case (east_west_state)
            EAST_WEST_GREEN: begin // 东西方向绿灯
                if (east_west_time > 0) begin
                    east_west_time <= east_west_time - 1;
                end else begin
                    east_west_state <= EAST_WEST_YELLOW; // 绿灯结束,进入黄灯
                    east_west_time <= YELLOW_TIME;
                end
            end
            EAST_WEST_YELLOW: begin // 东西方向黄灯
                if (east_west_time > 0) begin
                    east_west_time <= east_west_time - 1;
                end else begin
                    east_west_state <= EAST_WEST_RED; // 黄灯结束,进入红灯
                    east_west_time <= RED_TIME;
                end
            end
            EAST_WEST_RED: begin // 东西方向红灯
                if (east_west_time > 0) begin
                    east_west_time <= east_west_time - 1;
                end else begin
                    east_west_state <= EAST_WEST_GREEN; // 红灯结束,进入绿灯
                    east_west_time <= GREEN_TIME;
                end
            end
        endcase

        case (north_south_state)
            NORTH_SOUTH_GREEN: begin // 南北方向绿灯
                if (north_south_time > 0) begin
                    north_south_time <= north_south_time - 1;
                end else begin
                    north_south_state <= NORTH_SOUTH_YELLOW; // 绿灯结束,进入黄灯
                    north_south_time <= YELLOW_TIME;
                end
            end
            NORTH_SOUTH_YELLOW: begin // 南北方向黄灯
                if (north_south_time > 0) begin
                    north_south_time <= north_south_time - 1;
                end else begin
                    north_south_state <= NORTH_SOUTH_RED; // 黄灯结束,进入红灯
                    north_south_time <= RED_TIME;
                end
            end
            NORTH_SOUTH_RED: begin // 南北方向红灯
                if (north_south_time > 0) begin
                    north_south_time <= north_south_time - 1;
                end else begin
                    north_south_state <= NORTH_SOUTH_GREEN; // 红灯结束,进入绿灯
                    north_south_time <= GREEN_TIME;
                end
            end
        endcase
    end
end

最后,我们需要写一个模块来显示剩余时间:

always @(posedge clk) begin
    if (east_west_state == EAST_WEST_GREEN) begin
        time <= east_west_time;
    end else if (east_west_state == EAST_WEST_YELLOW) begin
        time <= east_west_time + GREEN_TIME;
    end else if (east_west_state == EAST_WEST_RED) begin
        time <= east_west_time + GREEN_TIME + YELLOW_TIME;
    end else if (north_south_state == NORTH_SOUTH_GREEN) begin
        time <= north_south_time;
    end else if (north_south_state == NORTH_SOUTH_YELLOW) begin
        time <= north_south_time + GREEN_TIME;
    end else if (north_south_state == NORTH_SOUTH_RED) begin
        time <= north_south_time + GREEN_TIME + YELLOW_TIME;
    end
end

完整代码如下:

module traffic_light_controller(
    input clk,
    input reset,
    output reg [2:0] east_west, // 红绿黄 0 1 2
    output reg [2:0] north_south, // 红绿黄 0 1 2
    output reg [3:0] time // 显示剩余时间
);

    parameter GREEN_TIME = 5;
    parameter YELLOW_TIME = 3;
    parameter RED_TIME = 8;

    parameter EAST_WEST_GREEN = 1;
    parameter EAST_WEST_YELLOW = 2;
    parameter EAST_WEST_RED = 0;

    parameter NORTH_SOUTH_GREEN = 2;
    parameter NORTH_SOUTH_YELLOW = 1;
    parameter NORTH_SOUTH_RED = 0;

    reg [2:0] east_west_state;
    reg [2:0] north_south_state;

    reg [3:0] east_west_time;
    reg [3:0] north_south_time;

    always @(posedge clk, posedge reset) begin
        if (reset) begin // 复位状态
            east_west_state <= EAST_WEST_RED;
            north_south_state <= NORTH_SOUTH_GREEN;
            east_west_time <= GREEN_TIME;
            north_south_time <= GREEN_TIME;
        end else begin
            case (east_west_state)
                EAST_WEST_GREEN: begin // 东西方向绿灯
                    if (east_west_time > 0) begin
                        east_west_time <= east_west_time - 1;
                    end else begin
                        east_west_state <= EAST_WEST_YELLOW; // 绿灯结束,进入黄灯
                        east_west_time <= YELLOW_TIME;
                    end
                end
                EAST_WEST_YELLOW: begin // 东西方向黄灯
                    if (east_west_time > 0) begin
                        east_west_time <= east_west_time - 1;
                    end else begin
                        east_west_state <= EAST_WEST_RED; // 黄灯结束,进入红灯
                        east_west_time <= RED_TIME;
                    end
                end
                EAST_WEST_RED: begin // 东西方向红灯
                    if (east_west_time > 0) begin
                        east_west_time <= east_west_time - 1;
                    end else begin
                        east_west_state <= EAST_WEST_GREEN; // 红灯结束,进入绿灯
                        east_west_time <= GREEN_TIME;
                    end
                end
            endcase

            case (north_south_state)
                NORTH_SOUTH_GREEN: begin // 南北方向绿灯
                    if (north_south_time > 0) begin
                        north_south_time <= north_south_time - 1;
                    end else begin
                        north_south_state <= NORTH_SOUTH_YELLOW; // 绿灯结束,进入黄灯
                        north_south_time <= YELLOW_TIME;
                    end
                end
                NORTH_SOUTH_YELLOW: begin // 南北方向黄灯
                    if (north_south_time > 0) begin
                        north_south_time <= north_south_time - 1;
                    end else begin
                        north_south_state <= NORTH_SOUTH_RED; // 黄灯结束,进入红灯
                        north_south_time <= RED_TIME;
                    end
                end
                NORTH_SOUTH_RED: begin // 南北方向红灯
                    if (north_south_time > 0) begin
                        north_south_time <= north_south_time - 1;
                    end else begin
                        north_south_state <= NORTH_SOUTH_GREEN; // 红灯结束,进入绿灯
                        north_south_time <= GREEN_TIME;
                    end
                end
            endcase
        end
    end

    always @(posedge clk) begin
        if (east_west_state == EAST_WEST_GREEN) begin
            east_west <= {1'b0, 1'b1, 1'b0}; // 绿灯
            time <= east_west_time;
        end else if (east_west_state == EAST_WEST_YELLOW) begin
            east_west <= {1'b0, 1'b0, 1'b1}; // 黄灯
            time <= east_west_time + GREEN_TIME;
        end else if (east_west_state == EAST_WEST_RED) begin
            east_west <= {1'b1, 1'b0, 1'b0}; // 红灯
            time <= east_west_time + GREEN_TIME + YELLOW_TIME;
        end

        if (north_south_state == NORTH_SOUTH_GREEN) begin
            north_south <= {1'b0, 1'b1, 1'b0}; // 绿灯
            time <= north_south_time;
        end else if (north_south_state == NORTH_SOUTH_YELLOW) begin
            north_south <= {1'b0, 1'b0, 1'b1}; // 黄灯
            time <= north_south_time + GREEN_TIME;
        end else if (north_south_state == NORTH_SOUTH_RED) begin
            north_south <= {1'b1, 1'b0, 1'b0}; // 红灯
            time <= north_south_time + GREEN_TIME + YELLOW_TIME;
        end
    end

endmodule
Verilog 交通灯控制器设计:十字路口信号灯控制与倒计时显示

原文地址: https://www.cveoy.top/t/topic/lxzN 著作权归作者所有。请勿转载和采集!

免费AI点我,无需注册和登录