import xml.etree.ElementTree as ET def make_mxfile(): # 基础参数 y_cs_high, y_cs_low = 80, 110 y_sclk_high, y_sclk_low = 180, 210 y_mosi_high, y_mosi_low = 280, 310 y_miso_high, y_miso_low = 380, 410 # 8个bit周期,每个100px,从x=100开始,到x=900结束 rise_edges = [150, 250, 350, 450, 550, 650, 750, 850] fall_edges = [190, 290, 390, 490, 590, 690, 790, 890] # MOSI: 0x5A = 0b01011010, MSB first mosi_bits = [0, 1, 0, 1, 1, 0, 1, 0] # MISO: 0xA5 = 0b10100101, MSB first miso_bits = [1, 0, 1, 0, 0, 1, 0, 1] lines = [] lines.append('') lines.append('') lines.append(' ') lines.append(' ') lines.append(' ') lines.append(' ') lines.append(' ') # 背景网格 lines.append(' ') lines.append(' ') lines.append(' ') # 标题 lines.append(' ') lines.append(' ') lines.append(' ') # MSB / LSB lines.append(' ') lines.append(' ') lines.append(' ') lines.append(' ') lines.append(' ') lines.append(' ') # 信号标签 for label, y, eid in [("CS", 85, "label_cs"), ("SCLK", 185, "label_sclk"), ("MOSI", 275, "label_mosi"), ("MISO", 365, "label_miso")]: lines.append(f' ') lines.append(f' ') lines.append(' ') # 垂直参考虚线(放在每个上升沿采样点) for i, x in enumerate(rise_edges): lines.append(f' ') lines.append(' ') lines.append(f' ') lines.append(f' ') lines.append(' ') lines.append(' ') # CS 波形 cs_points = [ (80, y_cs_high), (90, y_cs_high), (90, y_cs_low), (910, y_cs_low), (910, y_cs_high), (920, y_cs_high) ] lines.append(' ') lines.append(' ') lines.append(f' ') lines.append(f' ') lines.append(' ') for x, y in cs_points[1:-1]: lines.append(f' ') lines.append(' ') lines.append(' ') lines.append(' ') # SCLK 波形 sclk_pts = [(80, y_sclk_low), (100, y_sclk_low)] for rise, fall in zip(rise_edges, fall_edges): sclk_pts.extend([ (rise, y_sclk_low), (rise, y_sclk_high), (fall, y_sclk_high), (fall, y_sclk_low), ]) sclk_pts.append((920, y_sclk_low)) lines.append(' ') lines.append(' ') lines.append(f' ') lines.append(f' ') lines.append(' ') for x, y in sclk_pts[1:-1]: lines.append(f' ') lines.append(' ') lines.append(' ') lines.append(' ') # MOSI 波形 mosi_start_y = y_mosi_high if mosi_bits[0] else y_mosi_low mosi_pts = [(80, mosi_start_y), (100, mosi_start_y)] for i, bit in enumerate(mosi_bits): y_level = y_mosi_high if bit else y_mosi_low end_x = fall_edges[i] if i < len(fall_edges) else 900 mosi_pts.append((end_x, y_level)) if i + 1 < len(mosi_bits): y_next = y_mosi_high if mosi_bits[i+1] else y_mosi_low if y_next != y_level: mosi_pts.append((end_x, y_next)) mosi_pts.append((920, mosi_pts[-1][1])) lines.append(' ') lines.append(' ') lines.append(f' ') lines.append(f' ') lines.append(' ') for x, y in mosi_pts[1:-1]: lines.append(f' ') lines.append(' ') lines.append(' ') lines.append(' ') # MISO 波形 — 修复:sourcePoint 与第一个中间点同 y,避免斜线 miso_start_y = y_miso_high if miso_bits[0] else y_miso_low miso_pts = [(80, miso_start_y), (100, miso_start_y)] for i, bit in enumerate(miso_bits): y_level = y_miso_high if bit else y_miso_low end_x = fall_edges[i] if i < len(fall_edges) else 900 miso_pts.append((end_x, y_level)) if i + 1 < len(miso_bits): y_next = y_miso_high if miso_bits[i+1] else y_miso_low if y_next != y_level: miso_pts.append((end_x, y_next)) miso_pts.append((920, miso_pts[-1][1])) lines.append(' ') lines.append(' ') lines.append(f' ') lines.append(f' ') lines.append(' ') for x, y in miso_pts[1:-1]: lines.append(f' ') lines.append(' ') lines.append(' ') lines.append(' ') # MOSI 数据位标签 mosi_centers = [145, 240, 340, 440, 540, 640, 740, 840] for i, (bit, cx) in enumerate(zip(mosi_bits, mosi_centers)): lines.append(f' ') lines.append(f' ') lines.append(' ') # MISO 数据位标签 miso_centers = [145, 240, 340, 440, 540, 640, 740, 840] for i, (bit, cx) in enumerate(zip(miso_bits, miso_centers)): lines.append(f' ') lines.append(f' ') lines.append(' ') # 数据包标注 lines.append(' ') lines.append(' ') lines.append(' ') lines.append(' ') lines.append(' ') lines.append(' ') lines.append(' ') lines.append(' ') lines.append(' ') lines.append('') return "\n".join(lines) xml_content = make_mxfile() output_path = "SPI_Waveform_CPHA0_Corrected.drawio" with open(output_path, "w", encoding="utf-8") as f: f.write(xml_content) # 验证 MISO 起始点 import re with open(output_path, "r", encoding="utf-8") as f: content = f.read() match = re.search(r'id="miso".*?(.*?)', content, re.DOTALL) if match: pts = re.findall(r'', match.group(1)) print("MISO 点:") for x, y in pts[:4]: print(f" ({x}, {y})") src = re.search(r'id="miso".*?', content) if src: print(f"sourcePoint: ({src.group(1)}, {src.group(2)})") print("\n文件已保存:", output_path)