当前位置: 首页 > news >正文

3分钟教你如何使用国产AI编程神器Trae的SOLO模式+Agent Skills+DeepSeek,零代码开发了一个超实用的爆款app(小白也能上手)

大家好,我是一个完全不懂桌面应用开发的小白。但我用3分钟时间,在Trae这个AI编程工具里,通过SOLO模式+Agent Skills + DeepSeek,搞出了一个桌面应用。这篇文章我就手把手教你,如何用AI编程工具,让AI帮你写代码、做软件,全程不需要你写一行代码!🔥

🧠 第一步:搞清楚我们要用什么


先说几个关键词,其实很简单:


简单说:你在Trae里打开SOLO模式,装上合适的Skills,用DeepSeek当大脑,告诉AI你想做什么,AI就帮你把代码写出来


🛠️ 第二步:3分钟极速教程(真的只需要3分钟!)


第1分钟:安装Trae并配置DeepSeek
去Trae官网下载安装包(完全免费)

安装后打开,点击右上角的AI侧边栏

进入AI管理 → 模型设置

添加自定义模型,选择Provider为Novita(或其他支持DeepSeek的服务商)

从模型下拉框选择 DeepSeek-V3-0324(最新版,代码能力超强)

粘贴你的API Key(没有的话去Novita注册免费试用,一般送额度)

搞定!现在Trae的大脑已经换成DeepSeek了。

第2分钟:创建SOLO模式+安装Skills
在Trae中新建一个项目文件夹(比如叫「my-app」)

点击左下角切换到 SOLO模式(重要!只有SOLO模式才能用Skills)

在对话中输入:

帮我创建一个Skill,用于开发Electron桌面应用。Skill需要包含:项目初始化、窗口配置、多页面路由、打包配置等规范。

第3分钟:让AI生成你的追剧神器!
在SOLO模式对话中,输入以下指令:

用Electron帮我开发一个桌面应用,名字叫「剧多多」。 功能要求: 1. 点击按钮,主窗口直接跳转到对应平台的官网 2. 窗口大小设置为1280x720 3. 应用图标放在桌面,双击打开直接进入 4. 需要使用webview加载网页,确保V#I#P视频可以正常播放(保留登录态) 请使用我刚刚创建的Electron开发Skill,生成完整的项目代码。


然后——坐等奇迹发生!🎉

AI会开始思考、规划、生成代码。你只需要看到提示时点击「接受全部」就行。

生成架构图

生成代码

import os import sys from pathlib import Path def _find_widevine_cdm(): chrome_app_roots = [] for env_name in ("PROGRAMFILES", "PROGRAMFILES(X86)", "LOCALAPPDATA"): base = os.environ.get(env_name) candidates = [] for root in chrome_app_roots: if not root.exists(): continue try: candidates.extend( list(root.glob("WidevineCdm/*/_platform_specific/win_x64/widevinecdm.dll")) ) candidates.extend( list(root.glob("*/WidevineCdm/*/_platform_specific/win_x64/widevinecdm.dll")) ) except OSError: continue if not candidates: return None def version_key(p: Path): version = p.parents[2].name parts = [] for x in version.split("."): try: parts.append(int(x)) except ValueError: parts.append(0) return tuple(parts) best = max(candidates, key=version_key) version_dir = best.parents[2] return str(best), version_dir.name def _configure_qtwebengine_widevine(): found = _find_widevine_cdm() if not found: return cdm_path, cdm_version = found flags = os.environ.get("QTWEBENGINE_CHROMIUM_FLAGS", "") if "--widevine-cdm-path" in flags: return extra = ( f' --widevine-cdm-path="{cdm_path}"' f" --widevine-cdm-version={cdm_version}" " --disable-features=AutomationControlled" " --disable-direct-composition" " --disable-accelerated-video-decode" ) os.environ["QTWEBENGINE_CHROMIUM_FLAGS"] = (flags + extra).strip() _configure_qtwebengine_widevine() from PyQt6.QtWidgets import (QApplication, QMainWindow, QWidget, QVBoxLayout, QHBoxLayout, QLineEdit, QPushButton, QComboBox, QLabel, QMessageBox, QProgressBar, QGridLayout, QFrame, QScrollArea, QStackedWidget) from PyQt6.QtWebEngineWidgets import QWebEngineView from PyQt6.QtWebEngineCore import QWebEngineSettings, QWebEnginePage, QWebEngineScript, QWebEngineUrlRequestInterceptor from PyQt6.QtCore import QUrl, Qt, QSize, QStandardPaths, QTimer from PyQt6.QtGui import QIcon, QAction, QFont, QCursor, QDesktopServices import config try: from PyQt6.QtMultimedia import QMediaPlayer, QAudioOutput from PyQt6.QtMultimediaWidgets import QVideoWidget MULTIMEDIA_AVAILABLE = True except Exception: QMediaPlayer = None QAudioOutput = None QVideoWidget = None MULTIMEDIA_AVAILABLE = False VIDEO_PLATFORMS = [] class WebEngineView(QWebEngineView): def createWindow(self, _type): return self class VideoUrlInterceptor(QWebEngineUrlRequestInterceptor): def __init__(self, handler): super().__init__() self.handler = handler def interceptRequest(self, info): url = info.requestUrl().toString() if not url: return lower = url.lower() if ".m3u8" in lower or ".mp4" in lower: self.handler(url) class v_i_pVideoPlayer(QMainWindow): def __init__(self): super().__init__() self.resize(1280, 900) self.setStyleSheet("background-color: #4DB6AC;") # 全局青色背景 self.h264_supported = None self.pending_parse = False self.last_video_url = "" self.player_available = MULTIMEDIA_AVAILABLE self.media_player = None self.audio_output = None self.video_widget = None # 初始化界面 self.init_ui() # 加载默认首页 self.load_url(config.DEFAULT_HOME_URL) def init_ui(self): # 主窗口部件 central_widget = QWidget() self.setCentralWidget(central_widget) # 主布局 main_layout = QVBoxLayout() main_layout.setContentsMargins(0, 0, 0, 0) main_layout.setSpacing(0) central_widget.setLayout(main_layout) # --- 1. 顶部 Header 区域 --- header_widget = QWidget() header_widget.setStyleSheet("background-color: #00695C; color: white;") header_widget.setFixedHeight(50) header_layout = QHBoxLayout() header_layout.setContentsMargins(20, 0, 20, 0) header_widget.setLayout(header_layout) title_label.setFont(QFont("Microsoft YaHei", 14, QFont.Weight.Bold)) title_label.setStyleSheet("color: white;") info_label.setFont(QFont("Microsoft YaHei", 10)) info_label.setStyleSheet("color: #E0F2F1;") header_layout.addWidget(title_label) header_layout.addStretch() header_layout.addWidget(info_label) main_layout.addWidget(header_widget) # --- 2. 控制/搜索区域 --- control_container = QWidget() control_container.setStyleSheet("background-color: #4DB6AC;") # 青色背景 control_layout = QHBoxLayout() control_layout.setContentsMargins(20, 15, 20, 15) control_layout.setSpacing(10) control_container.setLayout(control_layout) # 导航按钮组 (小一点) nav_layout = QHBoxLayout() nav_layout.setSpacing(5) btn_style_nav = """ QPushButton { background-color: rgba(255, 255, 255, 0.2); color: white; border: none; border-radius: 4px; font-weight: bold; } QPushButton:hover { background-color: rgba(255, 255, 255, 0.4); } """ self.btn_back = QPushButton("←") self.btn_back.setFixedSize(30, 30) self.btn_back.setStyleSheet(btn_style_nav) self.btn_back.clicked.connect(self.navigate_back) self.btn_forward = QPushButton("→") self.btn_forward.setFixedSize(30, 30) self.btn_forward.setStyleSheet(btn_style_nav) self.btn_forward.clicked.connect(self.navigate_forward) self.btn_refresh = QPushButton("↻") self.btn_refresh.setFixedSize(30, 30) self.btn_refresh.setStyleSheet(btn_style_nav) self.btn_refresh.clicked.connect(self.reload_page) self.btn_home = QPushButton("首页") self.btn_home.setFixedSize(50, 30) self.btn_home.setStyleSheet(btn_style_nav) self.btn_home.clicked.connect(lambda: self.load_url(config.DEFAULT_HOME_URL)) nav_layout.addWidget(self.btn_back) nav_layout.addWidget(self.btn_forward) nav_layout.addWidget(self.btn_refresh) nav_layout.addWidget(self.btn_home) label_addr.setAlignment(Qt.AlignmentFlag.AlignCenter) label_addr.setFixedSize(120, 40) label_addr.setStyleSheet(""" background-color: #2ECC71; color: white; border-radius: 4px; font-size: 12px; """) # 地址输入框 self.url_input = QLineEdit() self.url_input.setPlaceholderText("在此输入或粘贴视频网址...") self.url_input.setFixedHeight(40) self.url_input.setStyleSheet(""" QLineEdit { border: 2px solid #2ECC71; border-radius: 4px; padding: 0 10px; font-size: 14px; background-color: white; } """) self.url_input.returnPressed.connect(self.load_from_input) # 线路选择 (稍微美化) self.combo_interface = QComboBox() self.combo_interface.setFixedHeight(40) self.combo_interface.setMinimumWidth(120) self.combo_interface.setStyleSheet(""" QComboBox { border: 2px solid #2ECC71; border-radius: 4px; padding: 0 10px; background-color: white; } QComboBox::drop-down { border: none; } """) for item in config.v_i_p_INTERFACES: self.combo_interface.addItem(item["name"], item["url"]) # 立即播放按钮 self.btn_play = QPushButton("立即播放") self.btn_play.setFixedSize(100, 40) self.btn_play.setCursor(QCursor(Qt.CursorShape.PointingHandCursor)) self.btn_play.setStyleSheet(""" QPushButton { background-color: #2ECC71; color: white; font-weight: bold; font-size: 14px; border-radius: 4px; border: none; } QPushButton:hover { background-color: #27ae60; } """) self.btn_play.clicked.connect(self.parse_video) # 用浏览器打开按钮 self.btn_open_browser = QPushButton("浏览器播放") self.btn_open_browser.setFixedSize(100, 40) self.btn_open_browser.setCursor(QCursor(Qt.CursorShape.PointingHandCursor)) self.btn_open_browser.setStyleSheet(""" QPushButton { background-color: #3498DB; color: white; font-weight: bold; font-size: 14px; border-radius: 4px; border: none; } QPushButton:hover { background-color: #2980B9; } """) self.btn_open_browser.clicked.connect(self.open_in_system_browser) # 组装控制栏 control_layout.addLayout(nav_layout) control_layout.addSpacing(15) control_layout.addWidget(label_addr) control_layout.addWidget(self.url_input, 1) # 拉伸 control_layout.addWidget(self.combo_interface) control_layout.addWidget(self.btn_play) control_layout.addWidget(self.btn_open_browser) main_layout.addWidget(control_container) # --- 3. 提示文字 --- tip_widget = QWidget() tip_widget.setStyleSheet("background-color: #4DB6AC;") tip_layout = QVBoxLayout() tip_layout.setContentsMargins(0, 5, 0, 10) tip_widget.setLayout(tip_layout) tip_label.setAlignment(Qt.AlignmentFlag.AlignCenter) tip_label.setStyleSheet("color: white; font-size: 12px;") tip_layout.addWidget(tip_label) main_layout.addWidget(tip_widget) web_container = QWidget() web_container.setStyleSheet("background-color: #4DB6AC; padding: 0px 20px;") web_layout = QVBoxLayout() web_layout.setContentsMargins(0, 0, 0, 0) web_container.setLayout(web_layout) self.browser = WebEngineView() self.browser.setStyleSheet("background-color: black;") if self.player_available: self.media_player = QMediaPlayer() self.audio_output = QAudioOutput() self.media_player.setAudioOutput(self.audio_output) self.video_widget = QVideoWidget() self.media_player.setVideoOutput(self.video_widget) try: data_path = QStandardPaths.writableLocation(QStandardPaths.StandardLocation.AppLocalDataLocation) profile_path = os.path.join(data_path, "v_i_p_video_player_profile") cache_path = os.path.join(profile_path, "cache") if not os.path.exists(profile_path): os.makedirs(profile_path, exist_ok=True) if not os.path.exists(cache_path): os.makedirs(cache_path, exist_ok=True) profile = self.browser.page().profile() profile.setPersistentStoragePath(profile_path) profile.setCachePath(cache_path) self.video_interceptor = VideoUrlInterceptor(self.on_video_url_detected) profile.setUrlRequestInterceptor(self.video_interceptor) print(f"Profile storage path set to: {profile_path}") except Exception as e: print(f"Failed to set profile path: {e}") script.setInjectionPoint(QWebEngineScript.InjectionPoint.DocumentCreation) script.setWorldId(QWebEngineScript.ScriptWorldId.MainWorld) script.setRunsOnSubFrames(True) self.browser.page().scripts().insert(script) settings = self.browser.settings() settings.setAttribute(QWebEngineSettings.WebAttribute.PluginsEnabled, True) settings.setAttribute(QWebEngineSettings.WebAttribute.JavascriptEnabled, True) settings.setAttribute(QWebEngineSettings.WebAttribute.LocalStorageEnabled, True) settings.setAttribute(QWebEngineSettings.WebAttribute.JavascriptCanOpenWindows, True) settings.setAttribute(QWebEngineSettings.WebAttribute.PlaybackRequiresUserGesture, False) settings.setAttribute(QWebEngineSettings.WebAttribute.FullScreenSupportEnabled, True) settings.setAttribute(QWebEngineSettings.WebAttribute.AllowRunningInsecureContent, True) # 启用更多高级特性以提高兼容性 settings.setAttribute(QWebEngineSettings.WebAttribute.DnsPrefetchEnabled, True) settings.setAttribute(QWebEngineSettings.WebAttribute.Accelerated2dCanvasEnabled, True) settings.setAttribute(QWebEngineSettings.WebAttribute.WebGLEnabled, True) settings.setAttribute(QWebEngineSettings.WebAttribute.XSSAuditingEnabled, False) settings.setAttribute(QWebEngineSettings.WebAttribute.LocalContentCanAccessRemoteUrls, True) settings.setAttribute(QWebEngineSettings.WebAttribute.HyperlinkAuditingEnabled, False) self.browser.urlChanged.connect(self.update_url_bar) self.browser.loadProgress.connect(self.update_progress) self.browser.titleChanged.connect(self.update_title) self.browser.loadFinished.connect(self.on_load_finished) if self.player_available and self.video_widget is not None: self.view_stack = QStackedWidget() self.view_stack.addWidget(self.browser) self.view_stack.addWidget(self.video_widget) web_layout.addWidget(self.view_stack) else: self.view_stack = None web_layout.addWidget(self.browser) main_layout.addWidget(web_container, 1) # 浏览器占据主要空间 self.progress_bar = QProgressBar() self.progress_bar.setFixedHeight(2) self.progress_bar.setTextVisible(False) self.progress_bar.setStyleSheet("QProgressBar { border: 0px; background-color: transparent; } QProgressBar::chunk { background-color: #2ECC71; }") main_layout.addWidget(self.progress_bar) # --- 5. 底部平台快捷栏 --- platform_widget = QWidget() platform_widget.setStyleSheet("background-color: #4DB6AC;") platform_layout = QVBoxLayout() platform_layout.setContentsMargins(20, 10, 20, 20) platform_widget.setLayout(platform_layout) bottom_tip.setAlignment(Qt.AlignmentFlag.AlignCenter) bottom_tip.setStyleSheet("color: white; font-size: 13px; margin-bottom: 10px;") platform_layout.addWidget(bottom_tip) # 图标布局 (单行显示) platforms_layout = QHBoxLayout() platforms_layout.setSpacing(15) # 生成按钮 for platform in VIDEO_PLATFORMS: btn = QPushButton(platform["name"]) btn.setFixedHeight(50) btn.setCursor(QCursor(Qt.CursorShape.PointingHandCursor)) # 使用动态颜色样式 btn.setStyleSheet(f""" QPushButton {{ background-color: white; color: {platform['color']}; font-size: 16px; font-weight: bold; border-radius: 6px; border: 1px solid #ddd; }} QPushButton:hover {{ background-color: #f9f9f9; border: 2px solid {platform['color']}; }} """) # 使用闭包绑定URL btn.clicked.connect(lambda checked, url=platform["url"]: self.load_url(url)) platforms_layout.addWidget(btn) platform_layout.addLayout(platforms_layout) main_layout.addWidget(platform_widget) # --- 逻辑功能 --- def load_url(self, url_str): """加载URL""" if not url_str.startswith('http'): url_str = 'https://' + url_str self.browser.load(QUrl(url_str)) def load_from_input(self): """从地址栏加载""" url = self.url_input.text().strip() if url: self.load_url(url) def parse_video(self): self.pending_parse = True self.last_video_url = "" if self.view_stack is not None: self.view_stack.setCurrentWidget(self.browser) self.browser.load(QUrl(final_url)) def open_in_system_browser(self): """在系统浏览器中打开当前页面""" QDesktopServices.openUrl(self.browser.url()) def open_in_system_browser_url(self, url): QDesktopServices.openUrl(QUrl(url)) def on_video_url_detected(self, url): if not self.pending_parse: return if url == self.last_video_url: return self.last_video_url = url if self.player_available and self.media_player is not None: self.play_video_url(url) self.pending_parse = False def play_video_url(self, url): if self.view_stack is not None and self.video_widget is not None: self.view_stack.setCurrentWidget(self.video_widget) self.media_player.setSource(QUrl(url)) self.media_player.play() def navigate_back(self): self.browser.back() def navigate_forward(self): self.browser.forward() def reload_page(self): self.browser.reload() def update_url_bar(self, qurl): """更新地址栏显示""" self.url_input.setText(qurl.toString()) self.url_input.setCursorPosition(0) def update_progress(self, progress): """更新进度条""" self.progress_bar.setValue(progress) if progress == 100: self.progress_bar.hide() else: self.progress_bar.show() def update_title(self, title): """更新窗口标题""" if __name__ == "__main__": app = QApplication(sys.argv) window = v_i_pVideoPlayer() window.show() sys.exit(app.exec())

3、项目开发说明文档


✨ 发生了什么?AI到底做了什么?
你可能会好奇:这几句话,AI真的能做出一个完整的软件吗?

答案是:能!而且做得很好!

DeepSeek V3.1在代码生成和推理方面的能力非常强,AIME 2025基准测试得分88.4%,接近GPT-5的水平。加上Trae的Agent模式,AI可以:

1、理解你的需求:知道你要做一个聚合视频的桌面应用

2、调用Skill规范:按照Electron开发的最佳实践来组织代码

3、生成完整项目:包括主进程、渲染进程、package.json、打包配置等

4、处理技术细节:比如webview配置、跨域问题、登录态保持

整个过程就像你请了一个24小时待命的程序员,你说需求,他写代码,你只管验收!

🎯 最终成果展示
代码生成后,在项目目录下运行:

bash npm start npm start

你就会看到——「剧#多#多」桌面应用打开了!

如果你想打包成exe/dmg发给朋友,只需要告诉AI:

AI会自动修改package.json,添加打包配置。运行 npm run dist,安装包就出来了!

💡 小白常见问题
Q1:我真的一点代码都不会,能搞定吗?

A:完全可以!我本人就是例子。全程只需要打字,AI写代码,你负责确认就行。

Q2:DeepSeek要钱吗?
A:DeepSeek本身是开源免费的
,但如果通过API调用,服务商可能会收少量费用。不过一般注册都送额度,做个这种小应用绰绰有余。

Q3:Skills到底是什么?必须自己创建吗?
A:Skill就是AI的「操作手册」
,告诉AI“做这类事情要按照这个流程”。你可以自己创建,也可以用别人分享的。网上有很多现成的Skill可以直接导入。

Q4:生成的软件安全吗?会不会有病毒?
A:代码都在你的电脑上生成
,你可以查看每一行代码。 如果不放心,可以让AI解释每段代码的作用。

🚀 进阶玩法:还能做什么?
学会了这个套路,你可以让AI帮你做:


只要你敢想,AI就能做!

📢 最后说几句
以前想做个软件,得学编程、学框架、踩无数坑,没几个月出不来。

现在有了Trae + DeepSeek + Agent Skills,普通人也能3分钟拥有自己的软件

我的「剧多多」已经打包好,想体验的朋友可以私信我,也可以按上面的教程自己做一个——自己做的用起来更香!

如果你按教程做出来了,欢迎在评论区晒图!有任何问题随时问,我看到就回。👇

#AI编程 #DeepSeek #Trae #零代码开发 #追剧神器 #个人项目 #效率工具

http://www.jsqmd.com/news/491787/

相关文章:

  • 免费/便宜/高性价比云服务器推荐及活动!实时更新(雨云/Vminss/Namesilo/阿里云)优惠码合集
  • 【触想智能】工业触摸屏显示器的主要特点以及其应用领域分析
  • 2026苏州B2B企业出海营销服务商哪家强?五家效果不错的苏州海外推广获客服务商盘点 - 品牌2025
  • AI智能智慧工厂厂区解决方案:“感知-平台-应用”三层架构,通过人脸识别、情绪分析与微服务架构(1+6+7体系)
  • 熬过无数失眠夜才懂,抛开常见灵芝孢子粉,小石丸真元丹凭何成新宠? - 资讯焦点
  • AI心智架构服务商怎么选?权威推荐与资质甄别指南 - 资讯焦点
  • 2026海藻钙优缺点解析 高口碑品牌推荐 - 品牌排行榜
  • 2026上海海外推广服务商推荐:海外独立站引流与海外社交媒体获客平台盘点(附带联系方式) - 品牌2025
  • 【AI智能体】——OpenClaw(龙虾)深度研究分享(六) 最坑痛点:Rate limit exceeded + Missing state双错绝杀指南
  • OpenCV中的VideoCapture后端参数详解
  • EEPROM AT93C66B读写测试
  • 2026西南引领全国弱电智能化浪潮:五家标杆企业权威解析 - 深度智识库
  • 欧意注册下载地址okxz.run复制进去-2026年最新版V5.6.12.5.21安卓/苹果版
  • 私域自动回复机器人:构建 7×24 小时在线的智能客户服务体系
  • 我的世界 (MC) 服务器推荐:雨云开服搭建教程 2026 新用户优惠码
  • 彻底卸载OpenClaw:完整指南
  • 入行AI的攻略
  • 2026国产 EDA 工具推荐:多行业适配的自主可控智能仿真解决方案 - 品牌2026
  • 抖音豆包九宫格验证码识别
  • 当钢铁有了灵魂:寻找那些最懂“交互叙事”的机械装置造梦者
  • 2026年高净值男性私密健康报告!肾虚阳痿吃什么好?精英人群补肾产品推荐TOP10,稳坐首位 - 资讯焦点
  • 【MySQL-索引调优】02:单列索引
  • 企微机器人开发:实现私域流量的自动化管理与智能交互
  • 软件测试工程师必须掌握的数据库基础知识:从入门到实战
  • Redis持久化策略
  • 基于Systick系统滴答定时器的延时时间计算
  • 2025房建首选品牌揭晓!空气能行业里谁上榜了? - 博客湾
  • SI2318 场效应管参数详解
  • 选对自动获客软件,少走弯路!AI 招财兔实测体验
  • 2026年NMN十大品牌权威榜单|抗衰健康热门品牌深度测评与选购指南 - 速递信息