.
  • 作者:city7cc
  • 积分:4065
  • 等级:专家教授
  • 2020/1/28 10:23:07
  • 中国面包师贴吧-楼主(阅:1555/回:0)一种具有三轴圆周64个圆球的弹道导弹变质心装置

    一种具有三轴圆周64个圆球的弹道导弹变质心装置

    技术领域

    本实用新型涉及一种具有三轴圆周64个圆球的弹道导弹变质心装置,尤其是弹道导弹变质心装置。

    背景技术

    现有常规弹道导弹变质心装置是利用内部圆球的滚动来改变导弹质量中心的,它们都很难实现自由灵活的快速改变导弹的质量中心。一种具有三轴圆周64个圆球的弹道导弹变质心装置利用一个圆周上面的64个圆球在这个圆环的圆周上的滚动来改变导弹质量中心的目的。同时它具有3个圆环,分别是X、Y、Z,它们就像空间中的坐标轴一样两两相交90度。而且每个圆环上面都有64个圆球,这63个圆球在这个圆周上面滚动就可以改变导弹的质量中心。

    实用新型内容

    为了解决常规弹道导弹变质心装置很难灵活方便的改变导弹质心的目的,一种具有三轴圆周64个圆球的弹道导弹变质心装置提供了一种非常容易快速改变导弹质心的装置。这个装置是一种利用三个圆周上面的64个圆球在圆周上面的滚动来改变导弹质心的装置。这三个圆周按照空间中的X、Y、Z三个轴一样分布,它们两两垂直90度。

    本实用新型解决其技术问题所采用的技术方案是:一种具有三轴圆周64个圆球的弹道导弹变质心装置,是安装在弹道导弹弹体中部的一个圆环型装置。该弹道导弹的弹头(1)安装在导弹单体(2)上部,变质心装置的圆环(3)安装在导弹弹体中部,火箭发动机(4)安装在导弹底部。如图1所示,变质心装置由圆环和安装在圆环上面的64个圆球组成,这64个圆球可以在圆环上面滚动,进而改变导弹的质心。如图2所示,64个圆球(5)安装在导弹变质心装置的一个圆环(3)上面。这64个圆球分别安装在相互垂直的3个圆环(7),(8),(9)上面。64个圆球(5)分别用圆环圆心处的圆杆(6)和圆环的圆心相连,64个圆球(5)被和圆环圆心相连的圆杆(6)拉着在圆环(3)上面滚动,就会使导弹单体的质心发生改变,进而会使打导弹的质心发生改变。如图3所示,3个圆环(7),(8),(9)分别控制着空间中X,Y,Z三个轴的质心,利用圆杆(6)围绕圆环(7),(8),(9)圆心的转动,进而改变圆球(5)在圆环上面的滚动,就会改变这个圆环的质心,进而改变导弹的质心。

    同时可以讲相邻的8个圆球分为一组,这样就可以将每个圆环上面的64个圆球分为8组,只要同时改变8个圆球在圆环上面的滚动方向就可以改变一个方向上面的质心。同时利用电磁铁代替圆球,同时增大或减少8个相邻电磁铁的电压,就会使8组电磁铁之间的电磁力减小或增大,进而就会改变一个方向上面的质心,进而就会改变导弹的质心。

    利用单片机STC8A8K64S4A12控制8路PWM波形的占空比增大或者减小,再利用PWM驱动电路,将PWM的5V电压升高为24V,就会代替64圆球的64个电磁铁的磁性增大或者减小,进而改变圆环在一个方向上面的质心,进而改变导弹在一个方向上面的质心。如图4所示,单片机STC8A8K64S4A12产生8路PWM波形。L298N驱动一路PWM波形使电磁铁产生电磁力。单片机STC8A8K64S4A12的控制程序可以在百度网盘上面下载微云文件分享:变质心下载地址:

    https://share.weiyun.com/5WKskWH:-|^|-:https://share.weiyun.com/5WKskWH:-|^|-:

    https://pan.baidu.com/s/1Qi4w_aC_XR1dsN94NF4epQ:-|^|-:https://www.urlshare.cn/umirror_url_check?_wv=1&srctype=touch&apptype=android&loginuin=316234760&plateform=qzone&url=https%3A%2F%2Fpan.baidu.com%2Fs%2F1Qi4w_aC_XR1dsN94NF4epQ&src_uin=316234760&src_scene=2&cli_scene=getDetail:-|^|-:

    程序的源代码如下:

    #include "config.h"

    #include "STC8xxx_PWM.H"

    #include    "eeprom.h"

    #include   "Exti.h"

    #include   "time.h"

    #include <math.H>

    //#include "EEPROM.H"

    #include   "USART.h"

    #include   "delay.h"

    #define EE_ADDRESS1   0x0100

    #define CMD_IDLE    0

    #define CMD_READ    1

    #define CMD_PROGRAM 2

    #define CMD_ERASE   3

    #define      Baudrate1         115200UL

    #define ENABLE_IAP 0x80           //if SYSCLK<30MHz

    extern int   xdata g_x,g_y,g_z;      //陀螺仪矫正参数

    extern float xdata a_x,a_y;         //角度矫正参数

    extern float data AngleX,AngleY;

    /*************   本地常量声明   **************/

    u8   code   T_Strings[]={"去年今日此门中,人面桃花相映红。人面不知何处去,桃花依旧笑春风。"};

    /*************   本地变量声明   **************/

    u8   xdata   tmp[1];

    u16 addr;

    u8 data h;

    int      data  speed0=0,speed1=0,speed2=0,speed3=0;   /[em]e169[/em]机速度参数

    int      data  PWM0=0,PWM1=0,PWM2=0,PWM3=0,PWM4=0,PWM5=0,PWM6=0,PWM7=0;         //加载至PWM模块的参数

    u8   xdata   tmp1[1];

    u8   i;

    #define EE_ADDRESS2   0x0300

    void    Timer0_Config(void);

    void    Timer1_Config(void);

    void   DisableEEPROM(void);

    void    EEPROM_read_n(u16 EE_address,u8 *DataAddress,u16 number);

    void    EEPROM_write_n(u16 EE_address,u8 *DataAddress,u16 number);

    void   EEPROM_SectorErase(u16 EE_address);

    /**********************************************/

    /*************  外部函数和变量声明 *****************/

    u8   CheckData(u8 dat)

    {

    if((dat >= '0') && (dat <= '9'))      return (dat-'0');

    if((dat >= 'A') && (dat <= 'F'))      return (dat-'A'+10);

    if((dat >= 'a') && (dat <= 'f'))      return (dat-'a'+10);

    return 0xff;

    }

    u16   GetAddress(void)

    {

    u16   address;

    u8   i;

    address = 0;

    if(COM1.RX_Cnt <  3)   return 65535;   //error

    if(COM1.RX_Cnt <= 5)   //5个字节以内是扇区操作,十进制, 支持命令:    E 0, E 12, E 120

            //                                    W 0, W 12, W 120

            //                                    R 0, R 12, R 120

    {

    for(i=2; i<COM1.RX_Cnt; i++)

    {

            if(CheckData(RX1_Buffer[i]) > 9)   return 65535;   //error

            address = address * 10 + CheckData(RX1_Buffer[i]);

    }

    if(address < 124)   //限制在0~123扇区

    {

            address <<= 9;

    return (address);

    }

    }

    else if(COM1.RX_Cnt == 8)   //8个字节直接地址操作,十六进制, 支持命令: E 0x1234, W 0x12b3, R 0x0A00

    {

    if((RX1_Buffer[2] == '0') && ((RX1_Buffer[3] == 'x') || (RX1_Buffer[3] == 'X')))

    {

            for(i=4; i<8; i++)

            {

            if(CheckData(RX1_Buffer[i]) > 0x0F)      return 65535;   //error

            address = (address << 4) + CheckData(RX1_Buffer[i]);

            }

            if(address < 63488)   return (address);   //限制在0~123扇区

    }

    }

            return   65535;   //error

    }

    //****************姿态计算*********************************************

    void PWM_int (void) interrupt    22   //PWM中断函数

    {

    PWMCFG = 0;   //CBIF;   //清除中断标志

    }

    void PWMGO(void)

    {

    //   int i=1;

    //设置需要使用的PWM输出口为强推挽模式

    P20 = 0;

    P21 = 0;

    P22 = 0;

    P23 = 0;

    //   P24 = 0;

    //   P25 = 0;

    //   P26 = 0;

    //   P27 = 0;

    P2n_push_pull(0x0f);   // PWM0-P2.0   PWM1-P2.1  PWM2-P2.2  PWM3-P2.3   PWM4-P2.4   PWM5-P2.5  PWM6-P1.6  PWM7-P1.7

    //****************************************以上为I/0初始化******************************************

    //使用定时器2作为时钟源

    EAXSFR();      //访问XFR

    PWMCFG = 0x00;   //   7位                     6位             5位    4位    3位    2位    1位    0位

            //   CBIF

            //1  计数器归零中断标志  计数器归零触发ADC    -      -      -      -      -      -

            //0                      归零时不触发ADC

    PWMIF = 0x00;   //  7位    6位  5位   4位   3位   2位   1位   0位

            //  C7IF  C6IF  C5IF  C4IF  C3IF  C2IF  C1IF  C0IF

            //相应PWM中断标志

    PWMFDCR = 0x00;   //  7位     6位   5位     4位    3位    2位   1位   0位

            // INVCMP  INVIO  ENFD  FLTFLIO  EFDI  FDCMP  FDIO  FDIF

    PWMCKS = 11;   //7位6位5位    4位             3位    2位    1位    0位

            //   置0    0-系统时钟分频          分频参数设定

            //          1-定时器2溢出       时钟=系统时钟/([3:0]+1)

    //PWMC  = 16000;   // 15位寄存器,决定PWM周期,数值为1-32767,单位:脉冲时钟

    PWMC  = 10000;

    // 以下为每个PWM输出口单独设置

    PWM0CR = 0x80;   //     7位      6位        5位   4位3位     2位         1位            0位

            //     ENCnO    CnINI       -    Cn_S      ECnI       ECnT2SI        ECnT1SI

            //1:   允许PWM  初始高电平       IO选择    允许中断   允许T2点中断   允许T1点中断

    //0:   禁止PWM  初始低电平       IO选择    禁止中断   禁止T2点中断   禁止T1点中断

    PWM1CR = 0x80;

    PWM2CR = 0x80;

    PWM3CR = 0x80;

    PWM4CR = 0x80;

    PWM5CR = 0x80;

    PWM6CR = 0x80;

    PWM7CR = 0x80;

    /*

    PWM0HLD = 0x00;

    PWM1HLD = 0x00;

    PWM2HLD = 0x00;

    PWM3HLD = 0x00;

    PWM4HLD = 0x00;

    PWM5HLD = 0x00;

    PWM6HLD = 0x00;

    PWM7HLD = 0x00;

    */

    PWM0T1 = 2000+PWM0*10;

    PWM1T1 = 2000+PWM1*10;

    PWM2T1 = 2000+PWM2*10;

    PWM3T1 = 2000+PWM3*10;

    PWM4T1 = 2000+PWM4*10;

    PWM5T1 = 2000+PWM5*10;

    PWM6T1 = 2000+PWM6*10;

    PWM7T1 = 2000+PWM7*10;

    //   PWM0T1 = 2000;

    //   PWM1T1 = 2000;

    //   PWM2T1 = 2000;

    //   PWM3T1 = 2000;

    //   PWM4T1 = 4000;

    //   PWM5T1 = 4000;

    //   PWM6T1 = 4000;

    //   PWM7T1 = 4000;

    PWM0T2 = 2000;

    PWM1T2 = 2000;

    PWM2T2 = 2000;

    PWM3T2 = 2000;

    PWM4T2 = 2000;

    PWM5T2 = 2000;

    PWM6T2 = 2000;

    PWM7T2 = 2000;

    PWMCR = 0x80;   //允许PWM

    EAXRAM();      //恢复访问XRAM

    }

    void   UART_config(void)

    {

    COMx_InitDefine      COMx_InitStructure;               //结构定义

    COMx_InitStructure.UART_Mode      = UART_8bit_BRTx;      //模式,       UART_ShiftRight,UART_8bit_BRTx,UART_9bit,UART_9bit_BRTx

    COMx_InitStructure.UART_BRT_Use   = BRT_Timer1;         //使用波特率,   BRT_Timer1, BRT_Timer2 (注意: 串口2固定使用BRT_Timer2)

    COMx_InitStructure.UART_BaudRate  = 115200ul;         //波特率, 一般 110 ~ 115200

    COMx_InitStructure.UART_RxEnable  = ENABLE;            //接收允许,   ENABLE或DISABLE

    COMx_InitStructure.BaudRateDouble = DISABLE;         //波特率加倍, ENABLE或DISABLE

    COMx_InitStructure.UART_Interrupt = ENABLE;            //中断允许,   ENABLE或DISABLE

    COMx_InitStructure.UART_Polity    = PolityLow;         //中断优先级, PolityLow,PolityHigh

    COMx_InitStructure.UART_P_SW      = UART1_SW_P30_P31;   //切换端口,   UART1_SW_P30_P31,UART1_SW_P36_P37,UART1_SW_P16_P17(必须使用内部时钟)

    COMx_InitStructure.UART_RXD_TXD_Short = DISABLE;      //内部短路RXD与TXD, 做中继, ENABLE,DISABLE

    USART_Configuration(USART1, &COMx_InitStructure);      //初始化串口1 USART1,USART2

    COMx_InitStructure.UART_Mode      = UART_8bit_BRTx;      //模式,       UART_ShiftRight,UART_8bit_BRTx,UART_9bit,UART_9bit_BRTx

    COMx_InitStructure.UART_BaudRate  = 57600ul;         //波特率,     110 ~ 115200

    COMx_InitStructure.UART_RxEnable  = ENABLE;            //接收允许,   ENABLE或DISABLE

    COMx_InitStructure.UART_Interrupt = ENABLE;            //中断允许,   ENABLE或DISABLE

    COMx_InitStructure.UART_Polity    = PolityLow;         //中断优先级, PolityLow,PolityHigh

    COMx_InitStructure.UART_P_SW      = UART2_SW_P10_P11;   //切换端口,   UART2_SW_P10_P11,UART2_SW_P46_P47

    USART_Configuration(USART2, &COMx_InitStructure);      //初始化串口2 USART1,USART2

    PrintString1("STC15F2K60S2 UART1 Test Prgramme!\r\n");   //SUART1发送一个字符串

    PrintString2("STC15F2K60S2 UART2 Test Prgramme!\r\n");   //SUART2发送一个字符串

    }

    // ===================== 主函数 =====================

    void main(void)

    {

    //所有I/O口全设为准双向,弱上拉模式

    P0M0=0x00;   P0M1=0x00;

    P1M0=0x00;   P1M1=0x00;

    P2M0=0x00;   P2M1=0x00;

    P3M0=0x00;   P3M1=0x00;

    P4M0=0x00;   P4M1=0x00;

    P5M0=0x00;   P5M1=0x00;

    P6M0=0x00;   P6M1=0x00;

    P7M0=0x00;   P7M1=0x00;

    PWMGO();

    //   u8   i;

    UART_config();

    PWMCR =  0xc0;//ECBI;   //允许PWM计数器归零中断

    EA = 1;   //允许总中断

    while (1)

    {

    delay_ms(1);

    if(COM1.RX_TimeOut > 0)      //超时计数

    {

            if(--COM1.RX_TimeOut == 0)

            {

            if(COM1.RX_Cnt > 0)

            {

            for(i=0; i<COM1.RX_Cnt; i++)   TX1_write2buff(RX1_Buffer[i]);   //收到的数据原样返回

            //    EEPROM_SectorErase(0X0100);

            EEPROM_write_n(0X0100,RX1_Buffer,64);

            EEPROM_read_n(0X0100,tmp1,64);

            P0=tmp1;

            //tmp[i]=RX1_Buffer[i];

            //  IAP_Gyro() ;

            //   IAPRead();

            //   PWMAA();

            //   PWMBB();

            if(!P00)

            {

            PWM0=PWM0-10;

            }

            else

            {

            PWM0=0;

            }

            if(!P01)

            {

            PWM1=PWM1-10;

            }

            else

            {

            PWM1=0;

            }

            if(!P02)

            {

            PWM2=PWM2-10;

            }

            else

            {

            PWM2=0;

            }

            if(!P03)

            {

            PWM3=PWM3-10;

            }

            else

            {

            PWM3=0;

            }

            if(!P04)

            {

            PWM4=PWM4-10;

            }

            else

            {

            PWM4=0;

            }

    if(!P05)

            {

            PWM5=PWM5-10;

            }

            else

            {

            PWM5=0;

            }

            if(!P06)

            {

            PWM6=PWM6-10;

            }

            else

            {

            PWM6=0;

            }

            if(!P07)

            {

            PWM7=PWM7-10;

            }

            else

            {

            PWM7=0;

            }

            //   PWM0=tmp[1]+tmp[2];

            //   PWM1=tmp[3]+tmp[4];

            //   PWM2=tmp[5]+tmp[6];

            //   PWM3=tmp[7]+tmp[8];

            //     PWM0=tmp[1];

            //   PWM1=tmp[2];

            //   PWM2=tmp[3];

            //   PWM3=tmp[4];

            PWMGO();

            }

            COM1.RX_Cnt = 0;

            }

    }

    if(COM2.RX_TimeOut > 0)      //超时计数

    {

            if(--COM2.RX_TimeOut == 0)

            {

            if(COM2.RX_Cnt > 0)

            {

            for(i=0; i<COM2.RX_Cnt; i++)   TX2_write2buff(RX2_Buffer[i]);   //收到的数据原样返回

            //   tmp[i]=RX1_Buffer[i];

            tmp[i]=RX1_Buffer[i];

            //    EEPROM_SectorErase(0X0100);

            EEPROM_write_n(0X0100,RX1_Buffer,64);

            EEPROM_read_n(0X0100,tmp1,64);

            P0=tmp1;

            if(!P00)

            {

            PWM0=PWM0+10;

            }

            else

            {

            PWM0=0;

            }

            if(!P01)

            {

            PWM1=PWM1+10;

            }

            else

            {

            PWM1=0;

            }

            if(!P02)

            {

            PWM2=PWM2+10;

            }

            else

            {

            PWM2=0;

            }

            if(!P03)

            {

            PWM3=PWM3+10;

            }

            else

            {

            PWM3=0;

            }

            if(!P04)

            {

            PWM4=PWM4+10;

            }

            else

            {

            PWM4=0;

            }

            if(!P05)

            {

            PWM5=PWM5+10;

            }

            else

            {

            PWM5=0;

            }

            if(!P06)

            {

            PWM6=PWM6+10;

            }

            else

            {

            PWM6=0;

            }

            if(!P07)

            {

            PWM7=PWM7+10;

            }

            else

            {

            PWM7=0;

            }

            PWMGO();

            }

            COM2.RX_Cnt = 0;

            }

    }

    }

    }

    //========================================================================

    // 函数: void   ISP_Disable(void)

    // 描述: 禁止访问ISP/IAP.

    // 参数: non.

    // 返回: non.

    // 版本: V1.0, 2012-10-22

    //========================================================================

    void   DisableEEPROM(void)

    {

    ISP_CONTR = 0;         //禁止ISP/IAP操作

    ISP_CMD   = 0;         //去除ISP/IAP命令

    ISP_TRIG  = 0;         //防止ISP/IAP命令误触发

    ISP_ADDRH = 0xff;      //清0地址高字节

    ISP_ADDRL = 0xff;      //清0地址低字节,指向非EEPROM区,防止误操作

    }

    //========================================================================

    // 函数: void EEPROM_read_n(u16 EE_address,u8 *DataAddress,u16 number)

    // 描述: 从指定EEPROM首地址读出n个字节放指定的缓冲.

    // 参数: EE_address:  读出EEPROM的首地址.

    //       DataAddress: 读出数据放缓冲的首地址.

    //       number:      读出的字节长度.

    // 返回: non.

    // 版本: V1.0, 2012-10-22

    //========================================================================

    void EEPROM_read_n(u16 EE_address,u8 *DataAddress,u16 number)

    {

    EA = 0;      //禁止中断

    ISP_CONTR = (ISP_EN + ISP_WAIT_FREQUENCY);   //设置等待时间,允许ISP/IAP操作,送一次就够

    ISP_READ();                           //送字节读命令,命令不需改变时,不需重新送命令

    do

    {

    ISP_ADDRH = EE_address / 256;      //送地址高字节(地址需要改变时才需重新送地址)

    ISP_ADDRL = EE_address % 256;      //送地址低字节

    ISP_TRIG();                     //先送5AH,再送A5H到ISP/IAP触发寄存器,每次都需要如此

            //送完A5H后,ISP/IAP命令立即被触发启动

            //CPU等待IAP完成后,才会继续执行程序。

    _nop_();

    *DataAddress = ISP_DATA;         //读出的数据送往

    EE_address++;

    DataAddress++;

    }while(--number);

    DisableEEPROM();

    EA = 1;      //重新允许中断

    }

    /******************** 扇区擦除函数 *****************/

    //========================================================================

    // 函数: void EEPROM_SectorErase(u16 EE_address)

    // 描述: 把指定地址的EEPROM扇区擦除.

    // 参数: EE_address:  要擦除的扇区EEPROM的地址.

    // 返回: non.

    // 版本: V1.0, 2013-5-10

    //========================================================================

    void EEPROM_SectorErase(u16 EE_address)

    {

    EA = 0;      //禁止中断

            //只有扇区擦除,没有字节擦除,512字节/扇区。

            //扇区中任意一个字节地址都是扇区地址。

    ISP_ADDRH = EE_address / 256;         //送扇区地址高字节(地址需要改变时才需重新送地址)

    ISP_ADDRL = EE_address % 256;         //送扇区地址低字节

    ISP_CONTR = (ISP_EN + ISP_WAIT_FREQUENCY);   //设置等待时间,允许ISP/IAP操作,送一次就够

    ISP_ERASE();                     //送扇区擦除命令,命令不需改变时,不需重新送命令

    ISP_TRIG();

    _nop_();

    DisableEEPROM();

    EA = 1;      //重新允许中断

    }

    //========================================================================

    // 函数: void EEPROM_write_n(u16 EE_address,u8 *DataAddress,u16 number)

    // 描述: 把缓冲的n个字节写入指定首地址的EEPROM.

    // 参数: EE_address:  写入EEPROM的首地址.

    //       DataAddress: 写入源数据的缓冲的首地址.

    //       number:      写入的字节长度.

    // 返回: non.

    // 版本: V1.0, 2012-10-22

    //========================================================================

    void EEPROM_write_n(u16 EE_address,u8 *DataAddress,u16 number)

    {

    EA = 0;      //禁止中断

    ISP_CONTR = (ISP_EN + ISP_WAIT_FREQUENCY);   //设置等待时间,允许ISP/IAP操作,送一次就够

    ISP_WRITE();                     //送字节写命令,命令不需改变时,不需重新送命令

    do

    {

    ISP_ADDRH = EE_address / 256;      //送地址高字节(地址需要改变时才需重新送地址)

    ISP_ADDRL = EE_address % 256;      //送地址低字节

    ISP_DATA  = *DataAddress;         //送数据到ISP_DATA,只有数据改变时才需重新送

    ISP_TRIG();

    _nop_();

    EE_address++;

    DataAddress++;

    }while(--number);

    DisableEEPROM();

    EA = 1;      //重新允许中断

    }

    #include "USART.h"

    COMx_Define   COM1,COM2;

    u8   xdata TX1_Buffer[COM_TX1_Lenth];   //发送缓冲

    u8    xdata RX1_Buffer[COM_RX1_Lenth];   //接收缓冲

    u8   xdata TX2_Buffer[COM_TX2_Lenth];   //发送缓冲

    u8    xdata RX2_Buffer[COM_RX2_Lenth];   //接收缓冲

    u8 USART_Configuration(u8 UARTx, COMx_InitDefine *COMx)

    {

    u8   i;

    u32   j;

    if(UARTx == USART1)

    {

    COM1.id = 1;

    COM1.TX_read    = 0;

    COM1.TX_write   = 0;

    COM1.B_TX_busy  = 0;

    COM1.RX_Cnt     = 0;

    COM1.RX_TimeOut = 0;

    COM1.B_RX_OK    = 0;

    for(i=0; i<COM_TX1_Lenth; i++)   TX1_Buffer[i] = 0;

    for(i=0; i<COM_RX1_Lenth; i++)   RX1_Buffer[i] = 0;

            if(COMx->UART_Mode > UART_9bit_BRTx)   return 2;   //模式错误

    if(COMx->UART_Polity == PolityHigh)      PS = 1;   //高优先级中断

    else                           PS = 0;   //低优先级中断

    SCON = (SCON & 0x3f) | COMx->UART_Mode;

    if((COMx->UART_Mode == UART_9bit_BRTx) ||(COMx->UART_Mode == UART_8bit_BRTx))   //可变波特率

    {

            j = (MAIN_Fosc / 4) / COMx->UART_BaudRate;   //按1T计算

            if(j >= 65536UL)   return 2;   //错误

            j = 65536UL - j;

    if(COMx->UART_BRT_Use == BRT_Timer1)

            {

            TR1 = 0;

            AUXR &= ~0x01;      //S1 BRT Use Timer1;

            TMOD &= ~(1<<6);   //Timer1 set As Timer

            TMOD &= ~0x30;      //Timer1_16bitAutoReload;

            AUXR |=  (1<<6);   //Timer1 set as 1T mode

            TH1 = (u8)(j>>8);

            TL1 = (u8)j;

            ET1 = 0;   //禁止中断

            TMOD &= ~0x40;   //定时

            INT_CLKO &= ~0x02;   //不输出时钟

            TR1  = 1;

            }

            else if(COMx->UART_BRT_Use == BRT_Timer2)

            {

            AUXR &= ~(1<<4);   //Timer stop

            AUXR |= 0x01;      //S1 BRT Use Timer2;

            AUXR &= ~(1<<3);   //Timer2 set As Timer

            AUXR |=  (1<<2);   //Timer2 set as 1T mode

            TH2 = (u8)(j>>8);

            TL2 = (u8)j;

            IE2  &= ~(1<<2);   //禁止中断

            AUXR &= ~(1<<3);   //定时

            AUXR |=  (1<<4);   //Timer run enable

            }

            else return 2;   //错误

    }

    else if(COMx->UART_Mode == UART_ShiftRight)

    {

            if(COMx->BaudRateDouble == ENABLE)   AUXR |=  (1<<5);   //固定波特率SysClk/2

            else                        AUXR &= ~(1<<5);   //固定波特率SysClk/12

    }

    else if(COMx->UART_Mode == UART_9bit)   //固定波特率SysClk*2^SMOD/64

    {

            if(COMx->BaudRateDouble == ENABLE)   PCON |=  (1<<7);   //固定波特率SysClk/32

            else                        PCON &= ~(1<<7);   //固定波特率SysClk/64

    }

    if(COMx->UART_Interrupt == ENABLE)   ES = 1;   //允许中断

    else                        ES = 0;   //禁止中断

    if(COMx->UART_RxEnable == ENABLE)   REN = 1;   //允许接收

    else                        REN = 0;   //禁止接收

    P_SW1 = (P_SW1 & 0x3f) | (COMx->UART_P_SW & 0xc0);   //切换IO

    if(COMx->UART_RXD_TXD_Short == ENABLE)   PCON2 |=  (1<<4);   //内部短路RXD与TXD, 做中继, ENABLE,DISABLE

    else                           PCON2 &= ~(1<<4);

    return   0;

    }

    if(UARTx == USART2)

    {

    COM2.id = 2;

    COM2.TX_read    = 0;

    COM2.TX_write   = 0;

    COM2.B_TX_busy  = 0;

    COM2.RX_Cnt     = 0;

    COM2.RX_TimeOut = 0;

    COM2.B_RX_OK    = 0;

    for(i=0; i<COM_TX2_Lenth; i++)   TX2_Buffer[i] = 0;

    for(i=0; i<COM_RX2_Lenth; i++)   RX2_Buffer[i] = 0;

    if((COMx->UART_Mode == UART_9bit_BRTx) ||(COMx->UART_Mode == UART_8bit_BRTx))   //可变波特率

    {

            if(COMx->UART_Polity == PolityHigh)      IP2 |=  1;   //高优先级中断

            else                           IP2 &= ~1;   //低优先级中断

            if(COMx->UART_Mode == UART_9bit_BRTx)   S2CON |=  (1<<7);   //9bit

            else                           S2CON &= ~(1<<7);   //8bit

            j = (MAIN_Fosc / 4) / COMx->UART_BaudRate;   //按1T计算

            if(j >= 65536UL)   return 2;   //错误

            j = 65536UL - j;

            AUXR &= ~(1<<4);   //Timer stop

            AUXR &= ~(1<<3);   //Timer2 set As Timer

            AUXR |=  (1<<2);   //Timer2 set as 1T mode

            TH2 = (u8)(j>>8);

            TL2 = (u8)j;

            IE2  &= ~(1<<2);   //禁止中断

            AUXR |=  (1<<4);   //Timer run enable

    }

    else   return 2;   //模式错误

    if(COMx->UART_Interrupt == ENABLE)   IE2   |=  1;      //允许中断

    else                        IE2   &= ~1;      //禁止中断

    if(COMx->UART_RxEnable == ENABLE)   S2CON |=  (1<<4);   //允许接收

    else                        S2CON &= ~(1<<4);   //禁止接收

    P_SW2 = (P_SW2 & ~1) | (COMx->UART_P_SW & 0x01);   //切换IO

    }

    }

    /*************** 装载串口发送缓冲 *******************************/

    void TX1_write2buff(u8 dat)   //写入发送缓冲,指针+1

    {

    TX1_Buffer[COM1.TX_write] = dat;   //装发送缓冲

    if(++COM1.TX_write >= COM_TX1_Lenth)   COM1.TX_write = 0;

    if(COM1.B_TX_busy == 0)      //空闲

    {

    COM1.B_TX_busy = 1;      //标志忙

    TI = 1;               //触发发送中断

    }

    }

    void TX2_write2buff(u8 dat)   //写入发送缓冲,指针+1

    {

    TX2_Buffer[COM2.TX_write] = dat;   //装发送缓冲

    if(++COM2.TX_write >= COM_TX2_Lenth)   COM2.TX_write = 0;

    if(COM2.B_TX_busy == 0)      //空闲

    {

    COM2.B_TX_busy = 1;      //标志忙

    SET_TI2();            //触发发送中断

    }

    }

    void PrintString1(u8 *puts)

    {

    for (; *puts != 0;   puts++)  TX1_write2buff(*puts);    //遇到停止符0结束

    }

    void PrintString2(u8 *puts)

    {

    for (; *puts != 0;   puts++)  TX2_write2buff(*puts);    //遇到停止符0结束

    }

    /*

    void COMx_write2buff(COMx_Define *COMx, u8 dat)   //写入发送缓冲,指针+1

    {

    if(COMx->id == 1)   TX1_write2buff(dat);

    if(COMx->id == 2)   TX2_write2buff(dat);

    }

    void PrintString(COMx_Define *COMx, u8 *puts)

    {

    for (; *puts != 0;   puts++)  COMx_write2buff(COMx,*puts);    //遇到停止符0结束

    }

    */

    /********************* UART1中断函数************************/

    void UART1_int (void) interrupt UART1_VECTOR

    {

    if(RI)

    {

    RI = 0;

    if(COM1.B_RX_OK == 0)

    {

            if(COM1.RX_Cnt >= COM_RX1_Lenth)   COM1.RX_Cnt = 0;

            RX1_Buffer[COM1.RX_Cnt++] = SBUF;

            COM1.RX_TimeOut = TimeOutSet1;

    }

    }

    if(TI)

    {

    TI = 0;

    if(COM1.TX_read != COM1.TX_write)

    {

            SBUF = TX1_Buffer[COM1.TX_read];

            if(++COM1.TX_read >= COM_TX1_Lenth)      COM1.TX_read = 0;

    }

    else   COM1.B_TX_busy = 0;

    }

    }

    /********************* UART2中断函数************************/

    void UART2_int (void) interrupt UART2_VECTOR

    {

    if(RI2)

    {

    CLR_RI2();

    if(COM2.B_RX_OK == 0)

    {

            if(COM2.RX_Cnt >= COM_RX2_Lenth)   COM2.RX_Cnt = 0;

            RX2_Buffer[COM2.RX_Cnt++] = S2BUF;

            COM2.RX_TimeOut = TimeOutSet2;

    }

    }

    if(TI2)

    {

    CLR_TI2();

    if(COM2.TX_read != COM2.TX_write)

    {

            S2BUF = TX2_Buffer[COM2.TX_read];

            if(++COM2.TX_read >= COM_TX2_Lenth)      COM2.TX_read = 0;

    }

    else   COM2.B_TX_busy = 0;

    }

    }

    #include   "delay.h"

    void  delay_ms(unsigned char ms)

    {

    unsigned int i;

    do{

            i = MAIN_Fosc / 13000;

            while(--i)   ;   //14T per loop

    }while(--ms);

    }

    使用KEILL4软件编译上述程序,同时,用台湾宏晶科技有限公司的单片机下载程序stc-isp-15xx-v6.86下载程序选择24M频率下载程序,在串口设置为 波特率115200,数据位8,校验位N,停止位1,无校验,进行通讯,在串口1发送任意16进制字符,8路PWM波形的占空比增加,在串口2发送任意字符,8路PWM波形的占空比减小。

    如图5所示使用SOLIDWORKS软件对导弹做静态应力分析,导弹的安全系数是3903.33,子弹头不为变形量最大,为0.1mm。

    上述的一种具有三轴圆周64个圆球的弹道导弹变质心装置,所述的是一种安装在弹道导弹弹体中部的圆环装置。

    附图说明

    下面结合附图和实施例对本实用新型进一步说明。

    图1为本实用新型结构图。

    图2为本实用新型装置结构图。

    图3为本实用新型三轴结构图。

    图4为本实用新型控制电路图。

    图5为本实用新型单片机下载PWM驱动电路图。

    图6为本实用新型单片机下载PWM驱动电路图静态应力分析图。

    图7为本实用新型控制电路图。

    图8为本实用新型控制电路图。

    图9为本实用新型控制电路图。

    图1中,1.导弹弹头,2. 导弹弹体,3.变质心装置上的圆环,4,火箭发动机。

    图2中,3. 变质心装置上的圆环,5. 变质心装置上的圆球,6. 变质心装置上的圆杆。

    图3中,7. Y轴圆环,8. X轴圆环,9. Z轴圆环。

    图4中,单片机STC8A8K64S4A12有2个串口。

    具体实施方式

    图1中,弹道导弹的弹头(1)安装在导弹单体(2)上部,变质心装置的圆环(3)安装在导弹弹体中部,火箭发动机(4)安装在导弹底部。

    图2中,64个圆球(5)安装在导弹变质心装置的一个圆环(3)上面。这64个圆球分别安装在相互垂直的3个圆环(7),(8),(9)上面。64个圆球(5)分别用圆环圆心处的圆杆(6)和圆环的圆心相连,64个圆球(5)被和圆环圆心相连的圆杆(6)拉着在圆环(3)上面滚动,就会使导弹单体的质心发生改变,进而会使导弹的质心发生改变。

    图3中X轴圆环,Y轴圆环,Z轴圆环相互垂直。每个圆环上面安装64个位置可调的圆球。

    图1

    图2

    图3

    图4

    图5

    图6



    发帖须知:

    1,发帖请遵守《计算机信息网络国际联网安全保护管理办法》、《互联网信息服务管理办法》、 《互联网电子公告服务管理规定》、《维护互联网安全的决定》等法律法规。

    2,请对您的言论负责,我们将保留您的上网记录和发帖信息。

    3,在此发帖表示认同我们的条款,我们有权利对您的言论进行审核、删除或者采取其他在法律、地方法规等条款规定之内的管理操作。
    内容:
    验证: 验证码,看不清楚?请点击刷新验证码 * 匿名发表需要进行验证!
     
           
    中国面包师贴吧-中国烘焙师贴吧- 弹性深蓝色可爱版右侧悬浮qq在线客服代码
    在线咨询 x
    有什么可以帮到您
    点击咨询
    -粤ICP备13040473号-2