OLED示波器的實現

OLED示波器是一種使用有機發光二極管(OLED)顯示屏來顯示波形的儀器。它可以實時顯示電壓、電流、頻率等信號的波形。

OLED顯示屏具有高對比度、高亮度、廣視角和快速響應時間等優點,使得OLED示波器在波形顯示方面具有更好的表現。與傳統的液晶顯示屏相比,OLED顯示屏的黑色更加純正,并且可以顯示更細小的細節。

OLED示波器通常具有多個通道,可以同時顯示多個信號的波形。它還可以通過調整時間、電壓和觸發等參數,更好地觀察和分析信號的特性。

我們移植了OLED示波器后可以用杜邦線接出單片機引腳,可用于查看某個模塊的波形等,方便程序調試。

我使用了FreeRTOS,要移植把任務改成int main 即可,注意引腳初始化。

#define accur 0.015295//accur=18*3.3/4096(3.3/4096就是ADC采樣精度,18是為了讓波形轉化一下能夠顯示在適當位子)/* wave開始任務 */
void wave_task(void *pvParameters)
{	u16 x=0;uint16_t ConvData=0;//ADC采樣數據while(1){	if(x<128){xQueueReceive(xQueue4,&ConvData,0);OLED_DrawWave(x,accur*ConvData);//這是個畫波形的函數//ConvData=0; 不注釋就是柱形x=(x+1)%128;}vTaskDelay(10);}
}

oled.c

#include "OLED.h"
#include "codetab.h"
#include "at32f435_437_board.h"
#include "at32f435_437_clock.h"
#include "at32f435_437_gpio.h"
#define OLED_CMD  0	//
#define OLED_DATA 1	//
#define OLED_MODE 0//OLED模式設置
//0:4線串行模式
//1:并行8080模式#define SIZE 16
#define XLevelL		0x02
#define XLevelH		0x10
#define Max_Column	128
#define Max_Row		64
#define	Brightness	0xFF 
#define X_WIDTH 	128
#define Y_WIDTH 	64	    
#define WriteCmd(x) oledWriteByte(x,OLED_CMD)
#define WriteDat(x) oledWriteByte(x,OLED_DATA)
#define OLED_DC_Set() gpio_bits_write(GPIOD, GPIO_PINS_6, TRUE)
#define OLED_DC_Clr() gpio_bits_write(GPIOD, GPIO_PINS_6, FALSE)
#define OLED_CS_Set() gpio_bits_write(GPIOD, GPIO_PINS_3, TRUE)
#define OLED_CS_Clr() gpio_bits_write(GPIOD, GPIO_PINS_3, FALSE)
/*
#define OLED_CS_Set() gpio_bits_write(GPIOC, GPIO_PINS_3, TRUE)
#define OLED_CS_Clr() gpio_bits_write(GPIOC, GPIO_PINS_3, FALSE)
#define OLED_DC_Set() gpio_bits_write(GPIOB, GPIO_PINS_1, TRUE)
#define OLED_DC_Clr() gpio_bits_write(GPIOB, GPIO_PINS_1, FALSE)*/
#define OLED_RST_Set() gpio_bits_write(GPIOE, GPIO_PINS_6, TRUE)
#define OLED_RST_Clr() gpio_bits_write(GPIOE, GPIO_PINS_6, FALSE)uint8_t Bef[3];//保存前一個數據的幾個參數1.要寫在第幾頁2.0x01要移動幾位3.寫什么數據
uint8_t Cur[3];//當前前一個數據1.要寫在第幾頁2.0x01要移動幾位3.寫什么數據
/*** @brief  spi configuration.* @param  none* @retval none*/
static void spi_config(void)
{spi_init_type spi_init_struct;crm_periph_clock_enable(CRM_SPI3_PERIPH_CLOCK, TRUE);spi_default_para_init(&spi_init_struct);spi_init_struct.transmission_mode = SPI_TRANSMIT_HALF_DUPLEX_TX;spi_init_struct.master_slave_mode = SPI_MODE_MASTER;spi_init_struct.mclk_freq_division = SPI_MCLK_DIV_32;spi_init_struct.first_bit_transmission = SPI_FIRST_BIT_MSB;spi_init_struct.frame_bit_num = SPI_FRAME_8BIT;spi_init_struct.clock_polarity = SPI_CLOCK_POLARITY_LOW;spi_init_struct.clock_phase = SPI_CLOCK_PHASE_1EDGE;spi_init_struct.cs_mode_selection = SPI_CS_SOFTWARE_MODE;spi_init(SPI3, &spi_init_struct);spi_enable(SPI3, TRUE);
}/*** @brief  gpio configuration.* @param  none* @retval none*/
static void oled_gpio_config(void)
{gpio_init_type gpio_initstructure;crm_periph_clock_enable(CRM_GPIOC_PERIPH_CLOCK, TRUE);crm_periph_clock_enable(CRM_GPIOD_PERIPH_CLOCK, TRUE);crm_periph_clock_enable(CRM_GPIOB_PERIPH_CLOCK, TRUE);crm_periph_clock_enable(CRM_GPIOE_PERIPH_CLOCK, TRUE);gpio_default_para_init(&gpio_initstructure);/* spi3 sck pin  PB 3*/ gpio_initstructure.gpio_out_type       = GPIO_OUTPUT_PUSH_PULL;gpio_initstructure.gpio_drive_strength = GPIO_DRIVE_STRENGTH_STRONGER;gpio_initstructure.gpio_pull           = GPIO_PULL_DOWN;gpio_initstructure.gpio_mode           = GPIO_MODE_MUX;gpio_initstructure.gpio_pins = GPIO_PINS_3;gpio_init(GPIOB, &gpio_initstructure);gpio_pin_mux_config(GPIOB, GPIO_PINS_SOURCE3, GPIO_MUX_6);/* spi3 mosi pin */gpio_initstructure.gpio_pull           = GPIO_PULL_DOWN;gpio_initstructure.gpio_pins           = GPIO_PINS_5;gpio_init(GPIOB, &gpio_initstructure);gpio_pin_mux_config(GPIOB, GPIO_PINS_SOURCE5, GPIO_MUX_6);/* set default parameter */gpio_default_para_init(&gpio_initstructure);/* configure the led gpio */gpio_initstructure.gpio_drive_strength = GPIO_DRIVE_STRENGTH_STRONGER;gpio_initstructure.gpio_out_type  = GPIO_OUTPUT_PUSH_PULL;gpio_initstructure.gpio_mode = GPIO_MODE_OUTPUT;gpio_initstructure.gpio_pins = GPIO_PINS_3;gpio_initstructure.gpio_pull = GPIO_PULL_NONE;gpio_init(GPIOD, &gpio_initstructure);gpio_initstructure.gpio_pins = GPIO_PINS_6;gpio_init(GPIOD, &gpio_initstructure);}void SPI_OLED_Init(void){oled_gpio_config();spi_config();OLED_CS_Clr();OLED_RST_Set();delay_ms(10);OLED_RST_Clr();delay_ms(10);OLED_RST_Set();}void spitransferByte(char data)
{spi_i2s_data_transmit(SPI3, data);while(spi_i2s_flag_get(SPI3, SPI_I2S_BF_FLAG) == SET);}void oledWriteByte(u8 dat, u8 cmd)
{if (cmd){OLED_DC_Set();}else if (cmd != 1){OLED_DC_Clr();}OLED_CS_Clr();spitransferByte(dat);OLED_CS_Set();OLED_DC_Set();
}void OLED_Init(void)
{SPI_OLED_Init();OLED_RST_Set();delay_ms(10);OLED_RST_Clr();delay_ms(10);OLED_RST_Set();WriteCmd(0xAE); //display offWriteCmd(0x20);	//Set Memory Addressing Mode	WriteCmd(0x10);	//00,Horizontal Addressing Mode;01,Vertical Addressing Mode;10,Page Addressing Mode (RESET);11,InvalidWriteCmd(0xb0);	//Set Page Start Address for Page Addressing Mode,0-7WriteCmd(0xc8);	//Set COM Output Scan DirectionWriteCmd(0x00); //---set low column addressWriteCmd(0x10); //---set high column addressWriteCmd(0x40); //--set start line addressWriteCmd(0x81); //--set contrast control registerWriteCmd(0xff); //亮度調節 0x00~0xffWriteCmd(0xa1); //--set segment re-map 0 to 127WriteCmd(0xa6); //--set normal displayWriteCmd(0xa8); //--set multiplex ratio(1 to 64)WriteCmd(0x3F); //WriteCmd(0xa4); //0xa4,Output follows RAM content;0xa5,Output ignores RAM contentWriteCmd(0xd3); //-set display offsetWriteCmd(0x00); //-not offsetWriteCmd(0xd5); //--set display clock divide ratio/oscillator frequencyWriteCmd(0xf0); //--set divide ratioWriteCmd(0xd9); //--set pre-charge periodWriteCmd(0x22); //WriteCmd(0xda); //--set com pins hardware configurationWriteCmd(0x12);WriteCmd(0xdb); //--set vcomhWriteCmd(0x20); //0x20,0.77xVccWriteCmd(0x8d); //--set DC-DC enableWriteCmd(0x14); //WriteCmd(0xaf); //--turn on oled panel
}void OLED_SetPos(unsigned char x, unsigned char y) //設置起始點坐標
{ WriteCmd(0xb0+x);WriteCmd((y&0x0f)|0x00);//LOWWriteCmd(((y&0xf0)>>4)|0x10);//HIGHT
}void OLED_Fill(unsigned char fill_Data)
{unsigned char m,n;for(m=0;m<8;m++){WriteCmd(0xb0+m);		//page0-page1WriteCmd(0x00);		//low column start addressWriteCmd(0x10);		//high column start addressfor(n=0;n<128;n++){WriteDat(fill_Data);}}
}void OLED_CLS(void)//清屏
{OLED_Fill(0x00);
}//--------------------------------------------------------------
// Prototype      : void OLED_ON(void)
// Calls          : 
// Parameters     : none
// Description    : 將OLED從休眠中喚醒
//--------------------------------------------------------------
void OLED_ON(void)
{WriteCmd(0X8D);  //設置電荷泵WriteCmd(0X14);  //開啟電荷泵WriteCmd(0XAF);  //OLED喚醒
}//--------------------------------------------------------------
// Prototype      : void OLED_OFF(void)
// Calls          : 
// Parameters     : none
// Description    : 讓OLED休眠 -- 休眠模式下,OLED功耗不到10uA
//--------------------------------------------------------------
void OLED_OFF(void)
{WriteCmd(0X8D);  //設置電荷泵WriteCmd(0X10);  //關閉電荷泵WriteCmd(0XAE);  //OLED休眠
}//--------------------------------------------------------------
// Prototype      : void OLED_ShowChar(unsigned char x, unsigned char y, unsigned char ch[], unsigned char TextSize)
// Calls          : 
// Parameters     : x,y -- 起始點坐標(x:0~127, y:0~7); ch[] -- 要顯示的字符串; TextSize -- 字符大小(1:6*8 ; 2:8*16)
// Description    : 顯示codetab.h中的ASCII字符,有6*8和8*16可選擇
//--------------------------------------------------------------
void OLED_ShowStr(unsigned char x, unsigned char y, unsigned char ch[], unsigned char TextSize)
{unsigned char c = 0,i = 0,j = 0;switch(TextSize){case 1:{while(ch[j] != '\0'){c = ch[j] - 32;if(x > 126){x = 0;y++;}//OLED_SetPos(x,y);OLED_SetPos(y,x);for(i=0;i<6;i++)WriteDat(F6x8[c][i]);x += 6;j++;}}break;case 2:{while(ch[j] != '\0'){c = ch[j] - 32;if(x > 120){x = 0;y++;}//OLED_SetPos(x,y);OLED_SetPos(y,x);for(i=0;i<8;i++)WriteDat(F8X16[c*16+i]);//OLED_SetPos(x,y+1);OLED_SetPos(y+1,x);for(i=0;i<8;i++)WriteDat(F8X16[c*16+i+8]);x += 8;j++;}}break;}
}//--------------------------------------------------------------
// Prototype      : void OLED_ShowCN(unsigned char x, unsigned char y, unsigned char N)
// Calls          : 
// Parameters     : x,y -- 起始點坐標(x:0~127, y:0~7); N:漢字在codetab.h中的索引
// Description    : 顯示codetab.h中的漢字,16*16點陣
//--------------------------------------------------------------
void OLED_ShowCN(unsigned char x, unsigned char y, unsigned char N)
{// Parameters     : x,y -- 起始點坐標(x:0~127, y:0~7); N:漢字在codetab.h中的索引// Description    : 顯示codetab.h中的漢字,16*16點陣unsigned char wm=0;unsigned int  adder=32*N;//OLED_SetPos(x , y);OLED_SetPos(y,x);for(wm = 0;wm < 16;wm++){WriteDat(F16x16[adder]);adder += 1;}//OLED_SetPos(x,y + 1);OLED_SetPos(y+1,x);for(wm = 0;wm < 16;wm++){WriteDat(F16x16[adder]);adder += 1;}
}//--------------------------------------------------------------
// Prototype      : void OLED_DrawBMP(unsigned char x0,unsigned char y0,unsigned char x1,unsigned char y1,unsigned char BMP[]);
// Calls          : 
// Parameters     : x0,y0 -- 起始點坐標(x0:0~127, y0:0~7); x1,y1 -- 起點對角線(結束點)的坐標(x1:1~128,y1:1~8)
// Description    : 顯示BMP位圖
//--------------------------------------------------------------
void OLED_DrawBMP(unsigned char x0,unsigned char y0,unsigned char x1,unsigned char y1,unsigned char BMP[])
{// Parameters     : x0,y0 -- 起始點坐標(x0:0~127, y0:0~7); x1,y1 -- 起點對角線(結束點)的坐標(x1:1~128,y1:1~8)// Description    : 顯示BMP位圖unsigned int j=0;unsigned char x,y;if(y1%8==0)y = y1/8;elsey = y1/8 + 1;for(y=y0;y<y1;y++){//OLED_SetPos(x0,y);OLED_SetPos(y,x0);for(x=x0;x<x1;x++){WriteDat(BMP[j++]);}}
}由B站Up主“爾等小眾”開源
///打波函數//
void Before_State_Update(uint8_t y)//根據y的值,求出前一個數據的有關參數
{Bef[0]=7-y/8;Bef[1]=7-y%8;Bef[2]=1<<Bef[1];
}
void Current_State_Update(uint8_t y)//根據Y值,求出當前數據的有關參數
{Cur[0]=7-y/8;//數據寫在第幾頁Cur[1]=7-y%8;//0x01要移動的位數Cur[2]=1<<Cur[1];//要寫什么數據
}void OLED_DrawWave(uint8_t x,uint8_t y)
{int8_t page_sub;uint8_t page_buff,i,j;Current_State_Update(y);//根據Y值,求出當前數據的有關參數page_sub=Bef[0]-Cur[0];//當前值與前一個值的頁數相比較//確定當前列,每一頁應該寫什么數據if(page_sub>0){page_buff=Bef[0];OLED_SetPos(page_buff,x);WriteDat(Bef[2]-0x01);page_buff--;for(i=0;i<page_sub-1;i++){OLED_SetPos(page_buff,x);WriteDat(0xff);page_buff--;}OLED_SetPos(page_buff,x);WriteDat(0xff<<Cur[1]);}else if(page_sub==0){if(Cur[1]==Bef[1]){OLED_SetPos(Cur[0],x);WriteDat(Cur[2]);}else if(Cur[1]>Bef[1]){OLED_SetPos(Cur[0],x);WriteDat((Cur[2]-Bef[2])|Cur[2]);}else if(Cur[1]<Bef[1]){OLED_SetPos(Cur[0],x);WriteDat(Bef[2]-Cur[2]);}}else if(page_sub<0){page_buff=Cur[0];OLED_SetPos(page_buff,x);WriteDat((Cur[2]<<1)-0x01);page_buff--;for(i=0;i<0-page_sub-1;i++){OLED_SetPos(page_buff,x);WriteDat(0xff);page_buff--;}OLED_SetPos(page_buff,x);WriteDat(0xff<<(Bef[1]+1));}Before_State_Update(y);//把下一列,每一頁的數據清除掉for(i=0;i<8;i++){OLED_SetPos(i, x+1) ;for(j=0;j<1;j++)WriteDat(0x00);}
}

移植參考說明

本文OLED示波器參考【0.96寸OLED示波】 https://www.bilibili.com/video/BV11E411V72p

他的oled是iic 我的是spi

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/web/40352.shtml
繁體地址,請注明出處:http://hk.pswp.cn/web/40352.shtml
英文地址,請注明出處:http://en.pswp.cn/web/40352.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

鴻蒙開發設備管理:【@ohos.usb (USB管理)】

USB管理 本模塊主要提供管理USB設備的相關功能&#xff0c;包括查詢USB設備列表、批量數據傳輸、控制命令傳輸、權限控制等。 說明&#xff1a; 本模塊首批接口從API version 8開始支持。后續版本的新增接口&#xff0c;采用上角標單獨標記接口的起始版本。 導入模塊 import …

【JavaScript腳本宇宙】優化你的Web色彩:精選JavaScript顏色工具對比

萬能色彩助手&#xff1a;詳解最受歡迎的JavaScript顏色庫 前言 在現代Web開發中&#xff0c;顏色處理和轉換是一個不可忽視的環節。無論是網站設計、數據可視化還是用戶界面開發&#xff0c;都離不開對顏色的精確控制和轉換。為了滿足這一需求&#xff0c;眾多JavaScript庫應…

Toocaa Studio已開發的功能

2024年07月01日 Toocaa Studio 一個激光切割雕刻機的上位機&#xff0c; 未來會對標Xtool的xTool Creative Space和LightBurn&#xff0c;同時它也是一款圖形編輯器&#xff0c;矢量圖形編輯器。 工具類 鼠標畫矩形或正方形 鼠標畫橢圓或畫圓 鼠標畫直線或軌跡路徑 往畫布中…

你的機器人購物新體驗——安全、高效、無憂

如果你跟我一樣&#xff0c;對找到那些“恰到好處”的商品充滿渴望&#xff0c;那么&#xff0c;讓我來告訴你為什么BFT會成為你的下一個購物“心頭好”。 BFT的優勢 高效安全的支付體系&#xff1a;BFT交易系統保障了交易的安全性和透明性&#xff0c;讓你的每一筆消費都安全…

Build a Large Language Model (From Scratch)附錄B(gpt-4o翻譯版)

來源&#xff1a;https://github.com/rasbt/LLMs-from-scratch?tabreadme-ov-file https://www.manning.com/books/build-a-large-language-model-from-scratch

《More Effective C++》《雜項討論——34、如何在同一個程序中結合C++和C》

文章目錄 1、Terms34:如何在同一個程序中結合C和C1.1 名稱重整1.2 statics的初始化1.3 動態內存的分配1.4 數據結構的兼容性 2、總結3、參考 1、Terms34:如何在同一個程序中結合C和C 在大型項目中一般都用C進行開發&#xff0c;但是不可避免會用一些C語言進行底層的調用。在確…

【寵粉贈書】UML 2.5基礎、建模與設計實踐

為了回饋粉絲們的厚愛&#xff0c;今天小智給大家送上一套系統建模學習的必備書籍——《UML 2.5基礎、建模與設計實踐》。下面我會詳細給大家介紹這本書&#xff0c;文末留有領取方式。 圖書介紹 《UML 2.5基礎、建模與設計實踐》以實戰為主旨&#xff0c;結合draw.io免費軟件…

匿名內部類

下面代碼中&#xff0c;Person24 是一個抽象類&#xff0c;這意味著它不能被直接實例化&#xff0c;只能通過繼承它的子類來實現其抽象方法。代碼片段中展示了如何使用匿名內部類來實現一個抽象類的實例。 package chapter04;public class Java24_Object_匿名內部類 {public s…

verilog行為建模(三):塊語句

目錄 1.塊語句2.延遲賦值語句 微信公眾號獲取更多FPGA相關源碼&#xff1a; 1.塊語句 塊語句用來將多個語句組織在一起&#xff0c;使得他們在語法上如同一個語句。 塊語句分為兩類&#xff1a; 順序塊&#xff1a;語句置于關鍵字begin和end之間&#xff0c;塊中的語句以順…

鴻蒙‘ohpm‘ 不是內部或外部命令,也不是可運行的程序-解決方案

&#x1f525; 博客主頁&#xff1a; 小韓本韓&#xff01; ?? 感謝大家點贊&#x1f44d;收藏?評論?? 在鴻蒙的DevEco Studio的終端下輸入 onpm -v 或者 你需要下載第三方ohpm包的時候提示‘ohpm‘ 不是內部或外部命令&#xff0c;也不是可運行的程序- 主要是因為我們…

學習測試1

計算機基礎 1、計算機范式&#xff1a;馮諾依曼機 2、存儲單元 bit、byte、KB、MB、GB3、網絡 ip、域名、ping 域名、 ipconfig測試工作的流程 ------------------------------------------------------------------------------------------- 一 編寫測試大綱 羅列測試…

C++STL函數對象的應用

STL函數對象 文章目錄 STL函數對象1.基本概念2.使用方法1. 簡單函數對象示例2. 函數對象作為算法參數3. Lambda表達式作為函數對象 2.一元謂詞和二元謂詞1.一元謂詞2.二元謂詞3.總結 3.算術仿函數1.使用示例2.Lambda表達式的替代 4.關系仿函數5.邏輯仿函數 C中的函數對象&#…

文化創新與社交媒體:探索Facebook的足跡

在過去的十多年里&#xff0c;Facebook從一個簡單的校園社交網絡發展成為全球最大的社交媒體平臺之一。它不僅改變了人們的溝通方式&#xff0c;更在許多方面推動了文化的創新和變革。本文將深入探索Facebook如何通過其平臺的演進和功能創新&#xff0c;成為文化創新的重要推動…

Ubuntu / Debian安裝FTP服務

本章教程,記錄在Ubuntu中安裝FTP服務的具體步驟。FTP默認端口:21 1、安裝 pure-ftpd sudo apt-get install pure-ftpd2、修改默認配置 # 與 centos 不同,這里需要在 /etc/pure-ftpd/conf 文件夾下執行下列命令,增加對應配置文件: # 創建 /etc/pure-ftpd/conf/PureDB 文件…

【數據結構】(6.2)堆的應用——Top-K問題(C語言)

系列文章目錄 文章目錄 系列文章目錄問題引入一、TopK 問題 是什么&#xff1f;二、TopK 問題解決思路2.1 TopK 思路2.2 隨機產生數字2.2 完整代碼2.3 驗證結果 問題引入 TopK 問題 (在一堆數據里面找到前 K 個最大 / 最小的數)。 一、TopK 問題 是什么&#xff1f; 生活中也…

2024 最新docker倉庫鏡像,6月,7月

目前下面的docker倉庫鏡像源還能使用。 vi /etc/docker/daemon.json添加如下配置{"registry-mirrors": ["https://hub.uuuadc.top", "https://docker.anyhub.us.kg", "https://dockerhub.jobcher.com", "https://dockerhub.icu&…

船舶雷達與導航系統選擇7/8防水插座的原因分析

概述 船舶雷達與導航系統在現代航海中扮演著至關重要的角色&#xff0c;它們為船舶提供準確的導航信息&#xff0c;確保航行的安全和效率。在這些系統中&#xff0c;7/8防水插座的使用尤為重要&#xff0c;因為它們能夠在惡劣的海上環境中提供穩定的電力和信號連接。接下來&am…

python的os.walk()

os.walk() 是一個非常有用的函數&#xff0c;用于在Python中遍歷文件夾樹。它返回一個生成器&#xff0c;該生成器在每次迭代時返回一個包含三個元素的元組&#xff1a;(當前文件夾的路徑&#xff0c;文件夾中的子文件夾的列表&#xff0c;文件夾中的文件的列表)。這個函數對于…

左耳聽風_007_06_如何才能擁有技術領導力

你好&#xff0c;我是陳浩老明左耳朵house.那通過上節課呢&#xff0c;相信你現在已經理解了什么才是技術領導力。 那今天呢我就來跟你繼續聊一聊怎樣才能擁有技術領導力。 首先呢你需要吃透基礎技術。 因為基礎技術啊是各種上層技術共同的技術。 吃透基礎技術是為了更好的…

Outlook發送大文件的問題是什么?怎么解決?

Outlook不僅是一款電子郵件客戶端&#xff0c;還包括日歷、任務、筆記、聯系人等功能&#xff0c;同時與Microsoft Office套件中的其他應用程序&#xff08;如Word、Excel、PowerPoint等&#xff09;集成緊密&#xff0c;方便用戶在不同應用程序之間切換&#xff0c;提高工作效…