From cf3d4da8e82065d5c4d1c5c4f3098ae85c5693a9 Mon Sep 17 00:00:00 2001 From: wingsummer <1326224942@qq.com> Date: Sun, 27 Apr 2025 11:31:15 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E6=9B=B4=E5=A5=BD=E7=9A=84=E4=BB=A3?= =?UTF-8?q?=E7=A0=81=E5=A1=AB=E5=85=85=E5=92=8C=E4=B8=80=E4=BA=9B=20Bug=20?= =?UTF-8?q?=E4=BF=AE=E5=A4=8D=EF=BC=9B?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- 3rdparty/QConsoleWidget/QConsoleWidget.cpp | 16 +- 3rdparty/QConsoleWidget/QConsoleWidget.h | 3 + CMakeLists.txt | 2 - lang/zh_CN/winghex_zh_CN.ts | 1323 ++++++++++---------- lang/zh_TW/winghex_zh_TW.ts | 1323 ++++++++++---------- src/class/appmanager.cpp | 7 +- src/class/appmanager.h | 6 + src/class/ascompletion.cpp | 245 ++-- src/class/ascompletion.h | 14 +- src/class/asconsolecompletion.cpp | 41 +- src/class/asconsolecompletion.h | 3 + src/class/ascontextmgr.cpp | 41 - src/class/ascontextmgr.h | 30 - src/class/asdebugger.cpp | 3 + src/class/ctypeparser.cpp | 27 +- src/class/qascodeparser.cpp | 2 +- src/class/scriptmachine.cpp | 257 ++-- src/class/scriptmachine.h | 15 +- src/class/scriptmanager.cpp | 20 +- src/control/editorview.cpp | 2 +- src/control/scriptingconsole.cpp | 38 +- src/control/scriptingconsole.h | 1 + src/define.h | 1 + src/dialog/mainwindow.cpp | 48 +- 24 files changed, 1811 insertions(+), 1657 deletions(-) delete mode 100644 src/class/ascontextmgr.cpp delete mode 100644 src/class/ascontextmgr.h diff --git a/3rdparty/QConsoleWidget/QConsoleWidget.cpp b/3rdparty/QConsoleWidget/QConsoleWidget.cpp index 695d12e..ee0363f 100644 --- a/3rdparty/QConsoleWidget/QConsoleWidget.cpp +++ b/3rdparty/QConsoleWidget/QConsoleWidget.cpp @@ -109,6 +109,15 @@ QString QConsoleWidget::getCommandLine() { return code; } +void QConsoleWidget::paste() { + QTextCursor textCursor = this->textCursor(); + const QMimeData *const clipboard = QApplication::clipboard()->mimeData(); + const QString text = clipboard->text(); + if (!text.isNull()) { + textCursor.insertText(text, channelCharFormat(StandardInput)); + } +} + void QConsoleWidget::handleReturnKey() { QString code = getCommandLine(); @@ -189,12 +198,7 @@ void QConsoleWidget::keyPressEvent(QKeyEvent *e) { // Allow paste only if the selection is in the interactive area ... if (e->key() == Qt::Key_V && e->modifiers() == Qt::ControlModifier) { if (selectionInEditZone || isCursorInEditZone()) { - const QMimeData *const clipboard = - QApplication::clipboard()->mimeData(); - const QString text = clipboard->text(); - if (!text.isNull()) { - textCursor.insertText(text, channelCharFormat(StandardInput)); - } + paste(); } e->accept(); diff --git a/3rdparty/QConsoleWidget/QConsoleWidget.h b/3rdparty/QConsoleWidget/QConsoleWidget.h index 82af016..7463284 100644 --- a/3rdparty/QConsoleWidget/QConsoleWidget.h +++ b/3rdparty/QConsoleWidget/QConsoleWidget.h @@ -77,6 +77,8 @@ public: // get the current command line QString getCommandLine(); + virtual void paste(); + public slots: // write to StandardOutput @@ -94,6 +96,7 @@ signals: protected: bool canPaste() const; bool canCut() const; + virtual void handleReturnKey(); virtual void handleTabKey(); // reimp QPlainTextEdit functions diff --git a/CMakeLists.txt b/CMakeLists.txt index 08988df..cbad0e5 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -253,8 +253,6 @@ set(CLASS_SRC src/class/ascompletion.h src/class/asbuilder.h src/class/asbuilder.cpp - src/class/ascontextmgr.h - src/class/ascontextmgr.cpp src/class/clangformatmanager.h src/class/clangformatmanager.cpp src/class/aspreprocesser.h diff --git a/lang/zh_CN/winghex_zh_CN.ts b/lang/zh_CN/winghex_zh_CN.ts index c7cf1c3..c76deda 100644 --- a/lang/zh_CN/winghex_zh_CN.ts +++ b/lang/zh_CN/winghex_zh_CN.ts @@ -74,25 +74,25 @@ AppManager - + GenericCallNotFullySupported 该软件脚本系统不完全支持通用调用,故软件将会退出。 - + SetupClang 启动 Clang 服务 - + OpeningFiles 打开文件 - - - - + + + + AlreadyOpened 文件已被打开 @@ -865,1172 +865,1183 @@ MainWindow - + File 文件 - - + + View 视图 - + About 关于 - + WingHexExplorer 羽云十六进制编辑器 - + loc: 坐标: - + sel: 选长: - + Edit 编辑 - + Script 脚本 - - - + + + Plugin 插件 - + Setting 设置 - - + + Log 日志 - + ExportFindResult 导出搜索结果 - + ClearFindResult 清空记录 - - + + FindResult 搜索结果 - - - - + + + + Copy 复制 - - - - - + + + + + CopyToClipBoard 数据已拷贝到粘贴板 - + LittleEndian 小端 - + BigEndian 大端 - + Number 数值 - - + + CheckSum 校验和 - - + + DeleteBookMark 删除书签 - - + + ClearBookMark 清空书签 - - - - + + + + BookMark 书签 - - + + DecodeText 解码字符串 - + ScriptConsole 脚本控制台 - - + + Basic 基础 - + New 新建 - + OpenF 打开文件 - + OpenWorkSpace 打开工作区 - + RecentFiles 最近打开 - - - + + + Reload 重新加载 - - + + Save 保存 - + SaveAs 另存为 - + ConvertWS 转为工作区 - + Export 导出 - + SaveSel 保存选区字节 - - - - + + + + General 基本 - + Undo 撤销 - + Redo 恢复 - + Cut 剪切 - + Paste 粘贴 - + Delete 删除 - + Clone 克隆 - + Lookup 查询 - + Find 查找 - + Goto 跳转 - - + + Encoding 编码 - + FileInfo 文件信息 - - + + Hex 十六进制 - + CutHex 剪切(十六进制) - + CopyHex 复制(十六进制) - + PasteHex 粘贴(十六进制) - - + + Fill 填充 - + FillZero 填充零 - - - - - + + + + + MetaData 标注 - + DeleteMetadata 删除标注 - + ClearMetadata 清空标注 - + MetaDataEdit 编辑标注 - + DeleteMetaData 删除标注 - + ClearMetaData 清空标注 - + Display 显示 - + ViewText 文本预览 - + Scale 缩放 - + SetupRecent 启动最近文件服务 - + SetupUI 初始化界面 - + SetupDocking 启动 Dock 服务 - + LaunchingLog 启动日志系统 - + SetupPluginSystem 启动插件系统 - + LoadingPlg: 加载插件中: - + SetupConsole 启动脚本控制台 - + SetupScriptManager 启动脚本管理器 - + SetupScriptService 启动脚本服务 - + SetupScriptEditor 构建脚本编辑器 - + SetupSetDialog 构建设置窗体 - + SetupPlgWidgets 启动插件组件 - + SetupDockingLayout 恢复 Dock 布局 - + SetupWaiting 启动即将完成 - + SetupFinished 启动完毕 - + NoExtension 无扩展 - - + + ExportResult 导出结果 - + NothingToSave 没有保存的数据 - + OpenExt 打开 - 拓展 - + ResetScale 重置缩放 - + ShowMetafg 标注前景色 - + ShowMetabg 标注背景色 - + ShowMetaComment 批注 - + MetaShowAll 显示所有标注 - + MetaHideAll 隐藏所有标注 - + FileStatus 文件状态 - - + + InfoSave 是否保存 - - + + ReadOnly 可读写 - - + + SetLocked 启用/禁用锁定编辑 - + ErrUnLock 锁定编辑失败 - - + + SetOver 启用/禁用改变大小 - + InputRequest - + 输入请求 - + + ScriptEngineInitFailed + 脚本引擎启动失败,将自动禁用该功能。 + + + UnsignedHex 无符号 Hex - + BgScriptOutput 后台脚本输出 - + ErrUnOver 锁定文件大小失败 - + Window 窗体 - + Editor 编辑器 - + Tools 工具 - + HexEditorLayout 编辑器布局 - + SetBaseAddr 设置基址 - + addressBase 基址 - + inputAddressBase 请输入基址 - + WarnBigBaseAddress 基址过大,你得到的地址将会不正确! - + ErrBaseAddress 非法基址输入 - + SetColInfo 显示/隐藏地址栏 - + SetHeaderInfo 显示/隐藏表头 - + SetAsciiString 显示/隐藏解码字符串 - + Layout 布局 - + Fullscreen 全屏 - + Default 默认 - - - + + + LayoutRestoring... 恢复布局中... - + RestoreLayout 恢复布局 - - + + SaveLayout 保存布局 - + ExportLog 导出日志 - + ClearLog 清空日志 - + InsepctQt 监视 Qt - + ScriptEditor 脚本编辑器 - + Scripts 脚本仓库 - + PluginFunctions 插件功能 - + ScriptSetting 脚本设置 - + PluginSettings 插件设置 - + Info 信息 - + Software 软件 - + Sponsor 赞助 - + CheckUpdate 检查更新 - + Wiki 网页 Wiki - + AboutQT 关于 QT - + SetPageIDEmptyTryUseName 设置页 ID 为空,尝试使用名称作为 ID - + SetPageDupNameIgnored 设置页重复的 ID 名称,已忽略加载 - + Plugin %1 contains a duplicate ID (%2) that is already registered by plugin %3 插件 %1 包含重复 ID (%2),该 ID 已被插件 %3 注册 - - + + ChooseFile 选择文件 - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + Error 错误 - - + + FileNotExist 文件不存在! - - - - - + + + + + FilePermission 因文件权限无法继续! - + ProjectFile (*.wingpro) 项目文件 (*.wingpro) - + ReloadSuccessfully 文件重新加载成功! - + ReloadUnSuccessfully 文件重新加载失败! - - - - + + + + ChooseSaveFile 请选择保存文件路径: - + NoMoreClone 克隆已到上限,无法继续操作! - + FindFininishBusy 查找任务繁忙,请勿重复查找! - + MayTooMuchFindResult 搜索数量已到达上限,结果可能不全,建议请按区段搜索。 - + SaveLayoutSuccess 保存布局成功 - + SaveLayoutError 保存布局失败 - + HasClonedView 该编辑页已被克隆编辑,如果关闭,相关联的页也会被关闭,你确认继续吗? - - - ReloadNeededYesOrNo - + + FileCloseBigFile + 大文件读取模式下目标文件被关闭,该标签将会被关闭。 - + + + ReloadNeededYesOrNo + 目标文件被修改,是否重新加载? + + + SaveWorkSpace 保存工作区 - + WingHexWorkSpace (*.wingpro) 羽云十六进制工作区 (*.wingpro) - + ConfirmSave 正在关闭未保存的文件或工作区,你确定保存吗? - + [Info] 【信息】 - + [Warn] 【警告】 - + [Error] 【错误】 - + ConfirmAPPSave 你尝试关闭程序,但仍存在未保存的文件或工作区,你确定保存这些更改吗? - - - + + + SaveSuccessfully 保存成功! - - + + SaveWSError 保存工作区错误! - - + + Warn 警告 - + Opening... 打开文件中... - + WorkSpaceOpening... 打开工作区中... - + Reloading... 重载文件中... - + Saving... 保存中... - + SaveNewFirst 请首先保存新建的文件 - + AlreadyWorkSpace 已经是工作区,无需转化 - + ConvWorkSpaceFailed 转化为工作区失败 - + ConvWorkSpaceSuccess 转化为工作区成功 - + SavingAs... 另存为中... - + SaveUnSuccessfully 保存失败! - + Exporting... 导出中... - + ChooseExportFile 请选择导出文件路径: - + ExportSuccessfully 导出成功! - + ExportUnSuccessfully 导出失败! - + SavingSel... 保存选中字节中... - + SaveSelSuccess 保存选区字节成功! - + SaveSelError 保存选区字节失败,因文件不具有可写权限! - - + + CutToClipBoard 数据已剪切到粘贴板! - - + + UnCutToClipBoard 由于保持大小限制,数据剪切到粘贴板失败! - - + + UnCopyToClipBoard 由于保持大小限制,数据剪切到复制板失败! - - + + Finding... 查找中... - + DeleteSuccess 删除成功 - + DeleteFailed 删除失败 - + FindFininish 查找结果完毕! - + PleaseInputFill 请输入填充字节值 - + FillInputTruncWarn 填充输入数值过大,将会被截断填充 - + FillInputError 填充字节输入错误 - - + + InputComment 请输入批注: - - + + BookmarkDelSuccess 删除书签成功 - + BookmarkDelNoItem 无书签可删除 - + BookmarkClearSuccess 书签清空完毕 - - - + + + NoSelection 没有选区,无法继续的操作! - + NoMetaData 无可编辑标记 - + PleaseClearSel 请清空选择 - + MetaDelSuccess 元数据删除成功 - + MetaDelNoItem 无元数据可删除 - + MetaClearSuccess 元数据清空完毕 - + FindResultExporting... 查找结果导出中... - + EmptyFindResult 没有可导出的搜索结果! - + SaveFindResult 导出搜索结果成功! - + SaveFindResultError 导出结果失败! - + TooManyBytesDecode 超出解码字节限制…… - + NoTextFileMayInvalid 该文件不是文本文件,以文本方式预览并不是一个好的方式,你确认继续吗? - + LayoutSaving... 布局保存中... - - + + PleaseInput 请输入 - + LogExporting... 日志导出中... - + ExportLogError 导出日志失败! - + ExportLogSuccess 导出日志成功,路径: - + ClearLogSuccess 清空日志成功! - + BadNetwork 无法与远程服务器的更新检查建立连接,请检查网络。 - + NewestVersion 当前软件为最新版本 - - + + OlderVersion 你使用的软件为老版本,建议到 Github 和 Gitee 的仓库发行版下载更新。 - + CheckingUpdate 检查更新中…… - + Too much opened files 打开的文件过多,无法继续操作! - + FilePermissionSure2Quit 因文件权限无法保存,你确认要退出吗? - + UnknownErrorSure2Quit 因未知错误无法保存,你确认要退出吗? - + WorkSpaceUnSavedSure2Quit 工作区文件无法保存,你确认要退出吗? - + CopyLimit 拷贝字节超出限制 - + ErrOpenFileBelow 打开文件出现错误(由于权限不足),如下为打开错误的文件: @@ -2467,12 +2478,12 @@ 该设置需要程序重启后生效 - + wingsummer 寂静的羽夏 - + WingCloudStudio 羽云工作室 @@ -2750,37 +2761,35 @@ ScriptMachine - + AngelScript callstack: AngelScript 调用堆栈: - + - Exception '%1' in '%2' — 在 ‘%2’ 中发生异常 ‘%1’ - + ExecNotAllowedInRoot 在管理员权限执行第三方命令为非法操作 - - - + + Script failed to build 脚本编译失败 - - + Cannot find 'int main()' or 'void main()' 无法找到程序入口点: "int main()" 或者 "void main()" - + Debugging, waiting for commands. 调试中,等待调试命令。 @@ -2790,1535 +2799,1545 @@ 初始化全局变量失败 - - + + The script failed with an exception 异常被抛出,脚本执行失败 - - + + The script was aborted 脚本被终止 - - + + The script terminated unexpectedly 脚本异常退出 - + The script exited with 脚本退出返回值: - + '%1' is already declared "%1" 已被声明 - + Abstract class '%1' cannot be instantiated 无法实例化抽象类 "%1" - + Accessing private property '%1' of parent class 非法访问父类的私有属性 "%1" - + Attribute '%1' informed multiple times 属性 "%1" 已被多次通知 - + Can't form arrays of subtype '%1' 无法创建子类型 "%1" 的数组 - + Can't inherit from class '%1' marked as final 无法从标记为 final 的类 "%1" 继承 - + Cannot access non-static member '%1' like this 无法和像使用 this 一样访问非静态成员 "%1" - + Can't construct handle '%1'. Use ref cast instead 无法构造句柄 "%1" 。请改用引用强制转换 - + Can't implicitly convert from '%1' to '%2'. 无法从 "%1' 隐式转换为 "%2"。 - + Compiling %1 正在编译 %1 - + Compiling auto generated %1 编译自动生成的 %1 - + Implemented property accessor '%1' does not expect index argument 已实现的属性访问器 "%1" 不需要索引参数 - + Implemented property accessor '%1' expects index argument 已实现的属性访问器 "%1" 需要索引参数 - + Data type can't be '%1' 数据类型不能为 "%1" - + All subsequent parameters after the first default value must have default values in function '%1' 在函数 "%1" 中,第一个默认值之后的所有后续参数都必须具有默认值 - + The method in the derived class must have the same return type as in the base class: '%1' 派生类中的方法必须具有与基类相同的返回类型:"%1" - + The name of the destructor '%1::~%2' must be the same as the class 析构函数 "%1::~%2" 的名称必须与类相同 - + Expected '%1' 应为 "%1" - + Expected '%1' or '%2' 应为 ”%1“ 或 ”%2“ - + Expression must be of boolean type, instead found '%1' 表达式必须是布尔类型,但实际使用的是 "%1" - + Expression '%1' is a data type 表达式 "%1" 是一种数据类型 - + External shared entity '%1' not found 未找到外部共享实体 "%1" - + External shared entity '%1' cannot redefine the original entity 外部共享实体 "%1" 无法重新定义原始实体 - + Failed while compiling default arg for parameter %1 in function '%2' 为函数 "%2" 中的参数 %1 编译默认参数时失败 - + Function '%1' not found 未找到函数 "%1" - + The property '%1' has mismatching types for the get and set accessors 属性 "%1" 的 get 和 set 访问器类型不匹配 - + Variable '%1' hides another variable of same name in outer scope 变量 "%1" 隐藏了外部作用域中另一个同名变量 - + Identifier '%1' is not a data type 标识符 "%1" 不是数据类型 - + Identifier '%1' is not a data type in global namespace 标识符 "%1" 不是全局命名空间中的数据类型 - + Identifier '%1' is not a data type in namespace '%2' or parent 标识符 "%1" 不是命名空间 "%2" 或其父级中的数据类型 - + Illegal operation on '%1' 对 "%1" 的非法操作 - + Illegal variable name '%1'. 非法变量名 "%1"。 - + Illegal access to inherited private property '%1' 非法访问继承的私有属性 "%1" - + Initialization lists cannot be used with '%1' 初始化列表不能与 "%1" 一起使用 - + Attempting to instantiate invalid template type '%1<%2>' 尝试实例化无效的模板类型 "%1<%2>" - + Instead found '%1' 而是找到了 "%1" - + Instead found identifier '%1' 而是找到标识符 "%1" - + Instead found reserved keyword '%1' 而是找到了保留关键字 "%1" - + Interface '%1' cannot be instantiated 无法实例化接口 "%1" - + Invalid unicode escape sequence, expected %1 hex digits 无效的 Unicode 转义序列,预期为 %1 个十六进制数字 - + Method '%1' declared as final and cannot be overridden 方法 "%1" 已声明为 final,因此无法被覆盖 - + Method '%1' marked as override but does not replace any base class or interface method 方法 "%1" 标记为覆盖,但并未替换任何基类或接口方法 - + Method '%1::%2' is missing the return type, nor is it the same name as object to be a constructor 方法 "%1::%2" 缺少返回类型,并且其名称与构造函数对象不同 - + Method '%1' is not part of object '%2' 方法 "%1" 不是对象 "%2" 的一部分 - + Missing implementation of '%1' 缺少 "%1" 的实现 - + Missing definition of '%1' 缺少 "%1" 的定义 - + Mixin class cannot be declared as '%1' Mixin 类不能声明为 "%1" - + Multiple matching signatures to '%1' "%1" 有多个匹配的签名 - + Found multiple get accessors for property '%1' 发现属性 "%1" 的多个 get 访问器 - + Found multiple set accessors for property '%1' 发现属性 "%1" 的多个集合访问器 - + Namespace '%1' doesn't exist. 命名空间 "%1" 不存在。 - - - - - - - - - - - - + + + + + + + + + + + + Name conflict. 名称冲突。 - + '%1' is an extended data type. "%1" 是扩展数据类型。 - + '%1' is a global property. "%1" 是全局属性。 - + '%1' is a named type. "%1" 是被命名的类型。 - + '%1' is a funcdef. "%1" 是一个函数签名定义。 - + '%1' is a global function. "%1" 是一个全局函数。 - + '%1' is a mixin class. "%1" 是一个 Mixin 类。 - + '%1' is a virtual property. "%1" 是虚拟属性。 - + '%1' is a class. "%1" 是一个类。 - + '%1' is an interface. "%1" 是一个接口。 - + '%1' is an object property. "%1" 是一个对象属性。 - + '%1' is a class method. "%1" 是一个类方法。 - + '%1' is already used. ”%1“ 已被使用。 - + No appropriate opHndlAssign method found in '%1' for handle assignment 在 "%1" 中未找到适当的 opHndlAssign 方法用于句柄分配 - + No conversion from '%1' to '%2' available. 无法进行从 "%1" 到 "%2" 的转换。 - + No conversion from '%1' to math type available. 无法将 "%1" 转换为数学类型。 - + No default constructor for object of type '%1'. "%1" 类型对象没有默认构造函数。 - + No appropriate opAssign method found in '%1' for value assignment 在 "%1" 中未找到适合赋值的 opAssign 方法 - + No copy constructor for object of type '%1'. 没有 "%1" 类型对象的复制构造函数。 - + No matching signatures to '%1' 没有与 "%1" 匹配的签名 - + No matching operator that takes the type '%1' found 未找到采用类型 "%1" 的匹配运算符 - + No matching operator that takes the types '%1' and '%2' found 未找到采用类型 "%1" 和 "%2" 的匹配运算符 - + No matching symbol '%1' 没有匹配的符号 "%1" - + Expression doesn't form a function call. '%1' evaluates to the non-function type '%2' 表达式不构成函数调用。"%1" 计算结果为非函数类型 "%2" - + '%1' is not declared "%1" 未被声明 - + '%1' is not initialized. ”%1“ 未初始化。 - + '%1' is not a member of '%2' ”%1“ 不是 ”%2“ 的成员 - + Type '%1' doesn't support the indexing operator 类型 "%1" 不支持索引运算符 - + Parameter type can't be '%1', because the type cannot be instantiated. 参数类型不能是 "%1",因为该类型无法实例化。 - + Previous error occurred while attempting to compile initialization list for type '%1' 尝试编译类型 "%1" 的初始化列表时发生先前的错误 - + Illegal call to private method '%1' 非法调用私有方法 "%1" - + Illegal access to private property '%1' 非法访问私有属性 "%1" - + Illegal call to protected method '%1' 非法调用受保护的方法 "%1" - + Illegal access to protected property '%1' 非法访问受保护的属性 "%1" - + Return type can't be '%1' 返回类型不能是 "%1" - + Shared code cannot access non-shared global variable '%1' 共享代码无法访问非共享全局变量 "%1" - + Shared code cannot call non-shared function '%1' 共享代码无法调用非共享函数 "%1" - + Shared type cannot implement non-shared interface '%1' 共享类型无法实现非共享接口 "%1" - + Shared class cannot inherit from non-shared class '%1' 共享类不能从非共享类 "%1" 继承 - + Shared code cannot use non-shared type '%1' 共享代码不能使用非共享类型 "%1" - + Shared type '%1' doesn't match the original declaration in other module 共享类型 "%1" 与其他模块中的原始声明不匹配 - + Template '%1' expects %2 sub type(s) 模板 "%1" 需要 %2 个子类型 - + Type '%1' cannot be a reference 类型 "%1" 不能是引用 - + Type '%1' is not available for this module 类型 "%1" 不适用于此模块 - + Type '%1' is not a template type 类型 "%1" 不是模板类型 - + Unexpected token '%1' 意外标记 "%1" - + Use of uninitialized global variable '%1'. 使用未初始化的全局变量 "%1"。 - + Unknown scope '%1' 未知作用域 "%1" - + Where '%1' is '%2' 其中 "%1" 是 "%2" - + Failed to initialize global variable '%1' 无法初始化全局变量 "%1" - + Exception '%1' in '%2' "%2" 中的异常 "%1" - + Type '%1' is missing behaviours 类型 "%1" 缺少的行为 - + Can't pass type '%1' by value unless the application type is informed in the registration 除非在注册时告知应用程序类型,否则无法按值传递类型 "%1" - + Can't return type '%1' by value unless the application type is informed in the registration 除非在注册时告知应用程序类型,否则无法按值返回类型 "%1" - + Don't support passing type '%1' by value to application in native calling convention on this platform 不支持在此平台上按照本机调用约定将类型 "%1" 按值传递给应用程序 - + Don't support returning type '%1' by value from application in native calling convention on this platform 不支持在此平台上按照本机调用约定从应用程序返回类型 "%1" 的值 - + Object {%1}. GC cannot destroy an object of type '%2' as it doesn't know how many references to there are. 对象 {%1}。GC 无法销毁类型为 "%2" 的对象,因为它不知道有多少个引用。 - + Object {%1}. GC cannot destroy an object of type '%2' as it can't see all references. Current ref count is %3. 对象 {%1}。GC 无法销毁类型为 "%2" 的对象,因为它无法看到所有引用。当前引用计数为 %3。 - + Object type '%1' doesn't exist 对象类型 "%1" 不存在 - + Cannot register. The template type instance '%1' has already been generated. 无法注册。模板类型实例 "%1" 已生成。 - + Template type '%1' doesn't exist 模板类型 "%1" 不存在 - + Template subtype '%1' doesn't exist 模板子类型 "%1" 不存在 - + Failed to read subtype of template type '%1' 无法读取模板类型 "%1" 的子类型 - + Failed in call to function '%1' (Code: %2, %3) 调用函数 "%1" 失败(代码:%2,%3) - + Failed in call to function '%1' with '%2' (Code: %3, %4) 使用 "%2" 调用函数 "%1" 失败(代码:%3,%4) - + Failed in call to function '%1' with '%2' and '%3' (Code: %4, %5) 使用 "%2" 和 "%3" 调用函数 "%1" 失败(代码:%4,%5) - + Type '%1' is still used by function '%2' 类型 "%1" 仍被函数 "%2" 使用 - + The builtin type in previous message is named '%1' 上一条消息中的内置类型名为 "%1" - + The function in previous message is named '%1'. The func type is %2 上一条消息中的函数名为 "%1"。函数类型为 %2 - + The script object of type '%1' is being resurrected illegally during destruction 类型为 "%1" 的脚本对象在销毁过程中被非法复活 - + LoadByteCode failed. The bytecode is invalid. Number of bytes read from stream: %1 LoadByteCode 失败。字节码无效。从流中读取的字节数:%1 - + Function '%1' appears to have been compiled without JIT entry points 函数 "%1" 似乎已在无 JIT 入口点的情况下进行编译 - + There is an external reference to an object in module '%1', preventing it from being deleted 存在对模块 "%1" 中对象的外部引用,导致无法删除该对象 - + Output argument expression is not assignable 输出参数表达式不可分配 - + Auto is not allowed here 这里禁止使用 auto 关键字 - + Can't find unambiguous implicit conversion to make both expressions have the same type 无法找到明确的隐式转换来使两个表达式具有相同的类型 - + Both conditions must call constructor 两个条件都必须调用构造函数 - + Base class doesn't have default constructor. Make explicit call to base constructor 基类没有默认构造函数。明确调用基类构造函数 - + Base class doesn't have copy constructor or default constructor and assign operator. Make explicit call to base constructor 基类没有复制构造函数或默认构造函数和赋值运算符。明确调用基类构造函数 - + Candidates are: 候选包括: - + Can't call a constructor in loops 无法在循环中调用构造函数 - + Can't call a constructor in switch 无法在 switch 中调用构造函数 - + Can't call a constructor multiple times 无法多次调用构造函数 - + Can't create delegate 无法创建委托 - + Can't create delegate for types that do not support handles 无法为不支持句柄的类型创建委托 - + Cannot flag function that will not be auto generated as deleted 无法将不会自动生成的函数标记为已删除 - + Conflict with explicit declaration of function and deleted function 与函数的显式声明和已删除函数冲突 - + Can't implement itself, or another interface that implements this interface 无法实现自身,也无法实现此接口的其他接口 - + Can't inherit from multiple classes 不能从多个类继承 - + Can't inherit from itself, or another class that inherits from this class 不能从其自身或从该类继承的其他类继承 - + Can't pass class method as arg directly. Use a delegate object instead 无法直接将类方法作为参数传递。请改用委托对象 - + Unable to resolve auto type 无法解析自动类型 - + Can't return reference to local value. 无法返回对本地值的引用。 - + Can't return value when return type is 'void' 返回类型为 "void" 时无法返回值 - + Implicit conversion changed sign of value 隐式转换改变了值的符号 - + A class cannot be both abstract and final 一个类不能同时是 abstract 和 final - + Compound assignments with property accessors on value types are not supported 不支持对值类型使用属性访问器的复合赋值 - + Compound assignments with indexed property accessors are not supported 不支持使用索引属性访问器的复合赋值 - + Compound assignments with property accessors require both get and set accessors 具有属性访问器的复合赋值需要 get 和 set 访问器 - + Variables cannot be declared in switch cases, except inside statement blocks 变量不能在 switch 语句中声明,除非在语句块内 - + The default case must be the last one default 情况必须是最后一个 - + The type of the default argument expression doesn't match the function parameter type 默认参数表达式的类型与函数参数类型不匹配 - + Deleted functions cannot have implementation 已删除的函数不能有实现 - + The destructor must not have any parameters 析构函数不能有任何参数 - + Value assignment on reference types is not allowed. Did you mean to do a handle assignment? 不允许对引用类型进行值分配。是要进行句柄分配吗? - + Compound assignment on reference types is not allowed 不允许对引用类型进行复合赋值 - + Duplicate named argument 重复命名参数 - + Duplicate switch case 重复的 switch case - + Else with empty statement else 中使用空语句 - + Empty list element is not allowed 不允许空列表元素 - + Empty switch statement 空的 switch 语句 - + Expected constant 应为常量 - + Expected data type 应为数据类型 - + Expected expression value 应为表达值 - + Expected identifier 应为标识符 - + Expected a list enclosed by { } to match pattern 应为用 { } 括起来的列表与模式匹配 - + Expected method or property 应为方法或属性 - + Expected one of: 应为为以下之一: - + Expected operator 应为操作符 - + Expected post operator 应为右操作符 - + Expected pre operator 应为左操作符 - + Expected string 应为字符串 - + Expression doesn't evaluate to a function 表达式无法计算函数值 - + Previous error occurred while attempting to create a temporary copy of object 尝试创建对象的临时副本时发生上一个错误 - + Float value truncated in implicit conversion to integer 浮点值在隐式转换为整数时被截断 - + Found multiple matching enum values 找到多个匹配的枚举值 - + A function with the same name and parameters already exists 具有相同名称和参数的函数已存在 - + Global variables have been disabled by the application 全局变量已被应用程序禁用 - + It is not allowed to perform a handle assignment on a non-handle property 不允许对非句柄属性执行句柄分配 - + The operand is implicitly converted to handle in order to compare them 操作数被隐式转换为句柄,以便进行比较 - + Handle to handle is not allowed 不允许使用句柄 - + If with empty statement 如果带有空语句 - + Illegal member type 非法成员类型 - + Illegal operation on this datatype 对该数据类型的非法操作 - + Illegal target type for reference cast 非法引用转换的目标类型 - + Interfaces can only implement other interfaces 接口只能实现其他接口 - + Invalid 'break' 无效的 break 关键字 - + Invalid character literal 无效的字符 - + Invalid 'continue' 无效的 continue 关键字 - + Invalid escape sequence 无效的转义序列 - + Invalid expression: ambiguous name 无效表达式:二义性名称 - + Invalid expression: stand-alone anonymous function 无效表达式:独立匿名函数 - + Invalid operation on method 方法操作无效 - + Invalid reference. Property accessors cannot be used in combined read/write operations 引用无效。属性访问器不能用于组合读/写操作。 - + Invalid scope resolution 范围解析无效 - + Invalid signature for virtual property 虚拟属性签名无效 - + Invalid type 类型无效 - + Invalid unicode code point 无效的 Unicode 代码点 - + Invalid unicode sequence in source 源代码中的 Unicode 序列无效 - + Invalid use of named arguments 命名参数的使用无效 - + The method cannot be named with the class name 该方法不能以类名命名 - + Mixin classes cannot have constructors or destructors Mixin 类不能有构造函数或析构函数 - + Mixin class cannot inherit from classes Mixin 类不能从类继承 - + Mixin classes cannot have child types Mixin 类不能有子类型 - + Found more than one matching operator 找到多个匹配的运算符 - + Multiline strings are not allowed in this application 此应用程序不允许使用多行字符串 - + Only objects have constructors 只有对象才有构造函数 - + Must return a value 必须返回一个值 - + Detected named argument with old syntax 检测到具有旧语法的命名参数 - + No appropriate indexing operator found 未找到合适的索引运算符 - + No appropriate opEquals method found 未找到合适的 opEquals 方法 - + The application doesn't support the default array type. 该应用程序不支持默认数组类型。 - + Non-const method call on read-only object reference 只读对象引用上的非常量方法调用 - + Non-terminated string literal 未终止的字符串 - + Not all paths return a value 并非所有路径都会返回值 - + Not enough values to match pattern 没有足够的值来模式匹配 - + Implicit conversion of value is not exact 值的隐式转换并不准确 - + Expression is not an l-value 表达式不是左值 - + Not a valid reference 无效引用 - + Not a valid lvalue 不是有效的左值 - + Nothing was built in the module 模块中没有构建任何内容 - + Object handle is not supported for this type 此类型不支持对象句柄 - + Only object types that support object handles can use &inout. Use &in or &out instead 只有支持对象句柄的对象类型才能使用 &inout。请改用 &in 或 &out - + A cast operator has one argument 强制类型转换运算符有一个参数 - + The code must contain one and only one function 代码必须包含一个且只能包含一个函数 - + The code must contain one and only one global variable 代码必须包含一个且只能有一个全局变量 - + Both operands must be handles when comparing identity 比较时,两个操作数都必须是句柄 - + The overloaded functions are identical on initial parameters without default arguments 重载函数在初始参数上相同,没有默认参数 - + Parameter already declared 参数已声明 - + Positional arguments cannot be passed after named arguments 位置参数不能在命名参数之后传递 - + Potentially matching non-const method is hidden on read-only object reference 可能匹配的非 const 方法隐藏在只读对象引用中 - + Property accessor with index must have 1 and only 1 index argument 带索引的属性访问器必须有 1 个且只能有 1 个索引参数 - + Property accessors have been disabled by the application 应用程序已禁用属性访问器 - + Property accessor must be implemented 必须实现属性访问器 - + Class properties cannot be declared as const 类属性不能声明为 const - + The property has no get accessor 该属性没有 get 访问器 - + The property has no set accessor 该属性没有设置访问器 - + Virtual property must have at least one get or set accessor 虚拟属性必须至少有一个 get 或 set 访问器 - + Resulting reference cannot be returned. Returned references must not refer to local variables. 无法返回结果引用。返回的引用不得引用局部变量。 - + Resulting reference cannot be returned. There are deferred arguments that may invalidate it. 无法返回结果引用。存在可能使其无效的延迟参数。 - + Resulting reference cannot be returned. The expression uses objects that during cleanup may invalidate it. 无法返回结果引用。表达式使用的对象在清理过程中可能会使其失效。 - + Reference is read-only 引用是只读的 - + Reference is temporary 参考是临时的 - + Reference types cannot be passed by value in function parameters 引用类型不能在函数参数中按值传递 - + Reference types cannot be returned by value from functions 引用类型不能通过函数返回值 - + The script section is empty 脚本节区为空 - + Signed/Unsigned mismatch 有符号/无符号不匹配 - + Strings are not recognized by the application 应用程序无法识别字符串 - + Case expressions must be literal constants case 表达式必须是文字常量 - + Switch expressions must be integral numbers switch 表达式必须是整数 - + The function has too many jump labels to handle. Split the function into smaller ones. 该函数的跳转标签过多,无法处理。请将函数拆分为较小的函数。 - + Too many values to match pattern 与模式匹配的值过多 - + Unexpected end of file 意外的文件结束 - + Unexpected variable declaration 意外的变量声明 - + Unreachable code 无法访问的代码 - + Virtual property contains unrecognized aspect 虚拟属性包含未被认可的部分 - + Unused script node 未使用的脚本节点 - + Value is too large for data type 对于数据类型来说,值太大 - + Void cannot be an operand in expressions void 不能作为表达式中的操作数 - + Warnings are treated as errors by the application 应用程序将警告视为错误 - + While parsing argument list 解析参数列表时 - + While parsing expression 解析表达式时 - + While parsing initialization list 解析初始化列表时 - + While parsing namespace 解析命名空间时 - + While parsing statement block 解析语句块时 - + Previous error occurred while including mixin 包含 mixin 时发生先前错误 - + Autohandles cannot be used with types that have been registered with NOCOUNT 自动句柄不能与已使用 NOCOUNT 注册的类型一起使用 - + First parameter to template factory must be a reference. This will be used to pass the object type of the template 模板工厂的第一个参数必须是引用。这将用于传递模板的对象类型 - + Invalid configuration. Verify the registered application interface. 配置无效。请验证已注册的应用程序接口。 - + A value type must be registered with a non-zero size 值类型必须注册为非零大小 - + The behaviour is not compatible with the type 行为与类型不兼容 - + A garbage collected ref type must have the addref, release, and all gc behaviours 垃圾收集引用类型必须具有 addref、release 和所有 gc 行为 - + A garbage collected value type must have the gc enum references behaviour 垃圾收集值类型必须具有 gc 枚举引用行为 - + A scoped reference type must have the release behaviour 作用域引用类型必须具有释放行为 - + A reference type must have the addref and release behaviours 引用类型必须具有 addref 和 release 行为 - + A non-pod value type must have at least one constructor and the destructor behaviours 非 pod 值类型必须至少有一个构造函数和析构函数行为 - + Template list factory expects two reference parameters. The last is the pointer to the initialization buffer 模板列表工厂需要两个引用参数。最后一个是指向初始化缓冲区的指针 - + List factory expects only one reference parameter. The pointer to the initialization buffer will be passed in this parameter 列表工厂仅需要一个引用参数。指向初始化缓冲区的指针将在此参数中传递 - + AddScriptObjectToGC called with null pointer 使用空指针调用 AddScriptObjectToGC - + An exception occurred in a nested call 嵌套调用中发生异常 - + Uh oh! The engine's reference count is increasing while it is being destroyed. Make sure references needed for clean-up are immediately released 哎呀!引擎的引用计数在被销毁时不断增加。确保立即释放清理所需的引用 - + The module is still in use and cannot be rebuilt. Discard it and request another module 该模块仍在使用中,无法重建。丢弃它并请求另一个模块 - + Property 属性 - + System function 系统函数 - + Variable declaration 变量声明 - + Stack overflow 栈溢出 - + Null pointer access 空指针访问 - + Divide by zero 除以零 - + Overflow in integer division 整数除法溢出 - + Overflow in exponent operation 指数运算溢出 - + Unrecognized byte code 无法识别的字节码 - + Invalid calling convention 无效调用约定 - + Unbound function called 未绑定的函数被调用 - + Out of range 越界 - + Caught an exception from the application 捕获应用程序异常 - + Mismatching types in value assignment 值分配中的类型不匹配 - + Too many nested calls 嵌套调用过多 - - + + Assert failed 断言失败 + + + GlobalBadDecl + + + + + ScriptRunUnsupported + + ScriptManager @@ -4332,6 +4351,16 @@ CanNotRunUsrScriptForPolicy 由于限制策略,无法在 Root 模式下运行用户脚本! + + + ScriptRunning + 脚本运行中 + + + + ScriptRunningRequestLastStop? + 脚本仍在运行中,是否终止上一个脚本再执行? + ScriptSettingDialog @@ -4399,37 +4428,37 @@ ScriptingConsole - + [Info] 【信息】 - + [Warn] 【警告】 - + [Error] 【错误】 - + [Console] 【控制台】 - + Copy 复制 - + Cut 剪切 - + Paste 粘贴 @@ -5343,7 +5372,7 @@ asDebugger - + {no engine} {无引擎} diff --git a/lang/zh_TW/winghex_zh_TW.ts b/lang/zh_TW/winghex_zh_TW.ts index 7156f66..7c12967 100644 --- a/lang/zh_TW/winghex_zh_TW.ts +++ b/lang/zh_TW/winghex_zh_TW.ts @@ -74,25 +74,25 @@ AppManager - + GenericCallNotFullySupported 該軟體腳本系統不完全支持通用調用,故軟體將會退出。 - + SetupClang 啟動 Clang 服務 - + OpeningFiles 打開檔 - - - - + + + + AlreadyOpened 檔已被打開 @@ -865,1172 +865,1183 @@ MainWindow - + File - - + + View 視圖 - + About 關於 - + WingHexExplorer 羽雲十六進制編輯器 - + loc: 座標: - + sel: 選長: - + Edit 編輯 - + Script 腳本 - - - + + + Plugin 插件 - + Setting 設置 - - + + Log 日誌 - + ExportFindResult 導出搜索結果 - + ClearFindResult 清空記錄 - - + + FindResult 搜索結果 - - - - + + + + Copy 複製 - - - - - + + + + + CopyToClipBoard 數據已拷貝到粘貼板 - + LittleEndian 小端 - + BigEndian 大端 - + Number 數值 - - + + CheckSum 校驗和 - - + + DeleteBookMark 刪除書簽 - - + + ClearBookMark 清空書簽 - - - - + + + + BookMark 書簽 - - + + DecodeText 解碼字串 - + ScriptConsole 腳本控制臺 - - + + Basic 基礎 - + New 新建 - + OpenF 打開檔 - + OpenWorkSpace 打開工作區 - + RecentFiles 最近打開 - - - + + + Reload 重新加載 - - + + Save 保存 - + SaveAs 另存為 - + ConvertWS 轉為工作區 - + Export 導出 - + SaveSel 保存選區位元組 - - - - + + + + General 基本 - + Undo 撤銷 - + Redo 恢復 - + Cut 剪切 - + Paste 粘貼 - + Delete 刪除 - + Clone 克隆 - + Lookup 查詢 - + Find 查找 - + Goto 跳轉 - - + + Encoding 編碼 - + FileInfo 檔資訊 - - + + Hex 十六進制 - + CutHex 剪切(十六進制) - + CopyHex 複製(十六進制) - + PasteHex 粘貼(十六進制) - - + + Fill 填充 - + FillZero 填充零 - - - - - + + + + + MetaData 標注 - + DeleteMetadata 刪除標注 - + ClearMetadata 清空標注 - + MetaDataEdit 編輯標注 - + DeleteMetaData 刪除標注 - + ClearMetaData 清空標注 - + Display 顯示 - + ViewText 文本預覽 - + Scale 縮放 - + SetupRecent 啟動最近檔服務 - + SetupUI 初始化介面 - + SetupDocking 啟動 Dock 服務 - + LaunchingLog 啟動日誌系統 - + SetupPluginSystem 啟動插件系統 - + LoadingPlg: 加載插件中: - + SetupConsole 啟動腳本控制臺 - + SetupScriptManager 啟動腳本管理器 - + SetupScriptService 啟動腳本服務 - + SetupScriptEditor 構建腳本編輯器 - + SetupSetDialog 構建設置窗體 - + SetupPlgWidgets 啟動插件組件 - + SetupDockingLayout 恢復 Dock 佈局 - + SetupWaiting 啟動即將完成 - + SetupFinished 啟動完畢 - + NoExtension 無擴展 - - + + ExportResult 導出結果 - + NothingToSave 沒有保存的數據 - + OpenExt 打開 - 拓展 - + ResetScale 重置縮放 - + ShowMetafg 標注前景色 - + ShowMetabg 標注背景色 - + ShowMetaComment 批註 - + MetaShowAll 顯示所有標注 - + MetaHideAll 隱藏所有標注 - + FileStatus 檔狀態 - - + + InfoSave 是否保存 - - + + ReadOnly 可讀寫 - - + + SetLocked 啟用/禁用鎖定編輯 - + ErrUnLock 鎖定編輯失敗 - - + + SetOver 啟用/禁用改變大小 - + InputRequest - + 輸入請求 - + + ScriptEngineInitFailed + 腳本引擎啟動失敗,將自動禁用該功能。 + + + UnsignedHex 無符號 Hex - + BgScriptOutput 後臺腳本輸出 - + ErrUnOver 鎖定檔大小失敗 - + Window 窗體 - + Editor 編輯器 - + Tools 工具 - + HexEditorLayout 編輯器佈局 - + SetBaseAddr 設置基址 - + addressBase 基址 - + inputAddressBase 請輸入基址 - + WarnBigBaseAddress 基址過大,你得到的地址將會不正確! - + ErrBaseAddress 非法基址輸入 - + SetColInfo 顯示/隱藏地址欄 - + SetHeaderInfo 顯示/隱藏表頭 - + SetAsciiString 顯示/隱藏解碼字串 - + Layout 佈局 - + Fullscreen 全屏 - + Default 默認 - - - + + + LayoutRestoring... 恢復佈局中... - + RestoreLayout 恢復佈局 - - + + SaveLayout 保存佈局 - + ExportLog 導出日誌 - + ClearLog 清空日誌 - + InsepctQt 監視 Qt - + ScriptEditor 腳本編輯器 - + Scripts 腳本倉庫 - + PluginFunctions 插件功能 - + ScriptSetting 腳本設置 - + PluginSettings 插件設置 - + Info 資訊 - + Software 軟體 - + Sponsor 贊助 - + CheckUpdate 檢查更新 - + Wiki 網頁 Wiki - + AboutQT 關於 QT - + SetPageIDEmptyTryUseName 設置頁 ID 為空,嘗試使用名稱作為 ID - + SetPageDupNameIgnored 設置頁重複的 ID 名稱,已忽略加載 - + Plugin %1 contains a duplicate ID (%2) that is already registered by plugin %3 插件 %1 包含重複 ID (%2),該 ID 已被插件 %3 註冊 - - + + ChooseFile 選擇檔 - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + Error 錯誤 - - + + FileNotExist 檔不存在! - - - - - + + + + + FilePermission 因檔許可權無法繼續! - + ProjectFile (*.wingpro) 專案檔 (*.wingpro) - + ReloadSuccessfully 檔重新加載成功! - + ReloadUnSuccessfully 檔重新加載失敗! - - - - + + + + ChooseSaveFile 請選擇保存檔路徑: - + NoMoreClone 克隆已到上限,無法繼續操作! - + FindFininishBusy 查找任務繁忙,請勿重複查找! - + MayTooMuchFindResult 搜索數量已到達上限,結果可能不全,建議請按區段搜索。 - + SaveLayoutSuccess 保存佈局成功 - + SaveLayoutError 保存佈局失敗 - + HasClonedView 該編輯頁已被克隆編輯,如果關閉,相關聯的頁也會被關閉,你確認繼續嗎? - - - ReloadNeededYesOrNo - + + FileCloseBigFile + 大檔讀取模式下目的檔案被關閉,該標籤將會被關閉。 - + + + ReloadNeededYesOrNo + 目的檔案被修改,是否重新載入? + + + SaveWorkSpace 保存工作區 - + WingHexWorkSpace (*.wingpro) 羽雲十六進制工作區 (*.wingpro) - + ConfirmSave 正在關閉未保存的檔或工作區,你確定保存嗎? - + [Info] 【資訊】 - + [Warn] 【警告】 - + [Error] 【錯誤】 - + ConfirmAPPSave 你嘗試關閉程式,但仍存在未保存的檔或工作區,你確定保存這些更改嗎? - - - + + + SaveSuccessfully 保存成功! - - + + SaveWSError 保存工作區錯誤! - - + + Warn 警告 - + Opening... 打開檔中... - + WorkSpaceOpening... 打開工作區中... - + Reloading... 重載檔中... - + Saving... 保存中... - + SaveNewFirst 請首先保存新建的檔 - + AlreadyWorkSpace 已經是工作區,無需轉化 - + ConvWorkSpaceFailed 轉化為工作區失敗 - + ConvWorkSpaceSuccess 轉化為工作區成功 - + SavingAs... 另存為中... - + SaveUnSuccessfully 保存失敗! - + Exporting... 導出中... - + ChooseExportFile 請選擇導出檔路徑: - + ExportSuccessfully 導出成功! - + ExportUnSuccessfully 導出失敗! - + SavingSel... 保存選中位元組中... - + SaveSelSuccess 保存選區位元組成功! - + SaveSelError 保存選區位元組失敗,因檔不具有可寫許可權! - - + + CutToClipBoard 數據已剪切到粘貼板! - - + + UnCutToClipBoard 由於保持大小限制,數據剪切到粘貼板失敗! - - + + UnCopyToClipBoard 由於保持大小限制,數據剪切到複製板失敗! - - + + Finding... 查找中... - + DeleteSuccess 刪除成功 - + DeleteFailed 刪除失敗 - + FindFininish 查找結果完畢! - + PleaseInputFill 請輸入填充位元組值 - + FillInputTruncWarn 填充輸入數值過大,將會被截斷填充 - + FillInputError 填充位元組輸入錯誤 - - + + InputComment 請輸入批註: - - + + BookmarkDelSuccess 刪除書簽成功 - + BookmarkDelNoItem 無書簽可刪除 - + BookmarkClearSuccess 書簽清空完畢 - - - + + + NoSelection 沒有選區,無法繼續的操作! - + NoMetaData 無可編輯標記 - + PleaseClearSel 請清空選擇 - + MetaDelSuccess 元數據刪除成功 - + MetaDelNoItem 無元數據可刪除 - + MetaClearSuccess 元數據清空完畢 - + FindResultExporting... 查找結果導出中... - + EmptyFindResult 沒有可導出的搜索結果! - + SaveFindResult 導出搜索結果成功! - + SaveFindResultError 導出結果失敗! - + TooManyBytesDecode 超出解碼位元組限制…… - + NoTextFileMayInvalid 該檔不是文本檔,以文本方式預覽並不是一個好的方式,你確認繼續嗎? - + LayoutSaving... 佈局保存中... - - + + PleaseInput 請輸入 - + LogExporting... 日誌導出中... - + ExportLogError 導出日誌失敗! - + ExportLogSuccess 導出日誌成功,路徑: - + ClearLogSuccess 清空日誌成功! - + BadNetwork 無法與遠程伺服器的更新檢查建立連接,請檢查網路。 - + NewestVersion 當前軟體為最新版本 - - + + OlderVersion 你使用的軟體為老版本,建議到 Github 和 Gitee 的倉庫發行版下載更新。 - + CheckingUpdate 檢查更新中…… - + Too much opened files 打開的檔過多,無法繼續操作! - + FilePermissionSure2Quit 因檔許可權無法保存,你確認要退出嗎? - + UnknownErrorSure2Quit 因未知錯誤無法保存,你確認要退出嗎? - + WorkSpaceUnSavedSure2Quit 工作區檔無法保存,你確認要退出嗎? - + CopyLimit 拷貝位元組超出限制 - + ErrOpenFileBelow 打開檔出現錯誤(由於許可權不足),如下為打開錯誤的檔: @@ -2467,12 +2478,12 @@ 該設置需要程式重啟後生效 - + wingsummer 寂靜的羽夏 - + WingCloudStudio 羽雲工作室 @@ -2750,37 +2761,35 @@ ScriptMachine - + AngelScript callstack: AngelScript 調用堆疊: - + - Exception '%1' in '%2' — 在 ‘%2’ 中發生異常 ‘%1’ - + ExecNotAllowedInRoot 在管理員許可權執行第三方命令為非法操作 - - - + + Script failed to build 腳本編譯失敗 - - + Cannot find 'int main()' or 'void main()' 無法找到程式入口點: "int main()" 或者 "void main()" - + Debugging, waiting for commands. 調試中,等待調試命令。 @@ -2790,1535 +2799,1545 @@ 初始化全局變數失敗 - - + + The script failed with an exception 異常被拋出,腳本執行失敗 - - + + The script was aborted 腳本被終止 - - + + The script terminated unexpectedly 腳本異常退出 - + The script exited with 腳本退出返回值: - + '%1' is already declared "%1" 已被聲明 - + Abstract class '%1' cannot be instantiated 無法實例化抽象類 "%1" - + Accessing private property '%1' of parent class 非法訪問父類的私有屬性 "%1" - + Attribute '%1' informed multiple times 屬性 "%1" 已被多次通知 - + Can't form arrays of subtype '%1' 無法創建子類型 "%1" 的數組 - + Can't inherit from class '%1' marked as final 無法從標記為 final 的類 "%1" 繼承 - + Cannot access non-static member '%1' like this 無法和像使用 this 一樣訪問非靜態成員 "%1" - + Can't construct handle '%1'. Use ref cast instead 無法構造句柄 "%1" 。請改用引用強制轉換 - + Can't implicitly convert from '%1' to '%2'. 無法從 "%1' 隱式轉換為 "%2"。 - + Compiling %1 正在編譯 %1 - + Compiling auto generated %1 編譯自動生成的 %1 - + Implemented property accessor '%1' does not expect index argument 已實現的屬性訪問器 "%1" 不需要索引參數 - + Implemented property accessor '%1' expects index argument 已實現的屬性訪問器 "%1" 需要索引參數 - + Data type can't be '%1' 數據類型不能為 "%1" - + All subsequent parameters after the first default value must have default values in function '%1' 在函數 "%1" 中,第一個默認值之後的所有後續參數都必須具有默認值 - + The method in the derived class must have the same return type as in the base class: '%1' 派生類中的方法必須具有與基類相同的返回類型:"%1" - + The name of the destructor '%1::~%2' must be the same as the class 析構函數 "%1::~%2" 的名稱必須與類相同 - + Expected '%1' 應為 "%1" - + Expected '%1' or '%2' 應為 ”%1“ 或 ”%2“ - + Expression must be of boolean type, instead found '%1' 運算式必須是布爾類型,但實際使用的是 "%1" - + Expression '%1' is a data type 運算式 "%1" 是一種數據類型 - + External shared entity '%1' not found 未找到外部共用實體 "%1" - + External shared entity '%1' cannot redefine the original entity 外部共用實體 "%1" 無法重新定義原始實體 - + Failed while compiling default arg for parameter %1 in function '%2' 為函數 "%2" 中的參數 %1 編譯默認參數時失敗 - + Function '%1' not found 未找到函數 "%1" - + The property '%1' has mismatching types for the get and set accessors 屬性 "%1" 的 get 和 set 訪問器類型不匹配 - + Variable '%1' hides another variable of same name in outer scope 變數 "%1" 隱藏了外部作用域中另一個同名變數 - + Identifier '%1' is not a data type 識別字 "%1" 不是數據類型 - + Identifier '%1' is not a data type in global namespace 識別字 "%1" 不是全局命名空間中的數據類型 - + Identifier '%1' is not a data type in namespace '%2' or parent 識別字 "%1" 不是命名空間 "%2" 或其父級中的數據類型 - + Illegal operation on '%1' 對 "%1" 的非法操作 - + Illegal variable name '%1'. 非法變數名 "%1"。 - + Illegal access to inherited private property '%1' 非法訪問繼承的私有屬性 "%1" - + Initialization lists cannot be used with '%1' 初始化列表不能與 "%1" 一起使用 - + Attempting to instantiate invalid template type '%1<%2>' 嘗試實例化無效的範本類型 "%1<%2>" - + Instead found '%1' 而是找到了 "%1" - + Instead found identifier '%1' 而是找到識別字 "%1" - + Instead found reserved keyword '%1' 而是找到了保留關鍵字 "%1" - + Interface '%1' cannot be instantiated 無法實例化介面 "%1" - + Invalid unicode escape sequence, expected %1 hex digits 無效的 Unicode 轉義序列,預期為 %1 個十六進制數字 - + Method '%1' declared as final and cannot be overridden 方法 "%1" 已聲明為 final,因此無法被覆蓋 - + Method '%1' marked as override but does not replace any base class or interface method 方法 "%1" 標記為覆蓋,但並未替換任何基類或介面方法 - + Method '%1::%2' is missing the return type, nor is it the same name as object to be a constructor 方法 "%1::%2" 缺少返回類型,並且其名稱與構造函數對象不同 - + Method '%1' is not part of object '%2' 方法 "%1" 不是對象 "%2" 的一部分 - + Missing implementation of '%1' 缺少 "%1" 的實現 - + Missing definition of '%1' 缺少 "%1" 的定義 - + Mixin class cannot be declared as '%1' Mixin 類不能聲明為 "%1" - + Multiple matching signatures to '%1' "%1" 有多個匹配的簽名 - + Found multiple get accessors for property '%1' 發現屬性 "%1" 的多個 get 訪問器 - + Found multiple set accessors for property '%1' 發現屬性 "%1" 的多個集合訪問器 - + Namespace '%1' doesn't exist. 命名空間 "%1" 不存在。 - - - - - - - - - - - - + + + + + + + + + + + + Name conflict. 名稱衝突。 - + '%1' is an extended data type. "%1" 是擴展數據類型。 - + '%1' is a global property. "%1" 是全局屬性。 - + '%1' is a named type. "%1" 是被命名的類型。 - + '%1' is a funcdef. "%1" 是一個函數簽名定義。 - + '%1' is a global function. "%1" 是一個全局函數。 - + '%1' is a mixin class. "%1" 是一個 Mixin 類。 - + '%1' is a virtual property. "%1" 是虛擬屬性。 - + '%1' is a class. "%1" 是一個類。 - + '%1' is an interface. "%1" 是一個介面。 - + '%1' is an object property. "%1" 是一個對象屬性。 - + '%1' is a class method. "%1" 是一個類方法。 - + '%1' is already used. ”%1“ 已被使用。 - + No appropriate opHndlAssign method found in '%1' for handle assignment 在 "%1" 中未找到適當的 opHndlAssign 方法用於句柄分配 - + No conversion from '%1' to '%2' available. 無法進行從 "%1" 到 "%2" 的轉換。 - + No conversion from '%1' to math type available. 無法將 "%1" 轉換為數學類型。 - + No default constructor for object of type '%1'. "%1" 類型對象沒有默認構造函數。 - + No appropriate opAssign method found in '%1' for value assignment 在 "%1" 中未找到適合賦值的 opAssign 方法 - + No copy constructor for object of type '%1'. 沒有 "%1" 類型對象的複製構造函數。 - + No matching signatures to '%1' 沒有與 "%1" 匹配的簽名 - + No matching operator that takes the type '%1' found 未找到採用類型 "%1" 的匹配運算符 - + No matching operator that takes the types '%1' and '%2' found 未找到採用類型 "%1" 和 "%2" 的匹配運算符 - + No matching symbol '%1' 沒有匹配的符號 "%1" - + Expression doesn't form a function call. '%1' evaluates to the non-function type '%2' 運算式不構成函數調用。"%1" 計算結果為非函數類型 "%2" - + '%1' is not declared "%1" 未被聲明 - + '%1' is not initialized. ”%1“ 未初始化。 - + '%1' is not a member of '%2' ”%1“ 不是 ”%2“ 的成員 - + Type '%1' doesn't support the indexing operator 類型 "%1" 不支持索引運算符 - + Parameter type can't be '%1', because the type cannot be instantiated. 參數類型不能是 "%1",因為該類型無法實例化。 - + Previous error occurred while attempting to compile initialization list for type '%1' 嘗試編譯類型 "%1" 的初始化列表時發生先前的錯誤 - + Illegal call to private method '%1' 非法調用私有方法 "%1" - + Illegal access to private property '%1' 非法訪問私有屬性 "%1" - + Illegal call to protected method '%1' 非法調用受保護的方法 "%1" - + Illegal access to protected property '%1' 非法訪問受保護的屬性 "%1" - + Return type can't be '%1' 返回類型不能是 "%1" - + Shared code cannot access non-shared global variable '%1' 共用代碼無法訪問非共用全局變數 "%1" - + Shared code cannot call non-shared function '%1' 共用代碼無法調用非共用函數 "%1" - + Shared type cannot implement non-shared interface '%1' 共用類型無法實現非共用介面 "%1" - + Shared class cannot inherit from non-shared class '%1' 共用類不能從非共用類 "%1" 繼承 - + Shared code cannot use non-shared type '%1' 共用代碼不能使用非共用類型 "%1" - + Shared type '%1' doesn't match the original declaration in other module 共用類型 "%1" 與其他模組中的原始聲明不匹配 - + Template '%1' expects %2 sub type(s) 範本 "%1" 需要 %2 個子類型 - + Type '%1' cannot be a reference 類型 "%1" 不能是引用 - + Type '%1' is not available for this module 類型 "%1" 不適用於此模組 - + Type '%1' is not a template type 類型 "%1" 不是範本類型 - + Unexpected token '%1' 意外標記 "%1" - + Use of uninitialized global variable '%1'. 使用未初始化的全局變數 "%1"。 - + Unknown scope '%1' 未知作用域 "%1" - + Where '%1' is '%2' 其中 "%1" 是 "%2" - + Failed to initialize global variable '%1' 無法初始化全局變數 "%1" - + Exception '%1' in '%2' "%2" 中的異常 "%1" - + Type '%1' is missing behaviours 類型 "%1" 缺少的行為 - + Can't pass type '%1' by value unless the application type is informed in the registration 除非在註冊時告知應用程式類型,否則無法按值傳遞類型 "%1" - + Can't return type '%1' by value unless the application type is informed in the registration 除非在註冊時告知應用程式類型,否則無法按值返回類型 "%1" - + Don't support passing type '%1' by value to application in native calling convention on this platform 不支持在此平臺上按照本機調用約定將類型 "%1" 按值傳遞給應用程式 - + Don't support returning type '%1' by value from application in native calling convention on this platform 不支持在此平臺上按照本機調用約定從應用程式返回類型 "%1" 的值 - + Object {%1}. GC cannot destroy an object of type '%2' as it doesn't know how many references to there are. 對象 {%1}。GC 無法銷毀類型為 "%2" 的對象,因為它不知道有多少個引用。 - + Object {%1}. GC cannot destroy an object of type '%2' as it can't see all references. Current ref count is %3. 對象 {%1}。GC 無法銷毀類型為 "%2" 的對象,因為它無法看到所有引用。當前引用計數為 %3。 - + Object type '%1' doesn't exist 對象類型 "%1" 不存在 - + Cannot register. The template type instance '%1' has already been generated. 無法註冊。範本類型實例 "%1" 已生成。 - + Template type '%1' doesn't exist 範本類型 "%1" 不存在 - + Template subtype '%1' doesn't exist 範本子類型 "%1" 不存在 - + Failed to read subtype of template type '%1' 無法讀取範本類型 "%1" 的子類型 - + Failed in call to function '%1' (Code: %2, %3) 調用函數 "%1" 失敗(代碼:%2,%3) - + Failed in call to function '%1' with '%2' (Code: %3, %4) 使用 "%2" 調用函數 "%1" 失敗(代碼:%3,%4) - + Failed in call to function '%1' with '%2' and '%3' (Code: %4, %5) 使用 "%2" 和 "%3" 調用函數 "%1" 失敗(代碼:%4,%5) - + Type '%1' is still used by function '%2' 類型 "%1" 仍被函數 "%2" 使用 - + The builtin type in previous message is named '%1' 上一條消息中的內置類型名為 "%1" - + The function in previous message is named '%1'. The func type is %2 上一條消息中的函數名為 "%1"。函數類型為 %2 - + The script object of type '%1' is being resurrected illegally during destruction 類型為 "%1" 的腳本對象在銷毀過程中被非法復活 - + LoadByteCode failed. The bytecode is invalid. Number of bytes read from stream: %1 LoadByteCode 失敗。位元組碼無效。從流中讀取的位元組數:%1 - + Function '%1' appears to have been compiled without JIT entry points 函數 "%1" 似乎已在無 JIT 入口點的情況下進行編譯 - + There is an external reference to an object in module '%1', preventing it from being deleted 存在對模組 "%1" 中對象的外部引用,導致無法刪除該對象 - + Output argument expression is not assignable 輸出參數運算式不可分配 - + Auto is not allowed here 這裏禁止使用 auto 關鍵字 - + Can't find unambiguous implicit conversion to make both expressions have the same type 無法找到明確的隱式轉換來使兩個運算式具有相同的類型 - + Both conditions must call constructor 兩個條件都必須調用構造函數 - + Base class doesn't have default constructor. Make explicit call to base constructor 基類沒有默認構造函數。明確調用基類構造函數 - + Base class doesn't have copy constructor or default constructor and assign operator. Make explicit call to base constructor 基類沒有複製構造函數或默認構造函數和賦值運算符。明確調用基類構造函數 - + Candidates are: 候選包括: - + Can't call a constructor in loops 無法在迴圈中調用構造函數 - + Can't call a constructor in switch 無法在 switch 中調用構造函數 - + Can't call a constructor multiple times 無法多次調用構造函數 - + Can't create delegate 無法創建委託 - + Can't create delegate for types that do not support handles 無法為不支持句柄的類型創建委託 - + Cannot flag function that will not be auto generated as deleted 無法將不會自動生成的函數標記為已刪除 - + Conflict with explicit declaration of function and deleted function 與函數的顯式聲明和已刪除函數衝突 - + Can't implement itself, or another interface that implements this interface 無法實現自身,也無法實現此介面的其他介面 - + Can't inherit from multiple classes 不能從多個類繼承 - + Can't inherit from itself, or another class that inherits from this class 不能從其自身或從該類繼承的其他類繼承 - + Can't pass class method as arg directly. Use a delegate object instead 無法直接將類方法作為參數傳遞。請改用委託對象 - + Unable to resolve auto type 無法解析自動類型 - + Can't return reference to local value. 無法返回對本地值的引用。 - + Can't return value when return type is 'void' 返回類型為 "void" 時無法返回值 - + Implicit conversion changed sign of value 隱式轉換改變了值的符號 - + A class cannot be both abstract and final 一個類不能同時是 abstract 和 final - + Compound assignments with property accessors on value types are not supported 不支持對值類型使用屬性訪問器的複合賦值 - + Compound assignments with indexed property accessors are not supported 不支持使用索引屬性訪問器的複合賦值 - + Compound assignments with property accessors require both get and set accessors 具有屬性訪問器的複合賦值需要 get 和 set 訪問器 - + Variables cannot be declared in switch cases, except inside statement blocks 變數不能在 switch 語句中聲明,除非在語句塊內 - + The default case must be the last one default 情況必須是最後一個 - + The type of the default argument expression doesn't match the function parameter type 默認參數運算式的類型與函數參數類型不匹配 - + Deleted functions cannot have implementation 已刪除的函數不能有實現 - + The destructor must not have any parameters 析構函數不能有任何參數 - + Value assignment on reference types is not allowed. Did you mean to do a handle assignment? 不允許對引用類型進行值分配。是要進行句柄分配嗎? - + Compound assignment on reference types is not allowed 不允許對引用類型進行複合賦值 - + Duplicate named argument 重複命名參數 - + Duplicate switch case 重複的 switch case - + Else with empty statement else 中使用空語句 - + Empty list element is not allowed 不允許空列表元素 - + Empty switch statement 空的 switch 語句 - + Expected constant 應為常量 - + Expected data type 應為數據類型 - + Expected expression value 應為表達值 - + Expected identifier 應為識別字 - + Expected a list enclosed by { } to match pattern 應為用 { } 括起來的列表與模式匹配 - + Expected method or property 應為方法或屬性 - + Expected one of: 應為為以下之一: - + Expected operator 應為操作符 - + Expected post operator 應為右操作符 - + Expected pre operator 應為左操作符 - + Expected string 應為字串 - + Expression doesn't evaluate to a function 運算式無法計算函數值 - + Previous error occurred while attempting to create a temporary copy of object 嘗試創建對象的臨時副本時發生上一個錯誤 - + Float value truncated in implicit conversion to integer 浮點值在隱式轉換為整數時被截斷 - + Found multiple matching enum values 找到多個匹配的枚舉值 - + A function with the same name and parameters already exists 具有相同名稱和參數的函數已存在 - + Global variables have been disabled by the application 全局變數已被應用程式禁用 - + It is not allowed to perform a handle assignment on a non-handle property 不允許對非句柄屬性執行句柄分配 - + The operand is implicitly converted to handle in order to compare them 運算元被隱式轉換為句柄,以便進行比較 - + Handle to handle is not allowed 不允許使用句柄 - + If with empty statement 如果帶有空語句 - + Illegal member type 非法成員類型 - + Illegal operation on this datatype 對該數據類型的非法操作 - + Illegal target type for reference cast 非法引用轉換的目標類型 - + Interfaces can only implement other interfaces 介面只能實現其他介面 - + Invalid 'break' 無效的 break 關鍵字 - + Invalid character literal 無效的字元 - + Invalid 'continue' 無效的 continue 關鍵字 - + Invalid escape sequence 無效的轉義序列 - + Invalid expression: ambiguous name 無效運算式:二義性名稱 - + Invalid expression: stand-alone anonymous function 無效運算式:獨立匿名函數 - + Invalid operation on method 方法操作無效 - + Invalid reference. Property accessors cannot be used in combined read/write operations 引用無效。屬性訪問器不能用於組合讀/寫操作。 - + Invalid scope resolution 範圍解析無效 - + Invalid signature for virtual property 虛擬屬性簽名無效 - + Invalid type 類型無效 - + Invalid unicode code point 無效的 Unicode 代碼點 - + Invalid unicode sequence in source 源代碼中的 Unicode 序列無效 - + Invalid use of named arguments 命名參數的使用無效 - + The method cannot be named with the class name 該方法不能以類名命名 - + Mixin classes cannot have constructors or destructors Mixin 類不能有構造函數或析構函數 - + Mixin class cannot inherit from classes Mixin 類不能從類繼承 - + Mixin classes cannot have child types Mixin 類不能有子類型 - + Found more than one matching operator 找到多個匹配的運算符 - + Multiline strings are not allowed in this application 此應用程式不允許使用多行字串 - + Only objects have constructors 只有對象才有構造函數 - + Must return a value 必須返回一個值 - + Detected named argument with old syntax 檢測到具有舊語法的命名參數 - + No appropriate indexing operator found 未找到合適的索引運算符 - + No appropriate opEquals method found 未找到合適的 opEquals 方法 - + The application doesn't support the default array type. 該應用程式不支持默認數組類型。 - + Non-const method call on read-only object reference 只讀對象引用上的非常量方法調用 - + Non-terminated string literal 未終止的字串 - + Not all paths return a value 並非所有路徑都會返回值 - + Not enough values to match pattern 沒有足夠的值來模式匹配 - + Implicit conversion of value is not exact 值的隱式轉換並不準確 - + Expression is not an l-value 運算式不是左值 - + Not a valid reference 無效引用 - + Not a valid lvalue 不是有效的左值 - + Nothing was built in the module 模組中沒有構建任何內容 - + Object handle is not supported for this type 此類型不支持對象句柄 - + Only object types that support object handles can use &inout. Use &in or &out instead 只有支持對象句柄的對象類型才能使用 &inout。請改用 &in 或 &out - + A cast operator has one argument 強制類型轉換運算符有一個參數 - + The code must contain one and only one function 代碼必須包含一個且只能包含一個函數 - + The code must contain one and only one global variable 代碼必須包含一個且只能有一個全局變數 - + Both operands must be handles when comparing identity 比較時,兩個運算元都必須是句柄 - + The overloaded functions are identical on initial parameters without default arguments 重載函數在初始參數上相同,沒有默認參數 - + Parameter already declared 參數已聲明 - + Positional arguments cannot be passed after named arguments 位置參數不能在命名參數之後傳遞 - + Potentially matching non-const method is hidden on read-only object reference 可能匹配的非 const 方法隱藏在只讀對象引用中 - + Property accessor with index must have 1 and only 1 index argument 帶索引的屬性訪問器必須有 1 個且只能有 1 個索引參數 - + Property accessors have been disabled by the application 應用程式已禁用屬性訪問器 - + Property accessor must be implemented 必須實現屬性訪問器 - + Class properties cannot be declared as const 類屬性不能聲明為 const - + The property has no get accessor 該屬性沒有 get 訪問器 - + The property has no set accessor 該屬性沒有設置訪問器 - + Virtual property must have at least one get or set accessor 虛擬屬性必須至少有一個 get 或 set 訪問器 - + Resulting reference cannot be returned. Returned references must not refer to local variables. 無法返回結果引用。返回的引用不得引用局部變數。 - + Resulting reference cannot be returned. There are deferred arguments that may invalidate it. 無法返回結果引用。存在可能使其無效的延遲參數。 - + Resulting reference cannot be returned. The expression uses objects that during cleanup may invalidate it. 無法返回結果引用。運算式使用的對象在清理過程中可能會使其失效。 - + Reference is read-only 引用是只讀的 - + Reference is temporary 參考是臨時的 - + Reference types cannot be passed by value in function parameters 引用類型不能在函數參數中按值傳遞 - + Reference types cannot be returned by value from functions 引用類型不能通過函數返回值 - + The script section is empty 腳本節區為空 - + Signed/Unsigned mismatch 有符號/無符號不匹配 - + Strings are not recognized by the application 應用程式無法識別字串 - + Case expressions must be literal constants case 運算式必須是文字常量 - + Switch expressions must be integral numbers switch 運算式必須是整數 - + The function has too many jump labels to handle. Split the function into smaller ones. 該函數的跳轉標籤過多,無法處理。請將函數拆分為較小的函數。 - + Too many values to match pattern 與模式匹配的值過多 - + Unexpected end of file 意外的檔結束 - + Unexpected variable declaration 意外的變數聲明 - + Unreachable code 無法訪問的代碼 - + Virtual property contains unrecognized aspect 虛擬屬性包含未被認可的部分 - + Unused script node 未使用的腳本節點 - + Value is too large for data type 對於數據類型來說,值太大 - + Void cannot be an operand in expressions void 不能作為運算式中的運算元 - + Warnings are treated as errors by the application 應用程式將警告視為錯誤 - + While parsing argument list 解析參數列表時 - + While parsing expression 解析運算式時 - + While parsing initialization list 解析初始化列表時 - + While parsing namespace 解析命名空間時 - + While parsing statement block 解析語句塊時 - + Previous error occurred while including mixin 包含 mixin 時發生先前錯誤 - + Autohandles cannot be used with types that have been registered with NOCOUNT 自動句柄不能與已使用 NOCOUNT 註冊的類型一起使用 - + First parameter to template factory must be a reference. This will be used to pass the object type of the template 範本工廠的第一個參數必須是引用。這將用於傳遞範本的對象類型 - + Invalid configuration. Verify the registered application interface. 配置無效。請驗證已註冊的應用程式介面。 - + A value type must be registered with a non-zero size 值類型必須註冊為非零大小 - + The behaviour is not compatible with the type 行為與類型不相容 - + A garbage collected ref type must have the addref, release, and all gc behaviours 垃圾收集引用類型必須具有 addref、release 和所有 gc 行為 - + A garbage collected value type must have the gc enum references behaviour 垃圾收集值類型必須具有 gc 枚舉引用行為 - + A scoped reference type must have the release behaviour 作用域引用類型必須具有釋放行為 - + A reference type must have the addref and release behaviours 引用類型必須具有 addref 和 release 行為 - + A non-pod value type must have at least one constructor and the destructor behaviours 非 pod 值類型必須至少有一個構造函數和析構函數行為 - + Template list factory expects two reference parameters. The last is the pointer to the initialization buffer 範本列表工廠需要兩個引用參數。最後一個是指向初始化緩衝區的指針 - + List factory expects only one reference parameter. The pointer to the initialization buffer will be passed in this parameter 列表工廠僅需要一個引用參數。指向初始化緩衝區的指針將在此參數中傳遞 - + AddScriptObjectToGC called with null pointer 使用空指針調用 AddScriptObjectToGC - + An exception occurred in a nested call 嵌套調用中發生異常 - + Uh oh! The engine's reference count is increasing while it is being destroyed. Make sure references needed for clean-up are immediately released 哎呀!引擎的引用計數在被銷毀時不斷增加。確保立即釋放清理所需的引用 - + The module is still in use and cannot be rebuilt. Discard it and request another module 該模組仍在使用中,無法重建。丟棄它並請求另一個模組 - + Property 屬性 - + System function 系統函數 - + Variable declaration 變數聲明 - + Stack overflow 棧溢出 - + Null pointer access 空指針訪問 - + Divide by zero 除以零 - + Overflow in integer division 整數除法溢出 - + Overflow in exponent operation 指數運算溢出 - + Unrecognized byte code 無法識別的位元組碼 - + Invalid calling convention 無效調用約定 - + Unbound function called 未綁定的函數被調用 - + Out of range 越界 - + Caught an exception from the application 捕獲應用程式異常 - + Mismatching types in value assignment 值分配中的類型不匹配 - + Too many nested calls 嵌套調用過多 - - + + Assert failed 斷言失敗 + + + GlobalBadDecl + + + + + ScriptRunUnsupported + + ScriptManager @@ -4332,6 +4351,16 @@ CanNotRunUsrScriptForPolicy 由於限制策略,無法在 Root 模式下運行用戶腳本! + + + ScriptRunning + 腳本運行中 + + + + ScriptRunningRequestLastStop? + 腳本仍在運行中,是否終止上一個腳本再執行? + ScriptSettingDialog @@ -4399,37 +4428,37 @@ ScriptingConsole - + [Info] 【資訊】 - + [Warn] 【警告】 - + [Error] 【錯誤】 - + [Console] 【控制臺】 - + Copy 複製 - + Cut 剪切 - + Paste 粘貼 @@ -5343,7 +5372,7 @@ asDebugger - + {no engine} {無引擎} diff --git a/src/class/appmanager.cpp b/src/class/appmanager.cpp index 6a22dbe..5beecd6 100644 --- a/src/class/appmanager.cpp +++ b/src/class/appmanager.cpp @@ -45,6 +45,8 @@ AppManager::AppManager(int &argc, char *argv[]) : QtSingleApplication(argc, argv) { ASSERT_SINGLETON; + _instance = this; + LanguageManager::instance(); InspectQtLogHelper::instance().init(); CrashHandler::instance().init(); @@ -102,6 +104,8 @@ AppManager::AppManager(int &argc, char *argv[]) his.add(cmd); } + _timer.start(); + _w = new MainWindow(splash); setActivationWindow(_w); @@ -133,7 +137,6 @@ AppManager::AppManager(int &argc, char *argv[]) connect(_w, &MainWindow::closed, this, []() { AppManager::instance()->exit(); }); - _instance = this; if (splash) splash->close(); @@ -152,6 +155,8 @@ AppManager *AppManager::instance() { return _instance; } MainWindow *AppManager::mainWindow() const { return _w; } +uint AppManager::currentMSecsSinceEpoch() { return _timer.elapsed(); } + void AppManager::openFile(const QString &file, bool autoDetect) { EditorView *editor = nullptr; Q_ASSERT(_w); diff --git a/src/class/appmanager.h b/src/class/appmanager.h index 13ca968..d1a9532 100644 --- a/src/class/appmanager.h +++ b/src/class/appmanager.h @@ -21,6 +21,8 @@ #include "dialog/mainwindow.h" #include "qtsingleapplication/src/qtsingleapplication.h" +#include + class AppManager : public QtSingleApplication { Q_OBJECT public: @@ -36,6 +38,8 @@ public: QApplication::tr("WingCloudStudio"); } + uint currentMSecsSinceEpoch(); + public slots: void openFile(const QString &file, bool autoDetect = true); void openRawFile(const QString &file); @@ -43,6 +47,8 @@ public slots: private: MainWindow *_w = nullptr; + QElapsedTimer _timer; + static AppManager *_instance; }; diff --git a/src/class/ascompletion.cpp b/src/class/ascompletion.cpp index 868c42b..82a50b7 100644 --- a/src/class/ascompletion.cpp +++ b/src/class/ascompletion.cpp @@ -25,6 +25,7 @@ #include "wingcodeedit.h" #include +#include #include #include #include @@ -41,8 +42,7 @@ Q_GLOBAL_STATIC_WITH_ARGS(QByteArray, LEFT_PARE_TRIGGER, ("(")) Q_GLOBAL_STATIC_WITH_ARGS(QByteArray, SEMI_COLON_TRIGGER, (";")) AsCompletion::AsCompletion(WingCodeEdit *p) - : WingCompleter(p), parser(ScriptMachine::instance().engine()), - m_parseDocument(true) { + : WingCompleter(p), parser(ScriptMachine::instance().engine()) { setTriggerList({*DOT_TRIGGER, *DBL_COLON_TRIGGER, // unleash the power of call tips *LEFT_PARE_TRIGGER, @@ -126,10 +126,43 @@ void AsCompletion::applyClassNodes(QList &nodes) { nodes = clsNodes; } -bool AsCompletion::parseDocument() const { return m_parseDocument; } +int AsCompletion::includeCallBack(const QString &include, bool quotedInclude, + const QString &from, AsPreprocesser *builder, + void *userParam) { + Q_UNUSED(userParam); -void AsCompletion::setParseDocument(bool newParseDocument) { - m_parseDocument = newParseDocument; + QFileInfo info(include); + bool isAbsolute = info.isAbsolute(); + bool hasNoExt = info.suffix().isEmpty(); + QString inc; + if (quotedInclude) { + if (isAbsolute) { + inc = include; + } else { + auto pwd = QFileInfo(from).absoluteDir(); + inc = pwd.absoluteFilePath(include); + } + } else { + // absolute include is not allowed in #include<> + if (isAbsolute) { + // ignored in code completion + return asSUCCESS; + } + + QDir dir(qApp->applicationDirPath()); + if (!dir.cd(QStringLiteral("aslib"))) { + // someone crash the software, ignored + return asSUCCESS; + } + inc = dir.absoluteFilePath(include); + } + + if (hasNoExt) { + inc += QStringLiteral(".as"); + } + + builder->loadSectionFromFile(inc); + return asSUCCESS; } void AsCompletion::clearFunctionTip() { emit onFunctionTip({}); } @@ -235,10 +268,7 @@ bool AsCompletion::processTrigger(const QString &trigger, return true; } - QList docNodes; - if (m_parseDocument) { - docNodes = parseDocument(); - } + QList docNodes = parseDocument(); // if trigger is empty, it's making editing if (trigger.isEmpty()) { @@ -383,8 +413,7 @@ QList AsCompletion::parseDocument() { // first preprocess the code AsPreprocesser prepc(engine); - // TODO: set include callback - // prepc.setIncludeCallback(); + prepc.setIncludeCallback(&AsCompletion::includeCallBack, this); auto r = prepc.loadSectionFromMemory(QStringLiteral("ASCOMPLETION"), code.toUtf8()); @@ -396,99 +425,109 @@ QList AsCompletion::parseDocument() { QList ret; for (auto &d : data) { - QAsCodeParser parser(engine); - auto syms = - parser.parseAndIntell(editor->textCursor().position(), d.script); - - for (auto &sym : syms) { - CodeInfoTip tip; - tip.name = sym.name; - tip.nameSpace = QString::fromUtf8(sym.scope.join("::")); - - switch (sym.symtype) { - case QAsCodeParser::SymbolType::Function: - case QAsCodeParser::SymbolType::FnDef: - tip.type = CodeInfoTip::Type::Function; - tip.addinfo.insert(CodeInfoTip::RetType, - QString::fromUtf8(sym.type)); - tip.addinfo.insert(CodeInfoTip::Args, - QString::fromUtf8(sym.additonalInfo)); - for (auto &var : sym.children) { - CodeInfoTip va; - va.dontAddGlobal = true; - va.name = var.name; - va.nameSpace = QString::fromUtf8(var.scope.join("::")); - va.addinfo.insert(CodeInfoTip::RetType, var.type); - va.type = CodeInfoTip::Type::Variable; - ret.append(va); - } - break; - case QAsCodeParser::SymbolType::Enum: - tip.type = CodeInfoTip::Type::Enum; - for (auto &e : sym.children) { - CodeInfoTip en; - en.dontAddGlobal = true; - en.name = e.name; - en.nameSpace = QString::fromUtf8(e.scope.join("::")); - en.type = CodeInfoTip::Type::Enumerater; - if (!e.additonalInfo.isEmpty()) { - en.addinfo.insert(CodeInfoTip::Comment, - en.name + QStringLiteral(" = ") + - e.additonalInfo); - } - ret.append(en); - } - break; - case QAsCodeParser::SymbolType::TypeDef: - tip.type = CodeInfoTip::Type::TypeDef; - break; - case QAsCodeParser::SymbolType::Variable: - tip.addinfo.insert(CodeInfoTip::RetType, sym.type); - tip.type = CodeInfoTip::Type::Variable; - break; - case QAsCodeParser::SymbolType::Class: - case QAsCodeParser::SymbolType::Interface: - for (auto &mem : sym.children) { - if (mem.vis != QAsCodeParser::Visiblity::Public) { - continue; - } - CodeInfoTip ctip; - ctip.name = mem.name; - ctip.nameSpace = QString::fromUtf8(mem.scope.join("::")); - if (mem.symtype == QAsCodeParser::SymbolType::Function) { - ctip.type = CodeInfoTip::Type::Function; - ctip.addinfo.insert(CodeInfoTip::RetType, - QString::fromUtf8(mem.type)); - ctip.addinfo.insert( - CodeInfoTip::Args, - QString::fromUtf8(mem.additonalInfo)); - for (auto &var : mem.children) { - CodeInfoTip va; - va.dontAddGlobal = true; - va.name = var.name; - va.nameSpace = - QString::fromUtf8(var.scope.join("::")); - va.addinfo.insert(CodeInfoTip::RetType, var.type); - va.type = CodeInfoTip::Type::Variable; - tip.children.append(va); - } - tip.children.append(ctip); - } else if (mem.symtype == - QAsCodeParser::SymbolType::Variable) { - ctip.addinfo.insert(CodeInfoTip::RetType, mem.type); - ctip.type = CodeInfoTip::Type::Variable; - tip.children.append(ctip); - } - } - tip.type = CodeInfoTip::Type::Class; - break; - case QAsCodeParser::SymbolType::Invalid: - case QAsCodeParser::SymbolType::Import: - continue; - } - - ret.append(tip); + qsizetype offset = -1; + if (d.section == QStringLiteral("ASCOMPLETION")) { + offset = editor->textCursor().position(); } + ret.append(parseScriptData(offset, d.script)); + } + + return ret; +} + +QList AsCompletion::parseScriptData(qsizetype offset, + const QByteArray &code) { + QList ret; + + auto engine = ScriptMachine::instance().engine(); + QAsCodeParser parser(engine); + auto syms = parser.parseAndIntell(offset, code); + + for (auto &sym : syms) { + CodeInfoTip tip; + tip.name = sym.name; + tip.nameSpace = QString::fromUtf8(sym.scope.join("::")); + + switch (sym.symtype) { + case QAsCodeParser::SymbolType::Function: + case QAsCodeParser::SymbolType::FnDef: + tip.type = CodeInfoTip::Type::Function; + tip.addinfo.insert(CodeInfoTip::RetType, + QString::fromUtf8(sym.type)); + tip.addinfo.insert(CodeInfoTip::Args, + QString::fromUtf8(sym.additonalInfo)); + for (auto &var : sym.children) { + CodeInfoTip va; + va.dontAddGlobal = true; + va.name = var.name; + va.nameSpace = QString::fromUtf8(var.scope.join("::")); + va.addinfo.insert(CodeInfoTip::RetType, var.type); + va.type = CodeInfoTip::Type::Variable; + ret.append(va); + } + break; + case QAsCodeParser::SymbolType::Enum: + tip.type = CodeInfoTip::Type::Enum; + for (auto &e : sym.children) { + CodeInfoTip en; + en.dontAddGlobal = true; + en.name = e.name; + en.nameSpace = QString::fromUtf8(e.scope.join("::")); + en.type = CodeInfoTip::Type::Enumerater; + if (!e.additonalInfo.isEmpty()) { + en.addinfo.insert(CodeInfoTip::Comment, + en.name + QStringLiteral(" = ") + + e.additonalInfo); + } + ret.append(en); + } + break; + case QAsCodeParser::SymbolType::TypeDef: + tip.type = CodeInfoTip::Type::TypeDef; + break; + case QAsCodeParser::SymbolType::Variable: + tip.addinfo.insert(CodeInfoTip::RetType, sym.type); + tip.type = CodeInfoTip::Type::Variable; + break; + case QAsCodeParser::SymbolType::Class: + case QAsCodeParser::SymbolType::Interface: + for (auto &mem : sym.children) { + if (mem.vis != QAsCodeParser::Visiblity::Public) { + continue; + } + CodeInfoTip ctip; + ctip.name = mem.name; + ctip.nameSpace = QString::fromUtf8(mem.scope.join("::")); + if (mem.symtype == QAsCodeParser::SymbolType::Function) { + ctip.type = CodeInfoTip::Type::Function; + ctip.addinfo.insert(CodeInfoTip::RetType, + QString::fromUtf8(mem.type)); + ctip.addinfo.insert(CodeInfoTip::Args, + QString::fromUtf8(mem.additonalInfo)); + for (auto &var : mem.children) { + CodeInfoTip va; + va.dontAddGlobal = true; + va.name = var.name; + va.nameSpace = QString::fromUtf8(var.scope.join("::")); + va.addinfo.insert(CodeInfoTip::RetType, var.type); + va.type = CodeInfoTip::Type::Variable; + tip.children.append(va); + } + tip.children.append(ctip); + } else if (mem.symtype == QAsCodeParser::SymbolType::Variable) { + ctip.addinfo.insert(CodeInfoTip::RetType, mem.type); + ctip.type = CodeInfoTip::Type::Variable; + tip.children.append(ctip); + } + } + tip.type = CodeInfoTip::Type::Class; + break; + case QAsCodeParser::SymbolType::Invalid: + case QAsCodeParser::SymbolType::Import: + continue; + } + + ret.append(tip); } return ret; diff --git a/src/class/ascompletion.h b/src/class/ascompletion.h index a79c8c6..e92b2b8 100644 --- a/src/class/ascompletion.h +++ b/src/class/ascompletion.h @@ -21,6 +21,8 @@ #include "WingCodeEdit/wingcompleter.h" #include "class/asdatabase.h" +class AsPreprocesser; + class AsCompletion : public WingCompleter { Q_OBJECT public: @@ -32,9 +34,6 @@ public: public: virtual QString wordSeperators() const override; - bool parseDocument() const; - void setParseDocument(bool newParseDocument); - void clearFunctionTip(); protected: @@ -43,6 +42,9 @@ protected: virtual QList parseDocument(); + QList parseScriptData(qsizetype offset, + const QByteArray &code); + signals: void onFunctionTip(const QString &content); @@ -55,9 +57,13 @@ private: const QList &docNodes); void applyClassNodes(QList &nodes); +private: + static int includeCallBack(const QString &include, bool quotedInclude, + const QString &from, AsPreprocesser *builder, + void *userParam); + private: ASDataBase parser; - bool m_parseDocument; }; #endif // _CPP_COMPLETION_H_ diff --git a/src/class/asconsolecompletion.cpp b/src/class/asconsolecompletion.cpp index e2e1b03..3e473bf 100644 --- a/src/class/asconsolecompletion.cpp +++ b/src/class/asconsolecompletion.cpp @@ -17,9 +17,46 @@ #include "asconsolecompletion.h" +#include "class/qascodeparser.h" #include "control/scriptingconsole.h" AsConsoleCompletion::AsConsoleCompletion(ScriptingConsole *p) - : AsCompletion(p), _console(p) { - setParseDocument(false); + : AsCompletion(p), _console(p) {} + +QList AsConsoleCompletion::parseDocument() { + auto editor = _console; + if (editor == nullptr) { + return {}; + } + + auto code = editor->currentCodes(); + auto engine = ScriptMachine::instance().engine(); + + QAsCodeParser parser(engine); + auto seg = parser.parse(code.toUtf8()); + if (std::find_if(seg.begin(), seg.end(), + [](const QAsCodeParser::CodeSegment &seg) { + return seg.isValid(); + }) == seg.end()) { + // wrap it to let code-completion work + code.prepend("void main(){").append('}'); + } + + // first preprocess the code + AsPreprocesser prepc(engine); + + // including is not supported in console + auto r = prepc.loadSectionFromMemory(QStringLiteral("ASConCOMPLETION"), + code.toUtf8()); + if (r <= 0) { + return {}; + } + + auto data = prepc.scriptData(); + if (data.size() == 1) { + auto d = data[0]; + return parseScriptData(d.script.length() - 1, d.script); + } else { + return {}; + } } diff --git a/src/class/asconsolecompletion.h b/src/class/asconsolecompletion.h index f0f6132..2cddd80 100644 --- a/src/class/asconsolecompletion.h +++ b/src/class/asconsolecompletion.h @@ -28,6 +28,9 @@ public: explicit AsConsoleCompletion(ScriptingConsole *p); virtual ~AsConsoleCompletion() = default; +protected: + virtual QList parseDocument(); + private: ScriptingConsole *_console; }; diff --git a/src/class/ascontextmgr.cpp b/src/class/ascontextmgr.cpp deleted file mode 100644 index 7499de3..0000000 --- a/src/class/ascontextmgr.cpp +++ /dev/null @@ -1,41 +0,0 @@ -/*============================================================================== -** Copyright (C) 2024-2027 WingSummer -** -** This program is free software: you can redistribute it and/or modify it under -** the terms of the GNU Affero General Public License as published by the Free -** Software Foundation, version 3. -** -** This program is distributed in the hope that it will be useful, but WITHOUT -** ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS -** FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more -** details. -** -** You should have received a copy of the GNU Affero General Public License -** along with this program. If not, see . -** ============================================================================= -*/ - -#include "ascontextmgr.h" - -// copy from base class -struct SContextInfo { - asUINT sleepUntil; - std::vector coRoutines; - asUINT currentCoRoutine; - asIScriptContext *keepCtxAfterExecution; -}; - -asContextMgr::asContextMgr() : CContextMgr() {} - -bool asContextMgr::findThreadWithUserData(asPWORD index, void *data) const { - for (auto &th : m_threads) { - auto ctx = th->keepCtxAfterExecution; - if (ctx) { - auto user = ctx->GetUserData(index); - if (user == data) { - return true; - } - } - } - return false; -} diff --git a/src/class/ascontextmgr.h b/src/class/ascontextmgr.h deleted file mode 100644 index d798321..0000000 --- a/src/class/ascontextmgr.h +++ /dev/null @@ -1,30 +0,0 @@ -/*============================================================================== -** Copyright (C) 2024-2027 WingSummer -** -** This program is free software: you can redistribute it and/or modify it under -** the terms of the GNU Affero General Public License as published by the Free -** Software Foundation, version 3. -** -** This program is distributed in the hope that it will be useful, but WITHOUT -** ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS -** FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more -** details. -** -** You should have received a copy of the GNU Affero General Public License -** along with this program. If not, see . -** ============================================================================= -*/ - -#ifndef ASCONTEXTMGR_H -#define ASCONTEXTMGR_H - -#include "AngelScript/sdk/add_on/contextmgr/contextmgr.h" - -class asContextMgr : public CContextMgr { -public: - asContextMgr(); - - bool findThreadWithUserData(asPWORD index, void *data) const; -}; - -#endif // ASCONTEXTMGR_H diff --git a/src/class/asdebugger.cpp b/src/class/asdebugger.cpp index 24b32f7..5631ffb 100644 --- a/src/class/asdebugger.cpp +++ b/src/class/asdebugger.cpp @@ -71,6 +71,9 @@ void asDebugger::takeCommands(asIScriptContext *ctx) { void asDebugger::lineCallback(asIScriptContext *ctx) { Q_ASSERT(ctx); + // prevent UI freezing + qApp->processEvents(); + // This should never happen, but it doesn't hurt to validate it if (ctx == nullptr) return; diff --git a/src/class/ctypeparser.cpp b/src/class/ctypeparser.cpp index 22d23a1..287c84a 100644 --- a/src/class/ctypeparser.cpp +++ b/src/class/ctypeparser.cpp @@ -456,7 +456,7 @@ void CTypeParser::stripComments(QStringList &lines) const { QStringLiteral("]"); // search comment start - while ((pos = line.indexOf(kSlash, pos)) != -1) { + while ((pos = line.indexOf(char(kSlash), pos)) != -1) { if (line.length() <= pos + 1) break; // the 1st '/' is at the end of line, so not a comment @@ -1070,7 +1070,7 @@ bool CTypeParser::parseDeclaration(const QString &line, if (line.isEmpty()) { return false; } - if (line[line.length() - 1] != kSemicolon) + if (line[line.length() - 1] != char(kSemicolon)) return false; QStringList tokens; @@ -1090,7 +1090,7 @@ bool CTypeParser::parseDeclaration(const QString &line, return false; } - if (tokens[++index].at(0) == kAsterisk) { + if (tokens[++index].at(0) == char(kAsterisk)) { decl.is_pointer = true; // size of a pointer is 4 types on a 32-bit system length = @@ -1148,14 +1148,14 @@ bool CTypeParser::parseEnumDeclaration(const QString &line, int &last_value, break; case 2: - if (kComma != tokens[1].at(0)) { + if (char(kComma) != tokens[1].at(0)) { return false; } decl.second = ++last_value; break; case 3: - if (kEqual != tokens[1].at(0)) { + if (char(kEqual) != tokens[1].at(0)) { return false; } @@ -1171,7 +1171,8 @@ bool CTypeParser::parseEnumDeclaration(const QString &line, int &last_value, break; case 4: - if (!(kEqual == tokens[1].at(0) && kComma == tokens[3].at(0))) { + if (!(char(kEqual) == tokens[1].at(0) && + char(kComma) == tokens[3].at(0))) { return false; } @@ -1208,8 +1209,8 @@ bool CTypeParser::parseAssignExpression(const QString &line) { // only 4 tokens for an assignment expression: var = number; if (4 == splitLineIntoTokens(line, tokens) && - kEqual == tokens[1].at(tokens[1].length() - 1) && - kSemicolon == tokens[3].at(tokens[3].length() - 1) && + char(kEqual) == tokens[1].at(tokens[1].length() - 1) && + char(kSemicolon) == tokens[3].at(tokens[3].length() - 1) && isNumericToken(tokens[2], number)) { const_defs_.insert(tokens[0], number); return true; @@ -1244,7 +1245,7 @@ bool CTypeParser::parsePreProcDirective(const QString &src, qsizetype &pos) { } // only handle header file included with "" - if (kQuotation == token[token.length() - 1]) { + if (char(kQuotation) == token[token.length() - 1]) { // get included header file name if (!getNextToken(src, pos, token, false)) { return false; @@ -1371,7 +1372,7 @@ bool CTypeParser::parseStructUnion(const bool is_struct, const bool is_typedef, if (is_typedef) { // format 1 if (!(getNextToken(src, pos, next_token) && - kSemicolon == next_token.at(0))) { + char(kSemicolon) == next_token.at(0))) { return false; } @@ -1392,7 +1393,7 @@ bool CTypeParser::parseStructUnion(const bool is_struct, const bool is_typedef, type_maps_[type_name] = type_maps_[type_alias]; } } else { // non-typedef - if (kSemicolon == token.at(0)) { + if (char(kSemicolon) == token.at(0)) { // format 2 is_decl = false; if (type_name.isEmpty()) { @@ -1547,7 +1548,7 @@ bool CTypeParser::parseEnum(const bool is_typedef, const QString &src, if (is_typedef) { // format 1 if (!(getNextToken(src, pos, next_token) && - kSemicolon == next_token.at(0))) { + char(kSemicolon) == next_token.at(0))) { return false; } @@ -1564,7 +1565,7 @@ bool CTypeParser::parseEnum(const bool is_typedef, const QString &src, ; } } else { // non-typedef - if (kSemicolon == token.at(0)) { + if (char(kSemicolon) == token.at(0)) { // format 2 is_decl = false; if (type_name.isEmpty()) { diff --git a/src/class/qascodeparser.cpp b/src/class/qascodeparser.cpp index 0c34f32..fa6e183 100644 --- a/src/class/qascodeparser.cpp +++ b/src/class/qascodeparser.cpp @@ -1194,7 +1194,7 @@ QList QAsCodeParser::parseScript(bool inBlock) { seg.offset = begin; seg.scope = currentNs; seg.type = SymbolType::Variable; - seg.codes = _code.sliced(begin, end - begin + 1); + seg.codes = _code.sliced(begin, end - begin); rewindTo(&t1); segs.append(seg); diff --git a/src/class/scriptmachine.cpp b/src/class/scriptmachine.cpp index 15e3e38..bbbff08 100644 --- a/src/class/scriptmachine.cpp +++ b/src/class/scriptmachine.cpp @@ -29,6 +29,7 @@ #include "AngelScript/sdk/add_on/weakref/weakref.h" #include "angelobjstring.h" +#include "class/appmanager.h" #include "class/asbuilder.h" #include "class/pluginsystem.h" #include "class/qascodeparser.h" @@ -42,13 +43,7 @@ #include #include -ScriptMachine::~ScriptMachine() { - if (_ctxMgr) { - delete _ctxMgr; - } - - destoryMachine(); -} +ScriptMachine::~ScriptMachine() { destoryMachine(); } bool ScriptMachine::init() { if (isInited()) { @@ -74,9 +69,7 @@ bool ScriptMachine::init() { bool ScriptMachine::isInited() const { return _engine != nullptr; } bool ScriptMachine::isRunning(ConsoleMode mode) const { - return _ctxMgr->findThreadWithUserData( - AsUserDataType::UserData_ContextMode, - reinterpret_cast(asPWORD(mode))); + return _ctx.value(mode) != nullptr; } bool ScriptMachine::configureEngine() { @@ -171,9 +164,12 @@ bool ScriptMachine::configureEngine() { return false; } - // Setup the context manager and register the support for co-routines - _ctxMgr = new asContextMgr(); + _ctxMgr = new CContextMgr; _ctxMgr->RegisterCoRoutineSupport(_engine); + _ctxMgr->SetGetTimeCallback([]() -> asUINT { + return AppManager::instance()->currentMSecsSinceEpoch(); + }); + _ctxMgr->RegisterThreadSupport(_engine); // Tell the engine to use our context pool. This will also // allow us to debug internal script calls made by the engine @@ -227,6 +223,9 @@ QString ScriptMachine::getCallStack(asIScriptContext *context) { } void ScriptMachine::destoryMachine() { + _ctxMgr->AbortAll(); + delete _ctxMgr; + _debugger->setEngine(nullptr); _engine->ShutDownAndRelease(); _engine = nullptr; @@ -389,9 +388,10 @@ bool ScriptMachine::executeScript(ConsoleMode mode, const QString &script, outputMessage(mode, info); } - // Once we have the main function, we first need to initialize the global - // variables Since we've set up the request context callback we will be able - // to debug the initialization without passing in a pre-created context + // Once we have the main function, we first need to initialize the + // global variables Since we've set up the request context callback we + // will be able to debug the initialization without passing in a + // pre-created context r = mod->ResetGlobalVars(0); if (r < 0) { MessageInfo info; @@ -405,9 +405,11 @@ bool ScriptMachine::executeScript(ConsoleMode mode, const QString &script, // The context manager will request the context from the // pool, which will automatically attach the debugger asIScriptContext *ctx = _ctxMgr->AddContext(_engine, func, true); + _ctx[mode] = ctx; ctx->SetUserData(reinterpret_cast(isDbg), AsUserDataType::UserData_isDbg); + mod->SetUserData(reinterpret_cast(isDbg), AsUserDataType::UserData_isDbg); @@ -421,8 +423,11 @@ bool ScriptMachine::executeScript(ConsoleMode mode, const QString &script, // Execute the script until completion // The script may create co-routines. These will automatically // be managed by the context manager - while (_ctxMgr->ExecuteScripts()) - ; + while (_ctxMgr->ExecuteScripts()) { + qApp->processEvents(); + } + + _ctx[mode] = nullptr; // Check if the main script finished normally r = ctx->GetState(); @@ -479,13 +484,24 @@ bool ScriptMachine::executeScript(ConsoleMode mode, const QString &script, return r >= 0; } -void ScriptMachine::abortDbgScript(ConsoleMode mode) { +void ScriptMachine::abortDbgScript() { if (_debugger->getEngine()) { _debugger->runDebugAction(asDebugger::ABORT); } } -void ScriptMachine::abortScript() { _ctxMgr->AbortAll(); } +void ScriptMachine::abortScript(ConsoleMode mode) { + auto ctx = _ctx.value(mode, nullptr); + if (ctx) { + ctx->Abort(); + } +} + +void ScriptMachine::abortScript() { + abortScript(ConsoleMode::Interactive); + abortScript(ConsoleMode::Scripting); + abortScript(ConsoleMode::Background); +} void ScriptMachine::messageCallback(const asSMessageInfo *msg, void *param) { MessageType t = MessageType::Print; @@ -1805,16 +1821,6 @@ asDebugger *ScriptMachine::debugger() const { return _debugger; } bool ScriptMachine::executeCode(ConsoleMode mode, const QString &code) { asIScriptModule *mod = createModuleIfNotExist(mode); - - QScopeGuard guard([mod, mode]() { - if (mode != ConsoleMode::Interactive) { - // Before leaving, allow the engine to clean up remaining objects by - // discarding the module and doing a full garbage collection so that - // this can also be debugged if desired - mod->Discard(); - } - }); - _engine->SetEngineProperty(asEP_BUILD_WITHOUT_LINE_CUES, false); // first, preparse the code @@ -1824,28 +1830,30 @@ bool ScriptMachine::executeCode(ConsoleMode mode, const QString &code) { asIScriptFunction *func = nullptr; auto ret = parser.parse(ccode); + // check whether there is any enum/class if (std::find_if(ret.begin(), ret.end(), [](const QAsCodeParser::CodeSegment &seg) { - return seg.isValid(); - }) == ret.end()) { + switch (seg.type) { + case QAsCodeParser::SymbolType::Enum: + case QAsCodeParser::SymbolType::Class: + case QAsCodeParser::SymbolType::Function: + case QAsCodeParser::SymbolType::Interface: + case QAsCodeParser::SymbolType::Import: + case QAsCodeParser::SymbolType::Variable: + return false; + case QAsCodeParser::SymbolType::Invalid: + case QAsCodeParser::SymbolType::TypeDef: + case QAsCodeParser::SymbolType::FnDef: + return true; + } + return true; + }) != ret.end()) { // ok, wrap the codes - ccode.prepend("void main(){").append("}"); + ccode.prepend("void f(){").append("}"); // start to compile - auto r = mod->CompileFunction(nullptr, ccode, -1, 0, &func); - if (r < 0) { - MessageInfo info; - info.mode = mode; - info.message = tr("Script failed to build"); - info.type = MessageType::Error; - outputMessage(mode, info); - return false; - } - } else { - mod->AddScriptSection("Runner", ccode, ccode.size(), 0); - - auto r = mod->Build(); - if (r < 0) { + auto cr = mod->CompileFunction(nullptr, ccode, 0, 0, &func); + if (cr < 0) { MessageInfo info; info.mode = mode; info.message = tr("Script failed to build"); @@ -1854,85 +1862,98 @@ bool ScriptMachine::executeCode(ConsoleMode mode, const QString &code) { return false; } - // Find the main function - func = mod->GetFunctionByDecl("void main()"); - if (func == nullptr) { - // Try again with "int main()" - func = mod->GetFunctionByDecl("int main()"); + // Set up a context to execute the script + // The context manager will request the context from the + // pool, which will automatically attach the debugger + asIScriptContext *ctx = _ctxMgr->AddContext(_engine, func, true); + _ctx[mode] = ctx; + + asPWORD isDbg = 0; + ctx->SetUserData(reinterpret_cast(isDbg), + AsUserDataType::UserData_isDbg); + mod->SetUserData(reinterpret_cast(isDbg), + AsUserDataType::UserData_isDbg); + + asPWORD umode = asPWORD(mode); + ctx->SetUserData(reinterpret_cast(umode), + AsUserDataType::UserData_ContextMode); + + ctx->SetExceptionCallback(asMETHOD(ScriptMachine, exceptionCallback), + this, asCALL_THISCALL); + + // Execute the script until completion + // The script may create co-routines. These will automatically + // be managed by the context manager + while (_ctxMgr->ExecuteScripts()) { + qApp->processEvents(); } - if (func == nullptr) { - MessageInfo info; - info.mode = mode; - info.message = tr("Cannot find 'int main()' or 'void main()'"); - info.type = MessageType::Error; - outputMessage(mode, info); - return false; - } - } + _ctx[mode] = nullptr; - // Set up a context to execute the script - // The context manager will request the context from the - // pool, which will automatically attach the debugger - asIScriptContext *ctx = _ctxMgr->AddContext(_engine, func, true); - - asPWORD isDbg = 0; - ctx->SetUserData(reinterpret_cast(isDbg), - AsUserDataType::UserData_isDbg); - mod->SetUserData(reinterpret_cast(isDbg), - AsUserDataType::UserData_isDbg); - - asPWORD umode = asPWORD(mode); - ctx->SetUserData(reinterpret_cast(umode), - AsUserDataType::UserData_ContextMode); - - ctx->SetExceptionCallback(asMETHOD(ScriptMachine, exceptionCallback), this, - asCALL_THISCALL); - - // Execute the script until completion - // The script may create co-routines. These will automatically - // be managed by the context manager - while (_ctxMgr->ExecuteScripts()) - ; - - // Check if the main script finished normally - int r = ctx->GetState(); - if (r != asEXECUTION_FINISHED) { - if (r == asEXECUTION_EXCEPTION) { - MessageInfo info; - info.mode = mode; - info.message = tr("The script failed with an exception") + - QStringLiteral("\n") + - QString::fromStdString(GetExceptionInfo(ctx, true)); - info.type = MessageType::Error; - outputMessage(mode, info); - r = -1; - } else if (r == asEXECUTION_ABORTED) { - MessageInfo info; - info.mode = mode; - info.message = tr("The script was aborted"); - info.type = MessageType::Error; - outputMessage(mode, info); - r = -1; + // Check if the main script finished normally + int r = ctx->GetState(); + if (r != asEXECUTION_FINISHED) { + if (r == asEXECUTION_EXCEPTION) { + MessageInfo info; + info.mode = mode; + info.message = + tr("The script failed with an exception") + + QStringLiteral("\n") + + QString::fromStdString(GetExceptionInfo(ctx, true)); + info.type = MessageType::Error; + outputMessage(mode, info); + r = -1; + } else if (r == asEXECUTION_ABORTED) { + MessageInfo info; + info.mode = mode; + info.message = tr("The script was aborted"); + info.type = MessageType::Error; + outputMessage(mode, info); + r = -1; + } else { + auto e = QMetaEnum::fromType(); + MessageInfo info; + info.message = tr("The script terminated unexpectedly") + + QStringLiteral(" (") + e.valueToKey(r) + + QStringLiteral(")"); + info.type = MessageType::Error; + outputMessage(mode, info); + r = -1; + } } else { - auto e = QMetaEnum::fromType(); - MessageInfo info; - info.message = tr("The script terminated unexpectedly") + - QStringLiteral(" (") + e.valueToKey(r) + - QStringLiteral(")"); - info.type = MessageType::Error; - outputMessage(mode, info); - r = -1; + r = 0; } + + func->Release(); + + // Return the context after retrieving the return value + _ctxMgr->DoneWithContext(ctx); + _engine->GarbageCollect(); + + return r >= 0; } else { - r = 0; + if (ret.length() == 1) { + auto s = ret.first(); + if (s.type == QAsCodeParser::SymbolType::Variable) { + auto r = mod->CompileGlobalVar(nullptr, ccode, 0); + if (r < 0 || mod->ResetGlobalVars() < 0) { + MessageInfo info; + info.mode = mode; + info.message = tr("GlobalBadDecl"); + info.type = MessageType::Error; + outputMessage(mode, info); + return false; + } + return true; + } + } + MessageInfo info; + info.mode = mode; + info.message = tr("ScriptRunUnsupported"); + info.type = MessageType::Error; + outputMessage(mode, info); } - - // Return the context after retrieving the return value - _ctxMgr->DoneWithContext(ctx); - _engine->GarbageCollect(); - - return r >= 0; + return false; } QString ScriptMachine::scriptGetExceptionInfo() { diff --git a/src/class/scriptmachine.h b/src/class/scriptmachine.h index 4fd0f11..ca84464 100644 --- a/src/class/scriptmachine.h +++ b/src/class/scriptmachine.h @@ -18,13 +18,15 @@ #ifndef SCRIPTMACHINE_H #define SCRIPTMACHINE_H +#include "AngelScript/sdk/add_on/contextmgr/contextmgr.h" #include "AngelScript/sdk/angelscript/include/angelscript.h" + #include "class/aspreprocesser.h" #include "asdebugger.h" -#include "class/ascontextmgr.h" #include +#include class ScriptMachine : public QObject { Q_OBJECT @@ -97,7 +99,7 @@ private: explicit ScriptMachine(); Q_DISABLE_COPY_MOVE(ScriptMachine) -public: +private: asIScriptModule *createModule(ConsoleMode mode); asIScriptModule *createModuleIfNotExist(ConsoleMode mode); asIScriptModule *module(ConsoleMode mode); @@ -143,7 +145,8 @@ public slots: bool executeScript(ConsoleMode mode, const QString &script, bool isInDebug = false); - void abortDbgScript(ConsoleMode mode); + void abortDbgScript(); + void abortScript(ConsoleMode mode); void abortScript(); protected: @@ -196,11 +199,13 @@ signals: private: asIScriptEngine *_engine = nullptr; asDebugger *_debugger = nullptr; - asContextMgr *_ctxMgr = nullptr; - QVector _ctxPool; + CContextMgr *_ctxMgr = nullptr; + + QQueue _ctxPool; QVector _rtypes; QMap _regcalls; + QMap _ctx; ConsoleMode _curMode = ConsoleMode::Background; }; diff --git a/src/class/scriptmanager.cpp b/src/class/scriptmanager.cpp index e706b3b..79a6b76 100644 --- a/src/class/scriptmanager.cpp +++ b/src/class/scriptmanager.cpp @@ -250,16 +250,18 @@ ScriptManager::buildUpRibbonScriptRunner(RibbonButtonGroup *group) { } void ScriptManager::runScript(const QString &filename) { - // ScriptMachine::instance().executeScript(filename); + auto &ins = ScriptMachine::instance(); + if (ins.isRunning(ScriptMachine::Background)) { + auto ret = QMessageBox::question(nullptr, tr("ScriptRunning"), + tr("ScriptRunningRequestLastStop?")); + if (ret == QMessageBox::Yes) { + ins.abortScript(ScriptMachine::Background); + } else { + return; + } + } - // Q_ASSERT(_console); - // _console->setMode(ScriptingConsole::Output); - // _console->stdWarn(tr("Excuting:") + filename); - // _console->newLine(); - // // TODO - // // _console->machine()->executeScript(filename); - // _console->appendCommandPrompt(); - // _console->setMode(ScriptingConsole::Input); + ins.executeScript(ScriptMachine::Background, filename); } QStringList ScriptManager::usrScriptsDbCats() const { diff --git a/src/control/editorview.cpp b/src/control/editorview.cpp index 95b914d..7f43bc6 100644 --- a/src/control/editorview.cpp +++ b/src/control/editorview.cpp @@ -36,7 +36,7 @@ #include #endif -constexpr qsizetype FILE_MAX_BUFFER = 0x6400000; // 100MB +constexpr qsizetype FILE_MAX_BUFFER = 0x32000000; // 800MB constexpr auto CLONE_LIMIT = 3; constexpr auto VIEW_PROPERTY = "__VIEW__"; diff --git a/src/control/scriptingconsole.cpp b/src/control/scriptingconsole.cpp index 2ebbfa5..bcae3b0 100644 --- a/src/control/scriptingconsole.cpp +++ b/src/control/scriptingconsole.cpp @@ -17,7 +17,6 @@ #include "scriptingconsole.h" #include "QConsoleWidget/QConsoleIODevice.h" -#include "class/logger.h" #include "class/scriptmachine.h" #include "class/scriptsettings.h" #include "class/skinmanager.h" @@ -84,19 +83,15 @@ void ScriptingConsole::handleReturnKey() { if (iodevice_->isOpen()) iodevice_->consoleWidgetInput(code); - emit consoleCommand(code); + if (!_isWaitingRead) { + emit consoleCommand(code); + } } } void ScriptingConsole::init() { _getInputFn = std::bind(&ScriptingConsole::getInput, this); - // _sp = new ScriptConsoleMachine(_getInputFn, this); - // connect(_sp, &ScriptConsoleMachine::onClearConsole, this, - // &ScriptingConsole::clear); - // connect(this, &ScriptingConsole::abortEvaluation, _sp, - // &ScriptConsoleMachine::abortScript); - connect(this, &QConsoleWidget::consoleCommand, this, &ScriptingConsole::runConsoleCommand); @@ -177,7 +172,7 @@ void ScriptingConsole::onOutput(const ScriptMachine::MessageInfo &message) { flush(); break; case ScriptMachine::MessageType::Print: - if (lastInfo.first != message.type) { + if (lastInfo.first != message.type && isNotBlockStart) { newLine(); } stdOut(message.message); @@ -219,7 +214,13 @@ void ScriptingConsole::applyScriptSettings() { void ScriptingConsole::runConsoleCommand(const QString &code) { auto exec = code.trimmed(); - if (exec.endsWith('\\')) { + if (exec == QStringLiteral("#ls")) { + + } else if (exec == QStringLiteral("#del")) { + + } else if (exec == QStringLiteral("#cls")) { + + } else if (exec.endsWith('\\')) { static QRegularExpression ex(QStringLiteral("[\\\\\\s]+$")); _codes += exec.remove(ex); setMode(Output); @@ -228,10 +229,8 @@ void ScriptingConsole::runConsoleCommand(const QString &code) { } else { setMode(Output); _codes += exec; - if (!ScriptMachine::instance().executeCode(ScriptMachine::Interactive, - _codes)) { - // WingMessageBox:: - } + ScriptMachine::instance().executeCode(ScriptMachine::Interactive, + _codes); _codes.clear(); appendCommandPrompt(); setMode(Input); @@ -239,11 +238,18 @@ void ScriptingConsole::runConsoleCommand(const QString &code) { } QString ScriptingConsole::getInput() { + auto &s = consoleStream(); appendCommandPrompt(true); setMode(Input); - consoleStream().device()->waitForReadyRead(-1); + s.status(); + auto d = s.device(); + auto ba = d->bytesAvailable(); + d->skip(ba); + _isWaitingRead = true; + d->waitForReadyRead(-1); QString instr; - consoleStream() >> instr; + s >> instr; + _isWaitingRead = false; setMode(Output); return instr; } diff --git a/src/control/scriptingconsole.h b/src/control/scriptingconsole.h index 013acc2..dad4614 100644 --- a/src/control/scriptingconsole.h +++ b/src/control/scriptingconsole.h @@ -68,6 +68,7 @@ protected slots: private: QString _codes; + bool _isWaitingRead = false; std::function _getInputFn; }; diff --git a/src/define.h b/src/define.h index 43b78ad..17e5f61 100644 --- a/src/define.h +++ b/src/define.h @@ -5,6 +5,7 @@ enum class CrashCode : int { AlreadyStart, LanguageFile, PluginSetting, + ScriptInitFailed, GenericCallNotSupported }; diff --git a/src/dialog/mainwindow.cpp b/src/dialog/mainwindow.cpp index 7648947..d937e20 100644 --- a/src/dialog/mainwindow.cpp +++ b/src/dialog/mainwindow.cpp @@ -40,6 +40,7 @@ #include "class/wingmessagebox.h" #include "class/wingupdater.h" #include "control/toast.h" +#include "define.h" #include "encodingdialog.h" #include "fileinfodialog.h" #include "finddialog.h" @@ -254,7 +255,11 @@ MainWindow::MainWindow(SplashDialog *splash) : FramelessMainWindow() { std::placeholders::_1); sm.registerCallBack(ScriptMachine::Background, callbacks); } else { - // TODO + QMessageBox::critical(this, qAppName(), + tr("ScriptEngineInitFailed")); + set.setScriptEnabled(false); + set.save(SettingManager::SCRIPT); + throw CrashCode::ScriptInitFailed; } // At this time, AngelScript service plugin has started @@ -1011,6 +1016,10 @@ MainWindow::buildUpScriptConsoleDock(ads::CDockManager *dock, showStatus(QStringLiteral("") + content + QStringLiteral("")); }); + connect( + m_scriptConsole, &ScriptingConsole::abortEvaluation, this, [this]() { + ScriptMachine::instance().abortScript(ScriptMachine::Interactive); + }); auto dw = buildDockWidget(dock, QStringLiteral("ScriptConsole"), tr("ScriptConsole"), m_scriptConsole); @@ -3167,16 +3176,29 @@ void MainWindow::connectEditorView(EditorView *editor) { editor->setProperty("__RELOAD__", false); connect(editor, &EditorView::need2Reload, this, [editor, this]() { if (editor->isBigFile()) { - editor->reload(); - } - if (currentEditor() == editor) { - auto ret = WingMessageBox::question(this, tr("Reload"), - tr("ReloadNeededYesOrNo")); - if (ret == QMessageBox::Yes) { + auto fileName = editor->fileName(); + if (!QFile::exists(fileName)) { + editor->raise(); + WingMessageBox::critical(this, tr("Error"), + tr("FileCloseBigFile")); + closeEditor(editor, true); + } + if (currentEditor() == editor) { editor->reload(); + } else { + editor->setProperty("__RELOAD__", true); } } else { - editor->setProperty("__RELOAD__", true); + editor->hexEditor()->document()->setDocSaved(false); + if (currentEditor() == editor) { + auto ret = WingMessageBox::question(this, tr("Reload"), + tr("ReloadNeededYesOrNo")); + if (ret == QMessageBox::Yes) { + editor->reload(); + } + } else { + editor->setProperty("__RELOAD__", true); + } } }); } @@ -3207,10 +3229,14 @@ void MainWindow::swapEditor(EditorView *old, EditorView *cur) { auto hexeditor = cur->hexEditor(); auto needReload = cur->property("__RELOAD__").toBool(); if (needReload) { - auto ret = WingMessageBox::question(this, tr("Reload"), - tr("ReloadNeededYesOrNo")); - if (ret == QMessageBox::Yes) { + if (cur->isBigFile()) { cur->reload(); + } else { + auto ret = WingMessageBox::question(this, tr("Reload"), + tr("ReloadNeededYesOrNo")); + if (ret == QMessageBox::Yes) { + cur->reload(); + } } cur->setProperty("__RELOAD__", false); }