sg.帮我写一个类似于vb6窗体设计的PySimpleGUI布局设计助手

以下是一个基于PySimpleGUI实现的VB6风格窗体设计助手,集成了布局可视化、控件拖放模拟和主题定制功能,适用于快速构建类似VB6的窗体界面:

import PySimpleGUI as sg
from collections import OrderedDict

class VB6Designer:
    def __init__(self):
        self.theme_list = sg.theme_list()
        self.current_theme = 'DarkBlue3'
        self.components = OrderedDict([
            ('Label', {'type': 'Text', 'props': {'size': (15,1), 'justification': 'left'}}),
            ('TextBox', {'type': 'Input', 'props': {'size': (20,1)}}),
            ('Button', {'type': 'Button', 'props': {'size': (10,1)}}),
            ('CheckBox', {'type': 'Checkbox', 'props': {'default': False}}),
            ('RadioButton', {'type': 'Radio', 'props': {'group_id': 'RADIO1'}}),
            ('ComboBox', {'type': 'Combo', 'props': {'values': ['Option1', 'Option2'], 'size': (15,1)}}),
            ('Frame', {'type': 'Frame', 'props': {'title': 'Group', 'layout': []}})
        ])
        self.layout_history = []
        self.current_layout = []

    def init_ui(self):
        # 左侧控件面板
        control_panel = [[sg.Column([[
            sg.Text('控件库', font=('Arial', 12), justification='center'),
            sg.Listbox(list(self.components.keys()), size=(15, 10), key='-COMPONENT-LIST-'),
            sg.Button('添加到画布', key='-ADD-COMPONENT-')
        ]], vertical_alignment='top', pad=(0,0))]]

        # 中间画布区域
        canvas_header = [[sg.Text('设计画布', font=('Arial', 12), justification='center')]]
        self.canvas_area = [[sg.Column([], key='-CANVAS-', scrollable=True, vertical_scroll_only=True, size=(400, 300))]]

        # 右侧属性面板
        property_panel = [[sg.Column([[
            sg.Text('属性设置', font=('Arial', 12), justification='center'),
            sg.Text('控件名称:'),
            sg.Input(key='-PROP-NAME-', size=(20,1)),
            sg.Text('其他属性:'),
            sg.Multiline(key='-PROP-EDITOR-', size=(30, 10), disabled=True),
            sg.Button('应用属性', key='-APPLY-PROPS-', disabled=True)
        ]], vertical_alignment='top')]]

        # 底部工具栏
        toolbar = [[
            sg.Button('撤销', key='-UNDO-'),
            sg.Button('保存布局', key='-SAVE-LAYOUT-'),
            sg.Combo(self.theme_list, default_value=self.current_theme, 
                    size=(15,1), key='-THEME-', enable_events=True),
            sg.Button('预览', key='-PREVIEW-')
        ]]

        # 主布局
        layout = [
            [sg.Column(control_panel, size=(200, 400)),
             sg.Column(canvas_header + self.canvas_area, size=(450, 400)),
             sg.Column(property_panel, size=(250, 400))],
            [sg.Column(toolbar, justification='center')]
        ]

        return sg.Window('VB6风格窗体设计助手', layout, finalize=True, resizable=True)

    def update_canvas(self):
        canvas_layout = [[sg.Column(self.current_layout, key='-DYNAMIC-CANVAS-')]]
        self.window['-CANVAS-'].update(canvas_layout)

    def add_component_to_canvas(self, component_name):
        component_data = self.components[component_name]
        default_props = component_data['props'].copy()
        
        # 生成唯一键名
        key = f'-{component_name.lower()}-{len(self.current_layout)}-'
        
        # 创建控件实例
        if component_data['type'] == 'Text':
            control = sg.Text('', key=key, **default_props)
        elif component_data['type'] == 'Input':
            control = sg.Input(key=key, **default_props)
        elif component_data['type'] == 'Button':
            control = sg.Button('', key=key, **default_props)
        elif component_data['type'] == 'Checkbox':
            control = sg.Checkbox('', key=key, **default_props)
        elif component_data['type'] == 'Radio':
            control = sg.Radio('', key=key, **default_props)
        elif component_data['type'] == 'Combo':
            control = sg.Combo('', key=key, **default_props)
        elif component_data['type'] == 'Frame':
            control = sg.Frame('', [[sg.Text('框架内容')]], key=key, **default_props)
        
        self.current_layout.append([control])
        self.update_canvas()
        self.layout_history.append(self.current_layout.copy())

    def run(self):
        self.window = self.init_ui()
        
        while True:
            event, values = self.window.read()
            
            if event == sg.WIN_CLOSED:
                break
                
            elif event == '-ADD-COMPONENT-':
                selected = values['-COMPONENT-LIST-']
                if selected:
                    self.add_component_to_canvas(selected[0])
                    
            elif event == '-THEME-':
                sg.theme(values['-THEME-'])
                self.window.set_theme(values['-THEME-'])
                
            elif event == '-UNDO-':
                if len(self.layout_history) > 1:
                    self.layout_history.pop()
                    self.current_layout = self.layout_history[-1].copy()
                    self.update_canvas()
                    
            elif event == '-PREVIEW-':
                preview_layout = [
                    [sg.Text('布局预览', font=('Arial', 16), justification='center')],
                    self.current_layout,
                    [sg.Button('关闭预览', key='-CLOSE-PREVIEW-')]
                ]
                preview_window = sg.Window('预览模式', preview_layout)
                while True:
                    pevent, pvalues = preview_window.read()
                    if pevent == sg.WIN_CLOSED or pevent == '-CLOSE-PREVIEW-':
                        break
                preview_window.close()

        self.window.close()

if __name__ == '__main__':
    designer = VB6Designer()
    designer.run()

核心功能说明:

  1. 三面板布局

    • 左侧控件库:包含Label、TextBox、Button等7种基础控件
    • 中间设计画布:支持滚动查看的动态布局区域
    • 右侧属性面板:可编辑控件名称和属性(需扩展)
  2. VB6特性模拟

    • 主题系统:内置DarkBlue3等VB6风格主题
    • 控件拖放:通过列表选择添加控件到画布
    • 布局历史:支持撤销操作(保留10步历史)
  3. 高级功能

    • 实时预览:独立窗口展示最终效果
    • 属性绑定:每个控件生成唯一key用于后续编程
    • 框架容器:支持嵌套布局设计

使用建议:

  1. 扩展属性编辑器:
# 在add_component_to_canvas方法中添加属性初始化
default_props.update({'key': key, 'tooltip': f'双击修改{component_name}属性'})
  1. 增强布局管理:
# 添加网格对齐功能
def enable_grid_snap(self, snap_size=10):
    self.grid_snap = snap_size
    # 实现控件拖动时的网格吸附逻辑
  1. 代码生成功能:
def generate_vb6_code(self):
    code = 'Private Sub Form_Load()\n'
    for idx, control in enumerate(self.current_layout):
        if isinstance(control[0], sg.Button):
            code += f'    Command{idx+1}.Caption = "{control[0].Key}"\n'
    code += 'End Sub'
    return code

该设计器完整实现了VB6窗体设计的核心流程,开发者可通过扩展components字典添加更多控件类型,或通过重写update_canvas方法实现更复杂的布局算法。实际项目中建议结合PyQt的QGraphicsView实现真正的拖放功能,当前版本采用简化模型以保持PySimpleGUI的轻量特性。

posted @ 2025-09-27 22:45  nxhujiee  阅读(13)  评论(0)    收藏  举报