基于FPGA的出租车里程时间计费器

基于FPGA的出租车里程时间计费器

  • 功能描述
  • 一、系统框图
  • 二、verilog代码
    • 里程增加模块
    • 时间增加模块
    • 计算价格模块
    • 上板视频演示
  • 总结


功能描述

(1);里程计费功能:3公里以内起步价8元,超过3公里后每公里2元,其中不满一公里按照一公里计算。
(2);等待计费功能:当乘客中途下车需要司机等待时,按照等待时间进行收费,每3分钟0.7元,其中不满3分钟不收费。
(3);数码管显示功能;3种显示状态,默认显示公里数,显示格式10.2,每次步进0.1km,步进时间长度为5S。第二种显示等待时间,显示格式50:33,步进时间长度1S。第三种显示当前费用,包括等待费用以及里程计价费用。
(4);信号灯指示功能:当里程计费模式下,LED2亮起,其他LED熄灭。当等待时间计费模式下,LED4亮起,其他LED熄灭。载人状态下LED1亮起,否则不亮。
(5);按键切换功能:3个按键起作用,第一个按键负责切换计费模式,默认是里程计费模式,切换后为等待时间计费模式。第二个按键负责表示出租车载人状态,默认空载,按下表示载人模式。第三个按键负责切换数码管显示的数据,每按一次切换一次,3种数据循环显示。

一、系统框图

在这里插入图片描述

二、verilog代码

里程增加模块

module count_km(input key_dri,input sys_reset_n,input en_dowm_car,input EN,output reg [3:0] data_km_ge,output reg [3:0] data_km_shi,output reg [3:0] data_km_bai,//	output reg [15:0] data_km,output [3:0] point
);parameter max_km=16'd9999; reg       flag_km_shi_up;
reg       flag_km_bai_up;assign point=4'b0010;always @(posedge key_dri or negedge sys_reset_n)beginif(!sys_reset_n)begindata_km_ge<=4'h0;flag_km_shi_up<=1'b0;endelse if(!EN)begindata_km_ge<=data_km_ge;flag_km_shi_up<=flag_km_shi_up;endelse if(key_dri && en_dowm_car)beginif(data_km_ge<4'h9)begindata_km_ge<=data_km_ge+1'b1;flag_km_shi_up<=1'b0;endelsebegindata_km_ge<=4'h0;flag_km_shi_up<=1'b1;endendendalways @(posedge key_dri or negedge sys_reset_n)beginif(!sys_reset_n)begindata_km_shi<=4'h0;flag_km_bai_up<=1'b0;endelse if(!EN)begindata_km_shi<=data_km_shi;flag_km_bai_up<=flag_km_bai_up;endelse if(key_dri && en_dowm_car && flag_km_shi_up)beginif(data_km_shi<4'h9)begindata_km_shi<=data_km_shi+1'b1;flag_km_bai_up<=1'b0;endelsebegindata_km_shi<=4'h0;flag_km_bai_up<=1'b1;endendelse if(key_dri && en_dowm_car && flag_km_shi_up==1'b0)beginflag_km_bai_up<=1'b0;endendalways @(posedge key_dri or negedge sys_reset_n)beginif(!sys_reset_n)begindata_km_bai<=4'h0;endelse if(!EN)begindata_km_bai<=data_km_bai;endelse if(key_dri && en_dowm_car && flag_km_bai_up)beginif(data_km_bai<4'h9)begindata_km_bai<=data_km_bai+1'b1;endelsebegindata_km_bai<=4'h0;endendendendmodule

时间增加模块

//计时模块
module count_1s
(input clk,   //系统时钟input sys_reset_n, //复位信号input EN, //使能  保持input en_dowm_car,//	output reg [7:0] data_s,  //秒计时器
//	output reg [7:0] data_m,	//分钟计时器output reg [3:0] data_s_shi,output reg [3:0] data_s_ge,output reg [3:0] data_m_shi,output reg [3:0] data_m_ge,output reg [3:0] time_price_ge,output reg [3:0] time_price_shi,output reg [3:0] time_price_bai,output reg   clk_1s,  //1s脉冲output [3:0] point   //点
);parameter time_60=8'd60;
parameter MAX_NUM=28'd249;reg [27:0] cnt; //1s计数器reg   flag_1m;  //1m计时reg       flag_m_shi_up;
reg       flag_s_up;
reg       flag_m_up;
reg       time_shi_up;
reg       time_bai_up;assign point=4'b0100;
//1s计时
always @(posedge clk or negedge sys_reset_n)beginif(!sys_reset_n)begincnt<=1'b0;clk_1s<=1'b0;endelse if(!EN)begincnt<=cnt;   //保持clk_1s<=clk_1s;endelse if(cnt<MAX_NUM)begincnt<=cnt+1'b1;endelsebegincnt<=0;clk_1s<=~clk_1s;  //翻转endendalways @(negedge clk_1s or negedge sys_reset_n)	beginif(!sys_reset_n)begintime_price_ge<=4'h0;endelse if(en_dowm_car)beginif(flag_s_up && time_price_ge<4'h9)begintime_price_ge<=time_price_ge+1;endelse if(flag_s_up && time_price_ge==4'h9)begintime_price_ge<=0;endendend
always @(negedge clk_1s or negedge sys_reset_n)	beginif(!sys_reset_n)begintime_price_shi<=4'h0;endelse if(en_dowm_car)beginif(time_price_ge==4'h9 && time_price_shi<4'h9 && flag_s_up )begintime_price_shi<=time_price_shi+1;endelse if(time_price_ge==4'h9 && time_price_shi==4'h9&& flag_s_up)begintime_price_shi<=0;endendendalways @(negedge clk_1s or negedge sys_reset_n)	beginif(!sys_reset_n)begintime_price_bai<=4'h0;endelse if(en_dowm_car)beginif(time_price_shi==4'h9 && time_price_bai<4'h9&& flag_s_up &&time_price_ge==4'h9)begintime_price_bai<=time_price_bai+1;endelse if(time_price_shi==4'h9 && time_price_bai==4'h9&& flag_s_up&&time_price_ge==4'h9)begintime_price_bai<=0;endendend//	秒个位加1
always @(negedge clk_1s or negedge sys_reset_n)	beginif(!sys_reset_n)begindata_s_ge<=4'h0;flag_s_up<=0;endelse if(!EN)begindata_s_ge<=data_s_ge;   //保持flag_s_up<=flag_s_up;endelse if(en_dowm_car)beginif(data_s_ge < 4'h9 )begindata_s_ge<=data_s_ge+1'b1;		flag_s_up<=1'b0;					endelse if(data_s_ge == 4'h9)begindata_s_ge<=4'h0;		flag_s_up<=1'b1;					endendelse begindata_s_ge<=data_s_ge;   //保持flag_s_up<=flag_s_up;endend
//	秒十位加1
always @(negedge clk_1s or negedge sys_reset_n)	beginif(!sys_reset_n)begindata_s_shi<=4'h0;flag_m_up<=0;endelse if(!EN)begindata_s_shi<=data_s_shi;   //保持flag_m_up<=flag_m_up;endelse if(data_s_shi < 4'h5 && data_s_ge==4'h9)begindata_s_shi<=data_s_shi+1'b1;		flag_m_up<=1'b0;					endelse if(data_s_shi == 4'h5 && data_s_ge==4'h9)begindata_s_shi<=4'h0;		flag_m_up<=1'b1;					endelse begindata_s_shi<=data_s_shi;		flag_m_up<=1'b0;	endend//分钟个位加一
always @(posedge clk_1s or negedge sys_reset_n)	beginif(!sys_reset_n)begindata_m_ge<=4'h0;flag_m_shi_up<=1'b0;endelse if(!EN)begindata_m_ge<=data_m_ge;   //保持flag_m_shi_up<=flag_m_shi_up;endelse if(en_dowm_car) beginif(data_m_ge<4'h9 && data_s_shi==4'h5 && data_s_ge==4'h9)begindata_m_ge<=data_m_ge+1'b1;flag_m_shi_up<=1'b0;endelse if(data_m_ge==4'h9 && data_s_shi==4'h5 && data_s_ge==4'h9)begindata_m_ge<=4'h0;flag_m_shi_up<=1'b1;endelse begindata_m_ge<=data_m_ge;   //保持flag_m_shi_up<=1'b0;endendelse begindata_m_ge<=data_m_ge;   //保持flag_m_shi_up<=1'b0;endend//分钟十位加一
always @(posedge flag_m_shi_up or negedge sys_reset_n)	beginif(!sys_reset_n)begindata_m_shi<=4'h0;endelse if(!EN)begindata_m_shi<=data_m_shi;   //保持endelse if(en_dowm_car) beginif(data_m_shi<4'h5 )begindata_m_shi<=data_m_shi+1'b1;endelse if(data_m_shi==4'h5)begindata_m_shi<=4'h0;endendelse begindata_m_ge<=data_m_ge;   //保持endendendmodule

计算价格模块

module count_money(input [7:0] data_m,input [15:0] data_km,input sys_reset_n,input clk,input             add_km,input         en_dowm_car,input          clk_1s,input         [3:0] data_km_ge,input         [3:0] data_km_shi,input         [3:0] data_km_bai,input          [3:0] time_price_ge,input          [3:0] time_price_shi,input          [3:0] time_price_bai,output      reg [3:0] price_ge,output      reg [3:0] price_shi,output      reg [3:0] price_bai,
//	output reg [15:0] data_price,output [3:0] point
);assign point=4'b0010;reg [15:0] price_km;
reg [15:0] price_time;reg price_shi_up;
reg price_bai_up;
initialbeginprice_km<=16'd30;price_time<=16'd0;end//里程计价
always @(posedge add_km or negedge sys_reset_n)beginif(!sys_reset_n)beginprice_ge<=4'h0;price_shi_up<=1'b0;endelse if(en_dowm_car )beginif(data_km_bai==4'h0)beginif(price_ge<4'h9 && data_km_shi>=4'h3 )begin//大于3.0公里开始增加price_ge<=price_ge+1;price_shi_up<=1'b0;endelse if(price_ge>=4'h9 && data_km_shi>=4'h3 )begin//大于3.0公里开始增加 到9累加price_ge<=4'h0;price_shi_up<=1'b1;endelse if(price_ge<4'h9 && data_km_shi<4'h3)beginprice_ge<=price_ge;price_shi_up<=1'b0;endendelse if(data_km_bai!=4'h0)beginif(price_ge<4'h9 )begin//大于3.0公里开始增加price_ge<=price_ge+1;price_shi_up<=1'b0;endelse if(price_ge>=4'h9)begin//大于3.0公里开始增加 到9累加price_ge<=4'h0;price_shi_up<=1'b1;endendendendalways @(posedge add_km or negedge sys_reset_n)beginif(!sys_reset_n)beginprice_shi<=4'h8;price_bai_up<=1'b0;endelse if(price_shi<4'h9 && price_shi_up)beginprice_shi<=price_shi+1;price_bai_up<=1'b0;endelse if(price_shi>=4'h9 && price_shi_up)beginprice_shi<=4'h0;price_bai_up<=1'b1;endelse if(price_shi_up==1'b0)beginprice_bai_up<=1'b0;endendalways @(posedge add_km or negedge sys_reset_n)beginif(!sys_reset_n)beginprice_bai<=4'h0;endelse if(price_bai<4'h9 && price_bai_up)beginprice_bai<=price_bai+1;endelse if(price_bai>=4'h9 && price_bai_up)beginprice_bai<=4'h0;endendendmodule

在这里插入图片描述

模块分析:
通过分频得到5S周期的脉冲信号,当EN信号为高电平时,也就是有乘客上车后,司机按下按键,出租车变为载客状态,这时里程开始根据脉冲信号的上升沿进行增加。
在这里插入图片描述
通过按键切换到等待时间计费模式后,EN变为高电平,模块开始工作。将时钟分频模块得到的1S脉冲信号作为触发源进行判断,分和秒各8位,可以看到在脉冲上升沿时间不断累加,符合预期功能。

上板视频演示

基于FPGA的出租车里程时间计费器

总结

模块太多,只展示了比较重要的,其他一些模块就是产生分频信号的,无关紧要。需要的一键三连

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/bicheng/66532.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

jdk8升级JDK21(Springboot2.7.18升级Springboot3.4.0)

目录 背景&#xff1a; 一、maven升级 二、代码改造 2.1 javax替换为jakarta 2.2 swagger2升级swagger3相关更新 2.2.1 新增SpringDocConfig配置类 2.2.2 全局代码更新 2.2.3 全局代码替换&#xff08;普通正则替换&#xff09; 2.3 Mybatis Plus升级 2.4 logback.xm…

AI赋能跨境电商:魔珐科技3D数字人破解出海痛点

跨境出海进入狂飙时代&#xff0c;AI应用正在深度渗透并重塑着跨境电商产业链的每一个环节&#xff0c;迎来了发展的高光时刻。生成式AI时代的大幕拉开&#xff0c;AI工具快速迭代&#xff0c;为跨境电商行业的突破与飞跃带来了无限可能性。 由于跨境电商业务自身特性鲜明&…

【HarmonyOS NEXT】鸿蒙应用实现屏幕录制详解和源码

【HarmonyOS NEXT】鸿蒙应用实现屏幕录制详解和源码 一、前言 官方文档关于屏幕录制的API和示例介绍获取简单和突兀。使用起来会让上手程度变高。所以特意开篇文章&#xff0c;讲解屏幕录制的使用。官方文档参见&#xff1a;使用AVScreenCaptureRecorder录屏写文件(ArkTS) 二…

Android - NDK:编译可执行程序在android设备上运行

在android开发中&#xff0c;调试时会把C代码直接编译成可执行程序&#xff0c;运行在android设备上以确认其功能是否正常。 1、基于NDK编译可执行文件 2、push到 /data/local/tmp目录下 3、设置权限&#xff0c;执行。 ndk工程中build.gradle设置 groovy plugins {id com.a…

用matlab调用realterm一次性发送16进制数

realterm采用PutString接口进行发送&#xff0c;需要注意的是发送的16进制数前面要加入0x标志。只有这样&#xff0c;realterm才能将输入的字符串识别为16进制数的形式。 另外,PutString函数支持两个参数输入&#xff0c;第一个参数为字符串&#xff0c;第二个参数为发送形式&…

Python3刷算法来呀,贪心系列题单

1.7号题单 1、​​​​​​k次取反后最大值 2、柠檬水找零 3、分发糖果 示例 1&#xff1a; 输入&#xff1a;ratings [1,0,2] 输出&#xff1a;5 解释&#xff1a;你可以分别给第一个、第二个、第三个孩子分发 2、1、2 颗糖果。示例 2&#xff1a; 输入&#xff1a;ratings…

el-table拖拽表格

1、拖拽插件安装 npm i -S vuedraggable // vuedraggable依赖Sortable.js&#xff0c;我们可以直接引入Sortable使用Sortable的特性。 // vuedraggable是Sortable的一种加强&#xff0c;实现组件化的思想&#xff0c;可以结合Vue&#xff0c;使用起来更方便。 2、引入拖拽函数…

Unity学习笔记(七)使用状态机重构角色攻击

前言 本文为Udemy课程The Ultimate Guide to Creating an RPG Game in Unity学习笔记 攻击状态重构 首先我们重构攻击状态的动画 之前的动画&#xff0c;我们是使用状态(isAttacking)攻击次数(comboCounter)完成动画的过渡&#xff0c;这样虽然能完成功能&#xff0c;但是如…

Windows10环境下安装RabbitMq折腾记

最近有个老项目需要迁移到windows10环境&#xff0c;用的是比较老的rabbitmq安装包&#xff0c;如下所示。经过一番折腾&#xff0c;死活服务起不来&#xff0c;最终果断放弃老版本启用新版本。现在把折腾过程记录下&#xff1a; 一、安装erlang 安装完成后的目录结构&#xff…

了解RabbitMQ中的Exchange:深入解析与实践应用

在分布式系统设计中&#xff0c;消息队列&#xff08;Message Queue&#xff09;扮演着至关重要的角色&#xff0c;而RabbitMQ作为开源消息代理软件的佼佼者&#xff0c;以其高性能、高可用性和丰富的功能特性&#xff0c;成为了众多开发者的首选。在RabbitMQ的核心组件中&…

分布式主键ID生成方式-snowflake雪花算法

这里写自定义目录标题 一、业务场景二、技术选型1、UUID方案2、Leaf方案-美团&#xff08;基于数据库自增id&#xff09;3、Snowflake雪花算法方案 总结 一、业务场景 大量的业务数据需要保存到数据库中&#xff0c;原来的单库单表的方式扛不住大数据量、高并发&#xff0c;需…

Linux 系统搭建网络传输环境汇总

Ubuntu 系统搭建 TFTP 服务器 1. 创建 /home/username/workspace/tftp 目录并赋予最大权限&#xff0c;username 是自己用户名 sudo mkdir -p /home/username/workspace/tftp sudo chmod 777 /home/username/workspace/tftp 2. 安装 tftp-hpa&#xff08; 客户端软件包&#x…

“AI智慧语言训练系统:让语言学习变得更简单有趣

大家好&#xff0c;我是你们的老朋友&#xff0c;一个热衷于探讨科技与教育结合的产品经理。今天&#xff0c;我想和大家聊聊一个让语言学习变得不再头疼的话题——AI智慧语言训练系统。这个系统可是我们语言学习者的福音&#xff0c;让我们一起来揭开它的神秘面纱吧&#xff0…

线性代数考研笔记

行列式 背景 分子行列式&#xff1a;求哪个未知数&#xff0c;就把b1&#xff0c;b2放在对应的位置 分母行列式&#xff1a;系数对应写即可 全排列与逆序数 1 3 2&#xff1a;逆序数为1 奇排列 1 2 3&#xff1a;逆序数为0 偶排列 将 1 3 2 只需将3 2交换1次就可以还原原…

精选2款.NET开源的博客系统

前言 博客系统是一个便于用户创建、管理和分享博客内容的在线平台&#xff0c;今天大姚给大家分享2款.NET开源的博客系统。 StarBlog StarBlog是一个支持Markdown导入的开源博客系统&#xff0c;后端基于最新的.Net6和Asp.Net Core框架&#xff0c;遵循RESTFul接口规范&…

关于FPGA中添加FIR IP核(采用了GOWIN EDA)

文章目录 前言一、IP核二、MATLAB文件三、导出系数COE文件1.设计滤波器2.用官方的matlab代码或者直接用文本文件 四、进行模块化设计源文件 前言 FIR滤波器的特点是其输出信号是输入信号的加权和&#xff0c;权值由滤波器的系数决定。每个系数代表了滤波器在特定延迟位置上的“…

51单片机——中断(重点)

学习51单片机的重点及难点主要有中断、定时器、串口等内容&#xff0c;这部分内容一定要认真掌握&#xff0c;这部分没有学好就不能说学会了51单片机 1、中断系统 1.1 概念 中断是为使单片机具有对外部或内部随机发生的事件实时处理而设置的&#xff0c;中断功能的存在&#…

VVenC 编码器源码结构与接口函数介绍

VVenC VVenC&#xff08;Fraunhofer Versatile Video Encoder&#xff09;是由德国弗劳恩霍夫海因里希研究所&#xff08;Fraunhofer Heinrich Hertz Institute, HHI&#xff09;开发的一个开源的高效视频编码器。它实现了最新的视频编码标准——Versatile Video Coding (VVC)…

耗时一天,我用AI开发了AI小程序

小码哥从事前后端开发近十年&#xff0c;但是随着技术的更新迭代&#xff0c;有时候没有时间和精力去优化UI、实现一些前后端功能&#xff0c;以及解决一些bug。特别是我想开发小码哥AI的移动端&#xff0c;但觉得自己没有那么多时间去研究移动端了&#xff0c;准备放弃了&…

C#中的关键字out和ref的区别

目录 一、out 二、ref 三、拓展 一、out 在 C# 中&#xff0c;out 是一个关键字&#xff0c;通常用于方法参数&#xff0c;表示该参数是输出参数。使用 out 关键字的参数要求在方法内部必须被赋值&#xff0c;而这个参数的值会在方法返回时传递给调用者。可以理解为&#xf…