You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

无法更新pyqtgraph蜡烛图:MT5 Tick数据导入后仅显示初始蜡烛

问题分析与修复

1. 跨线程UI更新违规

Qt的UI组件只能在主线程中修改,当前代码在子线程get_data_from_update中直接调用item.set_data(),属于跨线程操作,会导致UI无法正常刷新,甚至程序崩溃。

修复方法:使用Qt的信号槽机制,将数据更新操作切换到主线程执行:

# 新增信号类
class DataSignal(QtCore.QObject):
    update_data = QtCore.pyqtSignal(np.ndarray)

# 初始化信号
signal = DataSignal()

# 主线程绑定槽函数
def update_chart(data):
    item.set_data(data)
signal.update_data.connect(update_chart)

# 修改get_data_from_update函数
def get_data_from_update():
    while True:
        i = q.get()
        # 发送信号到主线程
        signal.update_data.emit(i)
        q.task_done()

2. 时间戳格式错误

当前代码将时间转成字符串后再存为float,导致所有时间值被解析为相同的数值(示例中的7.26202211e+12),蜡烛图会完全重叠,看起来没有更新。

修复方法:直接存储时间戳的原始数值(毫秒转秒的浮点数):

# 修改tick类的update_tick方法中的赋值语句
self.tick_array[self.current_tick_number,0], self.tick_array[self.current_tick_number,1], self.tick_array[self.current_tick_number,2] = current_tick[5]/1000.0, self.tick_array[self.current_tick_number-1, 2], current_tick[1]

3. 蜡烛宽度计算逻辑缺陷

当数据长度小于2时,self.data[1][0] - self.data[0][0]会导致索引错误或除以0,而且初始的全0数据会干扰宽度计算。

修复方法:在generatePicture中添加数据长度判断,过滤无效数据并设置默认宽度:

def generatePicture(self):
    self.picture = QtGui.QPicture()
    path = QtGui.QPainterPath()
    p = QtGui.QPainter(self.picture)
    p.setPen(pg.mkPen('w'))
    
    # 过滤掉全0的无效数据
    valid_data = self.data[np.any(self.data != 0, axis=1)]
    if len(valid_data) < 2:
        w = 0.1  # 设置默认宽度
    else:
        w = (valid_data[1][0] - valid_data[0][0]) / 3.
    
    for (t, open, close) in valid_data:
        rect_height = close - open
        # 处理高度为负的情况(open > close)
        rect_y = min(open, close)
        rect_height = abs(rect_height)
        rect = QtCore.QRectF(t-w, rect_y, w*2, rect_height)
        path.addRect(rect)

        if open > close:
            p.setBrush(pg.mkBrush('r'))
        else:
            p.setBrush(pg.mkBrush('g'))
        p.drawRect(rect)

    p.end()
    self._boundingRect = path.boundingRect()

4. 初始数据干扰

tick_array的第一行是全0数据,会影响图表的初始显示和后续数据处理。

修复方法:调整current_tick_number的初始值为0,跳过第一行无效数据:

class tick:
    last_tick = 0
    current_tick = 0
    current_tick_number = 0  # 从0开始
    
    def __init__(self):
        self.tick_array = np.zeros((100000,3), dtype = float)
        self.pass_data = False

内容的提问来源于stack exchange,提问作者thatoneguy

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.25 03:54:11